Ionic / Laravel App客户端身份验证管理

时间:2015-04-06 14:50:30

标签: angularjs laravel laravel-4 oauth-2.0 ionic-framework

我一直在摸索不同的实现和想法,以使这个工作,但我觉得我不是干这样做或尽可能聪明。我一直在关注这个"教程" Angular Auth

所以,我有一个功能齐全的laravel(4.2)后端设置,其中一些资源路由受到oauth过滤器的保护。我正在使用密码授予,一切都在那里工作得很好。我已经设置了登录/退出路线,并且能够登录到我的Ionic应用程序并从laravel获取和access_token和refresh_token就好了。使用refesh_token获取新的access_tokens也可以正常工作。但是,我在尝试弄清楚如何正确处理Ionic中的以下事情时遇到了一些问题:

  1. 确保access_token在用户点击Ionic状态之前没有过期,这将消耗我后端的资源。
  2. 处理用户的access_token&刷新令牌都已过期,要求他们重新登录到laravel后端,以获得一对新的访问权限。刷新令牌。我只有用户"登录"当他们需要获得一个新的access_token&刷新令牌(或者他们首先注册)作为这条路线,oauth / access_token,需要参数{username,password}。
  3. 我尝试过什么

    在我之前提到的文章中,他在run模块中设置了一个rootScope观察器,它监视statechangestart事件。

    $rootScope.$on('$stateChangeStart', function (event, next) {
        var authorizedRoles = next.data.authorizedRoles;
        if (!AuthService.isAuthorized(authorizedRoles)) {
           event.preventDefault();
           if (AuthService.isAuthenticated()) {
           // user is not allowed
              $rootScope.$broadcast(AUTH_EVENTS.notAuthorized);
           } else {
           // user is not logged in
              $rootScope.$broadcast(AUTH_EVENTS.notAuthenticated);
           }
        }
    });
    

    我没有使用角色所以当我实现这个时,我就有了类似的东西

    $rootScope.$on('$stateChangeStart', function(event, next) {
            if (next.url != "/login") {
                AuthService.isAuthenticated().then(function() {
                    console.log('you are already authed an logged in and trying to access: ' + next.url);
                }, function() {
                    event.preventDefault();
                    console.log('YOU DO NOT HAVE A VALID ACCESS TOKEN');
                    $location.path('/app/login');
                });
            }
        });
    

    isAuthenticated()只是在我的oauth过滤器中命中一条路径,所以如果它抛出一个错误(例如401),我知道access_token是坏的。然后我在我的AuthService服务中有一个私有方法,试图使用存储的用户刷新一个新的access_token

    function useRefreshToken() {
        console.log('Using refresh token to get new token:');
        var deferred = $q.defer();
        $http({
            method: 'POST',
            url: base_url.dev.url + 'oauth/access_token',
            data: $.param({
                grant_type: 'refresh_token',
                client_id: API.client_id,
                client_secret: API.client_secret,
                refresh_token: $localStorage.session.refresh_token
            }),
            headers: {
                'Content-Type': 'application/x-www-form-urlencoded'
            }
        }).success(function(data) {
            console.log('refresh token worked!');
            $localStorage.session.access_token = data.access_token;
            $localStorage.session.refresh_token = data.refresh_token;
            deferred.resolve();
        }).error(function(error) {
            console.log('refresh token failed');
            CurrentUserService.setLogged(false);
            console.log(JSON.stringify(error));
            deferred.reject(error);
        });
        return deferred.promise;
    };
    

    如果上面的方法返回一个被拒绝的承诺,我只是假设(这可能是个好主意?)刷新令牌已经过期,因此用户需要重新登录并检索新的访问权限。从我的laravel oauth / access_token路由刷新令牌对。

    所以上面的方法一直很好,因为我能够检查用户access_token是否有效,如果没有使用用户refresh_token检索新的access_token。

    这是我的isAuthenticated方法,以防你想看到它。它是我的AuthService服务中的公共方法。

    isAuthenticated: function() {
            console.log('Checking if token is still valid.');
            var deferred = $q.defer();
            $http.get(base_url.dev.url + 'valid-token', {
                params: {
                    access_token: $localStorage.session.access_token
                }
            }).success(function(data) {
                console.log('Token is still valid.');
                CurrentUserService.setLogged(true);
                deferred.resolve();
            }).error(function(error) {
                console.log(JSON.stringify(error));
                useRefreshToken().then(function() {
                    deferred.resolve();
                }, function(error) {
                    deferred.reject(error);
                });
            });
            return deferred.promise;
        }
    

    我遇到的一个大问题是,因为AuthService.isAuthenticated()方法运行异步,所以应用程序更改为的状态(例如PHOTOS)将在isAuthenticated返回之前被触发,如果我们在之前提到了Case:1在我的帖子的开头,PHOTOS状态将尝试使用无效的access_token在isAuthenticated方法能够使用refresh_token获取新的access_token之前尝试使用我的后端资源。

    现在我可以通过在每个状态上使用解析来避免上述问题,该状态使用isAuthenticated方法检查access_token并在需要消耗资源时获取新的状态。但那感觉非常糟糕。我为这篇文章的篇幅道歉,但我想确保你们知道所发生的一切以及我想要完成的事情。

    感谢任何反馈,批评和指导!谢谢你们。

0 个答案:

没有答案