# springcloud-demo **Repository Path**: hope4cc/springcloud-demo ## Basic Information - **Project Name**: springcloud-demo - **Description**: springcloud demo - **Primary Language**: Java - **License**: Not specified - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2022-12-08 - **Last Updated**: 2022-12-08 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README ## 搭建 ### 注册中心 #### Eureka ![截屏2022-12-08 14.07.33](https://tva1.sinaimg.cn/large/008vxvgGly1h8wdczv4kyj31f30u0djz.jpg) > eureka-server,这必须是一个独立的微服务 ##### 1、依赖 引入SpringCloud为eureka提供的starter依赖: ```xml org.springframework.cloud spring-cloud-starter-netflix-eureka-server ``` ##### 2、启动类 添加eureka-server服务启动类,一定要添加一个@EnableEurekaServer注解,开启eureka的注册中心功能: ```java @EnableEurekaServer @SpringBootApplication public class EurekaApplication { public static void main(String[] args) { SpringApplication.run(EurekaApplication.class,args); } } ``` ##### 3、application.yml文件 ```yaml server: port: 10086 spring: application: name: eureka-server eureka: client: service-url: defaultZone: http://127.0.0.1:10086/eureka ``` ##### 4、启动微服务 然后在浏览器访问:http://127.0.0.1:10086![截屏2022-12-08 14.11.03](https://tva1.sinaimg.cn/large/008vxvgGly1h8wdgmizl9j31h00t0n0e.jpg) #### Nacos [Nacos](https://nacos.io/)是阿里巴巴的产品,现在是[SpringCloud](https://spring.io/projects/spring-cloud)中的一个组件。相比[Eureka](https://github.com/Netflix/eureka)功能更加丰富 ##### 1、下载安装包 在Nacos的GitHub页面,提供有下载链接,可以下载编译好的Nacos服务端或者源代码: GitHub主页:https://github.com/alibaba/nacos GitHub的Release下载页:https://github.com/alibaba/nacos/releases ##### 2、启动 非常简单,进入bin目录,结构如下:![截屏2022-12-08 14.14.44](https://tva1.sinaimg.cn/large/008vxvgGly1h8wdkha5mej31be0a60u2.jpg) > Linux/Unix/Mac 启动命令(standalone代表着单机模式运行,非集群模式): ``` sh startup.sh -m standalone ``` 执行后的效果如图:![截屏2022-12-08 14.15.45](https://tva1.sinaimg.cn/large/008vxvgGly1h8wdljfxm2j320v0u0wre.jpg) ![截屏2022-12-08 14.16.50](https://tva1.sinaimg.cn/large/008vxvgGly1h8wdmmkd2rj31eo0qg76l.jpg) 默认的账号和密码都是nacos Nacos是SpringCloudAlibaba的组件,而SpringCloudAlibaba也遵循SpringCloud中定义的服务注册、服务发现规范。因此使用Nacos和使用Eureka对于微服务来说,并没有太大区别。 主要差异在于: - 依赖不同 - 服务地址不同 ##### 3、依赖 在父工程的pom文件中的``中引入SpringCloudAlibaba的依赖: ```xml com.alibaba.cloud spring-cloud-alibaba-dependencies 2.2.6.RELEASE pom import ``` 然后在user-service和order-service中的pom文件中引入nacos-discovery依赖: ```` com.alibaba.cloud spring-cloud-starter-alibaba-nacos-discovery ```` >注释掉eureka的依赖 ##### 4、配置nacos地址 在user-service和order-service的application.yml中添加nacos地址: ``` spring: cloud: nacos: server-addr: localhost:8848 ``` 重启微服务后,登录nacos管理页面,可以看到微服务信息: ![截屏2022-12-08 14.16.21](https://tva1.sinaimg.cn/large/008vxvgGly1h8wdm6ifinj32r00u0tfj.jpg) #### Nacos与Eureka的区别 Nacos和Eureka整体结构类似,服务注册、服务拉取、心跳等待,但是也存在一些差异:![截屏2022-12-08 14.20.33](https://tva1.sinaimg.cn/large/008vxvgGly1h8wdqi2ccaj31f40jgjtc.jpg) - Nacos与eureka的共同点 - 都支持服务注册和服务拉取 - 都支持服务提供者心跳方式做健康检测 - Nacos与Eureka的区别 - Nacos支持服务端主动检测提供者状态:临时实例采用心跳模式,非临时实例采用主动检测模式 - 临时实例心跳不正常会被剔除,非临时实例则不会被剔除 - Nacos支持服务列表变更的消息推送模式,服务列表更新更及时 - Nacos集群默认采用AP方式,当集群中存在非临时实例时,采用CP模式;Eureka采用AP方式 ### 网关 ##### 1、创建,引入网关依赖 ```xml org.springframework.cloud spring-cloud-starter-gateway com.alibaba.cloud spring-cloud-starter-alibaba-nacos-discovery ``` ##### 2、编写启动类 ```java package cn.hope.gateway; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; @SpringBootApplication public class GatewayApplication { public static void main(String[] args) { SpringApplication.run(GatewayApplication.class, args); } } ``` ##### 3、编写基础配置和路由规则 创建application.yml文件,内容如下: ```xml server: port: 10010 spring: application: name: gateway cloud: nacos: server-addr: 192.168.1.5:8848 gateway: routes: - id: user-service #路由标识,必须唯一 uri: lb://userservice #路由的目标地址 predicates: #路由断言,判断请求是否符合规则 - Path=/user/** # 路径断言 判断路径是否是以/user开头,如果是则符合 - id: order-service uri: lb://orderservice predicates: - Path=/order/** # - After=2031-04-13T15:14:47.433+08:00[Asia/Shanghai] #断言工厂 ``` ##### 4、重启测试 重启网关,访问http://localhost:10010/order/101时,符合`/order/**`规则,并且user服务提供者请求转发到uri:http://userservice/user/1,得到了结果: ![截屏2022-12-08 14.32.05](https://tva1.sinaimg.cn/large/008vxvgGly1h8we2k78g6j30oo0lkabj.jpg) ##### 5、网关路由的流程图 ![截屏2022-12-08 14.32.29](https://tva1.sinaimg.cn/large/008vxvgGly1h8we2wjidaj31gw0qowh2.jpg) ### Nacos配置中心(管理) 当微服务部署的实例越来越多,达到数十、数百时,逐个修改微服务配置就会让人抓狂,而且很容易出错。我们需要一种统一配置管理方案,可以集中管理所有实例的配置。![截屏2022-12-08 14.36.08](https://tva1.sinaimg.cn/large/008vxvgGly1h8we6pjxtbj31fa0ka407.jpg) Nacos一方面可以将配置集中管理,另一方可以在配置变更时,及时通知微服务,实现配置的热更新。 ##### 1、在nacos中添加配置文件 ![截屏2022-12-08 14.36.39](https://tva1.sinaimg.cn/large/008vxvgGly1h8we83qno6j32630u0tbx.jpg) 然后在弹出的表单中,填写配置信息:![截屏2022-12-08 14.37.52](https://tva1.sinaimg.cn/large/008vxvgGly1h8we8ism0bj319c0u00vf.jpg) >注意:项目的核心配置,需要热更新的配置才有放到nacos管理的必要。基本不会变更的一些配置还是保存在微服务本地比较好。 ##### 2、从微服务拉取配置 ![截屏2022-12-08 14.38.29](https://tva1.sinaimg.cn/large/008vxvgGly1h8we95e4zuj31fs0fqdhz.jpg) 1)引入nacos-config依赖 首先,在user-service服务中,引入nacos-config的客户端依赖: ```xml com.alibaba.cloud spring-cloud-starter-alibaba-nacos-config ``` 2)添加bootstrap.yaml ```yaml #bootstrap.yml文件,这个文件是引导文件,优先级高于application.yml spring: application: name: userservice # 服务名称 profiles: active: dev #开发环境,这里是dev 加载开发环境 cloud: nacos: server-addr: 192.168.1.5:8848 # Nacos地址 # discovery: # namespace: 8d5763cb-ceae-4518-8e5c-56cf3eea7ae3 #dev 环境 config: file-extension: yaml # 配置文件后缀名 ``` 这里会根据spring.cloud.nacos.server-addr获取nacos地址,再根据 `${spring.application.name}-${spring.profiles.active}.${spring.cloud.nacos.config.file-extension}`作为文件id,来读取配置。 本例中,就是去读取`userservice-dev.yaml`:![截屏2022-12-08 14.39.48](https://tva1.sinaimg.cn/large/008vxvgGly1h8weair625j31660keabt.jpg) 3)读取nacos配置 在user-service中的UserController中添加业务逻辑,读取pattern.dateformat配置: ``` @Autowired private PatternProperties patternProperties; @GetMapping("now") public String now(){ return LocalDateTime.now().format(DateTimeFormatter.ofPattern(patternProperties.getDateformat())); } ``` ![截屏2022-12-08 14.41.10](https://tva1.sinaimg.cn/large/008vxvgGly1h8webyu30xj30s007smxl.jpg) >还可以配置热更新,修改nacos中的配置后,微服务中无需重启即可让配置生效 > >配置共享微服务启动时,会去nacos读取多个配置文件 ### 消费者、服务者 ![截屏2022-12-08 14.43.10](https://tva1.sinaimg.cn/large/008vxvgGly1h8wee2q74pj311q060aa9.jpg) >订单服务需要调用 用户服务提供用户的信息,然后根据用户信息查询用户订单 cloud-demo:父工程,管理依赖 - order-service:订单微服务,负责订单相关业务 - user-service:用户微服务,负责用户相关业务 ![截屏2022-12-08 14.44.58](https://tva1.sinaimg.cn/large/008vxvgGly1h8wefwaquuj30lm0l40td.jpg) ![截屏2022-12-08 14.45.41](https://tva1.sinaimg.cn/large/008vxvgGly1h8wegnah31j31hc0kc41c.jpg) 案例参考 https://www.bilibili.com/video/BV1LQ4y127n4?p=1&vd_source=48ed7f457809eb86e053060013705429 ### 任务书需求 声明式服务调用方式 ***使用声明式服务调用方式进行服务消费者调用服务提供者的hello方法*** 抽取方式 >将Feign的Client抽取为独立模块,并且把接口有关的POJO、默认的Feign配置都放到这个模块中,提供给所有消费者使用。 在order-service中使用feign-api ``` cn.hope.demo feign-api 1.0 ``` ![截屏2022-12-08 14.52.22](https://tva1.sinaimg.cn/large/008vxvgGly1h8wennrcsdj31go08qmz6.jpg) 这是因为UserClient现在在cn.itcast.feign.clients包下, 而order-service的@EnableFeignClients注解是在cn.itcast.order包下,不在同一个包,无法扫描到UserClient。 解决扫描包问题 方式一: 指定Feign应该扫描的包: ```java @EnableFeignClients(basePackages = "cn.hope.feign.clients") ``` 方式二: 指定需要加载的Client接口: ```java @EnableFeignClients(clients = {UserClient.class}) ``` ``` // 使用该注解,表示这里要使用哪个服务提供者 @FeignClient("userservice") public interface UserClient { // 要调用该服务提供者的哪个方法 @GetMapping("/hello") String hello(); } ``` 服务提供者 ``` @GetMapping("/hello") public String helloCustomer() { return "hello"; } ``` 服务消费者调用 ``` public String hello(){ return userClient.hello(); } ``` ![截屏2022-12-08 14.50.14](https://tva1.sinaimg.cn/large/008vxvgGly1h8welemsqsj30m207yaab.jpg) ### 说说对springcloud的理解、注册中心的作用、配置中心的作用、网关的作用、什么负载均衡 ##### 对springcloud的理解 ![截屏2022-12-08 15.02.50](https://tva1.sinaimg.cn/large/008vxvgGly1h8weyn8fpmj31a80mwtcu.jpg) 从官网介绍可以看到,Spring Cloud 就是微服务系统架构的一站式解决方案,是各个微服务架构落地技术的集合体,俗称微服务全家桶 在平时我们构建微服务的过程中需要做如服务发现注册、配置中心、负载均衡、断路器、数据监控等操作,而Spring Cloud 为我们提供了一套简易的编程模型,使我们能在 Spring Boot 的基础上轻松地实现微服务项目的构建 ``` 什么是分布式? 同一个业务,部署在多个服务器上(不同的服务器运行同样的代码,干同一件事) *//优点:* 1.通过多台计算机完成同一个工作,达到更高的效率。 2.两机或多机内容、工作过程等完全一样。如果一台死机,另一台可以起作用。 ``` ``` 什么是分布式? 1.将各个组件分开部署,某个组件占一个服务器,互相独立,互相调用,可以将组件的功能发挥强大 2.一个业务分拆多个子业务,部署在不同的服务器上(不同的服务器,运行不同的代码,为了同一个目的) //优点: 1.模块之间独立,各做各的事,便于扩展,复用性高 2.高吞吐量。某个任务需要一个机器运行20个小时,将该任务用10台机器的分布式跑 (将这个任务拆分成10个小任务),可能2个小时就跑完了 ``` ``` 什么是集群? 集群和分布式并不冲突,可以有分布式集群 //可以把java,前端,测试看成是分布式,把都在做java的看成是集群 ``` ``` 什么是微服务? 1.简单来说微服务就是很小的服务,小到一个服务只对应一个单一的功能,只做一件事 2.将一个大的项目,按照需求(业务服务)模块拆解成一个个独立小模块(微小服务),然后独立部署,它们之间独立又相互调用 ``` ``` SpringBoot和SpringCloud有啥关系? SpringBoot专注于快速、方便的开发单个微服务个体,SpringCloud关注全局的服务治理框架。 //区别:SpringBoot可以离开SpringCloud独立使用开发项目,但是SpringCloud离不开SpringBoot,属于依赖的关系. ``` > Spring Cloud 为我们提供了一套简易的编程模型,使我们能在 Spring Boot 的基础上轻松地实现微服务项目的构建 ##### 注册中心的作用 >注册中心的作用一句话概括就是存放和调度服务,实现服务和注册中心,服务和服务之间的相互通信。 主要包括三个角色:服务提供者、服务消费者、注册中心。 **服务注册中心的作用就是【服务的注册】和【服务的发现】** - 服务注册,就是将提供某个服务的模块信息(通常是这个服务的ip和端口)注册到1个公共的组件上去 - 服务发现,就是新注册的这个服务模块能够及时的被其他调用者发现。不管是服务新增和服务删减都能实现自动发现。 常用的注册中心有zookeeper、Eureka、Nacos等 ##### 配置中心的作用 >当微服务部署的实例越来越多,达到数十、数百时,逐个修改微服务配置就会让人抓狂,而且很容易出错。我们需要一种统一配置管理方案,可以集中管理所有实例的配置。 服务拆分越多,配置项也就越多。而一旦有某项服务进行了调整,其他服务也需要相应调整。如果配置项都在每个项目的配置文件中配置,那么可想而知,只要一有改变,就得改配置文件,重新部署项目。比如:假如说3个微服务中关于数据库的配置项是完全一样的,倘若某天MySQL数据库迁移了,那么这3个微服务的配置文件也要全部修改; 当修改了配置之后,必须重启服务,否则配置无法生效; 如果我们将一些数据库信息直接配置在配置文件中,那么对于运维的同学来说,显然带来了更大的挑战与风险。因为项目极有可能是多人协作开发,而多人都可以直接连接数据库将会具有不小的风险(删库跑路了解一下)**因此,Spring Cloud 架构中专门集成了一套用于配置管理的组件 - 分布式配置中心(Spring Cloud Config)** ![截屏2022-12-08 15.13.54](https://tva1.sinaimg.cn/large/008vxvgGly1h8wfa2ipmej31fy0kwwg6.jpg) Nacos一方面可以将配置集中管理,另一方可以在配置变更时,及时通知微服务,实现配置的热更新。 ##### 网关的作用 为什么需要网关 Gateway网关是我们服务的守门神,所有微服务的统一入口。 网关的**核心功能特性**: - 请求路由 - 权限控制 - 限流 架构图: ![截屏2022-12-08 14.55.57](https://tva1.sinaimg.cn/large/008vxvgGly1h8werdyz4cj31ik0pmmzo.jpg) **权限控制**:网关作为微服务入口,需要校验用户是是否有请求资格,如果没有则进行拦截。 **路由和负载均衡**:一切请求都必须先经过gateway,但网关不处理业务,而是根据某种规则,把请求转发到某个微服务,这个过程叫做路由。当然路由的目标服务有多个时,还需要做负载均衡。 **限流**:当请求流量过高时,在网关中按照下流的微服务能够接受的速度来放行请求,避免服务压力过大。 *** nginx Nginx (engine x)*** 是一个高性能的HTTP和反向代理web服务器,同时也提供了IMAP/POP3/SMTP服务 ***zuul ,Zuul*** 是 Netflix 出品的一个基于 JVM 路由和服务端的负载均衡器。 ***spring-cloud-gateway*** 是spring 出品的 基于spring 的网关项目,集成断路器,路径重写,性能比Zuul好。 ##### 什么是负载均衡 负载均衡,英文名称为Load Balance,其含义就是指将负载(工作任务)进行平衡、分摊到多个操作单元上进行运行,例如FTP服务器、Web服务器、企业核心应用服务器和其它主要任务服务器等,从而协同完成工作任务。 看到这一连串的专业名词不是很好理解,举个例子 >用外卖APP的案例 我们假设一台云服务器ECS可以承载100人的同时进行访问,然而现在是中午,有一万个人同时对外卖APP提起访问请求。 但我们现在只有一台服务器,如果想让这一万人全部完成访问,第一种方法就是排队,但就算一个人进入APP到完成点餐退出只需要花两分钟,轮到最后一个人进来也要到三个小时以后。 所以我们用第二种方法,添加服务器,因为我们用的是云服务器,所以很容易添加,无需自己准备场地、安装、调试、测试。添加了99台服务器后,一万个用户就能够同时访问APP了。 但又出现了一个问题,这一百个服务器怎么分?如果用户都进一个服务器里,那么添加再多服务器也没用。 **这个时候就轮到负载均衡登场了**。![截屏2022-12-08 15.19.04](https://tva1.sinaimg.cn/large/008vxvgGly1h8wfff2bm6j30yk0ladi5.jpg) 负载均衡,是指**将负载(工作任务)进行平衡、分摊到多个操作单元上进行运行。** 通俗讲,就是指上级领导下发一个任务,但工作量大到交给一个人无法完成,于是主管又叫了几个人过来一起处理,由他亲自把大任务分解成多个小任务分配给不同的人,完成分配任务的就叫负载均衡。 负载均衡的算法有多种分类,这里介绍为大家介绍三种常见的,分别是**轮询、加权轮询、最小连接。**