@lspeasy/server 4.0.1 → 4.0.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -1
- package/dist/capability-guard.d.ts +2 -26
- package/dist/capability-guard.d.ts.map +1 -1
- package/dist/capability-guard.js +35 -171
- package/dist/capability-guard.js.map +1 -1
- package/dist/capability-proxy.js.map +1 -1
- package/dist/dispatcher.d.ts +46 -7
- package/dist/dispatcher.d.ts.map +1 -1
- package/dist/dispatcher.js +46 -7
- package/dist/dispatcher.js.map +1 -1
- package/dist/index.d.ts +52 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +52 -1
- package/dist/index.js.map +1 -1
- package/dist/lifecycle.js.map +1 -1
- package/dist/progress/partial-result-sender.d.ts +30 -1
- package/dist/progress/partial-result-sender.d.ts.map +1 -1
- package/dist/progress/partial-result-sender.js +30 -1
- package/dist/progress/partial-result-sender.js.map +1 -1
- package/dist/progress.js.map +1 -1
- package/dist/server.d.ts +168 -12
- package/dist/server.d.ts.map +1 -1
- package/dist/server.js +114 -12
- package/dist/server.js.map +1 -1
- package/dist/types.d.ts +102 -11
- package/dist/types.d.ts.map +1 -1
- package/dist/types.js +14 -3
- package/dist/types.js.map +1 -1
- package/dist/validation.js.map +1 -1
- package/package.json +7 -8
package/dist/index.js
CHANGED
|
@@ -1,5 +1,56 @@
|
|
|
1
1
|
/**
|
|
2
|
-
*
|
|
2
|
+
* LSP server package for hosting Language Server Protocol (LSP) servers.
|
|
3
|
+
*
|
|
4
|
+
* @remarks
|
|
5
|
+
* Use `@lspeasy/server` when you need to build the **provider** side of the
|
|
6
|
+
* Language Server Protocol — a daemon that editors and language-client tooling
|
|
7
|
+
* connect to in order to get diagnostics, completions, hover, go-to-definition,
|
|
8
|
+
* and other language intelligence features.
|
|
9
|
+
*
|
|
10
|
+
* The primary entry point is {@link LSPServer}. Construct it with
|
|
11
|
+
* {@link ServerOptions}, call `registerCapabilities(caps)` to declare what
|
|
12
|
+
* the server supports, register handlers with `onRequest` / `onNotification`,
|
|
13
|
+
* then call `listen(transport)` to accept the first client connection.
|
|
14
|
+
*
|
|
15
|
+
* ### Transport Decision Tree
|
|
16
|
+
*
|
|
17
|
+
* **Stdio** (`StdioTransport` from `@lspeasy/core/node`)
|
|
18
|
+
* — Use when: the client spawns your server as a child process (the canonical
|
|
19
|
+
* VS Code extension pattern). No network, no port management. Failure mode:
|
|
20
|
+
* `ConsoleLogger` writes to stdout and corrupts the LSP stream — always use
|
|
21
|
+
* `NullLogger` or a file-based logger with stdio.
|
|
22
|
+
*
|
|
23
|
+
* **WebSocket** (`WebSocketTransport` from `@lspeasy/core`)
|
|
24
|
+
* — Use when: multiple clients connect over a network, or the server must be
|
|
25
|
+
* browser-accessible. Each accepted WebSocket connection needs its own
|
|
26
|
+
* `LSPServer` instance. Failure mode: one client crash should not affect
|
|
27
|
+
* others — wrap each `wss.on('connection')` callback in try/catch and
|
|
28
|
+
* create a fresh `LSPServer` per socket.
|
|
29
|
+
*
|
|
30
|
+
* **TCP** (`TcpTransport` from `@lspeasy/core/node`)
|
|
31
|
+
* — Use when: building a persistent local daemon (e.g. a formatting server
|
|
32
|
+
* shared across editor sessions). Failure mode: client disconnect fires
|
|
33
|
+
* `close()` on the server instance — use `mode: 'server'` and create a new
|
|
34
|
+
* `LSPServer` on each reconnect.
|
|
35
|
+
*
|
|
36
|
+
* **DedicatedWorkerTransport** (`DedicatedWorkerTransport` from `@lspeasy/core`)
|
|
37
|
+
* — Use when: running the server logic in a Web Worker for in-process browser
|
|
38
|
+
* isolation. Zero serialization overhead. Failure mode: worker crash is
|
|
39
|
+
* silent from the server side — monitor the worker's `onerror` in the host.
|
|
40
|
+
*
|
|
41
|
+
* ### Typed capability namespaces
|
|
42
|
+
* After `registerCapabilities({ hoverProvider: true })`, TypeScript exposes
|
|
43
|
+
* `server.textDocument.onHover(handler)` — methods that are absent unless the
|
|
44
|
+
* corresponding capability is declared. This prevents accidentally registering
|
|
45
|
+
* handlers for capabilities the server never advertised.
|
|
46
|
+
*
|
|
47
|
+
* ### Handler conventions
|
|
48
|
+
* - {@link RequestHandler} — async, throws {@link ResponseError} for
|
|
49
|
+
* structured errors, checks `token.isCancellationRequested` for early exit.
|
|
50
|
+
* - {@link NotificationHandler} — fire-and-forget; unhandled rejections
|
|
51
|
+
* surface via `server.onError()`.
|
|
52
|
+
*
|
|
53
|
+
* @packageDocumentation
|
|
3
54
|
*/
|
|
4
55
|
// Main server class
|
|
5
56
|
export { LSPServer } from './server.js';
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAqDG;AAEH,oBAAoB;AACpB,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AAaxC,OAAO,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC;AAEzC,+BAA+B;AAC/B,OAAO,EAAE,iBAAiB,EAAE,MAAM,iBAAiB,CAAC;AACpD,OAAO,EAAE,mBAAmB,EAAE,MAAM,qCAAqC,CAAC;AA0B1E,OAAO,EAAE,aAAa,EAAE,gBAAgB,EAAE,aAAa,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AAEzF,uGAAuG;AACvG,gDAAgD"}
|
package/dist/lifecycle.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"lifecycle.js","sourceRoot":"","sources":["../src/lifecycle.ts"],"names":[],"mappings":"AAAA;;GAEG;AAWH;;GAEG;AACH,MAAM,OAAO,gBAAgB;IAIR,IAAI;IACJ,OAAO;IACP,MAAM;IALjB,kBAAkB,GAAuB,EAAE,CAAC;IAEpD,YACmB,IAAY,EACZ,OAAe,EACf,MAAc
|
|
1
|
+
{"version":3,"file":"lifecycle.js","sourceRoot":"","sources":["../src/lifecycle.ts"],"names":[],"mappings":"AAAA;;GAEG;AAWH;;GAEG;AACH,MAAM,OAAO,gBAAgB;IAIR,IAAI;IACJ,OAAO;IACP,MAAM;IALjB,kBAAkB,GAAuB,EAAE,CAAC;IAEpD,YACmB,IAAY,EACZ,OAAe,EACf,MAAc;oBAFd,IAAI;uBACJ,OAAO;sBACP,MAAM;IACtB,CAAC;IAEJ;;OAEG;IACH,oBAAoB,CAAC,YAAgC;QACnD,IAAI,CAAC,kBAAkB,GAAG,YAAY,CAAC;IACzC,CAAC;IAED;;OAEG;IACH,eAAe;QACb,OAAO,IAAI,CAAC,kBAAkB,CAAC;IACjC,CAAC;IAED;;OAEG;IACH,KAAK,CAAC,gBAAgB,CACpB,MAAwB,EACxB,UAAqB,EACrB,GAAoB;QAEpB,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,wBAAwB,CAAC,CAAC;QAC3C,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,oBAAoB,EAAE,MAAM,CAAC,CAAC;QAEhD,MAAM,MAAM,GAAqB;YAC/B,YAAY,EAAE,IAAI,CAAC,kBAAkB;YACrC,UAAU,EAAE;gBACV,IAAI,EAAE,IAAI,CAAC,IAAI;gBACf,OAAO,EAAE,IAAI,CAAC,OAAO;aACtB;SACF,CAAC;QAEF,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,oBAAoB,CAAC,CAAC;QACvC,OAAO,MAAM,CAAC;IAChB,CAAC;IAED;;OAEG;IACH,iBAAiB,CAAC,MAAyB;QACzC,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,sCAAsC,CAAC,CAAC;QACzD,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,qBAAqB,EAAE,MAAM,CAAC,CAAC;IACnD,CAAC;IAED;;OAEG;IACH,KAAK,CAAC,cAAc,CAAC,UAAqB,EAAE,GAAoB;QAC9D,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,yBAAyB,CAAC,CAAC;QAC5C,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,0BAA0B,CAAC,CAAC;IAC/C,CAAC;IAED;;OAEG;IACH,UAAU;QACR,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,aAAa,CAAC,CAAC;IAClC,CAAC;CACF"}
|
|
@@ -1,9 +1,38 @@
|
|
|
1
1
|
import type { ProgressToken } from '@lspeasy/core';
|
|
2
2
|
import type { BaseLSPServer } from '../server.js';
|
|
3
|
-
/**
|
|
3
|
+
/**
|
|
4
|
+
* Emits typed `$/progress` partial-result batches from server-side request handlers.
|
|
5
|
+
*
|
|
6
|
+
* @remarks
|
|
7
|
+
* Use `PartialResultSender` inside a `RequestHandler` when the client has
|
|
8
|
+
* supplied a `partialResultToken` (e.g. for `textDocument/references` or
|
|
9
|
+
* `workspace/symbol`). Call `send(token, value)` to stream result batches
|
|
10
|
+
* before returning the final response.
|
|
11
|
+
*
|
|
12
|
+
* @useWhen
|
|
13
|
+
* The client sets `partialResultToken` in the request params and you want to
|
|
14
|
+
* stream intermediate results (e.g. symbols found so far) rather than waiting
|
|
15
|
+
* for the complete set.
|
|
16
|
+
*
|
|
17
|
+
* @never
|
|
18
|
+
* NEVER call `send` after the handler has already returned a response — the
|
|
19
|
+
* `$/progress` notification will arrive after the client has closed the
|
|
20
|
+
* partial-result channel, and the client will silently discard or error on it.
|
|
21
|
+
*
|
|
22
|
+
* NEVER send partial results without a `partialResultToken` — the client has
|
|
23
|
+
* no way to correlate the `$/progress` notification to the pending request.
|
|
24
|
+
*
|
|
25
|
+
* @category Server
|
|
26
|
+
*/
|
|
4
27
|
export declare class PartialResultSender {
|
|
5
28
|
private readonly server;
|
|
6
29
|
constructor(server: BaseLSPServer);
|
|
30
|
+
/**
|
|
31
|
+
* Send a batch of partial results to the client.
|
|
32
|
+
*
|
|
33
|
+
* @param token - The `partialResultToken` from the originating request params.
|
|
34
|
+
* @param value - The partial result batch to stream to the client via `$/progress`.
|
|
35
|
+
*/
|
|
7
36
|
send<T>(token: ProgressToken, value: T): Promise<void>;
|
|
8
37
|
}
|
|
9
38
|
//# sourceMappingURL=partial-result-sender.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"partial-result-sender.d.ts","sourceRoot":"","sources":["../../src/progress/partial-result-sender.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAyB,aAAa,EAAE,MAAM,eAAe,CAAC;AAC1E,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAElD
|
|
1
|
+
{"version":3,"file":"partial-result-sender.d.ts","sourceRoot":"","sources":["../../src/progress/partial-result-sender.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAyB,aAAa,EAAE,MAAM,eAAe,CAAC;AAC1E,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAElD;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AACH,qBAAa,mBAAmB;IAClB,OAAO,CAAC,QAAQ,CAAC,MAAM;IAAnC,YAA6B,MAAM,EAAE,aAAa,EAAI;IAEtD;;;;;OAKG;IACG,IAAI,CAAC,CAAC,EAAE,KAAK,EAAE,aAAa,EAAE,KAAK,EAAE,CAAC,GAAG,OAAO,CAAC,IAAI,CAAC,CAS3D;CACF"}
|
|
@@ -1,9 +1,38 @@
|
|
|
1
|
-
/**
|
|
1
|
+
/**
|
|
2
|
+
* Emits typed `$/progress` partial-result batches from server-side request handlers.
|
|
3
|
+
*
|
|
4
|
+
* @remarks
|
|
5
|
+
* Use `PartialResultSender` inside a `RequestHandler` when the client has
|
|
6
|
+
* supplied a `partialResultToken` (e.g. for `textDocument/references` or
|
|
7
|
+
* `workspace/symbol`). Call `send(token, value)` to stream result batches
|
|
8
|
+
* before returning the final response.
|
|
9
|
+
*
|
|
10
|
+
* @useWhen
|
|
11
|
+
* The client sets `partialResultToken` in the request params and you want to
|
|
12
|
+
* stream intermediate results (e.g. symbols found so far) rather than waiting
|
|
13
|
+
* for the complete set.
|
|
14
|
+
*
|
|
15
|
+
* @never
|
|
16
|
+
* NEVER call `send` after the handler has already returned a response — the
|
|
17
|
+
* `$/progress` notification will arrive after the client has closed the
|
|
18
|
+
* partial-result channel, and the client will silently discard or error on it.
|
|
19
|
+
*
|
|
20
|
+
* NEVER send partial results without a `partialResultToken` — the client has
|
|
21
|
+
* no way to correlate the `$/progress` notification to the pending request.
|
|
22
|
+
*
|
|
23
|
+
* @category Server
|
|
24
|
+
*/
|
|
2
25
|
export class PartialResultSender {
|
|
3
26
|
server;
|
|
4
27
|
constructor(server) {
|
|
5
28
|
this.server = server;
|
|
6
29
|
}
|
|
30
|
+
/**
|
|
31
|
+
* Send a batch of partial results to the client.
|
|
32
|
+
*
|
|
33
|
+
* @param token - The `partialResultToken` from the originating request params.
|
|
34
|
+
* @param value - The partial result batch to stream to the client via `$/progress`.
|
|
35
|
+
*/
|
|
7
36
|
async send(token, value) {
|
|
8
37
|
const payload = {
|
|
9
38
|
token,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"partial-result-sender.js","sourceRoot":"","sources":["../../src/progress/partial-result-sender.ts"],"names":[],"mappings":"AAGA
|
|
1
|
+
{"version":3,"file":"partial-result-sender.js","sourceRoot":"","sources":["../../src/progress/partial-result-sender.ts"],"names":[],"mappings":"AAGA;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AACH,MAAM,OAAO,mBAAmB;IACD,MAAM;IAAnC,YAA6B,MAAqB;sBAArB,MAAM;IAAkB,CAAC;IAEtD;;;;;OAKG;IACH,KAAK,CAAC,IAAI,CAAI,KAAoB,EAAE,KAAQ;QAC1C,MAAM,OAAO,GAAG;YACd,KAAK;YACL,KAAK;SAC4C,CAAC;QAEpD,MAAM,IAAI,CAAC,MAAM,CAAC,gBAAgB,CAAC,YAAY,EAAE;YAC/C,GAAG,OAAO;SACX,CAAC,CAAC;IACL,CAAC;CACF"}
|
package/dist/progress.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"progress.js","sourceRoot":"","sources":["../src/progress.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAGH,OAAO,EACL,mBAAmB,EACnB,oBAAoB,EACpB,iBAAiB,EACjB,mBAAmB,EACpB,MAAM,eAAe,CAAC;AA6BvB;;GAEG;AACH,MAAM,oBAAoB;IAEd,KAAK;IACL,MAAM;IAFhB,YACU,KAAoB,EACpB,MAAsB
|
|
1
|
+
{"version":3,"file":"progress.js","sourceRoot":"","sources":["../src/progress.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAGH,OAAO,EACL,mBAAmB,EACnB,oBAAoB,EACpB,iBAAiB,EACjB,mBAAmB,EACpB,MAAM,eAAe,CAAC;AA6BvB;;GAEG;AACH,MAAM,oBAAoB;IAEd,KAAK;IACL,MAAM;IAFhB,YACU,KAAoB,EACpB,MAAsB;qBADtB,KAAK;sBACL,MAAM;IACb,CAAC;IAEJ,KAAK,CAAC,KAAK,CACT,KAAa,EACb,WAAqB,EACrB,OAAgB,EAChB,UAAmB;QAEnB,MAAM,KAAK,GAAG,mBAAmB,CAAC,KAAK,EAAE,WAAW,EAAE,OAAO,EAAE,UAAU,CAAC,CAAC;QAC3E,MAAM,IAAI,CAAC,MAAM,CAAC,gBAAgB,CAAC,YAAY,EAAE;YAC/C,KAAK,EAAE,IAAI,CAAC,KAAK;YACjB,KAAK;SACN,CAAC,CAAC;IACL,CAAC;IAED,KAAK,CAAC,MAAM,CAAC,OAAgB,EAAE,UAAmB;QAChD,MAAM,KAAK,GAAG,oBAAoB,CAAC,OAAO,EAAE,UAAU,CAAC,CAAC;QACxD,MAAM,IAAI,CAAC,MAAM,CAAC,gBAAgB,CAAC,YAAY,EAAE;YAC/C,KAAK,EAAE,IAAI,CAAC,KAAK;YACjB,KAAK;SACN,CAAC,CAAC;IACL,CAAC;IAED,KAAK,CAAC,GAAG,CAAC,OAAgB;QACxB,MAAM,KAAK,GAAG,iBAAiB,CAAC,OAAO,CAAC,CAAC;QACzC,MAAM,IAAI,CAAC,MAAM,CAAC,gBAAgB,CAAC,YAAY,EAAE;YAC/C,KAAK,EAAE,IAAI,CAAC,KAAK;YACjB,KAAK;SACN,CAAC,CAAC;IACL,CAAC;CACF;AAED;;;GAGG;AACH,MAAM,UAAU,sBAAsB,CACpC,KAAoB,EACpB,MAAsB;IAEtB,OAAO,IAAI,oBAAoB,CAAC,KAAK,EAAE,MAAM,CAAC,CAAC;AACjD,CAAC;AAED;;GAEG;AACH,OAAO,EAAE,mBAAmB,EAAE,CAAC"}
|
package/dist/server.d.ts
CHANGED
|
@@ -5,18 +5,75 @@ import type { Transport, Disposable, ServerCapabilities, ClientCapabilities, LSP
|
|
|
5
5
|
import type { ServerOptions, RequestHandler, NotificationHandler, NotebookDocumentHandlerNamespace } from './types.js';
|
|
6
6
|
import { ServerState } from './types.js';
|
|
7
7
|
/**
|
|
8
|
-
* LSP
|
|
8
|
+
* Full-featured LSP server with automatic lifecycle management, typed handlers,
|
|
9
|
+
* capability-aware namespaces, and pluggable middleware.
|
|
9
10
|
*
|
|
10
|
-
*
|
|
11
|
-
*
|
|
11
|
+
* @remarks
|
|
12
|
+
* `LSPServer` manages the complete LSP lifecycle (`initialize` / `initialized`
|
|
13
|
+
* / `shutdown` / `exit`) automatically. Register your handlers with
|
|
14
|
+
* `onRequest` / `onNotification`, declare capabilities with
|
|
15
|
+
* `registerCapabilities`, then start the server with `listen(transport)`.
|
|
12
16
|
*
|
|
13
|
-
*
|
|
17
|
+
* ### Capability-aware namespaces
|
|
18
|
+
*
|
|
19
|
+
* After calling `registerCapabilities(caps)`, the server exposes typed
|
|
20
|
+
* namespaces — e.g. `server.textDocument.onHover(handler)` — that are only
|
|
21
|
+
* present when the corresponding capability is declared. TypeScript enforces
|
|
22
|
+
* this at compile time so you cannot accidentally register a handler for a
|
|
23
|
+
* capability you never advertised.
|
|
24
|
+
*
|
|
25
|
+
* ### Transport selection
|
|
26
|
+
*
|
|
27
|
+
* - **Browser / universal**: `WebSocketTransport` (from `@lspeasy/core`)
|
|
28
|
+
* - **Node.js**: `StdioTransport`, `TcpTransport`, `IpcTransport` (from `@lspeasy/core/node`)
|
|
29
|
+
* - **Web Workers**: `DedicatedWorkerTransport`, `SharedWorkerTransport` (from `@lspeasy/core`)
|
|
30
|
+
*
|
|
31
|
+
* @useWhen
|
|
32
|
+
* You are building an LSP language server that editors and language-client
|
|
33
|
+
* tooling will connect to. `LSPServer` is the primary entry point for all
|
|
34
|
+
* server implementations.
|
|
35
|
+
*
|
|
36
|
+
* @avoidWhen
|
|
37
|
+
* You need a bare JSON-RPC layer without LSP semantics — use the transport
|
|
38
|
+
* and framing utilities directly instead.
|
|
39
|
+
*
|
|
40
|
+
* @never
|
|
41
|
+
* NEVER call `server.shutdown()` or `server.close()` from inside a request
|
|
42
|
+
* or notification handler — doing so attempts to close the transport while it
|
|
43
|
+
* is actively dispatching, causing a deadlock.
|
|
44
|
+
*
|
|
45
|
+
* NEVER mutate `ServerCapabilities` after `initialized` has been received.
|
|
46
|
+
* The client cached the `InitializeResult` at handshake time; runtime changes
|
|
47
|
+
* are invisible to it.
|
|
48
|
+
*
|
|
49
|
+
* NEVER share one `LSPServer` instance across multiple transports or
|
|
50
|
+
* connections. Each connection requires its own server instance to maintain
|
|
51
|
+
* independent protocol state (lifecycle phase, pending request IDs, etc.).
|
|
52
|
+
*
|
|
53
|
+
* NEVER send a server-to-client notification before the `initialize` response
|
|
54
|
+
* has been dispatched. Use the `initialized` notification handler as the
|
|
55
|
+
* earliest safe point for server-initiated messages.
|
|
14
56
|
*
|
|
15
57
|
* @example
|
|
16
|
-
*
|
|
17
|
-
*
|
|
18
|
-
*
|
|
19
|
-
*
|
|
58
|
+
* ```ts
|
|
59
|
+
* import { LSPServer } from '@lspeasy/server';
|
|
60
|
+
* // Node.js: import { StdioTransport } from '@lspeasy/core/node';
|
|
61
|
+
* // Browser: import { WebSocketTransport } from '@lspeasy/core';
|
|
62
|
+
*
|
|
63
|
+
* const server = new LSPServer({ name: 'my-lsp', version: '1.0.0' })
|
|
64
|
+
* .registerCapabilities({ hoverProvider: true });
|
|
65
|
+
*
|
|
66
|
+
* server.textDocument.onHover(async (params, token) => {
|
|
67
|
+
* if (token.isCancellationRequested) return null;
|
|
68
|
+
* return { contents: { kind: 'plaintext', value: 'Hello from my-lsp' } };
|
|
69
|
+
* });
|
|
70
|
+
*
|
|
71
|
+
* const transport = new StdioTransport();
|
|
72
|
+
* await server.listen(transport);
|
|
73
|
+
* ```
|
|
74
|
+
*
|
|
75
|
+
* @template Capabilities - Shape of the server capabilities, defaults to `ServerCapabilities`.
|
|
76
|
+
* @category Server
|
|
20
77
|
*/
|
|
21
78
|
export declare class BaseLSPServer<Capabilities extends Partial<ServerCapabilities> = ServerCapabilities> {
|
|
22
79
|
private readonly logger;
|
|
@@ -104,19 +161,56 @@ export declare class BaseLSPServer<Capabilities extends Partial<ServerCapabiliti
|
|
|
104
161
|
*/
|
|
105
162
|
expect<C extends Partial<ClientCapabilities>>(): this & Server<C, Capabilities>;
|
|
106
163
|
/**
|
|
107
|
-
* Send a server-to-client request.
|
|
164
|
+
* Send a server-to-client request and await the client's response.
|
|
165
|
+
*
|
|
166
|
+
* @param method - The LSP request method name (server-to-client direction).
|
|
167
|
+
* @param params - Optional request parameters.
|
|
168
|
+
* @returns A promise resolving to the client's result.
|
|
169
|
+
* @throws {Error} When not listening (transport not attached). Fix: only call `sendRequest` from inside a handler or after the `listening` event fires.
|
|
170
|
+
* @throws {Error} When the client returns a JSON-RPC error response. Fix: catch and inspect `error.code`; `window/showMessageRequest` rejections are user-initiated (user dismissed), not bugs.
|
|
171
|
+
* @throws {Error} When the request times out (if `requestTimeout` is configured). Fix: increase `ServerOptions.requestTimeout` for slow UI interactions like `window/showMessageRequest`.
|
|
172
|
+
*
|
|
173
|
+
* @category Server
|
|
108
174
|
*/
|
|
109
175
|
sendRequest<Method extends LSPRequestMethod<'serverToClient'>>(method: Method, params?: ParamsForRequest<Method>): Promise<ResultForRequest<Method>>;
|
|
110
176
|
/**
|
|
111
|
-
* Send a server-to-client notification.
|
|
177
|
+
* Send a server-to-client notification (fire-and-forget).
|
|
178
|
+
*
|
|
179
|
+
* @param method - The LSP notification method name (server-to-client direction).
|
|
180
|
+
* @param params - Optional notification parameters.
|
|
181
|
+
* @throws {Error} When not listening. Fix: only send notifications after `listen()` resolves and before `shutdown()` is called; guard with `isListening()`.
|
|
182
|
+
* @throws {Error} When the transport's underlying `send()` fails (e.g. broken socket). Fix: subscribe to `server.onError()` to catch transport-level write failures.
|
|
183
|
+
*
|
|
184
|
+
* @category Server
|
|
112
185
|
*/
|
|
113
186
|
sendNotification<Method extends LSPNotificationMethod<'serverToClient'>>(method: Method, params?: ParamsForNotification<Method>): Promise<void>;
|
|
114
187
|
/**
|
|
115
|
-
*
|
|
188
|
+
* Attaches the server to a transport and begins processing messages.
|
|
189
|
+
*
|
|
190
|
+
* @remarks
|
|
191
|
+
* After `listen()` returns the server is ready to receive the `initialize`
|
|
192
|
+
* request from the client. The LSP handshake proceeds automatically.
|
|
193
|
+
*
|
|
194
|
+
* @param transport - The transport to listen on.
|
|
195
|
+
* @throws {Error} When already listening. Fix: call `close()` then create a fresh `LSPServer` instance — do not reuse a single instance across connections.
|
|
196
|
+
*
|
|
197
|
+
* @category Lifecycle
|
|
116
198
|
*/
|
|
117
199
|
listen(transport: Transport): Promise<void>;
|
|
118
200
|
/**
|
|
119
|
-
*
|
|
201
|
+
* Initiates graceful shutdown, waits for in-flight handlers, then closes
|
|
202
|
+
* the transport.
|
|
203
|
+
*
|
|
204
|
+
* @remarks
|
|
205
|
+
* Waits up to `timeout` ms for pending handlers to complete, then
|
|
206
|
+
* cancels any remaining in-flight requests before closing. Use this method
|
|
207
|
+
* to shut down in response to an OS signal or editor session end.
|
|
208
|
+
*
|
|
209
|
+
* @param timeout - Maximum milliseconds to wait for in-flight handlers before
|
|
210
|
+
* force-cancelling them.
|
|
211
|
+
* @defaultValue 5000
|
|
212
|
+
*
|
|
213
|
+
* @category Lifecycle
|
|
120
214
|
*/
|
|
121
215
|
shutdown(timeout?: number): Promise<void>;
|
|
122
216
|
/**
|
|
@@ -165,6 +259,68 @@ export declare class BaseLSPServer<Capabilities extends Partial<ServerCapabiliti
|
|
|
165
259
|
*/
|
|
166
260
|
private handleResponse;
|
|
167
261
|
}
|
|
262
|
+
/**
|
|
263
|
+
* Full-featured LSP server with automatic lifecycle management, typed handlers,
|
|
264
|
+
* capability-aware namespaces, and pluggable middleware.
|
|
265
|
+
*
|
|
266
|
+
* @remarks
|
|
267
|
+
* `LSPServer` manages the complete LSP lifecycle (`initialize` / `initialized`
|
|
268
|
+
* / `shutdown` / `exit`) automatically. Register handlers with `onRequest` /
|
|
269
|
+
* `onNotification`, declare capabilities with `registerCapabilities`, then
|
|
270
|
+
* start with `listen(transport)`.
|
|
271
|
+
*
|
|
272
|
+
* ### Capability-aware namespaces
|
|
273
|
+
* After `registerCapabilities({ hoverProvider: true })`, TypeScript exposes
|
|
274
|
+
* `server.textDocument.onHover(handler)` — methods absent unless the
|
|
275
|
+
* corresponding capability is declared.
|
|
276
|
+
*
|
|
277
|
+
* @useWhen
|
|
278
|
+
* You are building an LSP language server that editors and language-client
|
|
279
|
+
* tooling will connect to.
|
|
280
|
+
*
|
|
281
|
+
* @avoidWhen
|
|
282
|
+
* You need a bare JSON-RPC layer without LSP semantics — use the transport
|
|
283
|
+
* and framing utilities from `@lspeasy/core` directly.
|
|
284
|
+
*
|
|
285
|
+
* @never
|
|
286
|
+
* NEVER call `server.shutdown()` or `server.close()` from inside a request
|
|
287
|
+
* or notification handler — doing so attempts to close the transport while it
|
|
288
|
+
* is actively dispatching, causing a deadlock.
|
|
289
|
+
*
|
|
290
|
+
* NEVER mutate `ServerCapabilities` after `initialized` has been received.
|
|
291
|
+
* The client cached the `InitializeResult` at handshake time; runtime changes
|
|
292
|
+
* are invisible to it.
|
|
293
|
+
*
|
|
294
|
+
* NEVER share one `LSPServer` instance across multiple transports or connections.
|
|
295
|
+
* Each connection requires its own server instance to maintain independent state.
|
|
296
|
+
*
|
|
297
|
+
* @example
|
|
298
|
+
* ```ts
|
|
299
|
+
* import { LSPServer } from '@lspeasy/server';
|
|
300
|
+
* import { StdioTransport } from '@lspeasy/core/node';
|
|
301
|
+
*
|
|
302
|
+
* const server = new LSPServer({ name: 'my-lsp', version: '1.0.0' })
|
|
303
|
+
* .registerCapabilities({ hoverProvider: true });
|
|
304
|
+
*
|
|
305
|
+
* server.textDocument.onHover(async (params, token) => {
|
|
306
|
+
* if (token.isCancellationRequested) return null;
|
|
307
|
+
* return { contents: { kind: 'plaintext', value: 'Hello from my-lsp' } };
|
|
308
|
+
* });
|
|
309
|
+
*
|
|
310
|
+
* await server.listen(new StdioTransport());
|
|
311
|
+
* ```
|
|
312
|
+
*
|
|
313
|
+
* @template ServerCaps - Shape of the server capabilities.
|
|
314
|
+
* @category Server
|
|
315
|
+
*/
|
|
168
316
|
export type LSPServer<ServerCaps extends Partial<ServerCapabilities> = ServerCapabilities> = BaseLSPServer<ServerCaps> & Server<ClientCapabilities, ServerCaps>;
|
|
317
|
+
/**
|
|
318
|
+
* Constructs an {@link LSPServer} instance.
|
|
319
|
+
*
|
|
320
|
+
* @param options - Optional {@link ServerOptions} to configure the server.
|
|
321
|
+
* @returns A new `LSPServer` instance.
|
|
322
|
+
*
|
|
323
|
+
* @category Server
|
|
324
|
+
*/
|
|
169
325
|
export declare const LSPServer: new <ServerCaps extends Partial<ServerCapabilities> = ServerCapabilities>(options?: ServerOptions<ServerCaps>) => LSPServer<ServerCaps>;
|
|
170
326
|
//# sourceMappingURL=server.d.ts.map
|
package/dist/server.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"server.d.ts","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,KAAK,EACV,SAAS,EAKT,UAAU,EAEV,kBAAkB,EAClB,kBAAkB,EAClB,gBAAgB,EAChB,qBAAqB,EACrB,gBAAgB,EAChB,gBAAgB,EAChB,qBAAqB,EACrB,MAAM,EAKP,MAAM,eAAe,CAAC;AAWvB,OAAO,KAAK,EACV,aAAa,EACb,cAAc,EACd,mBAAmB,EACnB,gCAAgC,EACjC,MAAM,YAAY,CAAC;AACpB,OAAO,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC;AAOzC
|
|
1
|
+
{"version":3,"file":"server.d.ts","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"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"}
|
package/dist/server.js
CHANGED
|
@@ -11,18 +11,75 @@ import { validateParams } from './validation.js';
|
|
|
11
11
|
import { CapabilityGuard, ClientCapabilityGuard } from './capability-guard.js';
|
|
12
12
|
import { initializeServerHandlerMethods, initializeServerSendMethods } from './capability-proxy.js';
|
|
13
13
|
/**
|
|
14
|
-
* LSP
|
|
14
|
+
* Full-featured LSP server with automatic lifecycle management, typed handlers,
|
|
15
|
+
* capability-aware namespaces, and pluggable middleware.
|
|
15
16
|
*
|
|
16
|
-
*
|
|
17
|
-
*
|
|
17
|
+
* @remarks
|
|
18
|
+
* `LSPServer` manages the complete LSP lifecycle (`initialize` / `initialized`
|
|
19
|
+
* / `shutdown` / `exit`) automatically. Register your handlers with
|
|
20
|
+
* `onRequest` / `onNotification`, declare capabilities with
|
|
21
|
+
* `registerCapabilities`, then start the server with `listen(transport)`.
|
|
18
22
|
*
|
|
19
|
-
*
|
|
23
|
+
* ### Capability-aware namespaces
|
|
24
|
+
*
|
|
25
|
+
* After calling `registerCapabilities(caps)`, the server exposes typed
|
|
26
|
+
* namespaces — e.g. `server.textDocument.onHover(handler)` — that are only
|
|
27
|
+
* present when the corresponding capability is declared. TypeScript enforces
|
|
28
|
+
* this at compile time so you cannot accidentally register a handler for a
|
|
29
|
+
* capability you never advertised.
|
|
30
|
+
*
|
|
31
|
+
* ### Transport selection
|
|
32
|
+
*
|
|
33
|
+
* - **Browser / universal**: `WebSocketTransport` (from `@lspeasy/core`)
|
|
34
|
+
* - **Node.js**: `StdioTransport`, `TcpTransport`, `IpcTransport` (from `@lspeasy/core/node`)
|
|
35
|
+
* - **Web Workers**: `DedicatedWorkerTransport`, `SharedWorkerTransport` (from `@lspeasy/core`)
|
|
36
|
+
*
|
|
37
|
+
* @useWhen
|
|
38
|
+
* You are building an LSP language server that editors and language-client
|
|
39
|
+
* tooling will connect to. `LSPServer` is the primary entry point for all
|
|
40
|
+
* server implementations.
|
|
41
|
+
*
|
|
42
|
+
* @avoidWhen
|
|
43
|
+
* You need a bare JSON-RPC layer without LSP semantics — use the transport
|
|
44
|
+
* and framing utilities directly instead.
|
|
45
|
+
*
|
|
46
|
+
* @never
|
|
47
|
+
* NEVER call `server.shutdown()` or `server.close()` from inside a request
|
|
48
|
+
* or notification handler — doing so attempts to close the transport while it
|
|
49
|
+
* is actively dispatching, causing a deadlock.
|
|
50
|
+
*
|
|
51
|
+
* NEVER mutate `ServerCapabilities` after `initialized` has been received.
|
|
52
|
+
* The client cached the `InitializeResult` at handshake time; runtime changes
|
|
53
|
+
* are invisible to it.
|
|
54
|
+
*
|
|
55
|
+
* NEVER share one `LSPServer` instance across multiple transports or
|
|
56
|
+
* connections. Each connection requires its own server instance to maintain
|
|
57
|
+
* independent protocol state (lifecycle phase, pending request IDs, etc.).
|
|
58
|
+
*
|
|
59
|
+
* NEVER send a server-to-client notification before the `initialize` response
|
|
60
|
+
* has been dispatched. Use the `initialized` notification handler as the
|
|
61
|
+
* earliest safe point for server-initiated messages.
|
|
20
62
|
*
|
|
21
63
|
* @example
|
|
22
|
-
*
|
|
23
|
-
*
|
|
24
|
-
*
|
|
25
|
-
*
|
|
64
|
+
* ```ts
|
|
65
|
+
* import { LSPServer } from '@lspeasy/server';
|
|
66
|
+
* // Node.js: import { StdioTransport } from '@lspeasy/core/node';
|
|
67
|
+
* // Browser: import { WebSocketTransport } from '@lspeasy/core';
|
|
68
|
+
*
|
|
69
|
+
* const server = new LSPServer({ name: 'my-lsp', version: '1.0.0' })
|
|
70
|
+
* .registerCapabilities({ hoverProvider: true });
|
|
71
|
+
*
|
|
72
|
+
* server.textDocument.onHover(async (params, token) => {
|
|
73
|
+
* if (token.isCancellationRequested) return null;
|
|
74
|
+
* return { contents: { kind: 'plaintext', value: 'Hello from my-lsp' } };
|
|
75
|
+
* });
|
|
76
|
+
*
|
|
77
|
+
* const transport = new StdioTransport();
|
|
78
|
+
* await server.listen(transport);
|
|
79
|
+
* ```
|
|
80
|
+
*
|
|
81
|
+
* @template Capabilities - Shape of the server capabilities, defaults to `ServerCapabilities`.
|
|
82
|
+
* @category Server
|
|
26
83
|
*/
|
|
27
84
|
export class BaseLSPServer {
|
|
28
85
|
logger;
|
|
@@ -165,7 +222,16 @@ export class BaseLSPServer {
|
|
|
165
222
|
return this;
|
|
166
223
|
}
|
|
167
224
|
/**
|
|
168
|
-
* Send a server-to-client request.
|
|
225
|
+
* Send a server-to-client request and await the client's response.
|
|
226
|
+
*
|
|
227
|
+
* @param method - The LSP request method name (server-to-client direction).
|
|
228
|
+
* @param params - Optional request parameters.
|
|
229
|
+
* @returns A promise resolving to the client's result.
|
|
230
|
+
* @throws {Error} When not listening (transport not attached). Fix: only call `sendRequest` from inside a handler or after the `listening` event fires.
|
|
231
|
+
* @throws {Error} When the client returns a JSON-RPC error response. Fix: catch and inspect `error.code`; `window/showMessageRequest` rejections are user-initiated (user dismissed), not bugs.
|
|
232
|
+
* @throws {Error} When the request times out (if `requestTimeout` is configured). Fix: increase `ServerOptions.requestTimeout` for slow UI interactions like `window/showMessageRequest`.
|
|
233
|
+
*
|
|
234
|
+
* @category Server
|
|
169
235
|
*/
|
|
170
236
|
async sendRequest(method, params) {
|
|
171
237
|
if (!this.transport) {
|
|
@@ -199,7 +265,14 @@ export class BaseLSPServer {
|
|
|
199
265
|
return promise;
|
|
200
266
|
}
|
|
201
267
|
/**
|
|
202
|
-
* Send a server-to-client notification.
|
|
268
|
+
* Send a server-to-client notification (fire-and-forget).
|
|
269
|
+
*
|
|
270
|
+
* @param method - The LSP notification method name (server-to-client direction).
|
|
271
|
+
* @param params - Optional notification parameters.
|
|
272
|
+
* @throws {Error} When not listening. Fix: only send notifications after `listen()` resolves and before `shutdown()` is called; guard with `isListening()`.
|
|
273
|
+
* @throws {Error} When the transport's underlying `send()` fails (e.g. broken socket). Fix: subscribe to `server.onError()` to catch transport-level write failures.
|
|
274
|
+
*
|
|
275
|
+
* @category Server
|
|
203
276
|
*/
|
|
204
277
|
async sendNotification(method, params) {
|
|
205
278
|
if (!this.transport) {
|
|
@@ -224,7 +297,16 @@ export class BaseLSPServer {
|
|
|
224
297
|
});
|
|
225
298
|
}
|
|
226
299
|
/**
|
|
227
|
-
*
|
|
300
|
+
* Attaches the server to a transport and begins processing messages.
|
|
301
|
+
*
|
|
302
|
+
* @remarks
|
|
303
|
+
* After `listen()` returns the server is ready to receive the `initialize`
|
|
304
|
+
* request from the client. The LSP handshake proceeds automatically.
|
|
305
|
+
*
|
|
306
|
+
* @param transport - The transport to listen on.
|
|
307
|
+
* @throws {Error} When already listening. Fix: call `close()` then create a fresh `LSPServer` instance — do not reuse a single instance across connections.
|
|
308
|
+
*
|
|
309
|
+
* @category Lifecycle
|
|
228
310
|
*/
|
|
229
311
|
async listen(transport) {
|
|
230
312
|
if (this.transport) {
|
|
@@ -248,7 +330,19 @@ export class BaseLSPServer {
|
|
|
248
330
|
this.events.emit('listening');
|
|
249
331
|
}
|
|
250
332
|
/**
|
|
251
|
-
*
|
|
333
|
+
* Initiates graceful shutdown, waits for in-flight handlers, then closes
|
|
334
|
+
* the transport.
|
|
335
|
+
*
|
|
336
|
+
* @remarks
|
|
337
|
+
* Waits up to `timeout` ms for pending handlers to complete, then
|
|
338
|
+
* cancels any remaining in-flight requests before closing. Use this method
|
|
339
|
+
* to shut down in response to an OS signal or editor session end.
|
|
340
|
+
*
|
|
341
|
+
* @param timeout - Maximum milliseconds to wait for in-flight handlers before
|
|
342
|
+
* force-cancelling them.
|
|
343
|
+
* @defaultValue 5000
|
|
344
|
+
*
|
|
345
|
+
* @category Lifecycle
|
|
252
346
|
*/
|
|
253
347
|
async shutdown(timeout = 5000) {
|
|
254
348
|
if (this.state === ServerState.Shutdown) {
|
|
@@ -521,6 +615,14 @@ export class BaseLSPServer {
|
|
|
521
615
|
this.pendingRequests.reject(String(id), new Error('Invalid response message'));
|
|
522
616
|
}
|
|
523
617
|
}
|
|
618
|
+
/**
|
|
619
|
+
* Constructs an {@link LSPServer} instance.
|
|
620
|
+
*
|
|
621
|
+
* @param options - Optional {@link ServerOptions} to configure the server.
|
|
622
|
+
* @returns A new `LSPServer` instance.
|
|
623
|
+
*
|
|
624
|
+
* @category Server
|
|
625
|
+
*/
|
|
524
626
|
// Generic constructor that preserves type parameters
|
|
525
627
|
export const LSPServer = BaseLSPServer;
|
|
526
628
|
//# sourceMappingURL=server.js.map
|