mirror of
https://gitlab.com/dwt1/dotfiles.git
synced 2026-04-23 11:30:23 +10:00
Updating Doom Emacs.
This commit is contained in:
@@ -7,8 +7,10 @@
|
||||
- [[#description][Description]]
|
||||
- [[#module-flags][Module Flags]]
|
||||
- [[#plugins][Plugins]]
|
||||
- [[#hacks][Hacks]]
|
||||
- [[#prerequisites][Prerequisites]]
|
||||
- [[#features][Features]]
|
||||
- [[#lsp-powered-project-search][LSP-powered project search]]
|
||||
- [[#configuration][Configuration]]
|
||||
- [[#troubleshooting][Troubleshooting]]
|
||||
|
||||
@@ -40,23 +42,36 @@ As of this writing, this is the state of LSP support in Doom Emacs:
|
||||
| [[../../lang/haskell/README.org][:lang haskell]] | haskell-mode | haskell-ide-engine |
|
||||
| [[../../lang/java/README.org][:lang java]] | java-mode | lsp-java |
|
||||
| [[../../lang/javascript/README.org][:lang javascript]] | js2-mode, rjsx-mode, typescript-mode | typescript-language-server |
|
||||
| [[../../lang/ocaml/README.org][:lang ocaml]] | taureg-mode | ocaml-language-server |
|
||||
| [[../../lang/ocaml/README.org][:lang ocaml]] | tuareg-mode | ocaml-language-server |
|
||||
| [[../../lang/php/README.org][:lang php]] | php-mode | php-language-server |
|
||||
| [[../../lang/python/README.org][:lang python]] | python-mode | lsp-python-ms |
|
||||
| [[../../lang/ruby/README.org][:lang ruby]] | ruby-mode, enh-ruby-mode | solargraph |
|
||||
| [[../../lang/ruby/README.org][:lang ruby]] | ruby-mode | solargraph |
|
||||
| [[../../lang/rust/README.org][:lang rust]] | rust-mode | rls |
|
||||
| [[../../lang/scala/README.org][:lang scala]] | scala-mode | metals |
|
||||
| [[../../lang/sh/README.org][:lang sh]] | sh-mode | bash-language-server |
|
||||
| [[../../lang/swift/README.org][:lang swift]] | swift-mode | sourcekit |
|
||||
| [[../../lang/web/README.org][:lang web]] | web-mode, css-mode, scss-mode, sass-mode, less-css-mode | vscode-css-languageserver-bin, vscode-html-languageserver-bin |
|
||||
| [[../../lang/purescript/README.org][:lang purescript]] | purescript-mode | purescript-language-server |
|
||||
|
||||
** Module Flags
|
||||
This module provides no flags.
|
||||
+ =+peek= Use =lsp-ui-peek= when looking up definitions and references with
|
||||
functionality from the =:tools lookup= module.
|
||||
+ =+eglot= Use [[https://elpa.gnu.org/packages/eglot.html][Eglot]] instead of [[https://github.com/emacs-lsp/lsp-mode][LSP-mode]] to implement the LSP client in
|
||||
Emacs.
|
||||
|
||||
** Plugins
|
||||
+ [[https://github.com/emacs-lsp/lsp-mode][lsp-mode]]
|
||||
+ [[https://github.com/emacs-lsp/lsp-ui][lsp-ui]]
|
||||
+ [[https://github.com/tigersoldier/company-lsp][company-lsp]]*
|
||||
+ [[https://github.com/emacs-lsp/lsp-ivy][lsp-ivy]]
|
||||
+ [[https://github.com/emacs-lsp/helm-lsp][helm-lsp]]
|
||||
+ [[https://github.com/joaotavora/eglot][eglot]]
|
||||
|
||||
** Hacks
|
||||
+ ~lsp-mode~ has been modified not to automatically install missing LSP servers.
|
||||
This is done to adhere to our "Your system, your rules" mantra, which insist
|
||||
that it is better etiquette to let the user decide when their development
|
||||
environment is modified. Use ~M-x lsp-install-server~ to install LSP servers
|
||||
manually.
|
||||
|
||||
* Prerequisites
|
||||
This module has no direct prerequisites, but major-modes require you to install
|
||||
@@ -66,8 +81,37 @@ You'll find a table that lists available language servers and how to install
|
||||
them [[https://github.com/emacs-lsp/lsp-mode#supported-languages][in the lsp-mode project README]]. The documentation of the module for your
|
||||
targeted language will contain brief instructions as well.
|
||||
|
||||
For eglot users, you can see the list of [[https://github.com/joaotavora/eglot/blob/master/README.md#connecting-to-a-server][default servers supported in the README]].
|
||||
There is also instructions to add another server easily.
|
||||
|
||||
* TODO Features
|
||||
** LSP-powered project search
|
||||
Without the =+eglot= flag, and when =:completion ivy= or =:completion helm= is
|
||||
active, LSP is used to search a symbol indexed by the LSP server :
|
||||
| Keybind | Description |
|
||||
|-----------+-------------------------------------|
|
||||
| =SPC c j= | Jump to symbol in current workspace |
|
||||
| =SPC c J= | Jump to symbol in any workspace |
|
||||
** Differences between eglot and lsp-mode
|
||||
Entering the debate about which one to use would be useless. Doom provides an
|
||||
easy way to switch out lsp client implementations so you can test for yourself
|
||||
which one you prefer.
|
||||
|
||||
Mainly, from a code point of view, lsp-mode has a lot of custom code for UI
|
||||
(=lsp-ui-peek=, =lsp-ui-sideline=, ...), while eglot is more barebones with a
|
||||
closer integration with "more basic" emacs packages (=eldoc=, =xref=, ...).
|
||||
|
||||
* TODO Configuration
|
||||
|
||||
* TODO Troubleshooting
|
||||
** My language server is not found
|
||||
Check the entry in the [[../../../docs/faq.org][FAQ]] about "Doom can't find my executables/doesn't inherit
|
||||
the correct ~PATH~"
|
||||
** LSP/Eglot is not started automatically in my buffer
|
||||
Make sure that you added the =+lsp= flag to the language you're using too in
|
||||
your init.el :
|
||||
#+BEGIN_SRC diff
|
||||
:lang
|
||||
-python
|
||||
+(python +lsp)
|
||||
#+END_SRC
|
||||
|
||||
@@ -1,4 +0,0 @@
|
||||
;;; feature/lsp/autoload.el -*- lexical-binding: t; -*-
|
||||
|
||||
;;;###autodef
|
||||
(defalias 'lsp! #'lsp-deferred)
|
||||
@@ -1,150 +1,16 @@
|
||||
;;; tools/lsp/config.el -*- lexical-binding: t; -*-
|
||||
|
||||
(defvar +lsp-company-backend 'company-lsp
|
||||
"What backend to prepend to `company-backends' when `lsp-mode' is active.
|
||||
(defvar +lsp-defer-shutdown 3
|
||||
"If non-nil, defer shutdown of LSP servers for this many seconds after last
|
||||
workspace buffer is closed.
|
||||
|
||||
This can be a single company backend or a list thereof. It can be anything
|
||||
`company-backends' will accept.")
|
||||
This delay prevents premature server shutdown when a user still intends on
|
||||
working on that project after closing the last buffer.")
|
||||
|
||||
|
||||
;;
|
||||
;;; Packages
|
||||
;;; Implementations
|
||||
|
||||
(use-package! lsp-mode
|
||||
:defer t
|
||||
:init
|
||||
(setq lsp-session-file (concat doom-etc-dir "lsp-session"))
|
||||
;; Don't prompt the user for the project root every time we open a new
|
||||
;; lsp-worthy file, instead, try to guess it with projectile.
|
||||
(setq lsp-auto-guess-root t)
|
||||
;; Auto-kill LSP server once you've killed the last buffer associated with its
|
||||
;; project.
|
||||
(setq lsp-keep-workspace-alive nil)
|
||||
|
||||
;; For `lsp-clients'
|
||||
(setq lsp-fsharp-server-install-dir (concat doom-etc-dir "lsp-fsharp/")
|
||||
lsp-groovy-server-install-dir (concat doom-etc-dir "lsp-groovy/")
|
||||
lsp-intelephense-storage-path (concat doom-cache-dir "lsp-intelephense/"))
|
||||
|
||||
:config
|
||||
(set-lookup-handlers! 'lsp-mode :async t
|
||||
:documentation 'lsp-describe-thing-at-point
|
||||
:definition 'lsp-find-definition
|
||||
:references 'lsp-find-references)
|
||||
|
||||
(defvar +lsp--deferred-shutdown-timer nil)
|
||||
(defadvice! +lsp-defer-server-shutdown-a (orig-fn)
|
||||
"Defer server shutdown for a few seconds.
|
||||
This gives the user a chance to open other project files before the server is
|
||||
auto-killed (which is usually an expensive process)."
|
||||
:around #'lsp--shutdown-workspace
|
||||
(if (or lsp-keep-workspace-alive
|
||||
(eq (lsp--workspace-shutdown-action lsp--cur-workspace)
|
||||
'restart))
|
||||
(funcall orig-fn)
|
||||
(when (timerp +lsp--deferred-shutdown-timer)
|
||||
(cancel-timer +lsp--deferred-shutdown-timer))
|
||||
(setq +lsp--deferred-shutdown-timer
|
||||
(run-at-time
|
||||
3 nil (lambda (workspace)
|
||||
(let ((lsp--cur-workspace workspace))
|
||||
(unless (lsp--workspace-buffers lsp--cur-workspace)
|
||||
(funcall orig-fn))))
|
||||
lsp--cur-workspace))))
|
||||
|
||||
(defadvice! +lsp-prompt-if-no-project-a (session file-name)
|
||||
"Prompt for the project root only if no project was found."
|
||||
:after-until #'lsp--calculate-root
|
||||
(cond ((not lsp-auto-guess-root)
|
||||
nil)
|
||||
((cl-find-if (lambda (dir)
|
||||
(and (lsp--files-same-host dir file-name)
|
||||
(file-in-directory-p file-name dir)))
|
||||
(lsp-session-folders-blacklist session))
|
||||
nil)
|
||||
((lsp--find-root-interactively session))))
|
||||
|
||||
(defadvice! +lsp-init-a (&optional arg)
|
||||
"Enable `lsp-mode' in the current buffer.
|
||||
|
||||
Meant to be a lighter alternative to `lsp', which is too eager about
|
||||
initializing lsp-ui-mode, company, yasnippet and flycheck. Instead, these have
|
||||
been moved out to their respective modules, or these hooks:
|
||||
|
||||
+ `+lsp-init-company-h' (on `lsp-mode-hook')
|
||||
+ `+lsp-init-ui-flycheck-or-flymake-h' (on `lsp-ui-mode-hook')
|
||||
|
||||
Also logs the resolved project root, if found."
|
||||
:override #'lsp
|
||||
(interactive "P")
|
||||
(require 'lsp-mode)
|
||||
(when lsp-auto-configure
|
||||
(require 'lsp-clients))
|
||||
(and (buffer-file-name)
|
||||
(setq-local
|
||||
lsp--buffer-workspaces
|
||||
(or (lsp--try-open-in-library-workspace)
|
||||
(lsp--try-project-root-workspaces
|
||||
(equal arg '(4))
|
||||
(and arg (not (equal arg 1))))))
|
||||
(prog1 (lsp-mode 1)
|
||||
;; Announce what project root we're using, for diagnostic purposes
|
||||
(if-let (root (lsp--calculate-root (lsp-session) (buffer-file-name)))
|
||||
(lsp--info "Guessed project root is %s" (abbreviate-file-name root))
|
||||
(lsp--info "Could not guess project root."))
|
||||
(lsp--info "Connected to %s."
|
||||
(apply #'concat
|
||||
(mapcar
|
||||
(lambda (it) (format "[%s]" (lsp--workspace-print it)))
|
||||
lsp--buffer-workspaces))))))
|
||||
|
||||
;; Don't prompt to restart LSP servers while quitting Emacs
|
||||
(add-hook! 'kill-emacs-hook (setq lsp-restart 'ignore)))
|
||||
|
||||
|
||||
(use-package! lsp-ui
|
||||
:hook (lsp-mode . lsp-ui-mode)
|
||||
:init
|
||||
(add-hook! 'lsp-ui-mode-hook
|
||||
(defun +lsp-init-ui-flycheck-or-flymake-h ()
|
||||
"Sets up flymake-mode or flycheck-mode, depending on `lsp-prefer-flymake'."
|
||||
(cond ((eq :none lsp-prefer-flymake))
|
||||
(lsp-prefer-flymake
|
||||
(lsp--flymake-setup))
|
||||
((require 'flycheck nil t)
|
||||
(require 'lsp-ui-flycheck)
|
||||
(lsp-ui-flycheck-enable t)))))
|
||||
:config
|
||||
(setq lsp-prefer-flymake nil
|
||||
lsp-ui-doc-max-height 8
|
||||
lsp-ui-doc-max-width 35
|
||||
lsp-ui-sideline-ignore-duplicate t
|
||||
;; lsp-ui-doc is redundant with and more invasive than
|
||||
;; `+lookup/documentation'
|
||||
lsp-ui-doc-enable nil
|
||||
;; Don't show symbol definitions in the sideline. They are pretty noisy,
|
||||
;; and there is a bug preventing Flycheck errors from being shown (the
|
||||
;; errors flash briefly and then disappear).
|
||||
lsp-ui-sideline-show-hover nil)
|
||||
|
||||
(set-lookup-handlers! 'lsp-ui-mode :async t
|
||||
:definition 'lsp-ui-peek-find-definitions
|
||||
:references 'lsp-ui-peek-find-references))
|
||||
|
||||
|
||||
(use-package! company-lsp
|
||||
:when (featurep! :completion company)
|
||||
:defer t
|
||||
:init
|
||||
;; Make sure that `company-capf' is disabled since it is incompatible with
|
||||
;; `company-lsp' (see lsp-mode#884)
|
||||
(add-hook! 'lsp-mode-hook
|
||||
(defun +lsp-init-company-h ()
|
||||
(if (not (bound-and-true-p company-mode))
|
||||
(add-hook 'company-mode-hook #'+lsp-init-company-h t t)
|
||||
(setq-local company-backends
|
||||
(cons +lsp-company-backend
|
||||
(remq 'company-capf company-backends)))
|
||||
(remove-hook 'company-mode-hook #'+lsp-init-company-h t))))
|
||||
:config
|
||||
(setq company-lsp-cache-candidates 'auto)) ;; cache candidates for better performance
|
||||
(if (featurep! +eglot)
|
||||
(load! "+eglot")
|
||||
(load! "+lsp"))
|
||||
|
||||
@@ -1,7 +1,15 @@
|
||||
;; -*- no-byte-compile: t; -*-
|
||||
;;; tools/lsp/packages.el
|
||||
|
||||
(package! lsp-mode)
|
||||
(package! lsp-ui)
|
||||
(when (featurep! :completion company)
|
||||
(package! company-lsp))
|
||||
(if (featurep! +eglot)
|
||||
(progn
|
||||
(package! eglot :pin "ac9239bed5e3bfbf057382d1a75cdfa23f2caddd")
|
||||
(package! project
|
||||
:recipe (:host github :repo "emacs-straight/project")
|
||||
:pin "da0333a697b18f0a863c1b1523d2fc7991b31174"))
|
||||
(package! lsp-mode :pin "5f3f9848b2d4afc69049121c60126a6405447106")
|
||||
(package! lsp-ui :pin "d92cf83d95c9ca177b735500ead88cf68dc2e2db")
|
||||
(when (featurep! :completion ivy)
|
||||
(package! lsp-ivy :pin "dce58b5509271bbedb53ba9d0278dcb563a43977"))
|
||||
(when (featurep! :completion helm)
|
||||
(package! helm-lsp :pin "5018af9c709a783de1b9e101e07c948cceed67f1")))
|
||||
|
||||
Reference in New Issue
Block a user