Node.js開發入門——MongoDB與Mongoose
為了儲存網站的使用者資料和業務資料,通常需要一個數據庫。MongoDB和Node.js特別般配,因為MongoDB是基於文件的非關係型資料庫,文件是按BSON(JSON的輕量化二進位制格式)儲存的,增刪改查等管理資料庫的命令和JavaScript語法很像。如果你在Node.js裡訪問MongoDB的資料,會有我們是一家人的感覺,特別親切。
我也準備使用MongoDB來作為我的資料庫。
MongoDB使用集合(collection)和文件(document)來描述和儲存資料,collection就相當於表,document相當於行,不過MySQL之類的關係型資料庫,表結構是固定的,比如某一行由若干列組成,行行都一樣,而MongoDB不同,一個集合裡的多個文件可以有不同的結構,更靈活一些。
安裝
到https://www.mongodb.org/downloads下載安裝包,Windows系統是msi檔案,我選擇的是“Windows 64-bit 2008 R2+”這個版本。
安裝非常簡單,你可以預設,也可以選擇安裝位置,我裝到了G盤MongoDB目錄下。安裝完後,目錄結構是這樣的:G:\MongoDB\Server\3.0\。
mongod、mongo以及其它的工具,都在3.0目錄下的bin目錄。
啟動
要使用MongoDB,需要指定一個資料夾讓它存放資料,我在G:\MongoDB下建立了一個名為db的資料夾。
開啟cmd,進入G:\MongoDB\Server\3.0\bin目錄,執行“mongod –dbpath=G:\MongoDB\db”,就會啟動MongoDB,看到下面的圖:
MongoDB啟動後,會監聽在一個埠上等待客戶端來連線,從上圖可以看出,預設監聽的埠是27017。你可以“–port”選項改變這個埠,比如“mongod –port 28018 –dbpath=G:\MongoDB\db”命令就會啟動MongoDB並監聽28018埠。
啟動了MongoDB,我們就可以使用mongo(互動式shell)來管理資料庫了。直接在bin目錄下執行mongo,就可以看到下圖:
mongo Shell預設連線到了test資料庫,還告訴我們可以輸入help來檢視幫助。你可以鍵入help並回車,看看都有哪些命令可用。
注意,mongod預設啟動時不帶鑑權,客戶端連上後就可以隨便操作,建庫、增刪改查等統統可以。你要想限制使用者許可權,可以自己配置下,我這裡就直接往下走了。
資料庫管理
新建資料庫
MongoDB的shell沒有提供新建資料庫的功能,不過你可以這樣:
use accounts
db.createCollection('accounts')
當你使用“use accounts”切換到名為accounts的資料庫時,實際上什麼也沒發生,只有當你呼叫了db.createCollection之後,新的資料庫才被儲存,然後你使用“show dbs”就可以看到新建的庫。
刪除資料庫
刪除資料庫需要切換到指定的庫,然後呼叫dropDatabase()。如下:
use accounts
db.dropDatabase()
呼叫dropDatabase之後,可以使用“show dbs”檢視。
建立集合
之前新建資料庫時已用到,呼叫createCollection即可。
顯示集合
這樣:
use accounts
show collections
獲取指定名字的集合
要得到集合物件,可以這樣:
use accounts
coll = db.getCollection("accounts")
刪除集合
要刪除集合,需要呼叫集合物件的drop()方法。這樣:
use accounts
coll = db.getCollection("accounts")
coll.drop();
向集合中新增文件
要把文件新增到集合,需要先得到collection物件,然後呼叫insert(document)方法。document引數是一個JSON物件。下面的命令往accounts集合裡添加了兩個使用者:
use accounts
coll = db.getCollection("accounts")
coll.insert({name:"ZhangSan",password:"123456"})
coll.insert({name:"WangEr",password:"nicai"})
在集合中查詢
使用集合物件的find()方法,可以列出集合裡的所有文件。這樣:
use accounts
coll = db.getCollection("accounts")
coll.find()
帶引數的find()方法可以根據某個欄位來查詢:
coll.find({name:"ZhangSan"})
從集合中刪除文件
使用collection物件的remove(object)方法可以刪除文件。它的引數是JS物件,它通過將你傳入物件的屬性與資料庫內資料比對來匹配某一個文件,匹配到後刪除,匹配不上就拉倒。假如你傳遞一個空的JS物件,就會刪除這個集合裡所有的文件。比如下面這樣:
use accounts
coll = db.getCollection("accounts")
coll.insert({name:"QianQi",password:"888888"})
coll.find()
coll.remove({name:"WangEr"})
coll.find()
coll.remove({})
coll.find()
更新集合中的文件
collection物件提供了兩種方法來更新文件:save(object)和update(query, update, options)。
save可以直接更新一個物件,下面的程式碼將ZhangSan的密碼修改為567890:
coll.save({_id:ObjectId("55cc25b360bcee730bafd2bf"),name:"ZhangSan",password:"567890"})
下面的update方法與上面的save效果一樣:
coll.update({name:"ZhangSan"},{name:"ZhangSan",password:"567890"})
update()的第二個引數update是一個物件,能指定更新時用的運算子,比如$set可以設定欄位的值,下面程式碼與前面等效:
coll.update({name:"ZhangSan"},{$set: {password:"567890"}});
使用mongoose管理資料庫
Node.js有針對MongoDB的資料庫驅動:mongodb。你可以使用“npm install mongodb”來安裝。
mongoose構建在mongodb之上,提供了Schema、Model和Document物件,用起來更為方便。
我們可以用Schema物件定義文件的結構(類似表結構),可以定義欄位和型別、唯一性、索引和驗證。Model物件表示集合中的所有文件。Document物件作為集合中的單個文件的表示。mongoose還有Query和Aggregate物件,Query實現查詢,Aggregate實現聚合。
廢話不多說,看看怎麼使用吧。
安裝mongoose
使用express準備一個TestMongoDB專案,命令序列如下:
express TestMongoDB
cd TestMongoDB
npm install
執行完上面的命令後,使用下面的命令安裝mongoose:
npm install mongoose --save
這個命令會安裝mongoose並將其作為專案的依賴,而mongoose依賴的MongoDB driver以及regexp等等模組也會被自動安裝。
使用mongoose
建議先看mongoose官方的quick start教程:http://mongoosejs.com/docs/index.html。講得很到位,雖然是E文,也很容易理解,讀之有如荒漠遇甘泉。
使用mongoose可以新建資料庫、新建集合、對集合內的文件進行CRUD操作,在寫程式碼時,可以對照著mongo shell驗證結果是否符合預期。
在TestMongoDB下新建一個mongo.js檔案,內容如下:
var mongoose = require('mongoose');
mongoose.connect('mongodb://localhost/accounts');
var db = mongoose.connection;
db.on('error', console.error.bind(console, 'connection error:'));
db.once('open', function() {
console.log('mongoose opened!');
var userSchema = new mongoose.Schema({
name:{type: String, unique: true},
password:String
},
{collection: "accounts"}
);
var User = mongoose.model('accounts', userSchema);
User.findOne({name:"WangEr"}, function(err, doc){
if(err) console.log(err);
else console.log(doc.name + ", password - " + doc.password);
});
var lisi = new User({name:"LiSi", password:"123456"});
lisi.save(function(err, doc){
if(err)console.log(err);
else console.log(doc.name + ' saved');
});
});
上面的檔案,直接執行“node mongo.js”命令即可檢視效果。
要使用mongoose,先require,然後使用connect方法連線資料庫。connect原型:
connect(uri, options, [callback])
uri的格式類似:“mongodb://user:[email protected]:port/database”。
mongoose的connection物件定義了一些事件,比如connected、open、close、error等,我們可以監聽這些事件。
在我們的示例程式碼裡,我監聽了open事件,在回撥函式中,定義了Schema,呼叫mongoose.model來編譯Schema得到Model物件。需要注意的是,定義Schema時指定的collection名字與mongoose.model的第一引數要保持一致。
拿到了Model物件,就可以執行增刪改查等操作了。Model物件有find()、findOne()、update()、remove()等方法,和我們在mongo shell裡的用法類似。這些方法都有一個可選的callback,當你提供這些callback時,執行的結果會通過這個callback返回給你。如果你不提供,這些方法會返回一個Query物件,你可以再通過Query組裝新的選項,然後呼叫Query的exec(callback)來提交查詢。
我在程式碼裡查詢WangEr的檔案時用了callback,沒用Query。
Model物件有個Model(doc)方法,用來構造一個文件(Document)。建立Lisi的文件時就是這種Document物件的save()方法可以將文件儲存到資料庫。
Mongoose就說這麼多吧,很多詳細的用法,用到時參考API文件吧,多數API都提供有示例程式碼片段。
其它文章: