1

我有一个这样的模板助手

Template.index.allUpcomingGames = function() {
    return Games.find({date: {$gte: new Date()}}, {sort: {date: 1}});
};

因此,如果我正确阅读文档,则每当此查询结果更改时,都应重新呈现模板。

我看到的实际行为是,当我第一次加载页面(空的 minimongo 缓存)时,模板没有呈现任何结果。当检测到增量更改并强制重新呈现模板时,项目会神奇地出现,因此大概是在查询返回之前发生初始页面加载,并且随后不会像我预期的那样被动地重新呈现。我究竟做错了什么?管理查询模板依赖项的最佳实践是什么?

更新 - 发布/订阅信息

应该包括发布/订阅。非常简单,我只是在此刻发布所有内容,尽管一旦它起作用,它会变得更聪明。我已经删除了自动发布包。

发布

Meteor.publish("allGames", function(userId) {
    return Games.find();
});

订阅

Meteor.subscribe("allGames", this.userId);

如您所见,我还没有使用 userId

更新 2 - 最小测试用例

我已将其简化为可重现的东西,看起来我对收藏存在根本的误解。我在这里整理了3个测试用例:

https://github.com/antiBaconMachine/meteorCollectionRenderingTests

我看到的 3 个测试的输出是

  1. 没有游戏
  2. 一个计数,后跟与流星服务器启动次数相等的记录
  3. 没有游戏

我希望第一个测试能够反应性地呈现,因为forEach应该获取我认为被车把调用的{{#each}}文档。来自流星文档:

游标是一种反应式数据源。第一次在响应式计算(例如,模板或自动运行)中使用 fetch、map 或 forEach 检索游标的文档时,Meteor 将注册对基础数据的依赖关系。

第二个测试按我的预期工作,这让我感到困惑,因为唯一的区别是我检索了计数。

我假设最后一次测试失败,因为我在文档准备好之前获取文档并且一旦检索到查询不再是反应性的?这只是一个猜测。

对此的任何见解将不胜感激,我有点迷茫。

4

1 回答 1

2

注意:最初的答案和随之而来的错误再现是完全不同的。一个帮助发现了另一个。寻找此答案的第二部分以获取真实信息。

回答最初的问题:

这种行为对我来说很有意义:

让我们看看您的查询:

Games.find({date: {$gte: new Date()}}, {sort: {date: 1}})

您正在查找所有游戏,按日期排序,其日期大于创建查询的日期。

因此,假设您在数据库中有以下项目:

A, date: 100
B, date: 200
C, date: 300

您的客户端 js 已加载,当前时间为350. 您的查询创建为Games.find({ date: {$gte: 350} }, {sort: {date: 1}});. A、B 和 C 肯定落后于350日期,因此不会被渲染。

然后你将一个新游戏插入数据库,比如说D, date: 400。是的,它应该由查看在 . 之后创建的所有内容的查询返回350

你期望什么行为?

更新的补充:

这是一个错误。

这个错误是为鲨鱼渲染引擎提交的。新引擎 (spark) 已解决此问题,并将在下一个 Meteor 版本中发布。(也许 0.7)

当您将 minimongo 游标作为模板数据上下文传递时,就会发生该错误。将数据获取到模板是一种非常不寻常的方式。我想这就是为什么它存在了这么久却没有被发现的原因。

临时解决方法是不将游标作为数据上下文传递。相反,您可以传递 id 或 name 或其他任何内容,然后为被调用者模板提供一个单独的模板助手,该模板返回适当的光标。

一件有趣的事情:您可以将光标嵌入到 #with 块助手中,而不是将光标传递给模板,它会按预期工作:

{{#with games}}
      <ul>
        {{#if this.count}}
            {{#each this}}
            <li class="u-margin--sm">
                <a href="/game/show/{{_id}}" class="col-md-8">{{name}}</a>
            </li>
            {{/each}}
        {{else}}
        <span class="t-small">No games</span>
        {{/if}}
    </ul>
{{/with}}

一切正常:)。

回复:withFetch

如果您使用length而不是count. 当您获取时,游标返回一个普通的 JS 数组,它没有count属性但有length.

于 2013-11-03T23:57:12.090 回答