我正在嘗試使用Shake來構建Java代碼,並且由於javac編譯器的特殊性質而有點卡住了。一般而言,對於大型項目的每個模塊,編譯器都會以該模塊的源文件的全部作爲輸入來調用,並在一次傳遞中生成所有輸出文件。隨後,我們通常採用由編譯器生成的.class文件,並將它們組裝成一個JAR(基本上只是一個ZIP)。帶有Shake的多輸入多輸出編譯器
例如,一個典型的Java模塊項目安排如下:
- 包含多個.java文件一個
src
目錄,他們中的一些深嵌套在一個樹多層次。 - a
bin
包含編譯器輸出的目錄。通常這個輸出遵循相同的目錄結構和文件名,用.class
代替每個.java文件,但映射是而不是必然是一對一的:一個.java文件可以生成零到多個.class文件!因此
我想在搖定義的規則如下:
1)如果src
下任何文件比更新bin
下任何文件然後擦除bin
所有內容並重新創建搭配:
javac -d bin <recursive list of .java files under src>
我知道這個規則似乎過高,但沒有調用編譯器w^e無法知道單個輸入文件中的小變更所導致的輸出變化程度。
2)如果bin
下的任何文件比module.jar
更新,然後重新創建module.jar
有:
jar cf module.jar -C bin .
非常感謝!
PS對靜脈「只使用Ant/Maven/Gradle /」的反應將不會感激!我知道這些工具開箱即用地提供了Java編譯,但是它們更難以編寫和彙總。這就是爲什麼我想試驗一個基於Haskell/Shake的工具。
非常感謝尼爾!這基本上工作,但需要一些小的更改。例如,我們需要「需要」.java和.class文件的完整路徑,包括src/bin前綴。我們還需要在調用javac之前明確創建'bin' dir。我應該編輯你的答案嗎? –
是的請!我懷疑,如果將getDirectoryFiles更改爲「[」src // *。java「],比之前預先設置src更容易,儘管兩者的行爲應該完全相同(並且效率同樣高)。爲了創建目錄,你需要liftIO $ createDirectory - 通常這不是必要的,因爲shake會創建所有知道輸出的目錄,但是在這裏它不知道bin。 –
我正在做類似的事情,但是當我'需要'動態生成的FilePath時,我似乎進入了「在MVar操作中無限期地被阻塞的線程」。 – user239558