SpringCloud之服务调用

3,539 阅读4分钟

简介

SpringCloud的服务调用有两个东西: Ribbon是一个客户端的负载均衡器,它提供对大量的HTTP和TCP客户端的访问控制。Feign也是用的Ribbon。

原理分析

ribbon实现的关键点是为ribbon定制的RestTemplate,ribbon利用了RestTemplate的拦截器机制,在拦截器中实现ribbon的负载均衡。负载均衡的基本实现就是利用applicationName从服务注册中心获取可用的服务地址列表,然后通过一定算法负载,决定使用哪一个服务地址来进行http调用。

详情可参考这篇文章 blog.csdn.net/qq_20597727…

使用

总体流程如下图:

服务提供者

注:这里需要有个服务注册与发现的注册中心,参考上一篇【SpringCloud之Eureka

创建一个服务提供者: 1.pom.xml文件

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
	<modelVersion>4.0.0</modelVersion>
	<parent>
		<groupId>cn.xbmchina</groupId>
		<artifactId>cloud-parent</artifactId>
		<version>1.0-SNAPSHOT</version>
		<relativePath/> <!-- lookup parent from repository -->
	</parent>

	<groupId>cn.xbmchina</groupId>
	<artifactId>cloud-eureka-client</artifactId>
	<version>0.0.1-SNAPSHOT</version>
	<name>cloud-eureka-client</name>
	<description>一个服务提供者</description>

	<properties>
		<java.version>1.8</java.version>
	</properties>
	<dependencies>
		<dependency>
			<groupId>org.springframework.cloud</groupId>
			<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
		</dependency>
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-web</artifactId>
		</dependency>
	</dependencies>

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

2.写接口提供给外部调用 这里用到@EnableEurekaClient注解,就是说将这个模块向eureka-server端注册,以便其他模块可以发现该服务。


@SpringBootApplication
@EnableEurekaClient
@RestController
public class CloudEurekaClientApplication {

	public static void main(String[] args) {
		SpringApplication.run(CloudEurekaClientApplication.class, args);
	}

	@Value("${server.port}")
	String port;

	@RequestMapping("/hi")
	public String home(@RequestParam(value = "name", defaultValue = "zero") String name) {
		return "hi " + name + " ,i am from port:" + port;
	}
}

3.配置文件连接到eureka服务端 注:application.name=cloud-eureka-client在下面的其他模块调用时是有用处的。

server:
  port: 8762

spring:
  application:
    name: cloud-eureka-client

eureka:
  client:
    serviceUrl:
      defaultZone: http://localhost:8761/eureka/
服务消费者

使用ribbon版

1.pom.xml文件,添加相关依赖

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
	<modelVersion>4.0.0</modelVersion>
	<parent>
		<groupId>cn.xbmchina</groupId>
		<artifactId>cloud-parent</artifactId>
		<version>1.0-SNAPSHOT</version>
		<relativePath/> <!-- lookup parent from repository -->
	</parent>
	<groupId>cn.xbmchina</groupId>
	<artifactId>cloud-service-ribbon</artifactId>
	<version>0.0.1-SNAPSHOT</version>
	<name>cloud-service-ribbon</name>
	<description>一个服务消费者</description>

	<properties>
		<java.version>1.8</java.version>
	</properties>

	<dependencies>
		<dependency>
			<groupId>org.springframework.cloud</groupId>
			<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
		</dependency>
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-web</artifactId>
		</dependency>
		<dependency>
			<groupId>org.springframework.cloud</groupId>
			<artifactId>spring-cloud-starter-netflix-ribbon</artifactId>
		</dependency>
		<dependency>
			<groupId>org.springframework.cloud</groupId>
			<artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
		</dependency>
	</dependencies>
</project>

2.利用RestTemplate 调用CLOUD-EUREKA-CLIENT上面定义的服务提供接口 注: @LoadBalanced :是为了负载均衡用的。就是说你如果有几台机都是同一接口的话,它会轮流的调用。

@SpringBootApplication
@EnableEurekaClient
@EnableDiscoveryClient
@EnableHystrix
@RestController
public class CloudServiceRibbonApplication {

	public static void main(String[] args) {
		SpringApplication.run(CloudServiceRibbonApplication.class, args);
	}


	@Bean
	@LoadBalanced  //负载均衡
	RestTemplate restTemplate() {
		return new RestTemplate();
	}

	@Autowired
	RestTemplate restTemplate;
	
	@GetMapping(value = "/hi")
	public String hi(@RequestParam String name) {
		return restTemplate.getForObject("http://CLOUD-EUREKA-CLIENT/hi?name="+name,String.class);
	}
}

3.配置文件连接到eureka服务端 注:application.name=cloud-eureka-client在下面的其他模块调用时是有用处的。

eureka:
  client:
    serviceUrl:
      defaultZone: http://localhost:8761/eureka/
server:
  port: 8764
spring:
  application:
    name: cloud-service-ribbon

使用Feign版 其实原理跟ribbon没啥差异,与上面不同的地方:

  • 它是用接口来弄的
  • 使用注解@EnableFeignClients

1.pom.xml 依赖

	<dependencies>
		<dependency>
			<groupId>org.springframework.cloud</groupId>
			<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
		</dependency>
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-web</artifactId>
		</dependency>
		<dependency>
			<groupId>org.springframework.cloud</groupId>
			<artifactId>spring-cloud-starter-openfeign</artifactId>
		</dependency>
	</dependencies>

2.在启动类中加入@EnableFeignClients注解

@SpringBootApplication
@EnableEurekaClient
@EnableDiscoveryClient
@EnableFeignClients
public class CloudServiceFeginApplication {
	public static void main(String[] args) {
		SpringApplication.run(CloudServiceFeginApplication.class, args);
	}
}

3.调用服务 注:这个是接口;@FeignClient中的值是服务端的名称。

@FeignClient(value = "cloud-eureka-client")
public interface TestService {

    @RequestMapping(value = "/hi",method = RequestMethod.GET)
    String helloworld(@RequestParam(value = "name") String name);

}

源码参考GitHub: github.com/xbmchina/cl…

总结

服务调用类似于用一个浏览器去调用服务器的接口然后接收或传递数据进行下一步的处理,不过这里是可以相互调用。 场景: 比如很多的电商网站有订单模块,仓库模块,支付模块等之间的相互调用。例如:生成订单,然后仓库模块减少,然后支付模块收到钱,接着通知仓库模块安排配送等。

用SpringCloud的分开各个模块,各负其职,这就是微服务的意义之一。

最后

如果对 Java、大数据感兴趣请长按二维码关注一波,我会努力带给你们价值。觉得对你哪怕有一丁点帮助的请帮忙点个赞或者转发哦。