From 498deb2d90401ad431288d2e2650e953b3ab4974 Mon Sep 17 00:00:00 2001 From: alvaro garcia fernandez Date: Thu, 4 Nov 2021 21:25:29 +0100 Subject: [PATCH] fix: oauth2-redirect outside of the base swagger path (#177) --- README.md | 32 +++++++++++++++++++++++--------- example/basic/main.go | 2 +- example/gzipped/main.go | 2 +- swagger.go | 32 ++++++++++++++++++++++++++++---- swagger_test.go | 9 +++++---- 5 files changed, 58 insertions(+), 19 deletions(-) diff --git a/README.md b/README.md index 6d81cda..b6e6221 100644 --- a/README.md +++ b/README.md @@ -8,12 +8,13 @@ gin middleware to automatically generate RESTFUL API documentation with Swagger [![GoDoc](https://godoc.org/github.com/swaggo/gin-swagger?status.svg)](https://godoc.org/github.com/swaggo/gin-swagger) [![Release](https://img.shields.io/github/release/swaggo/gin-swagger.svg?style=flat-square)](https://github.com/swaggo/gin-swagger/releases) - ## Usage ### Start using it + 1. Add comments to your API source code, [See Declarative Comments Format](https://swaggo.github.io/swaggo.io/declarative_comments_format/). 2. Download [Swag](https://github.com/swaggo/swag) for Go by using: + ```sh go get -u github.com/swaggo/swag/cmd/swag ``` @@ -21,14 +22,18 @@ go get -u github.com/swaggo/swag/cmd/swag 3. Run the [Swag](https://github.com/swaggo/swag) at your Go project root path(for instance `~/root/go-peoject-name`), [Swag](https://github.com/swaggo/swag) will parse comments and generate required files(`docs` folder and `docs/doc.go`) at `~/root/go-peoject-name/docs`. + ```sh swag init ``` + 4. Download [gin-swagger](https://github.com/swaggo/gin-swagger) by using: + ```sh go get -u github.com/swaggo/gin-swagger go get -u github.com/swaggo/files ``` + Import following in your code: ```go @@ -38,17 +43,21 @@ import "github.com/swaggo/files" // swagger embed files ``` ### Canonical example: + Now assume you have implemented a simple api as following: + ```go -// A get function which returns a hello world string by json +// A get function which returns a hello world string by json func Helloworld(g *gin.Context) { g.JSON(http.StatusOK,"helloworld") } ``` + So how to use gin-swagger on api above? Just follow the following guide. 1. Add Comments for apis and main function with gin-swagger rules like following: + ```go // @BasePath /api/v1 @@ -69,14 +78,17 @@ func Helloworld(g *gin.Context) { 2. Use `swag init` command to generate a docs, docs generated will be stored at 3. import the docs like this: I assume your project named `github.com/go-project-name/docs`. + ```go import ( docs "github.com/go-project-name/docs" ) ``` + 4. build your application and after that, go to http://localhost:8080/swagger/index.html ,you to see your Swagger UI. 5. The full code and folder relatives here: + ```go package main @@ -117,7 +129,9 @@ func main() { } ``` + Demo project tree, `swag init` is run at relative `.` + ``` . ├── docs @@ -137,17 +151,17 @@ You can configure Swagger using different configuration options func main() { r := gin.New() - ginSwagger.WrapHandler(swaggerFiles.Handler, - ginSwagger.URL("http://localhost:8080/swagger/doc.json"), + ginSwagger.WrapHandler(swaggerFiles.Handler, + ginSwagger.URL("http://localhost:8080/swagger/doc.json"), ginSwagger.DefaultModelsExpandDepth(-1)) r.Run() } ``` -| Option | Type | Default | Description | -|--------------------------|--------|------------|---------------------------------------------------------------------------| -| URL | string | "doc.json" | URL pointing to API definition | +| Option | Type | Default | Description | +| ------------------------ | ------ | ---------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | +| URL | string | "doc.json" | URL pointing to API definition | | DocExpantion | string | "list" | Controls the default expansion setting for the operations and tags. It can be 'list' (expands only the tags), 'full' (expands the tags and operations) or 'none' (expands nothing). | -| DeepLinking | bool | true | If set to true, enables deep linking for tags and operations. See the Deep Linking documentation for more information.| -| DefaultModelsExpandDepth | int | 1 | Default expansion depth for models (set to -1 completely hide the models) | +| DeepLinking | bool | true | If set to true, enables deep linking for tags and operations. See the Deep Linking documentation for more information. | +| DefaultModelsExpandDepth | int | 1 | Default expansion depth for models (set to -1 completely hide the models) | diff --git a/example/basic/main.go b/example/basic/main.go index 4b2f659..a3e6604 100644 --- a/example/basic/main.go +++ b/example/basic/main.go @@ -2,7 +2,7 @@ package main import ( "github.com/gin-gonic/gin" - "github.com/swaggo/files" + swaggerFiles "github.com/swaggo/files" "github.com/swaggo/gin-swagger" "github.com/swaggo/gin-swagger/example/basic/api" diff --git a/example/gzipped/main.go b/example/gzipped/main.go index fd3f7e7..8eeb264 100644 --- a/example/gzipped/main.go +++ b/example/gzipped/main.go @@ -3,7 +3,7 @@ package main import ( "github.com/gin-contrib/gzip" "github.com/gin-gonic/gin" - "github.com/swaggo/files" + swaggerFiles "github.com/swaggo/files" "github.com/swaggo/gin-swagger" _ "github.com/swaggo/gin-swagger/example/basic/docs" diff --git a/swagger.go b/swagger.go index b34d2f3..6748d30 100644 --- a/swagger.go +++ b/swagger.go @@ -14,6 +14,14 @@ import ( "github.com/swaggo/swag" ) +type swaggerConfig struct { + URL string + DeepLinking bool + DocExpansion string + DefaultModelsExpandDepth int + Oauth2RedirectURL template.JS +} + // Config stores ginSwagger configuration variables. type Config struct { //The url pointing to API definition (normally swagger.json or swagger.yaml). Default is `doc.json`. @@ -23,6 +31,21 @@ type Config struct { DefaultModelsExpandDepth int } +// Convert the config to a swagger one in order to fill unexposed template values. +func (c Config) ToSwaggerConfig() swaggerConfig { + return swaggerConfig{ + URL: c.URL, + DeepLinking: c.DeepLinking, + DocExpansion: c.DocExpansion, + DefaultModelsExpandDepth: c.DefaultModelsExpandDepth, + Oauth2RedirectURL: template.JS( + "`${window.location.protocol}//${window.location.host}$" + + "{window.location.pathname.split('/').slice(0, window.location.pathname.split('/').length - 1).join('/')}" + + "/oauth2-redirect.html`", + ), + } +} + // URL presents the url pointing to API definition (normally swagger.json or swagger.yaml). func URL(url string) func(c *Config) { return func(c *Config) { @@ -82,7 +105,7 @@ func CustomWrapHandler(config *Config, handler *webdav.Handler) gin.HandlerFunc matches := rexp.FindStringSubmatch(c.Request.RequestURI) if len(matches) != 3 { - c.Status(404) + c.Status(http.StatusNotFound) _, _ = c.Writer.Write([]byte("404 page not found")) return } @@ -107,7 +130,7 @@ func CustomWrapHandler(config *Config, handler *webdav.Handler) gin.HandlerFunc switch path { case "index.html": - _ = index.Execute(c.Writer, config) + _ = index.Execute(c.Writer, config.ToSwaggerConfig()) case "doc.json": doc, err := swag.ReadDoc() if err != nil { @@ -130,7 +153,7 @@ func DisablingWrapHandler(h *webdav.Handler, envName string) gin.HandlerFunc { return func(c *gin.Context) { // Simulate behavior when route unspecified and // return 404 HTTP code - c.String(404, "") + c.String(http.StatusNotFound, "") } } @@ -145,7 +168,7 @@ func DisablingCustomWrapHandler(config *Config, h *webdav.Handler, envName strin return func(c *gin.Context) { // Simulate behavior when route unspecified and // return 404 HTTP code - c.String(404, "") + c.String(http.StatusNotFound, "") } } @@ -230,6 +253,7 @@ window.onload = function() { url: "{{.URL}}", dom_id: '#swagger-ui', validatorUrl: null, + oauth2RedirectUrl: {{.Oauth2RedirectURL}}, presets: [ SwaggerUIBundle.presets.apis, SwaggerUIStandalonePreset diff --git a/swagger_test.go b/swagger_test.go index 3b8c54f..a288256 100644 --- a/swagger_test.go +++ b/swagger_test.go @@ -62,6 +62,7 @@ func TestWrapCustomHandler(t *testing.T) { w6 := performRequest("GET", "/notfound", router) assert.Equal(t, 404, w6.Code) + } func TestDisablingWrapHandler(t *testing.T) { @@ -94,11 +95,11 @@ func TestDisablingWrapHandler(t *testing.T) { w22 := performRequest("GET", "/disabling/doc.json", router) assert.Equal(t, 404, w22.Code) - w33 := performRequest("GET", "/disabling/favicon-16x16.png", router) - assert.Equal(t, 404, w33.Code) - - w44 := performRequest("GET", "/disabling/notfound", router) + w44 := performRequest("GET", "/disabling/oauth2-redirect.html", router) assert.Equal(t, 404, w44.Code) + + w55 := performRequest("GET", "/disabling/notfound", router) + assert.Equal(t, 404, w55.Code) } func TestDisablingCustomWrapHandler(t *testing.T) {