Demo快速上手

优雅关机

package mainimport ("context""github.com/gin-gonic/gin""log""net/http""os""os/signal""syscall""time"
)// 实现优雅关机和平滑重启
func main() {router := gin.Default()router.GET("/", func(c *gin.Context) {// 这个10秒的延时。是为了演示操作方便,实际上线一定注释掉time.Sleep(time.Second * 10)c.String(http.StatusOK, "hello xiaosheng")})srv := &http.Server{Addr:    ":8080",Handler: router,}// 必须开启一个go routine 因为如果不开起,下面会一直listen and serve,进入死循环// err != http.ErrServerClosed这个很重要go func() {// 开启一个goroutine启动服务if err := srv.ListenAndServe(); err != nil && err != http.ErrServerClosed {log.Fatalf("listen : %s\n", err)}}()// 等待中断信号来优雅关掉服务器, 为关闭服务器做一个5秒的延时quit := make(chan os.Signal, 1)// kill 默认会发送syscall.SIGTREN信号// kill -2发送syscall.SIGINT信号,我们常用的ctrl+c就是触发系统SIGINT信号// kill -9发送syscall.SIGKILL信号,但是不能被捕获,所以不需要添加他// signal.Notify把收到的syscall.SIGINT或syscall.SIGTREN信号传给quitsignal.Notify(quit, syscall.SIGINT, syscall.SIGTERM) // 此处不会阻塞<-quit                                               // 阻塞在此,当收到上述两种信号的时候才会往下执行log.Println("ShutDown Server ...")// 创建一个5秒超时的contextctx, cancel := context.WithTimeout(context.Background(), time.Second*5)defer cancel()// 5秒内优雅关闭服务, (将未处理完的请求处理完再关闭服务), 超过5秒就退出if err := srv.Shutdown(ctx); err != nil {log.Fatal("shut down:", err)}log.Println("Server exiting...")
}

平滑重启

import ("log""net/http""time""github.com/fvbock/endless""github.com/gin-gonic/gin"
)func main() {router := gin.Default()router.GET("/", func(c *gin.Context) {// 这个5秒的延时。是为了演示操作方便,实际上线一定注释掉time.Sleep(5 * time.Second)c.String(http.StatusOK, "hello gin!")})// 默认endless服务器会监听下列信号:// syscall.SIGHUP,syscall.SIGUSR1,syscall.SIGUSR2,syscall.SIGINT,syscall.SIGTERM和syscall.SIGTSTP// 接收到 SIGHUP 信号将触发`fork/restart` 实现优雅重启(kill -1 pid会发送SIGHUP信号)// 接收到 syscall.SIGINT或syscall.SIGTERM 信号将触发优雅关机// 接收到 SIGUSR2 信号将触发HammerTime// SIGUSR1 和 SIGTSTP 被用来触发一些用户自定义的hook函数if err := endless.ListenAndServe(":8080", router); err!=nil{log.Fatalf("listen: %s\n", err)}log.Println("Server exiting...")

Detail

优雅关机

服务端关机命令发出后不立即关机,而是等待当前还在处理的请求全部处理完毕后再退出程序,这样是一种对客户端友好的关机方式。
执行Ctrl+C时,会强制结束进程,这样导致正在访问的请求出现问题。
Go 1.8版本之后, http.Server内置的 Shutdown()方法就支持优雅关机

流程

8080端口开启了一个web服务,并且只注册了一条路由,“/”, 但客户端访问127.0.0.1:8080/时,过10秒才会响应,如果这时我们按下ctrl+c,给程序发送syscall.SIGINT信号,他会等待10秒将当前请求处理完,他才会消亡,当然也取决于创建的5秒的context超时时间。

平滑重启

可以使用fvbock/endless 来替换默认的 ListenAndServe启动服务来实现

import ("log""net/http""time""github.com/fvbock/endless""github.com/gin-gonic/gin"
)func main() {router := gin.Default()router.GET("/", func(c *gin.Context) {// 这个5秒的延时。是为了演示操作方便,实际上线一定注释掉time.Sleep(5 * time.Second)c.String(http.StatusOK, "hello xiaosheng !")})// 默认endless服务器会监听下列信号:// syscall.SIGHUP,syscall.SIGUSR1,syscall.SIGUSR2,syscall.SIGINT,syscall.SIGTERM和syscall.SIGTSTP// 接收到 SIGHUP 信号将触发`fork/restart` 实现优雅重启(kill -1 pid会发送SIGHUP信号)// 接收到 syscall.SIGINT或syscall.SIGTERM 信号将触发优雅关机// 接收到 SIGUSR2 信号将触发HammerTime// SIGUSR1 和 SIGTSTP 被用来触发一些用户自定义的hook函数if err := endless.ListenAndServe(":8080", router); err!=nil{log.Fatalf("listen: %s\n", err)}log.Println("Server exiting...")

流程

  • 在终端执行go build -o graceful_restart编译,并执行./graceful_restart,终端输出当前pid(假设为44444)
  • 将代码中处理请求函数返回的hello xiaosheng!修改为hello world!,再次编译go build -o graceful_restart
  • 打开浏览器访问127.0.0.1:8080/,此时客户端浏览器等待服务端返回响应。
  • 在终端执行kill -1 44444命令给程序发送syscall.SIGHUP重启信号
  • 等第3步客户端浏览器收到响应信息hello xiaosheng!后,再次访问127.0.0.1:8080/会收到hello world!的响应。

这样做在不影响当前未处理完请求的同时完成了程序代码的替换,实现了平滑重启。但实际上用的不多,因为实际都是多台服务器,或者说有类似supervisor的软件管理进程时就不适用这种方式,因为他进程pid变了,他自己重启和supervisor的软件管理进程给他重启就冲突了。

Go项目实现优雅关机与平滑重启相关推荐

  1. Go实现优雅关机与平滑重启

    前言 优雅关机就是服务端关机命令发出后不是立即关机,而是等待当前还在处理的请求全部处理完毕后再退出程序,是一种对客户端友好的关机方式.而执行Ctrl+C关闭服务端时,会强制结束进程导致正在访问的请求出 ...

  2. Golang服务平滑重启

    与重载配置相同的是我们也需要通过信号来通知server重启,但关键在于平滑重启,如果只是简单的重启,只需要kill掉,然后再拉起即可.平滑重启意味着server升级的时候可以不用停止业务. 我们先来看 ...

  3. supervisor 重启_Golang HTTP服务平滑重启及升级

    Golang HTTP服务在上线时,需要重新编译可执行文件,关闭正在运行的进程,然后再启动新的运行进程.对于访问频率比较高的面向终端用户的产品,关闭.重启的过程中会出现无法访问(nginx表现为502 ...

  4. 电脑关闭计算机怎么重启计算机,教您电脑关机后总是重启怎么办

    电脑关机后自动重启的问题,一直困扰一些朋友,通常就是关闭系统后,电脑又自己开机启动了,我们不得不拔掉电源或强制关机,要解决电脑无法关机变重启的问题就要找到原因然后解决,下面,小编讲处理电脑关机后总是重 ...

  5. java jar包 平滑重启,nginx 平滑重启的实现方法

    一.背景 在服务器开发过程中,难免需要重启服务加载新的代码或配置,如果能够保证server重启的过程中服务不间断,那重启对于业务的影响可以降为0.最近调研了一下nginx平滑重启,觉得很有意思,记录下 ...

  6. K8s上的Go服务怎么扩容、发版更新、回滚、平滑重启?教你用Deployment全搞定!

    经过前面不少文章的铺垫,终于可以写这个大家都感兴趣的话题了,在前面两篇文章,我们讲了Kubernetes里的 Pod和 副本集ReplicaSet (RS) 这两个API对象.知道了Pod是Kuber ...

  7. 关机状态下启动微型计算机叫什么,教你电脑关机后自动重启是什么原因

    很多朋友都想要知道电脑关机后自动重启有什么原因,其实电脑关机后自动重启是非常简单,如果大家想要了解的话,小编当然会告诉大家电脑关机后自动重启的原因!下面就给大家带来电脑关机后自动重启原因的介绍吧. 小 ...

  8. xp计算机重启记录,XP电脑关机后自动重启的解决方法

    有些xp系统用户反映在按了关机键后,电脑却莫名其妙地又自动重启了,这是怎么回事?应该怎么办?下面小编为大家介绍一下解决方法. 一.系统失败导致自动重启 1.在桌面上"我的电脑"鼠标 ...

  9. php:php-fpm平滑重启为什么无效

    一.问题 今天修改了fpm一些配置,需要上线重启fpm,但是发现一瞬间出现很多502的错误请求,查看日志发现以下错误 fpm:重启日志 nginx:错误日志 2023/04/23 15:19:00 [ ...

最新文章

  1. Java 如何设计 API 接口,实现统一格式返回?
  2. Zend SDK学习-1
  3. Android性能优化
  4. 计算机网络按信号频带占用方式分为,《计算机网络及组网技术》第2阶段测试题....
  5. LIS(基于贪心的O(NlogN)解法)
  6. 使用泛型实现单例提供者(原创翻译)
  7. [基础]PeopleSoft中的作业和调度作业集合定义
  8. Redis5.0重量级特性Stream尝鲜
  9. 孙鑫-MFC笔记三--绘图
  10. jquery和prototype冲突解决
  11. Neo4j下载安装以及Neo4j浏览器详细说明
  12. 什么是DC-DC转换器?DC-DC转换器是如何命名的?
  13. Oauth2.0 资源服务器搭建
  14. N款在线图片处理工具,让你的效率翻倍
  15. 推荐2个适合程序员使用的显示器
  16. 编译原理:语法制导翻译
  17. 如何找回存储在DBeaver连接中的数据库密码
  18. 论混合软件架构的设计
  19. 王自如评价鸿蒙OS,王自如发表致歉声明 测评将加利益相关说明
  20. python学习笔记(推荐有其他语言编程经验想学python的人看)

热门文章

  1. Java开发的模拟双色球抽奖程序 功能非常齐全 完整源码
  2. 应用Abaqus有限元软件中的cohesive单元模拟压头侵入地层随机断裂过程
  3. MATLAB 遭禁,CAD 也危险,国产工业软件如何突围?
  4. 1253:抓住那头牛(数轴上的问题)
  5. nodejs+vue+elementui二手车评估信息网站系统java python
  6. 【个人笔记】OpenCV4 C++ 快速入门 28课
  7. 【Linux】CPU频率控制|Conflicting CPU frequency values detected
  8. 【LTE】为什么使用SNR来表征信道质量,而并不用RSRQ?这两者的区别是什么?
  9. Kotlin小知识之高阶函数
  10. 玩转树莓派之环境搭建—安装TFT屏