我遇到了这个运行时异常
未为类型定义属性'System.String Name' “Microsoft.EntityFrameworkCore.Storage.ValueBuffer
当我尝试运行查询时。
我的模特关系如图:
这是我的模特课程:
public class Order : BaseObject
{
[Key, DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public int Id { get; set; }
public string OrderCode
{
get
{
return Constants.OrderCodePrefix + Id;
}
}
}
上课
OrderDetail
public class OrderDetail : BaseObject
{
[Key, DatabaseGenerated(DatabaseGeneratedOption.None)]
public Guid Id { get; set; }
public virtual Order Order { get; set; }
public virtual TrackTrace TrackTrace { get; set; }
}
TrackTrace
public class TrackTrace
{
[Key, DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public int TrackTraceId { get; set; }
public virtual List<TrackTraceStatus> TrackTraceStatus { get; set; }
public Guid OrderDetailId { get; set; }
[ForeignKey("OrderDetailId")]
public virtual OrderDetail OrderDetail { get; set; }
}
TrackStatus
public class TrackStatus
{
[Key, DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public int TrackStatusId { get; set; }
public string Name { get; set; }
public virtual List<TrackTraceStatus> TrackTraceStatus { get; set; }
}
TrackTraceStatus
public class TrackTraceStatus : BaseObject
{
public int TrackTraceId { get; set; }
public virtual TrackTrace TrackTrace { get; set; }
public int TrackStatusId { get; set; }
public virtual TrackStatus TrackStatus { get; set; }
}
public class OrderService : IOrderService
{
AuthContext _dbContext;
public OrderService(AuthContext context, ICommonDataService commonDataService)
{
_dbContext = context;
}
private IQueryable<Order> IncludeTrackingChildrent()
{
return _dbContext.Orders.AsNoTracking()
.Include(o => o.OrderDetails)
.ThenInclude(o => o.TrackTrace)
.ThenInclude(tr => tr.TrackTraceStatus)
.ThenInclude(ts => ts.TrackStatus)
.Where(o => o.OrderDetails.Any(m => !m.IsDeleted))
.Where(_ => !_.IsDeleted);
}
public async Task<BaseSearchResponse<Order>> Search(string trackStatus)
{
var response = new BaseSearchResponse<Order>();
var query = IncludeTrackingChildrent();
//search by tracking status
if (!string.IsNullOrEmpty(trackStatus))
{
query = query.Where(x => x.OrderDetails.Any(d => d.TrackTrace.TrackTraceStatus.Last().TrackStatus.Name == trackStatus));
}
response.Items = query.Skip(0).Take(30).ToList();
response.Total = response.Items.Count();
return response;
}
}
我已经切断了一些不必要的属性以简化它。 这是我进行查询的服务类:
Order
在我的系统中,OrderDetail
有多个OrderDetail
,每个TrackTrace
都有一个TrackTrace
表来跟踪投放状态,TrackStatus
是有1到5 Order
喜欢:Ordered,Delivering,ToOfficeA,ToOfficeB,ToCustomer。
查询目的是:获取具有任何OrderDetail
的{{1}},其中TrackTraceStatus
具有TrackStatus
的名称等于输入字符串。
当我尝试获取列表TrackTraceStatus
的元素时出现了问题,我尝试过Last()
LastOrDefault()
First()
FirstOrDefault()
或{{ 1}}。所有这些功能都给我错误。我不知道要上次 ElementAt()
检查其TrackTraceStatus
答案 0 :(得分:2)
除了EF Core翻译/处理错误(我的查询有不同的例外,但无论如何),从根本上你应该避免使用Last
函数并使用First
/ FirstOrDefault
/ Take(1)
在应用排序运算符之后,因为没有显式排序运算符,返回记录的顺序是未定义的,因此“first”,“last”等没有任何意义。
根据评论,目标是查找TrackStatus
的最后OrderDetail
(其中last表示最大TrackStatusId
的那个)并检查其名称是否与条件匹配。
第一部分可以通过“导航”到TrackStatus
记录,然后使用典型的“最后”OrderByDescending
+ FirstOrDefault
模式来实现。对于第二部分,在调用Select
之前只需FirstOrDefault
名称,然后将结果与所需名称进行比较:
query = query.Where(o => o.OrderDetails.Any(d => d.TrackTrace.TrackTraceStatus
.Select(tts => tts.TrackStatus)
.OrderByDescending(ts => ts.TrackStatusId)
.Select(ts => ts.Name)
.FirstOrDefault() == trackStatus));