Динамические типы возврата Dapper

Я использую dapper.net для сейчас, и это очень хороший ORM-конвертер, который отлично работает с динамическими типами .Net, но я заметил, что когда dapper извлекает данные из базы данных, он возвращается как тип строки Dapper, есть какой-либо способ, Я могу вернуть его в любом другом виде. Как System.Dynamic.ExpandoObject?

Ответы

Ответ 1

Объект DapperRow предназначен для совместного использования большого количества состояний между строками. Например, если вы извлекаете 40 строк, имена столбцов и т.д. Сохраняются только один раз. Если мы использовали ExpandoObject, это нужно было бы настроить для каждой строки. Следовательно, использование DapperRow в качестве детализации реализации за кадром является преднамеренной эффективностью.

Обратите внимание, что объект, возвращенный API-интерфейсом dynamic, также может быть отброшен как IDictionary<string,object>.

Однако я был бы открыт для поддержки других типов, которые поддерживают это использование словаря, из которых ExpandoObject является одним. Так что да, его можно было бы изменить так, чтобы:

var rows = conn.Query<ExpandoObject>(...);

работает. Он просто требует, чтобы код поддерживал его, и этот код в настоящее время не существует. Так что "нет, но, возможно, в будущем строить".

Обратите внимание, что вам вообще не нужно использовать DapperRow... Более ожидаемый сценарий - использовать общий API для материализации ваших собственных типов.

Ответ 2

Конечно!

В соответствии с документацией dapper используйте метод запроса и получите свои dymanics:

dynamic account = conn.Query<dynamic>(@"
                    SELECT Name, Address, Country
                    FROM Account
            WHERE Id = @Id", new { Id = Id }).FirstOrDefault();
Console.WriteLine(account.Name);
Console.WriteLine(account.Address);
Console.WriteLine(account.Country);

Как вы видите, вы получаете динамический объект, и вы можете получить доступ к его свойствам, если они хорошо определены в запросе.

Если вы опустите .FirstOrDefault(), вы получите IEnumerable<dynamic>, который вы можете делать с ним, как хотите.

Ответ 3

У меня есть эта проблема, и я решил таким образом!

Функция Query() возвращает коллекцию динамики, которая в действительности представляет собой типы объектов Dapper.SqlMapper.DapperRow. Dapper.SqlMapper.DapperRow является закрытым. Мне нужно было динамически добавлять свойства к объектам Dapper.SqlMapper.DapperRow, но это не работает. В результате я хотел преобразовать Dapper.SqlMapper.DapperRow в ExpandoObject.

Мне удалось создать этот общий вспомогательный метод, как показано ниже.

public class DapperHelpers
{
     public static dynamic ToExpandoObject(object value)
     {
         IDictionary<string, object> dapperRowProperties = value as IDictionary<string, object>;

         IDictionary<string, object> expando = new ExpandoObject();

         foreach (KeyValuePair<string, object> property in dapperRowProperties)
             expando.Add(property.Key, property.Value);

         return expando as ExpandoObject;
     }
}

Затем вы можете использовать это следующим образом:

IEnumerable<ExpandoObject> result = 
           db.SqlConn.Query(sqlScript)
               .Select(x=> (ExpandoObject)ToExpandoObject(x));

ссылка: проблемы с dapper-dot-net 166