package middleware import ( "encoding/json" "github.com/gin-contrib/sessions" "github.com/gin-gonic/gin" "message-pusher/common" "net/http" "net/url" ) type turnstileCheckResponse struct { Success bool `json:"success"` } func TurnstileCheck() gin.HandlerFunc { return func(c *gin.Context) { if common.TurnstileCheckEnabled { session := sessions.Default(c) turnstileChecked := session.Get("turnstile") if turnstileChecked != nil { c.Next() return } response := c.Query("turnstile") if response == "" { c.JSON(http.StatusOK, gin.H{ "success": false, "message": "Turnstile token 为空", }) c.Abort() return } rawRes, err := http.PostForm("https://challenges.cloudflare.com/turnstile/v0/siteverify", url.Values{ "secret": {common.TurnstileSecretKey}, "response": {response}, "remoteip": {c.ClientIP()}, }) if err != nil { common.SysError(err.Error()) c.JSON(http.StatusOK, gin.H{ "success": false, "message": err.Error(), }) c.Abort() return } defer rawRes.Body.Close() var res turnstileCheckResponse err = json.NewDecoder(rawRes.Body).Decode(&res) if err != nil { common.SysError(err.Error()) c.JSON(http.StatusOK, gin.H{ "success": false, "message": err.Error(), }) c.Abort() return } if !res.Success { c.JSON(http.StatusOK, gin.H{ "success": false, "message": "Turnstile 校验失败,请刷新重试!", }) c.Abort() return } session.Set("turnstile", true) err = session.Save() if err != nil { c.JSON(http.StatusOK, gin.H{ "message": "无法保存会话信息,请重试", "success": false, }) return } } c.Next() } }