多微服务合并为一个服务
公司微服务细分太多,最近跟我提说需要将几个微服务合为单体,经过几天的查阅,决定用二次打包的方式进行合并,然后部署的时候在nginx改下合并的微服务转发路劲即可,不需要前端修改路劲了。
方案
采用二次打包的方式进行合并,利用maven-dependency-plugin解压插件先将各微服务的jar包解压再用maven-assembly-plugin进行合并打包为一个jar包。
合并前问题处理
1、由于包合并时,相同的类会进行覆盖,会导致找不到类等,所以存在相同包下的相同类名作用不一致的话,需要调整下各服务的包名、类
2、类注册的bean的name相同时,会导致注册bean失败,所以需要调整各服务有相同bean的name,特别是@FeignClient的contextId,因为是以contextId作为bean的name。
3、重复扫描导致重复注册等,如@EnableJpaAuditing,重复扫描,导致重复注册jpaAuditingHandler,所以在有用到@EnableJpaAuditing的类上也加上@ConditionalOnMissingBean(name="jpaAuditingHandler")条件,已经注册过的,就不需要再注册了
4、因为每个微服务都有yml配置文件,所以需要写个合并适配器,将每个微服务的yml合并一起,后续会另外开篇文件细说yml的合并。
合并步骤和代码
1、pom文件添加需要合并的微服务依赖
<properties><project.build.sourceEncoding>UTF-8</project.build.sourceEncoding><project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding><module1.version>6.1.0</module1.version><module2.version>6.1.0</module2.version><module3.version>6.1.0</module3.version> </properties> <dependencies> //需要整合的微服务包,type、scope需填写正确,其中groupId、artifactId、version按需填写即可<dependency><groupId>com.lfq.module1</groupId><artifactId>module1</artifactId><version>${module1.version}</version><type>jar</type><scope>provided</scope></dependency><dependency><groupId>com.lf1.module2</groupId><artifactId>module2</artifactId><version>${module2.version}</version><type>jar</type><scope>provided</scope></dependency><dependency><groupId>com.lf1.module3</groupId><artifactId>module3</artifactId><version>${module3.version}</version><type>jar</type><scope>provided</scope></dependency> </dependencies> |
2、pom文件添加解压插件,将微服务解压到指定目录下
<!-- 将指定执行包解包到指定目录下 --> <plugin><groupId>org.apache.maven.plugins</groupId><artifactId>maven-dependency-plugin</artifactId><executions><execution><id>unpack-classes</id><phase>package</phase><goals><goal>unpack</goal></goals><configuration><artifactItems><artifactItem><groupId>com.lfq.module1</groupId><artifactId>module1</artifactId><outputDirectory>${project.build.directory}/work/addpack/module1</outputDirectory></artifactItem><artifactItem><groupId>com.lfq.module2</groupId><artifactId>module2</artifactId><outputDirectory>${project.build.directory}/work/addpack/module2</outputDirectory></artifactItem><artifactItem><groupId>com.lfq.module3</groupId><artifactId>module3</artifactId><outputDirectory>${project.build.directory}/work/addpack/module3</outputDirectory></artifactItem></artifactItems></configuration></execution></executions> </plugin> |
3、pom文件添加合并打包插件,将解压目录下的文件和本工程代码合并打包
<!-- 将解开的执行包与本工程代码合并打包 --> <plugin><groupId>org.apache.maven.plugins</groupId><artifactId>maven-assembly-plugin</artifactId><version>3.3.0</version><configuration><recompressZippedFiles>false</recompressZippedFiles></configuration><executions><execution><id>make-assembly</id><phase>package</phase><goals><goal>single</goal></goals><configuration><archive> <!-- 标红部分是合并后的执行包的启动类MANIFEST.MF文件,我这里选module1解压下的文件,按需配启动类 --><manifestFile>${project.build.directory}/work/addpack/module1/META-INF/MANIFEST.MF</manifestFile></archive><descriptors><descriptor>assembly.xml</descriptor> <!-- 加载指定的assembly配置文件 --></descriptors></configuration></execution></executions> <!-- 标红部分是合并yml处理的包,如果需要合并yml文件,需自定义适配器对yml进行合并处理,再将依赖包添加进来 --> <!-- <dependencies><dependency><groupId>com.fql.merge</groupId><artifactId>mergeHandle</artifactId><version>1.0-SNAPSHOT</version></dependency></dependencies> --> </plugin> |
4、添加assembly.xml文件描述合并打包
<assembly> <!-- id自定义 --><id>lfq</id><formats><!-- 打为jar包 --><format>jar</format></formats><includeBaseDirectory>false</includeBaseDirectory><fileSets><!-- 先将本工程内容输出 --><fileSet><directory>${project.build.directory}/classes</directory><outputDirectory>BOOT-INF/classes</outputDirectory></fileSet><!-- 输出解压目录下的内容 --><fileSet><directory>${project.build.directory}/work/addpack/module1</directory><outputDirectory>.</outputDirectory> <!-- 这里是module1下的DbDataController类不需要输出参与合并打包,即打包后的jar包没有DbDataController类,按需配置 --><excludes><exclude>**/DbDataController.class</exclude></excludes></fileSet><fileSet><directory>${project.build.directory}/work/addpack/module2</directory><outputDirectory>.</outputDirectory> <!-- 这里是module2下的application.yml不需要输出参与合并打包,按需配置 --><excludes><exclude>**/application.yml</exclude></excludes></fileSet><fileSet><directory>${project.build.directory}/work/addpack/module3</directory><outputDirectory>.</outputDirectory></fileSet></fileSets><!--标红部分是对yml文件合并处理,如果没有实现,可去掉 --> <containerDescriptorHandlers><containerDescriptorHandler><handlerName>yml-merge</handlerName><configuration><filePattern>.*/application.yml</filePattern><outputPath>BOOT-INF/classes/application.yml</outputPath></configuration></containerDescriptorHandler></containerDescriptorHandlers><!-- 本工程依赖 --><dependencySets><dependencySet><unpack>false</unpack><useProjectArtifact>false</useProjectArtifact><outputDirectory>BOOT-INF/lib</outputDirectory></dependencySet></dependencySets> </assembly> |
后续执行clean install 即可得到一个jar包。
相关文章:
多微服务合并为一个服务
公司微服务细分太多,最近跟我提说需要将几个微服务合为单体,经过几天的查阅,决定用二次打包的方式进行合并,然后部署的时候在nginx改下合并的微服务转发路劲即可,不需要前端修改路劲了。 方案 采用二次打包的方式进行…...
Springboot企业级开发--开发入门01
目录 目录 一.Spring Boot的主要特点和优势包括: 二.Spring Boot的核心功能可以归纳为以下几点: 三.Springboot是如何解决问题? Spring Boot 是一个开源的Java框架,其设计目标是为了简化新Spring应用的初始搭建以及开发过程。…...
bash和sh和./的区别
bash和sh和./的区别 今天在执行一个脚本的时候,用的是sh script.sh,执行报错,使用bash script.sh执行时就能成功,才知道sh和bash是不一样的 sh sh表示 Bourne Shell,是 Unix 系统上的一种基本的命令解释器。它也可以…...
LeetCode 3:寻找最长不含重复字符的子串长度
LeetCode 3:寻找最长不含重复字符的子串长度 在字符串处理中,寻找最长不含重复字符的子串长度是一个经典问题。 问题描述 给定一个字符串 s ,我们需要找出其中不含有重复字符的最长子串的长度。 解决方案 我们可以使用滑动窗口的方法来解…...

【自然语言处理四-从矩阵操作角度看 自注意self attention】
自然语言处理四-从矩阵操作角度看 自注意self attention 从矩阵角度看self attention获取Q K V矩阵注意力分数softmax注意力的输出再来分析整体的attention的矩阵操作过程从矩阵操作角度看,self attention如何解决问题的?W^q^ W^k^ W^v^这三个矩阵怎么获…...
Unity脚本,串行端口的握手协议(流控制)
在Unity的SerialPort构造函数中,流控制并没有被直接包含。流控制,也被称为握手,是一种过程,它管理数据的传输速度,以防止接收方被发送方发送的数据量所淹没。 在.NET的SerialPort类中,流控制是通过Handshak…...

2023 re:Invent 用 Amazon Q 打造你的知识库
前言 随着 ChatGPT 的问世,我们迎来了许多创新和变革的机会。一年一度的亚马逊云科技大会 re:Invent 也带来了许多前言的技术,其中 Amazon CEO Adam Selipsky 在 2023 re:Invent 大会中介绍 Amazon Q 让我印象深刻,这预示着生成式 AI 的又一…...

ChatGPT 国内快速上手指南
ChatGPT简介 ChatGPT是由OpenAI团队研发的自然语言处理模型,该模型在大量的互联网文本数据上进行了预训练,使其具备了深刻的语言理解和生成能力。 GPT拥有上亿个参数,这使得ChatGPT在处理各种语言任务时表现卓越。它的训练使得模型能够理解上…...

Docker 常用操作命令备忘
Docker 一旦设置好了环境,日常就只要使用简单命令就可以运行和停止。 于是,我每次用的时候,都想不起来一些关键性的命令到底怎么用,特此记录。 一、镜像管理 从公有仓库拉取镜像 (对于使用苹果电脑 M1/M2/M3 芯片的 …...

BUU [CISCN2019 华东南赛区]Web4
BUU [CISCN2019 华东南赛区]Web4 题目描述:Click to launch instance. 开题: 点击链接,有点像SSRF 使用local_file://协议读到本地文件,无法使用file://协议读取,有过滤。 local_file://协议: local_file…...

【卷积神经网络中用1*1 卷积有什么作用或者好处呢?】
🚀 作者 :“码上有前” 🚀 文章简介 :深度学习 🚀 欢迎小伙伴们 点赞👍、收藏⭐、留言💬 1*1 卷积有什么作用或者好处呢 作用降维和增加非线性特征组合和交互网络的宽度和深度调整全连接替代增强…...
分布式系统概念及其应用
分布式系统概念及其应用 随着互联网的飞速发展,数据量和计算需求不断增加,传统的集中式系统已经无法满足这些需求。因此,分布式系统应运而生,它通过将计算任务分散到多台计算机上,实现高效的计算和存储。本文将介绍分…...
数据报文转换
报文转换 🍓JSON🍒🍒JSON多字段映射成一个实体对象🍒🍒JSON反序列化为一个带有泛型的JAVA类型 🍓xml 🍓JSON 🍒🍒JSON多字段映射成一个实体对象 <dependency><…...

Python爬虫-付费代理推荐和使用
付费代理的使用 相对免费代理来说,付费代理的稳定性更高。本节将介绍爬虫付费代理的相关使用过程。 1. 付费代理分类 付费代理分为两类: 一类提供接口获取海量代理,按天或者按量收费,如讯代理。 一类搭建了代理隧道࿰…...

kubectl使用及源码阅读
目录 概述实践样例yaml 中的必须字段 kubectl 代码原理kubectl 命令行设置pprof 抓取火焰图kubectl 中的 cobra 七大分组命令kubectl createcreateCmd中的builder模式createCmd中的visitor访问者模式外层VisitorFunc分析 结束 概述 k8s 版本 v1.24.16 kubectl的职责 1.主要的…...

C++面试宝典第32题:零钱兑换
题目 给定不同面额的硬币coins和一个总金额amount,编写一个函数来计算可以凑成总金额所需的最少的硬币个数。如果没有任何一种硬币组合能组成总金额,则返回-1。说明:你可以认为每种硬币的数量是无限的。 示例1: 输入:coins = [1, 2, 5], amount = 11 输出:3 解释:11 = …...

pyspark分布式部署随机森林算法
前言 分布式算法的文章我早就想写了,但是一直比较忙,没有写,最近一个项目又用到了,就记录一下运用Spark部署机器学习分类算法-随机森林的记录过程,写了一个demo。 基于pyspark的随机森林算法预测客户 本次实验采用的…...

【Python笔记-设计模式】中介者模式
一、说明 中介者模式是一种行为设计模式,减少对象之间混乱无序的依赖关系。该模式会限制对象之间的直接交互,迫使它们通过一个中介者对象进行合作。 (一) 解决问题 降低系统中对象之间的直接通信,将复杂的交互转化为通过中介者进行的间接交…...
大语言模型构建的主要四个阶段(各阶段使用的算法、数据、难点以及实践经验)
大语言模型构建通常包含以下四个主要阶段:预训练、有监督微调、奖励建模和强化学习,简要介绍各阶段使用的算法、数据、难点以及实践经验。 预训练 需要利用包含数千亿甚至数万亿 单词的训练数据,并借助由数千块高性能 GPU 和高速网络组成的…...

[云原生] 二进制安装K8S(中)部署网络插件和DNS
书接上文,我们继续部署剩余的插件 一、K8s的CNI网络插件模式 2.1 k8s的三种网络模式 K8S 中 Pod 网络通信: (1)Pod 内容器与容器之间的通信 在同一个 Pod 内的容器(Pod 内的容器是不会跨宿主机的)共享…...

利用最小二乘法找圆心和半径
#include <iostream> #include <vector> #include <cmath> #include <Eigen/Dense> // 需安装Eigen库用于矩阵运算 // 定义点结构 struct Point { double x, y; Point(double x_, double y_) : x(x_), y(y_) {} }; // 最小二乘法求圆心和半径 …...
Ubuntu系统下交叉编译openssl
一、参考资料 OpenSSL&&libcurl库的交叉编译 - hesetone - 博客园 二、准备工作 1. 编译环境 宿主机:Ubuntu 20.04.6 LTSHost:ARM32位交叉编译器:arm-linux-gnueabihf-gcc-11.1.0 2. 设置交叉编译工具链 在交叉编译之前&#x…...

Lombok 的 @Data 注解失效,未生成 getter/setter 方法引发的HTTP 406 错误
HTTP 状态码 406 (Not Acceptable) 和 500 (Internal Server Error) 是两类完全不同的错误,它们的含义、原因和解决方法都有显著区别。以下是详细对比: 1. HTTP 406 (Not Acceptable) 含义: 客户端请求的内容类型与服务器支持的内容类型不匹…...

51c自动驾驶~合集58
我自己的原文哦~ https://blog.51cto.com/whaosoft/13967107 #CCA-Attention 全局池化局部保留,CCA-Attention为LLM长文本建模带来突破性进展 琶洲实验室、华南理工大学联合推出关键上下文感知注意力机制(CCA-Attention),…...

iPhone密码忘记了办?iPhoneUnlocker,iPhone解锁工具Aiseesoft iPhone Unlocker 高级注册版分享
平时用 iPhone 的时候,难免会碰到解锁的麻烦事。比如密码忘了、人脸识别 / 指纹识别突然不灵,或者买了二手 iPhone 却被原来的 iCloud 账号锁住,这时候就需要靠谱的解锁工具来帮忙了。Aiseesoft iPhone Unlocker 就是专门解决这些问题的软件&…...
渲染学进阶内容——模型
最近在写模组的时候发现渲染器里面离不开模型的定义,在渲染的第二篇文章中简单的讲解了一下关于模型部分的内容,其实不管是方块还是方块实体,都离不开模型的内容 🧱 一、CubeListBuilder 功能解析 CubeListBuilder 是 Minecraft Java 版模型系统的核心构建器,用于动态创…...
【android bluetooth 框架分析 04】【bt-framework 层详解 1】【BluetoothProperties介绍】
1. BluetoothProperties介绍 libsysprop/srcs/android/sysprop/BluetoothProperties.sysprop BluetoothProperties.sysprop 是 Android AOSP 中的一种 系统属性定义文件(System Property Definition File),用于声明和管理 Bluetooth 模块相…...

Cloudflare 从 Nginx 到 Pingora:性能、效率与安全的全面升级
在互联网的快速发展中,高性能、高效率和高安全性的网络服务成为了各大互联网基础设施提供商的核心追求。Cloudflare 作为全球领先的互联网安全和基础设施公司,近期做出了一个重大技术决策:弃用长期使用的 Nginx,转而采用其内部开发…...

CMake 从 GitHub 下载第三方库并使用
有时我们希望直接使用 GitHub 上的开源库,而不想手动下载、编译和安装。 可以利用 CMake 提供的 FetchContent 模块来实现自动下载、构建和链接第三方库。 FetchContent 命令官方文档✅ 示例代码 我们将以 fmt 这个流行的格式化库为例,演示如何: 使用 FetchContent 从 GitH…...

【笔记】WSL 中 Rust 安装与测试完整记录
#工作记录 WSL 中 Rust 安装与测试完整记录 1. 运行环境 系统:Ubuntu 24.04 LTS (WSL2)架构:x86_64 (GNU/Linux)Rust 版本:rustc 1.87.0 (2025-05-09)Cargo 版本:cargo 1.87.0 (2025-05-06) 2. 安装 Rust 2.1 使用 Rust 官方安…...