当一个程序需要与另一个程序通信时,许多开发人员会使用HTTP。Go的优势之一是其标准库的广度,HTTP也不例外。Go net/http
包不仅支持[创建HTTP服务器],而且它还可以作为客户端进行HTTP请求。
在本教程中,您将创建一个程序,向HTTP服务器发出几种类型的HTTP请求。首先,你将使用默认的Go HTTP客户端发起一个GET
请求。然后,你将改进你的程序,使用body发起一个POST
请求。最后,您将自定义您的POST
请求,以包含一个HTTP头并添加一个超时,如果您的请求花费了太长时间,则会触发超时。
Go net/http
包有几种不同的方式来使用它作为客户端。你可以使用一个通用的、全局的HTTP客户端,例如http.Get
,来快速发出一个只有URL和主体的HTTP GET
请求,或者你可以创建一个http.Request
来开始自定义单个请求的某些方面。在本节中,您将使用http.Get
创建一个初始程序来发出HTTP请求,然后您将更新它以使用默认HTTP客户端http.Request
。
http.Get
发起请求在程序的第一次迭代中,你将使用http.Get
函数向程序中运行的HTTP服务器发出请求。http.Get
函数很有用,因为你不需要在程序中进行任何额外的设置就可以发出请求。如果你需要发出单个快速请求,http.Get
可能是最好的选择。
要开始创建程序,需要一个目录来保存程序所在的目录。在本教程中,你将使用一个名为projects
的目录。
首先,创建projects
目录并导航到它:
mkdir projects
cd projects
接下来,创建项目目录并导航到它。在这种情况下,使用httpclient
目录:
mkdir httpclient
cd httpclient
在httpclient
目录下,使用nano
或者你最喜欢的编辑器来打开main.go
文件:
nano main.go
在main.go
文件中,首先添加以下几行:
main.go
package main
import (
"errors"
"fmt"
"net/http"
"os"
"time"
)
const serverPort = 3333
你添加package
名称main
,这样你的程序就会被编译为一个你可以运行的程序,然后包含一个import
语句,包含你将在这个程序中使用的各种包。之后,创建一个名为serverPort
的值为3333
的const
,它将被用作HTTP服务器监听的端口和HTTP客户端将要连接的端口。
接下来,在main.go
文件中创建一个main
函数,并设置一个goroutine来启动HTTP服务器:
main.go
...
func main() {
go func() {
mux := http.NewServeMux()
mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
fmt.Printf("server: %s /\n", r.Method)
})
server := http.Server{
Addr: fmt.Sprintf(":%d", serverPort),
Handler: mux,
}
if err := server.ListenAndServe(); err != nil {
if !errors.Is(err, http.ErrServerClosed) {
fmt.Printf("error running http server: %s\n", err)
}
}
}()
time.Sleep(100 * time.Millisecond)
你的HTTP服务器设置为只要请求根路径/
就使用fmt.Printf
来打印传入请求的信息。它还被设置为监听serverPort
。最后,一旦你启动了服务端goroutine,你的程序会在短时间内使用time.Sleep
。睡眠时间允许HTTP服务器有足够的时间启动并开始为你的下一个请求提供响应。
现在,同样在main
函数中,使用fmt.Sprintf
来设置请求URL,将http://localhost
主机名与服务器正在监听的serverPort
值结合起来。然后,使用http.Get
向该URL发出请求,如下所示:
main.go
...
requestURL := fmt.Sprintf("http://localhost:%d", serverPort)
res, err := http.Get(requestURL)
if err != nil {
fmt.Printf("error making http request: %s\n", err)
os.Exit(1)
}
fmt.Printf