此代码按预期工作:
ExhibitionName
属性根据字段的值来连接字段。
public partial class Client
{
public int Id { get; set; }
public int Reference { get; set; }
[StringLength(100)]
public string Name{ get; set; } = null!;
[StringLength(50)]
public string? Nickname{ get; set; }
public string ExhibitionName => (!String.IsNullOrWhiteSpace(Nickname) ? Nickname: Name) + " (" + Reference+ ")";
public DateOnly Added { get; set; }
// other properties
}
// db is the DbContext instance for Client.
db.Clients.Select(c => new { c.Id, c.ExhibitionName }).ToList();
但是,实体框架生成的 SQL 语句会返回表中的所有列,甚至是不相关的列,这是不可取的。
第二种选择是在模型映射中使用
HasComputedColumnSql
并通过数据库获得相同的结果。
还有第三种选择吗?
也就是说,因为在您当前的实现中,
ExhibitionName
未映射到数据库中的列。输出看起来像:
解决方案
您提到的解决方案之一是使用
HasComputedColumnSql
或 HasValueGenerator
要应用它,只需将您的属性更改为:
[JsonIgnore]
public string ExhibitionName { get; set; }
然后在
OnModelCreating
方法中添加:
modelBuilder.Entity<Client>().Property(x => x.ExhibitionName)
.HasValueGenerator<ExhibitionNameGenerator>();
最后一步是创建一个生成器,示例实现如下所示:
public class ExhibitionNameGenerator : ValueGenerator<string>
{
public override string Next(EntityEntry entry)
{
if(entry.Entity is Client clientEntity)
{
return (!String.IsNullOrWhiteSpace(clientEntity.Nickname) ? clientEntity.Nickname : clientEntity.Name) + " (" + clientEntity.Reference + ")";
}
// You need to handle this case here
return "";
}
public override bool GeneratesTemporaryValues => false;
}