OpenAPITools / OpenAPITools/openapi-generator

[BUG] Different behavior in "spring" and "kotlin-spring" generators

Open
#9,065 3 comments 3 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Issue: Bug
Dominant language
Java
Stars
26.8k
Forks
7.7k
PR merge metrics
PR metrics pending

Description

I have YAML for generation:

openapi: 3.0.1
info:
  title: OpenAPI definition
  version: v0
servers:
  - url: http://localhost:8021
    description: Local server url
paths:
  /coverages/policy-type:
    get:
      tags:
        - policy-type
      operationId: findAll
      parameters:
        - name: pageable
          in: query
          required: true
          schema:
            $ref: '#/components/schemas/Pageable'
      responses:
        "200":
          description: OK
          content:
            'application/json':
              schema:
                $ref: '#/components/schemas/PagePolicyTypeDto'

And I have plugin for server-generation with replacement import by org.springframework.data.domain.Pageable:

<plugin>
                <groupId>org.openapitools</groupId>
                <artifactId>openapi-generator-maven-plugin</artifactId>
                <version>5.0.0</version>
                <configuration>
                    <generatorName>kotlin-spring</generatorName>
                    <apiPackage>my</apiPackage>
                    <modelPackage>my.dto</modelPackage>
                    <generateApiTests>false</generateApiTests>
                    <generateModelTests>false</generateModelTests>
                    <configOptions>
                        <gradleBuildFile>false</gradleBuildFile>
                        <useTags>true</useTags>
                        <!--<library>spring-mvc</library>-->
                        <interfaceOnly>true</interfaceOnly>
                    </configOptions>
                </configuration>
                <executions>
                    <execution>
                        <id>policy-type-api-generator</id>
                        <goals>
                            <goal>generate</goal>
                        </goals>
                        <configuration>
                            <inputSpec>${project.basedir}/src/main/resources/api/PolicyTypeApi.yaml</inputSpec>
                            <importMappings>
                                Pageable=org.springframework.data.domain.Pageable,
                                PagePolicyTypeDto=my.dto.PolicyTypePageImpl
                            </importMappings>
                        </configuration>
                    </execution>
                </executions>
            </plugin>

And I have different code result in kotlin-spring generation:

    @GetMapping(
        value = ["/coverages/policy-type"],
        produces = ["application/json"]
    )
    fun findAll(@NotNull @RequestParam(value = "pageable", required = true) pageable: Pageable
    ): ResponseEntity<PolicyTypePageImpl> {
        return ResponseEntity(HttpStatus.NOT_IMPLEMENTED)
    }

spring generation:

    @ApiOperation(value = "", nickname = "findAll", notes = "", response = PolicyTypePageImpl.class, tags={ "policy-type", })
    @ApiResponses(value = { 
        @ApiResponse(code = 200, message = "OK", response = PolicyTypePageImpl.class) })
    @GetMapping(
        value = "/coverages/policy-type",
        produces = { "application/json" }
    )
    default ResponseEntity<PolicyTypePageImpl> findAll(@NotNull @ApiParam(value = "", required = true) @Valid org.springframework.data.domain.Pageable pageable) {
        getRequest().ifPresent(request -> {
            for (MediaType mediaType: MediaType.parseMediaTypes(request.getHeader("Accept"))) {
                if (mediaType.isCompatibleWith(MediaType.valueOf("application/json"))) {
                    String exampleString = "{ \"number\" : 7, \"numberOfElements\" : 1, \"last\" : true, \"size\" : 2, \"totalPages\" : 0, \"pageable\" : { \"size\" : 1, \"page\" : 0, \"sort\" : [ \"sort\", \"sort\" ] }, \"sort\" : { \"unsorted\" : true, \"sorted\" : true, \"empty\" : true }, \"first\" : true, \"content\" : [ { \"id\" : 0, \"title\" : \"title\" }, { \"id\" : 0, \"title\" : \"title\" } ], \"totalElements\" : 6, \"empty\" : true }";
                    ApiUtil.setExampleResponse(request, "application/json", exampleString);
                    break;
                }
            }
        });
        return new ResponseEntity<>(HttpStatus.NOT_IMPLEMENTED);

    }

There is a difference in
@NotNull @ApiParam(value = "", required = true) @Valid org.springframework.data.domain.Pageable pageable
and
@NotNull @RequestParam(value = "pageable", required = true) pageable: Pageable

In kotlin-case expects param with "pageable"-name, BUT it's the just wrapper for params "page", "size" and "sort" that present in org.springframework.data.domain.Pageable
Spring-behavior (without openapi generators) is such as "spring"-generator

And second mini-question: is there any way to use generic org.springframework.data.domain.Page with code-generation? I tried to replace by importMappings but it doesn't support generic types

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Reproduce the Maven configuration with the spring and kotlin-spring generators using the supplied OpenAPI YAML, then compare their generated method signatures and import mappings. Check the generator templates or entry points for Pageable parameter handling and generic Page mappings; done means the Kotlin output treats Pageable consistently and the supported generic mapping behavior is documented or tested.

Written by the indexing model from the issue text.

Assessment

Tech stack
java, kotlin, openapi, spring
Domain
api, backend, tooling
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Quiet
Clarity
Mostly clear
Newbie friendliness
45/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.