SpringCloud study notes (b, SpringCloud Config)

table of Contents:

  • Configuration Center Introduction
  • SpringCloud Config server
  • SpringCloud Config Client
  • Dynamic configuration bean properties
  • Some supplement ( source code analysis ): Spring event monitoring, health check health (), highly available distributed configuration center

Configuration Center Introduction:

1. What is the distribution center

From the literal meaning, the configuration center is a public service manager configuration; it manages the system configuration of business-related content, when the system starts to load the data.

2, the benefits of using the configuration center

) Form a unified management configuration, you can more effectively maintain configuration

) So that privacy more secure configuration (Configuration not in the project, but in the distribution center, so that the production configuration is not visible)

)。。。。。。

SpringCloud Config server:

1, add maven dependence

1 <dependency>
2     <groupId>org.springframework.cloud</groupId>
3     <artifactId>spring-cloud-config-server</artifactId>
4 </dependency>

2, start the classes with the @EnableConfigServer comment

3, configuration properties

1 # Configuration Center instance name
 2 spring.application.name = config- Server
 . 3  # port
 . 4 the server.port = 9090
 . 5  
. 6  ## disposed remote repository
 . 7  # Git repository address
 . 8 spring.cloud.config.server.git.uri = HTTPS: // github.com/xxx/xxx 
. 9  # local backup
 10 spring.cloud.config.server.git.basedir = GIT- config
 . 11  
12 is  ## local repository (the distal end may not be read git, svn, etc., directly read local configuration)
 13 is # = spring.profiles.active native 
14 # spring.cloud.config.server. native .search-locations = File: // / E: / Config SpringCloud
15  
16  ## Actuator
 . 17  # closed security check
 18 is management.security.enabled = to false

 SpringCloud Client:

1, add maven dependence

1 <dependency>
2     <groupId>org.springframework.cloud</groupId>
3     <artifactId>spring-cloud-config-client</artifactId>
4 </dependency>

2、配置bootstrap.properties、application.properties

1 ## Config Server configuration information 
2 ## to configure the service center address 
3 spring.cloud.config.uri = HTTP: // localhost: 9090/ 
4 ## Environment of application client application name 
5 spring.cloud.config.name = Test  . 6 ## disposed spring.profiles.active  7 spring.cloud.config.profile = version (git / dev 8 ## configured svn branch) 9 spring.cloud.config.label = master
1 ## The client instance name 
2 spring.application.name = config- Server 
. 3 ## provided by the client port 
4 server.port = 8080

Dynamic refresh configuration:

First, we know SpringCloud Config divided into server and client, the server used to pull remote configuration , the client used to pull the server is configured to supply with use , the refresh process configuration should have the following:

1, the server configured to pull in a git (long data acquisition time will pull the distal end of data)

2, the client pull configuration of the server (by calling the public java.lang.Object org.springframework.cloud.endpoint.GenericPostableMvcEndpoint.invoke () method allows the client to obtain the latest configuration server)

3, the refresh bean (although at this time we will find that client data have been refreshed, but why do we configure the data or the old value it, because the spring has been injected into this bean, so we also need to refresh the bean: @RefreshScope)

 

Says here we'll have a question, is it every time we refresh method to configure the client will need to manually curl the invoke ()? ? ?

The answer is no, we can have many methods, here cited a simple timer (timer that what should enforce it, let's look further invoke () source code).

1, we see public java.lang.Object org.springframework.cloud.endpoint.GenericPostableMvcEndpoint.invoke () , that invoke invoke call the parent class, we look at the next invoke the parent class;

 1 @RequestMapping(method = RequestMethod.POST)
 2 @ResponseBody
 3 @Override
 4 public Object invoke() {
 5     if (!getDelegate().isEnabled()) {
 6         return new ResponseEntity<>(Collections.singletonMap(
 7                 "message", "This endpoint is disabled"), HttpStatus.NOT_FOUND);
 8     }
 9     return super.invoke();
10 }

2, the parent >>> Invoke public java.lang.Object org.springframework.boot.actuate.endpoint.mvc.EndpointMvcAdapter.invoke () call parent class Invoke;

1 @Override
2 @ActuatorGetMapping
3 @ResponseBody
4 public Object invoke() {
5     return super.invoke();
6 }

3, protected java.lang.Object org.springframework.boot.actuate.endpoint.mvc.AbstractEndpointMvcAdapter.invoke () call to invoke an object, and this object is passed in through the constructor; we look at the step by step construction method delegate is where he comes from

 1 private final E delegate;
 2 
 3 public AbstractEndpointMvcAdapter(E delegate) {
 4     Assert.notNull(delegate, "Delegate must not be null");
 5     this.delegate = delegate;
 6 }
 7 
 8 protected Object invoke() {
 9     if (!this.delegate.isEnabled()) {
10         // Shouldn't happen - shouldn't be registered when delegate's disabled
11         return getDisabledResponse();
12     }
13     return this.delegate.invoke();
14 }

 4, see step by step through the Internet, found to be the beginning of public java.lang.Object org.springframework.cloud.endpoint.GenericPostableMvcEndpoint , then take a look at where we have constructed the call GenericPostableMvcEndpoint

 

From the figure we can see that there are three calls, but because we are the refresh operation, we boldly guess is the first refreshMvcEndpoint, we go in and see the point.

Found that the parameters are org.springframework.cloud.endpoint.RefreshEndpoint , we look at how to achieve RefreshEndpoint.

 1 @ConfigurationProperties(prefix = "endpoints.refresh", ignoreUnknownFields = false)
 2 @ManagedResource
 3 public class RefreshEndpoint extends AbstractEndpoint<Collection<String>> {
 4 
 5     private ContextRefresher contextRefresher;
 6 
 7     public RefreshEndpoint(ContextRefresher contextRefresher) {
 8         super("refresh");
 9         this.contextRefresher = contextRefresher;
10     }
11 
12     @ManagedOperation
13     public String[] refresh() {
14         Set<String> keys = contextRefresher.refresh();
15         return keys.toArray(new String[keys.size()]);
16     }
17 
18     @Override
19     public Collection<String> invoke() {
20         return Arrays.asList(refresh());
21     }
22 
23 }

From which we can see that invoke methods RefreshEndpoint refresh of the original call, and Set <String> keys = contextRefresher.refresh ( ) function when the refresh is performed! ! ! !!! Σ (゚Д゚Techno) Techno

To sum up : our job calling Set <String> keys = contextRefresher.refresh ( ) code to refresh the configuration it! ! !

Spring Event listening mode:

Spring event listener mode of essence observer mode, which is divided into two classes

1、ApplicationListener(监听器)>>> public interface ApplicationListener<E extends ApplicationEvent> extends EventListener

2、ApplicationEvent(监听对象)>>> public abstract class ApplicationEvent extends EventObject

Health check health ():

Health check health, the main job is an interface for the operating mode of the current system for display, we can customize the system to check their health, it can also be used provided good.

If we are to achieve their health checks, it should be how to achieve it, we look at health () source code.

1, we can see that from the start the log health () interface is a call:

public java.lang.Object org.springframework.boot.actuate.endpoint.mvc.HealthMvcEndpoint.invoke(javax.servlet.http.HttpServletRequest,java.security.Principal)方法

Our roots go in and see

 1 @ActuatorGetMapping
 2 @ResponseBody
 3 public Object invoke(HttpServletRequest request, Principal principal) {
 4     if (!getDelegate().isEnabled()) {
 5         // Shouldn't happen because the request mapping should not be registered
 6         return getDisabledResponse();
 7     }
 8     Health health = getHealth(request, principal);
 9     HttpStatus status = getStatus(health);
10     if (status != null) {
11         return new ResponseEntity<Health>(health, status);
12     }
13     return health;
14 }

2, can be seen from the above code to invoke the main return line 8, we continue to follow up

1 private Health getHealth(HttpServletRequest request, Principal principal) {
2     Health currentHealth = getCurrentHealth();
3     if (exposeHealthDetails(request, principal)) {
4         return currentHealth;
5     }
6     return Health.status(currentHealth.getStatus()).build();
7 }

The same code is the main line 2, continue to follow up

 1 private Health getCurrentHealth() {
 2     long accessTime = System.currentTimeMillis();
 3     CachedHealth cached = this.cachedHealth;
 4     if (cached == null || cached.isStale(accessTime, getDelegate().getTimeToLive())) {
 5         Health health = getDelegate().invoke();
 6         this.cachedHealth = new CachedHealth(health, accessTime);
 7         return health;
 8     }
 9     return cached.getHealth();
10 }

3, it can be seen from line 5, the proxy class is org.springframework.boot.actuate.endpoint.mvc.AbstractEndpointMvcAdapter Invoke method !!! Σ (゚Д゚Techno) Techno

Then we look at AbstractEndpointMvcAdapter implemented

To be sure which implementation class is the second HealthMvcEndpoint

4, you can only see the invoke method HealthMvcEndpoint 1,10 ψ (* `ー ') ψ

1 @Override
2 public Health invoke() {
3     return this.healthIndicator.health();
4 }

This is very simple, only one line of code; you can continue to follow up after that healthIndicator is an interface, and then we found this interface is initialized in the constructor, we look at who the object is initialized

 1 public HealthEndpoint(HealthAggregator healthAggregator, Map<String, HealthIndicator> healthIndicators) {
 2     super("health", false);
 3     Assert.notNull(healthAggregator, "HealthAggregator must not be null");
 4     Assert.notNull(healthIndicators, "HealthIndicators must not be null");
 5     CompositeHealthIndicator healthIndicator = new CompositeHealthIndicator(
 6             healthAggregator);
 7     for (Map.Entry<String, HealthIndicator> entry : healthIndicators.entrySet()) {
 8         healthIndicator.addHealthIndicator(getKey(entry.getKey()), entry.getValue());
 9     }
10     this.healthIndicator = healthIndicator;
11 }

Ha, had healthIndicator is CompositeHealthIndicator healthIndicator = new new CompositeHealthIndicator (healthAggregator) ;

So this.healthIndicator.health () is CompositeHealthIndicator of health, and health Come take a look at the CompositeHealthIndicator

1 @Override
2 public Health health() {
3     Map<String, Health> healths = new LinkedHashMap<String, Health>();
4     for (Map.Entry<String, HealthIndicator> entry : this.indicators.entrySet()) {
5         healths.put(entry.getKey(), entry.getValue().health());
6     }
7     return this.healthAggregator.aggregate(healths);
8 }

5, we can see from the code of health is CompositeHealthIndicator from this.indicators out all HealthIndicator, and call their health () method

And HealthIndicator is an interface, so we can achieve HealthIndicator customize health Interface () health check

But in fact we do not need to go packed layer, springboot has achieved a org.springframework.boot.actuate.health.AbstractHealthIndicator , so we realize AbstractHealthIndicator , and will be able to override the method doHealthCheck

To sum up : if we are to realize their health checks, only need to rewrite AbstractHealthIndicator doHealthCheck method on it

1 public class MyHealthIndicator extends AbstractHealthIndicator {
2     @Override
3     protected void doHealthCheck(Health.Builder builder) throws Exception {
4         System.out.println("自定义健康检查 MyHealthIndicator");
5         builder.down().withDetail("This is MyHealthIndicator", "just so so!");
6     }
7 }

Note: You need to inject into a bean MyHealthIndicator oh (✪ω✪)

Highly available distributed configuration center:

1, the traditional model

The traditional model is more config server clusters and high availability through load balancer

2, the service mode: config server registered to eureka

Guess you like

Origin www.cnblogs.com/bzfsdr/p/11589902.html