我正在尝试将最小起订量集成到我的项目中,该项目将linq应用于实体-大部分情况下都可以按预期工作。我遇到的问题是当我投影到一个匿名对象时,该对象具有“ SQLizer”可以处理但MOQ引发异常的可空属性。
例如:
public class Person {
public int Id {get;set;}
public virtual void Car Car {get; set;}
}
public class Car {
public int Id {get;set;}
}
public class Context {
public DbSet<Car> Cars {get;set;}
public DbSet<Person> People {get;set;}
}
// Just to show we have a person in the db without a car
context.People.Add(new Person{
Id = 1,
});
// This throws an exception on MOQ, but works in SQL
context.People.Select(person => new {
personId = person.Id,
carId = (int?)person.Car.Id
});
我只想强调我遇到的问题,也许不是最佳的数据结构。关于如何处理的想法?最简单的方法是在投影之前检查null值,但我觉得可能有更好的选择。
答案 0 :(得分:1)
使用上下文添加新的Person
时,似乎跳过了添加Car
实例并稍后尝试访问它的情况:
context.People.Select(person => new {
personId = person.Id,
carId = (int?)person.Car.Id // above you instantiated a Person without a Car instance
});
这里发生的是,在投射新元素期间,Select
语句试图访问Car
实例,而该实例根本不存在。
但是,如果您要拥有Person
个实例,其中将不包含
Car
更改代码以匹配以下两种方法之一:
第一个选项(使用null-coalescing和null-conditional运算符)
context.People.Select(person => new {
personId = person.Id,
carId = person.Car?.Id ?? 0 // 0 is the default value in case if Person doesn't have Car
});
第二个选项使用过滤
context.People.Where(p => p.Car != null).Select(person => new {
personId = person.Id,
carId = person.Car.Id
});