[英]Go - passing generic struct to function
Considering the following code, which is responding to GET '/venues/:id': 考虑以下代码,它响应GET'/场所/:id':
func venueShow(w http.ResponseWriter, req *http.Request) {
// get ID from params
vars := mux.Vars(req)
id := vars["id"]
// initialise new struct
var venue Venue
// select by id and scan into struct
db.First(&venue, id).Scan(&venue)
// turn it to json
response := structToJSON(&venue)
// write headers and provide response
w.Header().Set("Content-Type", "application/json")
w.Write(response)
}
and: 和:
func structToJSON (s interface{}) (response []byte) {
// turn it into pretty-ish json
response, err := json.MarshalIndent(&s, "", " ")
if err != nil {
return []byte("Venue does not exist")
}
// return the json as the reponse
return response
}
My structToJSON function is taking an empty interface as the argument, because I want to pass various different structs to the function and have them spewed out as JSON. 我的structToJSON函数将空接口作为参数,因为我想将各种不同的结构传递给函数并将它们作为JSON喷出。
However, it doesn't strike me as very safe. 但是,它并没有让我觉得非常安全。 If anything satisfies an empty interface, I could pass whatever I wanted into that function, and all sorts of errors might happen when json.Marshal tries to do it's business. 如果有任何东西满足空接口,我可以将任何我想要的东西传递给该函数,并且当json.Marshal试图做它的业务时可能会发生各种错误。 This (I suppose) would be caught by the compiler rather than at runtime, but is there a safer way? 这个(我想)会被编译器捕获而不是在运行时捕获,但有更安全的方法吗?
I could duplicate the structToJSON method for each different type of Struct/Model that I pass to it, but that's not very DRY. 我可以为我传递给它的每种不同类型的Struct / Model复制structToJSON方法,但这不是很干。
Thanks 谢谢
The Marshal function also receives its parameters as interface{}
therefore there's no way to detect if you are passing something invalid at compile time, it's all caught at runtime. Marshal函数也接收它作为interface{}
参数,因此没有办法检测你是否在编译时传递了一些无效的东西,它们都是在运行时捕获的。
One thing you can do to check if an invalid type was passed to Marshal is to check the error type, Marshal returns an UnsupportedTypeError
when you try to Marshal an invalid type (like chan
or func
) so you can check for that error when Marshaling. 检查是否将无效类型传递给Marshal的一件事是检查错误类型,当您尝试将无效类型(如chan
或func
) UnsupportedTypeError
时,Marshal会返回UnsupportedTypeError
,以便您可以在Marshaling时检查该错误。
So you could try something like that: 所以你可以尝试这样的事情:
if err != nil {
_, ok := err.(*json.UnsupportedTypeError)
if ok {
return []byte("Tried to Marshal Invalid Type")
} else {
return []byte("Venue does not exist")
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.