我正在使用fetch
API向我的POST
请求处理程序发送两个值...
fetch('http://localhost:8080/validation', {
method:'POST',
headers: {
'Accept': 'application/json',
'Content-Type': 'application/json'
},
body: JSON.stringify({
email:this.state.email,
password:this.state.password
})
我想将email
和password
保存为服务器端的字符串。这是我的尝试......
type credentials struct {
Test string
}
func Validate(rw http.ResponseWriter, req *http.Request, _ httprouter.Params) {
decoder := json.NewDecoder(req.Body)
var creds credentials
err := decoder.Decode(&creds)
if err != nil {
panic(err)
}
fmt.Println(creds.Test)
}
问题是我不知道发送给POST
的结构的格式究竟如何。我试图将req.Body
保存为字符串,但这不会产生任何效果。
当我打印fmt.Println
时,我得到一个空白区域。解析它的正确方法是什么?
答案 0 :(得分:3)
尝试
type credentials struct {
Email string `json:"email"`
Password string `json:"password"`
}
您正在接收带有两个值的JSON。接收结构应具有与您的请求匹配的结构。否则,没有占位符可以将JSON解码为,在您的情况下 - 电子邮件和密码没有匹配的结构字段。顺便说一句。如果你在你的JSON中发送"Test"
,这会有效,因为你的结构中有一个Test字段!
关于字段名称。如果JSON中的字段不以大写字母开头,或者甚至具有不同的名称,那么您应该使用所谓的标记。 有关标签的更多信息:https://golang.org/pkg/encoding/json/#Marshal
在我的示例中,我使用它们将结构字段名称与json字段进行匹配,即从email
结构的json匹配Email
字段中生成credentials
。
答案 1 :(得分:1)
req.Body
是io.Reader
,您可以使用ioutil.ReadAll
来排除它:
data, err := ioutil.ReadAll(req.Body)
asString := string(data) // you can convert to a string with a typecast
但我不确定这是否是您将req.Body
保存为字符串的意思。
要将响应解析为数据结构,您可以将其解组为*interface{}
类型的变量:
var creds interface{}
decoder.Decode(&creds)
然后检查值:
fmt.Printf("%#v\n", creds)
或者使用我觉得更容易阅读的pp.Println(creds)
。
creds
变量将代表在正文中找到的JSON对象,对于您的示例输入,这将是一个带有两个条目的map[string]interface{}
,可能两个都是字符串。类似的东西:
map[string]interface{}{
"email": email_value,
"password": password_value,
}
并使用以下方法检查值:
email, ok := creds["email"].(string)
if ok {
// email will contain the value because creds["email"] passed the type check
fmt.Printf("submitted email is %#v\n", email)
} else {
// "email" property was a string (may be missing, may be something else)
}
documentation of json.Unmarshal
解释了在关于解组接口值的讨论中,如何在不知道其结构的情况下解析任意JSON字符串的语义。