Ruby on rails 如何在angularjs Desive library auth服务上存储和设置用户?还是已经完成了?
我正在客户端上使用cloudspace angularjs设计库。当我尝试登录/注册时,我得到一个200 ok的响应,在ChromeJS控制台中可以看到普通用户对象。刷新页面似乎会丢失这些信息,尽管我假设服务会在某个时候存储这些信息,因为它还有logout和currentUser方法。 我的问题是: 1) 此服务是否实际存储用户?如果是,如何存储(即使用cookie或localstorage或内存) 2) 如果服务未存储用户,我如何将此信息存储在自定义cookie/localstorage中,更重要的是将用户设置到服务中,以便使用服务“isauthenticated”和“currentuser”方法 部分库自述说明 只需将Desive注册为模块的依赖项。然后,身份验证服务将可供使用Ruby on rails 如何在angularjs Desive library auth服务上存储和设置用户?还是已经完成了?,ruby-on-rails,angularjs,devise,Ruby On Rails,Angularjs,Devise,我正在客户端上使用cloudspace angularjs设计库。当我尝试登录/注册时,我得到一个200 ok的响应,在ChromeJS控制台中可以看到普通用户对象。刷新页面似乎会丢失这些信息,尽管我假设服务会在某个时候存储这些信息,因为它还有logout和currentUser方法。 我的问题是: 1) 此服务是否实际存储用户?如果是,如何存储(即使用cookie或localstorage或内存) 2) 如果服务未存储用户,我如何将此信息存储在自定义cookie/localstorage中,
angular.module('myModule', ['Devise']).
config(function(AuthProvider) {
// Configure Auth service with AuthProvider
}).
controller('myCtrl', function(Auth) {
// Use your configured Auth service.
});
Auth.login(creds):使用Auth.login()向服务器进行身份验证。请记住,凭证是以明文形式发送的;使用SSL连接来保护它们。creds是一个对象,它应该包含向服务器进行身份验证所需的任何凭据。Auth.login()将返回一个承诺,该承诺将解析为登录用户。有关将用户解析为可用对象的信息,请参见AuthProvider.parse()
angular.module('myModule', ['Devise']).
controller('myCtrl', function(Auth) {
var credentials = {
email: 'user@domain.com',
password: 'password1'
};
Auth.login(credentials).then(function(user) {
console.log(user); // => {id: 1, ect: '...'}
}, function(error) {
// Authentication failed...
});
});
我的部分代码:
main.js
var myApp = angular.module('mail_app', ['ngRoute', 'ngResource', 'Devise']);
myApp.config(function($routeProvider, $locationProvider, $httpProvider, AuthProvider) {
console.log("in router")
$locationProvider.html5Mode(true);
$httpProvider.defaults.headers.common['X-CSRF-Token'] =
$('meta[name=csrf-token]').attr('content');
$httpProvider.defaults.headers.common['ClientType'] = 'browser';
// Customise login
AuthProvider.loginMethod('POST');
AuthProvider.loginPath('/api/v1/users/login.json');
// Customise register
AuthProvider.registerMethod('POST');
AuthProvider.registerPath('/api/v1/users.json');
});
sessioncontroller.js
myApp.controller('SessionsController', ['$scope', 'Auth', '$http', function($scope, Auth, $http) {
console.log("in session controller")
console.log(Auth.isAuthenticated());
$scope.loginUser = function() {
console.log("in login")
var credentials = {
email: $scope.email,
password: $scope.password
};
Auth.login(credentials).then(function(user) {
$scope.authError = 'Success!';
console.log(user); // => {id: 1, ect: '...'}
Auth.currentUser = user;
}, function(error) {
$scope.authError = 'Authentication failed...';
});
};
$scope.registerUser = function(){
console.log("in register function")
var ncredentials = {
email: $scope.newEmail,
password: $scope.newPassword,
password_confirmation: $scope.newPasswordConfirmation
};
Auth.register(ncredentials).then(function(registeredUser) {
console.log(registeredUser); // => {id: 1, ect: '...'};
}, function(error) {
$scope.authError = 'Registration failed...';
});
};
$scope.getCurrentUser = function(){
Auth.currentUser().then(function(user) {
// User was logged in, or Devise returned
// previously authenticated session.
console.log(user); // => {id: 1, ect: '...'}
$scope.id = user.id;
}, function(error) {
// unauthenticated error
});
};
$scope.isUserAuthenticated = function(){
Auth.isAuthenticated();
};
}]);
首先,您需要了解Cookie和会话在Rails中是如何工作的 第条: Rails使用CookieStore来处理会话。这意味着一切 识别用户会话所需的信息将发送到 客户端,服务器上不存储任何内容。当用户发送 请求时,会处理和验证会话的cookie,以便rails, 典狱长、设计师等可以找出你是谁,并举例说明 从数据库中更正用户 这意味着,在每个请求上,Rails都会查看会话cookie,对其进行解码,并得到如下结果
cookie = {
"session_id": "Value",
"_csrf_token": "token",
"user_id": "1"
}
此时Rails知道当前用户具有id=1
,可以进行sql查询。(如current\u user=user.find(1)
)
当用户登录时,将创建cookie,当用户注销时,cookie将被销毁。如果Rails找不到cookie或cookie没有当前用户的信息,Desive将假定用户未登录(current\u user
为nil
)
即使您通过ajax登录(尤其是通过您的“angular_Desive”gem),也会创建cookie。它不存储在服务器上,而是存储在浏览器中。(这就是为什么如果您登录到一个浏览器,您不会自动登录到另一个浏览器)正如您所指出的,库不会保留登录者的信息,这是因为信息存储在cookie中,如果没有服务器的帮助,库无法解码cookie
这就是为什么如果当前用户刷新页面,您必须进行调用才能获取该用户。(对不起)
获取当前用户的方法非常简单。这是我找到的最干净的解决方案
# application_controller.rb
def me
render json: current_user
end
# routes.rb
get "me" => "application#me"
// main.js
// I am not familiar with angular_devise lib but you get the point:
// this method fetches from server when myApp is initialized (e.g. on page reload)
// and assigns the current_user so he/she can be used by the app
myApp.run(["AuthService", function(AuthService) {
AuthService.getUserFromServer();
}]);
如果必须加载特定于用户的数据,则必须先加载用户,然后加载数据。不用说,你将不得不使用承诺
TL;DR:您必须询问服务器
我愿意接受提问和评论。我想你的问题在于刷新。angular Desive库可能假设您在SPA(单页应用程序)中,因此它不应该刷新。有了这个假设,角度装置就可以把所有的信息存储在内存中。刷新页面时,基本上是从零开始引导应用程序。对服务器的请求可能是在应用程序启动时由您的代码发出的。您可能在应用程序启动时的某个地方调用了
Auth.currentUser()
,也有同样的问题。就用那块宝石吧
您还可以在应用程序控制器中消除“防止伪造”,但这是非常危险的。我的最佳猜测是,您需要使用“记住我”设计,这样它将创建一个永久性cookie,而不是会话cookie。您知道如何通过api实现这一点吗?我通常将带有用户数据的POST请求发送到“/users/sign_in.json”。我可以在“记住我”请求中添加哪些信息?