激活时获取数据时的Durandal KO绑定

时间:2015-01-04 22:58:25

标签: durandal knockout-mapping-plugin

参数控制要显示的数据。该参数在视图模型的activate方法中从activationData检索,并用于调用Web Api方法。返回数据,并将其添加到视图模型中,如此

define(['durandal/app', 'knockout', 'moment'], 
       function (app, config, ko, moment) {

  var vm = {
    app: app
  };

  vm.activate = function (activationData) {
    vm.ChecklistInstanceId = activationData.ChecklistInstanceId;
    $.ajax({
      url: "api/ChecklistInstance/" + vm.ChecklistInstanceId,
      headers: { Authorization: "Session " + app.SessionToken() }
    }).done(function (data) {
      $.extend(vm, ko.mapping.fromJS(data));
    });    
  };

  return vm;

});

在扩展后立即检查视图模型会发现它完全按照预期装饰了可观察对象。例如,vm.Caption()存在并返回我期望的字符串,而vm.Section()是一个适当填充的可观察数组,依此类推一个相当精细的对象图。

问题是绑定阶段已经发生,那时视图模型缺少我想要绑定的所有可观察对象。

两种可能的策略表明自己:

  • 先前获取参数
  • 重新结合

我不知道如何做其中任何一件事。谁能告诉我如何重新组织我的代码以允许绑定到参数化的数据?

2 个答案:

答案 0 :(得分:1)

第三种可能性发生在我身上:

define(['durandal/app', 'knockout', 'moment'], 
       function (app, config, ko, moment) {

  var vm = {
    app: app,
    Caption: ko.observable(),
    Section: ko.observableArray()
  };

  vm.activate = function (activationData) {
    vm.ChecklistInstanceId = activationData.ChecklistInstanceId;
    $.ajax({
      url: "api/ChecklistInstance/" + vm.ChecklistInstanceId,
      headers: { Authorization: "Session " + app.SessionToken() }
    }).done(function (data) {
      var foo = ko.mapping.fromJS(data);
      vm.Caption(foo.Caption());
      vm.Section(foo.Section());
    });    
  };

  return vm;

});

这是有效的,因为所有可观察的都存在于绑定阶段。这可能看起来令人惊讶,因为我只描述了一个潜在的深层对象图的根,但是可观察数组为空的事实导致绑定阶段顺利退出。

稍后在激活处理程序中,在 ko.mapping使用数据后,值将被添加到observable数组中,并且绑定成功。

我对此有一种dèjavu的感觉:它让人想起在八十年代使用TurboPascal中的前向声明解决的问题。 Laplusça改变......

答案 1 :(得分:0)

为了处理完全构造的视图,您需要将逻辑移动到attached处理程序或compositionComplete处理程序。正如您所说,在 activate 阶段,DOM尚未完全构建。您可以阅读这些生命周期回调here

通常,我们所做的是通过activate处理程序传递activationData,在本地存储activationData(如果你的viewModel是基于实例的,那么在构造函数中的属性上),然后引用该activationData in attachedcompositionComplete处理程序。

您可以在activate处理程序中获取数据,然后在本地存储数据。但那就是你应该做的一切。保留与视图相关的逻辑,以便稍后在循环中使用。在这种情况下,您可能需要从activate返回承诺,然后在收到您的数据后解决。你可以阅读它here

<强>更新

查看this post以及那里的对话。