Golang——http包

        Go语言内置的net/http包十分优秀,提供了http客户端和服务器的实现。

        超文本传输协议(HTTP,HyperText Transfer Protocol)是互联网上应用最为广泛的一种网络传输协议,所有的www文件都必须遵循这个标准。设计HTTP最初的目的是为了提供一种发布和接收HTML页面的方法。

一. HTTP客户端

        基本的HTTP/HTTPS请求Get,Head,Post和PostForm函数发出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后必须关闭回复的主体。

package mainimport ("io/ioutil""log""net/http"
)func main() {resp, err := http.Get("http://example.com")if err != nil {log.Println("http get fail")return}//关闭回复主体defer resp.Body.Close()body, err := ioutil.ReadAll(resp.Body)//...
}

        1.1 Get请求

        函数签名:

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

        Get向指定的URL发出Get请求,如果回应的状态码如下,Get会调用c.CheckRedirect后执行重定向。

301(Moved Permanently)

302(Found)

303(See Other)

307(Temporary Redirect)

        如果c.CheckRedirect执行失败或存在HTTP协议错误时,本方法返回错误。如果回应的状态码不是2xx,本方法并不会返回错误。如果返回值err为nil,resp.Body总是非nil的,调用者应该在读取完resp.Body后关闭它。

        Get是对DefaultClient的Get方法的包装。

        1.2 post和get示例服务端代码

package mainimport ("fmt""io/ioutil""net/http"
)func getHandleFunc(w http.ResponseWriter, r *http.Request) {defer r.Body.Close()data := r.URL.Query() //获得get方法的参数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()//请求数据类型是application/jsonb, 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方法示例

  • 不带参数客户端
package mainimport ("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}//关闭回复主体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))
}
  • 带参数客户端

        关于Get请求带参数需要使用Go语言内置的net/url标准库来处理。

package mainimport ("fmt""io/ioutil""net/http""net/url"
)func main() {apiUrl := "http://127.0.0.1:9090/get"//URL参数data := url.Values{}data.Set("name", "张三")data.Set("age", "20")//URL参数需要编码,因为有的特殊字符被赋予了特殊含义u, err := url.ParseRequestURI(apiUrl)if err != nil {fmt.Println("url parse fail ", err)}u.RawQuery = data.Encode() //url encodefmt.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请求

        函数签名:

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

        Post向指定的URL发送一个POST请求。bodyType为POST的数据类型,Body为POST数据,作为请求的主体。如果参数body实现了io.Closer接口,它会在发送请求后被关闭。调用者有责任在读取完返回值resp的主体后关闭它。

        Post是对包变量DefaultClient的Post方法的包装。

        1.5 post示例

package mainimport ("fmt""io/ioutil""net/http""strings"
)func main() {apiUrl := "http://127.0.0.1:9090/post"//表单数据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客户端头域,重定向和其它策略,创建一个client:

type Client struct {// Transport指定执行独立、单次HTTP请求的机制。// 如果Transport为nil,则使用DefaultTransport。Transport RoundTripper// CheckRedirect指定处理重定向的策略。// 如果CheckRedirect不为nil,客户端会在执行重定向之前调用本函数字段。// 参数req和via是将要执行的请求和已经执行的请求(切片,越新的请求越靠后)。// 如果CheckRedirect返回一个错误,本类型的Get方法不会发送请求req,// 而是返回之前得到的最后一个回复和该错误。(包装进url.Error类型里)//// 如果CheckRedirect为nil,会采用默认策略:连续10此请求后停止。CheckRedirect func(req *Request, via []*Request) error// Jar指定cookie管理器。// 如果Jar为nil,请求中不会发送cookie,回复中的cookie会被忽略。Jar CookieJar// Timeout指定本类型的值执行请求的时间限制。// 该超时限制包括连接时间、重定向和读取回复主体的时间。// 计时器会在Head、Get、Post或Do方法返回后继续运作并在超时后中断回复主体的读取。//// Timeout为零值表示不设置超时。//// Client实例的Transport字段必须支持CancelRequest方法,// 否则Client会在试图用Head、Get、Post或Do方法执行请求时返回错误。// 本类型的Transport字段默认值(DefaultTransport)支持CancelRequest方法。Timeout time.Duration
}

        Client类型代表HTTP客户端。它的零值(DefaultClient)是一个可用的使用DefaultTransport的客户端。

        Client的Transport字段一般会含有内部状态(缓存TCP连接),因此Client类型值应尽量被重用而不是每次需要都创建新的。Client类型值可以安全的被多个go程同时使用。

        Client类型的层次比RoundTripper接口(如Transport)高,还会管理HTTP的cookie和重定向等细节。

//设置重定向
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客户端库,它提供了连接池、重试、超时控制等功能,可以方便地进行 http 请求。

        要管理代理,TLS配置,keep-alive,压缩和其它设置,可以创建一个Transport,对应Client的Transport字段。

type Transport struct {// Proxy指定一个对给定请求返回代理的函数。// 如果该函数返回了非nil的错误值,请求的执行就会中断并返回该错误。// 如果Proxy为nil或返回nil的*URL置,将不使用代理。Proxy func(*Request) (*url.URL, error)// Dial指定创建TCP连接的拨号函数。如果Dial为nil,会使用net.Dial。Dial func(network, addr string) (net.Conn, error)// TLSClientConfig指定用于tls.Client的TLS配置信息。// 如果该字段为nil,会使用默认的配置信息。TLSClientConfig *tls.Config// TLSHandshakeTimeout指定等待TLS握手完成的最长时间。零值表示不设置超时。TLSHandshakeTimeout time.Duration// 如果DisableKeepAlives为真,会禁止不同HTTP请求之间TCP连接的重用。DisableKeepAlives bool// 如果DisableCompression为真,会禁止Transport在请求中没有Accept-Encoding头时,// 主动添加"Accept-Encoding: gzip"头,以获取压缩数据。// 如果Transport自己请求gzip并得到了压缩后的回复,它会主动解压缩回复的主体。// 但如果用户显式的请求gzip压缩数据,Transport是不会主动解压缩的。DisableCompression bool// 如果MaxIdleConnsPerHost!=0,会控制每个主机下的最大闲置连接。// 如果MaxIdleConnsPerHost==0,会使用DefaultMaxIdleConnsPerHost。MaxIdleConnsPerHost int// ResponseHeaderTimeout指定在发送完请求(包括其可能的主体)之后,// 等待接收服务端的回复的头域的最大时间。零值表示不设置超时。// 该时间不包括获取回复主体的时间。ResponseHeaderTimeout time.Duration// 内含隐藏或非导出字段
}
	tr := &http.Transport{TLSClientConfig: &tls.Config{RootCAs: pool,},DisableCompression: true,}client := &http.Client{Transport: tr,}resp, err := client.Get("http://example.com")//...

二. 服务端

        2.1 默认server

        ListenAndServer使用指定的监听地址和处理器启动一个HTTP服务端。处理器参数通常是nil,这表示采用包变量DefaultServeMux作为处理器。

        Handle和HandleFunc函数可以向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 mainimport ("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        // 监听的TCP地址,如果为空字符串会使用":http"Handler        Handler       // 调用的处理器,如为nil会调用http.DefaultServeMuxReadTimeout    time.Duration // 请求的读取操作在超时前的最大持续时间WriteTimeout   time.Duration // 回复的写入操作在超时前的最大持续时间MaxHeaderBytes int           // 请求的头域最大长度,如为0则用DefaultMaxHeaderBytesTLSConfig      *tls.Config   // 可选的TLS配置,用于ListenAndServeTLS方法// TLSNextProto(可选地)指定一个函数来在一个NPN型协议升级出现时接管TLS连接的所有权。// 映射的键为商谈的协议名;映射的值为函数,该函数的Handler参数应处理HTTP请求,// 并且初始化Handler.ServeHTTP的*Request参数的TLS和RemoteAddr字段(如果未设置)。// 连接在函数返回时会自动关闭。TLSNextProto map[string]func(*Server, *tls.Conn, Handler)// ConnState字段指定一个可选的回调函数,该函数会在一个与客户端的连接改变状态时被调用。// 参见ConnState类型和相关常数获取细节。ConnState func(net.Conn, ConnState)// ErrorLog指定一个可选的日志记录器,用于记录接收连接时的错误和处理器不正常的行为。// 如果本字段为nil,日志会通过log包的标准日志记录器写入os.Stderr。ErrorLog *log.Logger// 内含隐藏或非导出字段
}

        要管理服务端的行为,可以创建一个自定义的Server:

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

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/pingmian/12159.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

消息队列选型

一、要解决的问题 1.1 异步 分析&#xff1a; 需要根据场景来判断。若整体链路的逻辑中&#xff0c;某些逻辑是不需要强实时的&#xff0c;滞后一段时间是允许的&#xff0c;同时又不会对用户带来不好的体验&#xff0c;那么可以使用MQ完成异步操作。 例如&#xff1a;秒杀场…

解锁客户需求密码:银行业数据分析在业务决策中的关键作用

一、引言 在数字化和大数据时代的浪潮下&#xff0c;银行业正经历着前所未有的变革。作为数据分析领域的资深专家&#xff0c;我深知数据分析在银行业务发展中的重要性和价值。本文将从银行业数据分析的角度出发&#xff0c;深入探讨相关业务场景下的数据分析应用&#xff0c;…

UVa11419 SAM I AM

UVa11419 SAM I AM 题目链接题意分析AC 代码 题目链接 UVA - 11419 SAM I AM 题意 给出一个 RC 大小的网格&#xff0c;网格上面放了一些目标。可以在网格外发射子弹&#xff0c;子弹会沿着垂直或者水平方向飞行&#xff0c;并且打掉飞行路径上的所有目标&#xff0c;如下图所…

Java 环境变量未生效

在配置 Java 环境变量的时候&#xff0c;有可能会出现修改了JDK的路径&#xff0c;但是Java的环境变量没有相应切换的情况。比如&#xff1a; 但此时在控制台使用java -version命令输出的JDK版本不是新配置的版本&#xff0c;依然是之前的&#xff0c;甚至提示找不到java命令&a…

汇昌联信科技:拼多多电商的运营流程有哪些?

在当今互联网高速发展的时代&#xff0c;电商平台层出不穷&#xff0c;其中拼多多以其独特的团购模式和低价策略迅速崛起&#xff0c;成为众多消费者和商家的新宠。那么&#xff0c;拼多多电商的运营流程究竟包含哪些环节呢?接下来&#xff0c;我们将从商品上架、营销推广、订…

B/S版+java开发的医院绩效考核系统maven+Visual Studio Code 医院绩效考核管理系统 提升医疗服务质量的关键

B/S版java开发的医院绩效考核系统mavenVisual Studio Code 医院绩效考核管理系统 提升医疗服务质量的关键 医院绩效评价系统的建设&#xff0c;优化医院绩效管理体系&#xff0c;规范化工作目标的设计、沟通、评价与反馈&#xff0c;改进和提供医院管理人员的管理能力和成效&am…

关于linux的防护,以及群集你要知道的有哪些1-系统安全及应用

1、系统账号清理 1)将非登录用户shell设为/sbin/nologin useradd -s /sbin/nologin 用户名 usermod -s /sbin/nologin 用户名 2)锁定长期不使用的账号 usermod -L 用户名 (usermod -U 解锁) passwd -l 用户名 (passwd -u 解锁)…

Nginx - location 指令(二)

location 指令 location [ | ~ | ~* | ^~ ] uri {}不讨论 location name {} 形式 官方文档有如下描述&#xff1a; A location can either be defined by a prefix string, or by a regular expression. Regular expressions are specified with the preceding ~* modifier (…

【Web】HNCTF 2024 题解(部分)

目录 Please_RCE_Me ezFlask GoJava ez_tp GPTS Please_RCE_Me <?php if($_GET[moran] flag){highlight_file(__FILE__);if(isset($_POST[task])&&isset($_POST[flag])){$str1 $_POST[task];$str2 $_POST[flag];if(preg_match(/system|eval|assert|call|…

Linux进程间几种通信机制

一. 简介 经过前一篇文章的学习&#xff0c; 我们知道Linux下有两种标准&#xff1a;system V标准和 Posix标准。 System V 和 POSIX 标准是操作系统提供的接口标准&#xff0c;它们规定了操作系统应该如何实现一些基本功能&#xff0c;比如线程、进程间通信、文件处理等。 …

数组的学习

一.数组定义方法&#xff1a; 方法一&#xff1a; 数组名(value0 value1 value2 ...) 方法二&#xff1a; 数组名([0]value [1]value [2]value ...) 方法三&#xff1a; 列表名"value0 value1 value2 ..." 数组名($列表名) 方法四&#xff1a; 数组名[0]"va…

暴雨分布式存储集群助重庆高校打造智慧校园

教育是国家发展的基石&#xff0c;教育兴则国家兴&#xff0c;教育强则国家强。党的二十大报告指出&#xff0c;“加快建设教育强国”&#xff0c;并提出到2035年“建成教育强国”的总体目标。随着数字时代的到来&#xff0c;以物联网、大数据、云计算和人工智能为代表的数字技…

使用torch.nn.ModuleList构建神经网络

在 PyTorch 中&#xff0c;torch.nn.ModuleList 是一个持有子模块的类&#xff0c;它是 torch.nn.Module 的一个子类。与 torch.nn.Sequential 不同&#xff0c;ModuleList 不会自动地对添加到其中的模块进行前向传播。相反&#xff0c;它主要用于存储多个模块&#xff0c;并且…

线程与进程___(一)

1、线程 Thread 类创建得线程为前台线程&#xff0c;线程池中的为后台线程&#xff0c;&#xff0c;&#xff0c;Main方法结束后&#xff0c;前台线程仍然运行&#xff0c;直到完成&#xff0c;而后台线程立刻结束。 调用线程时候不会立刻进入 Running 状态&#xff0c; 而是…

redis原生命令及项目使用

主动更新策略 缓存问题及解决 布隆过滤出现哈希冲突解决方案: 选择合适的哈希函数:布隆过滤器的性能和哈希函数的选择密切相关。选择高效、低碰撞率的哈希函数可以降低误判率。通常使用的哈希函数有 MurmurHash、FNV 等。 合理设置过滤器大小:过滤器的大小(位数组的大小)…

学习笔记——字符串(单模+多模+练习题)

单模匹配 Brute Force算法&#xff08;暴力&#xff09; 算法思想 母串和模式串字符依次配对&#xff0c;如果配对成功则继续比较后面位置是否相同&#xff0c;如果出现匹配不成功的位置&#xff0c;则j&#xff08;模式串当前的位置&#xff09;从头开始&#xff0c;i&…

Docker和Kubernetes之间的关系

Docker和Kubernetes在容器化生态系统中各自扮演着不同的角色 它们之间是互补的&#xff0c;而不是替代关系。 Docker是一个开源的容器化平台&#xff0c;它允许开发人员将应用程序及其依赖项打包到一个可移植的容器中&#xff0c;并确保这些容器可以在任何Docker环境中一致地…

曲线救国:window 安装 docker

你好&#xff0c;我是 shengjk1&#xff0c;多年大厂经验&#xff0c;努力构建 通俗易懂的、好玩的编程语言教程。 欢迎关注&#xff01;你会有如下收益&#xff1a; 了解大厂经验拥有和大厂相匹配的技术等 希望看什么&#xff0c;评论或者私信告诉我&#xff01; 文章目录 一…

how do i get chat‘s members‘s ids by bot in telegram

how do i get chat’s members’s ids by bot in telegram? the bot is already a chat admin.please give examples using golang The GetChatAdministrators method in the go-telegram-bot-api package only retrieves information about chat administrators, not all ch…

L2-048 寻宝图 - java

L2-048 寻宝图 Java (javac) 时间限制 800 ms 内存限制 512 MB 其他编译器 时间限制 400 ms 内存限制 64 MB 栈限制 8192 KB 题目描述&#xff1a; 给定一幅地图&#xff0c;其中有水域&#xff0c;有陆地。被水域完全环绕的陆地是岛屿。有些岛屿上埋藏有宝藏&#xff0c;这些有…