【问题标题】:AngularJS: Bind angular service property to scopeAngularJS:将角度服务属性绑定到范围
【发布时间】:2014-12-08 06:08:40
【问题描述】:

场景

  • 我有一个服务UserService 维护用户的(布尔)sessionStatus
  • 视图有条件地在ng-show=sessionStatus 上显示 [LOGOUT](即,如果未登录 (false),则不显示)。
  • 因此,ViewControllersessionStatus 应该始终与 UserService 的匹配......对吗?
  • 如果您在 [LOGOUT] 可见时单击它,它会执行一些 loggy outty 操作,sessionStatus 值更改,并且视图应更新为 ng-show... 的新结果。

问题

  1. 目前,单击注销似乎不会更新 var UserService.sessionStatus?
  2. 当 UserService.logout() 发生并更改 UserService.sessionStatus 时,如何保持 $scope.sessionStatus 更新?
    • 如何将不断变化的 $scope 映射到 ng-show?

文件

查看

    <a ng-show="sessionStatus" ng-click="logout()">Logout</a>

视图控制器

    app.controller('AppController', function($scope, $interval, $http, UserService) {
      $scope.logout = function() { UserService.logout(); }

      // This ain't working
      $scope.$watch(UserService.sessionStatus, function() {
          $scope.sessionStatus = UserService.sessionStatus;
      });
    });

用户服务

注意:appUser 是 HTML 头部中注入的全局变量(在我让会话/cookie 内容正常工作之前,这是一个 hacky 修复)

  app.factory('UserService', function($http) {
    var pre;
    var sessionStatus;

    function init() {                   // Logged in  : Logged out             
      pre = appUser.user != undefined ? appUser.user  : { name: 'Logged out', uid: '0' };
      sessionStatus = pre.uid != "0"  ? true          : false;
    }

    function resetSession() { appUser = null; init(); }

    init();

    return {
      sessionStatus: function() { return sessionStatus; }, // update on change!

      logout: function() {
        $http.get("/logout").then(function (data, status, headers, config) {
          resetSession();
        })
      }
    };
  });

【问题讨论】:

  • 只是一个建议,而不是要求您更改要求。但是您应该始终保持显示注销链接,最好不要隐藏和显示。不过,如果您想实现该功能,请使用 $timeout 并且可以将超时间隔设置为 5 秒。在该超时代码中调用一个服务,该服务将检查会话是否有效并相应地更新范围变量。但是每 5 秒你就会调用你的服务器,所以请记住这一点。

标签: javascript angularjs angularjs-scope angularjs-service angularjs-controller


【解决方案1】:

而不是watch,只需使用作用域functionservice 返回会话状态。

$scope.sessionStatus = function() {
    return userService.sessionStatus();
};

您的注销链接如下所示:

<a ng-show="sessionStatus()" ng-click="logout()">Logout</a>

为您的功能而精简的 Plunker:http://plnkr.co/edit/u9mjQvdsvuSYTKMEfUwR?p=preview

【讨论】:

  • 哇哦,一个非常优雅的解决方案。 Angular 是否会不断运行该函数以自动检查更改的值?
  • 为什么只做$scope.sessionStatus = userService.sessionStatus;是不行的
  • 如果我们将 sessionStatus 更改为 : function(){return Date.now();} plnkr.co/edit/rW4Q7OMSzqVrk9fSBBsE?p=preview,为什么视图不会实时刷新。我希望看到毫秒滴答作响。
【解决方案2】:

使用作用域函数更简洁,是“正确”的做法。然而,为了完整起见,您也可以修复您的手表:

$scope.$watch(function () {
    return UserService.sessionStatus;
}, function() {
    $scope.sessionStatus = UserService.sessionStatus;
});

$watch method 的第一个参数采用 WatchExpression,它可以是字符串或方法。

但同样,$watch 不应该在控制器中使用。使用建议的作用域方法更干净,更容易测试。

【讨论】:

    猜你喜欢
    • 2015-12-07
    • 2015-06-15
    • 1970-01-01
    • 1970-01-01
    • 2014-01-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多