1
8
9
10
11 package openapi
12
13 import (
14 "context"
15 "fmt"
16 "net/http"
17 "strings"
18 )
19
20
21
22
23
24 type contextKey string
25
26 func (c contextKey) String() string {
27 return "auth " + string(c)
28 }
29
30 var (
31
32 ContextOAuth2 = contextKey("token")
33
34
35 ContextBasicAuth = contextKey("basic")
36
37
38 ContextAccessToken = contextKey("accesstoken")
39
40
41 ContextAPIKeys = contextKey("apiKeys")
42
43
44 ContextHttpSignatureAuth = contextKey("httpsignature")
45
46
47 ContextServerIndex = contextKey("serverIndex")
48
49
50 ContextOperationServerIndices = contextKey("serverOperationIndices")
51
52
53 ContextServerVariables = contextKey("serverVariables")
54
55
56 ContextOperationServerVariables = contextKey("serverOperationVariables")
57 )
58
59
60 type BasicAuth struct {
61 UserName string `json:"userName,omitempty"`
62 Password string `json:"password,omitempty"`
63 }
64
65
66 type APIKey struct {
67 Key string
68 Prefix string
69 }
70
71
72 type ServerVariable struct {
73 Description string
74 DefaultValue string
75 EnumValues []string
76 }
77
78
79 type ServerConfiguration struct {
80 URL string
81 Description string
82 Variables map[string]ServerVariable
83 }
84
85
86 type ServerConfigurations []ServerConfiguration
87
88
89 type Configuration struct {
90 Host string `json:"host,omitempty"`
91 Scheme string `json:"scheme,omitempty"`
92 DefaultHeader map[string]string `json:"defaultHeader,omitempty"`
93 UserAgent string `json:"userAgent,omitempty"`
94 Debug bool `json:"debug,omitempty"`
95 Servers ServerConfigurations
96 OperationServers map[string]ServerConfigurations
97 HTTPClient *http.Client
98 }
99
100
101 func NewConfiguration() *Configuration {
102 cfg := &Configuration{
103 DefaultHeader: make(map[string]string),
104 UserAgent: "OpenAPI-Generator/1.0.0/go",
105 Debug: false,
106 Servers: ServerConfigurations{
107 {
108 URL: "http://translator:5092",
109 Description: "No description provided",
110 },
111 },
112 OperationServers: map[string]ServerConfigurations{
113 },
114 }
115 return cfg
116 }
117
118
119 func (c *Configuration) AddDefaultHeader(key string, value string) {
120 c.DefaultHeader[key] = value
121 }
122
123
124 func (sc ServerConfigurations) URL(index int, variables map[string]string) (string, error) {
125 if index < 0 || len(sc) <= index {
126 return "", fmt.Errorf("index %v out of range %v", index, len(sc)-1)
127 }
128 server := sc[index]
129 url := server.URL
130
131
132 for name, variable := range server.Variables {
133 if value, ok := variables[name]; ok {
134 found := bool(len(variable.EnumValues) == 0)
135 for _, enumValue := range variable.EnumValues {
136 if value == enumValue {
137 found = true
138 }
139 }
140 if !found {
141 return "", fmt.Errorf("the variable %s in the server URL has invalid value %v. Must be %v", name, value, variable.EnumValues)
142 }
143 url = strings.Replace(url, "{"+name+"}", value, -1)
144 } else {
145 url = strings.Replace(url, "{"+name+"}", variable.DefaultValue, -1)
146 }
147 }
148 return url, nil
149 }
150
151
152 func (c *Configuration) ServerURL(index int, variables map[string]string) (string, error) {
153 return c.Servers.URL(index, variables)
154 }
155
156 func getServerIndex(ctx context.Context) (int, error) {
157 si := ctx.Value(ContextServerIndex)
158 if si != nil {
159 if index, ok := si.(int); ok {
160 return index, nil
161 }
162 return 0, reportError("Invalid type %T should be int", si)
163 }
164 return 0, nil
165 }
166
167 func getServerOperationIndex(ctx context.Context, endpoint string) (int, error) {
168 osi := ctx.Value(ContextOperationServerIndices)
169 if osi != nil {
170 if operationIndices, ok := osi.(map[string]int); !ok {
171 return 0, reportError("Invalid type %T should be map[string]int", osi)
172 } else {
173 index, ok := operationIndices[endpoint]
174 if ok {
175 return index, nil
176 }
177 }
178 }
179 return getServerIndex(ctx)
180 }
181
182 func getServerVariables(ctx context.Context) (map[string]string, error) {
183 sv := ctx.Value(ContextServerVariables)
184 if sv != nil {
185 if variables, ok := sv.(map[string]string); ok {
186 return variables, nil
187 }
188 return nil, reportError("ctx value of ContextServerVariables has invalid type %T should be map[string]string", sv)
189 }
190 return nil, nil
191 }
192
193 func getServerOperationVariables(ctx context.Context, endpoint string) (map[string]string, error) {
194 osv := ctx.Value(ContextOperationServerVariables)
195 if osv != nil {
196 if operationVariables, ok := osv.(map[string]map[string]string); !ok {
197 return nil, reportError("ctx value of ContextOperationServerVariables has invalid type %T should be map[string]map[string]string", osv)
198 } else {
199 variables, ok := operationVariables[endpoint]
200 if ok {
201 return variables, nil
202 }
203 }
204 }
205 return getServerVariables(ctx)
206 }
207
208
209 func (c *Configuration) ServerURLWithContext(ctx context.Context, endpoint string) (string, error) {
210 sc, ok := c.OperationServers[endpoint]
211 if !ok {
212 sc = c.Servers
213 }
214
215 if ctx == nil {
216 return sc.URL(0, nil)
217 }
218
219 index, err := getServerOperationIndex(ctx, endpoint)
220 if err != nil {
221 return "", err
222 }
223
224 variables, err := getServerOperationVariables(ctx, endpoint)
225 if err != nil {
226 return "", err
227 }
228
229 return sc.URL(index, variables)
230 }
231
View as plain text