微服务概述及如何搭建微服务

news2024/11/12 14:45:18

1. 微服务架构—SpringCloud

1.1 单体应用架构

将项目所有模块【功能】打成jar包或者war包,然后部署一个进程

在这里插入图片描述

优点:

  1. 部署简单:由于是完整的结构体,可以直接部署在一个服务器上即可
  2. 技术单一:项目不需要复杂的技术栈,往往一套熟悉的技术栈就可以完成开发

缺点:

  1. 系统启动慢,一个进程包含了所有的业务逻辑,涉及到的启动模块过多,导致系统的启动,重启时间周期过长
  2. 系统错误隔离性差、可用性差,任何一个模块的错误均可能造成整个系统的宕机;
  3. 可伸缩性差:系统的扩容只能只对这个应用进行扩容,无法结合业务模块的特点进行伸缩。
  4. 线上问题修复周期长:任何一个线上问题修复需要对整个应用系统进行全面升级。
  5. 跨语言程度差
  6. 不利于安全管理,所有开发人员都拥有全量代码。

1.2 微服务应用 70%

微服务架构风格是一种将一个单一应用程序开发为一组小型服务的方法,每个服务运行在自己的进程中,服务间通信采用轻量级通信机制【通常用HTTP资源API】,这些服务围绕业务能力构建并且可通过全自动部署机制独立部署。这些服务共用一个最小型的集中式的管理,服务可用不同的语言开发,使用不同的数据存储技术

在这里插入图片描述

解读微服务特点:
1:微服务是一种项目架构思想(风格)

2:微服务架构是一系列小服务的组合(组件化与多服务)

3:任何一个微服务,都是一个独立的进程(独立开发、独立维护、独立部署)

4:轻量级通信http协议(跨语言,跨平台) [接口编写]

5:服务粒度(围绕业务功能拆分-

6:去中心化管理

1.3 微服务架构的优势

一般用于大型项目,大企业

1.易于开发和维护
一个微服务只关注一个特定的业务功能,所以它的业务清晰、代码量较少。开发和维护单个微服务相对比较简单,整个应用是由若干个微服务构建而成,所以整个应用也会维持在可控状态;

部署麻烦——开发人员进行容器化部署【docker】

⒉.单个微服务启动较快
单个微服务代码量较少,所以启动会比较快;

3.局部修改容易部署
单体应用只要有修改,就要重新部署整个应用,微服务解决了这样的问题。一般来说,对某个微服务进行修改,只需要重新部署这个服务即可;

4.技术栈不受限
在微服务中,我们可以结合项目业务及团队的特点,合理地选择技术栈.

5.按需伸缩

购物车---->购物车这个系统集群搭建

1.4 微服务架构的缺点,即挑战

这么多小服务,如何管理他们?

这么多小服务,他们之间如何通讯?

这么多小服务,客户端怎么访问他们?

这么多小服务,一旦出现问题了,应该如何自处理?

这么多小服务,一旦出现问题了,应该如何排错?


相应的组件可以解决上面的相应的挑战。----把这些组件和在一起称为springcloud

1.5 SpringCloud与微服务的关系

  • Springcloud为微服务思想提供了完美的解决方案

  • Springcloud是一些列框架的集合体(服务的注册与发现【注册中心】、服务间远程调用、服务降级、服务熔断、服务限流、分布式事务等)

  • springcloud就是一系列框架的集合,为了解决微服务的挑战

    springcloud有两个版本: springcloud netflix [停止更新] 和springcloud alibaba。
    

1.6 SpringCloud和SpringBoot的关系

  • SpringBoot专注于快速方便的开发单个个体微服务。
  • SpringCloud是关注全局的微服务协调、整理、治理的框架,它将SpringBoot开发的单体整合并管理起来。
  • SpringBoot可以离开SpringCloud独立使用开发项目,但是SpringCloud离不开SpringBoot,属于依赖关系

2. 如何搭建微服务框架

  • 案例,如图示

在这里插入图片描述

创建一个商品微服务,一个订单微服务,通过购买添加订单

2.1 创建一个父工程并引入依赖

父工程仅创建一个maven工程即可

在这里插入图片描述

  • 引入依赖
<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <modules>
        <module>springcloud_common</module>
        <module>springcloud_product</module>
        <module>springcloud_order</module>
    </modules>
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.3.12.RELEASE</version>
        <!--修改版本-->
        <relativePath/> <!-- lookup parent from repository -->
    </parent>
    <groupId>com.zmq</groupId>
    <artifactId>spring_cloud_parent</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <!--只要是父工程打包方式都是pom,可以把src目录删除-->
    <!--因为父工程不负责代码编写,只负责子工程的管理-->
    <packaging>pom</packaging>
    <name>spring_cloud_parent</name>
    <description>spring_cloud_parent</description>

    <!-- 定义版本号 -->
    <properties>
        <java.version>1.8</java.version>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
        <!-- springcloud的版本 -->
        <spring-cloud.version>Hoxton.SR12</spring-cloud.version>
        <!-- 阿里巴巴的版本  springboot springcloud  springcloudalibaba 他们的版本必须对应
                https://github.com/alibaba/spring-cloud-alibaba/wiki/%E7%89%88%E6%9C%AC%E8%AF%B4%E6%98%8E
                 -->
        <spring-cloud-alibaba.version>2.2.8.RELEASE</spring-cloud-alibaba.version>
    </properties>
    <!--
        dependencyManagement: 只负责jar的管理不负责jar的下载。
         -->
    <dependencyManagement>
        <dependencies>
            <dependency>
                <groupId>org.springframework.cloud</groupId>
                <artifactId>spring-cloud-dependencies</artifactId>
                <version>${spring-cloud.version}</version>
                <type>pom</type>
                <scope>import</scope>
            </dependency>
            <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>
        </dependencies>
    </dependencyManagement>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>

</project>
  1. 可以选择将src目录删除

  2. 在pom文件中添加打包方式为pom

    只要是父工程打包方式都是pom

  3. 添加相关依赖

相关依赖的版本有对应要求,在下面网址可以查看对应关系——SpringCloud、SpringCloud Alibaba、SpringBoot三者之间

https://github.com/alibaba/spring-cloud-alibaba/wiki/%E7%89%88%E6%9C%AC%E8%AF%B4%E6%98%8E

在这里插入图片描述

2.2 创建一个公共模块

直接在父工程下创建模块即可

公共模块包含工具类、公共实体类【R】、实体类等

  • 依赖
<dependencies>
        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
        </dependency>
        <dependency>
            <groupId>com.baomidou</groupId>
            <artifactId>mybatis-plus-boot-starter</artifactId>
            <version>3.5.4</version>
        </dependency>
    </dependencies>
  • 商品实体类
@Data
@NoArgsConstructor
@AllArgsConstructor
@TableName("tbl_product")
public class Product {
    @TableId(type= IdType.AUTO)
    private Integer pid;
    private String pname;
    private BigDecimal price;
    private Integer stock;
}
  • 订单实体类
@Data
@NoArgsConstructor
@AllArgsConstructor
@TableName("tbl_order")
public class Order {
    @TableId(type = IdType.AUTO)
    private Integer id;
    private String orderNo;
    private Integer productId;
    private BigDecimal price; //因为double存在精度丢失问题
    private String pname;
    private Integer num;

    private Integer userid;

    private Integer status;

    //订单创建时间--Date存在线程安全问题--默认按照驼峰命名
    private LocalDateTime createTime;
}
  1. 价格使用BigDecimal类型,因为double存在精度丢失问题
  2. 时间类型使用LocalDateTime类型,因为Date存在线程安全问题
  3. mybatis-plus默认按照驼峰命名,以_为依据

2.3 创建商品微服务

直接在父工程下创建模块即可

  • 引入依赖
 <dependencies>
         <!--公共依赖-->
         <dependency>
             <groupId>com.ykq</groupId>
             <artifactId>qy174-springcloud-common</artifactId>
             <version>0.0.1-SNAPSHOT</version>
         </dependency>
        <!--数据库的依赖-->
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
        </dependency>
        <!--springboot-web依赖-->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
    </dependencies>
  • 创建配置文件application.properties
# 商品微服务的端口8001~8009
server.port=8001

# 起服务名
spring.application.name=product

# 数据源
spring.datasource.username=root
spring.datasource.password=root
spring.datasource.url=jdbc:mysql://localhost:3306/springcloud-product?useUnicode=true&characterEncoding=utf-8&useSSL=false&serverTimezone=Asia/Shanghai
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver

#mysql日志
mybatis-plus.configuration.log-impl=org.apache.ibatis.logging.stdout.StdOutImpl

#mybatis映射文件
mybatis-plus.mapper-locations=classpath*:mapper/*.xml
  • com.zmq下创建主启动类
@SpringBootApplication
@MapperScan("com.ykq.product.mapper")
public class ProductApp {
    public static void main(String[] args) {
        SpringApplication.run(ProductApp.class,args);
    }
}
  • mapper接口
public interface ProductMapper extends BaseMapper<Product> {
}
  • service接口
public interface ProductService {
    //根据商品id搜索商品
    public Product getById(Integer pid);
}
  • service接口实现类
public class ProductServiceImpl implements ProductService {

    @Autowired
    private ProductMapper productMapper;
    @Override
    public Product getById(Integer pid) {
        Product product = productMapper.selectById(pid);
        return product;
    }
}
  • controller持久类
@RestController
@RequestMapping("/product")
public class ProductController {
    @Autowired
    private ProductService productService;
    @GetMapping("/getById/{pid}")
    public Product getById(@PathVariable Integer pid) {
        Product product = productService.getById(pid);
        return product;
    }
}

2.4 创建订单微服务

  • 引入依赖
 <dependencies>
        <!--引入公共依赖-->
        <dependency>
            <groupId>com.zmq</groupId>
            <artifactId>springcloud_common</artifactId>
            <version>0.0.1-SNAPSHOT</version>
        </dependency>
        <!--数据库的依赖-->
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
        </dependency>
        <!--springboot-web依赖-->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
        <!--引入糊涂工具,便于调用雪花算法创建唯一的订单编号-->
        <dependency>
            <groupId>cn.hutool</groupId>
            <artifactId>hutool-all</artifactId>
            <version>5.8.16</version>
        </dependency>
    </dependencies>

引入hutool-all工具是为了使用雪花算法,生成唯一的订单编号

  • 创建application.properties配置文件
#端口号
server.port=9001
#服务名
spring.application.name=order
#数据源
spring.datasource.username=root
spring.datasource.password=root
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
spring.datasource.url=jdbc:mysql://localhost:3306/springcloud_order?useUnicode=true&characterEncoding=utf-8&useSSL=false&serverTimezone=Asia/Shanghai

#mysql日志
mybatis-plus.configuration.log-impl=org.apache.ibatis.logging.stdout.StdOutImpl

#mybatis映射文件
mybatis-plus.mapper-locations=classpath*:mapper/*.xml
  • com.zmq包下创建启动类
@SpringBootApplication
@MapperScan("com.zmq.mapper")
public class OrderApp {
    public static void main(String[] args) {
        SpringApplication.run(OrderApp.class,args);
    }
}
  • mapper接口
@Repository
public interface OrderMapper extends BaseMapper<Order> {
}
  • service接口
public interface OrderService {
    //添加订单
    public Order createOrder(Order order);
}
  • service接口实现类
@Service
public class OrderServiceImpl implements OrderService {
    @Autowired
    private OrderMapper orderMapper;
    @Override
    public Order createOrder(Order order) {
        orderMapper.insert(order);
        return order;
    }
}
  • controller控制类
@RestController
@RequestMapping("/order")
public class OrderController {

    @Autowired
    private OrderService orderService;

    @Autowired
    private RestTemplate restTemplate;

    @PostMapping("/saveOrder")
    public Order saveOrder(Integer pid, Integer num) {
        Order order = new Order();
        order.setOrderNo(IdUtil.getSnowflakeNextIdStr());//订单编号: 时间戳+随机数  雪花算法: 生成一个唯一的id
        order.setNum(num);
        order.setStatus(0);
        order.setCreateTime(LocalDateTime.now());
        order.setUserid(1);

        order.setProductId(pid);
        //根据商品id查询商品信息---远程调用商品微服务的接口。
        // 基于Http协议调用。[1]可以自己封装HttpClient工具类【适合所有场景】 [2] spring框架提高了一个HttpClient的工具类【适合spring工程】RestTemplate。
        //String url, Class<T> responseType, Object... uriVariables
        Product product = restTemplate.getForObject("http://localhost:8001/product/getById/" + pid, Product.class);
        if(product==null||product.getStock()<num){
            throw new RuntimeException("商品不存在或库存不足");
        }
        order.setPname(product.getPname());
        order.setPrice(product.getPrice());
        Order order1 = orderService.createOrder(order);

        return order1;
    }
}
  • config配置类
@Configuration
public class RestConfig {

    @Bean  //把方法的返回对象交于spring容器管理
    public RestTemplate restTemplate(){
        return new RestTemplate();
    }
}

远程调用商品微服务的接口——基于HTTP协议调用

两种实现方式

  1. 可以自己封装HttpClient工具类【适合所有场景】
  2. spring框架提高了一个HttpClient的工具类【适合spring工程】——RestTemplate

RestTemplate是一个执行HTTP请求的同步阻塞式工具类,它仅仅只是在 HTTP 客户端库(例如 JDK HttpURLConnection,Apache HttpComponents,okHttp 等)基础上,封装了更加简单易用的模板方法 API,方便程序员利用已提供的模板方法发起网络请求和处理,能很大程度上提升我们的开发效率

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1981642.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

windows启动nacos时报Caused by: java.lang.UnsatisfiedLinkErro错误

Caused by: java.lang.UnsatisfiedLinkError: C:\Users\Administrator\AppData\Local\Temp\2\librocksdbjni6009210463092880400.dll: Can’t find dependent libraries 因为电脑没有vc&#xff0c;或vc版本问题&#xff0c;下载对应的vc安装就可以了 VC“2015-2022”运行库官…

基础复习(反射、注解、动态代理)

反射 反射&#xff0c;指的是加载类的字节码到内存&#xff0c;并以编程的方法解刨出类中的各个成分&#xff08;成员变量、方法、构造器等&#xff09;。 1.获取类的字节码 &#xff08;3种方式&#xff09; public class Test1Class{public static void main(String[] arg…

全球社区的建立:Facebook在跨文化交流中的角色

在全球化日益加深的今天&#xff0c;跨文化交流成为了人们日常生活中的重要部分。Facebook作为全球最大的社交网络平台之一&#xff0c;正在发挥着越来越重要的作用。通过其广泛的用户基础和丰富的功能&#xff0c;Facebook不仅连接了来自不同国家和地区的人们&#xff0c;也在…

数据迁移数亿小文件该如何做到?

在数字化转型的浪潮中&#xff0c;企业在数据管理上遇到了诸多挑战&#xff0c;尤其是面对海量小文件的数据迁移问题。这类迁移任务不仅复杂&#xff0c;而且对效率、数据一致性和完整性的要求极高。 处理数亿小文件的数据迁移并非易事。当文件数量庞大&#xff0c;尤其是文件大…

吴恩达老师机器学习-ex8

data1 导入库&#xff0c;读取数据并进行可视化 因为这次的数据是mat文件&#xff0c;需要使用scipy库中的loadmat进行读取数据。 通过对数据类型的分析&#xff0c;发现是字典类型&#xff0c;查看该字典的键&#xff0c;可以发现又X等关键字。 import numpy as np import…

matplotlib库学习之绘图透明度设置(精炼准确)

matplotlib库学习之透明颜色设置 一、简介 在数据可视化中&#xff0c;透明度设置可以使图表更具层次感&#xff0c;特别是在多层叠加图表时。matplotlib库提供了多种方法来设置图表各个部分的透明度&#xff0c;包括图形、文本、图例、坐标轴等部分。 二、为什么要设置成透明…

某PM2项目管理系统 ExcelIn.aspx 文件上传漏洞复现

FOFA:body="PM2项目管理系统BS版增强工具.zip" 访问漏洞url抓包 上传压缩包 请求包 POST /FlowChartDefine/ExcelIn.aspx HTTP/1.1 Host: Accept-Encoding: gzip, deflate Content-Type: multipart/form-data; boundary=---------------------------335518608136…

WPF学习(2)-UniformGrid控件(均分布局)+StackPanel控件(栈式布局)

UniformGrid控件&#xff08;均分布局&#xff09; UniformGrid和Grid有些相似&#xff0c;只不过UniformGrid的每个单元格面积都是相等的&#xff0c;不管是横向的单元格&#xff0c;或是纵向的单元格&#xff0c;它们会平分整个UniformGrid。 UniformGrid控件提供了3个属性…

自动化测试使用jenkins做CICD持续集成(docker)

1.什么是&#xff08;CI/CD&#xff09; 1.1持续集成 定义&#xff1a;频繁地&#xff08;一天多次&#xff09;将代码集成到主干。将软件个人研发的部分向软件整体部分 交付&#xff0c;频繁进行集成以便更快地发现其中的错误。 每完成一点更新&#xff0c;就集成到主干&…

儿童活动床栏亚马逊temu美国ASTM F2085测试报告16 CFR 1224标准CPC认证办理

亚马逊temu美国站儿童活动床栏ASTM F2085-19测试报告活动床栏16 CFR 1224标准CPC认证 什么是便携式床栏杆&#xff1f; 便携式床栏杆是一种旨在安装在成人床上以防止儿童跌落的装置。便携式床栏适用于在没有帮助的情况下方便儿童&#xff08;通常为 2 至 5 岁&#xff09;上下…

编程深水区之并发①:什么是并发编程

并发编程是一种让程序能够执行多个任务的编程技术&#xff0c;多个任务的执行时间有重合&#xff0c;如交替执行、同时执行等。相对于传统的从上到下依次同步执行代码&#xff0c;我们也称并发编程为异步编程。目前&#xff0c;常见的并发模型主要有两种&#xff0c;一是多线程…

MySQL --- 内置函数介绍

目录 一、日期函数 二、字符串函数 三、数学函数 四、 其他函数 一、日期函数 current_date()当前日期current_time()当前时间current_timestamp()当前时间戳date(datetime)返回datetime的日期部分date_add(date&#xff0c;interval d_value_type) 在date中添加时间/日期…

在没有备份的条件下,如何恢复微信聊天记录?

推荐2款数据恢复工具1个简单实用方法&#xff0c;帮你找回微信误删聊天记录&#xff01; 操作简单&#xff0c;可用于iOS、安卓手机和PC电脑端 1、万兴数据管家 点击直达官网下载>>https://huifu.wondershare.cn 万兴数据管家是一款专业的微信数据恢复软件。 支持苹果…

鲁班上门维修安装系统源码开发之功能模式

鲁班上门维修安装系统在当今的趋势呈现出显著的增长与创新。随着物联网、智能家居的普及&#xff0c;以及消费者对便捷、高效生活方式的追求&#xff0c;鲁班上门维修安装系统凭借其多渠道预约、智能派单、在线支付与费用明细透明等优势&#xff0c;赢得了市场的广泛认可。 …

「面试必看」Vue百题斩~ Vue数据响应式原理的四个核心模块

vue 响应式原理的四个核心模块 Observe Observe 要实现的目标非常简单&#xff0c;就是把一个普通对象转换成响应式对象。 为了实现这一点&#xff0c;Observe 把对象的每个属性通过 Object.defineProperty 转换为带有 setter 和 getter 的属性&#xff0c;这样一来&#xf…

重头开始嵌入式第十二天(预处理和指针)

预处理 在 C 语言中&#xff0c;预处理是指在编译之前由预处理器对源代码进行的一些处理操作。 主要包括以下几个方面&#xff1a; 1. 宏定义&#xff1a;使用 #define 指令定义一个标识符来代表一个常量值、表达式或一段代码。 例如&#xff1a; #define PI 3.14159 2.…

亚马逊澳大利亚站 带绳窗帘认证步骤

带绳窗帘是一种室内用窗帘&#xff0c;可通过一根吊绳控制升降。此类商品包括但不限于蜂窝帘、水平百叶帘、百褶帘、卷式百叶帘、卷帘、透光帘、罗马帘、帘杆&#xff08;包括使用帘杆的商品&#xff0c;如带帘杆的窗帘和布帘&#xff09;、面板轨道和垂直百叶帘。 我们的带绳窗…

vue 开发工具 Hbuilder 简介及应用

一、简介 HBuilderX 是一款流行的前端开发工具&#xff0c;由DCloud公司开发。它支持多种编程语言&#xff0c;如HTML、CSS、JavaScript、Vue、UniApp等&#xff0c;非常适合用来开发Web应用、移动端应用和跨平台应用。 官网地址&#xff1a;https://www.dcloud.io/hbuilderx.…

ShardingSphere 内核工作原理

文章目录 内核工作原理配置管控SQL Parser: SQL解析引擎SQL Router- SQL 路由引擎SQL Rewriter : SQL 优化引擎SQL Executor &#xff1a; SQL执行引擎Result Merger&#xff1a; 结果归并 内核工作原理 ShardingSphere的整体架构图是这样的&#xff1a; 配置管控 在进入Shar…

火车站NTP电子钟,自动授时,保证时间精准

在现代交通体系中&#xff0c;火车站作为重要的交通枢纽&#xff0c;每天承载着大量乘客的出行需求。为了确保列车运行的准时性和乘客信息的准确性&#xff0c;火车站NTP电子钟成为不可或缺的一部分。本文将详细介绍火车站NTP电子钟的特点及其在不同场景中的应用优势。 一、火车…