AngularJS服務被注入到兩個獨立的模塊中。這會導致服務在第二個模塊調用它時分別重新初始化。我已經使用FireFox調試器來確認模塊正在重新初始化。我怎樣才能避免這個問題?爲什麼在重新加載路由時AngularJS服務會重新初始化?
以下是具體情況:
的AngularJS應用程序使用一個名爲auth
模塊中的認證服務管理認證的擔憂。 auth
服務被導入到message
模塊中,該模塊管理對安全/message
路由的訪問,並且auth
也被導入navigation
模塊,其管理登錄/註冊以及用戶瀏覽器中的導航鏈接的可見內容。用戶能夠使用鏈接到navigation
模塊的GUI工具成功登錄,然後作爲經過驗證的用戶成功重定向到安全/message
路由,因爲auth.authenticated1
和auth.authenticated2
屬性在重定向到/message
之前設置爲true
。
然而,火狐調試確認的問題是,當用戶刷新的瀏覽器重新加載/message
URL模式中,auth
模塊被重新初始化,設定auth.authenticated1
和auth.authenticated2
的值返回到錯誤的,因而即使用戶在使用用戶提供的有效憑證之前立即登錄,也會向用戶發送消息表明他們未登錄。 需要對下面的代碼進行哪些特定的更改,以便用戶在重新加載頁面時未被註銷?
我希望在/message
路線被加載或重新加載AngularJS代碼來檢查預先存在的價值auth.authenticated2
。如果auth.authenticated2=false
,則用戶會收到一條消息,指出他們已註銷。但是,如果auth.authenticated2=true
,我希望用戶能夠看到/message
路線上的安全內容。 我不想讓auth.authenticated2
在重新加載路線時自動重新設置爲false
,這是現在的方式。
這裏是message.html
的代碼,其包含用於/message
路線的GUI元素:
<div ng-show="authenticated2()">
<h1>Secure Content</h1>
<div>
<p>Secure content served up from the server using REST apis for authenticated users.</p>
</div>
</div>
<div ng-show="!authenticated2()">
<h1>You are not logged in.</h1>
</div>
這裏是message.js
的代碼,其是用於管理該/message
路由message
模塊,所述控制器:
angular.module('message', ['auth']).controller('message', function($scope, $http, $sce, auth) {
$scope.authenticated2 = function() {
return auth.authenticated2;
}
//Other code calling REST apis from the server omitted here to stay on topic
});
這裏是navigation
模塊的代碼,它也注入了auth
服務器冰:
angular.module('navigation', ['ngRoute', 'auth']).controller('navigation', function($scope, $route, auth, $http, $routeParams, $location) {
$scope.credentials = {};//from old navigation module
$scope.leadresult = "blank";
$scope.processStep = "start";
$scope.uname = "blank";
$scope.wleadid = "initial blank value";
$scope.existing = "blank";
$scope.tab = function(route) {
return $route.current && route === $route.current.controller;
};
$scope.authenticated1 = function() {
return auth.authenticated1;
}
$scope.authenticated2 = function() {
return auth.authenticated2;
}
$scope.login = function() {
auth.authenticate1($scope.credentials, function(authenticated1) {
//a bunch of stuff that does level 1 authentication, which is not relevant here
})
}
$scope.logout = auth.clear;
//some other methods to manage registration forms in a user registration process, which are omitted here because they are off-topic
$scope.pinForm = function(isValid) {//this method finishes authentication of user at login
if (isValid) {
$scope.resultmessage.webleadid = $scope.wleadid;
$scope.resultmessage.name = $scope.uname;
$scope.resultmessage.existing = $scope.existing;
var funcJSON = $scope.resultmessage;
auth.authenticate2(funcJSON, function(authenticated2) {
if (authenticated2) {
$location.path('/message');
$scope.$apply();//this line successfully re-directs user to `/message` route LOGGED IN with valid credentials
}
});
}
};
$scope.$on('$viewContentLoaded', function() {
//method that makes an unrelated call to a REST service for ANONYMOUS users
});
});
以下是在auth.js
爲auth
服務的代碼:
angular.module('auth', []).factory('auth', function($rootScope, $http, $location) {
var auth = {
authenticated1 : false,
authenticated2 : false,
usrname : '',
loginPath : '/login',
logoutPath : '/logout',
homePath : '/message',
path : $location.path(),
authenticate1 : function(credentials, callback) {
var headers = credentials && credentials.username ? {
authorization : "Basic " + btoa(credentials.username + ":" + credentials.password)
} : {};
$http.get('user', {
headers : headers
}).success(function(data) {
if (data.name) { auth.authenticated1 = true; }
else { auth.authenticated1 = false; }
callback && callback(auth.authenticated1);
}).error(function() {
auth.authenticated1 = false;
callback && callback(false);
});
},
authenticate2 : function(funcJSON, callback) {
$http.post('/check-pin', funcJSON).then(function(response) {
if(response.data.content=='pinsuccess'){
auth.authenticated2=true;
callback && callback(auth.authenticated2);
}else {
auth.authenticated2=false;
auth.authenticated2 = false;
callback && callback(false);
}
});
},
clear : function() {
$location.path(auth.loginPath);
auth.authenticated1 = false;
auth.authenticated2 = false;
$http.post(auth.logoutPath, {}).success(function() { console.log("Logout succeeded");
}).error(function(data) { console.log("Logout failed"); });
},
init : function(homePath, loginPath, logoutPath) {
auth.homePath = homePath;
auth.loginPath = loginPath;
auth.logoutPath = logoutPath;
}
};
return auth;
});
的routeProvider
由主js
文件的應用程序,這是hello.js
和是如下進行管理:
angular.module('hello', [ 'ngRoute', 'auth', 'home', 'message', 'public1', 'navigation' ])
.config(
function($routeProvider, $httpProvider, $locationProvider) {
$locationProvider.html5Mode(true);/* This line is one of 3 places where we set natural urls to remote the default # */
$routeProvider.when('/', {
templateUrl : 'js/home/home.html',
controller : 'home'
}).when('/message', {
templateUrl : 'js/message/message.html',
controller : 'message'
}).when('/public1', {
templateUrl : 'js/public1/public1.html',
controller : 'public1'
}).when('/register', {
templateUrl : 'js/navigation/register.html',
controller : 'navigation'
}).otherwise('/');
$httpProvider.defaults.headers.common['X-Requested-With'] = 'XMLHttpRequest';
}).run(function(auth) {
// Initialize auth module with the home page and login/logout path
// respectively
auth.init('/checkpin', '/login', '/logout');
});
@CodeMed你問的是他爲你寫一個認證系統。這不是一件小事。它完全綁定到你的服務器。你可能會考慮對cookie /認證令牌做更多的研究,然後在遇到困難時詢問更狹義的問題。 –
哇...請顯示代碼。 OP要求代碼希望你在開玩笑吧? –
Cookie必須在服務器端完成。我很抱歉,你要求一個理論上的答案,因爲你似乎沒有任何想法認證如何工作。 –