В чем разница между $injector.instantiate
, $injector.get
и $injector.invoke
в AngularJS?
$ injector.instantiate VS $injector.get VS $инжектор.инвук в угловых
Ответ 1
Учитывая следующую услугу:
app.service('myService', function ($q, $http) {
return {
q: $q,
http: $http
};
});
$injector.get(name, [caller]);
Возвращает экземпляр запрашиваемой службы.
$injector.get('myService');
// { q: $q, http: $http }
$injector.invoke(fn, [self], [locals]);
Вызывается предоставленный метод и проходит по заданным аргументам из $injector.
$injector.invoke(function (myService, $http) {
console.log(myService); // { q: $q, http: $http };
console.log(this); // { v: 'im this!' };
console.log($http); // null
}, { v: 'im this!' }, { $http: null });
$injector.instantiate(Тип, [locals]);
Создает новый экземпляр данного типа. Выполняет функцию конструктора, а затем вызывает новый экземпляр с аргументами, указанными в аннотации конструктора.
Предположим, что следующий класс:
function Person (fName, lName, $http, $q) {
return {
first_name: fName,
last_name: lName,
http: $http,
q: $q
}
}
Теперь, если бы мы хотели создать новое Person в нашем контроллере, мы могли бы сделать это следующим образом:
app.controller('...', function ($injector) {
var $http = $injector.get('$http');
var $q = $injector.get('$q');
var p = new Person('kasper', 'lewau', $http, $q);
console.log(p); // { first_name: 'kasper', last_name: 'lewau', http: $http, q: $q };
});
Представьте, что Person
имеет ~ 20 или около того зависимостей, и мы извлекали каждый из них методом $injector.get
.
обременительно! И - вам нужно будет синхронизировать ваши параметры и аргументы. тьфу.
Вместо этого вы можете сделать это:
app.controller('...', function ($injector) {
var p = $injector.instantiate(Person, {
fName: 'kasper',
lName: 'lewau'
});
console.log(p); // { first_name: 'kasper', last_name: 'lewau', http: $http, q: $q };
});
И - если бы мы захотели, мы могли бы предоставить locals для вызова .instantiate
, чтобы переопределить то, что обычно будет иметь внутренний $injector.get()
при создании экземпляра.
var p = $injector.instantiate(Person, {
fName: 'kasper',
lName: 'lewau'
}, { $http: 'Nothing!', $q: 'Nothing!' });
console.log(p); // { first_name: 'kasper', last_name: 'lewau', http: 'Nothing!', q: 'Nothing!' };
Надеюсь, это объяснит разницу между тремя. Если вам нужна дополнительная информация об их различиях, я бы рекомендовал следующие статьи:
- http://taoofcode.net/studying-the-angular-injector/
- http://taoofcode.net/studying-the-angular-injector-annotate/
- http://taoofcode.net/studying-the-angular-injector-invoke/
- http://taoofcode.net/studying-the-angular-injector-getservice/
- http://taoofcode.net/studying-the-angular-js-injector-instantiate/
Ответ 2
Дополнительные отметки к Kasper Lewau отвечают, потому что я не могу добавлять комментарии.
$injector.invoke(fn, [self], [locals], [serviceName]);
- Может использоваться для любой функции: конструктор класса или нет (он автоматически проверяет внутри) Параметр
- ' Self' используется только для чистой функции.
$injector.instantiate(Тип, [locals]);
- Должен использоваться только для конструкторов классов, или он будет строить пустой объект {}