Javascript 发布/订阅Meteor返回整个集合

Javascript 发布/订阅Meteor返回整个集合,javascript,mongodb,meteor,reactjs,Javascript,Mongodb,Meteor,Reactjs,我正在为我的Meteor应用程序实施发布/订阅架构。我还没有删除autopublish。我将React和kadira:flow router与kadira:React布局一起使用。它很好用 这是我的发布代码(/lib/publications.js,尽管我也尝试了/server/publications.js,没有更改): 当然,如果我在/server中使用它,我不会添加if语句。我在路由器中订阅这些出版物,如下所示(/lib/routing.js): 然后我在React组件中获得数据,如下所示

我正在为我的Meteor应用程序实施发布/订阅架构。我还没有删除
autopublish
。我将React和
kadira:flow router
kadira:React布局一起使用。它很好用

这是我的发布代码(
/lib/publications.js
,尽管我也尝试了
/server/publications.js
,没有更改):

当然,如果我在
/server
中使用它,我不会添加
if
语句。我在路由器中订阅这些出版物,如下所示(
/lib/routing.js
):

然后我在React组件中获得数据,如下所示(
/client/components/pages/game\u page.jsx
):

我从所有游戏中获取所有消息,而不是获取
gameId
等于传递的参数的所有消息。如果我删除发布/订阅,只需请求如下数据:

// ...
mixins: [ReactMeteorData],
getMeteorData: function() {
    return {
        messages: Messages.find({gameId: gameId}, {sort: {createdAt: -1}}).fetch()
    }
},
// ...
getMeteorData: function() {
    return {
        messages: Messages.find({}).fetch()
    }
},
getMeteorData: function() {
    return {
        messages: Messages.find({gameId: gameId}, {sort: {createdAt: -1}}).fetch()
    }
},

它工作得非常好。知道为什么吗?我想我遗漏了一些东西:关于发布/订阅本身,或者关于在路由器中使用订阅。

您必须删除自动发布包,因为默认情况下它发布集合中的所有内容


据我所知,每个订阅都会公开集合中的一些文档,因此,如果您对同一个集合有两个订阅,那么当您查询集合时,您将可以访问两个订阅公开的所有文档,因此它是累积的。

Autopublish package将所有数据发布到客户端(这就像您订阅了一个对所有集合执行
集合的发布。在所有集合上查找({})
)。这意味着您的自定义发布/订阅在示例中实际上不执行任何操作,如果您像这样查询数据:

// ...
mixins: [ReactMeteorData],
getMeteorData: function() {
    return {
        messages: Messages.find({gameId: gameId}, {sort: {createdAt: -1}}).fetch()
    }
},
// ...
getMeteorData: function() {
    return {
        messages: Messages.find({}).fetch()
    }
},
getMeteorData: function() {
    return {
        messages: Messages.find({gameId: gameId}, {sort: {createdAt: -1}}).fetch()
    }
},
您只会收到所有消息,这是正确的行为

无论如何,您应该始终在数据查询中进行如下显式查询:

// ...
mixins: [ReactMeteorData],
getMeteorData: function() {
    return {
        messages: Messages.find({gameId: gameId}, {sort: {createdAt: -1}}).fetch()
    }
},
// ...
getMeteorData: function() {
    return {
        messages: Messages.find({}).fetch()
    }
},
getMeteorData: function() {
    return {
        messages: Messages.find({gameId: gameId}, {sort: {createdAt: -1}}).fetch()
    }
},
因为如果您碰巧同时有两个不同的邮件订阅(出于不同的目的,即一个订阅一条包含所有详细信息的邮件,另一个订阅另一条包含较少详细信息/字段的邮件),此数据查询
messages.find({})
将使您获得在两个订阅中订阅的文档的联合,这可能不是您所期望的


因此,在您的情况下,删除autopublish包,并在数据访问中添加此显式查询(
messages:messages.find({gameId:gameId},{sort:{createdAt:-1})。fetch()
).

游戏id设置在哪里?我怀疑它最初是未定义的,因此meteor订阅了整个集合。因为它再也不会取消订阅,即使以后,同样的订阅会再次运行,你也不会丢失这些集合条目。它是从路线中获取的。
/game/:id
和作为
params.id
传递到订阅中。如果在
this.register(…)之前有I
console.log(params.id)
它正确地返回id。是的。在重写代码的某些部分以便更易于管理和更适合组件之后,我必须同意这是实际的答案。
autopublish
需要删除,
find({})
是不够的。需要在
getMeteorData
中进行完整的MongoDB查询。