2013-10-29 54 views
3

某些Clojure函數的文檔(例如defrecord)很長。在終端窗口運行Clojure時,我希望能夠通過尋呼機(如more(或less))發送doc的輸出。如果有人用Clojure寫的尋呼機功能,那麼我想我會喜歡的東西一起使用它:通過尋呼機發送Clojure'doc'輸出?

(with-out-str (doc defrecord)) 

或者,如果有一個實現尋呼機一個標準的Java類,我可以找出如何發送輸出到那個。

或者,我怎樣才能將doc的輸出發送到shell命令?這不會做的工作:

(clojure.java.shell/sh "more" :in (with-out-str (doc defrecord)))) 

[本主題是很難搜索到:「多」,「少」和「文檔」都顯得很常見的術語,事情就是這樣的「java尋呼機」彈出討論如何將文本分成多個頁面來格式化文檔。]

+0

爲什麼不直接寫一個打印文檔的程序然後將其傳遞給更多? – stonemetal

+1

'echo「(doc defrecord)」| clj | more' –

+2

每當你想要一個文檔字符串時旋轉一個完整的jvm clojure實例似乎有點極端 – noisesmith

回答

1
echo "(doc defrecord)" |clj|more 
2

您可以使用jline來實現此目的。如果您撥打setPaginationEnabled,請撥打true,並使用printColumns方法,在您的jline ConsoleReader上,它將顯示頁面。

但是,如果您試圖在標準的Leiningen REPL上執行此操作,事情會變得更加複雜。當前版本的Leiningen v2使用REPL-y,它在內部使用jline,但不使用printColumns,所以jline分頁被忽略。

但是,您可以通過REPL-y的ConsoleReader在reply.reader.simple-jline/jline-state中獲取當前的Leiningen REPL高度,並使用它來分割文檔字符串。

(defmacro doc2 [x] 
    `(let [h# (-> @reply.reader.simple-jline/jline-state :reader (.. getTerminal getHeight) (- 4)) 
     [s1# s2#] (split-at h# (-> ~x clojure.repl/doc with-out-str clojure.string/split-lines))] 
    (doseq [x# s1#] (println x#)) 
    (doseq [i# (partition-all h# s2#)] 
     (println "\n<more>") 
     (read-line) 
     (doseq [x# i#] (println x#))))) 

你會希望把這個宏放在profiles.clj:repl輪廓。

{:user {:plugins [...]} 
:repl {:repl-options {:init (defmacro doc2 [x] ...)}}} 

這把doc2宏在user命名空間,當你加載REPL。

+0

如果你使用這個,那麼'reply.reader.simple-jline/jline-state'就是特定於實現的單元,並且可能會在將來的REPLy版本中打破。另一個特定實現(可能會中斷)的解決方案在這裏:https://github.com/technomancy/leiningen/issues/1199#issuecomment-18815789 – trptcolin