运行模式和优雅关闭

Gin 有运行模式,也可以配合标准库实现优雅关闭。

一、运行模式

Gin 常见模式:

模式含义
debug开发模式,会输出更多调试信息
release生产模式,输出更少
test测试模式

设置环境变量:

GIN_MODE=release

也可以在代码里设置:

gin.SetMode(gin.ReleaseMode)

建议:

  • 本地开发用默认 debug。
  • 测试里用 gin.TestMode
  • 生产环境用 release。

二、router.Run 的限制

入门示例常写:

router.Run(":8080")

这很方便,但真实项目通常会用 http.Server,因为它能更好地控制超时和关闭流程。

三、优雅关闭

优雅关闭的意思是:

收到退出信号后,不立刻杀掉进程,而是给正在处理的请求一点时间完成。

示例:

package main

import (
	"context"
	"log"
	"net/http"
	"os/signal"
	"syscall"
	"time"

	"github.com/gin-gonic/gin"
)

func main() {
	router := gin.Default()
	router.GET("/health", func(c *gin.Context) {
		c.JSON(200, gin.H{"status": "ok"})
	})

	server := &http.Server{
		Addr:    ":8080",
		Handler: router,
	}

	ctx, stop := signal.NotifyContext(context.Background(), syscall.SIGINT, syscall.SIGTERM)
	defer stop()

	go func() {
		if err := server.ListenAndServe(); err != nil && err != http.ErrServerClosed {
			log.Fatalf("服务启动失败: %v", err)
		}
	}()

	<-ctx.Done()
	log.Println("收到退出信号,开始关闭服务")

	shutdownCtx, cancel := context.WithTimeout(context.Background(), 5*time.Second)
	defer cancel()

	if err := server.Shutdown(shutdownCtx); err != nil {
		log.Fatalf("服务关闭失败: %v", err)
	}

	log.Println("服务已关闭")
}

四、生产环境还要注意什么

至少关注:

  • 设置 GIN_MODE=release
  • 配置日志输出和日志轮转。
  • 配置反向代理,例如 Nginx。
  • 设置合理的请求超时。
  • 不要把密钥写死在代码里。
  • 如果在代理后面获取真实 IP,要认真配置可信代理。

初学阶段先会写接口,后面再逐步补齐这些工程化能力。