Передача текущего объема в службу AngularJS
Правильно ли передать "текущий" $scope
в службу AngularJS?
Я в ситуации, когда у меня есть $service, зная, что он потребляется только одним контроллером, и я хотел бы иметь ссылку на область управления в самих методах $service.
Является ли это философски правильным?
Или мне лучше передавать события в $rootScope, а затем заставить мой контроллер прослушивать их?
Ответы
Ответ 1
Чтобы контроллер знал, когда происходит что-то async, используйте Angular promises.
Чтобы спровоцировать $apply
, вам не нужна область действия, вы можете вызвать $rootScope.$apply
, поскольку нет разницы, вызывающей ее в определенной области или в корне.
Что касается чтения переменных, было бы лучше, если бы вы получили параметры. Но вы также можете прочитать его из области действия как параметр объекта, но я бы пошел с параметром, который сделает ваш сервисный интерфейс намного понятнее.
Ответ 2
Я бы сказал, если ваша функциональность специфична только для одного контроллера, чем вам не нужна служба.
Задачи контроллеров - манипулировать конкретной моделью, тогда как служба должна работать с глобальными задачами. Я предпочел бы придерживаться этой парадигмы вместо того, чтобы смешивать вещи.
Это то, что говорят документы
Сервис
Angular услуги - это синглтоны, которые выполняют определенные задачи, общие для веб-приложений.
контроллер
В Angular контроллер представляет собой функцию JavaScript (тип/класс), которая используется для расширения экземпляров angular Scope, исключая область корня.
PS: Кроме того, если вам нужно переварить, вы также можете ввести $rootScope в свою службу.
Ответ 3
Да. Вы можете передать $scope в службу при ее инициализации. В конструкторе службы вы можете присвоить области что-то вроде this._scope, а затем ссылаться на область действия в службе!
angular.module('blah').controller('BlahCtrl', function($scope, BlahService) {
$scope.someVar = 4;
$scope.blahService = new blahService($scope);
});
angular.module('blah').factory('blahService', function() {
//constructor
function blahService(scope) {
this._scope = scope;
this._someFunction()
}
//wherever you'd reference the scope
blahService.prototype._someFunction = function() {
this._scope['someVar'] = 5;
}
return blahService;
});
Ответ 4
Я лично считаю, что передача $scope
в службу - это плохая идея, потому что она создает любопытную циркулярную ссылку: контроллер зависит от службы, а служба зависит от области действия контроллера.
Вместо того, чтобы смешивать с точки зрения отношений, подобные вещи в конечном итоге мешают сборщику мусора.
Мой предпочтительный подход заключается в том, чтобы поместить объект в область управления и передать это службе. Таким образом, служба работает независимо от того, используется ли она внутри контроллера или, возможно, внутри другой службы в будущем.
Например, если служба должна нажимать и выталкивать элементы из массива errors
, мой код будет:
var errors = [];
$scope.errors = errors;
$scope.myService = new MyService(errors);
Служба взаимодействует с контроллером, работая на errors
.
Конечно, я должен быть осторожным в том, чтобы никогда не стереть всю ссылку на массив, но в конце концов, что общая проблема JS.
Я бы никогда не хотел использовать трансляцию, $apply
и/или подобные вещи, потому что хорошие методы OO всегда будут превзойти любые Angular -магики.