go - 将数据发布到端点后请求正文为空
问题描述
我不确定为什么在运行以下 curl 请求时不存在发布的数据:
curl --request POST http://localhost:4000 --header "Content-Type: application/json" --data '{ "hostname": "bbc.co.uk" }'
针对下面的代码。它本质上只是使用变量发布 json,hostname
但由于某种原因,它没有出现在结构数组中req.Body
或出现在Domain
结构数组中。请注意这是基于本教程
package main
import (
"encoding/json"
"log"
"net/http"
"fmt"
"github.com/gorilla/mux"
"github.com/gorilla/handlers"
)
type Domain struct {
hostname string `json:"hostname,omitempty"`
}
var domains []Domain
func CreateDomainEndpoint(w http.ResponseWriter, req *http.Request) {
var domain Domain
fmt.Println(req.Body)
_ = json.NewDecoder(req.Body).Decode(&domain)
domains = append(domains, domain)
json.NewEncoder(w).Encode(domains)
}
func main() {
router := mux.NewRouter()
router.HandleFunc("/", CreateDomainEndpoint).Methods("POST")
log.Fatal(http.ListenAndServe(":4000", handlers.CORS(handlers.AllowedHeaders([]string{"X-Requested-With", "Content-Type", "Authorization"}), handlers.AllowedMethods([]string{"GET", "POST", "PUT", "HEAD", "OPTIONS"}), handlers.AllowedOrigins([]string{"*"}))(router)))
}
解决方案
- JSON 编解码器会忽略该
hostname
字段,因为该字段未导出。通过大写字段名称来修复。 - 上有一场数据竞赛
domains
。通过使用mutex保护对变量的访问来修复。 - 应用程序忽略错误。通过检查并处理从 JSON 解码器返回的错误来修复。
这是带有修复的代码:
package main
import (
"encoding/json"
"log"
"net/http"
"sync"
"github.com/gorilla/handlers"
"github.com/gorilla/mux"
)
type Domain struct {
Hostname string `json:"hostname,omitempty"`
}
var (
domains []Domain
mu sync.Mutex
)
func CreateDomainEndpoint(w http.ResponseWriter, req *http.Request) {
var domain Domain
if err := json.NewDecoder(req.Body).Decode(&domain); err != nil {
http.Error(w, "bad request", 400)
return
}
mu.Lock()
domains = append(domains, domain)
// To avoid holding the mutex while writing to the
// response body, make a local copy of the slice header.
d := domains
mu.Unlock()
json.NewEncoder(w).Encode(d)
}
func main() {
router := mux.NewRouter()
router.HandleFunc("/", CreateDomainEndpoint).Methods("POST")
log.Fatal(http.ListenAndServe(":4000", handlers.CORS(handlers.AllowedHeaders([]string{"X-Requested-With", "Content-Type", "Authorization"}), handlers.AllowedMethods([]string{"GET", "POST", "PUT", "HEAD", "OPTIONS"}), handlers.AllowedOrigins([]string{"*"}))(router)))
}
推荐阅读
- java - 如何从 Java 中的 2 个不同类访问变量
- reactjs - 没有 Webpack 的反应。如何添加库 EmailJS?
- python - Snakemake - 如何按子目录获取目录中的所有文件
- java - 添加到另一个 JPanel(在 JFrame 中)的 JPanel 未显示
- javascript - 使用 MySQL 的 Node 和 Express
- java - 大十进制 setScale 有时会给出不同的值
- xml - 在序列化期间获取属性的自定义属性
- javascript - 使用 Axios 请求拦截器 (interceptors.request) 刷新 JWT Token - 一次多个请求的问题
- microsoft-teams - 在调用图形 api 在线会议 api 获取响应代码 400 时面临问题
- pycharm - 如何在 PyCharm 中为数据类自动生成文档字符串?