Search code examples
javaspring-bootgradleopenapiopenapi-generator

OpenApi 3 codegen java how to implement


Have an openapi yml file with contains a simple get request with response, from this yml have the java files below been generated (among others).

How should these java files be used? How to hook into the generated files?

Could simply copy the generated main and controller class into the main source tree, but does not seem to be the correct way.

--- edit ---

In the generated Controller class, how do I override the default responses that exist in the interface ExampleApi? Without having to modify the generated Controller class and have it in the VCS.

--- edit ---

build.gradle.kts

...
openApiGenerate {
    generatorName.set("spring")

    inputSpec.set("$rootDir/specs/api-example.yml")
    outputDir.set("$buildDir/generated")

    apiPackage.set("com.example.openapi.generated.api")
    invokerPackage.set("com.example.openapi.generated.invoker")
    modelPackage.set("com.example.openapi.generated.model")

    configOptions.set(mapOf(
            "dateLibrary" to "java8"
    ))
    systemProperties.set(mapOf(
            "modelDocs" to "false"
    ))
}
...

What should be done with these classes?

package com.example.openapi.generated.invoker;

import com.fasterxml.jackson.databind.Module;
import org.openapitools.jackson.nullable.JsonNullableModule;
import org.springframework.boot.CommandLineRunner;
import org.springframework.boot.ExitCodeGenerator;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.web.servlet.config.annotation.CorsRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;

@SpringBootApplication
@ComponentScan(basePackages = {"com.example.openapi.generated.invoker", "com.example.openapi.generated.api" , "org.openapitools.configuration"})
public class OpenAPI2SpringBoot implements CommandLineRunner {

    @Override
    public void run(String... arg0) throws Exception {
        if (arg0.length > 0 && arg0[0].equals("exitcode")) {
            throw new ExitException();
        }
    }

    public static void main(String[] args) throws Exception {
        new SpringApplication(OpenAPI2SpringBoot.class).run(args);
    }

    static class ExitException extends RuntimeException implements ExitCodeGenerator {
        private static final long serialVersionUID = 1L;

        @Override
        public int getExitCode() {
            return 10;
        }

    }

    @Bean
    public WebMvcConfigurer webConfigurer() {
        return new WebMvcConfigurer() {
            /*@Override
            public void addCorsMappings(CorsRegistry registry) {
                registry.addMapping("/**")
                        .allowedOrigins("*")
                        .allowedMethods("*")
                        .allowedHeaders("Content-Type");
            }*/
        };
    }

    @Bean
    public Module jsonNullableModule() {
        return new JsonNullableModule();
    }

}

package com.example.openapi.generated.api;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.context.request.NativeWebRequest;
import java.util.Optional;

@Controller
@RequestMapping("${openapi.basic.base-path:}")
public class ExampleApiController implements ExampleApi {

    private final NativeWebRequest request;

    @org.springframework.beans.factory.annotation.Autowired
    public ExampleApiController(NativeWebRequest request) {
        this.request = request;
    }

    @Override
    public Optional<NativeWebRequest> getRequest() {
        return Optional.ofNullable(request);
    }

}


Solution

  • You need to tell gradle to compile the files, there is no need to copy them.

    Add the path with the generated files to the sourceSets of your project. Something like this:

    sourceSets {
        main {
            java {
                srcDir("$buildDir/generated")
            }
        }
    }