Сообщение об ошибке
Сообщение: System.InvalidOperationException: Mapper не инициализирован.Вызовите Initialize с соответствующей конфигурацией.Если вы пытаетесь использовать экземпляры mapper через контейнер или иным образом, убедитесь, что у вас нет вызовов статических методов Mapper.Map, и если вы используете методы расширения ProjectTo или UseAsDataSource, убедитесь, что вы передаете соответствующий IConfigurationProvider.instance.
Проект приложения
Определить профиль сопоставления ( ApplicationMappingProfile.cs )
public class ApplicationMappingProfile : Profile
{
public ApplicationMappingProfile()
{
CreateMap<User, UserListDto>();
CreateMap<Permission, PermissionListDto>();
// add auto mapper mapping configurations here
}
}
Зарегистрировать службы Autopper ()ApplicationServiceCollectionExtensions.cs )
public static class ApplicationServiceCollectionExtensions
{
public static IServiceCollection AddKodkodApplication(this IServiceCollection services)
{
services.AddAutoMapper();
//todo: add conventional registrar
services.AddTransient<IUserAppService, UserAppService>();
services.AddTransient<IPermissionAppService, PermissionAppService>();
return services;
}
}
Проект модульного тестирования
Создание тестового сервера для запуска Startup.cs ( ApiTestBase.cs )
public class ApiTestBase : TestBase
{
protected static HttpClient Client;
public ApiTestBase()
{
//if this is true, Automapper is throwing exception
ServiceCollectionExtensions.UseStaticRegistration = false;
Client = GetTestServer();
}
private static HttpClient GetTestServer()
{
if (Client != null)
{
return Client;
}
var server = new TestServer(
new WebHostBuilder()
.UseStartup<Startup>()
.ConfigureAppConfiguration(config =>
{
config.SetBasePath(Path.GetFullPath(@"../../.."));
config.AddJsonFile("appsettings.json", false);
})
);
return server.CreateClient();
}
}
И тест ( AccountTests.cs ).
public class AccountTests : ApiTestBase
{
[Fact]
public async Task TestAuthorizedAccessAsync()
{
var responseLogin = await LoginAsTestUserAsync();
var responseContent = await responseLogin.Content.ReadAsAsync<OkObjectResult>();
var responseJson = JObject.Parse(responseContent.Value.ToString());
var token = (string)responseJson["token"];
var requestMessage = new HttpRequestMessage(HttpMethod.Get, "/api/test/GetUsers/");
requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", token);
var responseGetUsers = await Client.SendAsync(requestMessage);
Assert.Equal(HttpStatusCode.OK, responseGetUsers.StatusCode);
var users = await responseGetUsers.Content.ReadAsAsync<PagedList<UserListDto>>();
Assert.True(users.Items.Count > 0);
}
}
Этот тестовый метод вызывает метод /api/test/GetUsers/
, который использует appservice (PermissionAppService.cs).Эта служба приложения возвращает dto, который сопоставлен с сущностью с использованием automapper.Так что здесь происходит исключение.
Когда я удалил следующую строку:
ServiceCollectionExtensions.UseStaticRegistration = false;
Тогда я получаю следующую ошибку:
Сообщение: System.InvalidOperationException: Mapperуже инициализирован.Вы должны вызывать Initialize один раз для домена / процесса приложения.
Эта ошибка происходит, поскольку существует несколько классов, унаследованных от класса ApiTestBase.Если я запускаю только метод TestAuthorizedAccessAsync, он запускается без проблем.
Вопрос может быть немного сложным, извините за это :), не стесняйтесь спрашивать, где вы не понимаете.
ИСТОЧНИК ПРОЕКТА
Редактировать
Работает, когда я запускаю проект веб-API, который использует appServices
Редактировать2
если я добавлю следующие строки в конструктор TestBase, только один тест не пройден, а другие пройдены.
public TestBase()
{
lock (ThisLock)
{
Mapper.Reset();
Client = GetTestServer();
}
....