-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathdocs.go
More file actions
100 lines (88 loc) · 2.63 KB
/
docs.go
File metadata and controls
100 lines (88 loc) · 2.63 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
package fiberoapi
import (
"html/template"
"strings"
"github.com/gofiber/fiber/v2"
)
// DocConfig contains configuration for the documentation
type DocConfig struct {
Title string
Description string
Version string
DocsPath string // Path where docs will be served, default: "/docs"
JSONPath string // Path where OpenAPI JSON will be served, default: "/openapi.json"
YamlPath string // Path where OpenAPI YAML will be served, default: "/openapi.yaml"
}
// DefaultDocConfig returns default documentation configuration
func DefaultDocConfig() DocConfig {
return DocConfig{
Title: "API Documentation",
Description: "API documentation generated by fiber-oapi",
Version: "1.0.0",
DocsPath: "/docs",
JSONPath: "/openapi.json",
YamlPath: "/openapi.yaml",
}
}
// SetupDocs configures documentation routes for the OApiApp
func (o *OApiApp) SetupDocs(config ...DocConfig) {
cfg := DefaultDocConfig()
if len(config) > 0 {
cfg = config[0]
}
// Serve OpenAPI JSON specification
o.f.Get(cfg.JSONPath, func(c *fiber.Ctx) error {
spec := o.GenerateOpenAPISpec()
// Override info section with config values
if info, ok := spec["info"].(map[string]interface{}); ok {
info["title"] = cfg.Title
info["description"] = cfg.Description
info["version"] = cfg.Version
}
c.Set("Content-Type", "application/json")
return c.JSON(spec)
})
// Serve Redoc documentation
o.f.Get(cfg.DocsPath, func(c *fiber.Ctx) error {
// Generate HTML with embedded Redoc
html := generateRedocHTML(cfg.JSONPath, cfg.Title)
c.Set("Content-Type", "text/html")
return c.SendString(html)
})
// Serve additional docs routes (with trailing slash)
o.f.Get(cfg.DocsPath+"/", func(c *fiber.Ctx) error {
return c.Redirect(cfg.DocsPath)
})
}
// generateRedocHTML generates HTML page with embedded Redoc
func generateRedocHTML(jsonPath, title string) string {
tmpl := `<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8"/>
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>{{.Title}}</title>
<link href="https://fonts.googleapis.com/css?family=Montserrat:300,400,700|Roboto:300,400,700" rel="stylesheet">
<style>
body {
margin: 0;
padding: 0;
}
</style>
</head>
<body>
<redoc spec-url='{{.JSONPath}}'></redoc>
<script src="https://cdn.jsdelivr.net/npm/redoc@2.1.3/bundles/redoc.standalone.js"></script>
</body>
</html>`
t := template.Must(template.New("redoc").Parse(tmpl))
var buf strings.Builder
t.Execute(&buf, struct {
Title string
JSONPath string
}{
Title: title,
JSONPath: jsonPath,
})
return buf.String()
}