emacs-lsp / lsp-mode

Emacs client/library for the Language Server Protocol
https://emacs-lsp.github.io/lsp-mode
GNU General Public License v3.0
4.78k stars 884 forks source link

Need a way to control LSP server start/stop for a project #4111

Open madscientist opened 1 year ago

madscientist commented 1 year ago

I do a lot of work with a lot of different workspaces (this is a very large C++ project). I don't need or want all the features of LSP in many of them; I just want to create a Git worktree for example and go review some changes from another developer, then get out.

Secondly, when I'm doing major Git machinations like big rebase operations that have many steps, etc., I don't want or need the LSP server to be indexing all those intermediate operations; it just drags my system to a crawl.

Currently I can't find any way to handle this with lsp-mode. I can run lsp-workspace-shutdown but as soon as I visit a new file, lsp-mode will restart the LSP server.

I see there's a lsp-workspace-blacklist-remove, but I can't figure out how to use this. It's definitely not well-documented :) I can't find any way to control which things are added to that list automatically, or even interactively: I see from the source that in theory lsp--find-root-interactively should offer me the option to add things to the blacklist, but I never get any action popup so somehow this is being circumvented.

I would like much better control over start/stop of the server, at a project level. I would like a variable controlling whether or not the LSP server should be started by default whenever a file in a project is visited and there's not already an LSP server running there. Suppose we call it lsp-start-by-default (default t).

Secondly a variable tracking which projects have LSP disabled, so that if new files are visited in these projects we don't start an LSP server. Maybe that's the lsp-session-folders-blacklist, I'm not sure because I can't find a way to show what's in that or add things to it.

Then the behavior would be:

  1. when a new file is visited, if there's already an LSP server for that project then we connect to it.
  2. If there's no LSP server yet, then we check the list of disabled projects. If this project is in the list don't start a server. If it is not, then check lsp-start-by-default. If it's t then start the server. If it's nil then don't start the server.

Of course, we need a way to start the server if it's disabled, removing it from the disabled list; I don't know if the current lsp-workspace-restart-server can be used for that.

And the lsp-workspace-shutdown-server would add that project to the disabled projects list so that new servers wouldn't be started for files in that project until lsp-workspace-restart-server (or whatever) was explicitly called.

The defaults would preserve the status quo, but people could turn off LSP servers in some workspaces and it would "stick".

madscientist commented 1 year ago

Does anyone have any ideas here?

I mean it's getting so bad that I find myself avoiding opening files in Emacs and instead using less or something, just so the LSP server doesn't kick off in some random workspace I know I won't need to index.

help!!

yyoncho commented 1 year ago

IIUC one solution for you would be to write a wrapper over lsp function and put the logic that you want in that wrapper. You may take a look at lsp-find-workspace. You may also set lsp-keep-workspace-alive to nil.

necto commented 3 months ago

@madscientist , note that clangd has an option to limit how many workers it spawns. I have this in my config, and do not notice the drag even when opening anew a large C++ project

(setq lsp-clients-clangd-args '("-j=8"
                                "--background-index"))