角度承诺.then()重复?

时间:2016-11-21 15:54:08

标签: javascript angularjs promise angular-promise

我有一个函数,它返回一个promise,如果用户当前已登录则会解析,或者在用户登录后等待解析。所以你可以这样做......

myService.waitForLogin().then(function(){
    // Subscribe to pusher.com events
});

然后我在用户退出时使用类似的调用取消订阅事件。

麻烦的是我想在每次用户登录时运行我的.then()代码,所以这个过程是....

  • 如果用户已登录,请运行代码。

  • 如果没有,请等到他们登录,然后运行代码。

  • 如果他们退出然后重新登录,请再次运行代码。

我最初使用$ rootscope。$ on来监听登录/退出事件,这些事件对于重复发生很有效,但我需要它是基于用户已登录的情况下的承诺。

这是我的代码:

var defer = $q.defer();

if(isLoggedIn()){
    defer.resolve();
}

else{

    var offLoggedInTrue = $rootScope.$on('loggedin-true', function(){
        defer.resolve();
        offLoggedInTrue();
    });

}

return defer.promise;

2 个答案:

答案 0 :(得分:1)

您可以使用承诺通过在服务中存储延迟来控制登录状态,然后通过方法waitForLogin()返回承诺。但是,您可以通知它,而不是解析承诺,一旦您解决了登录承诺,它将无法再次解决,因此您可以notify并重复使用它多次。

注意:这是一个使用promises的解决方案,但是你可能会发现更好的使用事件,在我看来它更容易维护。

例如:

angular.module('myApp', [])
  .service('LoginStatusService', function($q) {

    // store a deferred to represent the login resolution state
    var loginDeferred = $q.defer();

    // the getter method to yout login promise
    this.waitForLogin = function() {
      return loginDeferred.promise;
    };

    // an example login method from where you could notify the login promise
    this.login = function(login, password) {
      /// do async login things and then
      loginDeferred.notify();
    };

    // when the deferred may need to got reseted
    this.logoff = function(login, password) {
      /// do logoff things and then
      // loginPromise = $q.defer();
    };
  })

然后在您的控制器或您想要的任何提供商上,您可以注入服务并使用它,如下所示:

  .controller('MyController', function(LoginStatusService) {

    LoginStatusService.waitForLogin().then(null, null, function () {
      // do your subscribe stuff here
    });
  });

答案 1 :(得分:1)

您可以继续使用" loggedin-true",在您订阅该事件后,您可以在用户已经登录时手动触发事件。这是一个小样本。



angular.module('app', [])
  .controller("mainController", function($scope, $rootScope) {
    $scope.output = "";
    $rootScope.$on('loggedin-true', function() {
      $scope.output += "loggedin event \n";
    });
    if (isLoggedIn()) {
      $rootScope.$emit("loggedin-true");
    }
    logOut($scope);
    logIn($scope, $rootScope);
  });

function isLoggedIn() {
  return true;
}

function logOut($scope) {
  $scope.output += "loggedout \n";
}

function logIn($scope, $rootScope) {
  $scope.output += "login \n";
  //login successfull
  $rootScope.$emit("loggedin-true");
}

<div ng-app="app" ng-controller="mainController">
  <pre>{{output}}<pre>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
&#13;
&#13;
&#13;