Go中JSON转换为struct时报空指针、非法字符错误求助
问题排查与解决
第一个报错:runtime error: invalid memory address or nil pointer dereference
原因:
- 触发空指针的核心原因是
r.Body为nil:当请求是GET、HEAD等没有请求体的类型时,Go标准库会将r.Body设为nil,直接传入json.NewDecoder会触发空指针panic - 你注释掉的类型断言代码如果取消注释,也需要先判断断言是否成功,直接写
.(model.User)如果类型不匹配同样会触发panic
第二个报错:invalid character '-' in numeric literal
原因:
传入的请求体不是合法JSON格式,常见触发场景:
- 发起请求时没有设置
Content-Type: application/json请求头,传递了表单格式(x-www-form-urlencoded/form-data)的内容,JSON解码器无法解析 - 手动拼写的JSON格式错误,比如数字字段混入横杠、引号未闭合、多余逗号等问题
修复后的代码
func MakeMap(w http.ResponseWriter, r *http.Request) { // 限制仅允许POST请求,避免GET请求导致r.Body为nil if r.Method != http.MethodPost { http.Error(w, "only POST request allowed", http.StatusMethodNotAllowed) return } // 类型断言增加ok判断,避免panic // userInfo, ok := context.Get(r, "userInfo").(model.User) // if !ok { // http.Error(w, "invalid user info", http.StatusUnauthorized) // return // } type _getData struct { Title string `json:"title"` Tag []string `json:"tag"` } var getData _getData // 提前判断r.Body非空再处理 if r.Body == nil { http.Error(w, "request body is empty", http.StatusBadRequest) return } defer r.Body.Close() // 必须加defer关闭请求体,避免资源泄漏 err := json.NewDecoder(r.Body).Decode(&getData) if err != nil { // 不要直接panic,返回规范HTTP错误提示 http.Error(w, "invalid request body: "+err.Error(), http.StatusBadRequest) return } fmt.Print(getData) // 正常业务逻辑处理完成后返回响应 w.WriteHeader(http.StatusOK) w.Write([]byte("success")) }
请求发送注意事项
- 必须使用POST方法发起请求
- 请求头必须添加
Content-Type: application/json - 请求体为合法JSON格式,示例如下:
{ "title": "测试标题", "tag": ["旅行", "美食"] }
内容的提问来源于stack exchange,提问作者Choi yun seok
相关产品推荐
相关产品推荐

