9

在 Discover Meteor 示例中,“posts”和“Posts”之间的区别是什么?为什么当我们从服务器插入时使用“posts”,而从浏览器查询时使用“posts”?系统不会因大小写差异而感到困惑吗?

我在posts.js 中看到了客户端帖子到服务器帖子的变量分配。将客户端大写并为服务器使用小型大写字母是一种传统的符号吗?

Posts = new Meteor.Collection('posts')

为什么 server/fixtures.js 使用“帖子”?我假设我们在浏览器(客户端)中查询“帖子”,并在服务器中使用“帖子”,就像我们在流星 mongo 中所做的那样。那么为什么我们现在在服务器中使用 Posts 呢?

4

2 回答 2

38

让我们区分在编写 Meteor 时可能需要处理的不同名称:

  • 变量名称,例如Posts = new Meteor.Collection(...). 这些仅用于您的代码知道如何访问此变量。Meteor 不知道也不关心它是什么,尽管约定是大写的。
  • 集合名称,例如new Meteor.Collection("posts"). 这映射到 MongoDB 集合(在服务器上)或 minimongo 集合(在客户端)的名称。
  • 发布和订阅名称,用在Meteor.publish("foo", ...)or中Meteor.subscribe("foo")。这些必须匹配客户端才能订阅服务器上的某些数据。

您需要在 Meteor 数据模型中匹配两件事:

  1. 出版物名称及其相应订阅
  2. (通常)客户端和服务器上的集合名称,如果使用默认集合模型

订阅名称需要始终与发布名称匹配。但是,为给定订阅发送的集合不需要与订阅名称有任何关系。事实上,可以在一个发布中发送多个游标,或者 在不同发布上发送一个集合,甚至在每个发布中发送多个订阅,它们在客户端中合并为一个。服务器和客户端也可以有不同的集合名称;继续阅读...

让我们回顾一下不同的案例:

  1. 简单的订阅模式。这是您通常在简单的 Meteor 演示中看到的。

    在客户端和服务器上,

    Posts = new Meteor.Collection("posts");
    

    仅在服务器上:

    Meteor.publish("postsPub", function() { 
        return Posts.find() 
    });
    

    仅在客户端:

    Meteor.subscribe("postsPub")
    

    这使用名为 的发布同步Posts集合(posts在数据库中命名)postsPub

  2. 一个出版物中的多个集合。您可以使用数组为单个发布发送多个游标。

    在客户端和服务器上:

    Posts = new Meteor.Collection("posts");
    Comments = new Meteor.Collection("comments");
    

    仅在服务器上:

    Meteor.publish("postsAndComments", function() { 
        return [ 
            Posts.find(), 
            Comments.find() 
        ]; 
    });
    

    仅在客户端:

    Meteor.subscribe("postsAndComments");
    

    这使用名为 的单个发布同步Posts集合以及集合。这种类型的发布非常适合关系数据;例如,您可能只想发布某些帖子以及仅与这些帖子关联的评论。查看可以自动构建这些游标的包CommentspostsAndComments

  3. 单个集合的多个出版物。您可以使用多个出版物为单个集合发送不同的数据切片,这些数据由 Meteor 自动合并。

    在服务器和客户端上:

    Posts = new Meteor.Collection("posts");
    

    仅在服务器上:

    Meteor.publish("top10Posts", function() { 
        return Posts.find({}, {
            sort: {comments: -1}, 
            limit: 10
        });
    });        
    Meteor.publish("newest10Posts", function() { 
        return Posts.find({}, {
            sort: {timestamp: -1},
            limit: 10
        }); 
    });
    

    仅在客户端:

    Meteor.subscribe("top10Posts");
    Meteor.subscribe("newest10Posts");
    

    这会将网站上评论最多的 10 个帖子和 10 个最新帖子推送给用户,用户可以看到两组数据合并到一个Posts集合中。如果最新帖子之一也是评论最多的帖子,反之亦然,则该Posts集合将包含少于 20 个项目。这是一个示例,说明 Meteor 中的数据模型如何允许您在不自己实现细节的情况下进行强大的数据合并操作。

  4. 每个出版物的多个订阅。您可以使用不同的参数从同一出版物中获取多组数据。

    在服务器和客户端上:

    Posts = new Meteor.Collection("posts");
    

    仅在服务器上:

    Meteor.publish("postsByUser", function(user) { 
        return Posts.find({
            userId: user
        });
    });        
    

    仅在客户端:

    Meteor.subscribe("postsByUser", "fooUser");
    Meteor.subscribe("postsByUser", "barUser");
    

    这会导致帖子由fooUserbarUser都显示在posts集合中。当您有几个不同的计算正在查看数据的不同切片并且可能会动态更新时,此模型很方便。请注意,当您在 a 中订阅时Deps.autorun(...),Meteor 会自动调用stop()任何以前具有相同名称的订阅句柄,但如果您在 a 之外使用这些订阅,autorun则需要自己停止它们。截至目前,您不能在autorun计算中使用相同的名称进行两个订阅,因为 Meteor 无法区分它们。

  5. 通过发布推送任意数据。您可以完全自定义发布,以在服务器和客户端上不需要相同的集合名称。事实上,服务器可以发布根本没有集合支持的数据。为此,您可以将API 用于发布功能

    仅在服务器上:

    Posts = new Meteor.Collection("posts"); 
    
    Meteor.publish("newPostsPub", function() {
        var sub = this;
        var subHandle = null;
    
        subHandle = Posts.find({}, {
            sort: {timestamp: -1},
            limit: 10
        })
        .observeChanges({
            added: function(id, fields) {
                sub.added("newposts", id, fields);            
            },
            changed: function(id, fields) {
                sub.changed("newposts", id, fields);            
            },
            removed: function(id) {
                sub.removed("newposts", id);
            }
        });
    
        sub.ready();
    
        sub.onStop(function() {
            subHandle.stop();
        })    
    });
    

    仅在客户端:

    NewPosts = new Meteor.Collection("newposts");
    
    Meteor.subscribe("newPostsPub");
    

    这使用Posts名为. posts_ NewPosts_ 请注意,不同于,它可以做很多其他的事情newpostsnewPostsPubobserveChangesobserve

    代码看起来很复杂,但是当您在发布函数中返回光标时,这基本上是 Meteor 在幕后生成的代码。以这种方式编写出版物可以让您更好地控制发送给客户的内容和不发送给客户的内容。不过要小心,因为您必须手动关闭observe句柄并标记订阅何时准备就绪。有关更多信息,请参阅Matt Debergalis 对此过程的描述(但是,该帖子已过时)。当然,您可以将其与上面的其他部分结合起来,以获得非常细微和复杂的出版物。

很抱歉这篇文章 :-) 但很多人对此感到困惑,我认为描述所有案例会很有用。

于 2013-09-18T19:41:47.430 回答
2

您决定命名约定,流星不在乎。

Posts 成为来自 mongo 服务器的文档集合。您可以通过调用 Posts.find({author: 'jim}) 来查找帖子。在您编写的示例中,流星被告知在内部将该集合称为“帖子”。如果名称相似,希望这很容易记住......

需要有一种方法来表达和跟踪客户可以获得哪些信息。有时可能会有多组不同细节的信息。示例:标题列表的摘要,但特定文档的详细信息。这些通常也称为“帖子”,因此最初可能会令人困惑:

Meteor.publish "posts", ->  # on server
  Posts.find()  

接着

dbs.subscriptions.posts = Meteor.subscribe 'posts'  # on client

发布和订阅名称必须匹配,但都可以这样命名:

PostsDB = new Meteor.Collection('postdocumentsonserver')

所以在mongo中你需要输入

db.postdocumentsonserver.find()

但否则你永远不需要关心'postdocumentsonserver'。然后

Meteor.publish "post_titles", ->
  PostsDB.find({},{fields:{name:1}})  

匹配

dbs.subscriptions.post_titles = Meteor.subscribe 'post_titles'
于 2013-09-18T08:39:20.877 回答