Skip to content

Commit 6c24eb6

Browse files
committed
Spring Authorization Server Metadata Endpoint not compatible. fixes #2606
1 parent 497bfae commit 6c24eb6

File tree

4 files changed

+400
-208
lines changed

4 files changed

+400
-208
lines changed

Diff for: springdoc-openapi-starter-common/src/main/java/org/springdoc/core/configuration/SpringDocSecurityOAuth2Customizer.java

+17-2
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,8 @@
44

55
import io.swagger.v3.core.util.AnnotationsUtils;
66
import io.swagger.v3.oas.annotations.enums.ParameterIn;
7+
import io.swagger.v3.oas.annotations.enums.SecuritySchemeType;
8+
import io.swagger.v3.oas.annotations.security.SecurityRequirements;
79
import io.swagger.v3.oas.models.OpenAPI;
810
import io.swagger.v3.oas.models.Operation;
911
import io.swagger.v3.oas.models.PathItem;
@@ -18,9 +20,14 @@
1820
import io.swagger.v3.oas.models.media.StringSchema;
1921
import io.swagger.v3.oas.models.parameters.HeaderParameter;
2022
import io.swagger.v3.oas.models.parameters.Parameter;
23+
import io.swagger.v3.oas.models.parameters.PathParameter;
2124
import io.swagger.v3.oas.models.parameters.RequestBody;
2225
import io.swagger.v3.oas.models.responses.ApiResponse;
2326
import io.swagger.v3.oas.models.responses.ApiResponses;
27+
import io.swagger.v3.oas.models.security.SecurityRequirement;
28+
import io.swagger.v3.oas.models.security.SecurityScheme;
29+
import io.swagger.v3.oas.models.security.SecurityScheme.In;
30+
import io.swagger.v3.oas.models.security.SecurityScheme.Type;
2431
import org.apache.commons.lang3.reflect.FieldUtils;
2532
import org.slf4j.Logger;
2633
import org.slf4j.LoggerFactory;
@@ -182,6 +189,10 @@ private void getOAuth2AuthorizationServerMetadataEndpoint(OpenAPI openAPI, Secur
182189
ReflectionUtils.makeAccessible(field);
183190
String defaultOauth2MetadataUri = (String) ReflectionUtils.getField(field, null);
184191
openAPI.getPaths().addPathItem(defaultOauth2MetadataUri , new PathItem().get(operation));
192+
operation = buildOperation(apiResponses);
193+
operation.addParametersItem(new PathParameter().name("subpath").schema(new StringSchema()));
194+
operation.summary("Valid when multiple issuers are allowed");
195+
openAPI.getPaths().addPathItem(defaultOauth2MetadataUri+"/{subpath}" , new PathItem().get(operation));
185196
}
186197
}
187198
}
@@ -252,7 +263,7 @@ private void getOAuth2TokenEndpoint(OpenAPI openAPI, SecurityFilterChain securit
252263
String mediaType = org.springframework.http.MediaType.APPLICATION_FORM_URLENCODED_VALUE;
253264
RequestBody requestBody = new RequestBody().content(new Content().addMediaType(mediaType, new MediaType().schema(requestSchema)));
254265
operation.setRequestBody(requestBody);
255-
operation.addParametersItem(new HeaderParameter().name("Authorization"));
266+
operation.addParametersItem(new HeaderParameter().name("Authorization").schema(new StringSchema()));
256267

257268
buildPath(oAuth2EndpointFilter, "tokenEndpointMatcher", openAPI, operation, HttpMethod.POST);
258269
}
@@ -310,6 +321,10 @@ private void getOidcProviderConfigurationEndpoint(OpenAPI openAPI, SecurityFilte
310321
ReflectionUtils.makeAccessible(field);
311322
String defaultOidcConfigUri = (String) ReflectionUtils.getField(field, null);
312323
openAPI.getPaths().addPathItem(defaultOidcConfigUri , new PathItem().get(operation));
324+
operation = buildOperation(apiResponses);
325+
operation.addParametersItem(new PathParameter().name("subpath").schema(new StringSchema()));
326+
operation.summary("Valid when multiple issuers are allowed");
327+
openAPI.getPaths().addPathItem("/{subpath}"+defaultOidcConfigUri , new PathItem().get(operation));
313328
}
314329
}
315330
}
@@ -360,7 +375,7 @@ private void getOidcClientRegistrationEndpoint(OpenAPI openAPI, SecurityFilterCh
360375
String mediaType = APPLICATION_JSON_VALUE;
361376
RequestBody requestBody = new RequestBody().content(new Content().addMediaType(mediaType, new MediaType().schema(schema)));
362377
operation.setRequestBody(requestBody);
363-
operation.addParametersItem(new HeaderParameter().name("Authorization"));
378+
operation.addParametersItem(new HeaderParameter().name("Authorization").schema(new StringSchema()));
364379

365380
buildPath(oAuth2EndpointFilter, "clientRegistrationEndpointMatcher", openAPI, operation, HttpMethod.POST);
366381
}

Diff for: springdoc-openapi-tests/springdoc-openapi-security-tests/src/test/resources/results/app10.json

+85-49
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,9 @@
5656
}
5757
}
5858
},
59+
"500": {
60+
"description": "Internal Server Error"
61+
},
5962
"400": {
6063
"description": "Bad Request",
6164
"content": {
@@ -65,18 +68,48 @@
6568
}
6669
}
6770
}
71+
}
72+
}
73+
}
74+
},
75+
"/.well-known/oauth-authorization-server": {
76+
"get": {
77+
"tags": [
78+
"authorization-server-endpoints"
79+
],
80+
"responses": {
81+
"200": {
82+
"description": "OK",
83+
"content": {
84+
"application/json": {
85+
"schema": {
86+
"$ref": "#/components/schemas/OAuth2AuthorizationServerMetadata"
87+
}
88+
}
89+
}
6890
},
6991
"500": {
7092
"description": "Internal Server Error"
7193
}
7294
}
7395
}
7496
},
75-
"/.well-known/oauth-authorization-server": {
97+
"/.well-known/oauth-authorization-server/{subpath}": {
7698
"get": {
7799
"tags": [
78100
"authorization-server-endpoints"
79101
],
102+
"summary": "Valid when multiple issuers are allowed",
103+
"parameters": [
104+
{
105+
"name": "subpath",
106+
"in": "path",
107+
"required": true,
108+
"schema": {
109+
"type": "string"
110+
}
111+
}
112+
],
80113
"responses": {
81114
"200": {
82115
"description": "OK",
@@ -101,8 +134,11 @@
101134
],
102135
"parameters": [
103136
{
137+
"name": "Authorization",
104138
"in": "header",
105-
"name": "Authorization"
139+
"schema": {
140+
"type": "string"
141+
}
106142
}
107143
],
108144
"requestBody": {
@@ -165,6 +201,9 @@
165201
}
166202
}
167203
},
204+
"500": {
205+
"description": "Internal Server Error"
206+
},
168207
"400": {
169208
"description": "Bad Request",
170209
"content": {
@@ -184,9 +223,6 @@
184223
}
185224
}
186225
}
187-
},
188-
"500": {
189-
"description": "Internal Server Error"
190226
}
191227
}
192228
}
@@ -215,15 +251,8 @@
215251
"text/html": {}
216252
}
217253
},
218-
"302": {
219-
"description": "Moved Temporarily",
220-
"headers": {
221-
"Location": {
222-
"schema": {
223-
"type": "string"
224-
}
225-
}
226-
}
254+
"500": {
255+
"description": "Internal Server Error"
227256
},
228257
"400": {
229258
"description": "Bad Request",
@@ -235,8 +264,15 @@
235264
}
236265
}
237266
},
238-
"500": {
239-
"description": "Internal Server Error"
267+
"302": {
268+
"description": "Moved Temporarily",
269+
"headers": {
270+
"Location": {
271+
"schema": {
272+
"type": "string"
273+
}
274+
}
275+
}
240276
}
241277
}
242278
}
@@ -280,6 +316,9 @@
280316
}
281317
}
282318
},
319+
"500": {
320+
"description": "Internal Server Error"
321+
},
283322
"400": {
284323
"description": "Bad Request",
285324
"content": {
@@ -289,9 +328,6 @@
289328
}
290329
}
291330
}
292-
},
293-
"500": {
294-
"description": "Internal Server Error"
295331
}
296332
}
297333
}
@@ -322,6 +358,9 @@
322358
"200": {
323359
"description": "OK"
324360
},
361+
"500": {
362+
"description": "Internal Server Error"
363+
},
325364
"400": {
326365
"description": "Bad Request",
327366
"content": {
@@ -331,9 +370,6 @@
331370
}
332371
}
333372
}
334-
},
335-
"500": {
336-
"description": "Internal Server Error"
337373
}
338374
}
339375
}
@@ -358,9 +394,6 @@
358394
"OAuth2AuthorizationServerMetadata": {
359395
"type": "object",
360396
"properties": {
361-
"issuer": {
362-
"type": "string"
363-
},
364397
"token_endpoint_auth_methods_supported": {
365398
"type": "array",
366399
"items": {
@@ -397,16 +430,19 @@
397430
"type": "string"
398431
}
399432
},
433+
"introspection_endpoint": {
434+
"type": "string"
435+
},
436+
"revocation_endpoint": {
437+
"type": "string"
438+
},
400439
"grant_types_supported": {
401440
"type": "array",
402441
"items": {
403442
"type": "string"
404443
}
405444
},
406-
"revocation_endpoint": {
407-
"type": "string"
408-
},
409-
"introspection_endpoint": {
445+
"issuer": {
410446
"type": "string"
411447
},
412448
"jwks_uri": {
@@ -424,40 +460,35 @@
424460
"type": "integer",
425461
"format": "int64"
426462
},
427-
"access_token": {
463+
"token_type": {
428464
"type": "string"
429465
},
430-
"refresh_token": {
466+
"access_token": {
431467
"type": "string"
432468
},
433-
"token_type": {
469+
"refresh_token": {
434470
"type": "string"
435471
}
436472
}
437473
},
438474
"OAuth2TokenIntrospection": {
439475
"type": "object",
440476
"properties": {
441-
"nbf": {
442-
"type": "integer",
443-
"format": "int64"
444-
},
445477
"scope": {
446478
"type": "string"
447479
},
448480
"jti": {
449481
"type": "string"
450482
},
451-
"client_id": {
452-
"type": "string"
453-
},
454-
"username": {
455-
"type": "string"
483+
"exp": {
484+
"type": "integer",
485+
"format": "int64"
456486
},
457-
"active": {
458-
"type": "boolean"
487+
"nbf": {
488+
"type": "integer",
489+
"format": "int64"
459490
},
460-
"iss": {
491+
"token_type": {
461492
"type": "string"
462493
},
463494
"aud": {
@@ -466,19 +497,24 @@
466497
"type": "string"
467498
}
468499
},
469-
"token_type": {
500+
"client_id": {
470501
"type": "string"
471502
},
472-
"exp": {
473-
"type": "integer",
474-
"format": "int64"
503+
"username": {
504+
"type": "string"
475505
},
476-
"sub": {
506+
"iss": {
477507
"type": "string"
478508
},
509+
"active": {
510+
"type": "boolean"
511+
},
479512
"iat": {
480513
"type": "integer",
481514
"format": "int64"
515+
},
516+
"sub": {
517+
"type": "string"
482518
}
483519
}
484520
}

0 commit comments

Comments
 (0)