mongodb java驅動關鍵對象轉化

目的

    瞭解mongodb java驅動如何和mongod作數據交互,同時瞭解object json bson的數據格式解析過程

概述

    mongodb採用的java轉json是使用自定義的方法:com.mongodb.util.JSON類來處理;

    轉json:public static String serialize(Object o)

    反轉json:public static Object parse(String s)

    那就看看這兩個方法的具體實現

java object to json

        mongodb java客戶端的對象主要是DBObject及其之類,採用遞歸方式處理嵌套關係,我們也可以從中學習到如何將一個對象轉爲string類型的其他格式。


類型 轉化方式
Null類型: 字符串 null
Boolean類型:對應的值 true
False
Number類型:
Byte Short Integer Long Float Double
BigInteger BigDecimal AutomicInteger
AutomicLong
返回對應數值的字符串
String類型:
這裏的string類型主要是DBObject的key,
對於mongodb,DBObject的key爲{“key”,...}這種格式,
因此要對特殊字符作處理,目前處理如下
\ -> \\ “ -> \* \n -> \\n \r -> \\r
\t -> \\t \b -> \\b
ASCII爲32之前的字符都忽略,這些是控制字符
舉例:
abc -> “abc”
“abc -> “\”abc”
a\b”c -> “a\\b\”c”
ObjectId類型:
對於ObjectId類型,先轉成BasicDBObject方式再進行解析
{“$oid”, objectId.toString()}
如objectId爲:789dsab4adafasdfsdfasdf873294
{“$oid” : 789dsab4adafasdfsdfasdf873294}
Iterable類型:
對於迭代起類型,遞歸調用每個類型進行處理
字符迭代器:[abc, bcd, cde, def ]
DBObject迭代器:[{“abc”, value}, {“bcd”, value }, {“cde”, def} ]
DBObject類型:
根據簡單類型遞歸處理
轉成形如:
{key:{key,value}, key:value}
Map類型:
這個基本不用想了,因爲DBObject本身就繼承自map,
所以map的解析和DBObject一致
同上
Date類型: {“$date”, "yyyy-MM-dd'T'HH:mm:ss.SSS'Z'"}
DBRefBase類型:
轉成DBObject
{”$ref”, ref.getRef(), “$id”, ref.getId()}
byte[]或者Binary: <Binary Data>
數組類型: [“key”:”value”, “key”:”value”]
Pattern類型:
轉DBObject
{"$regex": o.toString(), $options: Bytes.regexFlags(((Pattern) o).flags())}
BSONTimestamp類型:
轉DBObject
{“$ts”:t.getTime(), “$inc”:t.getInc()}
UUID類型:
轉DBObject
{"$uuid":uuid.toString()}
CodeWScope類型:
轉DBObject
{"$code":c.getCode(), "$scope": c.getScope()}
Code類型:
轉DBObject
{"$code":c.getCode()}
MinKey類型:
轉DBObject
{$minKey":1}
MaxKey類型:
轉DBObject
{"$maxKey":1}

json to java object

處理的內容比較明確:

null

NaN

true

false

字符串類型 \' \"

數字類型 0 - 9 + -

數組類型

對象

以上討論針對的是java對象轉成json對象,接下去討論json對象轉化爲bson對象。

這方面的內容bson連接討論的比較詳細,url爲:http://bsonspec.org/#/specification

不過看了這個文檔1個小時後終於把這個文檔的兩個事例看懂,因此有必要在這裏說明下,以便其他觀看文檔的人更容易理解

json to bson

還是現來看一下文檔中提到的兩個例子。

先看第一個

{"hello": "world"}

按格式規範轉應該是如下內容:

int32                                 -- 指定文檔大小,包括結尾的\x00
    \x02 (byte*) \x00                 -- 一個字符標明value的類型,接着是key字符串的byte值,最後以\x00結束
    int32 (byte*) \x00                -- int32是value btye大小加上\x00的長度,接着是value的具體值,最後以\x00結尾
\x00                                  -- \x00結尾

對應的具體形式:

\x16\x00\x00\x00                      -- 本文檔總字節數爲22
    \x02 hello \x00                   -- value類型爲string類型 key的值爲hello     
    \x06\x00\x00\x00 world \x00       -- value字節數爲6(包括結尾的\x00) value值爲world
\x00                                  -- 文檔結束
這樣一劃分,結構就清晰多了

以上簡單格式解析基本能對應上,再來看第二個例子:

{"BSON": ["awesome", 5.05, 1986]}

還是先轉成通用格式,這裏說明下array在bson中是一個內嵌文檔,格式如下{0:array[0], 1:array[1], 2:array[2]}:

int32                               -- 文檔大小
    \x04 (byte*) \x00               -- value類型 key值 結束符
    int32                           -- 內嵌文檔大小
        \x02 (byte*) \x00           -- value類型 key值 結束符
        int32 (byte*) \x00          -- string大小 value值 結束符
        \x01 (byte*) \x00           -- value類型 key值 結束符
        double                      -- value值
        \x10 (byte*) \x00           -- value類型 key值 結束符
        int32                       -- value值
    \x00
\x00


對應的具體形式:

"1\x00\x00\x00                        -- 文檔大小爲49,這裏的1是ascii值
    \x04 BSON \x00                    -- value爲array類型,key值爲bson
    &\x00\x00\x00                     -- 內嵌文檔大小爲38
        \x02 0 \x00                   -- value值的類型爲string, key的值爲0
        \x08\x00\x00\x00 awesome \x00 -- string大小爲8個字節, 值爲awesome
        \x01 1 \x00                   -- value爲double類型,key值爲1
        333333\x14@                   -- 5.05對應的byte[]值,大小爲8B,先調用Double.doubleToRawLongBits( x ),再以long方式寫入。
        \x10 2 \x00                   -- value爲32位整型,key值爲2
        \xc2\x07\x00\x00              -- 4B的值,echo $((12*16 + 2 + 7*16*16)),低位在前,高位在後
    \x00
\x00"

以上兩個列子基本上能瞭解如何把一個json對象轉成bson對象了,這樣在wireshark協議時基本上也沒什麼問題。

bson to json

1.如何判斷key,value編碼方式:

    每字節讀取,分析字節是否爲[0,127];是:表示爲純英文;如果有一個字符不爲這個範圍內的字符,表示包含其他字符方式,採用utf-8方式解碼

2.

後續繼續更新上去,可直接看mongodb源代碼

https://github.com/michel-kraemer/bson4jackson




發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章