2013-03-08 58 views
4

我正在尝试将登录用户从登录页面重定向到远离登录页面(如果他们尝试在应用程序中访问它)。与登录页面关联的控制器 - Login_controller调用授权服务中的功能 - Authorisation_service.isLoggedIn()。如果此服务返回true,则应将用户重定向到登录的概述页面。AngularJS - 控制器不等待条件语句中的服务返回值

通过记录到控制台我可以看到,在服务返回true之前,条件语句已经声明从服务返回的值是未定义的。之后服务确实会恢复正常,但已为时过晚。

如何让控制器的条件语句等待服务的返回值?

Authorise_service.js

myApp.factory('Authorise', ['User', '$http', '$location', '$rootScope', function(User, $http, $location, $rootScope) { 
    return { 
     isLoggedIn: function() { 
      if(((sessionStorage.username && sessionStorage.authKey) && (sessionStorage.username !== "null" && sessionStorage.authKey !== "null")) || ((localStorage.username && localStorage.authKey) && (localStorage.username !== "null" && localStorage.authKey !== "null"))) { 
       if(sessionStorage.username) { 
        var usernameLocal = sessionStorage.username; 
        var authKeyLocal = sessionStorage.authKey; 
       } else { 
        var usernameLocal = localStorage.username; 
        var authKeyLocal = localStorage.authKey; 
       } 
       //pass to server 
       var user = User.query({ usernameLocal: usernameLocal, authKeyLocal: authKeyLocal }, function(user) { 
        if(user.loginSuccess === 1) { 
         return true; 
        } else { 
         return false; 
        } 
       }); 
      } else { 
       return false; 
      } 
     } 
    }; 
}]); 

Login_controller.js

myApp.controller('Login_controller', function(Authorise, $scope, $location) { 
    if(Authorise.isLoggedIn() === true) { 
     console.log("Authorise.isLoggedIn() = true"); 
     $location.path('/teach/overview'); 
    } 
}); 

回答

5

Smk是对的。您可能试图依靠服务器尚未返回的数据。 “然而”是这里的关键问题,因为很可能您的数据可以从服务器中正确提取,您只需在准备好之前就参考结果!要检查这是否是事实,只需在User.query(...)回拨中添加console.log(user)即可。

Smk指出你正确的方法 - 使用PROMISE API。基本上,诺言是一个对象,当服务器准备好结果时,您可以进一步使用它来执行一些操作。为了说明这一点:

function myFunc() { 
    var result = false; 

    // You are calling async request to the server, so the execution won't wait for the 
    // results. It will simply fire server request and proceed to next lines. 
    serverCall(function(srvResponse){ 

     result = srvResponse.everythingIsGood; // This will be called after the whole method finishes! 
    }); 

    return result; // This will MOST PROBABLY return 'false' all the times. 
} 

而且这样做的正确方法:

function theRealLogicYouWantToDo(result) { 
    if (result) { 
     // ... 
    } else { 
     // ... 
    } 
} 

serverCall(function(srvResponse) { 
    theRealLogicYouWantToDo(srvResposne.everythingIsGood); 
}); 

This is nice tutorial这一切jQuery中。它不仅用于服务器调用,而且还用于JS中的其他地方。很好学习它。

+0

感谢您的详尽回复和教程链接非常有用 – Fisu 2013-03-08 13:09:31

+0

很高兴能帮助您,先生! – 2013-03-10 15:13:37

3

您需要返回promise

您的angularjs服务可以返回一个承诺,您可以在控制器中测试该值。