mgo 将 objectid 设置为 objectid hex,Mongodb 似乎无法读取

mgo is setting objectid to objectidhex, which doesnt seem to get read by Mongodb

我正在尝试使用 ObjectId 进行查询,通常在 mongodb 你会做这样的事情

db.collection.findOne({"_id":objectid("5d9d90e5ed645489aae6df64")})

这在我进行普通查询时有效,但在 go lang 中它给出了

的值
ObjectIdHex("5d9d90e5ed645489aae6df64")

而不是导致有效查询。

我已经多次阅读 mgo 文档试图使用

bson.ObjectId("5d9d90e5ed645489aae6df64")

但它仍然是一个我不明白的十六进制。我尝试了一些不同的组合,但它们几乎都只是在黑暗中拍摄。

Go 语言处理程序

package userhandlers

import (
    "log"
    "net/http"
    //"fmt"
    //"go.mongodb.org/mongo-driver/bson/primitive"
    //"go.mongodb.org/mongo-driver/bson"
    "labix.org/v2/mgo/bson"

    //Services
    databaseservice "malikiah.io/services/databaseService"
    passwordservice "malikiah.io/services/passwordService"

    //Structs
    userstructs "malikiah.io/structs/userStructs"
    databasestructs "malikiah.io/structs/databaseStructs"
)

func LoginHandler(response http.ResponseWriter, request *http.Request) {
    response.Header().Set("Content-Type", "application/json")
    response.WriteHeader(http.StatusOK)

    databaseQuery := databasestructs.Find{
        ID: bson.ObjectId(request.FormValue("_id")),
        MongoCollection: "users",
        Criteria: "_id",
        CriteriaValue: "",
        FindAll: false,
    }
    log.Println(databaseQuery)
    databaseservice.Login(databaseQuery)
}

Go 语言结构

package databasestructs

import (
    //"go.mongodb.org/mongo-driver/bson/primitive"
    "labix.org/v2/mgo/bson"
)

type Find struct {
    ID                      bson.ObjectId   `json:"_id,omitempty" bson:"_id,omitempty"`
    MongoCollection         string              `json:"mongoCollection,omitempty" bson:"mongoCollection,omitempty"`
    Criteria                string              `json:"criteria,omitempty" bson:"criteria,omitempty"`
    CriteriaValue           string              `json:"criteriaValue,omitempty" bson:"criteriaValue,omitempty"`
    FindAll                 bool                `json:"findAll,omitempty" bson:"findAll,omitempty"`
}

Go 语言函数

package databaseservice

import (
    "context"
    "log"

    //Structs
    userstructs "malikiah.io/structs/userStructs"
    databasestructs "malikiah.io/structs/databaseStructs"

    //"go.mongodb.org/mongo-driver/bson"
    "go.mongodb.org/mongo-driver/mongo"
    "go.mongodb.org/mongo-driver/mongo/options"
    "gopkg.in/mgo.v2/bson"

)

func Find(databaseQuery databasestructs.Find) (result string) {
    // Set client options
    clientOptions := options.Client().ApplyURI("mongodb://localhost:27017")

    // Connect to MongoDB
    client, err := mongo.Connect(context.TODO(), clientOptions)

    // Database name
    db := client.Database("malikiah")
    collection := db.Collection(databaseQuery.MongoCollection)

    if err != nil {
        log.Fatal(err)
    }

    if databaseQuery.Criteria == "_id" {
        log.Println(databaseQuery.ID)
        result := collection.FindOne(context.TODO(), bson.M{databaseQuery.Criteria: databaseQuery.ID}).Decode(&result)
        log.Println(result)
    } else if databaseQuery.Criteria == "" {

    } else if databaseQuery.FindAll == true {

    } else {

    }
    return
}

请注意,labix.org/v2/mgo 已不再维护,如果您想使用 mgo,请改用 github.com/globalsign/mgo。或者新的官方 mongo-go driver.

bson.ObjectId 是一种以 string 作为基础类型的类型:

type ObjectId string

所以当你像这样填充你的对象时:

databaseQuery := databasestructs.Find{
    ID: bson.ObjectId(request.FormValue("_id")),
    MongoCollection: "users",
    Criteria: "_id",
    CriteriaValue: "",
    FindAll: false,
}

bson.ObjectId(request.FormValue("_id")) 是 "nothing more" 那么类型 conversion. You convert the hex object ID string to bson.ObjectId, but this is not what you want. You want to parse the hex object ID. For that, use the bson.ObjectIdHex() function:

databaseQuery := databasestructs.Find{
    ID: bson.ObjectIdHex(request.FormValue("_id")),
    MongoCollection: "users",
    Criteria: "_id",
    CriteriaValue: "",
    FindAll: false,
}

请注意,如果传递的字符串是无效的十六进制对象 ID,bson.ObjectIdHex() 将出现混乱。使用 bson.IsObjectIdHex() to check it prior to calling bson.ObjectId(). For details, see .

如果你想使用官方驱动而不是mgo,你可以使用primitive.ObjectIDFromHex()函数来创建ObjectId,例如:

id, err := primitive.ObjectIDFromHex(request.FormValue("_id"))
if err != nil {
    // Handle error
    return
}
// If no error, you may use it:
databaseQuery := databasestructs.Find{
    ID: id,
    // ...
}