Как динамически определять URL таблиц перевода с помощью пользовательского загрузчика angular-translate?

#angularjs #angular-translate

#angularjs #angular-translate

Вопрос:

Как динамически определять URL таблиц перевода с помощью $translateProvider

В настоящее время мы выполняем — [https://angular-translate.github.io/docs/#/guide/12_asynchronous-loading ](асинхронная загрузка) в одном из наших приложений.Мы следовали этому методу почти 2 года. Но прямо сейчас перед нами стоит другая задача.Мы должны определить URL нашего файла перевода на основе логики.Логика такова: если файл существует в данном, location затем разрешите перевод через него или вернитесь к default location .

Моя текущая среда

  • версия angular-translate — 2.4.2 с angular-translate-partial-loader — 2.4.2
  • версия angular — 1.5

Структура приложения

 |-- mod 1
|   |-- de_de.json
|   |-- en_us.json
|   |-- es_es.json
|   `-- zh_tw.json
|-- mod 2
|   |-- de_de.json
...Followed by corresponding translation files.
  

Структура кода:

application.js

 myapp.config(['$translateProvider', '$translatePartialLoaderProvider',function ( $translateProvider, $translatePartialLoaderProvider ) {
    $translateProvider.useLoader( '$translatePartialLoader', {
        urlTemplate: 'i18n/{part}/{lang}.json'
    } );
    $translateProvider.preferredLanguage( "en_us" );
    $translateProvider.fallbackLanguage( "en_us" );
}]);
........
myapp.run( function ( $rootScope, $translate, editableOptions ) {
    $rootScope.$on( '$translatePartialLoaderStructureChanged', function () {
        $translate.refresh();
    } );
    editableOptions.theme = 'bs3';
} );
  

controller1.js

 myapp.controller1("Controller1",function($scope, ...,.., $translate, $translatePartialLoader,$rootScope) {
    /*@ngInject*/
    $translatePartialLoader.addPart('login');
    $translatePartialLoader.addPart('home');
.......
 $scope.setLanguage = function(lang) {
     $translate.use(lang);
    }
  

Пока все хорошо.Теперь мы хотим изменить логику application.js , чтобы сгенерировать таблицу перевода, разрешающую URL.Мы должны проверить, есть ли у нас таблицы перевода для particular_part/in_particular_language .

Ожидаемая структура и поведение

 |-- mod 1
|  |-- Custom
|  |  |-- de_de.json
|  |  |........followed by all custom translations for mod1 i.e, $translatePartialLoader.addPart('mod1') 
|  |-- en_us.json
|  |-- es_es.json
|   `-- zh_tw.json
|-- mod 2
|   |-- de_de.json
  

В новой структуре у нас будет пользовательский каталог под каждым модулем, если существует файл перевода для части / модуля в пользовательском, тогда разрешайте с помощью part/Custom/lang_key.json else fall back to part/lang_key.json(as before)

Как мы можем достичь этого с помощью ng-translate ? .

Подход, который я использовал, заключается в написании пользовательского загрузчика .Но options из $translatePartialLoader ограничивает аргумент только lang_key, который передается $translate.use(lang_key) .Как мы можем получить mod1 переданный $translatePartialLoader.addPart('mod1') в out customLoader .Мы не можем передать его, $translate.use('lang_key/mod1') поскольку мы вызываем $translate.use('land_key') только один раз, когда пользователь входит в систему.

Если мы сможем получить добавленный модуль из $translatePartialLoader('mod1') вызова, переданный в наш customLoader , то, основываясь на логике, мы сможем соответствующим образом разрешить переводы.В настоящее время я застрял на том, как получить добавленную часть в customLoader , поскольку она загружается контроллерами (контроллер 1 ..). Есть ли способ или пользовательский сервис, который должен быть написан для получения добавленной части / модуля.. в наш customLoader если да, можете ли вы направить меня или помочь мне с соответствующим кодом, ИЛИ нам придется изменить всю структуру приложения — если изменение структуры поможет, то какой должна быть структура?

Спасибо.

Ответ №1:

Пользовательский сервис для извлечения части или модуля, выбранного пользователем.

 myapp.factory('fetchLanguagePart', function ($q, $timeout) {
/*@ngInject*/
var languageService = {};
languageService.languagePart = ['defaultmod1', 'defaultmod2'];  //Translation tables from these parts are always required.

languageService.getLanguagePart = function () {
    var deferred = $q.defer();
    var url = purl();
    var part = grabbedPart;

    //Logic for part deciding.

    languageService.languagePart = part;
    return part;
}
return languageService;
})
  

Конфигурация

 myapp.config(['$translateProvider', '$translatePartialLoaderProvider', function ($translateProvider, $translatePartialLoaderProvider) {

    //Default language loader.

    // $translateProvider.useLoader( '$translatePartialLoader', {
    //  urlTemplate: 'i18n/{part}/{lang}.json'
    // } );

    //Custom language loader for angular-translate.

    $translateProvider.useLoader('customLanguageTemplateLoader', {})
    $translateProvider.forceAsyncReload(true);
    $translateProvider.useSanitizeValueStrategy();
}]);
  

CustomLoader извлекает таблицы перевода модуля по умолчанию и таблицы перевода пользовательского модуля, объединяет их и передает в angular-translate.

 myapp.factory('customLanguageTemplateLoader', function ($q, $http, fetchLanguagePart, $timeout) {
/*@ngInject*/
return function (options) {

    var getCustomLanguagePath = function (part) {
        return 'i18n/'   part   '/Custom/'   options.key   '.json';
    }
    var getFallBackLanguagePath = function (part) {
        return 'i18n/'   part   '/'   options.key   '.json';
    }
    //To fetch default part translations and then merge with custom part translations
    var fetchPartTranslations = function () {
        var deferred = $q.defer();
        var responses;
        var part = fetchLanguagePart.getLanguagePart();
        var customLanguageUrl = getCustomLanguagePath(part);
        var fallbackLanguageUrl = getFallBackLanguagePath(part);
        $http.get(fallbackLanguageUrl).success(function (fallbackResult) {
            responses = fallbackResu<
            $http.get(customLanguageUrl).success(function (customResult) {
                var updatedResult = angular.extend(responses, customResult);
                angular.extend(responses, customResult);
                deferred.resolve(responses);
            }).error(function (error) {
                deferred.resolve(responses);
            })
        })
        return deferred.promise;
    }
    var deferred = $q.defer();
    var part = fetchLanguagePart.getLanguagePart();
    var customLanguageUrl = getCustomLanguagePath(part);
    var fallbackLanguageUrl = getFallBackLanguagePath(part);
    var responses;

    //To fetch default module translation tables merge it with custom module translations and then merge the result of the two with  part translations.

    $http.get(getFallBackLanguagePath('home')).success(function (fallBackHome) {
        responses = fallBackHome;
        $http.get(getCustomLanguagePath('home')).success(function (customHomeResult) {
            var updatedResult = angular.extend(responses, customHomeResult);
            fetchPartTranslations().then(function (partTranslations) {
                angular.extend(responses, partTranslations);
                angular.extend(responses, customHomeResult);
                deferred.resolve(responses);
            });
        }).error(function (error) {
            fetchPartTranslations().then(function (partTranslations) {
                angular.extend(responses, partTranslations);
                deferred.resolve(responses);
            });
        })
    })
    return deferred.promise;
}
})