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

Golang請(qǐng)求fasthttp實(shí)踐

 更新時(shí)間:2021年11月03日 11:42:37   作者:FunTester  
本文主要介紹了Golang請(qǐng)求fasthttp實(shí)踐,文中通過示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下

原計(jì)劃學(xué)完Golang語言HTTP客戶端實(shí)踐之后,就可以繼續(xù)了,沒想到才疏學(xué)淺,在搜資料的時(shí)候發(fā)現(xiàn)除了Golang SDK自帶的net/http,還有一個(gè)更牛的HttpClient實(shí)現(xiàn)github.com/valyala/fasthttp,據(jù)說性能是net/http的10倍,我想可能是有點(diǎn)夸張了,后期我會(huì)進(jìn)行測(cè)試,以正視聽。

在github.com/valyala/fasthttp用到了對(duì)象池,為了在高性能測(cè)試中減少內(nèi)存的使用,fasthttp使用了兩個(gè)對(duì)象池(我只看了這倆):requestPool sync.Pool和responsePool sync.Pool,當(dāng)然fasthttp也提供了正常的對(duì)象創(chuàng)建API,后面我在案例中也會(huì)寫到。

基礎(chǔ)API演示

首先分享一下基礎(chǔ)的用法封裝:

PS:這個(gè)屬于練習(xí)版本,所以沒寫多少注釋。

package ft

import (
 "encoding/json"
 "fmt"
 "funtester/task"
 "github.com/valyala/fasthttp"
)


func FastGet(url string, args map[string]interface{}) ([]byte, error) {
 uri := url + "?" + task.ToValues(args)
 _, resp, err := fasthttp.Get(nil, uri)
 if err != nil {
  fmt.Println("請(qǐng)求失敗:", err.Error())
  return nil, err
 }
 return resp, err
}

func FastPostForm(url string, args map[string]interface{}) ([]byte, error) {

 // 填充表單,類似于net/url
 params := &fasthttp.Args{}
 for s, i2 := range args {
  sprintf := fmt.Sprintf("%v", i2)
  params.Add(s, sprintf)
 }
 _, resp, err := fasthttp.Post(nil, url, params)
 if err != nil {
  fmt.Println("請(qǐng)求失敗:", err.Error())
  return nil, err
 }
 return resp, nil
}

func FastPostJson(url string, args map[string]interface{}) ([]byte, error) {

 req := &fasthttp.Request{}
 req.SetRequestURI(url)

 marshal, _ := json.Marshal(args)
 req.SetBody(marshal)

 // 默認(rèn)是application/x-www-form-urlencoded,其實(shí)無所謂
 req.Header.SetContentType("application/json")
 req.Header.SetMethod("POST")

 resp := &fasthttp.Response{}
 if err := fasthttp.Do(req, resp); err != nil {
  fmt.Println("請(qǐng)求失敗:", err.Error())
  return nil, err
 }
 return resp.Body(), nil
}

其中兩點(diǎn)主要注意:

  • FastGet、FastPostForm使用的fasthttp提供的默認(rèn)獲取請(qǐng)求的方式,F(xiàn)astPostJson使用了自定義請(qǐng)求和獲取響應(yīng)的方式
  • 關(guān)于請(qǐng)求頭中的req.Header.SetContentType方法,其實(shí)無所謂,服務(wù)端都可以解析

高性能API演示

下面分享使用更高的性能(基于對(duì)象池)的API創(chuàng)建請(qǐng)求和獲取響應(yīng)的方式:

package task

import (
 "crypto/tls"
 "encoding/json"
 "fmt"
 "github.com/valyala/fasthttp"
 "log"
 "time"
)

var FastClient fasthttp.Client = fastClient()

// FastGet 獲取GET請(qǐng)求對(duì)象,沒有進(jìn)行資源回收
// @Description:
// @param url
// @param args
// @return *fasthttp.Request
func FastGet(url string, args map[string]interface{}) *fasthttp.Request {
 req := fasthttp.AcquireRequest()
 req.Header.SetMethod("GET")
 values := ToValues(args)
 req.SetRequestURI(url + "?" + values)
 return req
}

// FastPostJson POST請(qǐng)求JSON參數(shù),沒有進(jìn)行資源回收
// @Description:
// @param url
// @param args
// @return *fasthttp.Request
func FastPostJson(url string, args map[string]interface{}) *fasthttp.Request {
 req := fasthttp.AcquireRequest()
 // 默認(rèn)是application/x-www-form-urlencoded
 req.Header.SetContentType("application/json")
 req.Header.SetMethod("POST")
 req.SetRequestURI(url)
 marshal, _ := json.Marshal(args)
 req.SetBody(marshal)
 return req
}

// FastPostForm POST請(qǐng)求表單傳參,沒有進(jìn)行資源回收
// @Description:
// @param url
// @param args
// @return *fasthttp.Request
func FastPostForm(url string, args map[string]interface{}) *fasthttp.Request {
 req := fasthttp.AcquireRequest()
 // 默認(rèn)是application/x-www-form-urlencoded
 //req.Header.SetContentType("application/json")
 req.Header.SetMethod("POST")
 req.SetRequestURI(url)
 marshal, _ := json.Marshal(args)
 req.BodyWriter().Write([]byte(ToValues(args)))
 req.BodyWriter().Write(marshal)
 return req
}

// FastResponse 獲取響應(yīng),保證資源回收
// @Description:
// @param request
// @return []byte
// @return error
func FastResponse(request *fasthttp.Request) ([]byte, error) {
 response := fasthttp.AcquireResponse()
 defer fasthttp.ReleaseResponse(response)
 defer fasthttp.ReleaseRequest(request)
 if err := FastClient.Do(request, response); err != nil {
  log.Println("響應(yīng)出錯(cuò)了")
  return nil, err
 }
 return response.Body(), nil
}

// DoGet 發(fā)送GET請(qǐng)求,獲取響應(yīng)
// @Description:
// @param url
// @param args
// @return []byte
// @return error
func DoGet(url string, args map[string]interface{}) ([]byte, error) {
 req := fasthttp.AcquireRequest()
 defer fasthttp.ReleaseRequest(req) // 用完需要釋放資源
 req.Header.SetMethod("GET")
 values := ToValues(args)
 req.SetRequestURI(url + "?" + values)
 resp := fasthttp.AcquireResponse()
 defer fasthttp.ReleaseResponse(resp) // 用完需要釋放資源
 if err := FastClient.Do(req, resp); err != nil {
  fmt.Println("請(qǐng)求失敗:", err.Error())
  return nil, err
 }
 return resp.Body(), nil
}

// fastClient 獲取fast客戶端
// @Description:
// @return fasthttp.Client
func fastClient() fasthttp.Client {
 return fasthttp.Client{
  Name:                     "FunTester",
  NoDefaultUserAgentHeader: true,
  TLSConfig:                &tls.Config{InsecureSkipVerify: true},
  MaxConnsPerHost:          2000,
  MaxIdleConnDuration:      5 * time.Second,
  MaxConnDuration:          5 * time.Second,
  ReadTimeout:              5 * time.Second,
  WriteTimeout:             5 * time.Second,
  MaxConnWaitTimeout:       5 * time.Second,
 }
}

測(cè)試服務(wù)

用的還是moco_FunTester測(cè)試框架,腳本如下:

package com.mocofun.moco.main

import com.funtester.utils.ArgsUtil
import com.mocofun.moco.MocoServer
import org.apache.tools.ant.taskdefs.condition.And

class Share extends MocoServer {

    static void main(String[] args) {
        def util = new ArgsUtil(args)
        //                def server = getServerNoLog(util.getIntOrdefault(0,12345))
        def server = getServer(util.getIntOrdefault(0, 12345))
        server.get(both(urlStartsWith("/test"),existArgs("code"))).response("get請(qǐng)求")
        server.post(both(urlStartsWith("/test"), existForm("fun"))).response("post請(qǐng)求form表單")
        server.post(both(urlStartsWith("/test"), existParams("fun"))).response("post請(qǐng)求json表單")
        server.get(urlStartsWith("/qps")).response(qps(textRes("恭喜到達(dá)QPS!"), 1))
//        server.response(delay(jsonRes(getJson("Have=Fun ~ Tester !")), 1000))
        server.response("Have Fun ~ Tester !")
        def run = run(server)
        waitForKey("fan")
        run.stop()
    }
}

Golang單元測(cè)試

第一次寫Golang單測(cè),有點(diǎn)不適應(yīng),搞了很久才通。

package test

import (
 "funtester/ft"
 "funtester/task"
 "log"
 "testing"
)

const url = "http://localhost:12345/test"

func args() map[string]interface{} {
 return map[string]interface{}{
  "code": 32,
  "fun":  32,
  "msg":  "324",
 }
}

func TestGet(t *testing.T) {
 get := task.FastGet(url, args())
 res, err := task.FastResponse(get)
 if err != nil {
  t.Fail()
 }
 v := string(res)
 log.Println(v)
 if v != "get請(qǐng)求" {
  t.Fail()
 }
}

func TestPostJson(t *testing.T) {
 post := task.FastPostJson(url, args())
 res, err := task.FastResponse(post)
 if err != nil {
  t.Fail()
 }
 v := string(res)
 log.Println(v)
 if v != "post請(qǐng)求json表單" {
  t.Fail()
 }
}

func TestPostForm(t *testing.T) {
 post := task.FastPostForm(url, args())
 res, err := task.FastResponse(post)
 if err != nil {
  t.Fail()
 }
 v := string(res)
 log.Println(v)
 if v != "post請(qǐng)求form表單" {
  t.Fail()
 }
}

func TestGetNor(t *testing.T) {
 res, err := ft.FastGet(url, args())
 if err != nil {
  t.Fail()
 }
 v := string(res)
 log.Println(v)
 if v != "get請(qǐng)求" {
  t.Fail()
 }
}

func TestPostJsonNor(t *testing.T) {
 res, err := ft.FastPostJson(url, args())
 if err != nil {
  t.Fail()
 }
 v := string(res)
 log.Println(v)
 if v != "post請(qǐng)求json表單" {
  t.Fail()
 }
}

func TestPostFormNor(t *testing.T) {
 res, err := ft.FastPostForm(url, args())
 if err != nil {
  t.Fail()
 }
 v := string(res)
 log.Println(v)
 if v != "post請(qǐng)求form表單" {
  t.Fail()
 }
}

測(cè)試報(bào)告

用的自帶的控制臺(tái)輸出內(nèi)容:

=== RUN   TestGet
2021/10/18 18:56:49 get請(qǐng)求
--- PASS: TestGet (0.01s)
=== RUN   TestPostJson
2021/10/18 18:56:49 post請(qǐng)求json表單
--- PASS: TestPostJson (0.00s)
=== RUN   TestPostForm
2021/10/18 18:56:49 post請(qǐng)求form表單
--- PASS: TestPostForm (0.00s)
=== RUN   TestGetNor
2021/10/18 18:56:49 get請(qǐng)求
--- PASS: TestGetNor (0.00s)
=== RUN   TestPostJsonNor
2021/10/18 18:56:49 post請(qǐng)求json表單
--- PASS: TestPostJsonNor (0.00s)
=== RUN   TestPostFormNor
2021/10/18 18:56:49 post請(qǐng)求form表單
--- PASS: TestPostFormNor (0.00s)
=== RUN   TestStageJSON

到此這篇關(guān)于Golang請(qǐng)求fasthttp實(shí)踐的文章就介紹到這了,更多相關(guān)Golang請(qǐng)求fasthttp內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • 在go中使用omitempty的代碼實(shí)例

    在go中使用omitempty的代碼實(shí)例

    今天小編就為大家分享一篇關(guān)于在go中使用omitempty的代碼實(shí)例,小編覺得內(nèi)容挺不錯(cuò)的,現(xiàn)在分享給大家,具有很好的參考價(jià)值,需要的朋友一起跟隨小編來看看吧
    2019-04-04
  • go protobuf?詳解

    go protobuf?詳解

    Protobuf是Protocol Buffers的簡(jiǎn)稱,它是Google公司開發(fā)的一種數(shù)據(jù)描述語言,是一種輕便高效的結(jié)構(gòu)化數(shù)據(jù)存儲(chǔ)格式,可以用于結(jié)構(gòu)化數(shù)據(jù)串行化,或者說序列化,這篇文章主要介紹了protobuf?詳解,需要的朋友可以參考下
    2024-01-01
  • Go語言里的結(jié)構(gòu)體文法實(shí)例分析

    Go語言里的結(jié)構(gòu)體文法實(shí)例分析

    這篇文章主要介紹了Go語言里的結(jié)構(gòu)體文法,實(shí)例分析了結(jié)構(gòu)體文法的概念及使用技巧,具有一定參考借鑒價(jià)值,需要的朋友可以參考下
    2015-02-02
  • Go語言的Windows下環(huán)境配置以及簡(jiǎn)單的程序結(jié)構(gòu)講解

    Go語言的Windows下環(huán)境配置以及簡(jiǎn)單的程序結(jié)構(gòu)講解

    這篇文章主要介紹了Go語言的Windows下環(huán)境配置以及簡(jiǎn)單的程序結(jié)構(gòu)講解,從編程語言約定俗成的hellow world開始,需要的朋友可以參考下
    2015-10-10
  • Go gin權(quán)限驗(yàn)證實(shí)現(xiàn)過程詳解

    Go gin權(quán)限驗(yàn)證實(shí)現(xiàn)過程詳解

    這篇文章主要為大家介紹了Go gin權(quán)限驗(yàn)證實(shí)現(xiàn)過程詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-01-01
  • 深入理解golang的基本類型排序與slice排序

    深入理解golang的基本類型排序與slice排序

    大家都知道排序有內(nèi)部排序和外部排序,內(nèi)部排序是數(shù)據(jù)記錄在內(nèi)存中進(jìn)行排序,而外部排序是因排序的數(shù)據(jù)很大,一次不能容納全部的排序記錄,在排序過程中需要訪問外存。下面就來詳細(xì)介紹golang的基本類型排序與slice排序,有需要的朋友們可以參考借鑒。
    2016-09-09
  • Golang優(yōu)雅關(guān)閉channel的方法示例

    Golang優(yōu)雅關(guān)閉channel的方法示例

    Goroutine和channel是Go在“并發(fā)”方面兩個(gè)核心feature,下面這篇文章主要給大家介紹了關(guān)于Golang如何優(yōu)雅關(guān)閉channel的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),需要的朋友可以參考解決,下面來一起看看吧。
    2017-11-11
  • GoLang函數(shù)棧的使用詳細(xì)講解

    GoLang函數(shù)棧的使用詳細(xì)講解

    這篇文章主要介紹了GoLang函數(shù)棧的使用,我們的代碼會(huì)被編譯成機(jī)器指令并寫入到可執(zhí)行文件,當(dāng)程序執(zhí)行時(shí),可執(zhí)行文件被加載到內(nèi)存,這些機(jī)器指令會(huì)被存儲(chǔ)到虛擬地址空間中的代碼段,在代碼段內(nèi)部,指令是低地址向高地址堆積的
    2023-02-02
  • 如何在golang中使用shopspring/decimal來處理精度問題

    如何在golang中使用shopspring/decimal來處理精度問題

    本文主要介紹了如何在golang中使用shopspring/decimal來處理精度問題,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2023-04-04
  • Golang使用gzip壓縮字符減少redis等存儲(chǔ)占用的實(shí)現(xiàn)

    Golang使用gzip壓縮字符減少redis等存儲(chǔ)占用的實(shí)現(xiàn)

    本文主要介紹了Golang使用gzip壓縮字符減少redis等存儲(chǔ)占用的實(shí)現(xiàn),文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2023-01-01

最新評(píng)論