英文:
Transform http.Response into array of bytes
问题
我正在尝试开发一个TCP代理,在这个TCP代理中,我需要同时处理HTTP和TCP请求。
目前,对于传入的请求,我会检测它是HTTP请求还是TCP请求,如果是HTTP请求,我会将其解析为http.Request
:
func (s *TcpProxy) OnMessage(c *connection.Connection, ctx interface{}, data []byte) interface{} {
reader := bytes.NewReader(data)
newReader := bufio.NewReader(reader)
req, err := http.ReadRequest(newReader)
// 这是一个HTTP请求
}
现在,我可以方便地操作请求,因为我可以使用该接口提供的方法,然后最终将响应从代理发送回接收传入请求的服务。
func (s *TcpProxy) OnMessage(c *connection.Connection, ctx interface{}, data []byte) interface{} {
reader := bytes.NewReader(data)
newReader := bufio.NewReader(reader)
req, err := http.ReadRequest(newReader)
// 操作HTTP请求
// ...
// 代理请求
proxyReq, err := http.NewRequest(req.Method, proxyUrl, req.Body)
// 在向目标服务发出请求时捕获持续时间。
res, err := httpClient.Do(proxyReq)
buf := res.ToBuffer() // <= 我该如何实现这一步
c.Send(buf)
c.Close()
return nil
}
然而,我找不到将响应转换回字节数组或字符串的方法,我是否遗漏了什么?
英文:
I am trying to develop a tcp proxy, in this tcp proxy I will have to manipulate both http and tcp requests.
At the moment for the incoming request I detect if it is an http or tcp request, if it is an http then I parse it into an http.Request
:
func (s *TcpProxy) OnMessage(c *connection.Connection, ctx interface{}, data []byte) interface{} {
reader := bytes.NewReader(data)
newReader := bufio.NewReader(reader)
req, err := http.ReadRequest(newReader)
// This is an http request
}
Now I manipulate the request conveniently since I can use the methods exposed from that interface, then eventually I will send the response back from my proxy to the service that received the inbound request.
func (s *TcpProxy) OnMessage(c *connection.Connection, ctx interface{}, data []byte) interface{} {
reader := bytes.NewReader(data)
newReader := bufio.NewReader(reader)
req, err := http.ReadRequest(newReader)
// Manipulate http request
// ...
// Proxy the request
proxyReq, err := http.NewRequest(req.Method, proxyUrl, req.Body)
// Capture the duration while making a request to the destination service.
res, err := httpClient.Do(proxyReq)
buf := res.ToBuffer() // <= How can I achieve this
c.Send(buf)
c.Close()
return nil
}
However I cannot find a way to convert back the response into an array of bytes or string, am I missing something?
答案1
得分: 1
一个http.Request
对象有一个Write
方法:
func (r *Request) Write(w io.Writer) error
Write方法以二进制格式写入HTTP/1.1请求的头部和正文。
你可以使用这个方法将字节写入一个缓冲区对象。例如:
package main
import (
"bytes"
"fmt"
"net/http"
)
func main() {
var buf bytes.Buffer
req, err := http.NewRequest("GET", "http://google.com", nil)
if err != nil {
panic(err)
}
client := &http.Client{}
res, err := client.Do(req)
if err != nil {
panic(err)
}
defer res.Body.Close()
if err := res.Write(&buf); err != nil {
panic(err)
}
// ...在这里对缓冲区进行任何操作...
fmt.Println(buf.String())
}
一个缓冲区对象有一个Bytes
方法,如果你需要的话,它会返回一个字节数组。
英文:
An http.Request object has a Write
method:
>
> func (r *Request) Write(w io.Writer) error
>
>
> Write writes an HTTP/1.1 request, which is the header and body, in wire format.
You can use this to write the bytes into a buffer object. For example:
package main
import (
"bytes"
"fmt"
"net/http"
)
func main() {
var buf bytes.Buffer
req, err := http.NewRequest("GET", "http://google.com", nil)
if err != nil {
panic(err)
}
client := &http.Client{}
res, err := client.Do(req)
if err != nil {
panic(err)
}
defer res.Body.Close()
if err := res.Write(&buf); err != nil {
panic(err)
}
// ...do whatever you want with the buffer here...
fmt.Println(buf.String())
}
A Buffer object has a Bytes
method that will return a byte array, if that's what you want.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论