You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

MongoDB使用Decode解码嵌套结构体时字段为空的问题

MongoDB检索嵌套对象为空的问题解决

问题描述

我有一个模型可以正常生成JSON文档,但在检索文档时,嵌套的JSON对象为空。

查询代码

func (r *CourseRepo) GetCourseById(ctx context.Context, id string) (Course, error) {
    clog := log.GetLoggerFromContext(ctx)

    var course Course

    objID, err := primitive.ObjectIDFromHex(id)
    if err != nil {
        return course, err
    }

    filter := bson.M{"_id": objID}

    err = r.collection.FindOne(ctx, filter).Decode(&course)
    if err != nil {
        clog.ErrorCtx(err, log.Ctx{"msg": "an error occurred while finding a course"})

        return course, err
    }

    return course, nil
}

结构体定义

type Course struct {
    ObjectId    primitive.ObjectID `bson:"_id, omitempty"`
    Id          string             `json:"id"`
    Title       string             `json:"title"`
    Description string             `json:"description"`
    Lessons     string             `json:"lessons"`
    Duration    string             `json:"duration"`
    Details     struct {
        Title             string `json:"title"`
        Instructor        string `json:"instructor"`
        Introduction      string `json:"introduction"`
        Learn             string `json:"learn"`
        Topics            string `json:"topics"`
        Prerequisites     string `json:"prerequisites"`
        Goal              string `json:"goal"`
        AdditionalDetails string `json:"additionalDetails"`
        HighLevelOverview string `json:"highLevelOverview"`
    } `json:"course_details"`
}

返回结果

{
    "data": {
        "ObjectId": "64953ac1bf06bfdd7936cad8",
        "id": "",
        "title": "Java Algorithms",
        "description": "An awesome course",
        "lessons": "4",
        "duration": "10 hours",
        "course_details": {
            "title": "",
            "instructor": "",
            "introduction": "",
            "learn": "",
            "topics": "",
            "prerequisites": "",
            "goal": "",
            "additionalDetails": "",
            "highLevelOverview": ""
        }
    },
    "metadata": "none"
}

根据查阅的资料,Decode方法应该可以映射嵌套值,请问这是什么原因导致的?


原因与解决方法

核心问题是结构体字段缺少bson标签,MongoDB的Decode方法依赖bson标签来关联数据库存储的字段与结构体属性,当前仅配置了json标签,导致嵌套的Details字段无法完成映射。

具体修正项:

  1. 为Details结构体添加bson标签,对应数据库中存储的嵌套字段名(示例假设数据库中该字段名为course_details,需与实际存储一致)
  2. 修正ObjectId的bson标签格式,omitempty前不能有空格,正确格式为bson:"_id,omitempty"
  3. 为Id字段添加bson标签(若数据库中有对应字段),或在解码后手动将ObjectId转为字符串赋值给Id

修正后的结构体示例:

type Course struct {
    ObjectId    primitive.ObjectID `bson:"_id,omitempty" json:"ObjectId"`
    Id          string             `bson:"id,omitempty" json:"id"`
    Title       string             `bson:"title" json:"title"`
    Description string             `bson:"description" json:"description"`
    Lessons     string             `bson:"lessons" json:"lessons"`
    Duration    string             `bson:"duration" json:"duration"`
    Details     struct {
        Title             string `bson:"title" json:"title"`
        Instructor        string `bson:"instructor" json:"instructor"`
        Introduction      string `bson:"introduction" json:"introduction"`
        Learn             string `bson:"learn" json:"learn"`
        Topics            string `bson:"topics" json:"topics"`
        Prerequisites     string `bson:"prerequisites" json:"prerequisites"`
        Goal              string `bson:"goal" json:"goal"`
        AdditionalDetails string `bson:"additionalDetails" json:"additionalDetails"`
        HighLevelOverview string `bson:"highLevelOverview" json:"highLevelOverview"`
    } `bson:"course_details" json:"course_details"`
}

补充说明:

  • 若数据库中嵌套字段的键名与结构体子字段的json标签一致,bson标签可与json标签保持相同;若键名不同,需填写数据库实际存储的字段名。
  • 返回结果中Id为空,是因为该字段同样缺少bson标签,若Id是_id的字符串形式,可在解码后添加:course.Id = course.ObjectId.Hex()

内容的提问来源于stack exchange,提问作者Mike3355

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.18 08:57:47