15

Customizing your REPL in clj

 3 years ago
source link: https://insideclojure.org/2020/02/11/custom-repl/
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.

Customizing your REPL in clj

There was a question on Slack this evening about getting a similar effect to the injections feature of Leiningen in clj. There is no built-in feature for this, but you don’t really need one. The provided clojure.main/repl function is highly customizable. For example, it provides an :eval hook, which defaults to just the eval function.

But that’s a great place to inject your own code around every eval, you’re almost there. At an existing repl, you can try a program like this to start a new nested repl with that function:

(require '[clojure.main :as m])
(m/repl
  :init #(apply require m/repl-requires) 
  :eval (fn [form]
          (do
            (require '[clojure.pprint :refer [pp]])
            (eval form))))

The :init hook replicates what clojure.main uses as an initial binding set, so it’s good to repeat that. The :eval hook just does an additional referral, making pp always available.

You can start this as your actual repl at a command line by just smooshing it all together:

clj -e "(require '[clojure.main :as m]) \
        (m/repl :init #(apply require m/repl-requires) \
        :eval (fn [form] (do (require '[clojure.pprint :refer [pp]]) \
        (eval form))))"

Or you can pack it into your deps.edn (using the Corfield comma as bash-safe whitespace):

{:aliases {:repl {:main-opts ["-e" "(require,'[clojure.main,:as,m])(m/repl,:init,#(apply,require,m/repl-requires),:eval,(fn,[form],(do,(require,'[clojure.pprint,:refer,[pp]])(eval,form))))"]}}}

then just clj -A:repl

It would be pretty easy to wrap this tiny program into a tool with the injections as an argument for reuse but not sure it’s worth that.

Written on February 11, 2020

About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK