供参考,我有以下结构体:
type OpenOrderCleaned struct {
OrderID string `json:"orderId" bson:"orderId"`
DateTimeOrderPlaced time.Time `json:"dateTimeOrderPlaced" bson:"dateTimeOrderPlaced"`
OrderItems []struct {
OrderItemID string `json:"orderItemId" bson:"orderItemId"`
Ean string `json:"ean" bson:"ean"`
CancelRequest bool `json:"cancelRequest" bson:"cancelRequest"`
Quantity int `json:"quantity" bson:"quantity"`
} `json:"orderItems" bson:"orderItems"`
}
我收到了一个包含多个JSON实例的API响应,我想将其保存在MongoDB中,因此我使用了for循环。我希望通过使用唯一的orderId
字段来检查数据库中是否已经存在文档。我认为UpdateOne
是一个不错的选择,因为它有upsert
选项。因此,如果orderId不存在,就应该生成完整的文档并存储在数据库中。
for _, OpenOrderCleaned := range o.Orders {
c := auth.GetClient()
collection := c.Database("goprac").Collection(x)
filter := bson.M{"orderId": bson.M{"$eq": OpenOrderCleaned.OrderID}}
update := bson.M{
"$set": bson.M{
"orderId": OpenOrderCleaned.OrderID,
"dateTimeOrderPlaced": OpenOrderCleaned.DateTimeOrderPlaced,
"orderItems": OpenOrderCleaned.OrderItems,
},
}
ctx, _ := context.WithTimeout(context.Background(), 15*time.Second)
result, err := collection.UpdateOne(ctx, filter, update)
if err != nil {
fmt.Println("UpdateOne() result ERROR:", err)
os.Exit(1)
} else {
fmt.Println("UpdateOne() result:", result)
fmt.Println("UpdateOne() result TYPE:", reflect.TypeOf(result))
fmt.Println("UpdateOne() result MatchedCount:", result.MatchedCount)
fmt.Println("UpdateOne() result ModifiedCount:", result.ModifiedCount)
fmt.Println("UpdateOne() result UpsertedCount:", result.UpsertedCount)
fmt.Println("UpdateOne() result UpsertedID:", result.UpsertedID)
}
}
但是现在 Upsert
没有起作用。当我手动将文档放入 MongoDB 并运行程序时,它会进行更新。那么为什么没有在数据库中创建新的实例呢?我需要在某个地方声明 upsert=True
吗?或者是 "orderItems": OpenOrderCleaned.OrderItems
的映射不正确吗?
感谢任何帮助。
update
参数不是更新文档时,UpdateOne
似乎会默默失败。在从旧版本迁移代码时,我们忽略了这个变化。 - Zylid
是primitive.NilObjectID时,您是否遇到过问题,导致upsert最终会在id为00000000000的记录中结束?您如何处理这种情况? - Someone Special