OpenAPITools / openapi-generator

OpenAPI Generator allows generation of API client libraries (SDK generation), server stubs, documentation and configuration automatically given an OpenAPI Spec (v2, v3)
https://openapi-generator.tech
Apache License 2.0
21.9k stars 6.58k forks source link

[REQ] Add a new config for spring controller generation to add @Headers into the API definition #16054

Closed jsimas closed 1 year ago

jsimas commented 1 year ago

Is your feature request related to a problem? Please describe.

When using openapi generator with properties: generatorName = "spring" library = "spring-boot"

The API definition is generated using the following strategy:

CompletableFuture<ResponseEntity<DtoResponse>> methodName( @Parameter(name = "DtoRequest", description = "", required = true) @Valid @RequestBody DtoRequest req);

It would be great to add a possibility to add into the API definition the parameter headers (spring @RequestHeaders):

CompletableFuture<ResponseEntity<DtoResponse>> methodName( @Parameter(name = "DtoRequest", description = "", required = true) @Valid @RequestBody DtoRequest req, @RequestHeader HttpHeaders requestHeaders);

Describe the solution you'd like

Add a new property that should be consumed only if library = "spring-boot" Ex: configOptions = [ useSpringBoot3 : "true", addRequestHeadersToAPI: "true", #Default will be false, same behaviour as today (....) ]

That will add @RequestHeader HttpHeaders requestHeaders into the API definition parameters.

Describe alternatives you've considered

I've updated myself the mustache templates to achieve this - it's working. However this will add technical debt for the future. Every time I want to upgrade openapi generator version I will have to pull the new mustache templates and apply the same tranformation

Additional context

Be able to easily use request HttpHeaders in a controller that is generated or templated by open api generator

dabdirb commented 1 year ago

There's easy workaround that you need not change the mustache template. In controller you can find private final NativeWebRequest request; use example request.getHeader(HttpHeaders.ACCEPT);

jsimas commented 1 year ago

Hi! Let me start to thank you for your answer, however, I don't exactly follow.

Currently I'm using open api generator to generate controller API only, and then my controller implements the generated API. So, there is no NativeWebRequest object available to use.

dabdirb commented 1 year ago

That's really an issue that need enhance. In fact, before i use openapi generator, if i want use a servelet object, i just add a parameter in parameter, let spring autowire it, now i have to use nativerequest. Openapi is just a interface define the client /server data and operations, this issue is related to detail implementation on spring framework. I found there already have a similar parameter named "x-spring-paginated", so i suggest to add a vendor extension field, named as "x-spring-header".

jsimas commented 1 year ago

Hi!

I'm absolutely in agreement with you.

My solution was to change the mustache template and add the imports and add the @RequestHeader HttpHeaders headers to the API method being generated. Like this we implement the interface and let Spring autowire the HttpHeaders.

The issue off course is that I had to change a mustache template of openapi version 6.6.0, and this means whenever we update openapi gradle plugin we will have to look in the mustache template for changes and make the change again and again - not optimal.

I agree with you, it would be great to add a new config property to opt-in/opt-out to add RequestHeaders as paramater into the API generated method.

Pierre491 commented 1 year ago

Hi, I agree with what @jsimas said, I also did the same thing, furthermore these interfaces could also be used in a client (with OpenFeign, MethodInterceptor, or other solutions) and the headers in the method signature would be very convenient.

dabdirb commented 1 year ago

create a PR to fix it https://github.com/OpenAPITools/openapi-generator/pull/16663

EstebanMendez commented 8 months ago

I have been searching around quite a bit to see if there is support for the example below. This issue is the closest I have seen to be what I am looking for, hence commenting on this closed thread. So, my apologies.

Example:

api.yaml

components:
  parameters:
    SOME_PATH_PARAM:
      in: path
      name: somePathParam
      schema:
        type: string
      x-field-extra-annotation:
      - "@MyNiceAnnotation"

SomeGeneratedApiClass.java @Parameter(name = "somePathParam", description = "", required = true, in = ParameterIn.PATH) @PathVariable("somePathParam") @MyNiceAnnotation String somePathParam, After wrapping my head around the mustache template, I am affraid that it isn't supported, and that I would have to provide a PR myself for this feature. But, I wanted to check that maybe (just maybe) you had any idea if it is already supported.

jsimas commented 8 months ago

Not 100% sure, but I don't think that is supported out of the box

jsimas commented 8 months ago

The only thing it was done was to support:

  /api/myapi
    post:
      operationId: doSomething
      x-spring-provide-args: [ '@RequestHeader org.springframework.http.HttpHeaders headers' ]

To be able to generate the proper API declaration: public String doSomething(@RequestHeader org.springframework.http.HttpHeaders headers)