Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/324.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
我可以在运行时确定Java库的版本吗?_Java_Libraries - Fatal编程技术网

我可以在运行时确定Java库的版本吗?

我可以在运行时确定Java库的版本吗?,java,libraries,Java,Libraries,有可能在运行时确定第三方Java库的版本吗?尽管没有通用标准,但存在一种适用于大多数开源库的黑客攻击,或者通过Maven发布插件或兼容机制通过Maven存储库发布的任何东西。由于JVM上的大多数其他构建系统都是Maven兼容的,因此这应该也适用于通过Gradle或Ivy(可能还有其他)分发的库 Maven release插件(以及所有兼容的进程)在发布的Jar中创建一个名为META-INF/${groupId}.${artifactId}/pom.properties,其中包含属性groupId

有可能在运行时确定第三方Java库的版本吗?

尽管没有通用标准,但存在一种适用于大多数开源库的黑客攻击,或者通过Maven发布插件或兼容机制通过Maven存储库发布的任何东西。由于JVM上的大多数其他构建系统都是Maven兼容的,因此这应该也适用于通过Gradle或Ivy(可能还有其他)分发的库

Maven release插件(以及所有兼容的进程)在发布的Jar中创建一个名为
META-INF/${groupId}.${artifactId}/pom.properties
,其中包含属性
groupId
artifactId
version

通过检查并解析该文件,我们可以检测出大多数库版本的版本。示例代码(Java 8或更高版本):

输出,在我的机器上:

Optional[0.9.2]
Optional[24.1-jre]
Optional.empty

第三方Java库意味着一个Jar文件,Jar文件清单具有专门用于指定库版本的属性

注意:并非所有Jar文件都会指定版本,即使它们应该指定

Java内置的读取信息的方法是使用反射,但需要知道库中的某个类才能进行查询。不管是哪个类/接口

范例


正如我曾经被指派为许多非常传统的Java项目执行此任务一样,答案是“可以完成,但如何完成取决于”

首先,检查JAR MANIFEST.MF文件。有时候你会很幸运

其次,扫描JAR文件以查找版本字段。有时候你会很幸运,有时候这种价值观也会存在

第三,扫描包含的属性文件。有一种常见的ANT构建模式将版本保存在属性文件中(在属性文件中更容易更新)

第四,开始下载该项目可用的JAR文件。有时版本号确实丢失了,验证它的唯一方法是找到一个已知的旧版本并进行JAR到JAR的比较


还有其他技术,但这4种技术几乎涵盖了所有场景。对于一些名称很差的小众库来说,这可能是一个相当大的挑战。

最好打印出
名称,而不是
可选的
@ScaryWombat是的,但是如果没有版本,你会怎么做?很好的解决方案,谢谢。你说得对,这是更标准的方法。然而,Maven方式是由主要存储库的管理员实施的,因此它更可靠。理想情况下,我想我应该结合这些方法。#4是有趣的,同时也是悲伤的,刚从一部迪尔伯特卡通中脱颖而出。在那里,感受痛苦。
public static void main(String[] args) {
    Stream.of(io.vavr.collection.LinkedHashMultimap.class,
              com.google.common.collect.LinkedHashMultimap.class,
              java.util.LinkedHashMap.class)
          .map(VersionExtractor::extractVersion)
          .forEach(System.out::println);
}
Optional[0.9.2]
Optional[24.1-jre]
Optional.empty
public class Test {
    public static void main(String[] args) {
        printVersion(org.apache.http.client.HttpClient.class);
        printVersion(com.fasterxml.jackson.databind.ObjectMapper.class);
        printVersion(com.google.gson.Gson.class);
    }
    public static void printVersion(Class<?> clazz) {
        Package p = clazz.getPackage();
        System.out.printf("%s%n  Title: %s%n  Version: %s%n  Vendor: %s%n",
                          clazz.getName(),
                          p.getImplementationTitle(),
                          p.getImplementationVersion(),
                          p.getImplementationVendor());
    }
}