preface

Spring is the unofficial standard framework in the Java world, and any middleware that wants to thrive must support Spring’s various features, namely, seamlessly integrate into Spring.

Apollo serves as a distributed configuration center for Java applications, which can obtain remote configuration information through the Client provided by Apollo. How do you integrate this Client into the user’s application?

This requires an extension to the interface Spring provides us.

In previous articles, I’ve talked about some of Spring’s extension interfaces: The Spring extension interface is a must-know for an in-depth understanding of Spring’s advanced development.

To integrate into Spring, you first have to find the entry point and then register the relevant classes for your own system initialization. So how to find and deal with portals has become a science, and we’re going to look at how Apollo did that today.

The first entry: XML

XML is a configuration file for traditional Java projects, especially Spring MVC projects. Although automated configurations are now used, there are still legacy projects that use XML, so XML support is a must for most middleware.

Supporting XML requires adherence to several Spring conventions:

  1. inheritanceNamespaceHandlerSupportAn abstract class, rewrite the init method, call registerBeanDefinitionParser method, and to his inheritanceAbstractSingleBeanDefinitionParserThe subclass parses the tag, overrides its getBeanClass method, and returns a Bean that is used to register the associated Bean.
  2. Create a meta-INF directory on the classpathspring.handlersFile to point to the URL in the XML configurationNamespaceHandlerSupport.
  3. Create a file in the meta-INF directoryApollo - 1.0.0. XSDXSD file, used to interpret custom tags.
  4. In the meta-INF directory, continue the creationspring.schemasFile to point the XSD URL in the XML configuration to the XSD file.

Handlers will find the NamespaceHandlerSupport class in Spring based on the URL in the XML and parse the tag. You also get a setup bean from getBeanClass, in which the Apollo key class is registered.

The second entry: @import annotations

Java-based configuration is currently the popular alternative to XML-based configuration.

How to use @import annotations:

  1. Define a startup annotation of your own. With an @import annotation, which is essentially an import tag in XML, you can configure a class, and that class will be registered in the Spring container as a Bean, and you can work with that Bean. In Apollo, it is used as follows:
@Retention(RetentionPolicy.RUNTIME) @Target(ElementType.TYPE) @Documented
@Import(ApolloConfigRegistrar.class)
public @interface EnableApolloConfig {
  String[] value() default {ConfigConsts.NAMESPACE_APPLICATION};
  int order(a) default Ordered.LOWEST_PRECEDENCE;
}
Copy the code
  1. The ApolloConfigRegistrar class is the bean registered with Apollo. This bean is used to handle the @enableApolloConfig annotation and register the Apollo key bean into the Spring container.

  2. Users can use Apollo functionality via Spring (automatic updates, annotations, etc.) simply by annotating @enableApolloConfig on a class in the Spring system.

Third entry: SpringBoot Starter

Currently the most popular framework is SpringBoot, compatibility with SpringBoot is a big trend.

Spring Boot provides Spring-boot-Autoconfigure to make third-party frameworks compatible with Boot, called starter.

Creating a starter follows several conventions:

  1. Maven is introduced intospring-boot-autoconfigure artifact.
  2. Create a class to implementApplicationContextInitializerInterface to override the Initialize method, which is called when the container is initialized.
  3. Meta-inf createdspring.factoriesThe file is scanned automatically when Boot starts. You need to write a class created in Step 2 to this file, similarorg.springframework.context.ApplicationContextInitializer=\com.ctrip.framework.apollo.spring.boot.ApolloApplicationConte xtInitializer. The purpose of this class is to load key configurations into the Spring environment ahead of time (before container initialization).
  4. inspring.factoriesIn the file, you also need to get boot’sEnableAutoConfigurationThe auto-configuration class points to a custom class.This is the key to SpringBoot starter, such as:org.springframework.boot.autoconfigure.EnableAutoConfiguration=com.ctrip.framework.apollo.spring.boot.ApolloAutoConfigur ation. ApolloAutoConfiguration will be added to Apollo’s configuration bean. In this configuration bean, you can create a key bean that handles system-specific initialization classes. Apollo, for example:
@Configuration
@ConditionalOnProperty(PropertySourcesConstants.APOLLO_BOOTSTRAP_ENABLED)
@ConditionalOnMissingBean(PropertySourcesProcessor.class)// When the Bean does not exist in the Spring Context
public class ApolloAutoConfiguration {
  @Bean
  public ConfigPropertySourcesProcessor configPropertySourcesProcessor(a) {
    return newConfigPropertySourcesProcessor(); }}Copy the code

In the Apollo ConfigPropertySourcesProcessor key of the bean is used to register system.

conclusion

This article highlights three entry points:

  1. System key beans are returned in the getBeanClass method.
  2. @import annotations by defining beans in annotations and then processing them in that Bean.
  3. Through the SpringBoot Starter modespring.factoriesAutomatic configuration classes are defined in the file that can register system critical beans.

In future development, if you want to integrate with Spring, you can do it yourself in these three ways.