# server spring

Source: https://apigenie.pl/techdocs/reference/cli-generate_server_spring

Generate a Spring Boot server, or Spring Cloud / HTTP interface clients, in Java.

From an AsyncAPI document, the command generates a Spring Boot Kafka application instead; see
[apigenie-generator server spring (AsyncAPI)](/techdocs/reference/cli-generate_server_spring_asyncapi).

## Usage

```sh
apigenie-generator server spring [...OPTIONS] INPUT_FILE
```

## Description

The generator produces the same code as the `spring` generator of
[openapi-generator](https://openapi-generator.tech), and accepts the same options. A project
generated by openapi-generator can be regenerated by API Genie, and vice versa.

It supports three libraries:

- `spring-boot` (default): a Spring Boot application, with API interfaces (`PetApi`), controllers
  implementing them (`PetApiController`), optional delegates (`PetApiDelegate`), models,
  SpringDoc configuration and a Maven `pom.xml`
- `spring-cloud`: Feign clients (`PetApiClient`) and their security configuration
- `spring-http-interface`: `@HttpExchange` interfaces and a configurator creating their proxies

The `spring-cloud` and `spring-http-interface` clients are generated by the writers of
[`apigenie-generator client java`](/techdocs/reference/cli-generate_client_java) (its `feign` and
`http-interface` libraries), which also generates standalone clients on Spring's `RestClient` and
`RestTemplate`.

The generated project contains:

- `pom.xml` and `README.md`
- the application class, `RFC3339DateFormat`, `application.properties` and a copy of the OpenAPI
  document in `src/main/resources/openapi.yaml` (servers)
- API interfaces, grouped by the first segment of their paths or, with `useTags`, by tags
- models: classes with fluent setters, `equals`, `hashCode` and `toString`, enums, interfaces for
  `oneOf` schemas, and class hierarchies for `allOf` schemas with discriminators
- `.openapi-generator/FILES` (the list of generated files) and `.openapi-generator/VERSION`

Controllers (`*ApiController.java`) are generated only if they don't exist, so they can be
implemented. Files listed in `.openapi-generator-ignore` (which uses the syntax of `.gitignore`)
are not written.

The vendor extensions the generator reads are listed in "Extensions".

Differences from openapi-generator:

- `useSpringBoot3` is `true` by default
- generated files are marked with `@Generated(value = "API Genie")`
- unknown options are errors, not ignored
- the input must be an OpenAPI 3.0, 3.1 or 3.2 document; convert Swagger 2.0 documents with
  `apigenie convert`, and bundle documents referencing other files with `apigenie bundle`
- schemas whose names give the same class name (e.g. `app-permissions` and an inline
  `app_permissions`) get classes with numeric suffixes, e.g. `AppPermissions1`

Not supported: QUERY and other methods besides the eight classic ones (`additionalOperations`),
which are left out; callbacks and webhooks (only their payload models are generated); parameter
styles (`deepObject`, `spaceDelimited`, `pipeDelimited`) and parameters described with `content`;
request media types after the first one; streaming responses (`text/event-stream`, JSON Lines),
which are generated as a single list; strings with a `contentMediaType` as files or binary bodies
(only `format: binary` is); `prefixItems`, `patternProperties`, conditional schemas and
`multipleOf`; the flows of OAuth 2 schemes and mutual TLS in the SpringDoc configuration.

## Extensions

| Extension | Effect |
| --------- | ------ |
| `x-class-extra-annotation` | annotations of the class of a schema, e.g. `['@Entity']` |
| `x-implements` | interfaces the class of a schema implements |
| `x-field-extra-annotation` | annotations of the field of a property, or of the method parameter of a parameter |
| `x-extra-annotation` | annotations of the getter of a property |
| `x-setter-extra-annotation` | annotations of the setter of a property |
| `x-pattern-message`, `x-size-message`, `x-minimum-message`, `x-maximum-message` | `message` of the `@Pattern`, `@Size`, `@Min`/`@DecimalMin` and `@Max`/`@DecimalMax` annotations of a property |
| `x-jackson-json-include-policy` | `@JsonInclude` policy of a property, e.g. `non_empty` (`none` for no annotation) |
| `x-jackson-json-setter-nulls` | `@JsonSetter(nulls = ...)` of a property, e.g. `skip` (`none` for no annotation) |
| `x-enum-varnames` | names of the constants of an enum |
| `x-enum-descriptions` | Javadoc of the constants of an enum |
| `x-parent` | `true` makes a schema the superclass of the schemas extending it with `allOf`, without a discriminator |
| `x-discriminator-value` | the discriminator value of a subclass in `@JsonSubTypes` (default: the name of its schema) |
| `x-jackson-default-impl` | `defaultImpl` of the `@JsonTypeInfo` of a class with a discriminator |
| `x-defaultMapping` | `defaultMapping` of a discriminator in OpenAPI 3.0 and 3.1 documents: the `defaultImpl` of `@JsonTypeInfo`, without `x-jackson-default-impl` |
| `x-codegen-request-body-name` | on an operation or its request body: the name of the body parameter |
| `x-apigenie.codegen.controller-name` | on an operation: the API class of the operation, instead of its tag or path |
| `x-apigenie.codegen.action-name` | name of the method of an operation, instead of its `operationId` |
| `x-apigenie.codegen.disabled` | `true` on an operation or its path item leaves the operation out, with `skipDisabled` |
| `x-internal` | `true` on an operation leaves it out |
| `x-operation-extra-annotation` | annotations of the method of an operation (not with `spring-http-interface`) |
| `x-version-param` | `true` on a header or query parameter adds it to the `headers` or `params` of the `@RequestMapping` (not with `spring-http-interface`) |
| `x-spring-paginated` | `true` replaces the `page`, `size` and `sort` parameters of an operation with a `Pageable`; `false` keeps them even with `autoXSpringPaginated` |
| `x-spring-provide-args` | further arguments of the method of an operation, e.g. `['@RequestAttribute("tenant") String tenant']` (not with `spring-http-interface`) |

The extensions can live in an overlay for this target instead of in the document, e.g.
`spring.overlay.yaml`:

```yaml
overlay: 1.0.0
info:
  title: Spring annotations
  version: 1.0.0
actions:
  - target: $.paths['/pets'].get
    update:
      x-spring-paginated: true
  - target: $.components.schemas.Pet
    update:
      x-class-extra-annotation: ['@com.acme.Audited']
```

```sh
apigenie-generator server spring openapi.yaml --overlay spring.overlay.yaml -o out
```

## Options

### -c, --config

Path to the configuration file to use. See the "Configuration" section for more information.

### --overlay OVERLAY

Path to an OpenAPI Overlay (1.0 to 1.2) applied to the input before generating, e.g. one setting the
extensions of the "Extensions" section. Can be repeated: the overlays apply in order, after those
listed under `commands.generate.server_spring.overlay` in the configuration file (with paths
relative to it). Warnings and errors about a value an overlay set point to the overlay.

### --strict

Makes an overlay action whose target selects nothing an error (exit status 2, nothing is generated)
instead of a warning (`OVERLAY:LINE:COL: action #N (TARGET) selects no nodes.`).

### -o, --output

Directory where the project is generated.

### --package-name

Base package of the generated code, e.g. `com.example`. API, model and configuration classes are
generated in its `api`, `model` and `configuration` sub-packages, unless `apiPackage`,
`modelPackage` or `configPackage` are set.

### --package-version

Version of the generated project (`artifactVersion`). Defaults to the version of the API.

### -p, --property NAME=VALUE

Sets a generator option (see below), e.g. `-p delegatePattern=true`. Options given on the command
line take precedence over the configuration file. Mapping options take comma-separated lists,
e.g. `-p typeMappings=DateTime=java.time.Instant,UUID=String`. Applies to OpenAPI documents only;
using it with an AsyncAPI document is an error.

## Configuration

Options can also be set in the configuration file, either directly or in an
`additionalProperties` section, like in configuration files of openapi-generator. The `asyncapi`
key holds the options of the generation from AsyncAPI documents (see
[apigenie-generator server spring (AsyncAPI)](/techdocs/reference/cli-generate_server_spring_asyncapi#configuration)):

```yaml
version: '1.0'
commands:
  generate:
    server_spring:
      basePackage: com.example
      delegatePattern: true
      typeMappings:
        DateTime: java.time.Instant
```

| Option | Description |
| ------ | ----------- |
| `library` | Library template: spring-boot (server), spring-cloud (Feign client) or spring-http-interface (HTTP interface client) |
| `basePackage` | Base package for generated code |
| `invokerPackage` | Alias of basePackage |
| `apiPackage` | Package for generated API classes |
| `modelPackage` | Package for generated models |
| `configPackage` | Package for generated configuration classes |
| `groupId` | groupId in the generated pom.xml |
| `artifactId` | artifactId in the generated pom.xml |
| `artifactVersion` | Artifact version in the generated pom.xml |
| `artifactDescription` | Artifact description in the generated pom.xml |
| `artifactUrl` | Artifact URL in the generated pom.xml |
| `licenseName` | License name in the generated pom.xml |
| `licenseUrl` | License URL in the generated pom.xml |
| `developerName` | Developer name in the generated pom.xml |
| `developerEmail` | Developer email in the generated pom.xml |
| `developerOrganization` | Developer organization in the generated pom.xml |
| `developerOrganizationUrl` | Developer organization URL in the generated pom.xml |
| `scmConnection` | SCM connection in the generated pom.xml |
| `scmDeveloperConnection` | SCM developer connection in the generated pom.xml |
| `scmUrl` | SCM URL in the generated pom.xml |
| `parentGroupId` | groupId of the parent pom |
| `parentArtifactId` | artifactId of the parent pom |
| `parentVersion` | Version of the parent pom |
| `snapshotVersion` | Append -SNAPSHOT to the artifact version |
| `title` | Server title, used in property names (defaults to info.title) |
| `serverPort` | Server port (defaults to the port of the first server, or 8080) |
| `useSpringBoot3` | Generate code for Spring Boot 3 (jakarta); false means Spring Boot 2 |
| `useSpringBoot4` | Generate code for Spring Boot 4 |
| `useJackson3` | Use Jackson 3 (tools.jackson) instead of Jackson 2; requires useSpringBoot4 |
| `optionalAcceptNullable` | Use Optional.ofNullable in fluent setters of Optional properties |
| `useJspecify` | Use JSpecify (org.jspecify.annotations.Nullable) for null checks |
| `hideGenerationTimestamp` | Omit the generation date from @Generated annotations |
| `generationTimestamp` | Timestamp used in @Generated annotations |
| `generatorVersion` | Generator version written into generated files |
| `dateLibrary` | Date library: java8, java8-localdatetime, joda or legacy |
| `documentationProvider` | springdoc, source or none |
| `annotationLibrary` | swagger2 or none |
| `useSwaggerUI` | Serve Swagger UI |
| `interfaceOnly` | Generate only API interfaces, without controllers |
| `delegatePattern` | Delegate request handling to XxxApiDelegate interfaces |
| `skipDefaultInterface` | Don't generate default implementations of API methods |
| `useTags` | Group operations by tag instead of the first path segment |
| `requestMappingMode` | Where to put the class-level @RequestMapping: controller, api_interface or none |
| `useResponseEntity` | Wrap return types in ResponseEntity |
| `useOptional` | Use Optional for optional parameters |
| `useSpringController` | Annotate API interfaces with @Controller / @RestController |
| `returnSuccessCode` | Return the success code instead of 501 Not Implemented |
| `unhandledException` | Declare 'throws Exception' on API methods |
| `apiFirst` | Generate supporting files only |
| `async` | Return CompletableFuture from API methods |
| `reactive` | Generate reactive (WebFlux) code |
| `responseWrapper` | Wrapper of return types: CompletableFuture, Callable, Future, ListenableFuture, DeferredResult or a fully qualified class name |
| `includeHttpRequestContext` | Add the HTTP request (ServerWebExchange / HttpServletRequest) to API methods |
| `singleContentTypes` | Use a single content type per operation |
| `sortParamsByRequiredFlag` | Put required parameters before optional ones |
| `apiNameSuffix` | Suffix of API class names |
| `skipDeprecated` | Don't generate code for deprecated operations |
| `skipDisabled` | Don't generate code for operations disabled with x-apigenie |
| `autoXSpringPaginated` | Add x-spring-paginated to operations with 'page', 'size' and 'sort' query parameters |
| `substituteGenericPagedModel` | Replace schemas of pages of items (a 'content' array and pagination metadata) with PagedModel&lt;T&gt; |
| `generateSortValidation` | Validate the sort of Pageable parameters against the enum values of 'sort' parameters |
| `generatePageableConstraintValidation` | Validate Pageable parameters against the limits of 'page' and 'size' parameters |
| `virtualService` | Generate Virtualan annotations for virtual services |
| `useSpringSecurityPreAuthorize` | Generate @PreAuthorize annotations from OAuth2/OpenID Connect scopes |
| `springSecurityAuthorityPrefix` | Prefix of the authorities checked by @PreAuthorize annotations |
| `implicitHeaders` | Describe header parameters with @Parameters instead of method parameters |
| `implicitHeadersRegex` | Regular expression of header parameters described with @Parameters |
| `useHttpServiceProxyFactoryInterfacesConfigurator` | Use a HttpServiceProxyFactory in HttpInterfacesAbstractConfigurator (spring-http-interface) |
| `clientRegistrationId` | @ClientRegistrationId of API interfaces (spring-http-interface, Spring Boot 4) |
| `useFeignClientUrl` | Use the url attribute of @FeignClient (spring-cloud) |
| `useFeignClientContextId` | Use the contextId attribute of @FeignClient (spring-cloud) |
| `useBeanValidation` | Use Bean Validation annotations |
| `performBeanValidation` | Use Hibernate Validator annotations |
| `useSpringBuiltInValidation` | Rely on Spring's built-in validation (no @Validated) |
| `additionalNotNullAnnotations` | Add @NotNull to required path and body parameters |
| `openApiNullable` | Use JsonNullable for nullable properties |
| `serializableModel` | Make models implement Serializable |
| `useOneOfInterfaces` | Represent oneOf schemas as interfaces |
| `useDeductionForOneOfInterfaces` | Deduce oneOf subtypes from their properties |
| `generatedConstructorWithRequiredArgs` | Generate constructors with required arguments |
| `generateConstructorWithAllArgs` | Generate constructors with all arguments |
| `generateBuilders` | Generate builders for models |
| `sortModelPropertiesByRequiredFlag` | Put required properties first in constructors |
| `enumPropertyNaming` | Naming of enum constants: MACRO_CASE, original, legacy, camelCase, PascalCase, snake_case or UPPERCASE |
| `useEnumCaseInsensitive` | Match enum values ignoring case |
| `withXml` | Add XML annotations to models |
| `useSealed` | Use sealed classes and interfaces (Java 17+) |
| `containerDefaultToNull` | Initialize containers with null instead of empty ones |
| `legacyDiscriminatorBehavior` | Use the legacy discriminator behavior |
| `disableDiscriminatorJsonIgnoreProperties` | Don't ignore discriminator properties during serialization |
| `modelNamePrefix` | Prefix of model names |
| `camelCaseDollarSign` | Keep the case of the first letter after a leading $ in names |
| `useEnumValueInterface` | Make enums implement the ValuedEnum interface |
| `generateJsonIncludeAnnotations` | Add @JsonInclude annotations to model properties |
| `optionalNonNullPropertyJsonInclude` | @JsonInclude policy of optional, non-nullable properties: NON_NULL, NON_EMPTY, NON_DEFAULT or NONE |
| `generateJsonSetterNullsAnnotations` | Add @JsonSetter(nulls = ...) annotations to optional, non-nullable properties |
| `optionalNonNullPropertyJsonSetterNulls` | @JsonSetter(nulls = ...) mode of optional, non-nullable properties: SKIP or FAIL |
| `modelNameSuffix` | Suffix of model names |
| `additionalModelTypeAnnotations` | Annotations added to model classes, separated by semicolons |
| `additionalEnumTypeAnnotations` | Annotations added to enum classes, separated by semicolons |
| `additionalOneOfTypeAnnotations` | Annotations added to oneOf interfaces, separated by semicolons |
| `typeInfoDefaultImpls` | Classes used as defaultImpl of @JsonTypeInfo, by schema name (Schema=Class,...) |
| `typeMappings` | Mappings of OpenAPI types to Java types (type=JavaType,...) |
| `importMappings` | Mappings of Java types to imports (Type=package.Type,...) |
| `schemaMappings` | Mappings of schemas to existing classes (Schema=package.Class,...) |
| `modelNameMappings` | Mappings of schema names to model names (Schema=Model,...) |
| `nameMappings` | Mappings of property names to Java names (name=javaName,...) |
| `parameterNameMappings` | Mappings of parameter names to Java names (name=javaName,...) |
| `enumNameMappings` | Mappings of enum values to constant names (value=NAME,...) |
| `contentMediaTypeAsBinary` | Map strings with a non-JSON contentMediaType to binary types, like format: binary |
| `useImplicitOneOfDiscriminator` | Dispatch oneOf schemas without a discriminator on a property whose value is constant in every member |
| `jsonAccessForReadWriteOnly` | Read readOnly properties from JSON only and write writeOnly ones only (@JsonProperty access) |
