Skip to main content

Module lsp_watcher

Module lsp_watcher 

Source
Expand description

LSP file-watcher subsystem (Phase 5.8.AF.5 / Slice 1).

Owns a notify::RecommendedWatcher and the per-server LSP subscription map. Lives entirely on a dedicated tokio task on the LSP runtime — paramount goal #4 (CLAUDE.md): nothing that does I/O, classification, or LSP fan-out runs on the renderer’s per-tick loop.

§Shape

  • LspFileWatcherHandle — what Editor holds. Just a cmd_tx. Cheap to construct, cheap to send through, never blocks.
  • spawn_lsp_file_watcher_task — spawns the task on lsp_runtime. The task owns the watcher, the event rx, and a HashMap<server_id, CachedSubscription>. It select!s between commands from Editor and notify events.
  • Editor pushes a SyncSubscriptions command whenever the actor roster or per-server caps change. The task installs/ tears down recursive watches and replaces its in-memory subscription map atomically.
  • When notify fires an event, the task classifies it, matches it against every server’s WatcherSubscriptions, and fans out one workspace/didChangeWatchedFiles per interested server via the cloned LspSupervisorHandle. The supervisor handle’s did_change_watched_files notification is non-blocking (channel send on the per-server actor).

Constructing the notify watcher and calling watcher.watch/ watcher.unwatch are sync APIs; they’re invoked from inside the task via [tokio::task::block_in_place] so the LSP runtime (multi-thread) keeps polling other futures while a large recursive walk is in flight.

§What’s NOT here (deferred to Slice 2)

  • .gitignore / .ignore aware filtering at the notify callback so events for target/, .git/, node_modules/, etc. never enter the channel.
  • Per-server registered-glob filtering at the source so we don’t pay the inotify wakeup cost for irrelevant paths.

Both are pure-additive improvements that bolt onto this task’s existing structure.

Structs§

CachedSubscription
One server’s subscription snapshot + the fingerprint used to detect changes. Editor computes the fingerprint, stores its own server_id → fingerprint map, and only sends a WatcherCommand::SyncSubscriptions when at least one server’s fingerprint flipped (or the actor roster changed).
LspFileWatcherHandle
Handle held by Editor. Owning this is cheap; sending through it is non-blocking. Drop the handle to tear down the task (the watcher itself drops + every inotify watch is released).
WatcherIgnoreMatcher
Matcher consulted in the notify callback. A path is rejected when ANY of the per-root .gitignore matchers OR the baked default GlobSet says “ignore.” Built once per sync_roots call by the watcher task and published into the Arc<ArcSwap<...>> shared with the notify callback.

Enums§

WatcherCommand
Editor → watcher-task control commands.

Functions§

classify
Translate one notify::Event into an LSP FileChangeType.
spawn_lsp_file_watcher_task
Spawn the watcher task on the LSP runtime. Returns the handle Editor should keep. Returns Err only if notify itself fails to construct the OS watcher (out of inotify slots, etc.).