Базовая служба локализации ASP.NET Core 1.1
Я делаю приложение ASP.NET Core 1.1 и пытаюсь настроить локализацию.
Когда я делаю на моем ValuesController
реализация IStringLocalizer
он отлично работает и локализует мой файл ресурсов.
public ValuesController(IStringLocalizer<ValuesController> localizer, IService<BaseEntity> service)
{
_localizer = localizer;
_service = service;
}
Код выше найти мои ресурсы в "Resources/Controllers/ValuesController.en-US.resx".
Но когда я пытаюсь ввести IStringLocalizer
с общим сервисом он не может найти мой файл ресурсов.
public class Service<T> : IService<T>
where T : BaseEntity
{
#region Properties
protected IRepository Repository { get; set; }
protected IUnitOfWorkFactory UnitOfWorkFactory { get; set; }
private readonly ILogger _logger;
private readonly IStringLocalizer _localizer;
#endregion
#region Ctor
public Service(IRepository repository, IUnitOfWorkFactory unitOfWorkFactory,
ILogger<Service<T>> logger, IStringLocalizer<Service<T>> localizer)
{
Repository = repository;
UnitOfWorkFactory = unitOfWorkFactory;
_logger = logger;
_localizer = localizer;
}
}
Приведенный выше код не находит мой ресурс по адресу "Resources/Services/Base/Service.en-US.resx"
Есть идеи, как это сделать?
--- РЕДАКТИРОВАТЬ
MyControl.Api (Startup.cs)
Пространство имен MyControl.Api
services.AddLocalization(options => options.ResourcesPath = "Resources");
Эта строка находится внутри "MyControl.Api", а находится в пространстве имен "MyControl.Api".
Папка ресурсов в этой заявке работает для "Ресурсы / Контроллеры"
Мои сервисы находятся в пространстве имен "MyControl.Services"
Папка ресурсов в этом проекте (два проекта в одном решении)
"Ресурсы / Услуги /Base"
Пространство имен моего служебного файла - "MyControl.Services.Services.Base".
1 ответ
объяснение
Вы правы, проблема в общем классе. В соответствии с исходным кодом ResourceManagerStringLocalizer
(это по умолчанию IStringLocalizer
реализация) - этот класс содержит _resourceBaseName
личное поле. Эта же строка также используется для поиска файлов ресурсов в качестве параметра пути поиска в ResourceManager
учебный класс.
когда IStringLocalizer
вставляется в закрытый экземпляр универсального типа, это поле неправильно установлено с чем-то вроде:
FooProject.Resources.Services.FooService`1 [[System.Double, System.Private.CoreLib...
Вместо правильного:
FooProject.Resources.Services.FooService
Вы можете проверить локализатор _resourceBaseName
значение в отладчике. Вероятно, это ошибка, и вы могли бы открыть вопрос об этом на GitHub: https://github.com/aspnet/Localization/issues.
Временное решение
Можно создать ResourceManagerStringLocalizer
экземпляр вручную. Мы должны принять это baseName
часть из полного имени класса без имени csproj-файла и без самого имени класса:
Полное имя класса:
MyCsprojFileName.AnyFolder.SubFolder.FooClass
baseName
:
AnyFolder.SubFolder
Для кода, который вы предоставили baseName
возможно "Services.Base"
, Давайте напишем некоторый код, чтобы получить его в общем виде:
public class FooService<T>
{
private readonly IStringLocalizerFactory _factory;
public FooService(IStringLocalizerFactory factory)
{
_factory = factory;
}
public IStringLocalizer GetLocalizer()
{
var type = typeof(FooService<>);
string assemblyName = type.GetTypeInfo().Assembly.GetName().Name;
string typeName = type.Name.Remove(type.Name.IndexOf('`'));
string baseName = (type.Namespace + "." + typeName).Substring(assemblyName.Length).Trim('.');
var localizer = _factory.Create(baseName, assemblyName);
return localizer;
}
}