美文网首页
mongo bsonid 详解

mongo bsonid 详解

作者: 凡城长路 | 来源:发表于2021-11-12 14:40 被阅读0次

    本文将用bsonid=5a17b9d9ab102555b9c38874讲解

    bsonid的结构

    bsonid是一个12字节的值,前4个字节是unix时间戳的秒数,接着是三字节的机器码,然后是2字节的PID,最后是3个字节的增量

    BSONID  0-1-2-3---4-5-6---7-8---9-10-11
    释义    time     machine  pid     inc
    例子    5a17b9d9 ab1025   55b9    c38874
    

    时间戳

    前4位是一个unix的时间戳,精确到秒。是一个int类别,一共四个字节,转换为16进制,共8个字符。例子中的字符串"5a17b9d9"转为10进制是1511504345,也就是北京时间"2017/11/24 14:19:5"

    1. 隐藏了文档的创建时间,ObjectId大致会按照插入进行排序
    2. 记录了插入该记录的时候,该服务器的时间。
    3. 这个值并不是十分的重要,只要能区别就好

    机器ID

    4字节的时间戳后面是3个自己的机器码,区别不同的服务器产生的bsonid。golang的mongo驱动"gopkg.in/mgo.v2/bson"的实现如下

    func readMachineId() []byte {
        var sum [3]byte
        id := sum[:]
        hostname, err1 := os.Hostname()
        if err1 != nil {
            //如果找不到hostname就选择随机字数值
            _, err2 := io.ReadFull(rand.Reader, id)
            if err2 != nil {
                panic(fmt.Errorf("cannot get hostname: %v; %v", err1, err2))
            }
            return id
        }
        hw := md5.New()
        //对hostname MD5,取前三个字节
        hw.Write([]byte(hostname))
        copy(id, hw.Sum(nil))
        return id
    }
    

    PID

    机器码后面的是两个字节的进程ID,取进程ID的最后两个字节16位, 进程ID一般最大16位够描述了。

    b[7] = byte(processId >> 8)
    b[8] = byte(processId)
    

    增量

    增量也就是一个自动增加的计数器。允许256的3次方等于16777216条记录的唯一性,"gopkg.in/mgo.v2/bson"的实现如下,程序会在初始化的时候给给出一个随机的初始值,之后的增量在此值上增加。

    var objectIdCounter uint32 = readRandomUint32()
    
    // readRandomUint32 returns a random objectIdCounter.
    func readRandomUint32() uint32 {
        var b [4]byte
        _, err := io.ReadFull(rand.Reader, b[:])
        if err != nil {
            panic(fmt.Errorf("cannot read random object id: %v", err))
        }
        return uint32((uint32(b[0]) << 0) | (uint32(b[1]) << 8) | (uint32(b[2]) << 16) | (uint32(b[3]) << 24))
    }
    
    ...
    
    i := atomic.AddUint32(&objectIdCounter, 1)
    b[9] = byte(i >> 16)
    b[10] = byte(i >> 8)
    b[11] = byte(i)
    
    ...
    
    

    参考

    MongoDB中ObjectId的误区,以及引起的一系列问题
    http://bsonspec.org/

    相关文章

      网友评论

          本文标题:mongo bsonid 详解

          本文链接:https://www.haomeiwen.com/subject/ducozltx.html