Загрузка паролей ng-include из локального предварительно загруженного (JST) кеша шаблонов

У меня есть шаблон, предварительно загруженный в массив строк JavaScript, как var t = JST['firstTemplate'], где t было бы как,

<div>This scope has a value of {{value}}</div>

Как я могу использовать этот предварительно загруженный шаблон в ng-include Директива?

Обратите внимание, что мой шаблон в этом сценарии может быть более сложным, с возможными вложенными представлениями и шаблонами и их собственными вложенными областями и контроллерами. Так что я не уверен, поможет ли какая-либо из директив ng-bind?

ОБНОВИТЬ:

Глядя на источник ng-include похоже, что хороший способ сделать это - отделить логику загрузки шаблона от настраиваемого поставщика.

Текущий механизм загрузки по умолчанию просто $http.get с $templateCache в качестве поставщика кеша. Кажется, я могу вставить свой шаблон в JST['firstTemplate'] в кеширование шаблонов, но мне придется делать это во время запуска для каждого шаблона.

$templateCache.put('firstTemplate', JST['firstTemplate']);

а потом есть,

<div ng-include="firstTemplate"></div>

Я также мог бы написать пользовательскую директиву, которая идет бок о бок с каждым ng-include, который каким-то образом выполняет предварительное кэширование шаблонов. Это снова кажется неуклюжим.

ОБНОВЛЕНИЕ № 2

Я собираюсь переопределить templateCache, чтобы он использовал мой уже загруженный JST-хэш. Опубликуйте результаты, если это работает.

3 ответа

Решение

Вот решение, которое я нашел работающим, и это не хак, как я думал ранее (выше:-) По сути, украсьте метод $templateCache.get с помощью стандартного $provide.decorator, чтобы кэш выглядел в моем локальном предварительно загруженном кэш. Это просто работает.

angular.module('app').config([
  '$provide', 
  function($provide) {
    $provide.decorator('$templateCache', function($delegate, $sniffer) {
      var originalGet = $delegate.get;

      $delegate.get = function(key) {
        var value;
        value = originalGet(key);
        if (!value) {
          // JST is where my partials and other templates are stored
          // If not already found in the cache, look there...
          value = JST[key]();
          if (value) {
            $delegate.put(key, value);
          }
        }
        return value;
      };

      return $delegate;
    });

    return this;
  }
]);

Если вам интересно, почему у меня есть этот материал в JST, мы используем бэкэнд рельсов и конвейер ресурсов рельсов для доставки всех угловых активов. Шаблоны JST позволяют нам связывать все шаблоны и загружать их в приложение во время инициализации, а также избегать дополнительных обращений к серверу, которые обычно требуются при получении партиалов и другого содержимого шаблона.

Приведенный выше патч делает все это работающим с угловым.

Вместо ng-includeиспользовать ng-bind-html:

<div ng-bind-html="t"></div>

На вашем контроллере поместите шаблон на $scope:

$scope.t = JST['firstTemplate'];

Вам нужно будет включить ngSanitize как подмодуль (не забудьте добавить angular-sanitize.js тоже):

angular.module('app', ['ngSanitize']);

Сегодня я столкнулся с той же проблемой, вот мое решение:

Пользовательская директива, которая возвращает JST"server/info" в качестве шаблона:

/* jstTemplate.js */

/**
 * @desc template loader for JST templates
 * @example <div jst-template="server/info.html"></div>
 */


angular
    .module('myApp')
    .directive('jstTemplate', jstTemplate);

function jstTemplate() {
    return {
        restrict: 'A',
        template: function(element, attrs) {
            return JST[attrs.jstTemplate]();
        }
    }
};

Использование:

<div class="box">
    <div jst-template="server/info.html"></div>
</div>

attrs.jstTemplate содержит значение, которое мы указали в директиве.

Ура, Никлас

Другие вопросы по тегам