第九章 微服务项目的整合和测试
9.1 微服务项目整合
9.1.1 微服务项目结构预览
9.1.2 微服务项目功能介绍
1.microservice-eureka-server(Eureka注册中心)
文件9-1 application.yml
spring:
application:
name: eureka-server # 指定应用名称
server:
port: 8761
eureka:
client:
register-with-eureka: false
fetch-registry: false
service-url:
# defaultZone: http://localhost:${server.port}/eureka/
# 上线测试需要使用以下配置
defaultZone: http://eureka-server:${server.port}/eureka/
2.microservice-gateway-zuul(Zuul API 网关)
文件9-2 application.yml
spring:
application:
name: gateway-zuul # 指定应用名称
# cloud:
# inetutils:
# preferred-networks:
# - 10.0 # 设置注册到Eureka中心的优选服务地址
server:
port: 8050
eureka:
# instance:
# prefer-ip-address: true #优选通过IP地址找到对应的服务名称
client:
#配置eureka注册中心地址
serviceUrl:
defaultZone: http://localhost:8761/eureka/
# 上线测试需要使用以下配置
# defaultZone: http://eureka-server:8761/eureka/
#设置Hystrix熔断器判定超时时间
#hystrix:
# command:
# default:
# execution:
# isolation:
# thread:
# timeoutInMilliseconds: 60000
zuul:
ignoredServices: '*'
routes:
user-service:
path: /user-service/**
serviceId: user-service
order-service:
path: /order-service/**
serviceId: order-service
3.microservice-orderservice(订单管理微服务)
文件9-3 application.yml ·
#DB Configuration
spring:
datasource:
driver-class-name: com.mysql.jdbc.Driver
url: jdbc:mysql://localhost:3306/microservice_mallmanagement
# 与Docker整合时可使用以下配置(也可以使用具体的ip+端口)
# url: jdbc:mysql://mysql:3306/microservice_mallmanagement
username: root
password: 123456
application:
name: order-service # 指定应用名称
# cloud:
# inetutils:
# preferred-networks:
# - 10.0 # 设置注册到Eureka中心的优选服务地址
server:
port: 7900 # 指定该Eureka实例的端口号
eureka:
# instance:
# prefer-ip-address: true #优选通过IP地址找到对应的服务名称
client:
service-url:
defaultZone: http://localhost:8761/eureka/ #配置eureka注册中心地址
# 上线测试需要使用以下配置
# defaultZone: http://eureka-server:8761/eureka/
文件9-4OrderController.java
package com.itheima.controller;
import com.itheima.mapper.OrderMapper;
import com.itheima.po.Order;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixCommand;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.util.ArrayList;
import java.util.List;
@RestController
@RequestMapping("/order")
public class OrderController {
@Autowired
private OrderMapper orderMapper;
@GetMapping(path="/findOrders/{userid}")
@HystrixCommand(fallbackMethod = "findOrderfallback") //断路器
public List<Order> findOrder(@PathVariable("userid") Integer userid) {
List<Order> orders= this.orderMapper.selectOrder(userid);
return orders;
}
//针对上面断路器发现的问题编写回调方法(参数和返回值要一样)
public List<Order> findOrderfallback(Integer userid) {
List<Order> orders =new ArrayList<>();
return orders;
}
}
4.microservice-userservice(用户管理微服务)
文件9-5 application.yml ·
#DB Configuration
spring:
datasource:
driver-class-name: com.mysql.jdbc.Driver
url: jdbc:mysql://localhost:3306/microservice_mallmanagement
# 与Docker整合时可使用以下配置(也可以使用具体的ip+端口)
# url: jdbc:mysql://mysql:3306/microservice_mallmanagement
username: root
password: 123456
application:
name: user-service # 指定应用名称
# cloud:
# inetutils:
# preferred-networks:
# - 10.0 # 设置注册到Eureka中心的优选服务地址
server:
port: 8030 # 指定该Eureka实例的端口号
eureka:
# instance:
# prefer-ip-address: true #优选通过IP地址找到对应的服务名称
client:
service-url:
defaultZone: http://localhost:8761/eureka/ #配置eureka注册中心地址
# 上线测试需要使用以下配置
# defaultZone: http://eureka-server:8761/eureka/
#客户端动态访问常量配置
ORDERSERVICEURL: http://order-service/
文件9-6 UserController.java
package com.itheima.controller;
import com.itheima.mapper.UserMapper;
import com.itheima.po.Order;
import com.itheima.po.User;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.core.ParameterizedTypeReference;
import org.springframework.http.HttpMethod;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.client.RestTemplate;
import java.util.List;
@RestController
@RequestMapping("/user")
public class UserController {
@Autowired
private RestTemplate restTemplate;
@Autowired
private UserMapper userMapper;
@Value("${ORDERSERVICEURL}")
private String ORDERSERVICEURL;
@GetMapping(path="/findOrders/{username}")
public List<Order> getOrderByUsername(@PathVariable("username")
String username) {
User user = this.userMapper.selectUser(username);
//使用Ribbon后,可以使用http://order-service/而不用使用ip+端口
ResponseEntity<List<Order>> rateResponse =
restTemplate.exchange(ORDERSERVICEURL
+"/order/findOrders/"+user.getId(),
HttpMethod.GET, null,
new ParameterizedTypeReference<List<Order>>(){});
List<Order> orders = rateResponse.getBody();
return orders;
}
}
微服务项目的启动和测试
文件9-7 microservice_mallmanagement.sql
CREATE DATABASE microservice_mallmanagement;
USE microservice_mallmanagement;
DROP TABLE IF EXISTS tb_order
;
CREATE TABLE tb_order
(
id
int(11) NOT NULL AUTO_INCREMENT,
createtime
datetime DEFAULT NULL,
number
varchar(255) DEFAULT NULL,
userid
int(11) DEFAULT NULL,
PRIMARY KEY (id
)
) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=UTF8;
INSERT INTO tb_order
VALUES (‘1’, ‘2017-10-09 10:15:44’, ‘201709181459001’, ‘1’);
INSERT INTO tb_order
VALUES (‘2’, ‘2017-10-24 18:22:12’, ‘201709181459008’, ‘1’);
DROP TABLE IF EXISTS tb_user
;
CREATE TABLE tb_user
(
id
int(11) NOT NULL AUTO_INCREMENT,
address
varchar(255) DEFAULT NULL,
username
varchar(255) DEFAULT NULL,
PRIMARY KEY (id
)
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=UTF8;
INSERT INTO tb_user
VALUES (‘1’, ‘beijing’, ‘shitou’);
(1)测试接口方法
(2)测试API网关服务
9.2接口可视化工具-Swagger-UI
Swagger-UI使用方法
1.下载Swagger-UI项目
https://github.com/swagger-api/swagger-ui
2.引入Swagger-UI
3.加入Swagger依赖
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-swagger-ui</artifactId>
<version>2.2.2</version>
</dependency>
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-swagger2</artifactId>
<version>2.2.2</version>
</dependency>
4.编写配置类
package com.itheima.config;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.http.ResponseEntity;
import org.springframework.util.StopWatch;
import springfox.documentation.service.ApiInfo;
import springfox.documentation.spi.DocumentationType;
import springfox.documentation.spring.web.plugins.Docket;
import springfox.documentation.swagger2.annotations.EnableSwagger2;
import java.util.Date;
import static springfox.documentation.builders.PathSelectors.regex;
@Configuration
@EnableSwagger2
public class SwaggerConfiguration {
//定义API接口映射路径
public static final String DEFAULT_INCLUDE_PATTERN = "/user/.*";
private final Logger log =
LoggerFactory.getLogger(SwaggerConfiguration.class);
@Bean
public Docket swaggerSpringfoxDocket() {
log.debug("Starting Swagger");
StopWatch watch = new StopWatch();
watch.start();
//用于生成对应API接口文档的描述信息,可省略
ApiInfo apiInfo = new ApiInfo("用户管理API接口测试文档","description",
"termsOfServiceUrl","contact","version","","");
Docket docket = new Docket(DocumentationType.SWAGGER_2)
.apiInfo(apiInfo)
.genericModelSubstitutes(ResponseEntity.class)
.forCodeGeneration(true)
.genericModelSubstitutes(ResponseEntity.class)
.directModelSubstitute(java.time.LocalDate.class, String.class)
.directModelSubstitute(java.time.ZonedDateTime.class, Date.class)
.directModelSubstitute(java.time.LocalDateTime.class, Date.class)
.select()
.paths(regex(DEFAULT_INCLUDE_PATTERN))//匹配路径生成对应接口文档
.build();
watch.stop();
log.debug("Started Swagger in {} ms", watch.getTotalTimeMillis());
return docket;
}
}
9.2 Swagger-UI使用测试
1.整合测试
2.接口测试
订单管理API接口测试文档
用户管理API接口测试文档
接口测试结果
本章小结
本章主要讲解了微服务项目的整合以及接口测试。通过本章的学习,读者可以对微服务项目的使用有进一步的认识,熟悉Spring Boot 和Spring Cloud相关组件的整合开发,同时还可以掌握接口测试工具Swagger-UI的简单使用。