Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[New Docs PR] Config Docs #4477

Merged
merged 10 commits into from
Jul 18, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 12 additions & 0 deletions config/config-mp/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,18 @@
<groupId>org.eclipse.microprofile.config</groupId>
<artifactId>microprofile-config-api</artifactId>
</dependency>
<dependency>
<groupId>io.helidon.config</groupId>
<artifactId>helidon-config-metadata</artifactId>
<scope>provided</scope>
<optional>true</optional>
</dependency>
<dependency>
<groupId>io.helidon.config</groupId>
<artifactId>helidon-config-metadata-processor</artifactId>
<scope>provided</scope>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-api</artifactId>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,8 @@
import io.helidon.config.ConfigException;
import io.helidon.config.ConfigMappers;
import io.helidon.config.ConfigValue;
import io.helidon.config.metadata.Configured;
import io.helidon.config.metadata.ConfiguredOption;
import io.helidon.config.mp.spi.MpConfigFilter;
import io.helidon.config.mp.spi.MpMetaConfigProvider;

Expand All @@ -77,6 +79,7 @@
/**
* Configuration builder.
*/
@Configured(prefix = "mp.config")
class MpConfigBuilder implements ConfigBuilder {
private static final Logger LOGGER = Logger.getLogger(MpConfigBuilder.class.getName());
private static final String DEFAULT_CONFIG_SOURCE = "META-INF/microprofile-config.properties";
Expand Down Expand Up @@ -363,6 +366,7 @@ public Config build() {
* @param profile name of the profile, such as {@code dev, test}
* @return updated builder instance
*/
@ConfiguredOption(key = "profile", type = String.class, description = "Configure an explicit profile name.")
public MpConfigBuilder profile(String profile) {
this.profile = profile;
return this;
Expand Down
1 change: 1 addition & 0 deletions config/config-mp/src/main/java/module-info.java
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
requires transitive microprofile.config.api;
requires jakarta.annotation;
requires io.helidon.common.serviceloader;
requires static io.helidon.config.metadata;

exports io.helidon.config.mp;
exports io.helidon.config.mp.spi;
Expand Down
1 change: 1 addition & 0 deletions docs/config/config_reference.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ The following section lists all configurable types in Helidon.
- xref:{rootdir}/config/io_helidon_metrics_api_MetricsSettings.adoc[MetricsSettings (metrics.api)]
- xref:{rootdir}/config/io_helidon_metrics_serviceapi_MetricsSupport.adoc[MetricsSupport (metrics.serviceapi)]
- xref:{rootdir}/config/io_helidon_integrations_micrometer_MicrometerSupport.adoc[MicrometerSupport (integrations.micrometer)]
- xref:{rootdir}/config/io_helidon_config_mp_MpConfigBuilder.adoc[MpConfigBuilder (config.mp)]
- xref:{rootdir}/config/io_helidon_security_providers_oidc_common_OidcConfig.adoc[OidcConfig (security.providers.oidc.common)]
- xref:{rootdir}/config/io_helidon_security_providers_oidc_OidcProvider.adoc[OidcProvider (security.providers.oidc)]
- xref:{rootdir}/config/io_helidon_openapi_OpenAPISupport.adoc[OpenAPISupport (openapi)]
Expand Down
55 changes: 55 additions & 0 deletions docs/config/io_helidon_config_mp_MpConfigBuilder.adoc
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
///////////////////////////////////////////////////////////////////////////////

Copyright (c) 2022 Oracle and/or its affiliates.

Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at

http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.

///////////////////////////////////////////////////////////////////////////////

ifndef::rootdir[:rootdir: {docdir}/..]
:description: Configuration of io.helidon.config.mp.MpConfigBuilder
:keywords: helidon, config, io.helidon.config.mp.MpConfigBuilder
:basic-table-intro: The table below lists the configuration keys that configure io.helidon.config.mp.MpConfigBuilder
include::{rootdir}/includes/attributes.adoc[]

= MpConfigBuilder (config.mp) Configuration

// tag::config[]


Type: link:{javadoc-base-url}/io.helidon.config.mp/io/helidon/config/mp/MpConfigBuilder.html[io.helidon.config.mp.MpConfigBuilder]


[source,text]
.Config key
----
mp.config
----



== Configuration options



Optional configuration options:
[cols="3,3,2,5a"]

|===
|key |type |default value |description

|`profile` |string |{nbsp} |Configure an explicit profile name.

|===

// end::config[]
Original file line number Diff line number Diff line change
Expand Up @@ -19,55 +19,77 @@
= Microprofile Config Sources
:description: MicroProfile Config Sources
:keywords: helidon, mp, ordinal, mpconfig, yamlmpconfig
:feature-name: Config
:rootdir: {docdir}/../..

include::{rootdir}/includes/mp.adoc[]

A Config Source provides configuration values from different sources such as property files and user classes that are registered by the application.
== ToC

Helidon configuration sources can use different formats for the configuration data. You can specify the format on a per-source bases, mixing and matching formats as required.
- <<Creating MicroProfile Config Sources for Manual Setup of Config>>
- <<Creating Custom Config Sources>>
- <<Creating MicroProfile Config Sources from meta-config>>
- <<Extending Meta-Config to Create a Custom Config Source Type>>
- <<Creating MicroProfile Config Source from Helidon SE Config Source>>
- <<Creating MicroProfile Config Source from Helidon SE Config Instance>>

The following configuration sources can be used to retrieve the configuration:
== Creating MicroProfile Config Sources for Manual Setup of Config

You can use the following methods to create MicroProfile Config Sources to manually set up the Config from `org.eclipse.microprofile.config.spi.ConfigProviderResolver#getBuilder()` on `io.helidon.config.mp.MpConfigSources` class:

[cols="3,5"]
|===
|Source |Description

|System properties |A mutable source that uses `System.getProperties()` to obtain configuration values.

|Environment variables |An immutable source that uses `System.env()` to obtain configuration values and resolves aliases as defined by the MicroProfile Config specification.
|Method |Description

|`META-INF/microprofile-config.properties` |The properties config source as defined by MicroProfile Config specification.
|`systemProperties()` |System properties config source.

|File |Creates the source from a properties file on the file system with `MpConfigSources.create(Path)`.
|`environmentVariables()` |Environment variables config source.

|URL |Creates the source from properties from an URL with `MpConfigSources.create(URL)`.
|`create(java.nio.file.Path)` |Loads a properties file from file system. +
To load the properties file from file system with custom name, use `create(String, java.nio.file.Path)`.

|`Map<String, String>` |Creates the source from a Map with `MpConfigSources.create(Map)`.
|`create(java.util.Map)` |Creates an in-memory source from map. +
To create an in-memory source from map with custom name, use `create(String, java.util.Map)`.

|`Properties` |Creates the source directly from Properties with `MpConfigSources.create(Properties)`.
|`create(java.util.Properties)` |Creates an in-memory source from properties. +
To create an in-memory source from properties with custom name, use `create(String, java.util.Properties)`.

|File on classpath |Creates the source from a properties file on classpath with `MpConfigSources.classpath(String)`.
|===

|YAML |Creates the source from YAML using `YamlMpConfigSource.create(Path)` or `YamlMpConfigSource.create(URL)`.
=== Create Custom Map MicroProfile Config Source
You can create Microprofile Config Source from a map.

|===
[source,java]
.Create MicroProfile Config Source based on Environment Variables and Custom Map
----
ConfigProviderResolver resolver = ConfigProviderResolver.instance();

== Understanding the Ordering of Default Config Sources
org.eclipse.microprofile.config.Config config = resolver.getBuilder() <1>
.withSources(MpConfigSources.environmentVariables()) <2>
.withSources(MpConfigSources.create(Map.of("key","value"))) <3>
.build(); <4>

The default MicroProfile Config Sources are:
resolver.registerConfig(config, null); <5>
----
<1> Creates MicroProfile Config Source builder.
<2> Adds environment variables.
<3> Adds a custom map.
<4> Builds the MicroProfile Config Source.
<5> Registers the config, so it can be used by other components

* System properties (ordinal=400)
* Environment variables (ordinal=300)
* /META-INF/microprofile-config.properties (ordinal=100)
=== Create YAML MicroProfile Config Source

Each Config Source has an ordinal that determines the priority of the Config Source.
A Config Source with higher ordinal has higher priority as compared to the Config Source with
lower ordinal. The values taken from the high-priority Config Source overrides the values
from low-priority Config Source.
You can create YAML Microprofile Config Source from a path or a URL. When you create a MicroProfile instance from the builder,
the `YamlMpConfigSource` allows you to create a custom Config Source and register
it with the builder.

This helps to customize the configuration of Config Sources using external Config Source
if an external Config Source has higher ordinal values than the built-in Config Sources of the application.
[source,java]
.Create YamlMPConfigSource from a path
----
ConfigProviderResolver.instance().newBuilder()
.withSources(YamlMpConfigSource.create(path))
.build();
----

== Creating Custom Config Sources

Expand Down Expand Up @@ -121,65 +143,6 @@ public class CustomConfigSource implements ConfigSource {
<3> Returns the value of the requested key, or `null` if the key is not available
<4> Returns the ordinal of this Config Source.


== Creating MicroProfile Config Sources for Manual Setup of Config

You can use the following methods to create MicroProfile Config Sources to manually set up the Config from `org.eclipse.microprofile.config.spi.ConfigProviderResolver#getBuilder()` on `io.helidon.config.mp.MpConfigSources` class:

[cols="3,5"]
|===
|Method |Description

|`systemProperties()` |System properties config source.

|`environmentVariables()` |Environment variables config source.

|`create(java.nio.file.Path)` |Loads a properties file from file system. +
To load the properties file from file system with custom name, use `create(String, java.nio.file.Path)`.

|`create(java.util.Map)` |Creates an in-memory source from map. +
To create an in-memory source from map with custom name, use `create(String, java.util.Map)`.

|`create(java.util.Properties)` |Creates an in-memory source from properties. +
To create an in-memory source from properties with custom name, use `create(String, java.util.Properties)`.

|===

=== Create Custom Map MicroProfile Config Source
You can create Microprofile Config Source from a map.

[source,java]
.Create MicroProfile Config Source based on Environment Variables and Custom Map
----
ConfigProviderResolver resolver = ConfigProviderResolver.instance();

org.eclipse.microprofile.config.Config config = resolver.getBuilder() <1>
.withSources(MpConfigSources.environmentVariables()) <2>
.withSources(MpConfigSources.create(Map.of("key","value"))) <3>
.build(); <4>

resolver.registerConfig(config, null); <5>
----
<1> Creates MicroProfile Config Source builder.
<2> Adds environment variables.
<3> Adds a custom map.
<4> Builds the MicroProfile Config Source.
<5> Registers the config, so it can be used by other components

=== Create Yaml MicroProfile Config Source

You can create Yaml Microprofile Config Source from a path or a URL. When you create a MicroProfile instance from the builder,
the `YamlMpConfigSource` allows you to create a custom Config Source and register
it with the builder.

[source,java]
.Create YamlMPConfigSource from a path
----
ConfigProviderResolver.instance().newBuilder()
.withSources(YamlMpConfigSource.create(path))
.build();
----

== Creating MicroProfile Config Sources from meta-config

Instead of directly specifying the configuration sources in your code, you can use meta-configuration in a file that declares
Expand Down Expand Up @@ -209,6 +172,10 @@ sources:
optional: true <9>
- type: "yaml" <10>
classpath: "META-INF/database.yaml" <11>
- type: "hocon" <12>
classpath: "custom-application.conf" <13>
- type: "json" <14>
path: "path: conf/custom-application.json" <15>

----

Expand All @@ -223,6 +190,91 @@ sources:
<9> The file is optional (if not optional and no file is found, the bootstrap fails)
<10> Loads a YAML file
<11> Location of the file: `META-INF/database.yaml` on the classpath
<12> Loads a HOCON file
<13> Location of the file: `custom-application.conf` on the classpath
<14> Loads a JSON file
<15> Location of the file: `conf/custom-application.json` relative to the directory of where the app was executed on the file system.

*Important Note:* To enable support for `HOCON` and `JSON` types, add the following dependency to your project’s pom.xml.

[source,xml]
----
<dependency>
<groupId>io.helidon.config</groupId>
<artifactId>helidon-config-hocon-mp</artifactId>
</dependency>
----

== Extending Meta-Config to Create a Custom Config Source Type

Helidon meta-config by default supports the following types: environment-variables, system-properties, properties, yaml, hocon and json. Users can also extend meta-config to create a custom config source type by loading it using the Java Service Loader pattern. This is achieved by implementing `io.helidon.config.mp.spi.MpMetaConfigProvider` SPI and registering it as a service (Using `META-INF/services/${class-name}` file when using classpath, or using the `provides` statement in `module-info.java` when using module path).

The interface `io.helidon.config.mp.spi.MpMetaConfigProvider` requires implementation of the following methods:

* `Set<String> supportedTypes()`
* `List<? extends ConfigSource> create(String type, Config metaConfig, String profile);`

=== Example of a Meta-Config Custom Type

[source,java]
----
public class CustomMpMetaConfigProvider implements MpMetaConfigProvider {
@Override
public Set<String> supportedTypes() {
return Set.of("custom"); <1>
}

@Override
public List<? extends ConfigSource> create(String type, Config metaConfig, String profile) {
ConfigValue<Path> pathConfig = metaConfig.get("path").as(Path.class);
if (pathConfig.isPresent()) { <2>
Path path = pathConfig.get();
List<ConfigSource> sources = sourceFromPath(path, profile); <3>
if (sources != null && !sources.isEmpty()) {
return result;
}
location = "path " + path.toAbsolutePath();
} else {
ConfigValue<String> classpathConfig = metaConfig.get("classpath").as(String.class);
if (classpathConfig.isPresent()) { <4>
String classpath = classpathConfig.get();
List<ConfigSource> sources = sourceFromClasspath(classpath, profile); <5>
if (sources != null && !sources.isEmpty()) {
return sources;
}
location = "classpath " + classpath;
} else {
ConfigValue<URL> urlConfig = metaConfig.get("url").as(URL.class);
if (urlConfig.isPresent()) { <6>
URL url = urlConfig.get();
List<ConfigSource> sources = sourceFromUrlMeta(url, profile); <7>
if (sources != null && !sources.isEmpty()) {
return sources;
}
location = "url " + url;
} else {
throw new ConfigException("No config source location for " + config.key());
}
}
}
}
if (metaConfig.get("optional").asBoolean().orElse(false);) {
return List.of(); <8>
}
throw new ConfigException("Meta configuration could not find non-optional config source on " + location); <9>

}
----

<1> Returns the names of the types that will be supported in this meta-config.
<2> Processes config source from file system if `path` is provided.
<3> Method to parse config source from a specified `path`
<4> Processes config source from classpath location if `classpath` is provided.
<5> Method to parse config source from a specified `classpath`
<6> Processes config source from URL location if `location` is provided.
<7> Method to parse config source from a specified `url`
<8> Returns an empty result if set to `optional` and config source is not found.
<9> Throws a ConfigException if not set to `optional` and config source is not found.

== Creating MicroProfile Config Source from Helidon SE Config Source

Expand Down
Loading