[[configuration-guide]] = Configuration Guide [partintro] -- You can use Initializr to create your own service that can generate JVM projects. This section describes how you can create your own service and tune it for your needs, and also how you can configure an existing service. -- [[create-instance]] == Creating your own instance Initializr jars are available on https://repo.spring.io and can be used to create your own service. Initializr is split across several modules: * `initializr-generator`: core project generation library * `initializr-generator-spring`: optional module defining the conventions for a Spring Boot project. Can be replaced by your own conventions if necessary. * `initializr-metadata`: metadata infrastructure for various aspects of the project * `initializr-web`: REST endpoints * `initializr-actuator`: optional module to provide additional information and statistics on project generation * `initializr-docs`: documentation To understand concepts behind project generation, let's take a look at the first two in a little more detail. [[initializr-generator]] == Initializr Generator The `initializr-generator` module contains all the infrastructure necessary to generate projects. The `ProjectGenerator` class is the main entry point for project generation. Project generation occurs in a dedicated application context (`ProjectGenerationContext`), which means that for every project that is generated, the context only contains configuration and components corresponding to that project. The components registered in a `ProjectGenerationContext` are decided based on an immutable `ProjectDescription`. Components for a `ProjectGenerationContext` are defined in `@ProjectGenerationConfiguration`-annotated configuration classes. The `ProjectGenerationContext` imports `@ProjectGenerationConfiguration`-annotated configuration classes that are registered in `META-INF/spring.factories`. [indent=0] ---- io.spring.initializr.generator.project.ProjectGenerationConfiguration=\ com.example.acme.build.BuildProjectGenerationConfiguration,\ com.example.acme.code.SourceCodeProjectGenerationConfiguration ---- A project is defined by a `ProjectDescription` which consists of the following project properties: * A platform `Version` used by the project. This can be used to tune available dependencies according to the chosen generation. * The `BuildSystem` and `Packaging` * The JVM `Language` * The requested dependencies, indexed by ID * Basic coordinates such as `groupId`, `artifactId`, `name`, `description` * The name of the `application` * The root package name * The base directory for the project Before any project assets are generated, the `ProjectDescription` can be customized using ``ProjectDescriptionCustomizer``s. ``ProjectDescriptionCustomizer``s are beans in a `ProjectGenerationContext` and they can be ordered using Spring's `Ordered` interface. Once the description has been customized based on the available ``ProjectDescriptionCustomizer``s, the generator uses a `ProjectAssetGenerator` to generate the project assets. The default implementation of `ProjectAssetGenerator` generates a directory structure using ``ProjectContributor``s available in the `ProjectGenerationContext`. ``ProjectContributor``s can also be ordered using `Ordered`. Components such as ``ProjectContributor``s and ``ProjectDescriptionCustomizer``s are made available in a `ProjectGenerationContext` using conditions. Using conditions avoids exposing beans that have to check if they have to do something and makes the declaration idiomatic. Consider the following example: [source,java,indent=0] ---- @Bean @ConditionalOnBuildSystem(GradleBuildSystem.ID) @ConditionalOnPackaging(WarPackaging.ID) public BuildCustomizer warPluginContributor() { return (build) -> build.addPlugin("war"); } ---- This registers a bean only if the project to generate uses Gradle and `war` packaging. Check the `io.spring.initializr.generator.condition` package for more details. Custom conditions can easily be created by inheriting from `ProjectGenerationCondition`. This module also contains abstractions for various aspects of the project along with some convenient implementations: * A build system abstraction with Maven and Gradle implementations. * A language abstraction with Java, Groovy and Kotlin implementations, including a SourceCodeWriter for each implementation * A packaging abstraction with implementations for `jar` and `war` Adding new implementations for these involves creating a `BuildSystemFactory`, `LanguageFactory` and `PackagingFactory` and registering it in `META-INF/spring.factories` under `io.spring.initializr.generator.buildsystem.BuildSystemFactory`, `io.spring.initializr.generator.language.LanguageFactory` and `io.spring.initializr.generator.packaging.PackagingFactory` respectively. A JVM project typically contains a build file which contains the build configuration for the project. The `initializr-generator` module provides a model for `Build` with implementations for `Maven` and `Gradle`. This model can be manipulated depending on the conventions. The library also provides a `MavenBuildWriter` and `GradleBuildWriter` that can convert a `Build` model to a build file. The next section about the <> module showcases how the `Build` can be manipulated before the build file is written using customizers. [[initializr-generator-spring]] == Initializr Conventions for Spring Boot This is an optional module that defines the conventions that we think will be useful for any Spring Boot project. You can include this jar in your project if your service is meant for generating Spring Boot projects. In the section above, we looked at how ``ProjectContributor``s can be used to contribute assets to a project. This module contains concrete implementations of `ProjectContributor` along with the ``@ProjectGenerationConfiguration``s that configure them. For example, there is a `MavenBuildProjectContributor` which contributes the files for a Maven build, such as `pom.xml`. This contributor is registered as a bean in a `ProjectGenerationConfiguration` which is conditional on the build system being Maven. This module also introduces the concept of ``BuildCustomizer``s. ``BuildCustomizer``s are used to customize a project's `Build` and are ordered. For instance, if your service requires you to add a certain plugin to the build, you can provide a `BuildCustomizer` that adds the plugin and the customizer will be called according to the order specified on it. [[create-instance]] == Creating your own instance NOTE: This walkthrough of how to create your own service assumes that the service will be used for creating Spring Boot projects which is the why `initializr-generator-spring` jar is included. You can generate a project for your own instance on https://start.spring.io. Create a new project with the `web` dependency and add the following dependencies: [source,xml,indent=0,subs="verbatim,attributes"] ---- io.spring.initializr initializr-web {spring-initializr-version} io.spring.initializr initializr-generator-spring {spring-initializr-version} ---- Or if you are using Gradle: [source,groovy,indent=0,subs="verbatim,quotes,attributes"] ---- implementation("io.spring.initializr:initializr-web:{spring-initializr-version}") implementation("io.spring.initializr:initializr-generator-spring:{spring-initializr-version}") ---- NOTE: Spring Initializr releases are not available on Maven Central so you will need to configure the build to add an extra repository at `https://repo.spring.io/release`. Once you've started the application, you can hit http://localhost:8080. You'll get a json document that describes the capabilities of the service. None of the select capabilities will have values (except the one for the Spring Boot version, we will <>). In the rest of this section, we will configure those basic settings. [TIP] ==== Most of the settings are configured via `application.properties` using the `initializr` namespace. Because the configuration is highly hierarchical, we recommend using the yaml format that is more readable for such structure. If you agree, go ahead and rename `application.properties` to `application.yml`. ==== [[create-instance-basic-settings]] === Configuring basic settings Most of the select capabilities are configured via a simple list-based structure where each entry has an `id`, a `name` and whether that entry is the default or not. If no `name` is provided, the `id` is used instead. Let's configure the languages and the JVM generations we want to support: [source,yaml,indent=0] ---- initializr: javaVersions: - id: 11 default: false - id: 1.8 default: true languages: - name: Java id: java default: true - name: Kotlin id: kotlin default: false ---- If you restart the application and refresh http://localhost:8080, the language capability now has the options and default values defined above. NOTE: The language identifiers defined there must have a corresponding `Language` implementation. `java`, `kotlin` and `groovy` can be used out-of-the-box as implementations for those are available in the core library itself. The available packagings are also configurable that way: [source,yaml,indent=0] ---- initializr: packagings: - name: Jar id: jar default: true - name: War id: war default: false ---- NOTE: `Jar` and `War` packaging is available out-of-the-box. For additional packaging formats, you need to implement the `Packaging` abstraction and provide a `PackagingFactory` that corresponds to it. [[create-instance-text-only-settings]] === Configuring text-only settings Text-only capabilities include `groupId`, `artifactId`, `name`, `description`, `version` and `packageName`. Each capability has a default value if nothing is configured. The defaults can be overriden as show below: [source,yaml,indent=0] ---- initializr: group-id: value: org.acme artifact-id: value: my-app ---- [[create-instance-boot-versions]] === Configuring available Spring Boot versions If you look at http://projects.spring.io/spring-boot[the project home page for Spring Boot], the latest versions are displayed. And you've probably noticed that they match the drop down list that you automatically get with a default instance of the Initializr. The reason for that is that Spring Initializr calls an API on https://spring.io to retrieve the latest versions automatically. This makes sure that you always get the latest available versions. If you are behind a proxy, or need to customize the `RestTemplate` that is used behind the scenes, you can define a `RestTemplateCustomizer` bean in your configuration. For more details, {spring-boot-reference}/#boot-features-restclient-customization[check the documentation]. If you don't want the version to be upgraded automatically, you need to override the `InitializrMetadataUpdateStrategy` bean to provide your own strategy when the metadata has to be refreshed. For instance, you could swap to an implementation that always returns the contents of static `application.yml`: [source,java,indent=0] ---- @Bean public InitializrMetadataUpdateStrategy initializrMetadataUpdateStrategy() { return (metadata) -> metadata; } ---- The thing to remember is that, by default, you don't have to worry about upgrading your instance when a new Spring Boot version is released. However, you may need to <> to avoid requesting that service too often. [[create-instance-types]] === Configuring available project types The available project types mostly define the structure of the generated project and its build system. Once a project type is selected, the related action is invoked to generate the project. By default, Spring Initializr exposes the following resources (all accessed via HTTP GET): * `/pom.xml` generate a Maven `pom.xml` * `/build.gradle` generate a Gradle build * `/starter.zip` generate a complete project structure archived in a zip * `/starter.tgz` generate a complete project structure archived in a tgz The build system must be defined with a `build` tag providing the name of the `BuildSystem` to use (e.g. `maven`, `gradle`). Additional tags can be provided to further qualify the entry. Besides the mandatory `build` tag, a `format` tag is also available to define the format of the project (e.g. `project` for a full project, `build` for just a build file). By default, the HTML UI filters all the available types to only display the ones that have a `format` tag with value `project`. You can of course implement additional endpoints that generate whatever project structure you need but, for now, we'll simply configure our instance to generate a Gradle or a Maven project: [source,yaml,indent=0] ---- initializr: types: - name: Maven Project id: maven-project description: Generate a Maven based project archive tags: build: maven format: project default: true action: /starter.zip - name: Gradle Project id: gradle-project description: Generate a Gradle based project archive tags: build: gradle format: project default: false action: /starter.zip ---- NOTE: If you intend to build a custom client against your service, you can add as many tags as you want, and process them in the client in a way that makes sense for your users. For instance, the spring boot CLI uses them as a shortcut to the full type id. So rather than having to create a Gradle project as follows: [indent=0,subs="verbatim,quotes,attributes"] ---- $ spring init --type=gradle-project my-project.zip ---- You can simply define a more convenient build parameter: [indent=0,subs="verbatim,quotes,attributes"] ---- $ spring init --build=gradle my-project.zip ---- With that configuration, you should be able to generate your first project, congratulations! Let's now add dependencies so that you can start searching for them. [[create-instance-dependencies]] === Configuring dependencies The most basic `dependency` is composed of: * An `id` used in clients to refer to it * The full maven coordinates of the dependency (`groupId` and `artifactId`) * A display `name` (used in the UI and the search results) * A `description` can (and should) be added to provide more information about the dependency Spring Initializr automatically considers that a dependency without maven coordinates defines an official Spring Boot starter. In such a case, the `id` is used to infer the `artifactId`. For instance, the following configures the `spring-boot-starter-web` Starter: [source,yaml,indent=0] ---- initializr: dependencies: - name: Web content: - name: Web id: web description: Full-stack web development with Tomcat and Spring MVC ---- Each dependency is contained in a _group_ that gathers dependencies sharing a common surface area or any other form of grouping. In the example above, a `Web` group holds our unique dependency. A group can also provide default values for various settings, see the <> for more details. In our `spring-boot-starter-web` example above, the dependency is _managed_ by Spring Boot so there is no need to provide a `version` attribute for it. You'll surely need to define additional dependencies that are not provided by Spring Boot and we strongly recommend you to use a <>. If no BOM is available you can specify a version directly: [source,yaml,indent=0] ---- initializr: dependencies: - name: Tech content: - name: Acme id: acme groupId: com.example.acme artifactId: acme version: 1.2.0.RELEASE description: A solid description for this dependency ---- If you add this configuration and search for "acme" (or "solid"), you'll find this extra entry; generating a maven project with it should add the following to the pom: [source,xml,indent=0,subs="verbatim"] ---- com.example.acme acme 1.2.0.RELEASE ---- The rest of this section will detail the other configuration options. [[dependencies-version-range]] ==== Availability (version range) By default, a dependency is available regardless of the Spring Boot version you have selected. If you need to restrict a dependency to a certain Spring Boot generation you can add a `versionRange` attribute to its definition. A version range is a range of versions of Spring Boot which are valid in combination with it. The versions are *not* applied to the dependency itself, but rather used to filter out the dependency, or modify it, when different versions of Spring Boot are selected for the generated project. A typical version is composed of four parts: a major revision, a minor revision, a patch revision and a qualifier. Qualifiers are ordered as follows: * `M` for milestones (e.g. `2.0.0.M1` is the first milestone of the upcoming 2.0.0 release): can be seen as "beta" release * `RC` for release candidates (e.g. `2.0.0.RC2` is the second release candidate of upcoming 2.0.0 release) * `RELEASE` for general availability (e.g. `2.0.0.RELEASE` is 2.0.0 proper) * `BUILD-SNAPSHOT` for development build (`2.1.0.BUILD-SNAPSHOT` represents the latest available development build of the upcoming 2.1.0 release). TIP: snapshots are in a bit special in that scheme as they always represents the "latest state" of a release. `M1` represents the most oldest version for a given major, minor and patch revisions. A version range has a lower and an upper bound, and if the bound is inclusive it is denoted as a square bracket (`[` or `]`), otherwise it is exclusive and denoted by a parenthesis (`(` or `)`). For instance `[1.1.6.RELEASE,1.3.0.M1)` means from all versions from `1.1.6.RELEASE` up to but not including `1.3.0.M1` (concretely no including the `1.3.x` line and after). A version range can be a single value, e.g. `1.2.0.RELEASE`, which is short for "this version or greater". It is an inclusive lower bound with an implied infinite upper bound. If you need to specify "the latest release" in a given line, you can use a `x` rather than an hard-coded version. For instance, `1.4.x.BUILD-SNAPSHOT` is the latest snapshot build of the 1.4.x line. For instance, if you want to restrict a dependency from `1.1.0.RELEASE` to the latest stable release of the 1.3.x line, you'd use `[1.1.0.RELEASE,1.3.x.RELEASE]`. Snapshots are naturally ordered higher than released versions, so if you are looking to match a dependency to only the latest snapshots of Spring Boot, you could use a version range of `1.5.x.BUILD-SNAPSHOT` (assuming 1.5 was the latest). TIP: Remember to quote the values of a version range in YAML configuration files (with double quotes ""). See below in the section on <> for more examples and idioms. [[dependencies-repository]] ==== Repository If the dependency is not available on Maven Central (or whatever default repository that is configured on your end), you can also add a reference to a repository. A repository is declared at the top level (under `env`) and given an id via the key in the configuration: [source,yaml,indent=0] ---- initializr: env: repositories: my-api-repo-1: name: repo1 url: http://example.com/repo1 ---- Once defined, the repository can then be referred back to in a dependency [source,yaml,indent=0] ---- initializr: dependencies: - name: Other content: - name: Foo groupId: org.acme artifactId: foo version: 1.3.5 repository: my-api-repo-1 ---- It is usually preferable to have a BOM for every dependency, and attach the repository to the BOM instead. TIP: The snapshots and milestones repositories on `repo.spring.io` are automatically available with the `spring-snapshots` and `spring-milestones` identifiers respectively. [[create-instance-boms]] === Configuring Bill of Materials A Bill of Materials (BOM) is a special `pom.xml`, deployed to a Maven repository, and used to control dependency management for a set of related artifacts. In the Spring Boot ecosystem we usually use the suffix `-dependencies` on the artifact id of a BOM. In other projects we see `-bom`. It is recommended that all dependencies are included in a BOM of some sort, since they provide nice high level features for users of the dependency. It is also important that 2 BOMs used in a project do not contain conflicting versions for the same dependency, so the best practice is to look at the existing BOMs in the Initializr before you add a new one, and make sure that you aren't adding a conflict. In the Initializr a BOM is declared at the `env` level, and given an id through the configuration key. Example: [source,yaml,indent=0] ---- initializr: env: boms: my-api-bom: groupId: org.acme artifactId: my-api-dependencies version: 1.0.0.RELEASE repositories: my-api-repo-1 ---- If a BOM requires a special, non-default repository, then it can be referred to here, instead of having to explicitly list the repository again for each dependency. A dependency, or a dependency group, can declare that it requires the use of one or more BOMs by referring to the id: [source,yaml,indent=0] ---- initializr: dependencies: - name: Other content: - name: My API id : my-api groupId: org.acme artifactId: my-api bom: my-api-bom ---- [[dependencies-mappings]] ==== Map coordinates according to the Spring Boot version In addition to a Spring Boot version range for the dependency or a BOM, you can configure the version relationships at a finer grained level using version mappings. A dependency or BOM has a list of "mappings", each of which consists of a version range, and a set of one or more dependency properties to override for those versions of Spring Boot. You can use a mapping to switch the version of a dependency, or (better) the BOM, or to change its artifact id (if the project changed its packaging) for instance. Here's an example of a BOM with mappings: [source,yaml,indent=0] ---- initializr: env: boms: cloud-bom: groupId: com.example.foo artifactId: acme-foo-dependencies mappings: - versionRange: "[1.2.3.RELEASE,1.3.0.RELEASE)" groupId: com.example.bar artifactId: acme-foo-bom version: Arcturus.SR6 - versionRange: "[1.3.0.RELEASE,1.4.0.RELEASE)" version: Botein.SR7 - versionRange: "[1.4.0.RELEASE,1.5.x.RELEASE)" version: Castor.SR6 - versionRange: "[1.5.0.RELEASE,1.5.x.BUILD-SNAPSHOT)" version: Diadem.RC1 repositories: spring-milestones - versionRange: "1.5.x.BUILD-SNAPSHOT" version: Diadem.BUILD-SNAPSHOT repositories: spring-snapshots,spring-milestones ---- The primary use case here is to map Spring Boot versions to the preferred or supported versions of the Foo project. You can also see that for the milestone and snapshot BOMs, additional repositories are declared because those artifacts are not in the default repository. Initially the BOM was identified as `com.example.bar:acme-foo-bom` and renamed as of `Botein` to `com.example.foo:acme-foo-dependencies`. TIP: We also use the `x` trick in version ranges to avoid updating the range every time a new Spring Boot 1.5 bug fix release is available See below in the section on <> for more examples. [[dependencies-alias]] ==== Aliases A dependency has an id (e.g. "web-services"), but it could be necessary to provide a new id and still be able to serve request from client using the now deprecated id. To do so, an alias can be defined for ths dependency; [source,yaml,indent=0] ---- initializr: dependencies: - name: Other content: - name: Web Services id: web-services aliases: - ws ---- The same project can now be generated with `dependencies=ws` or `dependencies=web-services`. [[dependencies-facet]] ==== Facets A "facet" is a label on a dependency which is used to drive a code modification in the generated project. For example, `initializr-generator-spring` checks for the presence of a dependency with the `web` facet if the packaging type is `war`. The absence of a dependency with the `web` facet drives inclusion of a dependency with id `web` (defaulting to `spring-boot-starter-web` if such dependency is not available). The value of the "facets" property of a dependency is a list of strings. [[create-instance-dependencies-link]] ==== Links Links can be used to provide descriptive and hyperlink data to guide to user on how to learn more about a dependency. A dependency has a "links" property which is a list of `Link`. Each link has a `rel` label to identify it, an `href` and an optional (but recommended) `description`. The following `rel` value are currently officially supported: * `guide`: the link points to a guide describing how to use the related dependency. It can be a tutorial, a how-to or typically a guide available on https://spring.io/guides * reference: the link points to a section of a developer guide typically or any page that documents how to use the dependency The url can be templated if its actual value can change according to the environment. An URL parameter is specified with curly braces, something like `https://example.com/doc/{bootVersion}/section` defines a `bootVersion` parameter. The following attributes are currently supported: * `bootVersion`: the Spring Boot version that is currently active Here is an example that adds two links to the `acme` dependency: [source,yaml,indent=0] ---- initializr: dependencies: - name: Tech content: - name: Acme id: acme groupId: com.example.acme artifactId: acme version: 1.2.0.RELEASE description: A solid description for this dependency links: - rel: guide href: https://com.example/guides/acme/ description: Getting started with Acme - rel: reference href: http://docs.example.com/acme/html ---- [[create-instance-dependencies-search]] ==== Improve search results Each dependency can have a `weight` (a number >=0) and also `keywords` (list of string) that are used to prioritize them in the search feature in the web UI. If you type one of the keywords into the "Dependencies" box in the UI, those dependencies will be listed below, in order of decreasing weight, if they have one (unweighted dependencies come last). [[configuration-howto]] == '`How-to`' guides This section provides answers to some common '`how do I do that...`' type of questions that often arise when configuring Spring Initializr. [[howto-add-a-new-dependency]] === Add a new dependency To add a new dependency, first identify the Maven co-ordinates of the dependency you want to add (`groupId:artifactId:version`) and then check which versions of Spring Boot it works with. If there are multiple versions that work with different versions of Spring Boot, then that's fine too. * If there is a published BOM that manages the version of you dependency, then add that first, in the `env` section (see <>). * Then configure the dependency, fitting it into an existing group if you can, otherwise creating a new group. * If there is a BOM then omit the version. * If there is a Spring Boot version range (or min or max) that you need for this dependency, add that as a <>. [[howto-override-a-version]] === Override the version of a dependency Sometimes it happens that the BOM that normally manages your dependency version is in conflict with the newest version. Or maybe this is the case for only a range of Spring Boot versions. Or maybe there just is no BOM, or it's not worth creating one for just one dependency. In these cases you can specify the version manually for a dependency either at the top level, or in a <>. At the top level it looks like this (just a `version` property in a dependency): [source,yaml,indent=0] ---- initializr: dependencies: - name: Tech content: - name: Acme id: acme groupId: com.example.acme artifactId: acme version: 1.2.0.RELEASE description: A solid description for this dependency ---- [[howto-link-boot-version]] === Link a Boot version to a version of your dependency If your dependency requires a specific version of Spring Boot, ot different versions of Spring Boot require different versions of your dependency there are a couple of mechanisms to configure that. The simplest is to put a `versionRange` in the dependency declaration. This is a range of versions of Spring Boot, not of your dependency. For example: [source,yaml,indent=0] ---- initializr: dependencies: - name: Stuff content: - name: Foo id: foo ... versionRange: 1.2.0.M1 - name: Bar id: bar ... versionRange: "[1.5.0.RC1,2.0.0.M1)" ---- In this example `Foo` is available for Spring Boot 1.2.0 (or any milestone of 1.2.0) or greater, and `Bar` is available for Spring Boot 1.5.0 up to, but not including 2.0.0. If different versions of your dependency work with different versions of Spring Boot, that's when you need the `mappings` property. A mapping is a combination of a `versionRange` and some or all of the other properties of the dependency, overriding the values defined at the top level. For example: [source,yaml,indent=0] ---- initializr: dependencies: - name: Stuff content: - name: Foo id: foo groupId: org.acme.foo artifactId: foo-spring-boot-starter versionRange: 1.3.0.RELEASE bom: cloud-task-bom mappings: - versionRange: "[1.3.0.RELEASE,1.3.x.RELEASE]" artifactId: foo-starter - versionRange: "1.4.0.RELEASE" ---- In this example, The artifact of `foo` was changed to `foo-spring-boot-starter` as of the version that is compatible with Spring Boot 1.4. This mapping instruct that if Spring Boot 1.3.x is selected, the artifact Id should be set to `foo-starter`. A mapping can also be applied to a BOM declaration. For example: [source,yaml,indent=0] ---- initializr: env: boms: my-api-bom: groupId: org.acme artifactId: my-api-bom additionalBoms: ['my-api-dependencies-bom'] mappings: - versionRange: "[1.0.0.RELEASE,1.1.6.RELEASE)" version: 1.0.0.RELEASE repositories: my-api-repo-1 - versionRange: "1.2.1.RELEASE" version: 2.0.0.RELEASE repositories: my-api-repo-2 ---- In this example Spring Boot versions up to 1.1.6 select version 1.0.0 of the BOM, and set a different repository. Spring Boot versions 1.2.1 and above select 2.0.0 of the BOM and yet another repository. [[howto-add-snapshot-repository]] === Configure a snapshot repository A dependency, or a BOM, might require the use of a specific repository, if the default one (usually Maven Central) does not contain the artifacts. Normally, the best place to declare that is in the BOM configuration, but if there isn't a BOM then you can put it in the dependency itself. You can also use a Spring Boot <> to override the default repository for a dependency or BOM. [[howto-dependency-starter-flag]] === Make sure a regular dependency brings the base starter If a dependency does not stand on its own (and specifically if it does not depend on an existing Spring Boot starter) you can flag it as a "non starter": [source,yaml,indent=0] ---- initializr: dependencies: - name: Stuff content: - name: Lib id: lib groupId: com.acme artifactId: lib starter:false ---- When a project is generated that only has dependencies with this flag set, then the base Spring Boot starter is added as well. [[howto-group-share-settings]] === Share common dependency settings in a group A dependency group is a hint for user interface implementations, to group things together for users when they are selecting dependencies. It is also a convenient way to share settings between dependencies because every dependency inherits all the settings. The most common settings in a group are the `groupId`, `versionRange` and `bom`: [source,yaml,indent=0] ---- initializr: dependencies: - name: Stuff bom: stuff-bom versionRange: "[1.3.0.RELEASE,2.0.0.M1)" content: ... ---- These dependencies, by default, will be available only for Spring Boot versions 1.3 up to 2.0 (excluded) and will bring in the `stuff-bom` BOM. [[create-instance-advanced-config]] == Advanced configuration [[create-instance-advanced-config-caching]] === Caching configuration If you use the service, you'll notice that the logs have lots of entries with the message `Fetching boot metadata from https://spring.io/project_metadata/spring-boot`. To avoid checking for the latest Spring Boot versions too often, you should enable caching on your service. Spring Initializr has some auto-configuration to apply the proper caches if you are willing to use a JCache (JSR-107) implementation. Add the `javax.cache:cache-api` and your favorite JCache implementation and simply enable caching by adding `@EnableCaching` to your `@SpringBootApplication`. For instance, you could use `ehcache` by adding the following: [source,xml,indent=0,subs="verbatim,attributes"] ---- javax.cache cache-api org.ehcache ehcache ---- Or if you are using Gradle: [source,groovy,indent=0,subs="verbatim,quotes,attributes"] ---- implementation("javax.cache:cache-api") implementation("org.ehcache:ehcache") ---- You'll notice that the log entry is much more rare. If you do not want to use JSR-107, you should configure the cache yourselves. Here are the caches used by the application (each one will require some configuration to get it working): .Cache configuration |=== | cache name | Description |`initializr.metadata` |Cache the full metadata of the service. When the metadata expires, it is fully resolved again (including a check on spring.io for the latest Spring Boot versions). Adapt the expiration settings accordingly. |`initializr.dependency-metadata` |Cache dependency-specific metadata. |`initializr.templates` |Cache templates that are used to generate projects. |===