gpt4 book ai didi

c# - 没有 setter 的 Entity Framework 核心属性

转载 作者:行者123 更新时间:2023-12-04 00:22:34 25 4
gpt4 key购买 nike

在我的 .net core 3.1 应用程序中,我想将属性封装在某个实体中:

public class Sample : AuditableEntity
{
public Sample(string name)
{
Name = name;
}

public int Id { get; }

public string Name { get; }
}

因此,当我想检查此类 Sample 是否已经存在时,我已经删除了所有公共(public) setter ,因此在我的代码中某处
_context.Samples.Any(r => r.Name == name)

该行导致错误: System.InvalidOperationException: 'No suitable constructor found for entity type 'Sample'. The following constructors had parameters that could not be bound to properties of the entity type: cannot bind 'name' in 'Sample(string name)'.' .

所以我添加了代码空构造器
public class Sample : AuditableEntity
{
public Sample() { } // Added empty constructor here

public Sample(string name)
{
Name = name;
}

public int Id { get; }

public string Name { get; }
}

现在该行导致错误: System.InvalidOperationException: 'The LINQ expression 'DbSet<Sample>
.Any(s => s.Name == __name_0)' could not be translated. Either rewrite the query in a form that can be translated, or switch to client evaluation explicitly by inserting a call to either AsEnumerable(), AsAsyncEnumerable(), ToList(), or ToListAsync(). See https://go.microsoft.com/fwlink/?linkid=2101038 for more information.'
.

但是如果我将私有(private)集添加到 Name (或公共(public))然后一切正常(即使没有空的构造函数)。
public class Sample : AuditableEntity
{
public Sample(string name)
{
Name = name;
}

public int Id { get; }

public string Name { get; private set; } // added setter, removed empty constructor
}

谁能解释我为什么需要这个setter,例如Id不需要那个setter。

最佳答案

这与 Farhad Jabiyev 在评论中提到的反射有关。
EF 找不到该属性,它是隐藏的。当你做到 private set , EF 可以通过反射访问它,所以一切正常。

这可以通过支持字段 https://docs.microsoft.com/en-us/ef/core/modeling/backing-field 来完成。

From link above: Backing fields allow EF to read and/or write to a field rather than a property. This can be useful when encapsulation in the class is being used to restrict the use of and/or enhance the semantics around access to the data by application code, but the value should be read from and/or written to the database without using those restrictions/enhancements.



这意味着您必须像这样通过流利的 API 将映射添加到您的支持字段。
modelBuilder.Entity<Sample >()
.Property(b => b.Name)
.HasField("_name"); // this would have to be the name of the backing field

要访问自动 Prop 的支持字段,您可以使用 this-> Is it possible to access backing fields behind auto-implemented properties?

我会自己添加它,这样会更容易。
所以我的课看起来像这样。 您将需要 以上的映射并且映射解决了我的属性(property)是私有(private)的问题。如果没有映射,这将失败。
public class Sample : AuditableEntity
{
private string _name; //now EF has access to this property with the Mapping added
public Sample(string name)
{
_name = name;
}

public int Id { get; }

public string Name => _name;
}

请看一下Lerman的方法-> https://www.youtube.com/watch?v=Z62cbp61Bb8&feature=youtu.be&t=1191

关于c# - 没有 setter 的 Entity Framework 核心属性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59520102/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com