一、什么是单体架构
在软件设计的时候经常提到和使用经典的3层模型,即表现层,业务逻辑层,数据访问层。虽然在软件设计中划分了3层模型,但是对业务场景没有划分,一个典型的单体架构就是将所有的业务场景的表现层,业务逻辑层,数据访问层放在一个工程中最终经过编译,打包,部署在一台服务器上。此时服务架构如图:
二、什么是分布式架构
分布式:重在协同工作
分布式服务顾名思义服务是分散部署在不同的机器上的,一个服务可能负责几个功能,是一种面向SOA架构的,服务之间也是通过rpc来交互或者是webservice来交互的。逻辑架构设计完后就该做物理架构设计,系统应用部署在超过一台服务器或虚拟机上,且各分开部署的部分彼此通过各种通讯协议交互信息,就可算作分布式部署,生产环境下的微服务肯定是分布式部署的,分布式部署的应用不一定是微服务架构的,比如集群部署,它是把相同应用复制到不同服务器上,但是逻辑功能上还是单体应用。
三、什么是微服务架构
如果用户量只有几百人的小应用,单体应用就能搞定,即所有应用部署在一个应用服务器里,如果是很大用户量,且某些功能会被频繁访问,或者某些功能计算量很大,建议将应用拆解为多个子系统,各个子系统配置不同数量的集群,每个系统都叫做一个服务,当一个子系统有3个集群时我们也说该服务有3个实例,各自负责各自功能并拥有独立的数据库与缓存,这就是微服务架构。
微服务相比分布式服务来说,它的粒度更小,服务之间耦合度更低,拥有更加独立的数据源,由于每个微服务都由独立的小团队负责,因此它敏捷性更高,分布式服务最后都会向微服务架构演化,这是一种趋势, 不过服务微服务化后带来的挑战也是显而易见的,例如服务粒度小,数量大,后期运维将会很难
四、项目演化过程
单体架构 -> 分布式 -> 微服务
五、SpringCloud中五大常用组件
- 服务发现——Netflix Eureka
- 客服端负载均衡——Netflix Ribbon
- 断路器——Netflix Hystrix
- 服务网关——Netflix Zuul
- 分布式配置——Spring Cloud Config
六、SpringCloud与SpringBoot版本对应关系
Hoxton |
2.2.x |
Greenwich |
2.1.x |
Finchley |
2.0.x |
Edgware |
1.5.x |
Dalston |
1.5.x |
详情查看官网:https://start.spring.io/actuator/info
七、搭建SpringCloud项目
1.maven多模块的搭建
1.1新建一个maven工程
1.1.1. File -> New -> Project
1.1.2. Maven -> sdk -> next
1.1.3 填写GroupId和ArtifactId,-->next
1.1.4 项目名称,-->next
建好之后删除src文件,此项目作为父工程,不需要在src下写代码
注意:父工程全路径不能有“-”,不然子模块无法引用到父工程版本号
1.2 新建服务端
1.2.1 右击父工程 -> new -> module
1.2.2 选择maven项目,next
1.2.3 填写module名称
1.2.4 点击finish
1.2.5 项目结构
1.3 新建客户端
new module -->next>finish
1.4 统一版本管理与编译
父工程pom文件配置
<?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> <groupId>com.donleo</groupId> <artifactId>cloud</artifactId> <packaging>pom</packaging> <version>1.0-SNAPSHOT</version> <modules> <module>student</module> <module>eureka</module> </modules> <!--版本配置--> <properties> <spring-boot.version>2.3.2.RELEASE</spring-boot.version> <spring-cloud.version>Hoxton.SR9</spring-cloud.version> <java.version>1.8</java.version> </properties> <dependencyManagement> <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-dependencies</artifactId> <version>${spring-boot.version}</version> <type>pom</type> <scope>import</scope> </dependency> <dependency> <groupId>org.projectlombok</groupId> <artifactId>lombok</artifactId> <version>1.18.12</version> </dependency> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-dependencies</artifactId> <version>${spring-cloud.version}</version> <type>pom</type> <scope>import</scope> </dependency> </dependencies> </dependencyManagement> <build> <plugins> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> <version>${spring-boot.version}</version> </plugin> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-compiler-plugin</artifactId> <version>3.6.1</version> <configuration> <source>${java.version}</source> <target>${java.version}</target> </configuration> </plugin> </plugins> </build> </project>
1.5 配置服务端
1.5.1服务端pom文件配置
<?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"> <parent> <artifactId>cloud</artifactId> <groupId>com.donleo</groupId> <version>1.0-SNAPSHOT</version> </parent> <modelVersion>4.0.0</modelVersion> <artifactId>eureka</artifactId> <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-netflix-eureka-server</artifactId> </dependency> </dependencies> </project>
1.5.2 application.yml文件配置
spring: profiles: active: default ######################单节点配置################### --- spring: application: name: eureka-server #指定服务名称 profiles: default server: port: 8761 #指定运行端口 eureka: instance: hostname: localhost #指定主机地址 client: fetch-registry: false #指定是否要从注册中心获取服务(默认true) register-with-eureka: false #指定是否要注册到注册中心(默认true) server: enable-self-preservation: false #是否开启保护模式(默认true) eviction-interval-timer-in-ms: 3000 # 清理间隔(单位毫秒,默认是60*1000) # 配置日志级别 logging: level: com.netflix: warn ###########################集群配置########################### #节点一 --- spring: application: name: eureka-cluster #指定服务名称 profiles: eureka1 server: port: 8011 #指定运行端口 eureka: instance: hostname: localhost #指定主机地址 instance-id: ${spring.cloud.client.ip-address}:${server.port} client: register-with-eureka: true #指定是否要注册到注册中心(默认true) fetch-registry: true #指定是否要从注册中心获取服务(默认true) serviceUrl: defaultZone: http://localhost:8012/eureka/,http://localhost:8013/eureka/ #注册到另一个Eureka注册中心 server: enable-self-preservation: false #是否开启保护模式(默认true) eviction-interval-timer-in-ms: 3000 # 清理无效服务节点的时间间隔(单位毫秒,默认是60*1000) # 配置日志级别 logging: level: com.netflix: warn #节点二 --- spring: application: name: eureka-cluster #指定服务名称 profiles: eureka2 server: port: 8012 #指定运行端口 eureka: instance: hostname: localhost #指定主机地址 instance-id: ${spring.cloud.client.ip-address}:${server.port} client: register-with-eureka: true #指定是否要注册到注册中心(默认true) fetch-registry: true #指定是否要从注册中心获取服务(默认true) serviceUrl: defaultZone: http://localhost:8011/eureka/,http://localhost:8013/eureka/ #注册到另一个Eureka注册中心 server: enable-self-preservation: false #是否开启保护模式(默认true) eviction-interval-timer-in-ms: 3000 # 清理无效服务节点的时间间隔(单位毫秒,默认是60*1000) # 配置日志级别 logging: level: com.netflix: warn #节点三 --- spring: application: name: eureka-cluster #指定服务名称 profiles: eureka3 server: port: 8013 #指定运行端口 eureka: instance: hostname: localhost #指定主机地址 instance-id: ${spring.cloud.client.ip-address}:${server.port} client: register-with-eureka: true #指定是否要注册到注册中心(默认true) fetch-registry: true #指定是否要从注册中心获取服务(默认true) serviceUrl: defaultZone: http://localhost:8012/eureka/,http://localhost:8011/eureka/ #注册到另一个Eureka注册中心 server: enable-self-preservation: false #是否开启保护模式(默认true) eviction-interval-timer-in-ms: 3000 # 清理无效服务节点的时间间隔(单位毫秒,默认是60*1000) # 配置日志级别 logging: level: com.netflix: warn
1.5.3 单实例启动
在主程序上添加@EnableEurekaServer注解
在浏览器上输入地址:localhost:8761 ,界面如下
1.5.4 多实例启动
编辑配置,取消勾选Single instance only
激活配置文件,依次启动eureka1,eureka2,eureka3
控制台可以看到三个实例同时启动
访问8011端口可以发现有三个节点加入到了集群中
1.6 配置客户端
1.6.1客户端pom文件配置
<?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"> <parent> <artifactId>cloud</artifactId> <groupId>com.donleo</groupId> <version>1.0-SNAPSHOT</version> </parent> <modelVersion>4.0.0</modelVersion> <artifactId>student</artifactId> <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId> </dependency> </dependencies> </project>
子模块引用的版本号是父项目指定的版本号
1.6.2 客户端application.yml配置
spring: profiles: active: default #####################客户端单节点配置################### --- spring: application: name: stu-app profiles: default server: port: 9000 #运行端口号 eureka: instance: hostname: localhost #指定主机地址 instance-id: ${spring.cloud.client.ip-address}:${server.port} client: #healthcheck: #enabled: true register-with-eureka: true #注册到Eureka的注册中心 fetch-registry: true #获取注册实例列表 service-url: defaultZone: http://localhost:8761/eureka #配置注册中心地址 registry-fetch-interval-seconds: 10 # 设置服务消费者从注册中心拉取服务列表的间隔 #####################客户端集群配置################### #节点一 --- spring: application: name: stu-cluster1 profiles: stu1 server: port: 8101 #运行端口号 eureka: instance: hostname: localhost #指定主机地址 instance-id: ${spring.cloud.client.ip-address}:${server.port} client: #healthcheck: #enabled: true register-with-eureka: true #注册到Eureka的注册中心 fetch-registry: true #获取注册实例列表 service-url: defaultZone: http://localhost:8761/eureka #配置注册中心地址 registry-fetch-interval-seconds: 10 # 设置服务消费者从注册中心拉取服务列表的间隔 #节点二 --- spring: application: name: stu-cluster2 profiles: stu2 server: port: 8102 #运行端口号 eureka: instance: hostname: localhost #指定主机地址 instance-id: ${spring.cloud.client.ip-address}:${server.port} client: #healthcheck: #enabled: true register-with-eureka: true #注册到Eureka的注册中心 fetch-registry: true #获取注册实例列表 service-url: defaultZone: http://localhost:8761/eureka #配置注册中心地址 registry-fetch-interval-seconds: 10 # 设置服务消费者从注册中心拉取服务列表的间隔
1.6.3 在主程序上添加@EnableDiscoverClient注解,启动
服务端启动单实例窗口,访问8761端口,可以看到有一个客户端连接上了
到此,一个SpringCloud项目已经搭建好了