92

我有一个 AuthService,它登录一个用户,它返回一个用户 json 对象。我想要做的是设置该对象并在应用程序中反映所有更改(登录/注销状态),而无需刷新页面。

我将如何使用 AngularJS 完成此任务?

4

2 回答 2

180

实现这一点的最简单方法是使用服务。例如:

app.factory( 'AuthService', function() {
  var currentUser;

  return {
    login: function() { ... },
    logout: function() { ... },
    isLoggedIn: function() { ... },
    currentUser: function() { return currentUser; }
    ...
  };
});

然后,您可以在任何控制器中引用它。以下代码监视来自服务的值的更改(通过调用指定的函数),然后将更改的值同步到范围。

app.controller( 'MainCtrl', function( $scope, AuthService ) {
  $scope.$watch( AuthService.isLoggedIn, function ( isLoggedIn ) {
    $scope.isLoggedIn = isLoggedIn;
    $scope.currentUser = AuthService.currentUser();
  });
});

然后,当然,您可以使用您认为合适的信息;例如,在指令、模板等中。您可以在菜单控制器等中重复此操作(根据您的需要定制)。当您更改服务的状态时,所有这些都会自动更新。

更具体的内容取决于您的实施。

希望这可以帮助!

于 2013-01-08T00:41:29.257 回答
5

我会修改 Josh 的良好响应,补充一点,因为 AuthService 通常会引起任何人的兴趣(例如,如果没有人登录,除了登录视图之外的任何人都应该消失),也许更简单的替代方法是使用$rootScope.$broadcast('loginStatusChanged', isLoggedIn);(1 ) (2),而相关方(例如控制者)会使用$scope.$on('loginStatusChanged', function (event, isLoggedIn) { $scope.isLoggedIn = isLoggedIn; }.

(1)$rootScope作为服务的参数注入

(2) Note that, in the likely case of a asynchronous login operation, you'll want to notify Angular that the broadcast will change things, by including it in a $rootScope.$apply() function.

Now, speaking of keeping the user context in every/many controllers, you might not be happy listening for login changes in everyone of them, and might prefer to listen only in a topmost login controller, then adding other login-aware controllers as children/embedded controllers of this one. This way, the children controller will be able to see the inherited parent $scope properties such as your user context.

于 2013-09-27T08:07:05.573 回答