【问题标题】:angularjs- Why http request returns false with resolve?angularjs-为什么http请求通过resolve返回false?
【发布时间】:2016-07-15 08:58:53
【问题描述】:

我有一个登录系统...我正在尝试对网站实施登录/注销功能。

这是我关注的小提琴-FIDDLE

这是我的路线文件:

(function() {
  var onlyLoggedIn = function($location, $q, AuthService2) {
    var deferred = $q.defer();

    if (AuthService2.isLogin()) {
      deferred.resolve();
    } else {
      deferred.reject();
      $location.url('/login');
    }
    return deferred.promise;
  };

  angular.module('myApp', [
      'ngRoute',
      'myApp.login',
      'myApp.home',
      'myApp.logout',
      'myApp.notifications'
    ])
    .factory('AuthService2', ["$http", "$location", function($http, $location) {
      //var vm = this;
      var baseUrl = 'api/';

      return {

        isLogin: function() {
          var token;
          if (localStorage['entrp_token']) {
            token = JSON.parse(localStorage['entrp_token']);
          } else {
            token = "";
          }
          var data = {
            token: token
          };
          $http.post(baseUrl + 'validateUserToken', data).success(function(response) {
            if (response.msg == "authorized") {
              //console.log(response.msg);
              return localStorage.isLogged === "true";
            } else {
              return localStorage.isLogged === "false";
            }
          });
        }
      }
      return {
        isLogin: isLogin
      };
    }])

  .config(['$routeProvider', function($routeProvider) {
    $routeProvider
      .when('/login', {
        controller: 'LoginController',
        templateUrl: 'app/components/login/loginView.html',
        controllerAs: 'vm'
      })
      .when('/home', {
        controller: 'HomeController',
        templateUrl: 'app/components/home/homeView.html',
        resolve: {
          loggedIn: onlyLoggedIn
        },
        controllerAs: 'vm'
      })
      .when('/logout', {
        controller: 'LogoutController',
        templateUrl: 'app/components/login/loginView.html',
        resolve: {
          loggedIn: onlyLoggedIn
        },
        controllerAs: 'vm'
      })
      .when('/notifications', {
        controller: 'NotificationsController',
        templateUrl: 'app/components/notifications/notificationsView.html',
        resolve: {
          loggedIn: onlyLoggedIn
        },
        controllerAs: 'vm'
      })

    .otherwise({
      redirectTo: '/login'
    });
  }]);

})();

用户将访问登录页面。身份验证后,我设置了一个会话和一个本地存储令牌。

我使用 resolve 来检查用户是否有效。我为此定义了一个函数(您可以从代码中看到)。

登录后,我可以验证用户并设置会话,登录控制器将有效用户重定向到主页。但是用户到达了路线,他停留在登录页面本身。

我的 http 请求很好。我检查了它,它返回正确的结果。但我认为该函数返回 false 之后只有 http 请求被执行。因为我可以在 consoel 中看到 http 请求并返回肯定的结果,所以用户应该得到导航但它没有发生,因为 http 请求被延迟或其他原因。

我尝试在 if else 中发出警告消息,无论如何它总是进入 else 条件。

 if (AuthService2.isLogin()) {
      deferred.resolve();
    } else {
      deferred.reject();
      $location.url('/login');
    }

为什么会这样?我对 Angular 很陌生。这是角度的限制吗?

【问题讨论】:

  • 已审查示例。第一个错误是使用if (Auth.isLogin()),当您依赖实际上是承诺的请求并且您正在编写if 而不是.then() 来检查isLogin()。简单地说 - 你在检查登录功能中用同步 if 弄乱了异步 $http 登录请求。

标签: angularjs routing


【解决方案1】:

问题是您的 isLogin 函数中没有 return 语句。

您的 return 语句在 $http.post 回调中 NOT isLogin 因此 isLogin return undefined 因此解析为 falsy。

$http.post(baseUrl + 'validateUserToken', data).success(function(response) {
        //Notice that you are inside function(response) closure.
        if (response.msg == "authorized") {
          return localStorage.isLogged === "true";
        } else {
          return localStorage.isLogged === "false";
        }
      });

我可以建议你改为返回 $http.post,$http.post 返回一个你可以用这种方式使用的 promise 对象,下面是一个简短的例子,告诉你如何做到这一点。

isLogin: function() {
      //Omitted some code
      //This method return a promise object
      return $http.post(baseUrl + 'validateUserToken', data);
      });


AuthService2.isLogin().then(function(res){
    if (response.msg == "authorized") {
      deferred.resolve();
    } else {
      deferred.reject();
      $location.url('/login');
    }
}, errorCallback); //Optional if you want to handle when post request failed

代码未经测试,仅供参考。

【讨论】:

  • 你能用上述方法更新问题或小提琴吗?我相当肯定该方法应该在逻辑上起作用..
  • jsfiddle.net/pm1c3hok 检查这个小提琴。它模拟登录。单击登录按钮后,用户可以访问关于页面..这就是逻辑..检查控制台。 @Harry Lim
  • 从 isLogin 返回 localStorage.isLogged 已经足够知道用户是否登录了?如果为假,则重定向到登录页面...我不知道 $http.post 在这里服务的目的。
  • 在原帖中,$http 用于拨打电话..并使用后端数据检查用户的有效性..@Harry Lim
  • 该服务获取本地存储变量并使用数据库值验证它...@Harry Lim
猜你喜欢
  • 2019-01-16
  • 2017-11-25
  • 1970-01-01
  • 2016-05-12
  • 1970-01-01
  • 2013-11-09
  • 2016-10-16
  • 2018-10-10
  • 2013-09-18
相关资源
最近更新 更多