35.多个模块共用同一个jar包的正确姿势

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了35.多个模块共用同一个jar包的正确姿势相关的知识,希望对你有一定的参考价值。

参考技术A 在公司项目开发过程中,我负责钱包模块化拆分。由于自己对依赖掌握不好,拆分时遇到了一些个问题:多个模块需要共用同一个jar包。

在其中一个子模块的gradle中,将依赖改为如下,其他模块就可以用该模块下的jar包中的类了:

jar包的多层级maven依赖的坑与正确传递方法



这个问题简述起来就是项目加载jar包但是无法加载jar包的依赖

这是一个maven的特性吗?


问题发生前

程序猿经常自己写一些库实现或收集常用的逻辑方法(算法和设计模式等等),以方便多个项目使用,避免重复编码。本猿现在有这么一个库,本猿把他叫 E库E库用maven做工程和生命周期管理,以便能用到其他java工程中。同时库里面也引用了其他一些开源公共库,使用或包装他们以实现自己的功能。(如下是E库部分依赖截图)

E库的依赖的一部分
E库的依赖的一部分


本猿新建一个项目A,并引入这个自用的库,如果项目人多会用私库,多数情况不会超过5个人的,一般本猿会用项目中的文件夹做仓库。在项目A的pom.xml中加入这个文件夹做的仓库:

<repositories>
	<repository>
		<id>minimal-maven-repository</id>
		<url>file:///${project.basedir}/minimal-maven-repository</url>
		<layout>default</layout>
		<releases>
			<enabled>true</enabled>
		</releases>
		<snapshots>
			<enabled>true</enabled>
		</snapshots>
	</repository>
</repositories>

这里就用minimal-maven-repository这个文件夹做仓库。


现在,在项目A根目录执行如下命令把E库部署到这个仓库中:

VERSION=1.2.0-snapshot
mvn deploy:deploy-file -Dfile=/server/data/ejoker/target/ejoker-${VERSION}.jar -DgroupId=pro.jiefzz -DartifactId=ejoker -Dversion=${VERSION} -Dpackaging=jar -Durl=file:./minimal-maven-repository/ -DrepositoryId=minimal-maven-repository -DupdateReleaseInfo=true

如果用Nexus私库的话,上面这一步相当于把jar发布到私库,并在项目中引入私库地址。

其中:

选项 用途
-Dfile 指明部署的库的路径
-DgroupId 设置库的groupId
-DartifactId 设置库的唯一artifactId
-Dversion 设置当前要部署库的版本
-Dpackaging 部署的类型
-Durl 仓库的位置,这里用项目里的一个文件夹做仓库
-DrepositoryId 仓库的id,这个选项在部署到中央仓库时有用,这里自便
-DupdateReleaseInfo (字面意思理解)

如无意外大概会看到如下结果,即代表成功:

[INFO] Scanning for projects...
[INFO]                                                                         
[INFO] ------------------------------------------------------------------------
[INFO] Building willdelete 0.0.1-SNAPSHOT
[INFO] ------------------------------------------------------------------------
[INFO] 
[INFO] --- maven-deploy-plugin:2.7:deploy-file (default-cli) @ willdelete ---
Downloading: http://maven.aliyun.com/nexus/content/groups/public/org/codehaus/plexus/plexus-utils/1.5.6/plexus-utils-1.5.6.pom
Downloaded: http://maven.aliyun.com/nexus/content/groups/public/org/codehaus/plexus/plexus-utils/1.5.6/plexus-utils-1.5.6.pom (6 KB at 2.2 KB/sec)
Downloading: http://maven.aliyun.com/nexus/content/groups/public/org/codehaus/plexus/plexus/1.0.12/plexus-1.0.12.pom
Downloaded: http://maven.aliyun.com/nexus/content/groups/public/org/codehaus/plexus/plexus/1.0.12/plexus-1.0.12.pom (10 KB at 10.4 KB/sec)
Downloading: http://maven.aliyun.com/nexus/content/groups/public/org/codehaus/plexus/plexus-utils/1.5.6/plexus-utils-1.5.6.jar
Downloaded: http://maven.aliyun.com/nexus/content/groups/public/org/codehaus/plexus/plexus-utils/1.5.6/plexus-utils-1.5.6.jar (245 KB at 199.1 KB/sec)
Uploading: file:./minimal-maven-repository/pro/jiefzz/ejoker/1.2.0-snapshot/ejoker-1.2.0-snapshot.jar
Uploaded: file:./minimal-maven-repository/pro/jiefzz/ejoker/1.2.0-snapshot/ejoker-1.2.0-snapshot.jar (427 KB at 21306.2 KB/sec)
Uploading: file:./minimal-maven-repository/pro/jiefzz/ejoker/1.2.0-snapshot/ejoker-1.2.0-snapshot.pom
Uploaded: file:./minimal-maven-repository/pro/jiefzz/ejoker/1.2.0-snapshot/ejoker-1.2.0-snapshot.pom (398 B at 194.3 KB/sec)
Downloading: file:./minimal-maven-repository/pro/jiefzz/ejoker/maven-metadata.xml
Uploading: file:./minimal-maven-repository/pro/jiefzz/ejoker/maven-metadata.xml
Uploaded: file:./minimal-maven-repository/pro/jiefzz/ejoker/maven-metadata.xml (314 B at 153.3 KB/sec)
[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESS
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 5.570 s
[INFO] Finished at: 2019-09-26T21:29:43+08:00
[INFO] Final Memory: 8M/99M
[INFO] ------------------------------------------------------------------------

查看下minimal-maven-repository目录看看:

Jiefzzs-MacBook-Pro:willdelete kimffy$ tree minimal-maven-repository/
minimal-maven-repository/
└── pro
    └── jiefzz
        └── ejoker
            ├── 1.2.0-snapshot
            │   ├── ejoker-1.2.0-snapshot.jar
            │   ├── ejoker-1.2.0-snapshot.jar.md5
            │   ├── ejoker-1.2.0-snapshot.jar.sha1
            │   ├── ejoker-1.2.0-snapshot.pom
            │   ├── ejoker-1.2.0-snapshot.pom.md5
            │   └── ejoker-1.2.0-snapshot.pom.sha1
            ├── maven-metadata.xml
            ├── maven-metadata.xml.md5
            └── maven-metadata.xml.sha1

4 directories, 9 files

是不是跟你在别的仓库中看到的结构是一样的啊,仓库就是按这个结构装jar的。


现在,可以在项目A的pom.xml中引入E库以及一些项目中用到的库了:

    <dependency>
		<groupId>log4j</groupId>
		<artifactId>log4j</artifactId>
		<version>1.2.17</version>
	</dependency>
	<dependency>
		<groupId>org.slf4j</groupId>
		<artifactId>slf4j-log4j12</artifactId>
		<version>1.7.16</version>
	</dependency>
    <dependency>
		<groupId>pro.jiefzz</groupId>
		<artifactId>ejoker</artifactId>
		<version>1.2.0-snapshot</version>
	</dependency>
    <dependency>
		<groupId>org.apache.httpcomponents</groupId>
		<artifactId>httpclient</artifactId>
		<version>4.5.8</version>
	</dependency>

接下来,eclipse中

右键点击项目 -> maven -> update project

正常通过没毛病。


接下来在代码中使用项目A的写一段代码,并在里面用上E库

package pro.jiefzz.willdelete;

import pro.jiefzz.ejoker_support.rocketmq.DefaultMQConsumer;
import pro.jiefzz.ejoker_support.rocketmq.MQInstanceHelper;

/**
* Hello world!
*
*/
public class App 
{
    public static void main( String[] args )
    {
//        System.out.println( "Hello World!" );
        // 这个其实是E库中创建rocketmq客户端的一个助手类,没什么特别的逻辑的。
        DefaultMQConsumer createDefaultMQConsumer = MQInstanceHelper.createDefaultMQConsumer("", "127.0.0.1:9876", null);
    }
}

问题发生了

然后运行项目App主类:

eclipse点击运行App主类

鹅?! 找不到类?是本猿打开方式不对吗? 命令中敲一次mvn -Dmaven.test.skip=true clean compile package

eclipse点击运行App主类

-_-! 还真找不到啊。。。

java.lang.NoClassDefFoundError: org/apache/rocketmq/client/consumer/AllocateMessageQueueStrategy

这个明显是rocketmq的,而这个rocketmq的依赖不是E库带着的吗(参考上面的图)?难道本猿还要在项目A的pom.xml中贴一次E库的依赖吗?(其实本猿是故意调用E库中使用有依赖其他jar的代码的

以上是关于35.多个模块共用同一个jar包的正确姿势的主要内容,如果未能解决你的问题,请参考以下文章

thrift生产环境服务端使用的正确姿势

Maven 基础 | 解决依赖冲突的正确姿势

发布nuget包的正确姿势-保姆级教程

jar包的多层级maven依赖的坑与正确传递方法

发布nuget包的正确姿势---cicd自动打包发布nuget包

发布nuget包的正确姿势---cicd自动打包发布