anchor.diff:  ====
   When `@ConfigurationProperties` bean is registered that way, the bean will have a
   conventional name: `<prefix>-<fqn>`, where `<prefix>` is the environment key prefix
  -specified in the `@ConfigurationProperties` annotation and <fqn> the fully qualified
  +specified in the `@ConfigurationProperties` annotation and `<fqn>` the fully qualified
   name of the bean. If the annotation does not provide any prefix, only the fully qualified
   name of the bean is used.
   
  -The bean name in the example above will be `connection-com.example.ConnectionProperties`,
  -assuming that `ConnectionProperties` sits in the `com.example` package.
  +The bean name in the example above will be `foo-com.example.FooProperties`.
   ====
   
  -Even if the configuration above will create a regular bean for `ConnectionProperties`, we
  +Even if the configuration above will create a regular bean for `FooProperties`, we
   recommend that `@ConfigurationProperties` only deal with the environment and in particular
   does not inject other beans from the context. Having said that, The
   `@EnableConfigurationProperties` annotation is _also_ automatically applied to your project
   so that any _existing_ bean annotated with `@ConfigurationProperties` will be configured
  -from the `Environment` properties. You could shortcut `MyConfiguration` above by making
  -sure `ConnectionProperties` is a already a bean:
  -
  -[source,java,indent=0]
  -----
  -    @Component
  -    @ConfigurationProperties(prefix="connection")
  -	public class ConnectionProperties {
  -
  -		// ... getters and setters
  +from the `Environment`. You could shortcut `MyConfiguration` above by making sure
  +`FooProperties` is a already a bean:
  +
  +[source,java,indent=0]
  +----
  +	@Component
  +	@ConfigurationProperties(prefix="foo")
  +	public class FooProperties {
  +
  +		// ... see above
   
   	}
   ----
  
positive.code: 
  In order to validate values of nested properties, you must annotate the associated field
  as `@Valid` to trigger its validation. For example, building upon the above
  `ConnectionProperties` example:
  
  [source,java,indent=0]
  ----
  	@ConfigurationProperties(prefix="connection")
  	public class ConnectionProperties {
  
  		@NotNull
  		@Valid
  		private RemoteAddress remoteAddress;
  
  		// ... getters and setters
  
  		public static class RemoteAddress {
  
  			@NotEmpty
  			public String hostname;
  
  			// ... getters and setters
  
  
negative.code: [[boot-features-external-config-typesafe-configuration-properties]]
  === Type-safe Configuration Properties
  Using the `@Value("${property}")` annotation to inject configuration properties can
  sometimes be cumbersome, especially if you are working with multiple properties or your
  data is hierarchical in nature. Spring Boot provides an alternative method of working with
  properties that allows strongly typed beans to govern and validate the configuration of
  your application.
  
  [source,java,indent=0]
  ----
  	package com.example;
  
  	import java.net.InetAddress;
  	import java.util.ArrayList;
  	import java.util.Collections;
  	import java.util.List;
  
  	import org.springframework.boot.context.properties.ConfigurationProperties;
  
  	@ConfigurationProperties("foo")
  	public class FooProperties {
  
  		private boolean enabled;
  
  		private InetAddress remoteAddress;
  
  		private final Security security = new Security();
  
  		public boolean isEnabled() { ... }
  
  		public void setEnabled(boolean enabled) { ... }
  
  		public InetAddress getRemoteAddress() { ... }
  
  		public void setRemoteAddress(InetAddress remoteAddress) { ... }
  
  		public Security getSecurity() { ... }
  
  		public static class Security {
  
  			private String username;
  
  			private String password;
  
  			private List<String> roles = new ArrayList<>(Collections.singleton("USER"));
  
  			public String getUsername() { ... }
  
  			public void setUsername(String username) { ... }
  
  			public String getPassword() { ... }
  
  			public void setPassword(String password) { ... }
  
  			public List<String> getRoles() { ... }
  
  			public void setRoles(List<String> roles) { ... }
  
  		}
  	}
  ----
  
  The POJO above defines the following properties:
  
  * `foo.enabled`, `false` by default
  * `foo.remote-address`, with a type that can be coerced from `String`
  * `foo.security.username`, with a nested "security" whose name is determined by the name
  of the property. In particular the return type is not used at all there and could have
  been `SecurityProperties`
  * `foo.security.password`
  * `foo.security.roles`, with a collection of `String`
  
  [NOTE]
  ====
  Getters and setters are usually mandatory, since binding is via standard Java Beans
  property descriptors, just like in Spring MVC. There are cases where a setter may be
  omitted:
  
  * Maps, as long as they are initialized, need a getter but not necessarily a setter since
  they can be mutated by the binder.
  * Collections and arrays can be either accessed via an index (typically with YAML) or
  using a single comma-separated value (properties). In the latter case, a setter is
  mandatory. We recommend to always add a setter for such types. If you initialize a
  collection, make sure it is not immutable (as in the example above)
   * If nested POJO properties are initialized (like the `Security` field in the example
  above), a setter is not required. If you want the binder to create the instance on-the-fly
  using its default constructor, you will need a setter.
  
  Some people use Project Lombok to add getters and setters automatically. Make sure that
  Lombok doesn't generate any particular constructor for such type as it will be used
  automatically by the container to instantiate the object.
  ====
  
  TIP: See also the <<boot-features-external-config-vs-value,differences between `@Value`
  and `@ConfigurationProperties`>>.
  