前言
了解到这个框架其实是还是因为看书,然后花了一个星期作用把翻译出来的官方文档看了一遍,代码也跟着走了一遍,也算是有了个大概的认识吧。这里写一下体会吧。
简介
首先什么是Meteor(中文翻译:流星),我觉得取这个名字就是有它的意义的,因为用这个框架开发真的很快,就好像流星一样。它是一个基于Node.js和Mongodb的框架,使用DDP(分布式数据协议)在客户端和服务器间传送数据。这个是什么意思呢,也就是,我的数据资源在我客户端有一份,在我的服务器也有一份,我在操作客户端的时候,就不需要等待服务器那边的,马上可以做出响应,那么如果这个操作是非法的呢?也就是服务器那边没有操作成功,那客服端这边知道了以后,就会恢复了,这个有什么好处呢,这样只有我们的逻辑写的足够强壮的话,就不会出现服务器那边操作失败的情况了,这样我们就可以让客户端这里马上得到效果,无需等待。
结构
关于安装和使用在这里就不详细说了,首先介绍一下它的目录结构吧
这个就是Meteor1.04版本的一个目录结构,newmyapp就是我的项目的名称,.meteor就是他的核心文件,这个我们一般不用去管它,剩下的就是一个client和一个server的文件夹和一个package.json和git的忽略文件(里面就是忽略掉node_modules的文件,这个是我在这里可能使用了npm来安转Node.js的包?),就那么简单,client文件夹放客服端的文件,server文件夹放服务器的文件。不过我们在实际项目中,是会不断的添加目录的。我的项目目录就是下面这样的
可以看到多了好几个文件夹,我们一个一个来说
meteor 加载文件步奏
在 /lib 中的文件优先加载
所有以 main.* 命名的都在其他文件载入后载入
其他文件以字母顺序载入
- collection
这个文件夹里面存放着 Meteor 集合,《集合是一个特殊的数据结构,它将你的数据存储到持久的、服务器端的 MongoDB 数据库中,并且与每一个连接的用户浏览器进行实时地同步》这一段是来自官方的介绍,看起来是不是不知道在说什么,其实简单理解就是,这里保存了一些数据库的资源合集和特定数据库操作的方法和数据库操作规则,上代码吧 ./collections/posts.js
//这里就是所谓的集合,我们在这里定义了这个Posts就是一个对于数据库posts表的资源链接,这样我们就可以在客服端和服务器那边操作这个posts表了
Posts = new Mongo.Collection('posts');
//这里就是对于操作数据库自定义方法的一些限制,我们总不可能让其为所欲为
Posts.allow({
update: function(userId, post) {
// 只允许修改自己的文章
return ownsDocument(userId, post);
},
remove: function(userId, post) {
// 只允许修改自己的文章
return ownsDocument(userId, post);
}
});
Posts.deny({
update: function(userId, post, fieldNames, modifier) {
// 需要完成修改的时候不允许修改为已经存在的url
var rs = Posts.findOne({ url: modifier.$set.url, _id: { $ne: post._id } });
if (rs) {
return true;
}
return (_.without(fieldNames, 'url', 'title').length > 0);
}
});
Posts.deny({
update: function(userId, post, fieldNames, modifier) {
var errors = validatePost(modifier.$set);
return errors.title || errors.url;
}
});
validatePost = function(post) {
var errors = {};
if (!post.title)
errors.title = "请填写标题";
if (!post.url)
errors.url = "请填写URL";
return errors;
}
//还可以写一些自定义的操作
Meteor.methods({
postInsert: function(postAttributes) {
check(this.userId, String);
check(postAttributes, {
title: String,
url: String
});
var errors = validatePost(postAttributes);
if (errors.title || errors.url)
throw new Meteor.Error('invalid-post', "你必须为你的帖子填写标题和 URL");
var postWithSameLink = Posts.findOne({ url: postAttributes.url });
if (postWithSameLink) {
return {
postExists: true,
_id: postWithSameLink._id
}
}
var user = Meteor.user();
var post = _.extend(postAttributes, {
userId: user._id,
author: user.username,
submitted: new Date(),
commentsCount: 0,
upvoters: [],
votes: 0
});
var postId = Posts.insert(post);
return {
_id: postId
};
},
upvote: function(postId) {
// 检查数据类型