[非著者からの編集:これは2010年のものであり、プロセスは2011年5月から大幅に簡素化されています。2012年2月のセットアップノートとともに、この回答に投稿を追加します。]
Emacs、SLIME(Clojureと完全に連携します-swank-clojureを参照)、swank-clojure(SLIMEの対応するサーバーのClojure実装)、clojure-mode、Pareditなどのいくつかの要素をまとめる必要があります。もちろん、最初はClojure jarで、次にLeiningenがおそらく最も注目に値するいくつかの追加機能があります。すべてを設定すると、Emacs内で、質問で言及したすべてのワークフロー/編集機能が利用できるようになります。
基本設定:
以下は、これらすべてを設定する方法を説明する優れたチュートリアルです。Webには他にもありますが、他のいくつかはかなり時代遅れですが、これら2つは今のところ問題ないようです。
PhilHagelbergのブログに投稿されたclojureの作者に関する取引のトリックが見つかりました。Philは、swank-clojureとclojure-modeのほか、Emacsの世界に初めて来た人なら誰でも見ることをお勧めするEmacsスターターキットと呼ばれるパッケージを維持しています。これらの指示は、インフラストラクチャへの最近の変更で最新のものになっているようです。疑わしい場合は、ClojureのGoogleグループで追加情報を探してください。
Clojure、Incanter、Emacs、Slime、Swank、およびPareditの設定は、Incanterプロジェクトのブログに投稿されます。Incanterは、Clojureに直接埋め込まれた統計計算用のRのようなDSLを提供する魅力的なパッケージです。この投稿は、Incanterを使用する予定がない場合、またはインストールする予定がない場合でも役立ちます。
すべてを機能させる:
これらすべてを設定したら、すぐに使用を開始できますが、次のことを強くお勧めします。
SLIMEのマニュアルをご覧ください。ソースに含まれており、実際には非常に読みやすくなっています。また、50ページのモンスターマニュアル全体を読む必要がある理由はまったくありません。利用可能な機能を確認するために周りを見てください。
注:最新のアップストリームソースにあるSLIMEのautodoc機能はswank-clojureと互換性がありません-Phil HagelbergがELPAバージョンを使用するように推奨している場合、この問題は発生しません(説明については前述のブログ投稿を参照してください)または、autodocをオフのままにします(これはデフォルトの状態です)。後者のオプションには、Common Lispで最新のSLIMEを使用する場合でも使用できるという、いくつかの追加の魅力があります。
pareditのドキュメントをご覧ください。これを行うには2つの方法があります。(1)ソースを確認します。ファイルの先頭には、必要になる可能性のあるすべての情報を含む大量のコメントがあります。(2)C-h mparedit-modeがアクティブなときにEmacsと入力します-バッファがポップアップし、現在のメジャーモードに関する情報に続いて、すべてのアクティブなマイナーモードに関する情報が表示されます(pareditはその1つです)。
更新: Phil HagelbergによるPareditでこのクールなメモのセットを見つけました...これはテキストファイルへのリンクです。この情報が記載された素晴らしいスライドのセットをどこかで見たのを覚えていますが、今は見つからないようです。 。とにかく、それはそれがどのように機能するかについての素晴らしい要約です。間違いなくそれを見てください、私は今Pareditなしでは生きられません、そしてこのファイルはそれを使い始めるのを非常に簡単にするはずです、と私は信じます。:-)
実際、このC-h m組み合わせにより、SLIME REPL、clojureモード(C-c C-kコンパイルのために現在のバッファーを送信するために覚えておく必要があります)、そして実際にEmacsバッファーでアクティブなすべてのキーバインディングについて知ることができます。
ファイルからコードをロードした後、REPLでそれを実験用として:前述の使用C-c C-k次に、現在のバッファをコンパイルするために組み合わせてuse
又はrequire
REPLでその名前空間。次に、実験してください。
最後の注意:
すべてがクリックされる前に、しばらくの間調整する必要があることに備えてください。関係するツールはたくさんあり、それらの相互作用はほとんどスムーズですが、最初にいくつかの調整を行う必要がないと想定しても安全なほどではありません。
最後に、.emacs
他では見つけられないコードを少し示します(ただし、Phil Hagelbergによるクールな関数に基づいています)。私は、スワンクインスタンスをlein swank
(Leiningenのクールな機能の1つ)でclojure-project
開始することと、以下に示す関数を使用してEmacs内からすべてを開始することを交互に行います。私は、後者がによって提供される環境と厳密に一致する環境を生成するように最善を尽くしましたlein swank
。ああ、そしてEmacsでREPLを使ってすばやく汚い実験をしたいだけなら、正しい設定でM-x slime直接使用できるはずです。
(setq clojure-project-extra-classpaths
'(
"src/"
"classes/"
"test/"
))
(setq clojure-project-jar-classpaths
'(
"lib/"
))
(defun find-clojure-project-jars (path)
(apply #'append
(mapcar (lambda (d)
(loop for jar in (remove-if (lambda (f) (member f '("." "..")))
(directory-files d t))
collect jar into jars
finally return jars))
(remove-if-not #'file-exists-p
clojure-project-jar-classpaths))))
(defun find-clojure-jar (jars)
(let ((candidates
(remove-if-not
(lambda (jar)
(string-match-p "clojure\\([0-9.-]+\\(SNAPSHOT|MASTER\\)?\\)?\\.jar$" jar))
jars)))
(if candidates
(car candidates)
(expand-file-name "~/.clojure/clojure.jar"))))
(defun find-clojure-contrib-jar (jars)
(let ((candidates
(remove-if-not
(lambda (jar)
(string-match-p "clojure-contrib\\([0-9.-]+\\(SNAPSHOT|MASTER\\)?\\)?\\.jar$" jar))
jars)))
(if candidates
(car candidates)
(expand-file-name "~/.clojure/clojure-contrib.jar"))))
(defun clojure-project (path)
"Sets up classpaths for a clojure project and starts a new SLIME session.
Kills existing SLIME session, if any."
(interactive (list (ido-read-directory-name
"Project root:"
(locate-dominating-file default-directory "pom.xml"))))
(when (get-buffer "*inferior-lisp*")
(kill-buffer "*inferior-lisp*"))
(cd path)
(let* ((jars (find-clojure-project-jars path))
(clojure-jar (find-clojure-jar jars))
(clojure-contrib-jar (find-clojure-contrib-jar jars)))
(setq swank-clojure-binary nil
swank-clojure-jar-path clojure-jar
swank-clojure-extra-classpaths
(cons clojure-contrib-jar
(append (mapcar (lambda (d) (expand-file-name d path))
clojure-project-extra-classpaths)
(find-clojure-project-jars path)))
swank-clojure-extra-vm-args
(list (format "-Dclojure.compile.path=%s"
(expand-file-name "classes/" path)))
slime-lisp-implementations
(cons `(clojure ,(swank-clojure-cmd) :init swank-clojure-init)
(remove-if #'(lambda (x) (eq (car x) 'clojure))
slime-lisp-implementations))))
(slime))