mongoskin 学习总结
在node.js环境下使用mongoskin 操作mongoDB .
mongoskin 的安装非常简单 npm install mongoskin
mongoskin 的使用,上一篇博文已经说过,你可以返回去瞄一眼, 我是伟大的传送带
下面的内容针对 mongoskin 操作 mongoDB 的api来说明:
查
这应该是所有数据库的灵魂,通过简单的api可以帮助我们从海量数据库总准备找到自己想要的数据.
查询多条数据
原生方法: find()
使用: db.集合名.find([option])
[option] 为可选条件,可以空,也可以指定条件,如 {name:'xiaoxiao'}
查找当前集合下满足条件的所有数据.
返回值是一个游标,自动从 0 遍历符合条件的所有文档.
mongoskin 封装方法: find([option],callback)
[option] 同上为可选条件.
名称和原生的find() 方法同名,但是实现功能却不同.
返回值是一个对象,此对象上实现了好多方法来处理 find() 查找到的结果,返回内容如下:
你可以用上面的方法对find() 查找到的结果继续做二次处理,比如这样
db.集合名.find({name:'xiaoxiao'}).toArray(function(error,arrResult){ //这里的 arrResult 是一个查找结果数组 arrResult.forEach(function(item){ console.log(JSON.stringify(item)); }); }); //还有另外一种等价写法 db.集合名.find({name:'xiaoxiao'},function(error,result){ //这里的result仍然是一个对象,可以调用上图中的任意api result.each(function(err,person){ console.log(JSON.stringify(person)); }); });
查询一条数据
原生方法 findOne([option])
[option] 为选填条件.
返回符合条件的第一个文档.
mongoskin 对应的方法 findOne([option],callback)
最直观的就是看到mongoskin 多了一个回掉函数.[option] 同样为选填条件
使用也比较简单
db.集合名.findone({name:'xiaoxiao'},function(error,info){ //回掉函数直接拿到了查找到的info实体. })
1. $ne (不等于)
personCollection.find({age:{$ne:'2'}},function(error,result){ result.each(function(error,item){ console.log('==========>',item); }) })
上面的修改器 $ne 表示 age 字段不为 '2' 的所有指.
2. $in (某值是否在此指定的范围,后面一般指定一个范围数组,数组里面值的类型可以不相同) <---> $nin (和前面$in 正好相反,表示不在某个数组范围里)
personCollection.find({age:{$in:['2','3','4','5']}},function(error,result){ result.each(function(error,item){ console.log('==========>',item); }) })
上面修改器表示age 的值在后面数组给定的值的成员有哪些.(目前库里只有如下一条数据符合结果)
3. $lt, $lte, $gt, $gte 分别代表 <, <=,>, >=,它们是用来设置查询范围
personCollection.find({age:{$lte:'3'}},function(error,result){ result.each(function(error,item){ console.log('==========>',item); }) })
上面代码表示年龄 age 字段小于等于3的有哪些成员. 其他三个用法相同.
4. $or 或者,也是指定一个范围来使用,但与上面最大的差别在于, $in ,$nin 有且只有一个数组范围,而 $or 则可以是多个数组范围内满足条件
personCollection.find({$or:[{name:'王二小'},{age:'2'}]},function(error,result){ result.each(function(error,item){ console.log('==========>',item); }) })
上面代码表示查找 name 为'王二小' 或者 age 为'2' 的用户
增
把一个文档插入mongoDB 中, insert api用法比较简单,原生的api 和 mongoskin 基本一致.
原生方法 insert(doc) doc为必选项
var doc={name:'xiaoxiao',age:2}; db.集合名.insert(doc);
mongoskin 对应的方法 insert(doc,callback) doc为必选项,同时比原生的方法多了callback 回掉函数
var doc={name:'xiaoxiao',age:2}; db.集合名.insert(doc,function(error,result){ error?callback('insert fail',error):callback(null,result); });
改
数据修改2个api ,
原生方法:
update({查询字段},{修改部分})
findAndModify({查询字段},[排序字段],{修改部分},{配置属性});
mongoskin 方法:
update({查询字段},{修改部分},function(error,result){ //异步回掉函数 });
findAndModify({查询字段},[排序字段],{修改部分},{配置属性},function(error,result){ //异步回掉函数} });
原生的方法和mongoskin提供的方法参数一致,mongoskin只是支持异步回掉方式.
修改内容涉及到2种情况
(1)修改全局doc
(2)修改部分字段
当修改全部doc时: 数据库中之前有一条数据 {_id:'1111111',name:'xiaoxiao',age:'2'}
personCollection.update({_id:'1111111'},{_id:'1111111',name:'xiao',age:'7'},function(error,result){ console.log('========>',error,result); }) personCollection.findOne({_id: '1111111'}, function (error, result) { console.log('=======>', error, result); })
输出结果:
zhangzhi@moke:~/code/test$ node mongoTest.js ========> null 1 =======> null { _id: '1111111', name: 'xiao', age: '7' }
如果部分字段修改,要涉及到mongodb 总的修改器(修改器涉及的东西比较多,此文会不断更新.......)
$set (更新字段) <------> $unset (删除字段)
$set 修改对象 {_id:'1111111',name:'xiao',age:'7'} 中 name 为 '小小' age 为 '2'
personCollection.update({_id:'1111111'},{$set:{name:'小小',age:'2'}},function(error,result){ personCollection.findOne({_id: '1111111'}, function (error, result) { console.log('=======>', error, result); }) })
第一层回掉函数里嵌套的 findOne 函数只是为了打印出来看看是否更新成功,如果如下:
zhangzhi@moke:~/code/test$ node mongoTest.js =======> null { _id: '1111111', age: '2', name: '小小' }
ok,修改器成功修改字段 name 和 age 对应的值.
findAndModify 函数比较灵活,推荐使用此api ,如果要找的doc不存在则会自动创建新的doc,如果文档存在则更新,
参数比较多,我们一一说明,然后用doc 全部对象更新和 修改器局部字段更新方法走一遍.
mongoskin 中的 findAndModify({查询字段},[排序字段],{修改部分},{配置属性},function(error,result){ //异步回掉函数} });
查询字段: 如 {_id:'1111111'} 不论find 还是 Modify 必须依赖此字段在数据库中查找.
排序字段: 如 {age:1} 按顺序排列, {age:-1} 按倒序排列
修改部分: 如 全部文档 {_id:'1111111',name:'xiaoxiao',age:'8'} 部分字段修改 {$set:{name:'xiao',age:'9'}}
配置属性: 如 {new:true,upsert:true} //new 表示是否返回修改后的新对象, upsert 表示是否执行更新操作
personCollection.findAndModify({_id: '1111111'}, [], {$set: {name: '张小小', age: '2'}}, {new: true, upset: true}, function (error, result) { console.log('=======>', error, result); })
输出结果:
当修改数据并不是一个对象,而是对象的某个字段,更新局部内容,涉及到的修改器
$inc 按步长增加,比如给 age 字段增加1
personCollection.findAndModify({_id:'1111111'},[],{$inc:{age:1}},{new:true,upset:true},function(error,result){ console.log('=======>', error, result); });
$push 当更新的字段是一个数组,可以使用此修改器追加元素到数组里.
personCollection.findAndModify({_id:'1111111'},[],{$push:{tag:'一介布衣'}},{new:true,upset:true},function(error,result){ console.log('=======>', error, result); });
$pushAll 和 $push功能一致,只不过这个功能更强大,支持追加一个数组到原数组
personCollection.findAndModify({_id:'1111111'},[],{$pushAll:{tag:['node.js','javascript','nosql']}},{new:true,upset:true},function(error,result){ console.log('=======>', error, result); });
$addToSet 也是向数组追加元素,他的本领在于可以过滤数组里是否已经有此元素,如果有就不添加,如果没有就继续添加.具体使用中非常有用.
personCollection.findAndModify({_id:'1111111'},[],{$addToSet:{tag:'一介布衣'}},{new:true,upset:true},function(error,result){ console.log('=======>', error, result); });
因为上面已经添加过标签 "一介布衣" ,所以在这里继续添加时没有重复插入.
$pop 删除数组头部或者尾部删除一个值 {$pop:{filed:-1}} 从头删除, {$pop:{filed:1}} 从尾部删除
personCollection.findAndModify({_id:'1111111'},[],{$pop:{tag:-1}},{new:true,upset:true},function(error,result){ console.log('=======>', error, result); });
上面的代码把 tag 数组的头一个元素删除了,见下图
$pull 也是从数组中删除元素,他的独特功能是删除指定的元素 $pullAll 从元数组总删除指定数组中的元素.
personCollection.findAndModify({_id:'1111111'},[],{$pull:{tag:'nosql'}},{new:true,upset:true},function(error,result){ console.log('=======>', error, result); });
'nosql' 标签被删除了.接着看 $pullAll 的效果
personCollection.findAndModify({_id:'1111111'},[],{$pullAll:{tag:['node.js','javascript']}},{new:true,upset:true},function(error,result){ console.log('=======>', error, result); });
如上图 数组['node.js','javascript'] 中的2个元素都从 person 对象中删除,最后返回的对象, tag 数组已经为空.