【问题标题】:UI router: if resolve function is given as a named dependency, resolve only executes onceUI路由器:如果resolve函数作为命名依赖项,resolve只执行一次
【发布时间】:2014-07-10 10:32:33
【问题描述】:

我一直在我的 Angular 项目中广泛使用解析,为了便于阅读,我想将所有解析函数移动到独立模块中(某些州甚至可以共享相同的解析函数,无需我重写)。

所以,我有一个简化的例子:

angular.module("stream", [
  "resources.groups",
  "ui.router"
]).config(function ($stateProvider) {
  $stateProvider.state("stream", {
    url: ... ,
    views: ... ,
    resolve: {
      groups: function (groups) {
        console.log("Resolving groups");
        return groups.get();
      }
    }
  }
});

angular.module("conversations", [
  "resources.groups",
  "ui.router"
]).config(function ($stateProvider) {
  $stateProvider.state("conversations", {
    url: ... ,
    views: ... ,
    resolve: {
      groups: function (groups) {
        console.log("Resolving groups");
        return groups.get();
      }
    }
  }
});

在这种情况下,每次状态从任何其他状态更改为流或对话时都会记录“正在解析的组”(当然,流和对话的子状态除外)。例如,visit stream (groups resolved) -> visit state3 -> visit conversations (groups resolved) -> visit stream (groups resolved)

但是,当我将它重构为以下内容时,现在只在我访问使用它的任何状态时调用一次解析。例如,visit state3 -> visit stream (groups resolved) -> visit conversations (NOT resolved here or ever again) -> visit state3 -> visit stream -> visit conversations ...。以下是导致此行为的原因:

angular.module("stream", [
  "resolves.groups",
  "ui.router"
]).config(function ($stateProvider) {
  $stateProvider.state("stream", {
    url: ... ,
    views: ... ,
    resolve: {
      groups: "resolveGroups"
    }
  }
});

angular.module("conversations", [
  "resolves.groups",
  "ui.router"
]).config(function ($stateProvider) {
  $stateProvider.state("conversations", {
    url: ... ,
    views: ... ,
    resolve: { groups: "resolveGroups" }
    }
  }
});

angular.module("resolves.groups", [
  "resources.groups"
]).factory("resolveGroups", function (groups) {
  return groups.get();
});

如何实现解析函数从外部服务共享和重用的情况,但每次转换到使用它的状态时它仍然执行?

【问题讨论】:

    标签: javascript angularjs dependency-injection angular-ui-router


    【解决方案1】:

    服务方法的问题在于 AngularJS 服务是单例的,所以它们只会(懒惰地)实例化一次。

    但是,由于映射到 resolve 对象中的名称的可注入对象只不过是简单的独立数据结构(字符串数组和末尾的函数),因此您可以在配置时以常量公开它们:

    angular.module('myApp.resolvers')
      .constant('myAppResolvers', {
        groups: ['groups', function (groups) {
          return groups.get();
        }],
        myOtherThing: ['$http', 'myService', '$q', function ($http, myService, $q) {
          // code for resolving some other thing
        }]
      });
    

    然后在你的配置中:

    myApp.config('$stateProvider','myAppResovers', function ($stateProvider, myAppResolvers) {
      $stateProvider.state("stream", {
        url: ... ,
        views: ... ,
        resolve: {
          groups: myAppResolvers.groups
        }
    }
    

    这样就实现了代码复用。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-06-24
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-10-10
      相关资源
      最近更新 更多