[英]How to detect if received JSON has unknown fields
I'm trying to find some way to prohibit arbitrary JSON keys and fields in Go. For now, if I send payload with undeclared fields in struct, the service will work normally and will map the entity described fields (like json:"id,omitempty"
).我试图找到一些方法来禁止 Go 中的任意 JSON 键和字段。现在,如果我在结构中发送带有未声明字段的有效负载,该服务将正常工作并将 map 实体描述字段(如
json:"id,omitempty"
)。 For example:例如:
type Foo struct {
Bar int `json:"id,omitempty"`
}
Received JSON:收到JSON:
{
"id": 12,
"hey": "hey"
}
Can anybody help me to find the way of tracking unknown field in payload?谁能帮我找到跟踪有效载荷中未知字段的方法? I need to return an error in that case.
在那种情况下我需要返回一个错误。
you might want to use DisallowUnknownFields()
read for more info 您可能想使用
DisallowUnknownFields()
阅读更多信息
There is a proposal for golang 1.9 on this: proposal: some way to reject unknown fields in encoding/json.Decoder Golang 1.9对此有一个建议: proposal:一种拒绝encoding / json.Decoder中未知字段的方法
Till then you could try something like this playground (code also below). 到那时为止,您可以尝试像这样的游乐场 (下面的代码)。 The key idea is to parse the json into a map[string]interface{} and then work with the keys.
关键思想是将json解析为map [string] interface {},然后使用这些键。 This will of course get much more complicated if you have nested structs.
如果您具有嵌套结构,这当然会变得更加复杂。
package main
import (
"encoding/json"
"fmt"
)
type Foo struct {
Bar int `json:"id,omitempty"`
}
var allowedFooKeys = []string{"id"}
func main() {
b := []byte(`{
"id": 12,
"hey": "hey"
}`)
m := map[string]interface{}{}
if err := json.Unmarshal(b, &m); err != nil {
panic(err)
}
for k, _ := range m {
if !keyExists(k, allowedFooKeys) {
fmt.Println("Disallowed key in JSON:", k)
}
}
}
func keyExists(key string, keys []string) bool {
for _, k := range keys {
if k == key {
return true
}
}
return false
}
You can even get rid of the variable allowedFooKeys
by getting the allowed keys directly from the Foo
struct using reflect. 您甚至可以通过使用反射直接从
Foo
结构中获取允许的键来摆脱变量allowedFooKeys
。 For more info on that see here: How to read struct field ` ` decorators? 有关更多信息,请参见此处: 如何读取struct字段装饰器?
Since Go 1.10, the JSON decoder provides the DisallowUnknownFields()
option for this use case.自 Go 1.10 起,JSON 解码器为此用例提供了
DisallowUnknownFields()
选项。
func StrictUnmarshal(data []byte, v interface{}) error {
dec := json.NewDecoder(bytes.NewReader(data))
dec.DisallowUnknownFields()
return dec.Decode(v)
}
You can find a full working example here:您可以在此处找到完整的工作示例:
https://go.dev/play/p/HoGDIt8nJB7 https://go.dev/play/p/HoGDIt8nJB7
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.