我正在尝试扩展$log服务,以便它还向服务器发送消息.由于$http使用$log,我从Angular“找到循环依赖”中收到错误.
app.js:
angular.module("app").config(function($provide) { $provide.decorator("$log",function($delegate,NodeLogger) { var logFn = $delegate.log; $delegate.log = function(message) { NodeLogger.log(message); logFn.apply(null,arguments); }; }); });
NodeLogger.js:
angular.module("app").factory("NodeLogger",function($http) { function log(type,message) { var logMessage = type + ":" + message; $http.post("http://localhost:3000/log","message=" + logMessage); } return { log: log } });
我已经尝试在app.js中使用$injector来加载$http并且只是发出POST请求,但它给出了同样的错误.有办法解决这个问题吗?我可以避免使用$http / $资源吗?
谢谢!
解决方法
这是循环依赖的一个常见问题,当$http已经注入$log并通过注入你的工厂NodeLogger来装饰它时,注入$http你正在创建循环依赖.而不是直接从工厂注入工厂从工厂注入工厂,另一种方法是在工厂注入$injector并从注入器获取$http实例,而不是直接注入$http.这样可以避免在工厂创建期间出现循环依赖.一个重要的注意事项是返回$delegate,否则$log服务将不会保存任何实例.
$provide.decorator("$log",$injector) { var logFn = $delegate.log; $delegate.log = function(message) { //Get NodeLogger factory instance from injector var NodeLogger = $injector.get('NodeLogger'); NodeLogger.log(message); logFn.apply(null,arguments); }; //Return the delegate return $delegate; });
angular.module("app",[]).factory("NodeLogger",function($http) { function log(type,message) { var logMessage = type + ":" + message; $http.post("http://localhost:3000/log","message=" + logMessage); } return { log: log } }).config(function($provide) { $provide.decorator("$log",$injector) { var logFn = $delegate.log; $delegate.log = function(message) { var NodeLogger = $injector.get('NodeLogger'); NodeLogger.log(message); logFn.apply(null,arguments); }; return $delegate; }); }).run(function($log) { $log.log("Hey"); });;
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.3.15/angular.min.js"></script> <div ng-app="app"></div>