@karmaniverous/jeeves-watcher 0.19.1 → 0.21.0-0

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/LICENSE ADDED
@@ -0,0 +1,28 @@
1
+ BSD 3-Clause License
2
+
3
+ Copyright (c) 2025, Jason Williscroft
4
+
5
+ Redistribution and use in source and binary forms, with or without
6
+ modification, are permitted provided that the following conditions are met:
7
+
8
+ 1. Redistributions of source code must retain the above copyright notice, this
9
+ list of conditions and the following disclaimer.
10
+
11
+ 2. Redistributions in binary form must reproduce the above copyright notice,
12
+ this list of conditions and the following disclaimer in the documentation
13
+ and/or other materials provided with the distribution.
14
+
15
+ 3. Neither the name of the copyright holder nor the names of its
16
+ contributors may be used to endorse or promote products derived from
17
+ this software without specific prior written permission.
18
+
19
+ THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
20
+ AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21
+ IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
22
+ DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
23
+ FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
24
+ DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
25
+ SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
26
+ CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
27
+ OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28
+ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
package/README.md CHANGED
@@ -4,18 +4,20 @@ Filesystem watcher that keeps a [Qdrant](https://qdrant.tech/) vector store in s
4
4
 
5
5
  ## Requirements
6
6
 
7
- - **Node.js** ≥ 22
7
+ - **Node.js** ≥ 24.22.2
8
8
 
9
9
  ## Features
10
10
 
11
- - **Filesystem watching** — monitors directories for file changes via [chokidar](https://github.com/paulmillr/chokidar)
12
- - **Multi-format extraction** — PDF, HTML, DOCX, Markdown, plain text, and more
13
- - **Configurable chunking** — token-based text splitting with overlap control
11
+ - **Filesystem watching** — monitors directories for file changes via [@parcel/watcher](https://github.com/parcel-bundler/watcher) (one native subscription per watch root; [chokidar](https://github.com/paulmillr/chokidar) on request or when polling)
12
+ - **Multi-format extraction** — PDF, HTML, DOCX, Markdown, JSON and plain text (other extensions are read as plain text)
13
+ - **Configurable chunking** — character-based text splitting with overlap control
14
14
  - **Embedding providers** — Gemini (default) or mock (for testing); extensible via provider registry
15
15
  - **Qdrant sync** — automatic upsert/delete keeps the vector store current
16
16
  - **Rules engine** — glob-based inference rules for metadata enrichment
17
- - **REST API** — Fastify server for search, status, config, and management
18
- - **CLI** — `jeeves-watcher init`, `validate`, `start`, and more
17
+ - **REST API** — Fastify server for search, status, config, and management, with optional bearer API key (`api.apiKey`)
18
+ - **Source documents** — index records owned by another application, retrieved by HTTP callback on notification (`sources` config, `POST /documents`); see the [Source Documents guide](https://docs.karmanivero.us/jeeves-watcher/documents/Service_Guides.Source_Documents.html)
19
+ - **SDK** — [`@karmaniverous/jeeves-watcher-sdk`](https://www.npmjs.com/package/@karmaniverous/jeeves-watcher-sdk), a typed TypeScript client for the application-facing API
20
+ - **CLI** — `jeeves-watcher init`, `config validate`, `start`, and more
19
21
 
20
22
  ## Version Control (VCS)
21
23
 
@@ -51,9 +53,11 @@ Add a `vcs` block to your config:
51
53
  | Property | Default | Description |
52
54
  | --- | --- | --- |
53
55
  | `vcs.enabled` | `false` | Enable git-backed version control globally |
56
+ | `vcs.author.name` / `vcs.author.email` | `"jeeves-watcher"` / `"watcher@localhost"` | Git commit author identity |
54
57
  | `vcs.commitThrottleMs` | `30000` | Throttle interval (ms) for batching file changes into commits. Min: 1000 |
55
58
  | `vcs.maxBatchSize` | `1000` | Maximum files per commit batch. Flushes immediately when exceeded. Min: 1 |
56
- | `vcs.branch` | `"master"` | Git branch name for VCS operations. Squash retention and startup recovery target this branch |
59
+ | `vcs.maxFileBytes` | `100000000` | Size cap for versioned files (bytes, or `k`/`m`/`g`). A new file over it is not staged; a tracked file that grows past it is untracked in its own commit. `0` disables |
60
+ | `vcs.branch` | `"master"` | Git branch name for VCS operations. Squash retention targets this branch, and startup warns when HEAD is not on it |
57
61
  | `vcs.commitMessage.enabled` | `true` | Enable AI-generated commit messages |
58
62
  | `vcs.commitMessage.provider` | `"anthropic"` | AI provider (currently only `"anthropic"` supported) |
59
63
  | `vcs.commitMessage.model` | `"claude-haiku-4-0"` | AI model for commit message generation |
@@ -62,6 +66,9 @@ Add a `vcs` block to your config:
62
66
  | `vcs.retention.maxVersions` | `100` | Maximum commits retained per root (older ones squashed) |
63
67
  | `vcs.retention.squashCron` | `"0 0 * * *"` | Cron schedule for squash retention (5-field, checked every 60s) |
64
68
  | `vcs.defaultAccessToken` | — | Fallback git access token for all roots. Supports env var substitution |
69
+ | `vcs.staleLockThresholdMs` | `60000` | Age (ms) after which a git `index.lock` is considered stale and removed. Min: 5000 |
70
+ | `vcs.maxConsecutiveFailures` | `5` | Commit circuit breaker: trips after this many consecutive commit failures. Min: 1 |
71
+ | `vcs.circuitBreakerCooldownMs` | `300000` | Cooldown (ms) before a tripped breaker allows one recovery attempt; pending files are kept. Min: 1000 |
65
72
 
66
73
  ### Per-Root Overrides via `watch.paths`
67
74
 
@@ -71,15 +78,15 @@ Watch path entries can be objects with per-root VCS overrides:
71
78
  {
72
79
  "watch": {
73
80
  "paths": [
74
- "J:/domains/notes/**/*.md",
81
+ "/data/notes/**/*.md",
75
82
  {
76
- "path": "J:/domains/jira/**/*.json",
83
+ "path": "/data/tickets/**/*.json",
77
84
  "vcs": {
78
85
  "enabled": false
79
86
  }
80
87
  },
81
88
  {
82
- "path": "J:/domains/email/**/*.json",
89
+ "path": "/data/email/**/*.json",
83
90
  "vcs": {
84
91
  "remote": "https://github.com/org/email-archive.git",
85
92
  "accessToken": "${GITHUB_TOKEN}",
@@ -99,7 +106,7 @@ Per-root properties (`remote`, `accessToken`) are only available in per-root ove
99
106
  ### Deployment Notes
100
107
 
101
108
  - **Git dependency:** `git` must be on the system PATH. The watcher initializes a git repository in each VCS-enabled watch root automatically.
102
- - **stateDir:** The `.jeeves-metadata/` directory (configurable via `stateDir`) is always gitignored. VCS state (git repos) lives inside the watch roots themselves, not in stateDir.
109
+ - **stateDir:** With VCS enabled, `stateDir` (default `.jeeves-metadata`) must not overlap any watch root (equal, parent or child): startup fails otherwise. The `.gitignore` the watcher maintains in each VCS root always lists `.git/`, `node_modules/`, `.jeeves-watcher/` and `.jeeves-metadata/`. VCS state (git repos) lives inside the watch roots themselves, not in stateDir.
103
110
  - **Filesystem constraints:** Each VCS-enabled watch path entry must resolve to a single directory root (not a glob with wildcards in directory segments).
104
111
 
105
112
  ### Remote Push
@@ -115,7 +122,7 @@ When `remote` is set on a per-root VCS config, the watcher pushes to the remote
115
122
  "watch": {
116
123
  "paths": [
117
124
  {
118
- "path": "J:/domains/notes",
125
+ "path": "/data/notes",
119
126
  "vcs": {
120
127
  "remote": "https://github.com/org/notes-archive.git"
121
128
  }
@@ -134,18 +141,19 @@ To prevent unbounded history growth, the squash retention system periodically co
134
141
  - **`maxAgeDays`** and **`maxVersions`** define retention boundaries. The tighter constraint wins — if `maxAgeDays: 30` would keep 200 commits but `maxVersions: 100` caps at 100, only 100 are retained.
135
142
  - **`squashCron`** controls when squash runs (e.g., `"0 0 * * *"` = daily at midnight). Checked every 60 seconds.
136
143
  - After squash, old commits are replaced with a single "historical baseline" commit. If a remote is configured, squash triggers a force push.
144
+ - Squash rewrites history with git plumbing only: it never touches the working tree or the index, and moves the branch with a compare-and-swap, so a concurrent commit makes it stop without changing anything.
137
145
 
138
146
  ### API Endpoints
139
147
 
140
- | Endpoint | Method | Description |
141
- | ---------------------- | ------ | --------------------------------- |
142
- | `/vcs/status` | GET | VCS state for all roots |
143
- | `/vcs/history` | GET | Commit history for a path/glob |
144
- | `/vcs/show` | GET | File content at a specific commit |
145
- | `/vcs/diff` | GET | Diff between commits |
146
- | `/vcs/revert` | POST | Restore files from a past commit |
147
- | `/vcs/exclude` | POST | Manage gitignore exclusions |
148
- | `/vcs/check-exclusion` | GET | Check gitignore status of a path |
148
+ | Endpoint | Method | Description |
149
+ | --- | --- | --- |
150
+ | `/vcs/status` | GET | VCS state for all roots |
151
+ | `/vcs/history` | GET | Commit history for a path/glob |
152
+ | `/vcs/show` | GET | File content at a specific commit |
153
+ | `/vcs/diff` | GET | Diff between commits |
154
+ | `/vcs/revert` | POST | Restore files from a past commit |
155
+ | `/vcs/exclude` | POST | VCS-only exclusion (`.git/info/exclude`), untracking matches |
156
+ | `/vcs/check-exclusion` | GET | Whether git ignores a path: rule, file, line |
149
157
 
150
158
  ## JsonMap Built-in Helpers
151
159
 
@@ -165,11 +173,11 @@ The following helpers are available in every JsonMap `lib` context:
165
173
 
166
174
  ### `fetchSiblings`
167
175
 
168
- Retrieves extracted text from sibling files in the same directory, useful for contextual embedding (e.g., injecting surrounding email thread messages).
176
+ Retrieves text from sibling files (same directory, same extension) around the current file, useful for contextual embedding (e.g., injecting surrounding email thread messages). JSON siblings use the JSON text derivation; other files are read raw.
169
177
 
170
178
  **Options:** `{ before?: number (default 3), after?: number (default 1), sort?: "name" | "mtime" (default "name") }`
171
179
 
172
- Returns `string[]` of extracted text. Files that fail extraction are silently skipped.
180
+ Returns `string[]` of sibling text. Files that cannot be read are silently skipped. For a source document there is no file to read around, so `fetchSiblings` returns `[]`.
173
181
 
174
182
  ## Install
175
183
 
@@ -180,14 +188,14 @@ npm install @karmaniverous/jeeves-watcher
180
188
  ## Quick Start
181
189
 
182
190
  ```bash
183
- # Generate a config file
184
- npx jeeves-watcher init --output ./jeeves-watcher.config.json
191
+ # Generate ./config/config.json (--output is a directory)
192
+ npx jeeves-watcher init --output ./config
185
193
 
186
194
  # Validate it
187
- npx jeeves-watcher validate --config ./jeeves-watcher.config.json
195
+ npx jeeves-watcher config validate --config ./config/config.json
188
196
 
189
197
  # Start the watcher
190
- npx jeeves-watcher start --config ./jeeves-watcher.config.json
198
+ npx jeeves-watcher start --config ./config/config.json
191
199
  ```
192
200
 
193
201
  ## Documentation
@@ -196,6 +204,8 @@ Full docs, guides, and API reference:
196
204
 
197
205
  **[docs.karmanivero.us/jeeves-watcher](https://docs.karmanivero.us/jeeves-watcher)**
198
206
 
207
+ Upgrading an existing deployment? See [Upgrading](guides/upgrading.md).
208
+
199
209
  ## License
200
210
 
201
211
  BSD-3-Clause