简体   繁体   中英

How to map JSON field to POCO using Automapper

Is it possible to create mapping between POCO and JSON field using Automapper?

public class SomeObjectEntity
{
    //JSON
    public string TaskData { get; set; }
    public GUID Id { get; set; }
    public DateTime CreateTime { get; set; }
}

public class SomeObjectModel
{
    public string Name { get; set; }
    public string[] Emails { get; set; }
    public GUID Id { get; set; }
    public DateTime CreateTime { get; set; }
}

In TaskData i have this JSON string:

@"
{
    ""Name"": ""Denis"",
    ""EMails"": [
        ""someemail1@email.com"",
        ""someemail2@email.com""
    ]
}"

Is there any way to create map?

protected override void Configure()
{
    Mapper.CreateMap<SomeObjectEntity, SomeObjectModel>() ...

    Mapper.CreateMap<SomeObjectModel, SomeObjectEntity>() ...
}

Thanks.

From the code above, I see you want to turn the Name + Emails properties from the SomeObjectModel class and turn these into a JSON string and map this to the SomeObjectEntity.TaskData string property. This can be accomplished using a custom AutoMapper ValueResolver.

public class NameAndEmailResolver : ValueResolver<SomeObjectModel, string>
{
    protected override string ResolveCore(SomeObjectModel source)
    {
        // need a quick and dirty list so we can perform linq query to isolate properties and return an anonymous type
        var list = new List<SomeObjectModel>(){source};
        return JsonConvert.SerializeObject(list.Select(x => new{x.Name, x.Emails});
    }
}

And then call your mapper code:

Mapper.CreateMap<SomeObjectEntity, SomeObjectModel>()
    .ForMember(x => x.TaskData, map => map.ResolveUsing<NameAndEmailResolver>());

This is only for one way binding. You'll have to write the code to go the opposite direction: SomeObjectModel --> SomeObjectEntity.

As mentioned by Jeroen, you need to first deserialize your json string to its corresponding type. And to do that, you can use the following. Assuming your type corresponding to the json is T, the following will deserialize it and gives you an object you can use it to map.

private async Task<T> ParseJsonToObjectAsync(string jsonValue)
{
    var obj = await Task.Factory.StartNew(()=>JsonConvert.DeserializeObject<T>(jsonValue);
    return obj;
}

You can also use http://json2csharp.com/ to help you generate the type corresponding your json string. It will save you time. If SomeObjectEntity or TaskData in your description is the object representation of your json string, then that is what T is.

Once you have the json deserialized, you can either manually map or use https://github.com/AutoMapper/AutoMapper

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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