• 用于gin框架的CORS中间件,解决身份凭证和通配符不能同时设置问题,可同时配置附带身份凭证的请求和*通配符,chrome插件CORS跨域请求通配符


    用于gin框架的CORS中间件(当然,用在其他的框架和语言中相应的Header头设置和配置信息和应用原理都是一样的),解决Access-Control-Allow-Credentials  true身份凭证和 Access-Control-Allow-Origin: | 通配符不能同时设置问题,可同时配置附带身份凭证的请求和*通配符,以及在chrome插件中访问远程CORS跨域请求通配符问题等

    yaml配置信息

    注意修改相关的origin为你自己的, chrome插件的ID获取方式见  http跨域网络请求中的CORS(跨源资源共享) 那些事 -- HTTP跨域请求, chrome插件跨域请求使用详解, origin格式,origin通配符等-CSDN博客

    1. app:
    2. baseUrl: http://localhost:8080
    3. # 安全配置
    4. security:
    5. # api接口允许跨域调用的origin列表 格式 {scheme}://{域名端口或扩展ID} 可以使用通配符 * 或者? , 注意域名最后不带/斜杠
    6. corsAllowOrigins:
    7. - "http://localhost"
    8. - "http://localhost:8080"
    9. - "*.tekin.cn"
    10. - "*.yunnan.ws"
    11. - "chrome-extension://*" # 这个是在chrome扩展里面调用的域 * 表示允许所有的扩展调用, 只允许指定扩展,如: "chrome-extension://iflfjlikpkacloanbaaokocoafabjndg"
    12. corsAllowHeaders: "Content-Type,AccessToken,X-CSRF-Token, Authorization, Token,X-Token,X-User-Id"

    gin CORS中间件实现代码

     注意下面的代码中使用了viper来读取yaml中的配置信息,如果你使用其他配置信息读取方式,只需要修改viper相关的配置信息读取代码即可。

    strutils字符串模式匹配工具库安装: go get -u github.com/tekintian/strutils

    1. package middleware
    2. import (
    3. "net/http"
    4. "github.com/gin-gonic/gin"
    5. "github.com/tekintian/strutils"
    6. "github.com/spf13/viper"
    7. )
    8. // gin CORS middleware 应用于gin框架的CORS中间件
    9. // @author tekintian@gmail.com
    10. func SecurityCORS(c *gin.Context) {
    11. method := c.Request.Method
    12. // 放行所有OPTIONS方法
    13. if method == "OPTIONS" {
    14. c.AbortWithStatus(http.StatusNoContent)
    15. return // 直接退出当前请求
    16. }
    17. // 获取当前请求的origin; 地址形式: scheme://domain 如 "http://localhost:8000" 注意origin的最后是没有 / 斜杠的
    18. origin := c.GetHeader("Origin")
    19. // 如果请求origin在允许的origin之中,则直接将当前请求的origin设置为允许的origin
    20. if isAllowOrigin(origin) {
    21. c.Header("Access-Control-Allow-Origin", origin)
    22. } else {
    23. // 不在允许范围,将配置中的域名作为允许origin设置
    24. c.Header("Access-Control-Allow-Origin", viper.String("app.baseUrl"))
    25. }
    26. // 附带身份凭证的请求, 注意这里如果是true, 则 Access-Control-Allow-Origin 不允许使用 * 通配符
    27. c.Header("Access-Control-Allow-Credentials", "true")
    28. // 设定允许的请求方式
    29. c.Header("Access-Control-Allow-Methods", "POST,GET,OPTIONS,DELETE,PUT,HEAD,PATCH")
    30. // 允许的请求头信息, 默认"Content-Type,X-CSRF-Token,Authorization,Token"
    31. c.Header("Access-Control-Allow-Headers", viper.String("security.corsAllowHeaders"))
    32. // 暴露头信息
    33. c.Header("Access-Control-Expose-Headers", "Content-Length, Access-Control-Allow-Origin, Access-Control-Allow-Headers, Content-Type, New-Token, New-Expires-At")
    34. // 处理请求
    35. c.Next()
    36. }
    37. // 检测当前origin是否是允许的origin
    38. func isAllowOrigin(origin string) bool {
    39. // origin为空时 非跨域请求,直接放行
    40. if origin == "" {
    41. return true
    42. }
    43. corsAllowOrigins := viper.GetStringSlice("security.corsAllowOrigins")
    44. for _, v := range corsAllowOrigins {
    45. if v == origin || strutils.IsWmMatchingReg(origin, v) {
    46. return true
    47. }
    48. }
    49. return false
    50. }

    gin自定义中间件CORS使用示例

    1. func main() {
    2. r := gin.New()
    3. // 使用自定义的CORS中间件
    4. r.Use(middleware.SecurityCORS)
    5. r.GET("/", func(c *gin.Context) {
    6. c.JSON(200, gin.H{
    7. "html": "Hello, world!",
    8. })
    9. })
    10. // 监听并在 0.0.0.0:8080 上启动服务
    11. r.Run(":8080")
    12. }

  • 相关阅读:
    分布式系统——分布式系统知识脑图
    java-net-php-python-54jspm军舰管理系统计算机毕业设计程序
    Java实现一个简单的GitHub仓库信息爬取
    灌区量测水监测系统解决方案 灌区量测水系统解决方案 农业水价综合改革解决方案
    Filebeat+Kafka+ELK
    谷粒商城笔记+踩坑(25)——整合Sentinel实现流控和熔断降级
    算法综合篇专题三:二分法
    uni-app 之 vue位置怎样设置
    C++ 删除C盘中的用户(坑人必备,极度危险)
    AD的PCB开窗+挖槽(Altium Designer)
  • 原文地址:https://blog.csdn.net/tekin_cn/article/details/140988165