有没有办法从本地 jar 在 pom 文件中创建 Maven 依赖项
Is there a way to create maven dependency in pom file from a local jar
有一个 java 项目有太多的 jar 文件,很难管理所有这些文件。我知道有一种方法可以将此项目转换为 maven 项目,但我不想手动将项目中每个 jar 的依赖项添加到 pom 文件中。
有什么方法可以使用本地 jar 文件创建 pom 文件,使 pom 包含每个 jar 的依赖项标记。
编辑:我想澄清一下,我不想添加 jars from/to 本地存储库。
本地存储库方法对我不起作用,因为该项目将由不同系统的多个用户使用。
我想为已有的 jar 文件创建常规的 pom 依赖项以及 groupId、artifactId 和版本,以便在将项目转换为 Maven 项目时将其复制粘贴到 pom 文件中。由于我的项目中有大量 JAR,因此我必须全部手动完成。
@Milen Dyankov 提供的解决方案对我有用。我能够从大多数 JAR 文件中获得我需要的信息。
您可以手动将 JAR 安装到本地 Maven 存储库
第一种方式
按照此处的步骤操作
mvn install:install-file -Dfile=<path-to-file>
在这里您可以在命令行中添加这些信息
mvn install:install-file -Dfile=<path-to-file> -DgroupId=<group-id> -DartifactId=<artifact-id> -Dversion=<version>
<path-to-file>
提到了要安装的 JAR 的路径
<group-id>
提到要安装的 JAR 的组 ID
<artifact-id>
提到了要安装的 JAR 的工件 ID
<version>
提到的JAR版本
第二种方式
您可以创建不同的本地 Maven 存储库
按照步骤操作
我们可以考虑将新的本地 Maven 存储库命名为 maven-repository
,位于 ${basedir}
(包含 pom.xml 的目录)中。
在新的本地 Maven 存储库中部署本地 JAR,如下所示
mvn deploy:deploy-file -Dfile=<path-to-file> -DgroupId=<group-id> -DartifactId=<artifact-id> -Dversion=<version> -Dpackaging=jar -Durl=file:./maven-repository/ -DrepositoryId=maven-repository -DupdateReleaseInfo=true
你可以看到哪个 maven deploy:deploy-file
在远程存储库中安装了工件,但这里的存储库位于本地计算机中
安装 JAR 后,您需要在 pom.xml 文件中添加存储库
<repositories>
<repository>
<id>maven-repository</id>
<url>file:///${project.basedir}/maven-repository</url>
</repository>
</repositories>
据我所知,Maven 无法做到这一点。
您可以编写一个脚本来计算每个 jar 的 SHA1 值并在您的 Maven 存储库中搜索该 jar。或者,它可以打开罐子并搜索 pom.properties
以提取 Maven 坐标。
无论如何,这可能是编程工作量太大,除非您需要为许多项目这样做。
这个代码
public static void main(String[] args) throws IOException {
Set<String> missingMavenData = new HashSet<String>();
String FOLDER = "/path/to/your/folder/with/jars";
Files
.walk(Paths.get(FOLDER), FileVisitOption.FOLLOW_LINKS)
.map(Path::toFile)
.filter(f -> f.isFile())
.filter(f -> f.getName().endsWith(".jar"))
.map(f -> {
try {
return new JarFile(f);
} catch (IOException e) {
e.printStackTrace();
return null;
}
})
.filter(Objects::nonNull)
.map(jar -> {
Properties properties = null;
Enumeration<JarEntry> entries = jar.entries();
while (entries.hasMoreElements()) {
JarEntry jarEntry = entries.nextElement();
if (jarEntry.getName().matches("^META-INF/maven/.*/pom\.properties$")) {
try {
properties = new Properties();
properties.load(jar.getInputStream(jarEntry));
break;
} catch (IOException e) {
e.printStackTrace();
}
};
}
if (properties == null) {
missingMavenData.add(jar.getName());
}
return properties;
})
.filter(Objects::nonNull)
.forEach(properties -> {
System.out.println("<depencency>");
System.out.println(" <groupId>" + properties.getProperty("groupId")+ "</groupId>");
System.out.println(" <artifactId>" + properties.getProperty("artifactId")+ "</artifactId>");
System.out.println(" <version>" + properties.getProperty("version")+ "</version>");
System.out.println("</depencency>");
});
System.out.println("Those JAR files do not contain Maven metadata:");
missingMavenData.forEach(System.out::println);
}
将遍历您的 jar 文件并尝试在其中找到 Maven 元数据。它将为拥有它的人生成 POM 条目,并列出那些没有它的人,以便您可以手动添加它。希望对您有所帮助。
更新:
我在 BOM Helper Maven Plugin 中添加了 bom-helper:fromJars
目标,它的作用与上述代码大致相同。现在可以简单地添加插件
<plugin>
<groupId>com.commsen.maven</groupId>
<artifactId>bom-helper-maven-plugin</artifactId>
<version>0.2.0</version>
</plugin>
并将其配置为调用 fromJars
目标。也可以称为窗体命令行。例如:
mvn bom-helper:fromJars \
-Dbom-helper.jarsFolder=/path/to/folder/with/jars \
-Dbom-helper.inplace=true \
-Dbom-helper.recursive
将使用其中包含 Maven 元数据的所有 jar 的条目更新当前 pom。
您需要的是仅在您的服务器中可用的本地 maven nexus。考虑到你有只对你可用的罐子,我想你有它们的来源。因此,您应该能够将它们转换为 Maven 项目并将它们部署到您的本地 Nexus 中。结构固定后,maven会在解析项目时下载你的依赖和依赖的依赖。
或者您可以使用 <scope>system</scope>
,但这需要绝对路径,通常不建议这样做。
有一个 java 项目有太多的 jar 文件,很难管理所有这些文件。我知道有一种方法可以将此项目转换为 maven 项目,但我不想手动将项目中每个 jar 的依赖项添加到 pom 文件中。
有什么方法可以使用本地 jar 文件创建 pom 文件,使 pom 包含每个 jar 的依赖项标记。
编辑:我想澄清一下,我不想添加 jars from/to 本地存储库。 本地存储库方法对我不起作用,因为该项目将由不同系统的多个用户使用。
我想为已有的 jar 文件创建常规的 pom 依赖项以及 groupId、artifactId 和版本,以便在将项目转换为 Maven 项目时将其复制粘贴到 pom 文件中。由于我的项目中有大量 JAR,因此我必须全部手动完成。
@Milen Dyankov 提供的解决方案对我有用。我能够从大多数 JAR 文件中获得我需要的信息。
您可以手动将 JAR 安装到本地 Maven 存储库
第一种方式
按照此处的步骤操作
mvn install:install-file -Dfile=<path-to-file>
在这里您可以在命令行中添加这些信息
mvn install:install-file -Dfile=<path-to-file> -DgroupId=<group-id> -DartifactId=<artifact-id> -Dversion=<version>
<path-to-file>
提到了要安装的 JAR 的路径
<group-id>
提到要安装的 JAR 的组 ID
<artifact-id>
提到了要安装的 JAR 的工件 ID
<version>
提到的JAR版本
第二种方式
您可以创建不同的本地 Maven 存储库
按照步骤操作
我们可以考虑将新的本地 Maven 存储库命名为 maven-repository
,位于 ${basedir}
(包含 pom.xml 的目录)中。
在新的本地 Maven 存储库中部署本地 JAR,如下所示
mvn deploy:deploy-file -Dfile=<path-to-file> -DgroupId=<group-id> -DartifactId=<artifact-id> -Dversion=<version> -Dpackaging=jar -Durl=file:./maven-repository/ -DrepositoryId=maven-repository -DupdateReleaseInfo=true
你可以看到哪个 maven deploy:deploy-file
在远程存储库中安装了工件,但这里的存储库位于本地计算机中
安装 JAR 后,您需要在 pom.xml 文件中添加存储库
<repositories>
<repository>
<id>maven-repository</id>
<url>file:///${project.basedir}/maven-repository</url>
</repository>
</repositories>
据我所知,Maven 无法做到这一点。
您可以编写一个脚本来计算每个 jar 的 SHA1 值并在您的 Maven 存储库中搜索该 jar。或者,它可以打开罐子并搜索 pom.properties
以提取 Maven 坐标。
无论如何,这可能是编程工作量太大,除非您需要为许多项目这样做。
这个代码
public static void main(String[] args) throws IOException {
Set<String> missingMavenData = new HashSet<String>();
String FOLDER = "/path/to/your/folder/with/jars";
Files
.walk(Paths.get(FOLDER), FileVisitOption.FOLLOW_LINKS)
.map(Path::toFile)
.filter(f -> f.isFile())
.filter(f -> f.getName().endsWith(".jar"))
.map(f -> {
try {
return new JarFile(f);
} catch (IOException e) {
e.printStackTrace();
return null;
}
})
.filter(Objects::nonNull)
.map(jar -> {
Properties properties = null;
Enumeration<JarEntry> entries = jar.entries();
while (entries.hasMoreElements()) {
JarEntry jarEntry = entries.nextElement();
if (jarEntry.getName().matches("^META-INF/maven/.*/pom\.properties$")) {
try {
properties = new Properties();
properties.load(jar.getInputStream(jarEntry));
break;
} catch (IOException e) {
e.printStackTrace();
}
};
}
if (properties == null) {
missingMavenData.add(jar.getName());
}
return properties;
})
.filter(Objects::nonNull)
.forEach(properties -> {
System.out.println("<depencency>");
System.out.println(" <groupId>" + properties.getProperty("groupId")+ "</groupId>");
System.out.println(" <artifactId>" + properties.getProperty("artifactId")+ "</artifactId>");
System.out.println(" <version>" + properties.getProperty("version")+ "</version>");
System.out.println("</depencency>");
});
System.out.println("Those JAR files do not contain Maven metadata:");
missingMavenData.forEach(System.out::println);
}
将遍历您的 jar 文件并尝试在其中找到 Maven 元数据。它将为拥有它的人生成 POM 条目,并列出那些没有它的人,以便您可以手动添加它。希望对您有所帮助。
更新:
我在 BOM Helper Maven Plugin 中添加了 bom-helper:fromJars
目标,它的作用与上述代码大致相同。现在可以简单地添加插件
<plugin>
<groupId>com.commsen.maven</groupId>
<artifactId>bom-helper-maven-plugin</artifactId>
<version>0.2.0</version>
</plugin>
并将其配置为调用 fromJars
目标。也可以称为窗体命令行。例如:
mvn bom-helper:fromJars \
-Dbom-helper.jarsFolder=/path/to/folder/with/jars \
-Dbom-helper.inplace=true \
-Dbom-helper.recursive
将使用其中包含 Maven 元数据的所有 jar 的条目更新当前 pom。
您需要的是仅在您的服务器中可用的本地 maven nexus。考虑到你有只对你可用的罐子,我想你有它们的来源。因此,您应该能够将它们转换为 Maven 项目并将它们部署到您的本地 Nexus 中。结构固定后,maven会在解析项目时下载你的依赖和依赖的依赖。
或者您可以使用 <scope>system</scope>
,但这需要绝对路径,通常不建议这样做。