欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Golang中http包的具體使用

 更新時間:2024年05月14日 09:16:33   作者:兩片空白  
Go語言內(nèi)置的net/http包十分優(yōu)秀,提供了http客戶端和服務(wù)器的實(shí)現(xiàn),本文主要介紹了Golang中http包的具體使用,具有一定的參考價值,感興趣的可以了解一下

Go語言內(nèi)置的net/http包十分優(yōu)秀,提供了http客戶端和服務(wù)器的實(shí)現(xiàn)。

超文本傳輸協(xié)議(HTTP,HyperText Transfer Protocol)是互聯(lián)網(wǎng)上應(yīng)用最為廣泛的一種網(wǎng)絡(luò)傳輸協(xié)議,所有的www文件都必須遵循這個標(biāo)準(zhǔn)。設(shè)計HTTP最初的目的是為了提供一種發(fā)布和接收HTML頁面的方法。

一. HTTP客戶端

基本的HTTP/HTTPS請求Get,Head,Post和PostForm函數(shù)發(fā)出HTTP/HTTPS請求。

	resp, err := http.Get("http://example.com")
	//...
	resp, err = http.Post("http://example.com", "image/jpeg", &buf)
	//...
	resp, err = http.PostForm("http://example.com", url.Values{"key": {"value"}, "id": {"123"}})

程序在使用完response后必須關(guān)閉回復(fù)的主體。

package main

import (
	"io/ioutil"
	"log"
	"net/http"
)

func main() {
	resp, err := http.Get("http://example.com")
	if err != nil {
		log.Println("http get fail")
		return
	}
	//關(guān)閉回復(fù)主體
	defer resp.Body.Close()

	body, err := ioutil.ReadAll(resp.Body)
    //...
}

1.1 Get請求

函數(shù)簽名:

func Get(url string) (resp *Response, err error)

Get向指定的URL發(fā)出Get請求,如果回應(yīng)的狀態(tài)碼如下,Get會調(diào)用c.CheckRedirect后執(zhí)行重定向。

  • 301(Moved Permanently)
  • 302(Found)
  • 303(See Other)
  • 307(Temporary Redirect)

如果c.CheckRedirect執(zhí)行失敗或存在HTTP協(xié)議錯誤時,本方法返回錯誤。如果回應(yīng)的狀態(tài)碼不是2xx,本方法并不會返回錯誤。如果返回值err為nil,resp.Body總是非nil的,調(diào)用者應(yīng)該在讀取完resp.Body后關(guān)閉它。

Get是對DefaultClient的Get方法的包裝。

1.2 post和get示例服務(wù)端代碼

package main

import (
	"fmt"
	"io/ioutil"
	"net/http"
)

func getHandleFunc(w http.ResponseWriter, r *http.Request) {
	defer r.Body.Close()

	data := r.URL.Query() //獲得get方法的參數(shù)
	fmt.Println(data.Get("name"))
	fmt.Println(data.Get("age"))

	answer := `{"status":"ok"}`
	w.Write([]byte(answer))
}

func postHandleFunc(w http.ResponseWriter, r *http.Request) {
	defer r.Body.Close()
	//請求數(shù)據(jù)類型是application/json
	b, err := ioutil.ReadAll(r.Body)
	if err != nil {
		fmt.Println("read request body fail ", err)
		return
	}
	fmt.Println(string(b))

	answer := `{"statue":"ok"}`
	w.Write([]byte(answer))
}

func handleFunc(w http.ResponseWriter, r *http.Request) {
	fmt.Println("get a link....")
	switch r.Method {
	case http.MethodGet:
		http.HandleFunc("/get", getHandleFunc)
	case http.MethodPost:
		http.HandleFunc("/post", postHandleFunc)
	}
}

func main() {
	http.HandleFunc("/", handleFunc)
	err := http.ListenAndServe(":9090", nil)
	if err != nil {
		fmt.Println("http server fail ", err)
		return
	}
}

1.3 get方法示例

不帶參數(shù)客戶端

package main

import (
	"fmt"
	"io/ioutil"
	"log"
	"net/http"
)

func main() {
	resp, err := http.Get("https://www.baidu.com")
	if err != nil {
		log.Println("http get fail ", err)
		return
	}
	//關(guān)閉回復(fù)主體
	defer resp.Body.Close()

	body, err := ioutil.ReadAll(resp.Body)
	if err != nil {
		log.Println("read resp body fail ", err)
		return
	}

	fmt.Print(string(body))
}

帶參數(shù)客戶端

關(guān)于Get請求帶參數(shù)需要使用Go語言內(nèi)置的net/url標(biāo)準(zhǔn)庫來處理。

package main

import (
	"fmt"
	"io/ioutil"
	"net/http"
	"net/url"
)

func main() {
	apiUrl := "http://127.0.0.1:9090/get"
	//URL參數(shù)
	data := url.Values{}
	data.Set("name", "張三")
	data.Set("age", "20")

	//URL參數(shù)需要編碼,因?yàn)橛械奶厥庾址毁x予了特殊含義
	u, err := url.ParseRequestURI(apiUrl)
	if err != nil {
		fmt.Println("url parse fail ", err)
	}
	u.RawQuery = data.Encode() //url encode
	fmt.Println(u.String())

	resp, err := http.Get(u.String())
	if err != nil {
		fmt.Printf("url %v get fail %v", u.String(), err)
		return
	}
	defer resp.Body.Close()

	b, err := ioutil.ReadAll(resp.Body)
	if err != nil {
		fmt.Println("read body fail ", err)
		return
	}
	fmt.Println(string(b))
}

1.4 post請求

函數(shù)簽名:

func Post(url string, bodyType string, body io.Reader) (resp *Response, err error)

Post向指定的URL發(fā)送一個POST請求。bodyType為POST的數(shù)據(jù)類型,Body為POST數(shù)據(jù),作為請求的主體。如果參數(shù)body實(shí)現(xiàn)了io.Closer接口,它會在發(fā)送請求后被關(guān)閉。調(diào)用者有責(zé)任在讀取完返回值resp的主體后關(guān)閉它。

Post是對包變量DefaultClient的Post方法的包裝。

1.5 post示例

package main

import (
	"fmt"
	"io/ioutil"
	"net/http"
	"strings"
)

func main() {
	apiUrl := "http://127.0.0.1:9090/post"

	//表單數(shù)據(jù)
	contenttype := "application/json"
	data := `{"name":"張三", "age":18}`
	resp, err := http.Post(apiUrl, contenttype, strings.NewReader(data))
	if err != nil {
		fmt.Printf("url : %v post fail err : %v\n", apiUrl, err)
		return
	}
	defer resp.Body.Close()

	b, err := ioutil.ReadAll(resp.Body)
	if err != nil {
		fmt.Println("read body err ", err)
		return
	}
	fmt.Println(string(b))
}

1.6 自定義Client

要管理HTTP客戶端頭域,重定向和其它策略,創(chuàng)建一個client:

type Client struct {
    // Transport指定執(zhí)行獨(dú)立、單次HTTP請求的機(jī)制。
    // 如果Transport為nil,則使用DefaultTransport。
    Transport RoundTripper
    // CheckRedirect指定處理重定向的策略。
    // 如果CheckRedirect不為nil,客戶端會在執(zhí)行重定向之前調(diào)用本函數(shù)字段。
    // 參數(shù)req和via是將要執(zhí)行的請求和已經(jīng)執(zhí)行的請求(切片,越新的請求越靠后)。
    // 如果CheckRedirect返回一個錯誤,本類型的Get方法不會發(fā)送請求req,
    // 而是返回之前得到的最后一個回復(fù)和該錯誤。(包裝進(jìn)url.Error類型里)
    //
    // 如果CheckRedirect為nil,會采用默認(rèn)策略:連續(xù)10此請求后停止。
    CheckRedirect func(req *Request, via []*Request) error
    // Jar指定cookie管理器。
    // 如果Jar為nil,請求中不會發(fā)送cookie,回復(fù)中的cookie會被忽略。
    Jar CookieJar
    // Timeout指定本類型的值執(zhí)行請求的時間限制。
    // 該超時限制包括連接時間、重定向和讀取回復(fù)主體的時間。
    // 計時器會在Head、Get、Post或Do方法返回后繼續(xù)運(yùn)作并在超時后中斷回復(fù)主體的讀取。
    //
    // Timeout為零值表示不設(shè)置超時。
    //
    // Client實(shí)例的Transport字段必須支持CancelRequest方法,
    // 否則Client會在試圖用Head、Get、Post或Do方法執(zhí)行請求時返回錯誤。
    // 本類型的Transport字段默認(rèn)值(DefaultTransport)支持CancelRequest方法。
    Timeout time.Duration
}

Client類型代表HTTP客戶端。它的零值(DefaultClient)是一個可用的使用DefaultTransport的客戶端。

Client的Transport字段一般會含有內(nèi)部狀態(tài)(緩存TCP連接),因此Client類型值應(yīng)盡量被重用而不是每次需要都創(chuàng)建新的。Client類型值可以安全的被多個go程同時使用。

Client類型的層次比RoundTripper接口(如Transport)高,還會管理HTTP的cookie和重定向等細(xì)節(jié)。

//設(shè)置重定向
client := &http.Client{
    CheckRedirect : redirectPolicyFunc,
}

resp, err := client.Get("http://example.com")
//...

//加請求頭部
req, err := http.NewRequest("Get", "http://example.com", nil)
//...

req.Header.Add("If-None-Match", `W/"wyzzy"`)
resp, err := client.Do(req)
//...

1.7 自定義Transport

go語言中的http.transport是一個高性能的http客戶端庫,它提供了連接池、重試、超時控制等功能,可以方便地進(jìn)行 http 請求。

要管理代理,TLS配置,keep-alive,壓縮和其它設(shè)置,可以創(chuàng)建一個Transport,對應(yīng)Client的Transport字段。

type Transport struct {
    // Proxy指定一個對給定請求返回代理的函數(shù)。
    // 如果該函數(shù)返回了非nil的錯誤值,請求的執(zhí)行就會中斷并返回該錯誤。
    // 如果Proxy為nil或返回nil的*URL置,將不使用代理。
    Proxy func(*Request) (*url.URL, error)
    // Dial指定創(chuàng)建TCP連接的撥號函數(shù)。如果Dial為nil,會使用net.Dial。
    Dial func(network, addr string) (net.Conn, error)
    // TLSClientConfig指定用于tls.Client的TLS配置信息。
    // 如果該字段為nil,會使用默認(rèn)的配置信息。
    TLSClientConfig *tls.Config
    // TLSHandshakeTimeout指定等待TLS握手完成的最長時間。零值表示不設(shè)置超時。
    TLSHandshakeTimeout time.Duration
    // 如果DisableKeepAlives為真,會禁止不同HTTP請求之間TCP連接的重用。
    DisableKeepAlives bool
    // 如果DisableCompression為真,會禁止Transport在請求中沒有Accept-Encoding頭時,
    // 主動添加"Accept-Encoding: gzip"頭,以獲取壓縮數(shù)據(jù)。
    // 如果Transport自己請求gzip并得到了壓縮后的回復(fù),它會主動解壓縮回復(fù)的主體。
    // 但如果用戶顯式的請求gzip壓縮數(shù)據(jù),Transport是不會主動解壓縮的。
    DisableCompression bool
    // 如果MaxIdleConnsPerHost!=0,會控制每個主機(jī)下的最大閑置連接。
    // 如果MaxIdleConnsPerHost==0,會使用DefaultMaxIdleConnsPerHost。
    MaxIdleConnsPerHost int
    // ResponseHeaderTimeout指定在發(fā)送完請求(包括其可能的主體)之后,
    // 等待接收服務(wù)端的回復(fù)的頭域的最大時間。零值表示不設(shè)置超時。
    // 該時間不包括獲取回復(fù)主體的時間。
    ResponseHeaderTimeout time.Duration
    // 內(nèi)含隱藏或非導(dǎo)出字段
}
	tr := &http.Transport{
		TLSClientConfig: &tls.Config{
			RootCAs: pool,
		},
		DisableCompression: true,
	}

	client := &http.Client{
		Transport: tr,
	}

	resp, err := client.Get("http://example.com")
	//...

二. 服務(wù)端

2.1 默認(rèn)server

ListenAndServer使用指定的監(jiān)聽地址和處理器啟動一個HTTP服務(wù)端。處理器參數(shù)通常是nil,這表示采用包變量DefaultServeMux作為處理器。

Handle和HandleFunc函數(shù)可以向DefaultServeMux添加處理器。

	http.Handle("/foo", fooHandler)
	http.HandleFunc("/hello", func(w http.ResponseWriter, r *http.Request) {
		fmt.Fprintf(w, "hello %q", html.EscapeString(r.URL.Path))
	})

	log.Fatal(http.ListenAndServe(":8080", nil))

2.2 示例

package main

import (
	"fmt"
	"net/http"
)

func sayHello(w http.ResponseWriter, r *http.Request) {
	defer r.Body.Close()
	fmt.Fprintln(w, "hello 張三")
}

func main() {
	http.HandleFunc("/", sayHello)
	err := http.ListenAndServe(":8080", nil)
	if err != nil {
		fmt.Println("http server fail, err ", err)
		return
	}
}

2.3 自定義Server

type Server struct {
    Addr           string        // 監(jiān)聽的TCP地址,如果為空字符串會使用":http"
    Handler        Handler       // 調(diào)用的處理器,如為nil會調(diào)用http.DefaultServeMux
    ReadTimeout    time.Duration // 請求的讀取操作在超時前的最大持續(xù)時間
    WriteTimeout   time.Duration // 回復(fù)的寫入操作在超時前的最大持續(xù)時間
    MaxHeaderBytes int           // 請求的頭域最大長度,如為0則用DefaultMaxHeaderBytes
    TLSConfig      *tls.Config   // 可選的TLS配置,用于ListenAndServeTLS方法
    // TLSNextProto(可選地)指定一個函數(shù)來在一個NPN型協(xié)議升級出現(xiàn)時接管TLS連接的所有權(quán)。
    // 映射的鍵為商談的協(xié)議名;映射的值為函數(shù),該函數(shù)的Handler參數(shù)應(yīng)處理HTTP請求,
    // 并且初始化Handler.ServeHTTP的*Request參數(shù)的TLS和RemoteAddr字段(如果未設(shè)置)。
    // 連接在函數(shù)返回時會自動關(guān)閉。
    TLSNextProto map[string]func(*Server, *tls.Conn, Handler)
    // ConnState字段指定一個可選的回調(diào)函數(shù),該函數(shù)會在一個與客戶端的連接改變狀態(tài)時被調(diào)用。
    // 參見ConnState類型和相關(guān)常數(shù)獲取細(xì)節(jié)。
    ConnState func(net.Conn, ConnState)
    // ErrorLog指定一個可選的日志記錄器,用于記錄接收連接時的錯誤和處理器不正常的行為。
    // 如果本字段為nil,日志會通過log包的標(biāo)準(zhǔn)日志記錄器寫入os.Stderr。
    ErrorLog *log.Logger
    // 內(nèi)含隱藏或非導(dǎo)出字段
}

要管理服務(wù)端的行為,可以創(chuàng)建一個自定義的Server:

	s := &http.Server{
		Addr:           ":8080",
		Handler:        myHander,
		ReadTimeout:    10 * time.Second,
		WriteTimeout:   10 * time.Second,
		MaxHeaderBytes: 1 << 20,
	}

到此這篇關(guān)于Golang中http包的具體使用的文章就介紹到這了,更多相關(guān)Golang http包內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家! 

相關(guān)文章

  • win10下安裝Go和Goland的詳細(xì)教程

    win10下安裝Go和Goland的詳細(xì)教程

    這篇文章主要介紹了win10下安裝Go和Goland的詳細(xì)教程,本文給大家提到了go和golang之間的區(qū)別,本文給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2020-12-12
  • Golang中的path/filepath包用法

    Golang中的path/filepath包用法

    這篇文章主要介紹了Golang中的path/filepath包用法,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2020-12-12
  • 淺析Go語言中數(shù)組的使用

    淺析Go語言中數(shù)組的使用

    數(shù)組用于在單個變量中存儲相同類型的多個值,而不是為每個值聲明單獨(dú)的變量,這篇文章主要為大家介紹了Go語言中數(shù)組的簡單使用,需要?的可以參考下
    2023-08-08
  • Go語言O(shè)RM框架構(gòu)造查詢條件示例詳解

    Go語言O(shè)RM框架構(gòu)造查詢條件示例詳解

    這篇文章主要為大家介紹了Go語言O(shè)RM框架構(gòu)造查詢條件示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2022-12-12
  • 淺析Go語言中的逃逸分析

    淺析Go語言中的逃逸分析

    在Go語言中,內(nèi)存分配和逃逸分析是至關(guān)重要的概念,對于理解代碼的性能和內(nèi)存使用情況至關(guān)重要,本文將深入探討Go語言中的內(nèi)存分配原理以及逃逸分析的作用,希望對大家有所幫助
    2024-04-04
  • Go中Vendo機(jī)制的使用

    Go中Vendo機(jī)制的使用

    自Go1.6起,Go語言正式啟用vendor機(jī)制,允許將項(xiàng)目依賴放入項(xiàng)目內(nèi)的vendor目錄,類似私有GOPATH,本文就來介紹一下Vendo機(jī)制的使用,感興趣的可以了解一下
    2024-10-10
  • Golang使用ini庫讀取配置詳情

    Golang使用ini庫讀取配置詳情

    這篇文章主要介紹了Golang使用ini庫讀取配置詳情,go-ini是一個非常方便、高效的go配置文件操作庫。使用它在項(xiàng)目中讀取和修改配置文件,下文相關(guān)資料需要的小伙伴可可以參考一下
    2022-04-04
  • Golang連接池的幾種實(shí)現(xiàn)案例小結(jié)

    Golang連接池的幾種實(shí)現(xiàn)案例小結(jié)

    這篇文章主要介紹了Golang連接池的幾種實(shí)現(xiàn)案例小結(jié),文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2020-03-03
  • golang gorm 操作mysql及gorm基本用法

    golang gorm 操作mysql及gorm基本用法

    golang 官方的那個操作mysql的有點(diǎn)麻煩所以就使用了gorm,下面就gorm的使用做下簡單介紹,感興趣的朋友跟隨小編一起看看吧
    2018-11-11
  • Go操作etcd的實(shí)現(xiàn)示例

    Go操作etcd的實(shí)現(xiàn)示例

    etcd是近幾年比較火熱的一個開源的、分布式的鍵值對數(shù)據(jù)存儲系統(tǒng),提供共享配置、服務(wù)的注冊和發(fā)現(xiàn),本文主要介紹etcd的安裝和使用,感興趣的可以了解一下
    2021-09-09

最新評論