简体   繁体   English

我可以使用AutoMapper在两个不可变的字段之间进行映射吗?

[英]Can I use AutoMapper to map between two fields which are immutable?

I have the following two classes (many properties elided for brevity). 我有以下两个类(为简洁起见,省略了许多属性)。

Service Layer POCO: 服务层POCO:

public class TicketFlag
{
    public ContactKey ContactKey;
}

LINQ to SQL generated POCO: LINQ to SQL生成的POCO:

public class TicketFlag
{
    public string ContactKey;    
}

When trying to use AutoMapper to map between these two on service calls -> database save, I'm getting the following exception: 尝试使用AutoMapper在服务调用->数据库保存这两者之间映射时,出现以下异常:

Exception of type 'AutoMapper.AutoMapperMappingException' was thrown.
 ---> System.ArgumentException: Type 'ContactKey' does not have a default constructor

ContactKey does not have a default constructor on purpose. ContactKey没有故意的默认构造函数。 Basically, it takes a string and a list of objects and can serialize/deserialize itself. 基本上,它需要一个字符串和一个对象列表,并且可以对自身进行序列化/反序列化。

I have tried creating a mapping function (and it's inverse) like so: 我尝试过创建一个映射函数(它是相反的),如下所示:

Mapper.CreateMap<string, ContactKey>().ConvertUsing(s => ContactKeySerializer.Serialize(s));

But I'm still getting complaints because ContactKey doesn't have a default constructor. 但是我仍然在抱怨,因为ContactKey没有默认的构造函数。

Is there a way to get AutoMapper to not use the default constructor to do it's property mapping? 有没有一种方法可以使AutoMapper不使用默认构造函数进行属性映射? Really, just mapping properties on the ContactKey isn't sufficient - I need to have it call the constructor, or get spit out from my ContactKeySerializer class. 确实,仅在ContactKey上映射属性是不够的-我需要让它调用构造函数,或者从我的ContactKeySerializer类中吐出来。

First, you should probably be using properties for these things, not fields. 首先,您可能应该将属性用于这些东西,而不是字段。 However, I doubt that's part of your problem. 但是,我怀疑这是您的问题的一部分。

Instead of trying to create a map from string to ContactKey , you could try to make this part of the map from one TicketFlag to the other: 与其尝试创建从stringContactKey的映射, ContactKey尝试将这一部分从一个TicketFlag映射到另一个TicketFlag

Mapper.CreateMap<LINQtoSQL.TicketFlag, Service.Layer.TicketFlag>()
 .ForMember(dest => dest.ContactKey,
 mem => mem.ResolveUsing(src => ContactKeySerializer.Serialize(src.ContactKey)));

I think that would prevent the error you're getting. 我认为这样可以防止您遇到错误。

AutoMapper is complaining that you don't have a default constructor because AutoMapper needs to create an empty instance of the target class before it can map values to it. AutoMapper抱怨您没有默认的构造函数,因为AutoMapper需要先创建目标类的空实例,然后才能将值映射到它。 It can't call your ContractKey's parameterized constructor - how would it? 它无法调用您的ContractKey的参数化构造函数-它将如何?

In this case it might seem simple, if the constructor looks like this: 在这种情况下,如果构造函数如下所示,则看起来很简单:

public ContracktKey(string keyValue){}

But what if it had two parameters? 但是,如果有两个参数怎么办?

public ContracktKey(string keyValue, string otherValue){}

How would it know where to put the value? 它怎么知道将价值放在哪里? What if you only provided one string? 如果您只提供一个字符串怎么办?

I think it would be best to follow others' advice and map the two TicketFlag objects. 我认为最好听从别人的建议,并映射两个TicketFlag对象。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM