go | gin多服务 | goroutine | ReadTimeout&WriteTimeout

采用 go 的协程完成 gin多服务
什么多服务?就是启动服务器后,可以同时访问多个资源,比如router01、router02
ReadTimeout 读取请求超时时间,一般防止客户端慢请求,导致长时间占用服务器资源
WriteTimeout 写入响应超时时间,一般是防止客户端读取响应慢,导致长时间占用服务器资源

可以这么理解,就是服务器这边的效率是特别高的,出现的问题都是从客户端那边冒出来的
然后,服务器要读取来自客户端的请求 所有叫ReadTimeout 读取请求超时时间,这个是从客户端从开始发起请求到结束发起请求结束的时间,如果一个请求数据,一直慢吞吞的发送,这个时间段服务器其实是中断来处理这个业务的,这个时间段的资源全部用来等待请求数据,是不是占用了很多资源?
WriteTimeout 叫写入响应超时时间,就是服务器要响应客户端的请求,如果客户端读取服务器的响应很慢,水管那头(客户端)一直减速,水管这头(服务器)的写入速度是不是也响应的被减缓了?

package main

import (
	"log"
	"net/http"
	"time"

	"github.com/gin-gonic/gin"
	"golang.org/x/sync/errgroup"
)

var (
	g errgroup.Group
)

func route01() http.Handler {
	e := gin.New()
	e.Use(gin.Recovery())
	e.GET("/", func(c *gin.Context) {
		c.JSON(
			http.StatusOK,
			gin.H{
				"code":  http.StatusOK,
				"error": "wellcome server 01",
			},
		)
	})
	return e
}

func router02() http.Handler {
	// 创建一个新的Gin引擎
	e := gin.New()
	// 为这个引擎添加一个中间件,它可以捕获处理请求过程中的任何panic并将错误写入日志
	e.Use(gin.Recovery())
	// 为这个引擎添加一个GET 路由,当收到这个请求时,调用处理函数
	e.GET("/", func(c *gin.Context) {
		// c.JSON 是一个方法,生成JSON格式的HTTP响应
		c.JSON(
			http.StatusOK,
			gin.H{
				"code":  http.StatusOK,
				"error": "wellcome server02",
			},
		)
	})
	return e
}

/*
		go run example_14_runservers.go
		example_14_runservers.go:9:2: no required module provides package golang.org/x/sync/errgroup; to add it:
	    go get golang.org/x/sync/errgroup
		[root@localhost gin_test]# go get golang.org/x/sync/errgroup
*/
func main() {
	server01 := &http.Server{
		Addr:         ":8080",
		// Handler 接收所有的HTTP请求
		Handler:      route01(),	
		// ReadTimeout 读取请求的超时时间		防止慢速攻击(客户端故意以非常慢的速度发送请求,导致服务器资源被长时间占用)	
		ReadTimeout:  5 * time.Second,
		//WriteTimeout 写入响应的超时时间		防止客户端读取响应过慢,导致服务器资源被长时间占用
		WriteTimeout: 10 * time.Second,
	}

	server02 := &http.Server{
		Addr:         ":8081",
		Handler:      router02(),
		ReadTimeout:  5 * time.Second,
		WriteTimeout: 10 * time.Second,
	}
	// 会在新的goroutine中启动服务器
	//server02.ListenAndServe() 是 Go 语言 net/http 包中 Server 结构体的一个方法。
	//这个方法会启动一个 HTTP 服务器,使其开始监听其 Addr 字段指定的网络地址,并等待并处理接收到的 HTTP 请求。

	//当我们说 server02.ListenAndServe() 会阻塞 goroutine,意思是这个方法会一直运行,
	//直到服务器停止。在这个方法运行期间,它所在的 goroutine 不会执行其他代码,也就是说,这个 goroutine 被 "阻塞" 了。
	g.Go(func() error {
		return server01.ListenAndServe()
	})

	g.Go(func() error {
		return server02.ListenAndServe()
	})

	/*
		等待由group启动的所有goroutine结束
		收集gorountine 出现的错误
		调用 g.wait的goroutine会阻塞,等待所有的g.Go启动后的goroutine结束。
		只有所有的g.Go启动的goroutine结束之后,才执行g.wait收集错误
	*/
	if err := g.Wait(); err != nil {
		log.Fatal("the err is ", err)
	}

}
轻量级:goroutine 是非常轻量级的,它的创建和切换的开销都非常小。一个 Go 程序可以同时运行数十万甚至数百万个 goroutine,而在大多数操作系统上,同时运行这么多的线程是不可能的。

内存占用:每个 goroutine 的堆栈大小开始时非常小(只有几 KB),并且可以根据需要增长和缩小,而线程的堆栈大小通常是固定的,通常为几 MB。

调度:goroutine 的调度是由 Go 运行时进行的,而不是由操作系统进行的。这意味着 Go 运行时可以更精细地控制 goroutine 的执行,例如,当一个 goroutine 在等待 I/O 操作时,Go 运行时可以运行其他 goroutine。

并发编程模型:Go 语言提供了 channel 和 select 语句,使得在 goroutine 之间进行通信和同步变得非常简单。这是一种不同于传统的共享内存并发模型的并发编程模型,它更易于理解和使用。

相关推荐

  1. 服务合并为一个服务

    2024-04-07 06:06:04       58 阅读
  2. nginx配置服务

    2024-04-07 06:06:04       189 阅读
  3. nginx 配置服务

    2024-04-07 06:06:04       23 阅读
  4. linux—服务免密登录

    2024-04-07 06:06:04       48 阅读
  5. go | gin服务 | goroutine | ReadTimeout&WriteTimeout

    2024-04-07 06:06:04       38 阅读

最近更新

  1. docker php8.1+nginx base 镜像 dockerfile 配置

    2024-04-07 06:06:04       94 阅读
  2. Could not load dynamic library ‘cudart64_100.dll‘

    2024-04-07 06:06:04       100 阅读
  3. 在Django里面运行非项目文件

    2024-04-07 06:06:04       82 阅读
  4. Python语言-面向对象

    2024-04-07 06:06:04       91 阅读

热门阅读

  1. ffmpeg 从现有视频中截取一段

    2024-04-07 06:06:04       37 阅读
  2. 如何从vue项目界面上看出来node.js版本

    2024-04-07 06:06:04       33 阅读
  3. cycle GAN

    2024-04-07 06:06:04       36 阅读
  4. Pytorch中的nn.Embedding()

    2024-04-07 06:06:04       37 阅读
  5. Redis过期删除策略和内存淘汰机制

    2024-04-07 06:06:04       45 阅读
  6. 前端node使用WebSocket实现实时通信例子

    2024-04-07 06:06:04       33 阅读