From 0c311a517250262425fafd62d162c0683434c252 Mon Sep 17 00:00:00 2001 From: Henrik Lissner Date: Thu, 22 May 2025 18:06:19 +0200 Subject: [PATCH] feat(elixir): add treesit support --- modules/lang/elixir/README.org | 6 ++-- modules/lang/elixir/config.el | 53 +++++++++++++++++++++-------- modules/lang/elixir/doctor.el | 4 +++ modules/tools/tree-sitter/config.el | 2 -- 4 files changed, 45 insertions(+), 20 deletions(-) diff --git a/modules/lang/elixir/README.org b/modules/lang/elixir/README.org index c1189cccf..9615660ee 100644 --- a/modules/lang/elixir/README.org +++ b/modules/lang/elixir/README.org @@ -11,11 +11,11 @@ This module provides support for [[https://elixir-lang.org/][Elixir programming ** Module flags - +lsp :: - Enable LSP support for ~elixir-mode~. Requires [[doom-module::tools lsp]] and a langserver - (supports [[https://github.com/elixir-lsp/elixir-ls/][elixir-ls]]). + Enable LSP support for ~elixir-mode~. Requires [[doom-module::tools lsp]] and a + langserver (supports [[https://github.com/elixir-lsp/elixir-ls/][elixir-ls]]). - +tree-sitter :: Leverages tree-sitter for better syntax highlighting and structural text - editing. Requires [[doom-module::tools tree-sitter]]. + editing. Requires Emacs 30.1+ and [[doom-module::tools tree-sitter]]. ** Packages - [[doom-package:elixir-mode]] diff --git a/modules/lang/elixir/config.el b/modules/lang/elixir/config.el index d49f5d9aa..8d1f6a1aa 100644 --- a/modules/lang/elixir/config.el +++ b/modules/lang/elixir/config.el @@ -8,14 +8,8 @@ ;; ;;; Packages -(use-package! elixir-mode - :defer t - :init - ;; Disable default smartparens config. There are too many pairs; we only want - ;; a subset of them (defined below). - (provide 'smartparens-elixir) - :config - (set-ligatures! 'elixir-mode +(defun +elixir-common-config (mode) + (set-ligatures! mode ;; Functional :def "def" :lambda "fn" @@ -29,7 +23,7 @@ :return "return" :yield "use") ;; ...and only complete the basics - (sp-with-modes 'elixir-mode + (sp-with-modes mode (sp-local-pair "do" "end" :when '(("RET" "")) :unless '(sp-in-comment-p sp-in-string-p) @@ -37,16 +31,22 @@ (sp-local-pair "do " " end" :unless '(sp-in-comment-p sp-in-string-p)) (sp-local-pair "fn " " end" :unless '(sp-in-comment-p sp-in-string-p))) - (when (modulep! +lsp +tree-sitter) - (add-hook 'elixir-ts-mode-local-vars-hook #'lsp! 'append)) + (when (modulep! +lsp) + (add-hook (intern (format "%s-local-vars-hook" mode)) #'lsp! 'append))) + + +(use-package! elixir-mode + :defer t + :init + ;; Disable default smartparens config. There are too many pairs; we only want + ;; a subset of them (defined below). + (provide 'smartparens-elixir) (when (modulep! +lsp) - (add-hook 'elixir-mode-local-vars-hook #'lsp! 'append) (after! lsp-mode (add-to-list 'lsp-file-watch-ignored-directories "[/\\\\]_build\\'"))) - - (when (modulep! +tree-sitter) - (add-hook 'elixir-mode-local-vars-hook #'tree-sitter! 'append)) + :config + (+elixir-common-config 'elixir-mode) (after! highlight-numbers (puthash 'elixir-mode @@ -54,6 +54,29 @@ highlight-numbers-modelist))) +(use-package! elixir-ts-mode + :when (modulep! +tree-sitter) + :when (fboundp 'elixir-ts-mode) ; 30.1+ only + :defer t + :init + (set-tree-sitter! 'elixir-mode 'elixir-ts-mode + '((elixir :url "https://github.com/elixir-lang/tree-sitter-elixir" + :rev "v0.3.3") + (heex :url "https://github.com/phoenixframework/tree-sitter-heex" + :rev "v0.7.0"))) + :config + ;; HACK: Rely on `major-mode-remap-defaults'. + (cl-callf2 rassq-delete-all 'php-ts-mode auto-mode-alist) + + (+elixir-common-config 'elixir-ts-mode)) + + +(use-package! heex-ts-mode + :when (modulep! +tree-sitter) + :when (fboundp 'heex-ts-mode) ; 30.1+ only + :mode "\\.[hl]?eex\\'") + + (use-package! flycheck-credo :when (modulep! :checkers syntax -flymake) :after elixir-mode diff --git a/modules/lang/elixir/doctor.el b/modules/lang/elixir/doctor.el index 2c0306692..a6c454108 100644 --- a/modules/lang/elixir/doctor.el +++ b/modules/lang/elixir/doctor.el @@ -4,3 +4,7 @@ (assert! (or (not (modulep! +tree-sitter)) (modulep! :tools tree-sitter)) "This module requires (:tools tree-sitter)") + +(assert! (or (not (modulep! +tree-sitter)) + (fboundp 'elixir-ts-mode)) + "Can't find `elixir-ts-mode'; Emacs 30.1+ is required") diff --git a/modules/tools/tree-sitter/config.el b/modules/tools/tree-sitter/config.el index 78c32cc03..d6f14220e 100644 --- a/modules/tools/tree-sitter/config.el +++ b/modules/tools/tree-sitter/config.el @@ -26,10 +26,8 @@ (css "https://github.com/tree-sitter/tree-sitter-css" nil nil nil nil) (dart "https://github.com/ast-grep/tree-sitter-dart" nil nil nil nil) (dockerfile "https://github.com/camdencheek/tree-sitter-dockerfile" nil nil nil nil) - (elixir "https://github.com/elixir-lang/tree-sitter-elixir" nil nil nil nil) (go "https://github.com/tree-sitter/tree-sitter-go" nil nil nil nil) (gomod "https://github.com/camdencheek/tree-sitter-go-mod" nil nil nil nil) - (heex "https://github.com/phoenixframework/tree-sitter-heex" nil nil nil nil) (html "https://github.com/tree-sitter/tree-sitter-html" nil nil nil nil) (java "https://github.com/tree-sitter/tree-sitter-java" nil nil nil nil) (javascript "https://github.com/tree-sitter/tree-sitter-javascript" "master" "src" nil nil)