我正在使用C#构建ASP.NET MVC 2应用程序,并且我成功地使用Automapper在ViewModel和业务对象之间来回映射值。
除了几个显式属性之外,我的业务对象还将字典包装为一个catch all,用于未明确定义的属性。类似于:
public class MyBusinessObject {
public void SetExtraPropertyValue<T>(string key, T value) {
// ...
}
public T GetExtraPropertyValue<T>(string key, T defaultValue) {
// ...
}
}
在我的ViewModel中,我可以自由创建我想要的任何属性,但我无法修改业务对象。
所以我想说我创建了一个这样的视图模型:
class MyViewModel {
public string CustomProp { get; set; }
}
我想要存储和检索的值需要使用
businessModelInstance.SetExtraPropertyValue("CustomProp", newVal);
和
businessModelInstance.GetExtraPropertyValue("CustomProp");
我向两个方向都有问题 首先,当从MyBusinessObject转到MyViewModel时,我认为在我的自定义Automapper配置文件中应该很简单:
CreateMap<MyBusinessObject, MyViewModel>()
.ForMember(dest => dest.CustomProp,
opt => opt.MapFrom(s => s.GetExtraPropertyValue("CustomProp", "")));
但是,MyBusinessObject.CustomProp
永远不会填充,但其他属性也是如此
其次,我不知道如何配置从MyViewModel.CustomProp
获取值到调用MyBusinessObject.SetExtraPropertyValue
。
MyBusinessObject.SetExtraPropertyValue("CustomProp",
MyViewModel.CustomProp)
<小时/> 更新:以下是基于@Patrick Steele建议的解决方案: 我向视图模型属性添加了一个自定义属性,我希望将其映射到额外的属性键。自定义TypeConverter使用反射来正确查找这些属性和地图属性。
public class ItemExtraPropertyConverter : ITypeConverter<MyViewModel, MyBusinessObject>
{
public MyBusinessObject Convert(ResolutionContext context)
{
var destination = context.DestinationValue as MyBusinessObject;
if (destination == null )
throw new InvalidOperationException("Destination type is not of type MyBusinessObject");
foreach (var property in context.SourceType.GetProperties())
foreach (var attribute in property.GetCustomAttributes(true).OfType<ExtraPropertyAttribute>())
{
var key = attribute.Key;
if (string.IsNullOrEmpty(key))
key = property.Name;
destination.SetExtraPropertyValue(key, property.GetValue(context.SourceValue, null));
}
return destination;
}
}
public class ExtraPropertyAttribute : Attribute
{
public ExtraPropertyAttribute()
{
}
public ExtraPropertyAttribute(string key)
{
Key = key;
}
public string Key { get; set; }
}
public class MyViewModel
{
[ExtraProperty]
public string CustomProp { get; set; }
[ExtraProperty("OtherPropertyValue")]
public string CustomProp2 { get; set; }
}
在自定义配置文件类的配置方法中:
CreateMap<MyViewModel, MyBusinessObject>()
.ConvertUsing<ItemExtraPropertyConverter>();
答案 0 :(得分:0)
我的猜测是你的GetExtraPropertyValue和SetExtraPropertyValue实现有问题。我汇总了一个快速测试,你上面提供的映射按预期工作。这是我用于测试的实现:
public class MyBusinessObject
{
private readonly Dictionary<string, object> extraProperties = new Dictionary<string, object>();
public int Id { get; set; }
public string Name { get; set; }
public void SetExtraPropertyValue<T>(string key, T value)
{
extraProperties.Add(key, value);
}
public T GetExtraPropertyValue<T>(string key, T defaultValue)
{
if (extraProperties.ContainsKey(key))
{
return (T)extraProperties[key];
}
return defaultValue;
}
}