Hacktoberfest 2026: le issue che i maintainer hanno segnato per ottobre, aperte e adatte ai principianti. Sfoglia le issue Hacktoberfest

[rush] RFC: Rush Daemon (rushd) — server-first re-architecture with thin clients

Aperta
#5,863 2 commenti 1 reazione 0 assegnatari Vedi su GitHub

Nessuno ha ancora preso questa issue.

Valutazione

Difficoltà
5/5
Tempo stimato
Più di una settimana
Idoneità per principianti
20/100
Tipo di issue
Funzionalità
Chiarezza
Da chiarire
Stato di attività
Tranquilla
Stack tecnologico
nodejs, typescript

Direzione di ricerca

Start with this RFC and the referenced watch-mode overhaul PR #5378 and Reporter Overhaul issue #5858. The proposed entry points are @microsoft/rush, @rushstack/rush-cli-client, and new protocol, transport, renderer, client-core, and daemon packages. Done would require an agreed server-first architecture and a staged implementation that preserves current CLI behavior, but no specific files or tests are named.

Scritto dal modello di indicizzazione a partire dal testo della issue.

Descrizione

design proposal

1. Summary

Rush is a CLI-first application: @microsoft/rush is a thin launcher that resolves the workspace's
rushVersion, loads the matching @microsoft/rush-lib, and runs the entire engine in-process, once per
invocation
. Every command re-reads configuration, rebuilds the operation graph, re-resolves state, and
throws it all away on exit.

This RFC proposes rushd, a long-lived, per-workspace daemon that owns the engine and keeps build
state warm (config, project graph, operation graph, file watchers, plugins). rush becomes a very thin
client
that forwards the command to the daemon and pumps stdout/stderr/stdin back to the terminal — an
interaction transparent to the user and to scripts. All interesting work happens in the daemon; the
client only owns presentation. There is one daemon per Rush workspace, and it auto-starts on
first use.

The model is directly inspired by Bazel's client/server architecture.
It reuses the watch-mode overhaul (PR #5378) to keep the build graph warm, and the Reporter Overhaul
(#5858) for the presentation-free event contract that flows over the wire. The default flip ships as Rush 6.

2. Context and Motivation

  • Cold start every time. Config parsing, graph construction, and snapshotting are repeated on every
    rush build/rush install/rush update, even when nothing changed.
  • No resident watch state. The watch-mode overhaul makes the operation graph stateful and warm-able, but
    a CLI process cannot keep it resident across invocations.
  • Presentation is fused to the engine. rush-lib writes ANSI/English directly, which blocks non-terminal
    clients (agents, IDEs, web) and makes output hard to adapt for CI/agents.
  • Concurrency is hostile. A second rush command today races or fails ("another rush is running")
    instead of coordinating.
  • Agent/AI ergonomics. Long-running foreground processes (rush start) and verbose output are poor for agents; a daemon
    plus a structured client protocol fixes both.

3. Goals and Non-Goals

Goals
  • A per-workspace daemon that keeps RushConfiguration + operation graph + watchers + plugins warm.
  • A thin client that is byte-for-byte transparent: identical stdout/stderr, exit codes, TTY/color/width
    behavior, stdin, and Ctrl+C semantics as today.
  • Terminal rendering lives in the client wrapper — no SIGWINCH/terminal-control signals sent to the
    daemon; the client owns width/color/resize.
  • Auto-start the daemon on demand; new rush daemon start|stop|restart|status|logs subcommands.
  • The daemon handles rush install / rush update and restarts itself (with socket handoff) when
    they change installed state.
  • Queue-and-wait concurrency: a conflicting command waits rather than failing, with exclusivity
    classes and shared-build merging.
  • Warm-set management: auto-evict idle projects, telemetry-weighted warm selection.
  • A presentation-free protocol enabling additional clients (MCP, web, IDE).
  • An experimental graph CLI to inspect/scope the warm watch graph.
  • Delivered as new split packages merged incrementally into main at 0.x, then a Rush 6 cutover.
Non-Goals
  • Redesigning operation scheduling, parallelism, or cobuild (the daemon observes the existing engine).
  • Multi-workspace or multi-user shared daemons (strictly one per workspace, per user).
  • Remote/networked daemons — transport is local (Unix socket / Windows named pipe), loopback only.
  • Replacing rush-lib — the engine is reused, not rewritten (strangler-fig decomposition).
  • Shipping the web dashboard UX itself (only the wiring to serve/attach it).

4. Proposed Solution

 rush (thin client)                         rushd (daemon, 1 per workspace)
 ─────────────────                          ───────────────────────────────
 parse minimal argv                         WorkspaceSession (warm):
 resolve workspace key  ──socket/pipe──►      RushConfiguration + graph + watcher + plugins
 forward request envelope                    RequestScheduler (exclusivity + queue-and-wait + merge)
 (argv,cwd,env,columns,colorLevel)           CommandRouter (phased vs global, per-request context)
 pump stdout/stderr/stdin  ◄──events/log──   ReloadController (fingerprint, tiers, self-restart/handoff)
 own ALL presentation                        emits presentation-free events (reporter contract, #5858)
 permanent in-process fallback               keeps state warm across invocations

Key architectural decisions:

  • Presentation on the client. The engine emits a structured, presentation-free event stream
    (adopting @rushstack/reporter's event contract, #5858); the client renders it. The daemon never touches
    terminal-control state.
  • Transparency via a request envelope, not shared TTY. The client sends columns/colorLevel/cwd/env
    per request; the daemon injects these per-request (never process.chdir/mutating global process.env).
  • Queue-and-wait scheduling with SHARED-BUILD / SHARED-READ / EXCLUSIVE classes; install/update
    are EXCLUSIVE and trigger reload tiers.
  • Self-managing lifecycle. After install/update, the daemon sends the client its exit code, then
    drains, restarts a successor, and hands off the socket; version-mismatch also triggers a restart.
  • Warm-set bounding. LRU idle eviction under a memory budget + telemetry-weighted warm selection;
    best-effort, never correctness-affecting.
  • Split packages from day one (protocol / transport / renderer / client-core / daemon), with a separate
    CLI-specific client package
    (@rushstack/rush-cli-client) until cutover, so @microsoft/rush is untouched
    pre-6.

5. Relationship to In-Flight Work

  • Watch-mode overhaul (PR #5378) — hard prerequisite. Provides the stateful IOperationGraph
    (setEnabledStates, invalidateOperations, scheduled iterations, terminal-destination management) the
    daemon keeps warm. Its hook churn is @alpha/@beta (not a Rush 5 stable-API break).
  • Reporter Overhaul (#5858) — reused, not duplicated. Supplies the presentation-free event envelope +
    NDJSON wire adapter + built-in reporters. Its "daemon-aligned major default flip" is the Rush 6 cutover;
    the two efforts share a breaking-change set (ILogger.terminal, RushSession.terminalProvider, plugin-API
    gating) and cut over together.
Lingua principale
TypeScript
Stelle
6.5k
Fork
708
Merge medio
5g 19h
PR unite (30g)
48

Guida per i contributori

Nessuna guida per i contributori indicizzata per questo repository

Come iniziare

  1. Leggi tutta la issue e poi la guida ai contributi del progetto.
  2. Commenta sulla issue per dire che te ne occupi tu — evita che due persone facciano lo stesso lavoro.
  3. Fai un fork del repository e lavora su un branch.
  4. Apri una pull request che faccia riferimento al numero della issue.

Altre issue di microsoft/rushstack

Tutte le issue di microsoft/rushstack

Issue simili

Altre issue su TypeScript

Ricevi le nuove issue nella tua casella

Un breve riepilogo di issue GitHub adatte ai principianti.