Dapper MultiMap не работает с splitOn со значением NULL
У меня проблема с MultiMaps в dapper, пытаясь разделить на столбец, содержащий NULL
. Кажется, что Dapper не создает экземпляр объекта, и моя функция сопоставления получает NULL
вместо объекта.
Здесь мое новое испытание:
class Product
{
public int Id { get; set; }
public string Name { get; set; }
public Category Category { get; set; }
}
class Category
{
public int Id { get; set; }
public string Name { get; set; }
public string Description { get; set; }
}
public void TestMultiMapWithSplitWithNullValue()
{
var sql = @"select 1 as id, 'abc' as name, NULL as description, 'def' as name";
var product = connection.Query<Product, Category, Product>(sql, (prod, cat) =>
{
prod.Category = cat;
return prod;
}, splitOn: "description").First();
// assertions
product.Id.IsEqualTo(1);
product.Name.IsEqualTo("abc");
product.Category.IsNotNull();
product.Category.Id.IsEqualTo(0);
product.Category.Name.IsEqualTo("def");
product.Category.Description.IsNull();
}
Неверная строка product.Category.IsNotNull();
из-за того, что cat
передана функции отображения NULL
.
Я также добавил этот метод в класс Assert:
public static void IsNotNull(this object obj)
{
if (obj == null)
{
throw new ApplicationException("Expected not null");
}
}
Ответы
Ответ 1
Это "по-дизайн", хотя я был бы готов пересмотреть его.
В частности, это поведение помогает левым объединениям. Возьмите это, например:
cnn.Query<Car,Driver>("select * from Cars c left join Drivers on c.Id = CarId",
(c,d) => {c.Driver = d; return c;})
Проблема заключается в том, что если мы разрешим создание "оверлея" объекта Driver
, каждый Car
будет иметь теги Driver
, в которых соединение завершилось неудачно.
Чтобы обойти, мы могли бы сканировать весь разбитый сегмент и обеспечить, чтобы ВСЕ значения были NULL
перед отображением объекта NULL
. Это будет иметь очень незначительное влияние на мультиформатор.
Чтобы обходной путь для вашего случая, вы можете вставить суррогатную колонку:
var sql = @"select 1 as id, 'abc' as name, '' as split,
NULL as description, 'def' as name";
var product = connection.Query<Product, Category, Product>(sql, (prod, cat) =>
{
prod.Category = cat;
return prod;
}, splitOn: "split").First();
Ответ 2
Для всех, кто хочет визуализации:
Dapper разбивается на последнее имя равного столбца:
![введите описание изображения здесь]()
Разрешить местоположение столбцов:
![введите описание изображения здесь]()
null проблема:
![введите описание изображения здесь]()
Помененный столбец null:
![введите описание изображения здесь]()
Сплитон на помощь:
![введите описание изображения здесь]()