2016-10-09 75 views
5

我有一个非常简单的Go web服务器。接收入站json负载是工作。然后它将有效负载发布到一个或多个需要字节数组的服务。有效载荷不需要检查。刚刚发过来。将io.ReadCloser转换为字节数组的最有效方法

在这种情况下,它会接收入站作业并将其发送到Google PubSub。这可能是另一项服务 - 它并不重要。 我试图找到最有效的方法来将对象转换为字节数组,而无需先解码它。

为什么?在一台服务器上解码并转换为JSON似乎有点浪费,只能稍后解组。另外,我不想在两个包中保留两个相同的结构。

如何将io.ReadCloser转换为字节数组,所以我只需要解组一次。我想是这样的答案,但不认为这是最有效的方法之一:

From io.Reader to string in Go

我的HTTP服务器的代码如下所示:您转换读者字节

func Collect(d DbManager) http.HandlerFunc { 
    return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { 
    w.Header().Set("Content-Type", "application/json; charset=utf-8") 

    code := 422 
    obj := Report{} 
    response := Response{} 
    response.Message = "Invalid request" 

    decoder := json.NewDecoder(r.Body) 
    decoder.Decode(&obj) 

    if obj.Device.MachineType != "" { 
     msg,_ := json.Marshal(obj) 
     if d.Publish(msg, *Topic) { 
      code = 200 
     } 
     response.Message = "Ok" 
    } 

    a, _ := json.Marshal(response) 
    w.WriteHeader(code) 
    w.Write(a) 
    return 
}) 
} 

回答

10

,由阅读它。有没有一种更有效的方式来做到这一点。

body, err := ioutil.ReadAll(r.Body) 

如果是无条件从io.Reader转移字节到io.Writer,你可以只使用io.Copy

+0

酷,我已经试过了,但它输出空...我还没有意识到,试图在解码之后这么做会这样做。两个经验教训,欢呼大耳朵。 –

+0

记住'io.Copy'是分配的,这是一个好主意。你可能会想在热路径中使用'io.CopyBuffer'。 –

+1

@AmmarBandukwala,除非你已经有一个缓冲区,它们是相同的,复制只是调用CoffyBuffer。您需要在某个时间点进行分配,并且在std lib http请求的方案中,它是许多此类分配中的一个,并且可能不重要。 – JimB

相关问题