首先要理解 MongoDB 儲存的格式 BSON,就是 Binary JSON,雖然呈現都是 JSON 格式,但儲存還是有型別之分,這就是 BSON 的優點。
BSON 型別有以下幾種,常見的就不特別說明了
embedded document
或 nested document
,更白話的說就是文件內的子文件,如範例的 publisher
欄位:{
"_id": ObjectId("612cf44a031915cb2af17374"),
"name":"Barcraft",
"publisher":
{
"companyName":"Clizzard",
"country":"Taiwan",
"city":"Taipei"
}
}
{
"_id": ObjectId("612cf44a031915cb2af17374"),
"regexField": /[1-5]/
}
{
"_id": ObjectId("612cf44a031915cb2af17374"),
"jsCode": "function() {var a = 1;}"
}
--
資料型別有很多,不過使用上多半還是原始的那幾種,比較多人討論到的是時間型別。
Date
我本身還真的沒使用過,大部分都是使用Timestamp
就能解決,且還有時區問題,如果沒開發過跨時區系統,請務必縝密思考使用情境,例如不同時區的使用者如何查詢資料。
ObjectId
長相如下:_id: ObjectId("612cf44a031915cb2af17374")
_id 是由16進位、24字元所組成的(請特別注意並不等於 string),故 ObjectId 為 12 bytes,這 12 bytes 組成依序為:
特別要注意的是 timestamp 精確度只到秒級;第二項的隨機碼又可拆分為
*註:這個項目在 MongoDB document 已經移除細節討論,不過還是可以從過往文章來了解
所以最常被提及到的是,「系統產生的 _id 是否會重複?」關於這個答案其實可以從拆分的這 12 bytes 得到答案,在非刻意的情況下,理論上是有可能重複的。假設一秒內一台機器的同一個process,產生超過 3bytes 的計數器數量,就有可能會重複了。但在大部分商務情境使用,應該是沒什麼機會遇到
可以,只要你確保 Collection 層級的唯一性。
假設這是一個會員 Collection,那通常 MemberId
就相當適合當作 _id 欄位,因為 MemberId 是不會重複的,且可以快速地找到這筆資料,是上上之選。
其實上面的問題就給出答案了,不需要。
int, long 都可以當作是 _id 的型別,只是 MongoDB 幫你產生的是 ObjectId。
本系列文章會同步發表於我個人的部落格 Pie Note