#c# #automapper
#c# #automapper
Вопрос:
Вероятно, это простой ответ, но я только начинаю осваивать AutoMapper.
В любом случае, у меня есть объект домена, подобный этому:
public class User
{
public string Name { get; set; }
public FacebookUser FacebookUser { get; set; }
}
И ViewModel, подобный этому:
public class UserViewModel
{
public string Name { get; set; }
public long FacebookUniqueId { get; set; }
}
Вот что у меня есть в моей конфигурации AutoMapper:
Mapper.CreateMap<User,UserViewModel>()
.ForMember(dest => dest.FacebookUniqueId, opt => opt.MapFrom(src => src.FacebookUser.FacebookUniqueId))
Но оно выдает исключение, когда FacebookUser
объект равен null, чего и следовало ожидать.
Как мне сообщить AutoMapper:
Сопоставьте UserViewModel.FacebookUniqueId для пользователя.FacebookUser.FacebookUniqueId, за исключением случаев, когда оно равно null, затем используйте
0
.
Есть идеи?
Ответ №1:
opt => opt.MapFrom(src => src.FacebookUser == null ? 0 : src.FacebookUser.FacebookUniqueId)
Блин, если бы я только что проверил, сработала ли первая идея, подумал, что MapFrom
метод принимает только выражение, указывающее на свойство, чтобы разрешить его таким образом…
Комментарии:
1. Оно выдало ошибку object ref на
src.FacebookUser.FacebookUniqueId
, посколькуsrc.FacebookUser
равно null — не знаю, почему это не сработало для вас. В любом случае, добавление заменителя null сделало свое дело — ура!2. На самом деле, это все еще выдает ошибку — я думал, это сработало, потому что я выполнил сборку, и моя страница отрисовалась должным образом. Но когда я запустил его в режиме отладки, он снова выдал исключение в той же строке. Думаю, AutoMapper проглатывает исключения. Итак, я думаю, что этот конкретный оператор нуждается в проверке null — но как?
3. теперь это должно сработать. Сначала у меня было это, и я думал, что это не сработает, но, по-видимому, это так. Извините, я не протестировал это сначала.
4. да, это то, что я понял, проверка на нуль старой школы. Я надеялся, что у AutoMapper есть собственный интеллектуальный метод для этого. Ну что ж, это работает. Спасибо.
Ответ №2:
Предоставленный вами код работает в последней версии Automapper. Я немного изучил исходные тексты и нашел следующий код:
try
{
var result = _method((TSource)source.Value);
return source.New(result, MemberType);
}
catch (NullReferenceException)
{
return source.New(null, MemberType);
}
Как вы можете видеть теперь, Automapper улавливает все исключения Null при разрешении цепных сопоставлений. Следующий тест зеленого цвета:
[TestFixture]
public class AutomapperChainingMappingTest
{
[Test]
public void ChainMapping_NullProperty_DefaultValueSet()
{
AutoMapper.Mapper.CreateMap<User, UserViewModel>()
.ForMember(x => x.FacebookUniqueId, o => o.MapFrom(x => x.FacebookUser.FacebookUniqueId));
var source = new User();
var model = AutoMapper.Mapper.Map<UserViewModel>(source);
Assert.AreEqual(model.FacebookUniqueId, default(long));
}
}
public class User
{
public FacebookUser FacebookUser { get; set; }
}
public class UserViewModel
{
public long FacebookUniqueId { get; set; }
}
public class FacebookUser
{
public long? FacebookUniqueId { get; set; }
}