86 lines
1.8 KiB
Go
86 lines
1.8 KiB
Go
|
package middleware
|
||
|
|
||
|
import (
|
||
|
"encoding/json"
|
||
|
"fmt"
|
||
|
"go-api/static"
|
||
|
"net/http"
|
||
|
"net/textproto"
|
||
|
"regexp"
|
||
|
"strings"
|
||
|
|
||
|
"github.com/gin-gonic/gin"
|
||
|
)
|
||
|
|
||
|
type SwaggerOptions struct {
|
||
|
Root string
|
||
|
}
|
||
|
|
||
|
var regex = regexp.MustCompile(`(src|href)="./`)
|
||
|
var specRegex = regexp.MustCompile(`url:.+`)
|
||
|
|
||
|
func SwaggerSpecServe() gin.HandlerFunc {
|
||
|
return func(c *gin.Context) {
|
||
|
b, err := static.GetSpec()
|
||
|
if err != nil {
|
||
|
c.String(http.StatusNotFound, "not found")
|
||
|
return
|
||
|
}
|
||
|
|
||
|
var j map[string]interface{}
|
||
|
if err := json.Unmarshal(b, &j); err != nil {
|
||
|
c.String(http.StatusInternalServerError, "internal error")
|
||
|
return
|
||
|
}
|
||
|
|
||
|
if _, ok := j["host"]; ok {
|
||
|
j["host"] = c.Request.Host
|
||
|
}
|
||
|
if xfp := c.Request.Header.Get(textproto.CanonicalMIMEHeaderKey("X-Forwarded-Proto")); xfp != "" && xfp == "https" {
|
||
|
j["schemes"] = []string{xfp}
|
||
|
}
|
||
|
|
||
|
c.JSON(http.StatusOK, j)
|
||
|
}
|
||
|
}
|
||
|
|
||
|
func SwaggerServe(prefix string, opts *SwaggerOptions) gin.HandlerFunc {
|
||
|
return func(c *gin.Context) {
|
||
|
fp := c.Request.URL.Path
|
||
|
|
||
|
if prefix != "" {
|
||
|
if !strings.HasPrefix(fp, prefix) {
|
||
|
c.Next()
|
||
|
return
|
||
|
}
|
||
|
if fp = strings.Replace(fp, prefix, "", 1); fp == "" {
|
||
|
fp = "/"
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// end of slash replace to index.html file
|
||
|
if strings.HasSuffix(fp, "/") {
|
||
|
fp += "index.html"
|
||
|
}
|
||
|
|
||
|
if b, mime, err := static.GetWebFile(fp); err == nil {
|
||
|
// 如果是 index.html 要更新內部的連結 轉換成絕對路徑
|
||
|
if fp == "/index.html" {
|
||
|
replPrefix := prefix
|
||
|
if !strings.HasSuffix(replPrefix, "/") {
|
||
|
replPrefix += "/"
|
||
|
}
|
||
|
|
||
|
b = regex.ReplaceAll(b, []byte(fmt.Sprintf(`$1="%s`, replPrefix)))
|
||
|
b = specRegex.ReplaceAll(b, []byte(fmt.Sprintf(`url: '%s.json',`, prefix)))
|
||
|
}
|
||
|
|
||
|
c.Writer.Header().Set(textproto.CanonicalMIMEHeaderKey("Content-Type"), mime)
|
||
|
c.Status(http.StatusOK)
|
||
|
c.Writer.Write(b)
|
||
|
c.Abort()
|
||
|
}
|
||
|
|
||
|
}
|
||
|
}
|