Expanded Clojure to really work
Lots of leader keys to tie into Cider.
This commit is contained in:
		
							parent
							
								
									16cf7659e6
								
							
						
					
					
						commit
						a8e5fec161
					
				
					 1 changed files with 164 additions and 26 deletions
				
			
		|  | @ -24,12 +24,13 @@ A literate programming file for programming in Clojure. | ||||||
|   ;; |   ;; | ||||||
|   ;;; Code: |   ;;; Code: | ||||||
|   #+end_src |   #+end_src | ||||||
| I like [[http://clojure.org][Clojure]] as a /modern Lisp/, but I don’t get to play with it much. | I like [[http://clojure.org][Clojure]] as a /modern Lisp/, but I don’t get to play with it much anymore. 😢 | ||||||
| The following instructions create a fully blinged-out Emacs-Clojure setup. | The following instructions create a fully blinged-out Emacs-Clojure setup. | ||||||
| * Introduction | * Introduction | ||||||
| To get Clojure working on a new system, try the following on a Mac: | To get Clojure working on a new system, try the following on a Mac: | ||||||
| #+begin_src sh | #+begin_src sh | ||||||
|   brew install clojure/tools/clojure |   brew install clojure/tools/clojure | ||||||
|  |   brew install leiningen | ||||||
| #+end_src | #+end_src | ||||||
| 
 | 
 | ||||||
| And make sure it works: | And make sure it works: | ||||||
|  | @ -42,24 +43,31 @@ Or by starting a REPL: | ||||||
|   clj |   clj | ||||||
| #+end_src | #+end_src | ||||||
| 
 | 
 | ||||||
| Also, download this script: |  | ||||||
| #+begin_src sh |  | ||||||
|   curl -o ~/bin/lein https://raw.githubusercontent.com/technomancy/leiningen/stable/bin/lein |  | ||||||
|   chmod u+x ~/bin/lein |  | ||||||
| #+end_src |  | ||||||
| 
 |  | ||||||
| Then for each project, create the project directory with this command: | Then for each project, create the project directory with this command: | ||||||
| #+begin_src sh | #+begin_src sh | ||||||
|   lein new app fresh-app |   lein new app fresh-app | ||||||
| #+end_src | #+end_src | ||||||
| * Emacs Support | * Emacs Support | ||||||
| We begin with using [[https://github.com/clojure-emacs/clojure-mode/][clojure-mode]]: | Let’s create a keybinding menu of Clojure-related commands: | ||||||
|  | #+begin_src emacs-lisp | ||||||
|  |   (general-create-definer ha-clojure-leader | ||||||
|  |         :states '(normal visual motion) | ||||||
|  |         :keymaps 'clojure-mode-map | ||||||
|  |         :prefix "SPC m" | ||||||
|  |         :global-prefix "<f17>" | ||||||
|  |         :non-normal-prefix "S-SPC") | ||||||
|  | #+end_src | ||||||
|  | 
 | ||||||
|  | Next, install and configure [[https://github.com/clojure-emacs/clojure-mode/][clojure-mode]]: | ||||||
| #+begin_src emacs-lisp | #+begin_src emacs-lisp | ||||||
|   (use-package clojure-mode |   (use-package clojure-mode | ||||||
|     :init |     :init | ||||||
|     (add-to-list 'org-babel-load-languages '(clojure . t)) |     (add-to-list 'org-babel-load-languages '(clojure . t)) | ||||||
| 
 | 
 | ||||||
|     :config |     :config | ||||||
|  |     ;; Predefine a "help" sequence used later on: | ||||||
|  |     (ha-clojure-leader "h" '(:ignore t :which-key "help")) | ||||||
|  | 
 | ||||||
|     (defun ha-prettify-clojure () |     (defun ha-prettify-clojure () | ||||||
|       "Make the Clojure syntax prettier." |       "Make the Clojure syntax prettier." | ||||||
|       (push '("fn"   . ?𝝀) prettify-symbols-alist) |       (push '("fn"   . ?𝝀) prettify-symbols-alist) | ||||||
|  | @ -72,35 +80,155 @@ We begin with using [[https://github.com/clojure-emacs/clojure-mode/][clojure-mo | ||||||
| Need the IDE feature of [[https://github.com/clojure-emacs/cider][Cider]]: | Need the IDE feature of [[https://github.com/clojure-emacs/cider][Cider]]: | ||||||
| #+begin_src emacs-lisp | #+begin_src emacs-lisp | ||||||
|   (use-package cider |   (use-package cider | ||||||
|     :commands (cider cider-connect cider-jack-in) |     :after clojure-mode | ||||||
|  |     :commands (cider-connect cider-jack-in cider) | ||||||
|     :init |     :init | ||||||
|     (setq cider-auto-select-error-buffer nil |     (setq cider-show-error-buffer t | ||||||
|  |           ;; The use of paredit when editing Clojure (or any other Lisp) code is | ||||||
|  |           ;; highly recommended. You're probably using it already in your | ||||||
|  |           ;; clojure-mode buffers (if you're not you probably should). You might | ||||||
|  |           ;; also want to enable paredit in the REPL buffer as well. | ||||||
|  |           ;; (add-hook 'cider-repl-mode-hook #'paredit-mode) | ||||||
|  | 
 | ||||||
|  |           ;; Don't select the error buffer when it's displayed: | ||||||
|  |           cider-auto-select-error-buffer nil | ||||||
|  | 
 | ||||||
|  |           ;; Controls whether to pop to the REPL buffer on connect. | ||||||
|           cider-repl-pop-to-buffer-on-connect nil |           cider-repl-pop-to-buffer-on-connect nil | ||||||
|  | 
 | ||||||
|           cider-repl-use-clojure-font-lock t |           cider-repl-use-clojure-font-lock t | ||||||
|  | 
 | ||||||
|  |           ;; T to wrap history around when the end is reached. | ||||||
|           cider-repl-wrap-history t |           cider-repl-wrap-history t | ||||||
|  | 
 | ||||||
|           cider-repl-history-size 1000 |           cider-repl-history-size 1000 | ||||||
|           cider-show-error-buffer t | 
 | ||||||
|  |           ;; Hide `*nrepl-connection*' and `*nrepl-server*' buffers from appearing | ||||||
|  |           ;; in some buffer switching commands like switch-to-buffer | ||||||
|           nrepl-hide-special-buffers t |           nrepl-hide-special-buffers t | ||||||
|  | 
 | ||||||
|           ;; Stop error buffer from popping up while working in buffers other than the REPL: |           ;; Stop error buffer from popping up while working in buffers other than the REPL: | ||||||
|           nrepl-popup-stacktraces nil)) |           nrepl-popup-stacktraces nil) | ||||||
|  | 
 | ||||||
|  |     ;; Enabling CamelCase support for editing commands (like forward-word, | ||||||
|  |     ;; backward-word, etc) in the REPL is quite useful since we often have | ||||||
|  |     ;; to deal with Java class and method names. The built-in Emacs minor | ||||||
|  |     ;; mode subword-mode provides such functionality | ||||||
|  |     :hook (cider-repl-mode . #'subword-mode) | ||||||
|  | 
 | ||||||
|  |     :config | ||||||
|  |     (ha-clojure-leader | ||||||
|  |      "w" '(:ignore t :which-key "cider") | ||||||
|  |      "w s" '("start" . cider-jack-in) | ||||||
|  |      "w r" '("restart" . cider-restart) | ||||||
|  |      "w c" '("connect" . cider-connect) | ||||||
|  |      "w b" '("switch" . cider-switch-repl-buffer) | ||||||
|  |      "w n" '("namespace" . cider-repl-set-ns) | ||||||
|  |      "w e" '("describe" . cider-describe-connection) | ||||||
|  |      "w x" '("interrupt" . cider-interrupt) | ||||||
|  |      "w q" '("quit" . cider-quit) | ||||||
|  | 
 | ||||||
|  |      "b" '(:ignore t :which-key "load") | ||||||
|  |      "b b" '("load buffer" . cider-load-buffer) | ||||||
|  |      "b f" '("load file" . cider-load-file) | ||||||
|  |      "b f" '("load all" . cider-load-all-files) | ||||||
|  |      "b r" '("refresh all" . cider-ns-refresh) | ||||||
|  | 
 | ||||||
|  |      "e" '(:ignore t :which-key "eval") | ||||||
|  |      "e e" '("last s-expr" . cider-eval-last-sexp) | ||||||
|  |      "e E" '("replace s-expr" . cider-eval-last-sexp-and-replace) | ||||||
|  |      "e ." '("s-expr point" . cider-eval-sexp-at-point) | ||||||
|  |      "e f" '("defun" . cider-eval-defun-at-point) | ||||||
|  |      "e F" '("file" . cider-eval-file) | ||||||
|  |      "e b" '("buffer" . cider-eval-buffer) | ||||||
|  |      "e r" '("region" . cider-eval-region) | ||||||
|  |      "e R" '("to repl" . cider-eval-last-sexp-to-repl) | ||||||
|  |      "e n" '("namespace" . cider-eval-ns-form) | ||||||
|  |      "e ;" '("expression" . cider-read-and-eval) | ||||||
|  |      "e i" '("inspect" . cider-inspect) | ||||||
|  | 
 | ||||||
|  |      "e p" '(:ignore t :which-key "pprint") | ||||||
|  |      "e p p" '("last s-expr" . cider-pprint-eval-last-sexp) | ||||||
|  |      "e p f" '("defun" . cider-pprint-eval-defun-at-point) | ||||||
|  |      "e p r" '("to repl" . cider-pprint-eval-last-sexp-to-repl) | ||||||
|  | 
 | ||||||
|  |      ;; Overshadowing xref menu in `ha-programming': | ||||||
|  |      "s" '(:ignore t :which-key "search") | ||||||
|  |      "s d" '("definition" . cider-find-resource) | ||||||
|  |      "s s" '("var" . cider-find-var) | ||||||
|  |      "s f" '("file" . cider-find-ns) | ||||||
|  |      "s o" '("other window" . xref-find-definitions-other-window) | ||||||
|  |      "s D" '("deps" . cider-xref-fn-deps) | ||||||
|  |      "s b" '("back" . cider-pop-back) | ||||||
|  | 
 | ||||||
|  |      "t" '(:ignore t :which-key "test") | ||||||
|  |      "t t" '("run test" . cider-test-run-test) | ||||||
|  |      "t r" '("rerun test" .cider-test-rerun-test) | ||||||
|  |      "t a" '("run all" .  cider-test-run-ns-tests) | ||||||
|  |      "t p" '("run project" .cider-test-run-project-tests) | ||||||
|  |      "t f" '("run failed" .cider-test-rerun-failed-tests) | ||||||
|  |      "t R" '("show report" .  cider-test-show-report) | ||||||
|  |      "t T" '("toggle test/file" . projectile-toggle-between-implementation-and-test) | ||||||
|  | 
 | ||||||
|  |      "d" '(:ignore t :which-key "docs") | ||||||
|  |      "d d" '("documentation" . cider-doc) | ||||||
|  |      "d s" '("search docs" . cider-apropos-documentation) | ||||||
|  |      "d j" '("javadocs" . cider-javadoc) | ||||||
|  |      "d c" '("clojuredocs" . cider-clojuredocs) | ||||||
|  |      "d a" '("apropos" . cider-apropos))) | ||||||
| #+end_src | #+end_src | ||||||
| Read the entire [[https://docs.cider.mx/][CIDER manual]]. | Read the entire [[https://docs.cider.mx/][CIDER manual]], specifically the [[https://docs.cider.mx/cider/usage/cider_mode.html][Usage document]]. | ||||||
| ** Linting | ** Linting | ||||||
| Using [[https://github.com/jonase/eastwood#emacs--cider][Eastwood]] with the [[https://github.com/clojure-emacs/squiggly-clojure][Squiggly Clojure]] project to add lint warnings to [[file:emacs.org::*Flycheck][Flycheck]]: | *Note:* The [[https://develop.spacemacs.org/layers/+lang/clojure/README.html][Spacemacs community]] recommends using [[https://github.com/borkdude/clj-kondo][clj-kondo]] in combination with [[https://github.com/candid82/joker][joker]]. | ||||||
|  | Add lint warnings to [[file:emacs.org::*Flycheck][Flycheck]]: | ||||||
| #+begin_src elisp | #+begin_src elisp | ||||||
|   (use-package flycheck-clojure |   (use-package flycheck-clojure | ||||||
|     :after flycheck |     :after flycheck | ||||||
|     :config |     :config | ||||||
|     (flycheck-clojure-setup)) |     (flycheck-clojure-setup)) | ||||||
| #+end_src | #+end_src | ||||||
| ** Snippets |  | ||||||
| 
 | 
 | ||||||
| For clojure-specific templates for [[https://github.com/capitaomorte/yasnippet][yasnippets]], clone David Nolen's [[http://github.com/swannodette/clojure-snippets][clojure-snippets]] repository into my =snippets= directory: | To install the =joker= binary: | ||||||
|   #+begin_src sh :tangle no | #+begin_src sh | ||||||
|     git clone http://github.com/swannodette/clojure-snippets ~/.emacs/snippets/clojure-mode |   brew install candid82/brew/joker | ||||||
| #+end_src | #+end_src | ||||||
| 
 | 
 | ||||||
| Or install it as a package: | And the [[https://github.com/candid82/flycheck-joker][flycheck-joker]] package should do the trick: | ||||||
|  | #+begin_src emacs-lisp | ||||||
|  |   (use-package flycheck-joker) | ||||||
|  | #+end_src | ||||||
|  | 
 | ||||||
|  | To install the =clj-kondo= binary is a bit more involved: | ||||||
|  | #+begin_src sh | ||||||
|  |   curl -sLO https://raw.githubusercontent.com/clj-kondo/clj-kondo/master/script/install-clj-kondo | ||||||
|  |   chmod +x install-clj-kondo | ||||||
|  |   ./install-clj-kondo | ||||||
|  | #+end_src | ||||||
|  | 
 | ||||||
|  | And the [[https://github.com/borkdude/flycheck-clj-kondo][flycheck-clj-kondo]] project should do the integration: | ||||||
|  | #+begin_src emacs-lisp | ||||||
|  |   (use-package flycheck-clj-kondo) | ||||||
|  | #+end_src | ||||||
|  |  Search on Clojars more easily | ||||||
|  | This [[https://github.com/joshuamiller/clojars.el][clojars]] extension allows you to search for projects on [[www.clojars.org][clojars.org]] and copies your selection to the kill ring in a format suitable for your =project.clj=. | ||||||
|  | #+begin_src emacs-lisp | ||||||
|  |   (use-package clojars | ||||||
|  |     :after clojure-mode | ||||||
|  |     :config | ||||||
|  |     (ha-clojure-leader | ||||||
|  |      "h j" '("clojars" . clojars))) | ||||||
|  | #+end_src | ||||||
|  | ** Clojure Cheatsheet | ||||||
|  | The [[https://github.com/clojure-emacs/clojure-cheatsheet][clojure-cheatsheet]] | ||||||
|  | #+begin_src emacs-lisp | ||||||
|  |   (use-package clojure-cheatsheet | ||||||
|  |     :after clojure-mode | ||||||
|  |     :config | ||||||
|  |     (ha-clojure-leader | ||||||
|  |      "h c" '("cheatsheet" . clojure-cheatsheet))) | ||||||
|  | #+end_src | ||||||
|  | ** Snippets | ||||||
|  | For clojure-specific templates for [[https://github.com/capitaomorte/yasnippet][yasnippets]], we use David Nolen's [[http://github.com/swannodette/clojure-snippets][clojure-snippets]] repository: | ||||||
|   #+begin_src elisp |   #+begin_src elisp | ||||||
|   (use-package clojure-snippets) |   (use-package clojure-snippets) | ||||||
|   #+end_src |   #+end_src | ||||||
|  | @ -108,11 +236,21 @@ Or install it as a package: | ||||||
| The [[https://github.com/clojure-emacs/clj-refactor.el][clj-refactor]] project: | The [[https://github.com/clojure-emacs/clj-refactor.el][clj-refactor]] project: | ||||||
| #+begin_src elisp | #+begin_src elisp | ||||||
|   (use-package clj-refactor |   (use-package clj-refactor | ||||||
|  |     :after clojure-mode | ||||||
|     :hook |     :hook | ||||||
|     (clojure-mode . clj-refactor-mode) |     (clojure-mode . clj-refactor-mode) | ||||||
|  | 
 | ||||||
|     :config |     :config | ||||||
|     ;; Configure the Clojure Refactoring prefix: |     ;; Configure the Clojure Refactoring prefix. | ||||||
|     (cljr-add-keybindings-with-prefix "C-c .") |     (cljr-add-keybindings-with-prefix "C-c .") | ||||||
|  | 
 | ||||||
|  |     (ha-clojure-leader | ||||||
|  |      ;; Would really like to have this on the SPC m prefix: | ||||||
|  |      "r"  '("refactoring" . hydra-cljr-help-menu/body) | ||||||
|  | 
 | ||||||
|  |      "h d" '("describe refactoring" . cljr-describe-refactoring) | ||||||
|  |      "h r" '("refactoring" . hydra-cljr-toplevel-form-menu/body)) | ||||||
|  | 
 | ||||||
|     :diminish clj-refactor-mode) |     :diminish clj-refactor-mode) | ||||||
| #+end_src | #+end_src | ||||||
| 
 | 
 | ||||||
|  |  | ||||||
		Loading…
	
		Reference in a new issue