Go语言 转架CORS

quhf5bfb  于 2023-02-01  发布在  Go
关注(0)|答案(9)|浏览(106)

我使用Go gin框架gin

func CORSMiddleware() gin.HandlerFunc {
    return func(c *gin.Context) {
        c.Writer.Header().Set("Content-Type", "application/json")
        c.Writer.Header().Set("Access-Control-Allow-Origin", "*")
        c.Writer.Header().Set("Access-Control-Max-Age", "86400")
        c.Writer.Header().Set("Access-Control-Allow-Methods", "POST, GET, OPTIONS, PUT, DELETE, UPDATE")
        c.Writer.Header().Set("Access-Control-Allow-Headers", "Content-Type, Content-Length, Accept-Encoding, X-CSRF-Token, Authorization, X-Max")
        c.Writer.Header().Set("Access-Control-Allow-Credentials", "true")

        if c.Request.Method == "OPTIONS" {
            c.AbortWithStatus(200)
        } else {
            c.Next()
        }
    }
}

我得到了状态代码:200 OK,但是OPTIONS请求后没有任何React。看起来我错过了什么,但是我不明白我错在哪里。
有人能帮帮我吗?

gjmwrych

gjmwrych1#

FWIW,这是我的CORS中间件,适合我的需要。

func CORSMiddleware() gin.HandlerFunc {
    return func(c *gin.Context) {
        c.Writer.Header().Set("Access-Control-Allow-Origin", "*")
        c.Writer.Header().Set("Access-Control-Allow-Credentials", "true")
        c.Writer.Header().Set("Access-Control-Allow-Headers", "Content-Type, Content-Length, Accept-Encoding, X-CSRF-Token, Authorization, accept, origin, Cache-Control, X-Requested-With")
        c.Writer.Header().Set("Access-Control-Allow-Methods", "POST, OPTIONS, GET, PUT")

        if c.Request.Method == "OPTIONS" {
            c.AbortWithStatus(204)
            return
        }

        c.Next()
    }
}
omvjsjqw

omvjsjqw2#

还有官方的gin中间件用于处理CORS请求github.com/gin-contrib/cors
您可以使用$ go get github.com/gin-contrib/cors安装它,然后将此中间件添加到应用程序中,如下所示:程序包干线

import (
    "time"

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

func main() {
    router := gin.Default()
    // CORS for https://foo.com and https://github.com origins, allowing:
    // - PUT and PATCH methods
    // - Origin header
    // - Credentials share
    // - Preflight requests cached for 12 hours
    router.Use(cors.New(cors.Config{
        AllowOrigins:     []string{"https://foo.com"},
        AllowMethods:     []string{"PUT", "PATCH"},
        AllowHeaders:     []string{"Origin"},
        ExposeHeaders:    []string{"Content-Length"},
        AllowCredentials: true,
        AllowOriginFunc: func(origin string) bool {
            return origin == "https://github.com"
        },
        MaxAge: 12 * time.Hour,
    }))
    router.Run()
}
5f0d552i

5f0d552i3#

func CORSMiddleware() gin.HandlerFunc {
    return func(c *gin.Context) {

        c.Header("Access-Control-Allow-Origin", "*")
        c.Header("Access-Control-Allow-Credentials", "true")
        c.Header("Access-Control-Allow-Headers", "Content-Type, Content-Length, Accept-Encoding, X-CSRF-Token, Authorization, accept, origin, Cache-Control, X-Requested-With")
        c.Header("Access-Control-Allow-Methods", "POST,HEAD,PATCH, OPTIONS, GET, PUT")

        if c.Request.Method == "OPTIONS" {
            c.AbortWithStatus(204)
            return
        }

        c.Next()
    }
}

那就用它

router = gin.New()  
router.Use(CORSMiddleware())
xkrw2x1b

xkrw2x1b4#

我花了大概一个小时的时间来弄明白为什么互联网上的一些例子可以工作,而另一些不行。所以我明白了其中的区别--行的顺序很重要,首先你应该使用config,然后声明你的端点,而不是相反的方式。
作品:

router := gin.Default()
router.Use(cors.Default())
router.GET("/ping", pong)
router.Run(":8082")

不起作用:

router := gin.Default()
router.GET("/ping", pong)
router.Use(cors.Default())
router.Run(":8082")
mccptt67

mccptt675#

有一个包https://github.com/rs/cors,它可以正确地处理CORS请求。它包含了流行路由器的示例,包括gin

package main

import (
    "net/http"

    "github.com/gin-gonic/gin"
    cors "github.com/rs/cors/wrapper/gin"
)

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

    router.Use(cors.Default())
    router.GET("/", func(context *gin.Context) {
        context.JSON(http.StatusOK, gin.H{"hello": "world"})
    })

    router.Run(":8080")
}

一般情况下,只需在gin中间件中添加router.Use(cors.Default())的默认处理即可。

3zwjbxry

3zwjbxry6#

我们创建了一个最小的中间件。

import (
    "github.com/gin-gonic/gin"
    "net/http"
)

type optionsMiddleware struct {

}

func CreateOptionsMiddleware() *optionsMiddleware{
    return &optionsMiddleware{}
}

func (middleware *optionsMiddleware)Response(context *gin.Context){
    if context.Request.Method == "OPTIONS" {
        context.AbortWithStatus(http.StatusNoContent)
    }
}

并注册到gin中间件:

app  := gin.New()
app.Use(middleware.CreateOptionsMiddleware().Response).
    Use(next-middleware)......
vtwuwzda

vtwuwzda7#

这对我很有效-注意:直接设置报头。

func CORSMiddleware() gin.HandlerFunc {
    return func(c *gin.Context) {

        c.Header("Access-Control-Allow-Origin", "*")
        c.Header("Access-Control-Allow-Headers", "*")
        /*
            c.Writer.Header().Set("Access-Control-Allow-Origin", "*")
            c.Writer.Header().Set("Access-Control-Allow-Credentials", "true")
            c.Writer.Header().Set("Access-Control-Allow-Headers", "access-control-allow-origin, access-control-allow-headers")
            c.Writer.Header().Set("Access-Control-Allow-Methods", "GET, HEAD, POST, PUT, DELETE, OPTIONS, PATCH")
        */

        if c.Request.Method == "OPTIONS" {
            c.AbortWithStatus(204)
            return
        }

        c.Next()
    }
}
n7taea2i

n7taea2i8#

使用gin-contrib/cors

import "github.com/gin-contrib/cors"

[...]

router.Use(cors.New(cors.Config{
    AllowOrigins:     []string{"http://localhost:4040"},
    AllowMethods:     []string{"GET"},
    AllowHeaders:     []string{"Content-Type", "Content-Length", "Accept-Encoding", "Authorization", "Cache-Control"},
    ExposeHeaders:    []string{"Content-Length"},
    AllowCredentials: true,
    MaxAge:           12 * time.Hour,
}))

在我的例子中,在此之前我有一个JWT令牌中间件,它阻塞了所有OPTION预处理请求,把CORS中间件放在第一位解决了这个问题。

rhfm7lfc

rhfm7lfc9#

我的前端添加了一个尾随斜线的网址,因为我得到的CORS,做尾随斜线检查。

相关问题