簡體   English   中英

如何調試 Leiningen 生成的 jar 中的靜態初始化程序錯誤?

[英]How to debug static initialiser errors in jars generated by Leiningen?

在我的 Clojure 庫testlib ,我有一個帶有:gen-class指令的命名空間,如下所示:

(ns com.some_long_path.NewClass
  (:import (java.util List ArrayList))
  (:gen-class
     :name com.some_long_path.NewClass
     :methods [^{:static true} [getValues [String] java.util.List]]
  )
  (:require
    [testlib.core :refer [var1 var2]]))

(defn getValues [^String]
  (java.util.ArrayList. [3 5]))

如果我嘗試在testlib項目的另一個命名空間中import這個類(在調用compile ),我可以調用getValues方法而不會出錯。

不過,如果我lein install ,包括testlib在另一個項目jartest ,然后在下面的測試命名空間使用

(ns jartest.core
  (:import [com.some_long_path NewClass]))

(NewClass.)
(NewClass/getValues "some string")

調用NewClass構造函數會出現異常

CompilerException java.lang.NoClassDefFoundError: Could not initialize class com.some_long_path.NewClass

getValues作為結果給出

CompilerException java.lang.IllegalStateException: Attempting to call unbound fn: #'com.some_long_path.NewClass/getValues

但是,如果我從上面的NewClass命名空間定義中刪除require ,該代碼甚至可以在另一個庫中工作。 所以問題是由一些缺少的依賴項引起的,盡管我已經確保testlib所有依賴testlib也包含在jartest ,並且testlib.core命名空間是 AOT 編譯的。

另外,我嘗試反編譯生成的com.some_long_path.NewClass類文件,並且有一個靜態初始化塊,如下所示:

static
{
  Util.loadWithClass("/com/some_long_path/NewClass", NewClass.class);
}

很可能上述錯誤是從loadWithClass拋出的。 但我如何找出到底是哪里出了問題?

謝謝!

更新:我能夠通過二進制搜索錯誤找出我需要的命名空間中有什么問題(注釋掉代碼,直到事情再次運行)。 原來,一些文件被slurp編輯從resources文件夾中testlib ,但他們並沒有出現在jartest項目。 更改代碼以使用clojure.java.io/resource解決了該問題。 然而,問題仍然存在 - 如何在不訴諸蠻力方法的情況下確切地找出問題所在?

這是強制性的答案 - 沒有更好的方法,沒有更深入地理解依賴樹,這通常只能通過注釋掉內容並查看現在有效的方法來完成。 這是我從 clojure 加載 java 類和使用 gen-class 的經驗。

繼承人希望這不是最高投票的答案。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM