cURL与Postman POST请求正常,Golang请求返回400错误排查
解决Golang POST GooglePay Token返回400的问题
核对JSON序列化的转义差异
Golang的encoding/json包对字符转义更严格,比如Unicode字符、特殊符号的处理可能和cURL/Postman不一致。可以把Golang生成的JSON字节转成字符串输出(fmt.Println(string(jsonBytes))),和cURL请求里的Body逐字符对比,确认是否存在转义差异。手动设置Content-Length头
自动计算的Content-Length可能因为隐形字符(如换行、空格)出现偏差,手动设置能确保和cURL请求完全一致:jsonBytes, err := json.Marshal(yourPayload) if err != nil { // 处理错误 } req, err := http.NewRequest("POST", targetURL, bytes.NewBuffer(jsonBytes)) if err != nil { // 处理错误 } req.Header.Set("Content-Length", strconv.Itoa(len(jsonBytes)))严格匹配Content-Type头
部分服务器对字符编码有强制要求,确保Golang设置的Content-Type和cURL一致,比如:req.Header.Set("Content-Type", "application/json; charset=utf-8")禁用HTTP客户端自动压缩
Golang的http.Client默认会请求gzip压缩,若服务器对压缩请求处理异常会返回400,可关闭该功能:client := &http.Client{ Transport: &http.Transport{ DisableCompression: true, }, }完全复刻cURL的请求头
除了User-Agent,还要将Accept、Connection、Accept-Encoding等所有cURL里的请求头都手动设置到Golang请求中,避免隐形的头差异:req.Header.Set("Accept", "*/*") req.Header.Set("Connection", "keep-alive") // 其他cURL包含的请求头逐一添加直接复用cURL的原始Body
把cURL中能正常运行的JSON字符串直接作为请求Body发送,而非Golang序列化生成:rawValidBody := `{"token":"your-googlepay-token", ...}` // 复制cURL里的完整Body req, err := http.NewRequest("POST", targetURL, strings.NewReader(rawValidBody))若此方法成功,说明问题出在Golang的JSON序列化环节;若仍失败,则排查客户端配置或请求头的细节。
内容的提问来源于stack exchange,提问作者Awernx
相关产品推荐
相关产品推荐

