最近在用mongoDB搭建可视化系统的数据库,记录一下使用过程中解决的问题
目录结构:
- 1.将csv文件导入到mongoDB
- 2.使用mongoose建Model时,集合名称自动加s变复数的问题
- 3.mongoDB数据库中将时间从字符串格式转换成Date日期格式
- 4.循环集合更新文档中的某些字段**
- 5.node.js+mongoDB教程**
1.将csv文件导入到mongoDB
手头的原始数据是csv格式的,要用mongoDB数据库首先遇到的问题就是这样导入数据,使用mongoimport命令即可,具体命令如下:
mongoimport -d users -c contacts --type csv --file path/of/file/to/import.csv
其中:
-d: 即--db的缩写,将csv文件导入的数据库
-c: 即--collection的缩写,csv在数据库中保存的集合名称
更多可选参数信息见官方文档
- 如果csv文件第一行是字段名称,则使用--headerline
mongoimport -d users -c contacts --file /path/of/file/to/import.csv --headerline
- 如果csv文件没有字段名称,则使用--fieldFile另行指定字段名称所在文件,字段名文件中,每行写入一个字段,不需要用逗号分隔,字段文件的格式可以为csv, txt等。
mongoimport -d users -c contacts --file /path/of/file/to/import.csv --fieldFile /path/of/fieldfile.csv
【!】这里我遇到一个问题,在怎么运行以上命令都报错,SyntaxError: missing ; before statement。这时只要退出shell即可,以上命令是在mongoDB安装目录下运行的,而不是shell中。
导入json,tsv格式的文件也是类似的操作,详见官方文档
2.使用mongoose建Model时,集合名称自动加s变复数的问题
【问题描述】
在使用mongoose连接mongoDB数据库的过程中,先建Schema,再建Model,分别如下:
...
//建Schema
var MovieSchema = new mongoose.Schema({
name: String,
password: String
});
...
//建Model
var Movie = mongoose.model('Movie', MovieSchema);
...
这样写本以为会添加到数据库Movie集合中,实际操作时会在数据库中新建集合movies,并完成添加操作。
如果建Model时,如下这样写,则会正常添加到movies集合中(没有movies,则创建并添加)。
var Movie = mongoose.model('movies', MovieSchema);
【原因分析】
由以上现象可以推断mongoose在内部创建collection时将我们传递的collection名小写化,同时如果小写化的名称后面没有字母s,则会在其后面添加s,因此出现创建集合movies。
【解决办法】
只要在创建Schema和Model的时候稍加改动,就可以免去小写化和自动+s的困扰,创建方法如下:
var MovieSchema = new mongoose.Schema({
name: String,
password: String
},{collection:'movie'});
var card = mongoose.model('movie', MovieSchema , 'movie');
3.mongoDB数据库中将时间从字符串格式转换成Date日期格式
在数据库中,有同是String类型的日期字段和时间字段,如下图,现在想把它们组装成一个Date类型的字段。
最开始的时候我是这样写的
var newDate = new Date("2015-04-01 19:20:33");
但是一直提示Invalid Date,百思不得解,直到我在Stack Overflow上看到这个问题Converting string to date in mongodb,原来是字符串拼接的问题。
下面是可以正常完成转换的格式中的一种
var newDate = new Date("2015 04 01 19:20:33 +0800");
格式可以正常转换了,但是有遇到另外一个问题,转换前后的数据是下图这样的
转换后的时间刚好少了8小时,而UTC(世界标准时间)刚好比CST(中国标准时间)晚8小时,即Robomongo的默认显示是时间标准时间,可以在设置中调整为所在地时区,调整方法如下图
调整后的时间显示,如下图
4.循环集合更新文档中的某些字段
转换一个doc的时间问题解决了,那么怎么更新正个集合的时间呢,最开始我的想法是这样的
db.collectionName.find({}).forEach(function (doc) {
doc.dateTime = new Date("dateJoinTIme");
print( doc.dateTime );
});
但是shell报错
TypeError: db.getCollection(...).find(...).foreach is not a function
【解决办法】使用 "Bulk"
具体的使用方法如下,这里用到了我在3中提到的转换时间的方法:
var collection = db.getCollection('test');
var bulkOp = collection.initializeOrderedBulkOp();
var count = 0;
collection.find().forEach(function(doc) {
//重新组装new Date()中的时间字符串
var dd = doc.date.split('-');
var newDate = new Date(dd[0]+' '+dd[1]+' '+dd[2]+' '+':'+doc.time+' +0800');
//更新dateTime字段,没有此字段则添加字段
bulkOp.find({ '_id': doc._id }).updateOne({
'$set': { 'dateTime': newDate }
});
//删除文档中的某个字段
bulkOp.find({ '_id': doc._id }).updateOne({
'$unset': { 'time': doc.time }
});
count++;
if (count % 100 === 0) {
// 每100次操作后执行一次,并完成bulkOp的初始化
bulkOp.execute();
bulkOp = collection.initializeOrderedBulkOp();
}
});
// 清理队列
if (count > 0) {
bulkOp.execute();
}
5.node.js+mongoDB教程
在不断的遇到问题解决问题的过程中,查了一些书,不得不感慨技术更新换代太快,技术前进的速度远远超过了书的翻译速度,网上教程帮的很大忙,下面列举的这些教程不能说是完美无缺,但是在我搭建数据库和后台系统的过程中给了我很大的帮助,思路清晰明了,帮助我在极短的时间内快速上手。
mongoDB: 8篇mongoDB教程
express+mongoose: 目前14篇,还在更的一套比较完整的教程
node.js+mongoose: 一套简单的实现增删改查的样例
【参考资料】
mongoimport
CNode社区
4循环更新集合中的文档-Stack Overflow