Mapping doesn't await child using AfterMappingAsync (Async package)
When mapping objects using the Async package:
await _mapper.From(result).AdaptToTypeAsync<ParentDto>();
We see that the mapping is not complete when the result is already returned.
config.NewConfig<Parent, ParentDto>()
.Map(dest => dest.ParentDetailsInternal, src => src.ParentDetails)
.AfterMappingAsync(AfterMappingParentToDto)
;
config.NewConfig<ParentDetail, ParentDetailDto>()
.Include<ParentDetailSubType, ParentDetailSubTypeDto>()
.AfterMappingAsync(AfterMappingChildToDto)
;
It seems the .Map method is not expecting async methods further down the mapping chain. The AfterMappingAsync on the child is not yet finished.
Found a work-around for now by adding this in the AfterMappingSync method of the parent:
private async Task AfterMappingParentToDto(Parent source, ParentDto target)
{
// Wait for previous tasks to end to make sure all child mappings have finished.
var tasks = (List<Task>)MapContext.Current?.Parameters.GetValueOrDefault("Mapster.Async.tasks");
if(tasks != null && tasks.Any())
{
await Task.WhenAll(tasks);
}
But I don't like using the static name Mapster.Async.tasks directly. (That's not public btw, thank you open source)
I'll try to create a pull request on the async package.
Good catch there, looking forward to the PR. I will ensure it gets merged quickly and push a prerelease package for you.
Hi, I got to this thread while try to figure out if we should migrate from automapper to mapster. Basically the biggest motivation for us it async mappers. Does \ will it exist in mapster?
Thanks!