golang,go,博客,开源,编程

开发gin中间件

Published on with 0 views and 0 comments

在 Gin 框架中,中间件是处理请求和响应的函数,可以在请求进入路由处理函数之前或响应返回客户端之前执行。中间件广泛用于执行公共任务,例如身份验证、日志记录、错误处理、请求限流等。

开发 Gin 中间件的步骤

开发一个 Gin 中间件的基本步骤如下:

  1. 创建中间件函数: 中间件是一个接收 *gin.Context 作为参数的函数。你可以在中间件中进行一些操作,然后调用 c.Next() 将控制权交给下一个中间件或路由处理函数。
  2. 使用中间件: 可以在全局范围使用中间件,或者只在特定的路由或路由组上使用。

中间件的基本结构

Gin 中间件函数的结构如下:

func MyMiddleware() gin.HandlerFunc {
    return func(c *gin.Context) {
        // 执行中间件的操作,比如日志记录、权限验证等

        // 调用 c.Next() 将请求传递给后续的中间件/处理函数
        c.Next()

        // 在请求完成后,进行响应后的操作,比如记录响应时间等
    }
}

示例:开发自定义中间件

下面我们通过开发几个简单的中间件示例,帮助你理解如何使用和编写 Gin 中间件。

1. 日志记录中间件

这个中间件记录每个请求的基本信息,例如请求方法、请求路径和请求时间。

package main

import (
    "fmt"
    "github.com/gin-gonic/gin"
    "time"
)

func Logger() gin.HandlerFunc {
    return func(c *gin.Context) {
        // 记录请求开始时间
        start := time.Now()

        // 继续处理请求
        c.Next()

        // 请求完成后,记录日志
        duration := time.Since(start)
        fmt.Printf("Request %s %s took %v\n", c.Request.Method, c.Request.URL.Path, duration)
    }
}

func main() {
    r := gin.Default()

    // 使用日志记录中间件
    r.Use(Logger())

    r.GET("/hello", func(c *gin.Context) {
        c.JSON(200, gin.H{"message": "Hello, World!"})
    })

    r.Run(":8080")
}

在这个示例中,每次访问 /hello 路径时,都会输出类似下面的日志:

Request GET /hello took 1.223ms

2. 身份验证中间件

在这个示例中,我们开发一个简单的身份验证中间件,检查请求头中是否有有效的 Token。如果没有,则返回 401 错误。

func AuthMiddleware() gin.HandlerFunc {
    return func(c *gin.Context) {
        token := c.GetHeader("Authorization")

        // 假设 Token 是 "Bearer mytoken123"
        if token != "Bearer mytoken123" {
            c.JSON(401, gin.H{"error": "Unauthorized"})
            c.Abort() // 阻止后续的处理
            return
        }

        // 如果 Token 验证成功,继续处理请求
        c.Next()
    }
}

func main() {
    r := gin.Default()

    // 仅对 /secure 路由启用身份验证中间件
    r.GET("/secure", AuthMiddleware(), func(c *gin.Context) {
        c.JSON(200, gin.H{"message": "You have access to the secure route"})
    })

    r.GET("/public", func(c *gin.Context) {
        c.JSON(200, gin.H{"message": "This is a public route"})
    })

    r.Run(":8080")
}

访问 /secure 时,需要提供有效的 Authorization 头,否则会返回 401 错误。而 /public 路由不需要身份验证。

3. CORS 中间件

CORS(跨域资源共享)中间件用于允许跨域请求。这里是一个自定义的 CORS 中间件的示例:

func CORSMiddleware() gin.HandlerFunc {
    return func(c *gin.Context) {
        // 设置 CORS 头,允许跨域请求
        c.Header("Access-Control-Allow-Origin", "*")
        c.Header("Access-Control-Allow-Methods", "GET, POST, PUT, DELETE, OPTIONS")
        c.Header("Access-Control-Allow-Headers", "Content-Type, Authorization")

        // 如果是 OPTIONS 请求,则直接返回 200 响应
        if c.Request.Method == "OPTIONS" {
            c.AbortWithStatus(200)
            return
        }

        // 继续处理请求
        c.Next()
    }
}

func main() {
    r := gin.Default()

    // 使用 CORS 中间件
    r.Use(CORSMiddleware())

    r.GET("/hello", func(c *gin.Context) {
        c.JSON(200, gin.H{"message": "Hello, World!"})
    })

    r.Run(":8080")
}

此中间件允许所有来源的请求,可以自定义 Access-Control-Allow-Origin 等头部,控制哪些源可以访问你的资源。


中间件的使用

中间件可以全局使用,也可以针对某些路由或路由组使用:

1. 全局使用中间件

将中间件应用于所有路由:

r := gin.Default()
r.Use(Logger()) // 将 Logger 中间件应用于所有路由

r.GET("/hello", func(c *gin.Context) {
    c.JSON(200, gin.H{"message": "Hello, World!"})
})

r.Run(":8080")

2. 路由级别使用中间件

将中间件仅应用于某些路由:

r := gin.Default()

// 只有 /secure 路由使用 AuthMiddleware 中间件
r.GET("/secure", AuthMiddleware(), func(c *gin.Context) {
    c.JSON(200, gin.H{"message": "Secure route"})
})

// /public 路由不使用任何中间件
r.GET("/public", func(c *gin.Context) {
    c.JSON(200, gin.H{"message": "Public route"})
})

r.Run(":8080")

3. 路由组使用中间件

可以为一组路由应用同一个中间件:

r := gin.Default()

// 创建一个路由组
authorized := r.Group("/admin")
authorized.Use(AuthMiddleware()) // 应用 AuthMiddleware 到这个路由组
{
    authorized.GET("/dashboard", func(c *gin.Context) {
        c.JSON(200, gin.H{"message": "Welcome to the admin dashboard"})
    })
}

r.Run(":8080")

总结

  1. 中间件的结构:每个中间件都是一个返回 gin.HandlerFunc 的函数,gin.HandlerFunc 类型的函数接受一个 *gin.Context 参数,表示请求的上下文。
  2. 中间件的作用:可以用于请求处理前或响应处理后的操作,如日志记录、身份验证、请求限流、跨域请求处理等。
  3. 使用中间件:可以通过 r.Use() 全局使用,或通过路由级别或路由组级别使用。

通过自定义和组合不同的中间件,你可以很容易地扩展和定制你的 Gin 应用的功能。


标题:开发gin中间件
作者:mooncakeee
地址:http://blog.dd95828.com/articles/2025/01/06/1736152457948.html
联系:scotttu@163.com