私は、ユーザー識別機能付きのSpring + AngularJS RestFulアプリケーションを持っています。AngularJS Controllerでイベントの優先度を指定する方法は?
とすぐに、私は次のようにこのデータを保存するには、ユーザーがログインしているとおり、私は私が私のメインコントローラに実装されている他のタブでこのsessionStorage
を持ちたいので
$window.sessionStorage.user
をここに提案される解決策: https://stackoverflow.com/a/32766809/1281500
また、このコントローラでは、ユーザがログインしているかどうかを確認するために、$stateChangeStart
イベントを聞きます。ユーザーがログインしていない場合、私は彼を対応するログインページにリダイレクトします。
エクスプローラで新しいタブを開くと問題が発生します。あなたは以下のコードでわかるように、私はこのような新しいタブに古いタブから$window.sessionStorage.user
変数を取得:
else if (event.key == 'sessionStorage' && !$window.sessionStorage.length) {
// another tab sent data <- get it
var data = JSON.parse(event.newValue);
for (var key in data) {
$window.sessionStorage.setItem(key, data[key]);
}
しかし$stateChangeStart
のコードがそう$window.sessionStorage.user
上記のスニペットの前に実行されるではありません利用はまだありませんし、ユーザーは常に彼はすでに(元のタブに少なくとも)に記録されていても、ログインページにリダイレクトされ
$rootScope.$on('$stateChangeStart', function (event, toState, toParams) {
// if the user tries to access a restricted page an is not logged in, he is redirected to the login view
var restrictedPage = $.inArray(toState.name, ['login', 'sign-up']) === -1;
// "$window.sessionStorage.user" IS ALWAYS "UNDEFINED" just after a new tab is opened
if (restrictedPage && $window.sessionStorage.user === undefined) {
// Go to login page
}
});
完全なコントローラのコードは以下の通りです。 $stateChangeStart
ブロックでユーザーの資格情報を利用するにはどうすればよいですか?
(function() {
'use strict';
angular
.module('app.core')
.controller('CoreController', CoreController);
CoreController.$inject = ['$q', '$scope', '$rootScope', '$state', '$location', '$cookies', 'LoginService', '$window'];
function CoreController($q, $scope, $rootScope, $state, $location, $cookies, LoginService, $window) {
var vm = this;
var sessionStorage_transfer = function(event) {
if(!event) { event = $window.event; } // ie suq
if(!event.newValue) return; // do nothing if no value to work with
if (event.key == 'getSessionStorage') {
// another tab asked for the sessionStorage -> send it
$window.localStorage.setItem('sessionStorage', JSON.stringify(sessionStorage));
// the other tab should now have it, so we're done with it.
$window.localStorage.removeItem('sessionStorage'); // <- could do short timeout as well.
} else if (event.key == 'sessionStorage' && !$window.sessionStorage.length) {
// another tab sent data <- get it
var data = JSON.parse(event.newValue);
for (var key in data) {
$window.sessionStorage.setItem(key, data[key]);
}
}
};
// listen for changes to localStorage
if($window.addEventListener) {
$window.addEventListener("storage", sessionStorage_transfer);
} else {
$window.attachEvent("onstorage", sessionStorage_transfer);
};
// ask other tabs for session storage (this is ONLY to trigger event)
if (!$window.sessionStorage.length) {
$window.localStorage.setItem('getSessionStorage', 'user');
$window.localStorage.removeItem('getSessionStorage', 'user');
};
$rootScope.$on('$stateChangeStart', function (event, toState, toParams) {
// if the user tries to access a restricted page an is not logged in, he is redirected to the login view
var restrictedPage = $.inArray(toState.name, ['login', 'sign-up']) === -1;
if (restrictedPage && $window.sessionStorage.user === undefined) {
// Go to login page
}
});
}
})();
UPDATE
私のアプリケーションは、それは次のように動作しますステートレスです:
- 初めてのアプリケーションへのユーザーアクセス私は、ユーザー名とパスワードを確認しています正しい(Spring Restサービスへの呼び出し)、その時点でユーザーのトークンを生成します。このトークンとユーザーデータは、ともに
$window.sessionStorage.authToken
と$window.sessionStorage.authToken
のようにsessionStorageに格納されます。私はRESTfulなアプリケーションへのすべての要求にこのトークンを送る今から
function login(valid) {
if(!valid) return;
LoginService.authenticate(vm.user)
.then(
function(user) {
var authToken = user.token;
$window.sessionStorage.authToken = authToken;
vm.authError = false;
if (vm.rememberMe) {
var now = new Date();
var expireDate = new Date(now.getFullYear(), now.getMonth() + 1, now.getDate());
$cookies.put(AUTH_TOKEN_COOKIE, authToken, {'expires': expireDate});
}
LoginService.getUser()
.then(
function(user) {
$window.sessionStorage.user = user
$state.go('installations');
}
);
},
function(errAuthentication) {
vm.authError = true;
$window.sessionStorage.user = null;
}
);
}
- と私はトークンをチェック春でフィルタを持っている: 私は別のAngularJSコントローラ(LoginController)からこれを管理しますユーザー資格情報が正しい。このトークンが存在しないか、もう有効でない場合、Spring Securityは対応する例外をスローし、この例外をキャッチしてログインページにリダイレクトします(このコードは現在の質問では重要ではないと思いますが、必要であれば)。
だから、基本的に私のユーザーは、現在sessionStorage
オブジェクトに住んでいる、私はちょうど私がプロセスの最初のログイン時に格納された変数をチェックし、ユーザーがログインされているかどうかをチェックするサービスを持っていません。
私はこれがプロセスを少しはっきりさせるのに役立つことを願っています。
ありがとうございました。
このログインはSpringをまったく経由していませんか? – ChiefTwoPencils
私の更新をもう少し詳しくチェックしてください。ありがとうございました。 – rocotocloc