I'm learning my way around AngularJS at the moment. I've largely got to grips with the way Angular handles dependency injection, but there's a gap I can't find an answer for.
我正在学习AngularJS的方法。我基本上已经掌握了Angular处理依赖注入的方式,但是我找不到答案的差距。
Say I have a service which retrieves data from the web, based on a user's query; it might look like this:
假设我有一个服务,它根据用户的查询从Web检索数据;它可能看起来像这样:
var webBasedServiceModule = angular.module('WebBasedService', []);
webBasedServiceModule
.factory('webBasedService', function ($http) {
var rootUrl = "http://example.com/myApi?query=";
return {
getData: function(query) {
return $http.get(rootUrl + query)
.then(function(httpCallbackArg) {
return doSomething(httpCallbackArg);
});
}
}
});
I'm injecting the $http service, so I can mock it for testing. However, I've got the root URL of my web service hard-coded in the class. Ideally, I'd like to decouple this URL from the service class, and inject it as a dependency. However, I don't see a way to inject a string or another primitive into an angular factory function. I would ideally like the code to look like this:
我正在注入$ http服务,所以我可以模拟它进行测试。但是,我已经在课堂上硬编码了我的Web服务的根URL。理想情况下,我想将此URL与服务类分离,并将其作为依赖项注入。但是,我没有看到将字符串或其他基元注入角度工厂函数的方法。理想情况下,我希望代码看起来像这样:
var webBasedServiceModule = angular.module('WebBasedService', []);
webBasedServiceModule
.factory('webBasedService', function ($http, rootUrl) {
return {
getData: function(query) {
return $http.get(rootUrl + query)
.then(function(httpCallbackArg) {
return doSomething(httpCallbackArg);
});
}
}
});
One solution I can see is just to create a UrlProviderService
and inject that service into the WebBasedService
module, then call urlProvider.Url
or similar. That seems a little smelly: it seems like overkill to create a whole new service just for one piece of configuration data. I can even imagine that I might create a service which is a string, like so:
我能看到的一个解决方案就是创建一个UrlProviderService并将该服务注入WebBasedService模块,然后调用urlProvider.Url或类似的。这似乎有点臭:为一个配置数据创建一个全新的服务似乎有些过分。我甚至可以想象我可能会创建一个字符串服务,如下所示:
var urlServiceModule = angular.module('UrlService', []);
urlServiceModule
.factory('rootUrl', function () {
return "http://example.com/myApi?query=";
});
This seems like an abuse of the service concept though.
这似乎是滥用服务概念。
Does AngularJS offer a 'standard' solution to the problem of injecting primitives as configuration data? Or do I just use one of the solutions above?
AngularJS是否为注入基元作为配置数据的问题提供了“标准”解决方案?或者我只使用上述解决方案之一?
2 个解决方案
#1
9
You can use .constant()
to inject in your configuration.
您可以使用.constant()注入配置。
var app = angular.module("app", []);
app.constant("rootUrl", "http://www.example.com");
app.factory('webBasedService', function ($http, rootUrl) {
return {
rootUrl: rootUrl
}
});
app.controller("MyCtrl", ["$scope", "webBasedService", function ($scope, webBasedService) {
$scope.rootUrl = webBasedService.rootUrl;
}]);
关于jsfiddle的例子
#2
0
Expanding on the (fantastic) answer above - which was exactly the clue I needed - here's a slightly different flavour for those of us who prefer named functions. I'd been puzzling how to do this for AGES, so cheers Mark!!
扩展上面的(梦幻般的)答案 - 这正是我需要的线索 - 对于我们这些喜欢命名功能的人来说,这是一种略微不同的味道。我一直在为AGES如何做到这一点令人费解,所以欢呼马克!
angular.module('myModule', [])
.constant('rootUrl','http://localhost:3001')
.factory('dataService', ['$http', 'rootUrl', dataServiceImplementation])
.controller('MainController', ['$scope', 'dataService', mainController])
#1
9
You can use .constant()
to inject in your configuration.
您可以使用.constant()注入配置。
var app = angular.module("app", []);
app.constant("rootUrl", "http://www.example.com");
app.factory('webBasedService', function ($http, rootUrl) {
return {
rootUrl: rootUrl
}
});
app.controller("MyCtrl", ["$scope", "webBasedService", function ($scope, webBasedService) {
$scope.rootUrl = webBasedService.rootUrl;
}]);
关于jsfiddle的例子
#2
0
Expanding on the (fantastic) answer above - which was exactly the clue I needed - here's a slightly different flavour for those of us who prefer named functions. I'd been puzzling how to do this for AGES, so cheers Mark!!
扩展上面的(梦幻般的)答案 - 这正是我需要的线索 - 对于我们这些喜欢命名功能的人来说,这是一种略微不同的味道。我一直在为AGES如何做到这一点令人费解,所以欢呼马克!
angular.module('myModule', [])
.constant('rootUrl','http://localhost:3001')
.factory('dataService', ['$http', 'rootUrl', dataServiceImplementation])
.controller('MainController', ['$scope', 'dataService', mainController])