我在这里挣扎着角。我学到的是模块的工厂和服务功能只创建一个对象的一个实例,它将属性(函数和变量)与它相关联。并且该实例可在整个应用程序的控制器中使用。
在我的应用中,我创建了一个服务模块userAngService
,如下所示:
var ser = angular.module('userAngService',[]);
ser.service('userAngService',['$cookies','$location','$http','$log','$rootScope',function($cookies,$location,$http,$log,$rootScope){
this.user = {};
$rootScope.username = {};
$rootScope.user = {};
/*this.loadUserData = function(username){
return $http({
method: 'GET',
url: 'http://localhost:7070/storyBoard/webapi/profiles/'+username
}).success(function(data){
user = data.data;
//return user;
});
};*/
this.login = function(val){
return $http({
method: 'GET',
url: 'http://localhost:7070/storyBoard/webapi/stories?username='+val.username+'&password='+val.password
}).then(function(data){
if(data.data==="Success"){
$rootScope.username = val.username;
$cookies.put("username", val.username);
$http({
method: 'GET',
url: 'http://localhost:7070/storyBoard/webapi/profiles/'+val.username
}).success(function(data){
console.log(data);
this.user = data;
console.log(this.user);
});
$location.path("/home");
}else{
window.alert('Wrong username or password');
}
});
};
this.logout = function(){
$rootScope.user.username = "";
$cookies.remove("username");
$location.path("/Diary");
};
this.addToShelf = function(wsPublish){
wsPublish.author = $rootScope.user.username;
return $http({
method: 'POST',
url:'http://localhost:7070/storyBoard/webapi/stories',
data: wsPublish
}).then(function(data){
this.user.stories.push(data.data);
});
};
}]);
它包含3个函数和私有变量this.user
以及2个rootScope变量$rootScope.username
& $rootScope.user
。
我们关注的功能是this.login()
函数。
现在,
要使用此服务模块,我创建了一个模块AllControllers
:
var app = angular.module('AllControllers',['userAngService']);
我将 2个控制器与之关联起来。
第一个控制器:
app.controller('LoginFormController',['$cookies','$rootScope','$log','$scope','userAngService','userBean',function($cookies,$rootScope,$log,$scope,userAngService,userBean){
$scope.login = function(val){
userAngService.login(val);
};
$scope.logout = function(){
userAngService.logout();
};
$scope.publishGroup = function(obj){
userBean.publishGroup(obj);
};
}]);
*此控制器注入了userAngService
的依赖关系,并且它的login()
功能会委托调用login() function of userAngService
服务
login()
中的userAngService
函数更改了其私有变量属性。
然后,我试图在另一个控制器中使用,以及所有问题所在。
当我在promise
本身记录返回的userAngService
数据时,它已成功记录但当我尝试在另一个控制器中访问时,它只记录空对象
第二个控制器(从那里访问服务的私有变量):
app.controller('ReachController',['$cookies','$scope','$rootScope','userAngService',function($cookies,$scope,$rootScope,userAngService){
$scope.user = {};
$scope.username = {};
$scope.user = userAngService.user;
console.log(userAngService.user);
$scope.username = $cookies.get("username");
/*userAngService.loadUserData($scope.username).then(function(data){
$scope.user = data.data;
console.log($scope.user);
});*/
console.log($scope.user);
console.log($rootScope.user);
$scope.logout = function(){
userAngService.logout();
};
$scope.addToShelf = function(wsPublish){
userAngService.addToShelf(wsPublish);
};
}]);
一个空对象只能意味着对象属性被定义为null并且不会被login()
服务函数更新。但是,在userAndService
中success
回调;
console.log(data);
this.user = data;
console.log(this.user);
这些代码行成功记录了返回的数据,而在ReachController
或第二个控制器的行中;
$scope.user = userAngService.user;
...
console.log($scope.user);
将此日志记录到控制台:
Object {}
没有错误,所以代码是正确的但是在概念上我猜错了。请帮忙!
答案 0 :(得分:0)
如果您想要返回数据使用工厂而不是服务。
服务始终返回包含数据的方法。
console.log(data);
this.user = data;
console.log(this.user);
“this”对象用于Success函数的本地范围。它会覆盖服务“这个”对象。
答案 1 :(得分:0)
我的猜测是问题在于服务和父模块的命名 - userAngService
。尝试将模块重命名为userAngServiceModule
。当您向userAngService
添加依赖项时,无论您是指模块还是服务,我都希望angular的DI会混淆。
答案 2 :(得分:0)
promise this
处理程序中的.then
上下文与服务的this
上下文不同。
app.service("myService", function($http) {
var myService = this;
this.data = {};
this.fetch = function(url) {
//return promise
return (
$http.get(url).then (function onFulfilled(response) {
//Won't work
//this.data = response.data;
//Instead use the binding
myService.data = response.data;
//Return data for chaining
return myService.data;
}).catch (function onRejected(response) {
console.log(response.status);
//throw to chain rejection
throw response;
});
);
};
});
this
函数中的onFulfilled
上下文与服务的this
上下文不同。而是将服务的this
上下文绑定到变量,并在promise onFulfilled
方法的.then
函数中使用该变量。
另请注意,this.data
服务在XHR完成后的某个时间,服务的$http
变量将在未来设置 。为确保数据可用,请使用fetch
函数返回的承诺。
var promise = myService.fetch(url);
promise.then (function onFulfilled(data) {
$scope.data = data;
}).catch( function onRejected(errorResponse) {
console.log(errorResponse.status);
});