@xneog/dsh-tool-fs-search 0.1.0 → 0.1.3-alpha.1
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.i18n.yaml +2 -2
- package/README.md +129 -34
- package/README.zh.md +131 -36
- package/lib/index.js +15 -10
- package/lib/types/direct-call.d.ts +2 -1
- package/lib/types/search-core.d.ts +5 -6
- package/package.json +22 -29
- package/lib/invariant.js +0 -23
- package/lib/types/invariant.d.ts +0 -16
package/README.i18n.yaml
CHANGED
|
@@ -2,5 +2,5 @@
|
|
|
2
2
|
# side as of the last confirmed-consistent state. Both languages carry equal authority;
|
|
3
3
|
# after editing either side, bring the other along and re-record with:
|
|
4
4
|
# pnpm run verify-translation-pairing --write packages/fs/tool-fs-search/README.md
|
|
5
|
-
README.md:
|
|
6
|
-
README.zh.md:
|
|
5
|
+
README.md: 902eaa1acb3cdff48bcdea44623a7979f1b6dc91
|
|
6
|
+
README.zh.md: a91e89ee282e47e7b96748aa56e0e1adfba28c89
|
package/README.md
CHANGED
|
@@ -1,55 +1,133 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: "The model-facing glob and grep discovery tools for users and maintainers composing or debugging workspace search for agents."
|
|
3
|
+
kind: "package-reference"
|
|
4
|
+
---
|
|
5
|
+
|
|
1
6
|
# @xneog/dsh-tool-fs-search
|
|
2
7
|
|
|
3
8
|
English | [中文](README.zh.md)
|
|
4
9
|
|
|
5
|
-
|
|
10
|
+
## Summary
|
|
11
|
+
|
|
12
|
+
`dsh-tool-fs-search` provides the model-facing filesystem discovery tools — `glob` and `grep` — backed by a packaged ripgrep binary, so no host `rg` install and no filesystem backend are needed. Each call runs ripgrep itself with a fixed argument set and returns workdir-relative results, and the tools are always available because every carrier packages ripgrep. Results are bounded by configurable caps, and a capped result is saved in full through the optional spill store when one is mounted. Choose this package when the model should discover files by pattern or search file contents; text file reading, writing, and editing are the sibling `dsh-tool-fs` package's job.
|
|
13
|
+
|
|
14
|
+
## Table of Contents
|
|
15
|
+
|
|
16
|
+
- [Use this package](#use-this-package)
|
|
17
|
+
- [Understand the implementation](#understand-the-implementation)
|
|
18
|
+
- [Further Exploration](#further-exploration)
|
|
19
|
+
- [Model Experience](#model-experience)
|
|
20
|
+
- [Known Limitations and Deferred Work](#known-limitations-and-deferred-work)
|
|
21
|
+
- [Dev Note](#dev-note)
|
|
22
|
+
|
|
23
|
+
-----
|
|
6
24
|
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
25
|
+
<a id="use-this-package"></a>
|
|
26
|
+
## Use this package
|
|
27
|
+
|
|
28
|
+
Mount the tools after a `ctx.subprocess` backend; no host `rg` install is needed, and no filesystem provider is required. The model then gets modification-time-ordered file discovery and line-oriented content search, each bounded and timeout-guarded.
|
|
29
|
+
|
|
30
|
+
### Minimal composition
|
|
31
|
+
|
|
32
|
+
A subprocess backend, then the tools; the spill backend is optional and makes capped results fully recoverable.
|
|
33
|
+
|
|
34
|
+
```yaml
|
|
35
|
+
- name: '@xneog/dsh-subprocess-local'
|
|
36
|
+
- name: '@xneog/dsh-tool-fs-search'
|
|
37
|
+
config:
|
|
38
|
+
sampleOverCapGlobResults: false
|
|
39
|
+
- name: '@xneog/dsh-spill-local'
|
|
13
40
|
```
|
|
14
41
|
|
|
15
|
-
|
|
42
|
+
`sampleOverCapGlobResults` is required and has no fallback: deployments choose the over-cap ordering contract explicitly. When formatted spill succeeds, both modes preserve the complete sorted list in the spill artifact.
|
|
16
43
|
|
|
17
|
-
|
|
44
|
+
### The tools
|
|
18
45
|
|
|
19
|
-
|
|
46
|
+
| Tool | Arguments | Behavior |
|
|
47
|
+
|---|---|---|
|
|
48
|
+
| `glob` | `pattern`, `path?` | Finds files whose paths match a glob pattern, including hidden and ignored files but excluding VCS metadata; a pattern with no `/` matches basenames at any depth, so `*` matches the whole tree; complete results stay modification-time ordered |
|
|
49
|
+
| `grep` | `pattern`, `path?`, `include?` | Searches file contents with a ripgrep regex and returns matches grouped by file as `Line N: <preview>`; `include` is one positive glob filter, with comma-separated lists and negated values rejected up front |
|
|
50
|
+
|
|
51
|
+
Routine budgets stay out of the model-facing schema: a model that needs surrounding context reads the matched file with `read`, and one that needs later results follows the returned spill locator's retrieval hint.
|
|
20
52
|
|
|
21
|
-
|
|
53
|
+
### Configuration
|
|
22
54
|
|
|
23
|
-
`sampleOverCapGlobResults` is required
|
|
55
|
+
`sampleOverCapGlobResults` is required; the remaining keys are optional search caps with the defaults below.
|
|
24
56
|
|
|
25
57
|
| Key | Default | Meaning |
|
|
26
58
|
|---|---|---|
|
|
27
|
-
| `sampleOverCapGlobResults` | none (required) | `true` samples an over-cap `glob` page across top-level entries; `false` keeps the modification-time-ordered head
|
|
28
|
-
| `globMaxResults` | `100` | Max paths one `glob` call shows inline
|
|
29
|
-
| `grepMaxMatches` | `250` | Max flat matches one `grep` call retains inline
|
|
30
|
-
| `grepMaxLineBytes` | `2000` | Byte cap per matched-line preview
|
|
31
|
-
| `rawOutputMaxBytes` | `20000000` | Max complete raw `rg` stdout a search will parse
|
|
32
|
-
| `timeoutMs` | `30000` | Cooperative tool-call budget
|
|
33
|
-
| `graceMs` | `3000` |
|
|
34
|
-
| `stderrMaxBytes` | `65536` | Diagnostic-tail budget for `rg` stderr
|
|
59
|
+
| `sampleOverCapGlobResults` | none (required) | `true` samples an over-cap `glob` page across top-level entries; `false` keeps the modification-time-ordered head |
|
|
60
|
+
| `globMaxResults` | `100` | Max paths one `glob` call shows inline |
|
|
61
|
+
| `grepMaxMatches` | `250` | Max flat matches one `grep` call retains inline; later matches go to the formatted spill artifact |
|
|
62
|
+
| `grepMaxLineBytes` | `2000` | Byte cap per matched-line preview, preserving UTF-8 boundaries |
|
|
63
|
+
| `rawOutputMaxBytes` | `20000000` | Max complete raw `rg` stdout a search will parse; larger raw output fails with `SEARCH_RAW_OUTPUT_OVERFLOW` |
|
|
64
|
+
| `timeoutMs` | `30000` | Cooperative tool-call budget on both tools, enforced through `exec.signal` |
|
|
65
|
+
| `graceMs` | `3000` | Terminate-escalation grace the subprocess seam grants past `timeoutMs` |
|
|
66
|
+
| `stderrMaxBytes` | `65536` | Diagnostic-tail budget for `rg` stderr |
|
|
67
|
+
| `searchMetaMaxBytes` | `65536` | Max bytes of one search's serialized `presentationMeta`; trailing groups/paths drop past it |
|
|
35
68
|
|
|
36
|
-
|
|
69
|
+
The generated [configuration catalog](../../../docs/config-catalog.md#xneogdsh-tool-fs-search) is the exhaustive source for every accepted field and its JSDoc.
|
|
37
70
|
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
71
|
+
### Deployment requirement
|
|
72
|
+
|
|
73
|
+
Node deployments receive the `@vscode/ripgrep` platform package on supported macOS, Linux, and Windows targets; Python SDK wheels copy the target-native binary beside the single-file runtime as a `-rg` sidecar. No carrier requires a host `rg`. Returned paths are displayed relative to the resolved workdir (the calling session's cwd when present) and are follow-up-readable with `read` only when that workdir and the filesystem root are the same workspace.
|
|
74
|
+
|
|
75
|
+
### Failures and recovery
|
|
76
|
+
|
|
77
|
+
Search failures carry the package-owned codes `SEARCH_INVALID_PATTERN` (ripgrep rejected the regex or glob), `SEARCH_FAILED` (a failed launch, inaccessible target, signal kill, or malformed `--json` output), `SEARCH_RAW_OUTPUT_OVERFLOW` (raw output over the cap), and `SEARCH_ABORTED` (cooperative timeout or caller cancellation). Exit 0 is success with results and exit 1 is a successful empty search; model argument mistakes stay ordinary tool argument errors.
|
|
78
|
+
|
|
79
|
+
-----
|
|
80
|
+
|
|
81
|
+
<a id="understand-the-implementation"></a>
|
|
82
|
+
## Understand the implementation
|
|
42
83
|
|
|
43
|
-
|
|
84
|
+
<details>
|
|
85
|
+
<summary>Implementation internals — click to expand</summary>
|
|
44
86
|
|
|
45
|
-
|
|
87
|
+
This section explains the design decisions behind the search tools and points at the code that realizes them; the observable behavior is fully covered in [Use this package](#use-this-package).
|
|
46
88
|
|
|
47
|
-
|
|
89
|
+
### Design concept
|
|
48
90
|
|
|
49
|
-
|
|
91
|
+
Local workspace discovery is naturally a process-backed `rg` workflow, and putting search on `ctx.fs` would force every filesystem backend to grow a search API. The subprocess seam owns spawn execution, process-tree termination, environment scrubbing, and bounded output capture; this package owns schemas, argument validation, argv construction, parsing, retention, formatted-result spill, and timeout declaration. The tools never expose a background job — the call returns only after `rg` exits, is terminated by the cooperative timeout, is aborted, or fails.
|
|
50
92
|
|
|
51
|
-
|
|
93
|
+
### Source map
|
|
52
94
|
|
|
95
|
+
| File | Role |
|
|
96
|
+
|---|---|
|
|
97
|
+
| [`src/index.ts`](src/index.ts) | Plugin entry: `Config`, tool composition, cap validation |
|
|
98
|
+
| [`src/glob.ts`](src/glob.ts) | `glob` schema, argv, parsing, inline sampling, formatting |
|
|
99
|
+
| [`src/grep.ts`](src/grep.ts) | `grep` schema, argv, `--json` parsing, preview retention, formatting |
|
|
100
|
+
| [`src/search-core.ts`](src/search-core.ts) | Shared spawn helper, `SEARCH_*` errors, spill handoff, workdir-relative display |
|
|
101
|
+
| [`src/presentation.ts`](src/presentation.ts) | Search-card metadata projection |
|
|
102
|
+
| [`src/direct-call.ts`](src/direct-call.ts) | Direct-call result acceptance for spill post-processing |
|
|
103
|
+
|
|
104
|
+
### How a search runs
|
|
105
|
+
|
|
106
|
+
Each call resolves the packaged binary (`@vscode/ripgrep`, or the executable's `-rg` sidecar in a pkg single-file runtime), prepends `--no-config` so a host `RIPGREP_CONFIG_PATH` cannot inject a `--pre` preprocessor into the unconfined spawn, and passes every model-controlled value as a plain argv element — no shell layer exists, so no quoting applies. Collect-mode budgets bound complete stdout and a stderr tail; a lossy stdout read fails as `SEARCH_RAW_OUTPUT_OVERFLOW` rather than parsing a silently-partial stream. The tools never read a raw spill path.
|
|
107
|
+
|
|
108
|
+
### Two budgets, two artifacts
|
|
109
|
+
|
|
110
|
+
Raw stdout and stderr are internal transport details; the tools always collect the complete result in memory, and only the inline page is capped. When a call yields more logical results than the inline cap, a best-effort spill saves the complete formatted preview to the spill store and the page carries its locator, while dispatches whose full value never enters model context skip the spill. Missing or failed spill keeps the inline page and reports that the complete result could not be saved — never an error. The collection and spill handoff live in `src/search-core.ts` and `src/presentation.ts`.
|
|
111
|
+
|
|
112
|
+
</details>
|
|
113
|
+
|
|
114
|
+
-----
|
|
115
|
+
|
|
116
|
+
<a id="further-exploration"></a>
|
|
117
|
+
## Further Exploration
|
|
118
|
+
|
|
119
|
+
Read these pages when the package-level contract is not enough. They move from the tools to the subprocess seam, the spill store, and the filesystem family.
|
|
120
|
+
|
|
121
|
+
- [Filesystem subsystem](../../../docs/subsystems/filesystem.md) — exhaustive provider contract, policy events, and error taxonomy.
|
|
122
|
+
- [tool-fs](../tool-fs/README.md) — the sibling `read`/`write`/`edit` tools for follow-up reads.
|
|
123
|
+
- [Subprocess capability](../../../docs/subsystems/subprocess.md) — the spawn seam these tools execute through.
|
|
124
|
+
- [Spill store](../../spill/spill/README.md) — the optional backend that makes capped results fully recoverable.
|
|
125
|
+
- [Timeout utility](../../util/timeout/README.md) — the `MAX_TIMER_DELAY_MS` bound on the terminate grace.
|
|
126
|
+
- [Generated tool catalog](../../../docs/tool-catalog.md#xneogdsh-tool-fs-search) — the exhaustive schemas this package registers.
|
|
127
|
+
|
|
128
|
+
-----
|
|
129
|
+
|
|
130
|
+
<a id="model-experience"></a>
|
|
53
131
|
## Model Experience
|
|
54
132
|
|
|
55
133
|
### System prompt
|
|
@@ -88,7 +166,7 @@ Prefix-stable while the plugin scope, sampling choice, and guidance text are unc
|
|
|
88
166
|
|
|
89
167
|
#### What the model sees
|
|
90
168
|
|
|
91
|
-
The glob description states the configured over-cap ordering. The generated [`glob` and `grep` schemas](../../../docs/tool-catalog.md#
|
|
169
|
+
The glob description states the configured over-cap ordering. The generated [`glob` and `grep` schemas](../../../docs/tool-catalog.md#xneogdsh-tool-fs-search) use `sampleOverCapGlobResults: true`; the tools are registered unconditionally.
|
|
92
170
|
|
|
93
171
|
#### Token effect
|
|
94
172
|
|
|
@@ -102,7 +180,7 @@ Prefix-stable while tool visibility and definitions are unchanged. Registration
|
|
|
102
180
|
|
|
103
181
|
#### What the model sees
|
|
104
182
|
|
|
105
|
-
`glob` returns one path per line; `grep` groups `Line <line>: <preview>` matches beneath each path. Empty searches return `No files found` or `No matches found`. A capped result ends with its omission count plus the spill locator and backend retrieval hint, or says the complete result could not be saved. With `sampleOverCapGlobResults: true`, an over-cap `glob` page takes paths round-robin across entries immediately beneath the actual search root, and the footer states the sampled basis and how many top-level entries it reached;
|
|
183
|
+
`glob` returns one path per line; `grep` groups `Line <line>: <preview>` matches beneath each path. Empty searches return `No files found` or `No matches found`. A capped result ends with its omission count plus the spill locator and backend retrieval hint, or says the complete result could not be saved. With `sampleOverCapGlobResults: true`, an over-cap `glob` page takes paths round-robin across entries immediately beneath the actual search root, and the footer states the sampled basis and how many top-level entries it reached; with `false`, the page is the modification-time-ordered head and keeps the plain capped-result footer. The spill artifact always holds the complete list in modification-time order.
|
|
106
184
|
|
|
107
185
|
#### Token effect
|
|
108
186
|
|
|
@@ -128,7 +206,24 @@ Append-only; newly visible content follows the reusable request prefix and does
|
|
|
128
206
|
|
|
129
207
|
## Known Limitations and Deferred Work
|
|
130
208
|
|
|
209
|
+
<a id="known-limitations-and-deferred-work"></a>
|
|
210
|
+
|
|
211
|
+
|
|
212
|
+
These limits define when the search tools are a poor fit or need special operational care. They are current package constraints, not a general search comparison or a task backlog.
|
|
213
|
+
|
|
131
214
|
- **Search and file access have no shared-workspace proof** — returned paths are follow-up-readable only when the workdir and filesystem root denote the same workspace; the package performs no runtime cross-service validation.
|
|
132
|
-
- **The packaged binary is fixed at dependency version** — `@vscode/ripgrep
|
|
215
|
+
- **The packaged binary is fixed at dependency version** — Node deployments use the version selected by `@vscode/ripgrep`; Python single-file runtimes copy that target-native version into the required `-rg` sidecar. An unsupported platform or a corrupted installation fails with `SEARCH_FAILED`, while the Python runtime package rejects a missing sidecar before launch. Remote or virtual filesystems need a co-located workspace or another search consumer.
|
|
133
216
|
- **The schemas expose one bounded page** — offset pagination, case-mode switches, alternate output modes, and provider-backed discovery remain outside this package; capped complete output requires a spill backend.
|
|
134
|
-
- **Sampling, when enabled, groups by first path segment beneath the search root only** — an over-cap `glob` page balances across those top-level entries, so a result concentrated deeper
|
|
217
|
+
- **Sampling, when enabled, groups by first path segment beneath the search root only** — an over-cap `glob` page balances across those top-level entries, so a result concentrated deeper is still shown unevenly below that level; recursive balancing is deferred.
|
|
218
|
+
|
|
219
|
+
<a id="dev-note"></a>
|
|
220
|
+
### Dev Note
|
|
221
|
+
|
|
222
|
+
<details>
|
|
223
|
+
<summary>Working context for maintainers — click to expand</summary>
|
|
224
|
+
|
|
225
|
+
None.
|
|
226
|
+
|
|
227
|
+
</details>
|
|
228
|
+
|
|
229
|
+
**Runtime invariant:** No companion is published. This model-facing adapter has no independent lifecycle stream; execution relations are owned by the capability seam it calls.
|
package/README.zh.md
CHANGED
|
@@ -1,55 +1,133 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: "面向模型的 glob 与 grep 发现工具:供组合或排查 agent 工作区搜索的用户与维护者使用。"
|
|
3
|
+
kind: "package-reference"
|
|
4
|
+
---
|
|
5
|
+
|
|
1
6
|
# @xneog/dsh-tool-fs-search
|
|
2
7
|
|
|
3
8
|
[English](README.md) | 中文
|
|
4
9
|
|
|
5
|
-
|
|
10
|
+
## 概述
|
|
6
11
|
|
|
7
|
-
|
|
8
|
-
// A deployment chooses how over-cap glob pages are selected.
|
|
9
|
-
await ctx.plugin(LocalSubprocessRuntime) // @xneog/dsh-subprocess-local
|
|
10
|
-
await ctx.plugin(ToolFsSearch, { sampleOverCapGlobResults: false })
|
|
11
|
-
// Optional: a spill backend makes capped results fully recoverable.
|
|
12
|
-
await ctx.plugin(LocalSpillStore) // @xneog/dsh-spill-local
|
|
13
|
-
```
|
|
12
|
+
`dsh-tool-fs-search` 提供面向模型的文件系统发现工具——`glob` 与 `grep`——由打包的 ripgrep 二进制支持,因此既不需要宿主 `rg` 安装,也不需要文件系统后端。每次调用都由 ripgrep 自身以固定参数集执行,并返回相对于工作目录的结果;由于每种载体都打包 ripgrep,工具始终可用。结果受可配置上限约束,达到上限的结果会在挂载可选 spill 存储时完整保存。当模型需要按模式发现文件或搜索文件内容时选择本包;文本文件的读取、写入与编辑是同级 `dsh-tool-fs` 包的职责。
|
|
14
13
|
|
|
15
|
-
|
|
14
|
+
## 目录
|
|
16
15
|
|
|
17
|
-
|
|
16
|
+
- [使用本包](#use-this-package)
|
|
17
|
+
- [理解实现](#understand-the-implementation)
|
|
18
|
+
- [进一步探索](#further-exploration)
|
|
19
|
+
- [模型体验](#model-experience)
|
|
20
|
+
- [已知限制与延期工作](#known-limitations-and-deferred-work)
|
|
21
|
+
- [开发备注](#dev-note)
|
|
18
22
|
|
|
19
|
-
|
|
23
|
+
-----
|
|
20
24
|
|
|
21
|
-
|
|
25
|
+
<a id="use-this-package"></a>
|
|
26
|
+
## 使用本包
|
|
22
27
|
|
|
23
|
-
`
|
|
28
|
+
在 `ctx.subprocess` 后端之后挂载工具;无需宿主 `rg` 安装,也无需文件系统提供方。模型随后获得按修改时间排序的文件发现与按行组织的内容搜索,两者都有界并受超时防护。
|
|
24
29
|
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
30
|
+
### 最小组合
|
|
31
|
+
|
|
32
|
+
一个子进程后端,然后是工具;spill 后端为可选,使达到上限的结果可完整恢复。
|
|
33
|
+
|
|
34
|
+
```yaml
|
|
35
|
+
- name: '@xneog/dsh-subprocess-local'
|
|
36
|
+
- name: '@xneog/dsh-tool-fs-search'
|
|
37
|
+
config:
|
|
38
|
+
sampleOverCapGlobResults: false
|
|
39
|
+
- name: '@xneog/dsh-spill-local'
|
|
40
|
+
```
|
|
41
|
+
|
|
42
|
+
`sampleOverCapGlobResults` 是必填项且没有回退值:部署必须显式选择超过上限时的排序约定。格式化 spill 成功时,两种模式都会在 spill 产物中保留完整排序列表。
|
|
35
43
|
|
|
36
|
-
|
|
44
|
+
### 工具
|
|
37
45
|
|
|
38
46
|
| 工具 | 参数 | 行为 |
|
|
39
47
|
|---|---|---|
|
|
40
|
-
| `glob` | `pattern`、`path?` |
|
|
41
|
-
| `grep` | `pattern`、`path?`、`include?` |
|
|
48
|
+
| `glob` | `pattern`、`path?` | 查找路径匹配 glob 模式的文件,包含隐藏与忽略文件但排除 VCS 元数据;不含 `/` 的模式匹配任意深度的基名,因此 `*` 匹配整棵树;完整结果保持按修改时间排序 |
|
|
49
|
+
| `grep` | `pattern`、`path?`、`include?` | 用 ripgrep 正则搜索文件内容,并按文件分组返回 `Line N: <preview>` 匹配;`include` 是一个正向 glob 过滤器,逗号分隔列表与否定值会被前置拒绝 |
|
|
50
|
+
|
|
51
|
+
常规预算不进入面向模型的 schema:需要周边上下文的模型用 `read` 读取匹配文件,需要后续结果的模型遵循返回的 spill locator 检索提示。
|
|
52
|
+
|
|
53
|
+
### 配置
|
|
54
|
+
|
|
55
|
+
`sampleOverCapGlobResults` 为必填;其余键是可选的搜索上限,默认值如下。
|
|
56
|
+
|
|
57
|
+
| 键 | 默认值 | 含义 |
|
|
58
|
+
|---|---|---|
|
|
59
|
+
| `sampleOverCapGlobResults` | 无(必填) | `true` 在顶层条目之间对超过上限的 `glob` 页面采样;`false` 保留按修改时间排序的前部 |
|
|
60
|
+
| `globMaxResults` | `100` | 一次 `glob` 调用内联展示的最大路径数 |
|
|
61
|
+
| `grepMaxMatches` | `250` | 一次 `grep` 调用内联保留的最大平铺匹配数;后续匹配写入格式化 spill 产物 |
|
|
62
|
+
| `grepMaxLineBytes` | `2000` | 每条匹配行预览的字节上限,保留 UTF-8 边界 |
|
|
63
|
+
| `rawOutputMaxBytes` | `20000000` | 搜索将解析的完整原始 `rg` stdout 上限;更大的原始输出以 `SEARCH_RAW_OUTPUT_OVERFLOW` 失败 |
|
|
64
|
+
| `timeoutMs` | `30000` | 附加到两个工具的协作式工具调用预算,通过 `exec.signal` 强制执行 |
|
|
65
|
+
| `graceMs` | `3000` | subprocess seam 在 `timeoutMs` 之外授予的终止升级宽限期 |
|
|
66
|
+
| `stderrMaxBytes` | `65536` | `rg` stderr 的诊断尾部预算 |
|
|
67
|
+
| `searchMetaMaxBytes` | `65536` | 一次搜索序列化 `presentationMeta` 的字节上限;超出部分丢弃尾部的组/路径 |
|
|
68
|
+
|
|
69
|
+
生成的[配置目录](../../../docs/config-catalog.zh.md#xneogdsh-tool-fs-search)是每个受支持字段及其 JSDoc 的穷尽式真源。
|
|
70
|
+
|
|
71
|
+
### 部署要求
|
|
72
|
+
|
|
73
|
+
Node 部署在受支持的 macOS、Linux 与 Windows 目标上获得 `@vscode/ripgrep` 平台包;Python SDK wheel 把目标原生二进制复制到单文件运行时旁,作为 `-rg` 伴随文件。两种载体均不要求宿主安装 `rg`。返回路径相对于解析后的工作目录显示(有会话 cwd 时使用会话 cwd),只有该工作目录与文件系统根目录是同一工作区时,才能用 `read` 继续读取。
|
|
74
|
+
|
|
75
|
+
### 失败与恢复
|
|
76
|
+
|
|
77
|
+
搜索失败携带本包定义的错误码:`SEARCH_INVALID_PATTERN`(ripgrep 拒绝正则或 glob)、`SEARCH_FAILED`(启动失败、目标不可访问、信号终止或 `--json` 输出格式错误)、`SEARCH_RAW_OUTPUT_OVERFLOW`(原始输出超过上限)与 `SEARCH_ABORTED`(协作式超时或调用方取消)。退出 0 表示成功且有结果,退出 1 表示成功的空搜索;模型参数错误仍是普通工具参数错误。
|
|
78
|
+
|
|
79
|
+
-----
|
|
80
|
+
|
|
81
|
+
<a id="understand-the-implementation"></a>
|
|
82
|
+
## 理解实现
|
|
42
83
|
|
|
43
|
-
|
|
84
|
+
<details>
|
|
85
|
+
<summary>实现细节——点击展开</summary>
|
|
44
86
|
|
|
45
|
-
|
|
87
|
+
本节解释搜索工具背后的设计决策,并指出实现它们的代码位置;可观察行为已在[使用本包](#use-this-package)中完整说明。
|
|
46
88
|
|
|
47
|
-
|
|
89
|
+
### 设计理念
|
|
48
90
|
|
|
49
|
-
|
|
91
|
+
本地工作区发现天然是由进程支持的 `rg` 工作流;如果把搜索放到 `ctx.fs` 上,就会迫使每个文件系统后端扩展搜索 API。subprocess seam 负责 spawn 执行、进程树终止、环境清理与有界输出捕获;本包负责 schema、参数校验、argv 构造、解析、保留、格式化结果 spill 与超时声明。工具绝不暴露后台任务——只有在 `rg` 退出、被协作式超时终止、被中止或失败后,调用才会返回。
|
|
50
92
|
|
|
51
|
-
|
|
93
|
+
### 源码地图
|
|
52
94
|
|
|
95
|
+
| 文件 | 职责 |
|
|
96
|
+
|---|---|
|
|
97
|
+
| [`src/index.ts`](src/index.ts) | 插件入口:`Config`、工具组合、上限校验 |
|
|
98
|
+
| [`src/glob.ts`](src/glob.ts) | `glob` schema、argv、解析、内联采样、格式化 |
|
|
99
|
+
| [`src/grep.ts`](src/grep.ts) | `grep` schema、argv、`--json` 解析、预览保留、格式化 |
|
|
100
|
+
| [`src/search-core.ts`](src/search-core.ts) | 共享 spawn 助手、`SEARCH_*` 错误、spill 交接、工作目录相对展示 |
|
|
101
|
+
| [`src/presentation.ts`](src/presentation.ts) | 搜索卡片元数据投影 |
|
|
102
|
+
| [`src/direct-call.ts`](src/direct-call.ts) | spill 后处理的直接调用结果接受 |
|
|
103
|
+
|
|
104
|
+
### 搜索如何运行
|
|
105
|
+
|
|
106
|
+
每次调用解析打包二进制(`@vscode/ripgrep`,或 pkg 单文件运行时中可执行程序的 `-rg` 伴随文件),前置 `--no-config`,使宿主的 `RIPGREP_CONFIG_PATH` 无法向不受约束的 spawn 注入 `--pre` 预处理器,并把每个模型控制的值作为普通 argv 元素传入——不存在 shell 层,因此不涉及 shell 引号处理。collect 模式预算限制完整 stdout 与 stderr 尾部;lossy stdout 读取以 `SEARCH_RAW_OUTPUT_OVERFLOW` 失败,而不是解析静默不完整的流。工具从不读取原始 spill 路径。
|
|
107
|
+
|
|
108
|
+
### 两类预算、两类产物
|
|
109
|
+
|
|
110
|
+
原始 stdout 与 stderr 是内部传输细节;工具始终把完整结果收集到内存中,只有内联页面设有上限。当调用产生超过内联上限的逻辑结果时,尽力而为的 spill 会把完整格式化预览保存到 spill 存储,页面携带其 locator;完整值不会进入模型上下文的分派则跳过 spill。spill 缺失或失败时保留内联页面,并报告完整结果无法保存——绝不会成为错误。收集与 spill 交接位于 `src/search-core.ts` 与 `src/presentation.ts`。
|
|
111
|
+
|
|
112
|
+
</details>
|
|
113
|
+
|
|
114
|
+
-----
|
|
115
|
+
|
|
116
|
+
<a id="further-exploration"></a>
|
|
117
|
+
## 进一步探索
|
|
118
|
+
|
|
119
|
+
当包级约定不够用时阅读以下页面。它们从工具逐步进入 subprocess seam、spill 存储与文件系统家族。
|
|
120
|
+
|
|
121
|
+
- [文件系统子系统](../../../docs/subsystems/filesystem.zh.md)——穷尽式提供方约定、策略事件与错误分类体系。
|
|
122
|
+
- [tool-fs](../tool-fs/README.zh.md)——用于后续读取的同级 `read`/`write`/`edit` 工具。
|
|
123
|
+
- [子进程能力](../../../docs/subsystems/subprocess.zh.md)——这些工具执行所经由的 spawn seam。
|
|
124
|
+
- [Spill 存储](../../spill/spill/README.zh.md)——使达到上限结果可完整恢复的可选后端。
|
|
125
|
+
- [超时工具](../../util/timeout/README.zh.md)——终止宽限期的 `MAX_TIMER_DELAY_MS` 上限。
|
|
126
|
+
- [生成工具目录](../../../docs/tool-catalog.zh.md#xneogdsh-tool-fs-search)——本包注册的穷尽式 schema。
|
|
127
|
+
|
|
128
|
+
-----
|
|
129
|
+
|
|
130
|
+
<a id="model-experience"></a>
|
|
53
131
|
## 模型体验
|
|
54
132
|
|
|
55
133
|
### 系统提示词
|
|
@@ -88,7 +166,7 @@ Use the grep tool — not shell grep or rg — to search file contents. Use read
|
|
|
88
166
|
|
|
89
167
|
#### 模型看到的内容
|
|
90
168
|
|
|
91
|
-
glob 描述声明了配置的超过上限排序方式。生成的 [`glob` 和 `grep` schema](../../../docs/tool-catalog.md#
|
|
169
|
+
glob 描述声明了配置的超过上限排序方式。生成的 [`glob` 和 `grep` schema](../../../docs/tool-catalog.zh.md#xneogdsh-tool-fs-search) 使用 `sampleOverCapGlobResults: true`;工具无条件注册。
|
|
92
170
|
|
|
93
171
|
#### Token 影响
|
|
94
172
|
|
|
@@ -102,7 +180,7 @@ glob 描述声明了配置的超过上限排序方式。生成的 [`glob` 和 `g
|
|
|
102
180
|
|
|
103
181
|
#### 模型看到的内容
|
|
104
182
|
|
|
105
|
-
`glob` 每行返回一个路径;`grep` 在每个路径下分组展示 `Line <line>: <preview>` 匹配。空搜索返回 `No files found` 或 `No matches found`。达到上限的结果以省略计数结尾,并附 spill locator 与后端检索提示,或说明完整结果无法保存。启用 `sampleOverCapGlobResults: true` 时,超过上限的 `glob`
|
|
183
|
+
`glob` 每行返回一个路径;`grep` 在每个路径下分组展示 `Line <line>: <preview>` 匹配。空搜索返回 `No files found` 或 `No matches found`。达到上限的结果以省略计数结尾,并附 spill locator 与后端检索提示,或说明完整结果无法保存。启用 `sampleOverCapGlobResults: true` 时,超过上限的 `glob` 页面按实际搜索根正下方的条目轮转取路径,页脚说明采样依据及其覆盖的顶层条目数;`false` 时页面是按修改时间排序的前部,并保留普通的上限结果页脚。spill 产物始终持有按修改时间排序的完整列表。
|
|
106
184
|
|
|
107
185
|
#### Token 影响
|
|
108
186
|
|
|
@@ -126,9 +204,26 @@ glob 描述声明了配置的超过上限排序方式。生成的 [`glob` 和 `g
|
|
|
126
204
|
|
|
127
205
|
仅追加;新可见内容跟在可复用请求前缀之后,不会使既有 KV Cache 条目失效。
|
|
128
206
|
|
|
129
|
-
##
|
|
207
|
+
## 已知限制与延期工作
|
|
208
|
+
|
|
209
|
+
<a id="known-limitations-and-deferred-work"></a>
|
|
210
|
+
|
|
211
|
+
|
|
212
|
+
这些限制说明搜索工具何时不合适,或何时需要特别的运维注意。它们是当前包约束,不是通用搜索对比或任务积压。
|
|
130
213
|
|
|
131
214
|
- **搜索与文件访问没有共享工作区证明**——只有当工作目录与文件系统根目录指向同一工作区时,返回路径才可继续读取;本包不执行运行时跨服务校验。
|
|
132
|
-
-
|
|
215
|
+
- **打包二进制固定在依赖版本上**——Node 部署使用 `@vscode/ripgrep` 选择的版本;Python 单文件运行时将对应目标的原生版本复制为必需的 `-rg` 伴随文件。不支持的平台或损坏的安装会以 `SEARCH_FAILED` 使调用失败,Python 运行时包则会在启动前拒绝缺少伴随文件的安装。远程或虚拟文件系统需要共置的工作区或另一个搜索消费方。
|
|
133
216
|
- **schema 只暴露一个有界页面**——偏移分页、大小写开关、替代输出模式与提供方支撑的发现仍不在本包范围内;达到上限的完整输出需要 spill 后端。
|
|
134
|
-
- **启用采样时仅按搜索根正下方的第一段路径分组**——超过上限的 `glob`
|
|
217
|
+
- **启用采样时仅按搜索根正下方的第一段路径分组**——超过上限的 `glob` 页面在这些顶层条目之间平衡,因此集中在更深处的结果在该层级之下仍会呈现不均;递归平衡被延期。
|
|
218
|
+
|
|
219
|
+
<a id="dev-note"></a>
|
|
220
|
+
### 开发备注
|
|
221
|
+
|
|
222
|
+
<details>
|
|
223
|
+
<summary>维护者的工作上下文——点击展开</summary>
|
|
224
|
+
|
|
225
|
+
无。
|
|
226
|
+
|
|
227
|
+
</details>
|
|
228
|
+
|
|
229
|
+
**运行时不变式:** 不发布伴生入口。这个模型侧 adapter 没有独立 lifecycle stream;执行关系由它调用的 capability seam 负责。
|
package/lib/index.js
CHANGED
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
import z from "@xneog/schemastery";
|
|
2
2
|
import { MAX_TIMER_DELAY_MS } from "@xneog/dsh-timeout";
|
|
3
|
-
import { isAbsolute, relative, sep } from "node:path";
|
|
3
|
+
import { isAbsolute, join, parse, relative, sep } from "node:path";
|
|
4
4
|
import { defineTool } from "@xneog/dsh-tools";
|
|
5
|
+
import { existsSync } from "node:fs";
|
|
5
6
|
import { HarnessError } from "@xneog/dsh-llm";
|
|
6
7
|
import { ItemRetainer, TextRetainer } from "@xneog/dsh-output-retention";
|
|
7
8
|
//#region lib/types/search-core.js
|
|
@@ -107,18 +108,22 @@ let rgPathPromise;
|
|
|
107
108
|
/**
|
|
108
109
|
* The packaged ripgrep binary path, resolved lazily once per process.
|
|
109
110
|
*
|
|
110
|
-
*
|
|
111
|
-
*
|
|
112
|
-
*
|
|
113
|
-
*
|
|
114
|
-
*
|
|
115
|
-
* the package's documented no-load-time-probe contract.
|
|
111
|
+
* A single-file runtime uses the executable's `-rg` sidecar because a native
|
|
112
|
+
* helper cannot be spawned from pkg's virtual filesystem. Node-mode builds
|
|
113
|
+
* fall back to the platform package selected by `@vscode/ripgrep`. Resolving
|
|
114
|
+
* at the call boundary keeps a missing or corrupt binary at the first search
|
|
115
|
+
* call as `SEARCH_FAILED`, rather than failing the Loader composition.
|
|
116
116
|
*
|
|
117
117
|
* @returns the packaged binary's absolute path; the memoized promise rejects
|
|
118
118
|
* when the platform package cannot be resolved.
|
|
119
119
|
*/
|
|
120
120
|
function resolveRgPath() {
|
|
121
|
-
rgPathPromise ??=
|
|
121
|
+
rgPathPromise ??= Promise.resolve().then(async () => {
|
|
122
|
+
const executable = parse(process.execPath);
|
|
123
|
+
const executableSidecar = process.platform === "win32" ? join(executable.dir, `${executable.name}-rg.exe`) : `${process.execPath}-rg`;
|
|
124
|
+
if ("pkg" in process && existsSync(executableSidecar)) return executableSidecar;
|
|
125
|
+
return (await import("@vscode/ripgrep")).rgPath;
|
|
126
|
+
});
|
|
122
127
|
return rgPathPromise;
|
|
123
128
|
}
|
|
124
129
|
/**
|
|
@@ -767,7 +772,7 @@ function applyGlobTool(ctx, caps) {
|
|
|
767
772
|
const overCapGuidance = caps.sampleOverCapGlobResults ? "while a larger one is sampled across top-level entries, so it spans the tree instead of one subtree." : "while a larger one keeps the modification-time-ordered head.";
|
|
768
773
|
ctx.systemPrompt.section({
|
|
769
774
|
name: "tool:glob",
|
|
770
|
-
order:
|
|
775
|
+
order: ctx.systemPrompt.getSectionOrder("TOOL_GLOB"),
|
|
771
776
|
text: `Use the glob tool — not shell find — to discover files by path pattern. A pattern with no "/" matches basenames at any depth, so "*" matches every file in the tree rather than its top level. Results are files only, never directories, and include hidden and ignored files: a result that fits comes back in modification-time order, ${overCapGuidance}`
|
|
772
777
|
});
|
|
773
778
|
const overCapDescription = caps.sampleOverCapGlobResults ? `a larger result instead returns ${caps.maxResults} paths sampled across top-level entries` : `a larger result returns the first ${caps.maxResults} paths in modification-time order`;
|
|
@@ -1076,7 +1081,7 @@ function presentGrepResult(_args, result) {
|
|
|
1076
1081
|
function applyGrepTool(ctx, caps) {
|
|
1077
1082
|
ctx.systemPrompt.section({
|
|
1078
1083
|
name: "tool:grep",
|
|
1079
|
-
order:
|
|
1084
|
+
order: ctx.systemPrompt.getSectionOrder("TOOL_GREP"),
|
|
1080
1085
|
text: "Use the grep tool — not shell grep or rg — to search file contents. Use read on a matched file when you need surrounding context."
|
|
1081
1086
|
});
|
|
1082
1087
|
const tool = defineTool({
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
/** Shared top-level-call post-policy selection for search result spill. @module dsh-tool-fs-search/direct-call */
|
|
2
2
|
import type { Context } from '@xneog/cordis';
|
|
3
|
-
import type {
|
|
3
|
+
import type { PostToolDecision, ToolDefinition, ToolExecution, ToolExecutionResult } from '@xneog/dsh-tools';
|
|
4
|
+
import type { JsonValue } from '@xneog/dsh-util-values';
|
|
4
5
|
/**
|
|
5
6
|
* Return the accepted canonical value only when this tool still owns a direct
|
|
6
7
|
* successful top-level call and no downstream policy replaced either projection.
|
|
@@ -87,12 +87,11 @@ export interface RipgrepRun {
|
|
|
87
87
|
/**
|
|
88
88
|
* The packaged ripgrep binary path, resolved lazily once per process.
|
|
89
89
|
*
|
|
90
|
-
*
|
|
91
|
-
*
|
|
92
|
-
*
|
|
93
|
-
*
|
|
94
|
-
*
|
|
95
|
-
* the package's documented no-load-time-probe contract.
|
|
90
|
+
* A single-file runtime uses the executable's `-rg` sidecar because a native
|
|
91
|
+
* helper cannot be spawned from pkg's virtual filesystem. Node-mode builds
|
|
92
|
+
* fall back to the platform package selected by `@vscode/ripgrep`. Resolving
|
|
93
|
+
* at the call boundary keeps a missing or corrupt binary at the first search
|
|
94
|
+
* call as `SEARCH_FAILED`, rather than failing the Loader composition.
|
|
96
95
|
*
|
|
97
96
|
* @returns the packaged binary's absolute path; the memoized promise rejects
|
|
98
97
|
* when the platform package cannot be resolved.
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@xneog/dsh-tool-fs-search",
|
|
3
3
|
"description": "Model-facing filesystem discovery tools (glob, grep) backed by the packaged ripgrep binary (@vscode/ripgrep)",
|
|
4
|
-
"version": "0.1.
|
|
4
|
+
"version": "0.1.3-alpha.1",
|
|
5
5
|
"publishConfig": {
|
|
6
6
|
"access": "public"
|
|
7
7
|
},
|
|
@@ -18,47 +18,40 @@
|
|
|
18
18
|
"types": "./lib/types/index.d.ts",
|
|
19
19
|
"default": "./lib/index.js"
|
|
20
20
|
},
|
|
21
|
-
"./invariant": {
|
|
22
|
-
"types": "./lib/types/invariant.d.ts",
|
|
23
|
-
"default": "./lib/invariant.js"
|
|
24
|
-
},
|
|
25
21
|
"./src/*": "./src/*",
|
|
26
22
|
"./package.json": "./package.json"
|
|
27
23
|
},
|
|
28
24
|
"files": [
|
|
29
25
|
"lib/index.js",
|
|
30
|
-
"lib/invariant.js",
|
|
31
26
|
"lib/types/**/*.d.ts"
|
|
32
27
|
],
|
|
33
28
|
"license": "MIT",
|
|
34
29
|
"dependencies": {
|
|
35
30
|
"@vscode/ripgrep": "^1.18.0",
|
|
36
|
-
"@xneog/schemastery": "
|
|
31
|
+
"@xneog/schemastery": "^3.18.2"
|
|
37
32
|
},
|
|
38
33
|
"peerDependencies": {
|
|
39
|
-
"@xneog/dsh-
|
|
40
|
-
"@xneog/dsh-
|
|
41
|
-
"@xneog/dsh-
|
|
42
|
-
"@xneog/dsh-
|
|
43
|
-
"@xneog/dsh-
|
|
44
|
-
"@xneog/dsh-
|
|
45
|
-
"@xneog/dsh-
|
|
46
|
-
"@xneog/
|
|
47
|
-
"@xneog/dsh-
|
|
48
|
-
"@xneog/cordis": "0.1.0"
|
|
34
|
+
"@xneog/dsh-llm": "^0.1.3-alpha.1",
|
|
35
|
+
"@xneog/dsh-output-retention": "^0.1.3-alpha.1",
|
|
36
|
+
"@xneog/dsh-session": "^0.1.3-alpha.1",
|
|
37
|
+
"@xneog/dsh-spill": "^0.1.3-alpha.1",
|
|
38
|
+
"@xneog/dsh-subprocess": "^0.1.3-alpha.1",
|
|
39
|
+
"@xneog/dsh-timeout": "^0.1.3-alpha.1",
|
|
40
|
+
"@xneog/dsh-tools": "^0.1.3-alpha.1",
|
|
41
|
+
"@xneog/cordis": "^4.0.2",
|
|
42
|
+
"@xneog/dsh-system-prompt": "^0.1.3-alpha.1"
|
|
49
43
|
},
|
|
50
44
|
"devDependencies": {
|
|
51
|
-
"@xneog/dsh-
|
|
52
|
-
"@xneog/dsh-
|
|
53
|
-
"@xneog/dsh-
|
|
54
|
-
"@xneog/dsh-
|
|
55
|
-
"@xneog/dsh-
|
|
56
|
-
"@xneog/dsh-
|
|
57
|
-
"@xneog/dsh-
|
|
58
|
-
"@xneog/
|
|
59
|
-
"@xneog/dsh-
|
|
60
|
-
"@xneog/dsh-
|
|
61
|
-
"@xneog/dsh-tools": "0.1.
|
|
62
|
-
"@xneog/cordis": "0.1.0"
|
|
45
|
+
"@xneog/dsh-subprocess": "^0.1.3-alpha.1",
|
|
46
|
+
"@xneog/dsh-agent": "^0.1.3-alpha.1",
|
|
47
|
+
"@xneog/dsh-llm": "^0.1.3-alpha.1",
|
|
48
|
+
"@xneog/dsh-output-retention": "^0.1.3-alpha.1",
|
|
49
|
+
"@xneog/dsh-session": "^0.1.3-alpha.1",
|
|
50
|
+
"@xneog/dsh-system-prompt": "^0.1.3-alpha.1",
|
|
51
|
+
"@xneog/dsh-timeout": "^0.1.3-alpha.1",
|
|
52
|
+
"@xneog/cordis": "^4.0.2",
|
|
53
|
+
"@xneog/dsh-subprocess-local": "^0.1.3-alpha.1",
|
|
54
|
+
"@xneog/dsh-spill": "^0.1.3-alpha.1",
|
|
55
|
+
"@xneog/dsh-tools": "^0.1.3-alpha.1"
|
|
63
56
|
}
|
|
64
57
|
}
|
package/lib/invariant.js
DELETED
|
@@ -1,23 +0,0 @@
|
|
|
1
|
-
//#region lib/types/invariant.js
|
|
2
|
-
/**
|
|
3
|
-
* Package-owned invariant companion for `@xneog/dsh-tool-fs-search`.
|
|
4
|
-
* @module @xneog/dsh-tool-fs-search/invariant
|
|
5
|
-
*/
|
|
6
|
-
const PACKAGE_NAME = "@xneog/dsh-tool-fs-search";
|
|
7
|
-
/** Cordis companion plugin name. */
|
|
8
|
-
const name = "tool-fs-search-invariant";
|
|
9
|
-
/** Service required before the companion can reserve package ownership. */
|
|
10
|
-
const inject = ["invariants"];
|
|
11
|
-
/**
|
|
12
|
-
* No runtime invariant: this model-facing adapter has no independent lifecycle stream; execution
|
|
13
|
-
* relations are owned by the capability seam it calls.
|
|
14
|
-
*/
|
|
15
|
-
const install = () => {};
|
|
16
|
-
/**
|
|
17
|
-
* Register this package's invariant companion.
|
|
18
|
-
* @param ctx - Cordis context carrying the invariant service.
|
|
19
|
-
* @returns the installed registration's disposer after setup succeeds.
|
|
20
|
-
*/
|
|
21
|
-
const apply = (ctx) => Promise.resolve(ctx.invariants.register(PACKAGE_NAME, install));
|
|
22
|
-
//#endregion
|
|
23
|
-
export { apply, inject, name };
|
package/lib/types/invariant.d.ts
DELETED
|
@@ -1,16 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Package-owned invariant companion for `@xneog/dsh-tool-fs-search`.
|
|
3
|
-
* @module @xneog/dsh-tool-fs-search/invariant
|
|
4
|
-
*/
|
|
5
|
-
import type { Context } from '@xneog/cordis';
|
|
6
|
-
/** Cordis companion plugin name. */
|
|
7
|
-
export declare const name = "tool-fs-search-invariant";
|
|
8
|
-
/** Service required before the companion can reserve package ownership. */
|
|
9
|
-
export declare const inject: string[];
|
|
10
|
-
/**
|
|
11
|
-
* Register this package's invariant companion.
|
|
12
|
-
* @param ctx - Cordis context carrying the invariant service.
|
|
13
|
-
* @returns the installed registration's disposer after setup succeeds.
|
|
14
|
-
*/
|
|
15
|
-
export declare const apply: (ctx: Context) => Promise<() => void>;
|
|
16
|
-
//# sourceMappingURL=invariant.d.ts.map
|