本文整理了微服务开发的核心技术栈,包含 SpringCloud、Nacos、Docker、MQ 等技术点。

📑 目录

  1. 认识微服务
  2. 微服务远程调用
  3. 注册中心
  4. 负载均衡
  5. 配置管理
  6. HTTP 客户端 Feign
  7. 统一网关 Gateway
  8. Docker 容器化
  9. 消息队列 MQ

认识微服务

什么是微服务

微服务是一种架构风格,将单体应用拆分为多个小型服务,每个服务独立运行、独立部署。

微服务架构

技术选型对比

技术对比

SpringCloud 生态

SpringCloud 是微服务解决方案,提供了一整套微服务技术组件。

SpringCloud

📌 版本注意:SpringCloud 与 SpringBoot 版本需要兼容

版本兼容


微服务远程调用

基于 RestTemplate

1. 注册 RestTemplate Bean

1
2
3
4
@Bean
public RestTemplate restTemplate() {
return new RestTemplate();
}

2. 服务远程调用

1
2
String url = "http://user-service/user/" + order.getUserId();
User user = restTemplate.getForObject(url, User.class);

注册中心

Eureka 注册中心

搭建 Eureka Server:

1
2
3
4
5
6
7
8
9
server:
port: 10086
spring:
application:
name: eurekaserver
eureka:
client:
service-url:
defaultZone: http://localhost:10086/eureka/

注册服务到 Eureka:

1
2
3
4
eureka:
client:
service-url:
defaultZone: http://localhost:10086/eureka/

Nacos 注册中心

服务注册到 Nacos:

1
2
3
4
spring:
cloud:
nacos:
server-addr: localhost:8848

负载均衡

Ribbon 负载均衡

Ribbon 是客户端负载均衡器,会拦截 RestTemplate 请求,根据负载策略分发请求。

Ribbon

Nacos 集群负载

根据集群进行负载均衡:

1
2
3
4
5
spring:
cloud:
nacos:
discovery:
cluster-name: SH # 集群名称

配置管理

Nacos 配置管理

统一配置管理:

1
2
3
4
5
6
spring:
cloud:
nacos:
config:
server-addr: localhost:8848
file-extension: yaml

配置热更新

方式一:使用 @RefreshScope

1
2
3
4
5
6
@RefreshScope
@RestController
public class UserController {
@Value("${pattern.dateformat}")
private String dateformat;
}

方式二:使用 @ConfigurationProperties

1
2
3
4
5
@ConfigurationProperties(prefix = "pattern")
@Data
public class PatternProperties {
private String dateformat;
}

HTTP 客户端 Feign

RestTemplate 问题

  • 代码可读性差
  • 参数 URL 复杂
  • 缺乏灵活

Feign 客户端使用

1. 引入依赖

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

2. 定义 Feign 接口

1
2
3
4
5
@FeignClient("user-service")
public interface UserClient {
@GetMapping("/user/{id}")
User findById(@PathVariable("id") Long id);
}

3. 启用 Feign

1
2
3
@EnableFeignClients
@SpringBootApplication
public class OrderApplication {}

Feign 配置

配置文件方式:

1
2
3
4
5
feign:
client:
config:
default:
loggerLevel: basic

Java 代码方式:

1
2
3
4
5
6
7
@Configuration
public class FeignConfig {
@Bean
public Logger.Level feignLoggerLevel() {
return Logger.Level.FULL;
}
}

统一网关 Gateway

为什么需要网关

  • 统一入口
  • 鉴权校验
  • 请求路由
  • 限流熔断

网关作用

搭建网关服务

1
2
3
4
5
6
7
8
9
10
11
12
13
14
server:
port: 10010
spring:
application:
name: gateway
cloud:
nacos:
server-addr: localhost:8848
gateway:
routes:
- id: user-service
uri: lb://user-service
predicates:
- Path=/user/**

路由断言工厂

断言 说明 示例
Path 路径匹配 - Path=/user/**
Method 请求方法 - Method=GET
Query 请求参数 - Query=username

过滤器

自定义全局过滤器:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
@Component
public class AuthorizeFilter implements GlobalFilter, Ordered {
@Override
public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {
// 1. 获取请求参数
String auth = exchange.getRequest().getQueryParams().getFirst("authorization");

// 2. 判断是否放行
if ("admin".equals(auth)) {
return chain.filter(exchange);
}

// 3. 拦截
exchange.getResponse().setStatusCode(HttpStatus.UNAUTHORIZED);
return exchange.getResponse().setComplete();
}

@Override
public int getOrder() {
return -1;
}
}

过滤器执行顺序:

  • 按 @Order 升序执行
  • Order 值越小,优先级越高

跨域配置

1
2
3
4
5
6
7
8
9
10
11
@Configuration
public class CorsConfig {
@Bean
public CorsWebFilter corsFilter() {
CorsConfiguration config = new CorsConfiguration();
config.addAllowedOrigin("*");
config.addAllowedMethod("*");
config.addAllowedHeader("*");
return new CorsWebFilter(config);
}
}

Docker 容器化

镜像操作命令

命令 说明
docker images 查看镜像
docker rmi <image> 删除镜像
docker pull <name> 拉取镜像
docker save -o file.tar image 导出镜像
docker load -i file.tar 导入镜像

容器命令

命令 说明
docker run -d -p 8080:80 nginx 创建并运行容器
docker ps 查看运行中的容器
docker logs -f <container> 查看日志
docker exec -it <container> bash 进入容器
docker stop/start/restart <container> 容器操作
docker rm <container> 删除容器

数据卷

1
2
3
4
5
# 创建数据卷
docker volume create mydata

# 挂载数据卷
docker run -v mydata:/data nginx

Dockerfile

1
2
3
4
5
FROM openjdk:8-jdk
WORKDIR /app
COPY jar/app.jar /app/app.jar
EXPOSE 8080
ENTRYPOINT ["java", "-jar", "/app/app.jar"]

消息队列 MQ

异步调用方案

消息队列是微服务间异步调用的常用方案,主要作用:

  • 削峰填谷:缓解高并发压力
  • 解耦:服务间无直接依赖
  • 异步:无需等待返回结果

MQ作用

常见 MQ 产品

产品 特点
RabbitMQ 功能丰富、社区活跃
RocketMQ 阿里开源、分布式
Kafka 大数据场景、高吞吐

📚 参考资源