Go驱动读取MongoDB数字字段的类型判定与安全转换问询
安全处理MongoDB数字字段的类型转换问题
当然有安全的处理方式,核心思路是通过类型断言分支处理所有可能的数字类型,或者借助辅助函数统一转换逻辑,避免直接断言导致的panic。另外,更推荐的做法是直接解码到结构体,从根源上避免类型松散的问题。
方案一:用辅助函数处理map场景
如果必须使用map[string]interface{},可以编写一个通用的数字转换函数,覆盖MongoDB中常见的数字类型(int32、int64、float64等),确保转换安全:
import "math" // ToInt 尝试将任意类型的数字转换为int,转换失败返回指定默认值 func ToInt(v interface{}, defaultValue int) int { switch val := v.(type) { case int: return val case int32: return int(val) case int64: return int(val) case uint: return int(val) case uint32: return int(val) case uint64: return int(val) case float32: // 若需要四舍五入而非截断,可替换为 return int(math.Round(float64(val))) return int(val) case float64: // 同理,如需四舍五入用math.Round return int(val) default: return defaultValue } }
改进原代码,使用辅助函数替代直接断言:
var data map[string]interface{} err := col.FindOne(nil, map[string]interface{}{"uid": uid}).Decode(&data) if err != nil { // 务必处理查询错误 log.Println("查询用户失败:", err) return } currLevelInt := ToInt(data["currLevel"], 1)
这个函数会自动适配不同的数字类型,类型不匹配时返回默认值,完全避免panic风险。
方案二:直接解码到结构体(更优)
如果你的数据结构是固定的,优先使用结构体解码,MongoDB Go驱动会自动处理兼容的数字类型转换,无需手动处理类型断言:
import "go.mongodb.org/mongo-driver/bson" // 定义与MongoDB文档匹配的结构体 type User struct { UID int `bson:"uid"` CurrLevel int `bson:"currLevel"` // 其他字段根据实际需求添加 } func main() { var user User err := col.FindOne(nil, bson.M{"uid": uid}).Decode(&user) if err != nil { log.Println("查询用户失败:", err) return } // 直接使用结构体字段,类型明确 currLevelInt := user.CurrLevel }
驱动会自动将MongoDB中的int32、int64、甚至是值为整数的float64转换为结构体里的int字段,代码更简洁健壮,从根源上避免了类型松散的问题。
内容的提问来源于stack exchange,提问作者armnotstrong
相关产品推荐
相关产品推荐

