2024 年 Clojure 状况调查》中分享您的想法!

欢迎!请参阅关于页面以了解更多关于该功能的信息。

0
java.classpath

我有一个项目,该项目将数据存储在期望在类路径中找到的 resources 目录中。当项目使用 java.classpath 0.2.2 和 clojure-maven-plugin 1.3.20+ 时,调用 (java.classpath/classpath) 会产生意外的结果 - 显示一些 sun 东西,但没有依赖项,没有 clojure,没有我的代码或资源。看起来 Clojure 正在运行,只是对类路径 API 的调用存在问题。

比较:

java.classpath 0.1.0 和 c-m-plugin 1.3.9 表现正常。

java.classpath 0.1.0 和 c-m-plugin 1.3.20 可能会导致问题,并且有时类路径上只显示一个看似是空清单的单项。

在此处跨帖 clojure-maven-plugin
https://github.com/talios/clojure-maven-plugin/issues/81

8 个回答

0

此评论由:drlivingston 发布

在以下 java 版本中也有此问题
Java 版本:1.7.0_45,供应商:Oracle Corporation

0

此评论由:stuart.sierra 发布

我可以通过所有版本的 java.classpath 和 clojure-maven-plugin 1.3.13 及以后的版本来验证此行为。

从 clojure-maven-plugin 的 1.3.13 版本开始,该插件不再通过 {{-cp}} 在命令行上指定 Java 类路径,而是生成一个包含实际类路径的清单文件的临时 JAR 文件,并用 {{-jar}} 启动 Java。

请参阅 clojure-maven-plugin(链接:https://github.com/talios/clojure-maven-plugin/pull/58 文本:拉取请求 #58)(链接:https://github.com/talios/clojure-maven-plugin/commit/8d8e90e41806a6927c11347e6fc13344ba53c887 文本:提交 8d8e90e4)。

{{clojure.java.classpath/classpath}} 查看加载 Clojure 的类加载器,在此情况下是 {{sun.misc.Launcher$AppClassLoader}} 的子类加载器。AppClassLoader 是 (链接: http://docs.oracle.com/javase/6/docs/api/java/net/URLClassLoader.html 文本:URLClassLoader) 的子类,但其 (链接: http://docs.oracle.com/javase/6/docs/api/java/net/URLClassLoader.html#getURLs() 文本:getURLs) 方法只返回 JAR 文件的 URL。没有明显的 API 用于在不打开和读取 JAR 文件内容的情况下获取清单文件的 {{Class-Path}} 属性。

0
by

此评论由:stuart.sierra 发布

进一步深入 OpenJDK 源代码,URLClassLoader 会在需要时按需读取 JAR 清单文件以加载类或资源。要找到 URLClassLoader 可能打开的所有 URL 列表,就必须重新实现此逻辑以读取所有清单文件。它还必须是递归的(JAR 清单引用包含清单的另一个 JAR 文件)并且能检测到循环。

0
by

此评论由:drlivingston 发布

感谢您对此事的关注。
我理解的是,这是 clojure-maven-plungin 和 clojure.java.classpath 合作完成的功能的正确/期望的行为吗?

所以我正在检查 jar 文件,尽管我意识到我认为我没有查看嵌套的 jar 文件 - 类加载器会不会像嵌套文件一样检查?现在您说还有一个第三个案例我需要处理,对吧?清单文件? clojure.java.classpath 有用来读取它们的实用方法吗?

我一直在使用像这样的代码来识别类路径上的所有可访问内容

https://github.com/drlivingston/kr/blob/master/kr-core/src/main/clojure/edu/ucdenver/ccp/utils.clj#L101

谢谢,
Kevin

0
by

此评论由:stuart.sierra 发布

目前,clojure.java.classpath 既不处理 JAR 清单文件也不处理嵌套 JAR 文件。正如我在先前的评论中所述,支持这些功能将是困难的,并且短期内不太可能成为我的优先事项。我愿意审阅一个补丁以添加此功能,但它必须证明它能防止递归循环。

根据我对 (链接: http://docs.oracle.com/javase/7/docs/technotes/guides/jar/jar.html 文本:JAR 文件规范) 的阅读,clojure-maven-plugin 的行为可能与 JAR 规范的精神相悖,该规范如此描述 "Class-Path" 清单属性

{quote}
"Class-Path: 此属性的值指定了该应用程序或扩展需要的相关扩展或库的相对 URL。"(加了着重号)
{quote}

clojure-maven-plugin 创建了一个带有 "Class-Path" 属性的 JAR 清单,该属性包含指向其他没有嵌入含清单的 JAR 文件中 JAR 文件的绝对 URL。

我总是认为只有当打包完整的应用程序或JDK扩展时,才使用具有类路径(Class-Path)属性的JAR清单文件,而不是作为一种在开发期间指定类路径的机制。很明显,这是可能的,就像目前的clojure-maven-plugin所展示的那样,但这不是我希望依赖的功能。

一般来说,JDK不支持枚举类路径上的所有文件,因为类路径可以包含指向远程资源的URL,这些资源在需要时下载。

0

此评论由:drlivingston 发布

有趣。我没有意识到这些功能如此灵活。
感谢您的评论。

因此,对CP进行递归迭代似乎可能是一件不好的事情,尽管我想这并不比您恰好请求加载位于CP最里面的、最深的角落中的内容更糟,对吧?

我把资源文件放在CP上,然后让应用程序通过它们名称的前缀来查找它们。例如,查找所有“foo.bar”,然后我会得到“foo.bar.baz1”和“foo.bar.baz2”等等,而无需应用程序知道那里有什么,也不需要生成或维护清单。这是处理类路径上资源的已知反模式吗?

0

此评论由:stuart.sierra 发布

{quote}
这是处理类路径上资源的已知反模式吗?
{quote}

是的。

0
参考:[链接](https://clojure.atlassian.net/browse/CLASSPATH-6)(由 alex+import 报告)
...