How Spring Boot Creates Custom starter

Keywords: Spring Attribute Maven Java

Background:

(1) Sometimes in the company, sometimes self-developed middleware needs to be depended on by other projects. At this time, starter can be directly introduced to realize automatic configuration, which can make the code of other projects pollution-free intrusion.

(2) Spring Boot uses starter mode extensively, such as spring-boot-starter-redis, spring-boot-starter-jdbc, spring-boot-starter-data-jpa, spring-boot-starter-amqp. We can do it ourselves once, and understand and learn Spring Boot's programming ideas more deeply.

1. First, we use Spring Initializr of IDEA to create projects directly, introducing web dependencies.

<dependency>
   <groupId>org.springframework.boot</groupId>
   <artifactId>spring-boot-starter-web</artifactId>
</dependency>

2. Then delete the boot class, test class and the following maven plug-in. The starter we created belongs to the dependency package and does not need to start the class. Otherwise, errors will be reported in subsequent jar calls.

<plugin>
   <groupId>org.springframework.boot</groupId>
   <artifactId>spring-boot-maven-plugin</artifactId>
</plugin>

3. Create configuration classes to configure related properties for the introduced starter

@ConfigurationProperties(prefix = "spring.user")
public class UserProperties {

    private String name;
    private Integer age;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public Integer getAge() {
        return age;
    }

    public void setAge(Integer age) {
        this.age = age;
    }
}

4. Create Client end, define related methods to manipulate attributes, simulate data processing.

public class UserClient {
    private UserProperties userProperties;

    public UserClient() {
    }

    public UserClient(UserProperties userProperties) {
        this.userProperties = userProperties;
    }

    public String getName(){
        return userProperties.getName();
    }

    public Integer getAge(){
        return userProperties.getAge();
    }
}

5. Automatically create client, create user client instance

Note: @ConditionalOnProperty is used to control whether configuration is enabled. Its name or value attribute has the same meaning, except that name is an array and value binds only one attribute. Configuration takes effect when the name or value attribute specifies a value for havingValue, otherwise the configuration does not take effect. That is, in the following configuration, the configuration takes effect only when enabled is true.

@Configuration
@EnableConfigurationProperties(value = UserProperties.class)
public class UserAutoConfigure {

    @Bean
    @ConditionalOnProperty(prefix = "spring.user", value = "enabled", havingValue = "true")
    public UserClient userClient(UserProperties userProperties) {
        return new UserClient(userProperties);
    }
}

6. Activate the configuration class. In other projects, if you want to activate configuration classes, there are two ways, one is through the spring.factories file, the other is through annotations, which are implemented separately below.

  • Through the spring.factories file

Create the META-INF directory under resources, create the spring.factories file below it, and declare that you automatically configure the path of the class UserAutoConfigure as follows

org.springframework.boot.autoconfigure.EnableAutoConfiguration=\
  com.anhe.springbootstarteruser.properties.UserAutoConfigure
  • Or through annotations, you can activate the configuration class simply by adding @EnableUserClient annotations to the main class without writing a spring.factories file. The annotations are defined as follows:

    The key is the @Import annotation, which also states the path of the automatic configuration class UserAutoConfigure

@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
@Import({UserAutoConfigure.class})
public @interface EnableUserClient {
}

7. Configure application.properties prompts. We prefer to see configuration information or default values when adding configuration. We can configure it as follows:

Create the file spring-configuration-metadata.json under META-INF as follows:

{
  "properties": [
    {
      "name": "spring.user.name",
      "defaultValue": "cxytinadi"
    },
    {
      "name": "spring.user.enabled",
      "type": "java.lang.Boolean",
      "defaultValue": false
    },
    {
      "name": "spring.user.age",
      "type": "java.lang.Integer",
      "defaultValue": 18
    }
  ]
}

Then prompts will automatically appear when other projects are configured, including the default values of the configuration.

8. Then enter in Terminal:

mvn clean install

Relevant jar packages are packaged into local warehouses and can be used directly by other local projects.

9.demo example:

Other projects introduce dependencies:

<dependency>
     <groupId>com.anhe</groupId>
     <artifactId>spring-boot-starter-user</artifactId>
     <version>0.0.1-SNAPSHOT</version>
</dependency>

application.properties add configuration

spring.user.age=20
spring.user.name=tystsyts
spring.user.enabled=true

If the configuration annotation is started directly, you need to add the @EnableUserClient annotation on the main class, and then write the controller validation in the new project:

@RestController
public class UserController {

    @Autowired
    private UserClient userClient;

    @GetMapping("/user")
    public Map<String,Object> getUserInfo() {
        Map<String, Object> map = new HashMap<>();
        map.put("name",userClient.getName());
        map.put("age",userClient.getAge());
        return map;
    }
}

Browsers access http://localhost:8080/user to get results

{
  "name": "tystsyts",
  "age": 20
}

Posted by Wabin on Thu, 18 Jul 2019 20:37:17 -0700