前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >golang常用的http请求操作

golang常用的http请求操作

作者头像
赵云龙龙
发布2020-05-22 15:43:21
1.4K0
发布2020-05-22 15:43:21
举报
文章被收录于专栏:python爱好部落

Golang诞生已经超过十个年头了,发展得愈发完善,其简单方便的协程并发机制使得其在爬虫领域有着一定的天赋。

首先我们来看一看,Golang相对于Python这个爬虫领域的传统强者,有哪些优点和缺点。

优点:

完善简便的协程并发机制 并发数量大 占用资源少 运行速度更快 部署方便 缺点:

数据处理比较繁琐 成熟工具不是很多 资料较少 实现相同逻辑需要的代码更多 由于Golang本身静态语言的特性,和其特别的异常处理方式等等原因,在发起较复杂的请求时需要的代码量自然会比Python多不少,但是其并发的数量也是远超Python的,所以两者应用的场景并不十分相同,我们可以根据需要灵活的选择。

在刚刚接触Golang的http包时,觉得其非常的方便,发起请求只需要一行代码:

http.Get("https://www.baidu.com") 就算与Python的requests在便利方面也不遑多让,然而在Golang勾起了我的兴趣,并深入接触后,我发现并非如此。最简单的http.Get方法只能发起最简单的请求,一旦要设置headers、cookies等属性时,需要写的代码会成几何倍数上升,而设置代理或者管理重定向等操作,会更加复杂。

这个摸索的过程中最痛苦的是,在网上能找到资料非常的稀少,大多数时候只能阅读官方文档和阅读net标准库的源码。所幸Go语言的特性使得阅读Go源码是一件比较简单的事,相对于其他语言来说。

之前用python写各种网络请求的时候写的非常顺手,但是当打算用golang写的时候才发现相对来说还是python的那种方式用的更加顺手,习惯golang的用法之后也就差别不大了,下面主要整理了常用的通过golang发起的GET请求以及POST请求的代码例子 这里以httpbin为例: httpbin.org 这个网站能测试 HTTP 请求和响应的各种信息,比如 cookie、ip、headers 和登录验证等,且支持 GET、POST 等多种方法,对 web 开发和测试很有帮助。

它用 Python + Flask 编写,是一个开源项目。

官方网站:http://httpbin.org/ 开源地址:https://github.com/Runscope/httpbin

基本的GET请求

代码语言:javascript
复制
//基本的GET请求
package main

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

func main() {
    resp, err := http.Get("http://httpbin.org/get")
    if err != nil {
        fmt.Println(err)
        return
    }
    defer resp.Body.Close()
    body, err := ioutil.ReadAll(resp.Body)
    fmt.Println(string(body))
    fmt.Println(resp.StatusCode)
    if resp.StatusCode == 200 {
        fmt.Println("ok")
    }
}

带参数的Get请求

代码语言:javascript
复制
package main

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

func main(){
    resp, err := http.Get("http://httpbin.org/get?name=zhaofan&age=23")
    if err != nil {
        fmt.Println(err)
        return
    }
    defer resp.Body.Close()
    body, _ := ioutil.ReadAll(resp.Body)
    fmt.Println(string(body))

}

但是如果我们想要把一些参数做成变量而不是直接放到url中怎么操作,代码例子如下:

代码语言:javascript
复制
package main

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

func main(){
    params := url.Values{}
    Url, err := url.Parse("http://httpbin.org/get")
    if err != nil {
        return
    }
    params.Set("name","zhaofan")
    params.Set("age","23")
    //如果参数中有中文参数,这个方法会进行URLEncode
    Url.RawQuery = params.Encode()
    urlPath := Url.String()
    fmt.Println(urlPath) // https://httpbin.org/get?age=23&name=zhaofan
    resp,err := http.Get(urlPath)
    defer resp.Body.Close()
    body, _ := ioutil.ReadAll(resp.Body)
    fmt.Println(string(body))
}

解析JSON类型的返回结果

代码语言:javascript
复制
package main

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

type result struct {
    Args string `json:"args"`
    Headers map[string]string `json:"headers"`
    Origin string `json:"origin"`
    Url string `json:"url"`
}

func main() {
    resp, err := http.Get("http://httpbin.org/get")
    if err != nil {
        return
    }
    defer resp.Body.Close()
    body, _ := ioutil.ReadAll(resp.Body)
    fmt.Println(string(body))
    var res result
    _ = json.Unmarshal(body,&res)
    fmt.Printf("%#v", res)
}

GET请求添加请求头

代码语言:javascript
复制
package main

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

func main() {
    client := &http.Client{}
    req,_ := http.NewRequest("GET","http://httpbin.org/get",nil)
    req.Header.Add("name","zhaofan")
    req.Header.Add("age","3")
    resp,_ := client.Do(req)
    body, _ := ioutil.ReadAll(resp.Body)
    fmt.Printf(string(body))
}

从上述的结果可以看出我们设置的头是成功了:

golang 发起POST请求

基本的POST使用

代码语言:javascript
复制
package main

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

func main() {
    urlValues := url.Values{
        "name":{"zhaofan"},
        "age":{"23"},
    }
    reqBody:= urlValues.Encode()
    resp, _ := http.Post("http://httpbin.org/post", "text/html",strings.NewReader(reqBody))
    body,_:= ioutil.ReadAll(resp.Body)
    fmt.Println(string(body))
}

另外一种方式

代码语言:javascript
复制
package main

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

func main() {
    urlValues := url.Values{
        "name":{"zhaofan"},
        "age":{"23"},
    }
    reqBody:= urlValues.Encode()
    resp, _ := http.Post("http://httpbin.org/post", "text/html",strings.NewReader(reqBody))
    body,_:= ioutil.ReadAll(resp.Body)
    fmt.Println(string(body))
}

发送JSON数据的post请求

代码语言:javascript
复制
package main

import (
    "bytes"
    "encoding/json"
    "fmt"
    "io/ioutil"
    "net/http"
)

func main() {
    client := &http.Client{}
    data := make(map[string]interface{})
    data["name"] = "zhaofan"
    data["age"] = "23"
    bytesData, _ := json.Marshal(data)
    req, _ := http.NewRequest("POST","http://httpbin.org/post",bytes.NewReader(bytesData))
    resp, _ := client.Do(req)
    body, _ := ioutil.ReadAll(resp.Body)
    fmt.Println(string(body))

}

不用client的post请求

代码语言:javascript
复制
package main

import (
    "bytes"
    "encoding/json"
    "fmt"
    "io/ioutil"
    "net/http"
)

func main() {
    data := make(map[string]interface{})
    data["name"] = "zhaofan"
    data["age"] = "23"
    bytesData, _ := json.Marshal(data)
    resp, _ := http.Post("http://httpbin.org/post","application/json", bytes.NewReader(bytesData))
    body, _ := ioutil.ReadAll(resp.Body)
    fmt.Println(string(body))
}
本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2020-05-08,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 python粉丝团 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 基本的GET请求
  • 带参数的Get请求
  • 解析JSON类型的返回结果
  • GET请求添加请求头
  • golang 发起POST请求
    • 基本的POST使用
      • 发送JSON数据的post请求
        • 不用client的post请求
        领券
        问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档