有没有更简单的方法来使用net/http实现JSON REST服务?

huangapple go评论124阅读模式
英文:

Is there a simpler way to implement a JSON REST service with net/http?

问题

我正在尝试使用net/http开发一个REST服务。

该服务接收一个包含所有输入参数的JSON结构。我想知道是否有一种更简单、更短的方法来实现以下代码:

  1. func call(w http.ResponseWriter, r *http.Request) {
  2. if err := r.ParseForm(); err != nil {
  3. fmt.Printf("Error parsing request %s\n", err)
  4. }
  5. var buf []byte
  6. buf = make([]byte, 256)
  7. var n, err = r.Body.Read(buf)
  8. var decoded map[string]interface{}
  9. err = json.Unmarshal(buf[:n], &decoded)
  10. if err != nil {
  11. fmt.Printf("Error decoding json: %s\n", err)
  12. }
  13. var uid = decoded["uid"]
  14. ...
  15. }

如你所见,为了提取第一个参数,需要相当多的代码行。有什么想法吗?

英文:

I am trying to develop a REST service with net/http.

The service receives a JSON structure containing all the input parameters. I wonder if there is an easier and shorter way to implement the following:

  1. func call(w http.ResponseWriter, r *http.Request) {
  2. if err := r.ParseForm(); err != nil {
  3. fmt.Printf("Error parsing request %s\n", err)
  4. }
  5. var buf []byte
  6. buf = make([]byte, 256)
  7. var n, err = r.Body.Read(buf)
  8. var decoded map[string]interface{}
  9. err = json.Unmarshal(buf[:n], &decoded)
  10. if err != nil {
  11. fmt.Printf("Error decoding json: %s\n", err)
  12. }
  13. var uid = decoded["uid"]
  14. ...
  15. }

As you can see it requires quite a number of lines just to get to the extraction of the first parameter. Any ideas?

答案1

得分: 6

你不需要调用r.ParseForm,如果请求的主体包含一个JSON结构,并且你不需要任何URL参数。

你也不需要缓冲区,可以使用:

  1. decoder := json.NewDecoder(r.Body)

然后:

  1. error := decoder.Decode(decoded)

将它们整合在一起:

  1. func call(w http.ResponseWriter, r *http.Request) {
  2. values := make(map[string]interface{})
  3. if error := json.NewDecoder(r.Body).Decode(&values); error != nil {
  4. panic(error)
  5. }
  6. uid := values["uid"].(int)
  7. }

不过,如果你能正式定义你期望的输入结构的结构类型,会更好:

  1. type UpdateUserInformationRequest struct {
  2. UserId int `json:"uid"`
  3. // 其他字段...
  4. }

并且使用该结构的实例,而不是更通用的map。

英文:

You don't need to call r.ParseForm if the body of the request will contain a JSON structure and you don't need any URL parameters.

You don't need the buffer either; you can use:

  1. decoder := json.NewDecoder(r.Body)

And then:

  1. error := decoder.Decode(decoded)

Putting it all together:

  1. func call(w http.ResponseWriter, r *http.Request) {
  2. values := make(map[string]interface{})
  3. if error := json.NewDecoder(r.Body).Decode(&values); error != nil {
  4. panic(error)
  5. }
  6. uid := values["uid"].(int)
  7. }

It would be much nicer, though, if you could formally define the structure of the input that you're expecting in a struct type:

  1. type UpdateUserInformationRequest struct {
  2. UserId int `json:"uid"`
  3. // other fields...
  4. }

And use an instance of this struct instead of a more general map.

huangapple
  • 本文由 发表于 2014年5月12日 18:48:36
  • 转载请务必保留本文链接:https://go.coder-hub.com/23606981.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定