如何在Golang中实现跨域资源共享策略_允许指定域名访问

Go语言实现CORS需精确匹配Origin并显式声明响应头:允许特定域名时设Access-Control-Allow-Origin为该域名;携带凭证时必须禁用通配符、启用AllowCredentials且Origin严格匹配;推荐使用rs/cors库自动处理预检与校验。

在 Go 语言中实现跨域资源共享(CORS),关键是在 HTTP 响应头中正确设置 Access-Control-Allow-Origin 等字段,并只允许你信任的指定域名,而非使用通配符 *(尤其当携带凭证时不可用)。

明确允许特定域名(不带凭证)

如果前端请求不携带 Cookie 或 Authorization 头(即 credentials: false),可直接在响应头中写死目标域名:

  • 检查请求头中的 Origin 是否在白名单内(如 https://example.com
  • 若匹配,设置 Access-Control-Allow-Origin: https://example.com
  • 同时建议设置 Access-Control-Allow-MethodsAccess-Control-Allow-Headers

示例(使用标准 net/http):

func corsMiddleware(next http.Handler) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
origin := r.Header.Get("Origin")
allowedOrigins := []string{"https://example.com", "https://admin.example.org"}

isAllowed := false
for _, o := range allowedOrigins {
if origin == o {
isAllowed = true
break
}
}

if isAllowed {
w.Header().Set("Access-Control-Allow-Origin", origin)
w.Header().Set("Access-Control-Allow-Methods", "GET, POST, PUT, DELETE, OPTIONS")
w.Header().Set("Access-Control-Allow-Headers", "Content-Type, Authorization")
}

if r.Method == "OPTIONS" {
w.WriteHeader(http.StatusOK)
return
}

next.ServeHTTP(w, r)
})
}

支持携带凭证的跨域请求

当前端设置 credentials: true(例如发送 Cookie 或 Bearer Token),Access-Control-Allow-Origin **不能为 ***,且必须精确匹配 Origin。同时需显式开启:

立即学习“go语言免费学习笔记(深入)”;

  • Access-Control-Allow-Credentials: true
  • 确保 Access-Control-Allow-Origin 是单个具体域名(如 https://app.example.com
  • 浏览器会拒绝 Origin: https://app.example.comAllow-Origin: * 的响应

注意:此时无法用通配子域(如 https://*.example.com),需手动比对或使用正则(谨慎验证)。

使用第三方库简化处理(推荐)

rs/cors 库可更安全、灵活地管理策略:

import "github.com/rs/cors"

handler := cors.New(cors.Options{
AllowedOrigins: []string{"https://example.com", "https://dashboard.example.net"},
AllowedMethods: []string{"GET", "POST", "PUT", "DELETE", "OPTIONS"},
AllowedHeaders: []string{"Content-Type", "Authorization"},
ExposedHeaders: []string{"X-Total-Count"},
AllowCredentials: true,
}).Handler(yourMux)

它自动处理预检(OPTIONS)、Origin 校验、Header 注入,避免手写逻辑出错。

常见陷阱与注意事项

  • 不要在生产环境返回 Access-Control-Allow-Origin: * 同时设 AllowCredentials: true —— 这会导致浏览器直接拦截
  • 确保反向代理(如 Nginx)未覆盖或删除你的 CORS 响应头
  • 开发时可用浏览器开发者工具的 Network 面板查看请求/响应头,确认 OriginAllow-Origin 是否一致
  • 若后端部署在子路径(如 /api/v1),CORS 配置与路由无关,只取决于 HTTP 请求头

不复杂但容易忽略细节,核心就是“精确匹配 + 显式声明 + 拒绝默认通配”。