经验首页 前端设计 程序设计 Java相关 移动开发 数据库/运维 软件/图像 大数据/云计算 其他经验
当前位置:技术经验 » 程序设计 » PHP » 查看文章
PHP转Go系列 | GET 和 POST 请求的使用姿势
来源:cnblogs  作者:Yxh_blogs  时间:2024/7/1 11:26:09  对本文有异议

大家好,我是码农先森。

说到 HTTP 请求工具想必对我们做 Web 开发的程序员都不陌生,只要涉及到网络请求都必须使用。对于我们 PHP 程序员来说,最熟悉不过的就是 CURL 扩展,只要安装的这个扩展便可随意发起 HTTP 请求。 但在 PHP 语言中还有一个很好用的 Composer 包「guzzlehttp/guzzle」,相信大家只要做 PHP 开发的都接触过。

转到 Go 语言后,有些人也会在想 Go 中有没有这样的工具包呢?说实话,我从事 Go 语言开发这么挺久,也始终没有发现有类似 guzzle 这么好用的工具包。我想其中的原因可能是 Go 语言的官方标准库中提供了「net/http」工具,这个也能满足日常的开发需求,大家也就没有想再造轮子的兴趣了。话不多说,接下来我们开始介绍在 PHP 语言和 Go 语言中的使用姿势。

在 php_http 目录下中使用 Composer 命令安装 guzzle 包。

  1. [manongsen@root ~]$ pwd
  2. /home/manongsen/workspace/php_to_go/php_http
  3. [manongsen@root php_http]$ composer require guzzlehttp/guzzle

在 go_http 目录下中使用 go mod init 初始化 Go 项目。

  1. [manongsen@root ~]$ pwd
  2. /home/manongsen/workspace/php_to_go/go_http
  3. [manongsen@root go_http]$ go mod init go_http

这是初始化完成后的项目结构。

  1. [manongsen@root php_to_go]$ tree -L 2
  2. .
  3. ├── README.md
  4. ├── go_http
  5. ├── go.mod
  6. ├── go.sum
  7. └── main.go
  8. └── php_http
  9. ├── composer.json
  10. ├── composer.lock
  11. ├── index.php
  12. └── vendor

这次我们主要介绍最常用的两种请求方法,分别是 GET 请求和 POST 请求。

在 PHP 中先通过 require 加载到 GuzzleHttp 类库,然后实例化 \GuzzleHttp\Client 类,并通过构造函数设置 base_uri 和 timeout 参数,再基于 $client 对象发起 GET 请求和 POST 请求,在使用过程中需要注意捕获异常情况。

  1. // php_to_go/php_http/index.php
  2. <?php
  3. require 'vendor/autoload.php';
  4. try {
  5. // 构建请求客户端
  6. $client = new GuzzleHttp\Client([
  7. // 设置基础的请求地址
  8. 'base_uri' => 'https://www.baidu.com',
  9. // 设置超时时间
  10. 'timeout' => 3.0,
  11. ]);
  12. // -----------------GET 请求-----------------------
  13. $response = $client->request('GET', '/', [
  14. 'query' => ['wd' => 'php'] // 设置搜索参数
  15. ]);
  16. // 获取 HTTP 响应状态码
  17. print_r($response->getStatusCode());
  18. // 获取 HTTP 响应数据体
  19. print_r($response->getBody());
  20. // -----------------POST 请求-----------------------
  21. $response = $client->request('POST', '/', [
  22. 'json' => ['wd' => 'php'] // 设置搜索参数
  23. ]);
  24. // 获取 HTTP 响应状态码
  25. print_r($response->getStatusCode());
  26. // 获取 HTTP 响应数据体
  27. print_r($response->getBody());
  28. } catch (GuzzleHttp\Exception\RequestException $e) {
  29. // 捕获请求异常
  30. echo "Error: " . $e->getMessage();
  31. }

从上面的代码可以看出在 PHP 中发起 HTTP 请求使用起来还是很简单的。那么在 Go 中 GET 和 POST 的使用方法是怎样的呢?从下面的代码量上来看就要多很多了,先要 import 相关的标准库,比如 net/http、encoding/json 等。

其次定义一个 http.Client{} 结构体的对象,并且设置 HTTP 请求的超时时间。然后再调用 client.Get() 或 client.Post() 方法来发起 GET 及 Post 请求。最后再使用 ioutil.ReadAll 方法从 response.Body 网络数据流中读取出 HTTP 请求体数据,读取完数据之后要记得关闭资源。这里需要注意的一点是 response.Body 网络数据流是不能重复读取,初学者这里是容易犯错的点。

  1. // php_to_go/go_http/main.go
  2. package main
  3. import (
  4. "bytes"
  5. "encoding/json"
  6. "fmt"
  7. "io/ioutil"
  8. "net/http"
  9. "net/url"
  10. "time"
  11. )
  12. func main() {
  13. // 定义 基础的请求地址
  14. baseUrl := "https://www.baidu.com"
  15. // 创建一个 HTTP 客户端
  16. client := &http.Client{
  17. Timeout: 3 * time.Second, // 设置超时时间为 3 秒
  18. }
  19. // ----------------------GET请求--------------------------
  20. // 构建请求参数
  21. params := url.Values{}
  22. params.Add("wd", "go")
  23. // 发起 GET 请求
  24. response, err := client.Get(baseUrl + params.Encode())
  25. if err != nil {
  26. fmt.Printf("发起请求时出现错误: %v\n", err)
  27. return
  28. }
  29. // 关闭资源 防止资源泄露
  30. defer response.Body.Close()
  31. // 读取 HTTP 响应体数据
  32. body, err := ioutil.ReadAll(response.Body)
  33. if err != nil {
  34. fmt.Printf("读取响应时出现错误: %v\n", err)
  35. return
  36. }
  37. // 输出 HTTP 响应状态码
  38. fmt.Printf("status: %v\n", response.Status)
  39. // 输出 HTTP 响应体数据
  40. fmt.Printf("body: %v\n", string(body))
  41. // ----------------------POST请求--------------------------
  42. // 定义请求的参数
  43. reqParams := map[string]string{
  44. "wd": "go",
  45. }
  46. jsonData, err := json.Marshal(reqParams)
  47. if err != nil {
  48. fmt.Printf("JSON 编码错误: %v", err)
  49. return
  50. }
  51. // 创建一个新的字节缓冲区并将 jsonData 数据放入缓存区
  52. reqBody := bytes.NewBuffer(jsonData)
  53. // 发起 POST 请求,请求的内容格式为 JSON 格式
  54. response, err = client.Post(baseUrl, "application/json", reqBody)
  55. if err != nil {
  56. fmt.Printf("发起请求时出现错误: %v", err)
  57. return
  58. }
  59. // 关闭资源 防止资源泄露
  60. defer response.Body.Close()
  61. // 读取 HTTP 响应体数据
  62. body, err = ioutil.ReadAll(response.Body)
  63. if err != nil {
  64. fmt.Printf("读取响应时出现错误: %v", err)
  65. return
  66. }
  67. // 输出 HTTP 响应状态码
  68. fmt.Printf("status: %v\n", response.Status)
  69. // 输出 HTTP 响应体数据
  70. fmt.Printf("body: %v\n", string(body))
  71. }

从使用的角度来看 PHP 比 Go 要简单的多,异常捕获使用 try catch{} 即可,反观 Go 中要通过 if != err {} 来反复的判断是否有错误,略显繁琐。同时在这个例子中也就可以看得出 php 的开发效率比 go 要快的多,go 中要时刻注意变量的类型、数据的读取、资源的关闭等情况,php 则一梭子就开发完了。

但 Go 的执行效率可比 PHP 高的多,Go 作为静态语言直接打包成了二进制可执行文件,而 PHP 是动态语言执行时才开始解析代码。因此两者刚好互补,学习 Go 也更利于我们 PHPer 了解系统资源、网络请求、缓存区等的使用方式,这些都是在 PHP 中很少能接触到的。

对于 HTTP 工具的使用姿势,其实最重要的是要掌握 Header 头各种参数的配置,比如 Content-Type、Proxy、Authorization、Cookies、Cert 等,那么我这里在把 GuzzleHttp 和 net/http 的官方文档附上,方便大家更加深入的学习。

推荐


欢迎关注、分享、点赞、收藏、在看,我是微信公众号「码农先森」作者。

原文链接:https://www.cnblogs.com/yxhblogs/p/18267989

 友情链接:直通硅谷  点职佳  北美留学生论坛

本站QQ群:前端 618073944 | Java 606181507 | Python 626812652 | C/C++ 612253063 | 微信 634508462 | 苹果 692586424 | C#/.net 182808419 | PHP 305140648 | 运维 608723728

W3xue 的所有内容仅供测试,对任何法律问题及风险不承担任何责任。通过使用本站内容随之而来的风险与本站无关。
关于我们  |  意见建议  |  捐助我们  |  报错有奖  |  广告合作、友情链接(目前9元/月)请联系QQ:27243702 沸活量
皖ICP备17017327号-2 皖公网安备34020702000426号