Spring Cloud Netflix overview and architecture design

Source: Internet
Author: User
Tags java web

About Spring Cloud
Spring Cloud is a complete framework for implementing microservices based on spring boot. He provides components such as configuration management, service discovery, circuit breakers, intelligent routing, micro-proxies, control buses, global locks, decision-making campaigns, distributed sessions, and cluster state management required for micro-service development. Most importantly, working with the Spring boot framework will make it very convenient for you to develop a cloud service for your microservices architecture.
Spring cloud contains a very large number of sub-frameworks, of which spring cloud Netflix is a framework that was developed by Netflix and later incorporated into the Spring Cloud family, which mainly provides modules such as service discovery, circuit breakers and monitoring, intelligent routing, Client load balancing, and so on.
The spring cloud Netflix project is not long enough to be incorporated into the spring cloud family or 2 years ago, so there are fewer documents to use, in addition to official documentation, there are some Chinese communities in the country. However, if you are just beginning to touch this and want to use it to build a micro-service application architecture, there will always be a sense of how to start. Therefore, this article is to look at the overall framework of the various components, what is the use of, how to interact. Finally, the actual experience, introduce the possible problems, as well as some problems, the use of what kind of solution.
Micro-Service Architecture
First, let's look at the features or usage scenarios that a generic microservices architecture requires:
We split the entire system into several subsystems based on the business.
Each subsystem can deploy multiple applications, using load balancing across multiple applications.
A service registry is required, all services are registered in the registry, and load balancing is achieved by using a certain policy through the services registered in the registry.
All clients access the backend service through the same gateway address, and through the routing configuration, the gateway determines which service the URL request is handled by. Load balancing is also used when the request is forwarded to the service.
Services sometimes also require mutual access. For example, there is a user module, the other services in the processing of some business, to obtain user data of customer service.
A circuit breaker is required to handle time-outs and errors in the service invocation in a timely manner, preventing the overall system from being paralysed by one of the service's problems.
A monitoring function is also required to monitor the time spent on each service invocation.
Spring Cloud Netflix components and deployment
The Spring Cloud Netflix framework just meets all of the above requirements, and most importantly, it's very simple to use. The components that Spring Cloud Netflix contains and its main features are as follows:
Eureka, service registration and discovery, it provides a service registry, service discovery client, and a convenient interface for viewing all registered services. All services use Eureka's Service discovery client to register themselves with the Eureka server.
Zuul, gateways, all clients request access to the backend services through this gateway. He can use a certain routing configuration to determine which service a URL is handled by. and obtain the registered service from Eureka to forward the request.
Ribbon, load Balancing, when a Zuul gateway sends a request to an application of a service, if a service launches multiple instances, it is sent to a service instance through the Ribbon through a certain load balancing policy.
Feign, service clients, and services can use Resttemplate or feign client access if they need to access each other. It uses the Ribbon by default to achieve load balancing.
Hystrix, monitoring and circuit breakers. We only need to add the hystrix tag on the service interface, we can realize the monitoring of this interface and the circuit breaker function.
Hystrix Dashboard, monitoring panel, he provides an interface to monitor the time spent by service calls on various services.
Turbine, monitoring aggregation, using hystrix monitoring, we need to open the monitoring information for each service instance to view. Turbine can help us aggregate the monitoring information of all service instances into one place and view them uniformly. So you do not need to open a page by view.
Here is the group architecture diagram for the service architecture implemented using the sub-framework described above:
Https://img.mukewang.com/5b2b79110001d64a14501090.jpg

In, there are several places to be explained: Br/>zuul network Sekiya registered in the registry, it also as a service to unified view.
Load balancing is not a standalone component that runs on gateways, service invocations, and so on, and whenever a service needs to be accessed, the Ribbon is used to get an instance of the service removed. The ribbon obtains a list of services and instances from the Eureka registry, rather than from the registry when each request is sent.
We can use Resttemplate for inter-service calls, or we can configure Feignclient to use, regardless of the way, the Ribbon load balancer is used by default as long as the service registration is used. (Resttemplate need to add @loadbalanced)

Viewing the monitoring information is to enter the monitoring url:http://serviceip:port/hystrix.stream of the service on the Hystrix dashboard, you can view the running monitoring information graphically.
If you want to aggregate the monitoring information for all services together, you need to use turbine to aggregate the monitoring information for the services you need.
We can also see how the architecture is deployed:
Deploy a single gateway application independently
The service registry and monitoring can be configured in one application or 2 applications.
Service registries can also be deployed with multiple, differentiated by zone zones to achieve high availability.
Each service deploys one or more instances, depending on the load and the need for high availability.

Spring Cloud Netflix Component development
As mentioned above, the development of the spring Cloud Netflix-based microservices is very simple, generally we are working with spring boot, if you want to use in your original Java Web application can also be added by the relevant configuration to practice. Here, just look at the service registration and Monitoring module development, as well as the development of service calls, others can directly refer to the above series of articles.
Development of registration and monitoring Center
This is very simple, just one of the following classes:
1
2
3
4
5
6
7
8 @SpringBootApplicationbr/> @EnableEurekaServer
public class Applicationregistry {
public static void Main (string[] args) {
New Springapplicationbuilder (Application.class). Web (True). Run (args);
}
}
The @springbootapplication of the spring boot tag here illustrates that the current application is a spring boot application. This allows me to start the application directly in the IDE using the main function, or it can be packaged and started with the command line. Of course, you can also start a packaged war package with a server such as Tomcat. Br/> using the label @enableeurekaserver, you can start the components of the Eureka Service registry during the boot process. It listens on a port, which is 8761 by default, to receive service registration. and provide a Web page, open later, you can see the registered services.
Of course, in order to use the above components, we need to add the corresponding dependencies in the Maven Pom file, such as using Spring-boot-starter-parent, Rely on Spring-cloud-starter-eureka-server and Spring-cloud-starter-hystrix-dashboard.
Inter-service Call
In the various documents on the Internet, there is no clear explanation of the call between services, so here is a special explanation of how this is developed.
There are two ways to make service calls, Resttemplate and feignclient. Whatever the way, he is invoking the service's HTTP interface through the rest interface, and the parameters and results are serialized and deserialized by Jackson by default. Because of the interface defined by spring MVC's Restcontroller, the returned data is serialized into JSON data via Jackson.
Resttemplate
In this way, you only need to define a resttemplate bean and set it to loadbalanced:
1
2
3
4
5
6
7
8 @Configuration
public class Somecloudconfiguration {br/> @LoadBalanced
Resttemplate Resttemplate () {
return new Resttemplate ();
}
}
So we can inject this bean into the place where we need it:
1
2
3
4
5
6
7
8
9 public class Someserviceclass {br/> @Autowired

Public String Getuserbyid (Long userId) {
Userdto results = resttemplate.getforobject ("http://users/getUserDetail/" + userId, Userdto.class);
return results;
}
}

Where users are the service Id,ribbon will get an instance of the service from the list of service instances, send the request, and get the results. The object userdto requires a serial number, and its inverse sequence number is automatically completed.
Feignclient
In addition to the above method, we can also use feignclient. Or look directly at the code:
1
2
3
4
5
6
7 @FeignClient (value = "users", Path = "/users")
Public interface Usercompositeservice {
@RequestMapping (value = "/getuserdetail/{id}",
method = Requestmethod.get,
produces = Mediatype.application_json_value)
userdto Getuserbyid (@PathVariable Long ID);
}

We only need to use @feignclient to define an excuse, and Spring Cloud feign will help us build an implementation of it to get the data from the appropriate users service.
Where value in the @FeignClient (value = "users", Path = "/users/getuserdetail") is the service Id,path is the path prefix for this set of interfaces.
In the following method definition, it is like setting up Spring MVC interface, for this method, it corresponds to the URL is/users/getuserdetail/{id}.
Then, when it is used, it is injected into the same way as a generic service:
1
2
3
4
5
6
7
8
9 public class Someotherserviceclass {br/> @Autowired

public void dosomething () {
// .....
Userdto results = Userservice.getuserbyid (userId);
Other operation ...
}
}

Problems encountered
Because the spring cloud has less documentation, the architecture of the microservices is relatively complex, and there are a number of problems to be encountered in the development, some of which is how to better use the framework to build the architecture, and some of the problems are how to configure them. Here are some of the things I have to offer when building a microservices architecture.
Request Timeout Issue
The default timeout for the Zuul gateway is very short, in order to ensure that the service can be quickly responded to when it is invoked. However, we will have some business methods that run longer, especially on test servers. At this time, you need to adjust the timeout. There are several places for this timeout:
Load balancer Ribbon, Load balancer has a timeout setting, including link time and read time
The Hystrix circuit Breaker also has a timeout setting that needs to be returned at the appropriate time, rather than waiting on a request.
The corresponding configuration is as follows:

1
2
3 Hystrix.command.default.execution.isolation.thread.timeoutInMilliseconds = 30000
Ribbon. ReadTimeout = 30000
Ribbon. ConnectTimeout = 15000
Problem with Service ID
The ID of the service, which is the service name, can be set by APPLICATION.YML or bootstrap.yml:
1 spring.application.name = Users

Problems with managing paths
The Spring boot app defaults to open some managed interfaces, such as the/info,/health, and metrics monitored interface/metrics. If you use the default path, there is no problem using hystrix monitoring, the service Registry's listening service status, but if you want to use a different path, such as/management/info,/management/health, there are a lot of things involved, and, Each version may have some more or less problems, causing you to encounter a different problem. The problems I have encountered are:
Registered successfully but could not find the service
First, the registration succeeds, and you can see the individual services on the Eureka Server page. However, when you call through the gateway, you are always prompted that the service cannot be found. At this point it may be necessary to configure the following in the application.yml of each service:
1
2
3
4
5
6 Eureka:
Instance
Nonsecureport: ${server.port}
AppName: ${spring.application.name}
Statuspageurlpath: ${management.context-path}/info
Healthcheckurlpath: ${management.context-path}/health

To put it simply, this is to tell the Eureka server when registering, what the port of the service is, and what the path is to listen to the state. This is because we use a different management interface path, and the Eureka server does not use the corresponding path.
If everything works, you can click on a registered service on the Eureka server and you should be able to open an info page. He may be blank, but at least the Eureka server can know that the service is functioning properly through this.
This issue is not available in all versions, but only in some spring cloud versions.
Hystrix monitoring with managed paths set
Just said the Hystrix monitoring path is Http://serviceIp:port/hystrix.stream, if you set the path of the management interface, then this monitoring path will also become:
1 Http://serviceip:port/${management.context-path}/hystrix.stream
If you want to use turbine aggregation again, turbine will not be found because it defaults to the server address and port on the Eureka server and adds/hystrix.stream later. At this point, you will need to set turbine:
1
2
3
4
5
6 Turbine:
Aggregator:
Clusterconfig:user
Appconfig:user
Instanceurlsuffix:
USER:/user/hystrix.stream

Managing the security of a path
For micro-service deployment of several machines, you can open a firewall to control who can access the management interface, but, even so, for security, and so on, I generally will also use the management side interface with spring security to protect. As a result, the monitoring interface cannot be accessed directly.
Permission validation for inter-service calls
In general, our API interface requires some kind of authorization to access, after the successful login, and then through tokens or cookies and other means to invoke the interface.
With the spring Cloud netfix Framework, when logging in, the login request is forwarded to the appropriate user service, and after successful landing, a cookie or header token will be set. The client then requests the verification information from the Zuul gateway to the appropriate service.
When the Zuul gateway forwards the request to the backend service, it will send some headers to the server by default, such as: Cookie, Set-cookie, Authorization. In this way, the related headers of the client request can be passed to the server, and the cookie set by the server can also be uploaded to the client.
However, if you want to prohibit certain headers from being transmitted to the server, you can disable it in the APPLICATION.YML configuration of the Zuul gateway in the following way:
1
2
3
4
5
6 Zuul:
Routes
Users
Path:/users/**
Sensitiveheaders:cookie,set-cookie,authorization
Serviceid:user
That is, set sensitiveheaders.
Just said that one of our services sometimes needs to invoke another service, when this request is not initiated by the client, and the header of his request will not have any authentication information. In this case, there are two ways to do this:
Through the firewall and other settings, to ensure that the interface between service calls, only a few address access;
Set a generic token, placed in the header, which has permission to invoke all of the interface calls between the services.
Set the token for the real user of the request in some way, and put it in the authentication header.
For the latter two ways, you need to get the token in some way and put it in the header. If you call using Resttemplate, you can add an options with a header in the request.
It can also be set by the following interceptor, which can work on both the Resttemplate and feignclient ways:
1
2
3
4
5
6
7
8
9
Ten @Bean
Public Requestinterceptor Requestinterceptor () {
return new Requestinterceptor () {br/> @Override
String AuthToken = GetToken ();
Template.header (Auth_token_header, AuthToken);
}
};
}
At the same time, if you want to get the real IP of the request in a service, (because the request is forwarded through the gateway, you get the IP directly via request is the IP of the gateway), you can get it from headerx-forwarded-host. If you want to disable this header, you can also:
1 zuul.addproxyheaders = False

These are the basic use and architectural design of the spring cloud Netflix framework. Of course, as your microservices system gets more complex, you'll need a lot of other spring cloud components and other technologies. But if you understand the basics and use of the spring cloud framework, it's easier to look at other things.

Spring Cloud Netflix overview and architecture design

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.