前言:有幸看到尚硅谷3月刚发布的 Spring Cloud 教学视频,使用了spring cloud最新版本和技术,该系列为看该教学视频记录的学习笔记。
视频地址:尚硅谷2020最新版SpringCloud(H版&alibaba)框架开发教程全套完整版从入门到精通(大牛讲授spring cloud)_哔哩哔哩 (゜-゜)つロ 干杯~-bilibili
微服务概述
微服务体系结构的思想提倡将大型软件拆分成一个个微小的服务,相对于面向服务软件架构(SOA)拆分粒度更小,最好是拆分成原子性服务,即不可以再继续拆分,服务之间的耦合度更低。不同于面向服务软件架构,微服务架构中没有企业服务总线,服务的调用流程不是在总线中固定顺序,取而代之的是一种 api 网关的方式统一编排微服务,api 网关不负责服务的调用顺序,只对客户端传来的请求进行路由,对众多的微服务接口进行聚合。
Spring Cloud
Spring Cloud 是一系列框架的有序集合。它利用 Spring Boot 的开发便利性巧妙地简化了分布式系统基础设施的开发,如服务发现注册、配置中心、消息总线、负载均衡、断路器、数据监控等,都可以用 Spring Boot 的开发风格做到一键启动和部署。Spring Cloud 并没有重复制造轮子,它只是将各家公司开发的比较成熟、经得起实际考验的服务框架组合起来,通过 Spring Boot 风格进行再封装屏蔽掉了复杂的配置和实现原理,最终给开发者留出了一套简单易懂、易部署和易维护的分布式系统开发工具包。
- 服务注册与发现 eureka->zookeeper/consul/nacos
- 服务调用与负载均衡 ribbon/loadbalancer feign/openfeign
- 服务熔断&&降级 hystrix -> resilience4j/spring alibaba sentinel
- 服务消息队列
- 配置中心管理 spring cloud config/nacos
- 服务网关 netflix oss zuul/spring cloud gateway
- 服务监控
- 全链路追踪
- 自动化构建部署
- 服务定时任务调度操作
版本说明
SpringBoot
SpringBoot:截至 2020/03/19,最新版本 2.2.5
SpringCloud
Spring Cloud 采用了英国伦敦地铁站的名称来命名,并由地铁站名称字母 A-Z 依次类推的形式来发布迭代版本。
SpringCloud 是一个由许多子项目组成的综合项目,各子项目有不同的发布节奏。为了管 SpringCloud 与各子项目的版本依赖关系,发布了一个清单,其中包括了某个 SpringCloud 版本对应的子项目版本。为了避免 SpringCloud 版本号与子项目版本号混淆,SpringCloud 版本采用了名称而非版本号的命名,这些版本的名字采用了伦敦地铁站的名字,根据字母表的顺序来对应版本时间顺序。例如 Angel 是第一个版本, Brixton 是第二个版本。
最新版本是 Hoxton。
SpringBoot 和 SpringCloud 的版本对应关系查看: https://start.spring.io/actuator/info
选用版本
框架/软件 | 版本 |
---|---|
spring cloud | Hoxton.SR1 |
spring boot | 2.2.2. RELEASE |
spring cloud alibaba | 2.1.0.RELEASE |
Java | Java8 |
Maven | 3.5 及以上 |
Mysql | 5.7 及以上 |
maven dependencyManagement
父 pom 通常会使用 dependencyManagement 管理子项目的版本号
<!--统一管理jar包版本-->
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
<junit.version>4.12</junit.version>
<log4j.version>1.2.17</log4j.version>
<lombok.version>1.16.18</lombok.version>
<mysql.version>8.0.19</mysql.version>
<druid.version>1.1.16</druid.version>
<druid.spring.boot.starter.version>1.1.10</druid.spring.boot.starter.version>
<spring.boot.version>2.2.2.RELEASE</spring.boot.version>
<spring.cloud.version>Hoxton.SR1</spring.cloud.version>
<spring.cloud.alibaba.version>2.1.0.RELEASE</spring.cloud.alibaba.version>
<mybatis.spring.boot.version>1.3.0</mybatis.spring.boot.version>
</properties>
<!--子模块继承后,提供作用:锁定版本+子module不用groupId和version-->
<dependencyManagement>
<dependencies>
<!--springboot 2.2.2-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>{spring.boot.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!--Spring cloud Hoxton.SR1-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>{spring.cloud.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!--Spring cloud alibaba 2.1.0.RELEASE-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-alibaba-dependencies</artifactId>
<version>{spring.cloud.alibaba.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>{mysql.version}</version>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid</artifactId>
<version>{druid.version}</version>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid-spring-boot-starter</artifactId>
<version>{druid.spring.boot.starter.version}</version>
</dependency>
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>{mybatis.spring.boot.version}</version>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>{lombok.version}</version>
</dependency>
</dependencies>
</dependencyManagement>
环境预搭建-订单模块
新建子模块cloud-provider-payment8001
pom
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!--监控-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid-spring-boot-starter</artifactId>
<!--如果没写版本,从父层面找,找到了就直接用,全局统一-->
<version>${druid.spring.boot.starter.version}</version>
</dependency>
<!--mysql-connector-java-->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
</dependency>
<!--jdbc-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
建表:
create database cloud2020;
use cloud2020;
CREATE TABLE `payment` (
`id` bigint(20) NOT NULL AUTO_INCREMENT COMMENT '主键',
`serial` varchar(200) CHARACTER SET utf8 COLLATE utf8_general_ci DEFAULT NULL COMMENT '支付流水号',
PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8 COLLATE = utf8_general_ci COMMENT = '支付表' ROW_FORMAT = Dynamic;
yaml配置
server:
port: 8001
spring:
application:
name: cloud-payment-service
datasource:
# 当前数据源操作类型
type: com.alibaba.druid.pool.DruidDataSource
# mysql驱动类
driver-class-name: com.mysql.cj.jdbc.Driver
url: jdbc:mysql://localhost:3306/cloud2020?useUnicode=true&characterEncoding=UTF-8&useSSL=false
username: root
password: 123456
mybatis:
mapperLocations: classpath*:mapper/*.xml
type-aliases-package: com.rhett.springcloud.entities
业务类
POJO
@Data
@AllArgsConstructor
@NoArgsConstructor
public class Payment implements Serializable {
private Long id;
private String serial;
}
统一数据响应实体类:
/**
* 与前端交互的统一数据响应接口
* @param <T>
*/
@Data
@AllArgsConstructor
@NoArgsConstructor
public class CommonResult<T> {
private Integer code;
private String message;
private T data;
public CommonResult(Integer code,String message){
this(code,message,null);
}
}
Dao
@Mapper
public interface PaymentDao {
public int create(Payment payment);
public Payment getPaymentById(@Param("id") Long id);
}
mapper文件:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.rhett.springcloud.dao.PaymentDao">
<insert id="create" parameterType="Payment" useGeneratedKeys="true" keyProperty="id">
insert into payment(serial) values(#{serial});
</insert>
<resultMap id="BaseResultMap" type="com.rhett.springcloud.entities.Payment">
<id column="id" property="id" jdbcType="BIGINT"/>
<id column="serial" property="serial" jdbcType="VARCHAR"/>
</resultMap>
<select id="getPaymentById" parameterType="Long" resultMap="BaseResultMap">
select * from payment where id=#{id};
</select>
</mapper>
service
接口:
public interface PaymentService {
public int create(Payment payment);
public Payment getPaymentById(Long id);
}
实现:
@Service
public class PaymentServiceImpl implements PaymentService {
@Resource
private PaymentDao paymentDao;
@Override
public int create(Payment payment) {
return paymentDao.create(payment);
}
@Override
public Payment getPaymentById(Long id) {
return paymentDao.getPaymentById(id);
}
}
controller
@RestController
@Slf4j
public class PaymentController {
@Resource
private PaymentService paymentService;
@PostMapping(value = "/payment")
public CommonResult create(Payment payment){
int result = paymentService.create(payment);
log.info("****插入结果:"+result);
if(result>0){
return new CommonResult(200,"插入数据库成功",result);
}else {
return new CommonResult(500,"插入数据库失败");
}
}
@GetMapping(value = "/payment/{id}")
public CommonResult<Payment> getPaymentById(@PathVariable("id") Long id){
Payment payment = paymentService.getPaymentById(id);
log.info("****插入结果:"+payment);
if(payment!=null){
return new CommonResult(200,"查询成功",payment);
}else {
return new CommonResult(500,"没有对应记录,查询ID:"+id);
}
}
}
热部署配置
添加依赖:
<!--热部署-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<scope>runtime</scope>
<optional>true</optional>
</dependency>
在IDEA设置=>Compiler,勾上如下图配置

快捷键CTRL+SHIFT+ALT+/
选择registry,勾上如下图配置

环境预搭建-消费者订单模块
将即将用到的模块中的公共业务类抽取到一个新的模块cloud-api-commons
,使用依赖引入:

新建模块cloud-consumer-order80
pom
<dependencies>
<dependency>
<groupId>com.rhett</groupId>
<artifactId>cloud-api-commons</artifactId>
<version>${project.version}</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!--监控-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
<!--热部署-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<scope>runtime</scope>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
yaml配置
server:
port: 80
配置类
@Configuration
public class ApplicationContextConfig {
@Bean
public RestTemplate getRestTemplate(){
return new RestTemplate();
}
}
controller
@RestController
public class OrderController {
public static final String PAYMENT_URL = "http://localhost:8001";
@Resource
private RestTemplate restTemplate;
@PostMapping("/consumer/payment")
public CommonResult<Payment> create(Payment payment){
return restTemplate.postForObject(PAYMENT_URL+"/payment", payment,CommonResult.class);
}
@GetMapping("/consumer/payment/{id}")
public CommonResult<Payment> getPayment(@PathVariable("id") Long id){
return restTemplate.getForObject(PAYMENT_URL+"/payment/"+id,CommonResult.class);
}
}
最后的项目结构:

这样一个简单的微服务模块就构建完成了,后面要学的eureka会基于该项目。
原创文章,作者:彭晨涛,如若转载,请注明出处:https://www.codetool.top/article/springcloud%e6%a6%82%e8%bf%b0%e5%92%8c%e5%ad%a6%e4%b9%a0%e9%a1%b9%e7%9b%ae%e9%a2%84%e6%90%ad%e5%bb%ba/