@ansonlai/docx-redline-js 0.6.2 → 0.7.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/AGENTS.md +30 -9
- package/CHANGELOG.md +58 -0
- package/README.md +48 -6
- package/dist/docx-redline-js.esm.js +3 -4
- package/dist/docx-redline-js.esm.js.map +2 -2
- package/dist/docx-redline-js.esm.min.js +51 -51
- package/dist/docx-redline-js.esm.min.js.map +2 -2
- package/docs/AGENT_FAST_START.md +23 -24
- package/docs/AGENT_KNOWLEDGE_BASE.md +36 -14
- package/docs/SKILL_AUTHORING.md +56 -19
- package/docs/releases/0.7.0.md +219 -0
- package/docs/schemas/document-operations.schema.json +14 -1
- package/docs/validation-reports/2026-09-14-localized-patching-rollout.md +90 -0
- package/index.d.ts +2 -0
- package/node/cli-help.js +26 -6
- package/node/cli.js +300 -35
- package/package.json +5 -1
- package/services/batch-operation-orchestrator.js +25 -16
- package/services/document-inspection.js +2 -3
- package/services/document-operation-applier.js +78 -9
- package/services/document-operation-contract.js +105 -7
- package/services/document-operation-mutations.js +36 -36
- package/services/localized-replacement-compiler.js +304 -0
- package/services/operation-batch-compiler.js +42 -1
- package/services/operation-preflight.js +10 -6
- package/services/standalone-operation-runner.d.ts +79 -7
package/AGENTS.md
CHANGED
|
@@ -21,16 +21,31 @@ specific advanced operation, API, or recovery topic you need.
|
|
|
21
21
|
|
|
22
22
|
## Ordinary document edits
|
|
23
23
|
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
24
|
+
For a literal mechanical edit with known old and new text, try one fail-closed
|
|
25
|
+
apply call. When global matching is too broad, use a longer, fairly unique
|
|
26
|
+
nearby phrase plus a directional range:
|
|
27
|
+
|
|
28
|
+
```bash
|
|
29
|
+
docx-redline apply contract.docx --search "distinctive nearby heading or phrase" --context-range 1:3 --find "thirty (30) days" --replace "sixty (60) days" --profile agent --output reviewed.docx
|
|
30
|
+
```
|
|
31
|
+
|
|
32
|
+
Generic or repeated anchors widen the unioned scope and may return
|
|
33
|
+
`AMBIGUOUS_TARGET`, costing a recovery turn. On success, treat
|
|
34
|
+
`results[i].change.context.anchorMatchCount > 1` as a signal to confirm the
|
|
35
|
+
returned location and excerpts.
|
|
36
|
+
|
|
37
|
+
For semantic drafting, inspect once and apply once. With a structured wrapper,
|
|
38
|
+
use revision-bound handles. For shell-only work, use serializer-backed stdin:
|
|
28
39
|
|
|
29
40
|
```bash
|
|
30
41
|
docx-redline extract contract.docx --search "termination" --around 3
|
|
31
42
|
node emit-operations.mjs | docx-redline apply contract.docx --operations - --profile agent --compact --output reviewed.docx
|
|
32
43
|
```
|
|
33
44
|
|
|
45
|
+
A single deleted paragraph found in rejected view can be restored verbatim with
|
|
46
|
+
`apply --restore --target-id ID`; add one `--find`/`--replace` pair for a small
|
|
47
|
+
exact correction. This shortcut does not infer ranges or companion paragraphs.
|
|
48
|
+
|
|
34
49
|
For every ordinary text operation, `modified` is the complete desired
|
|
35
50
|
accepted-view content. Copy inspected `exactText` verbatim and include
|
|
36
51
|
`paragraphId` or `fingerprint`. Independent strong targets are bound against the
|
|
@@ -39,10 +54,13 @@ Consolidate incompatible writes to the same source; use captures for intentional
|
|
|
39
54
|
created-content dependencies.
|
|
40
55
|
|
|
41
56
|
Require `completion: true`, `written: true`, a non-null output path, and no
|
|
42
|
-
per-operation errors.
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
57
|
+
per-operation errors. Localized edits also require
|
|
58
|
+
`results[i].change.committed: true`, `finalDisposition: "applied"`, and
|
|
59
|
+
`verification.acceptedViewMatchesCompiledText: true`. Follow
|
|
60
|
+
`error.recovery.action` and `retryPlan`; never retry unchanged failed arguments.
|
|
61
|
+
Follow `selection.hint` for restorable text. Do not accept/reject another
|
|
62
|
+
reviewer's work or remove comments without explicit user authorization. The
|
|
63
|
+
source is never overwritten unless `--in-place` is explicit.
|
|
46
64
|
|
|
47
65
|
The agent profile preserves progressive execution and the ordinary revision
|
|
48
66
|
policy. Add `--atomic` or `--existing-revisions slice-cross-author` only when
|
|
@@ -64,7 +82,10 @@ targeting, revision allocation, comments, numbering, validation, or rollback.
|
|
|
64
82
|
The stateful wrapper in `examples/agent-session-wrapper.mjs` is a testable
|
|
65
83
|
development demonstration only. It is excluded from package files and exports.
|
|
66
84
|
Production harnesses own their transport and negotiate the minimum CLI
|
|
67
|
-
`contractVersion`/capabilities they use.
|
|
85
|
+
`contractVersion`/capabilities they use. The 0.7.0 localized fast path requires
|
|
86
|
+
contract 8 and its localized replacement, speculative apply, and change-summary
|
|
87
|
+
capabilities; the narrow restore shortcut additionally requires
|
|
88
|
+
`restore-shortcuts-v1`.
|
|
68
89
|
|
|
69
90
|
## Code map
|
|
70
91
|
|
package/CHANGELOG.md
CHANGED
|
@@ -2,6 +2,64 @@
|
|
|
2
2
|
|
|
3
3
|
## Unreleased
|
|
4
4
|
|
|
5
|
+
- Added a narrow single-paragraph restore shortcut. A restore with a strong
|
|
6
|
+
rejected-view target may omit `modified` for verbatim restoration or provide
|
|
7
|
+
exact `replacements`; the CLI exposes the same path through `apply --restore
|
|
8
|
+
--target-id ID`. Ranges, captures, weak targets, and inferred companion
|
|
9
|
+
content remain excluded.
|
|
10
|
+
|
|
11
|
+
- Fixed rejected-view restore receipts so `resolvedTarget` text, fingerprint,
|
|
12
|
+
revision view, and match diagnostics describe the view actually used to
|
|
13
|
+
resolve the target.
|
|
14
|
+
- Fixed alternate-view search hints to honor `--revised`, `--table`, and
|
|
15
|
+
`--body`, and retained compact revision authors plus `deleted`/`inserted` cues
|
|
16
|
+
in `extract` output so empty revision-view paragraphs are self-explanatory.
|
|
17
|
+
|
|
18
|
+
## 0.7.0
|
|
19
|
+
|
|
20
|
+
### Agent Performance and Localized Editing
|
|
21
|
+
|
|
22
|
+
- **Localized exact replacements:** `redline`/`replace` operations may provide
|
|
23
|
+
`replacements: [{ find, replace, occurrence? }]` instead of a complete
|
|
24
|
+
`modified` paragraph. The compiler resolves the accepted-view source once,
|
|
25
|
+
applies non-overlapping exact replacements simultaneously, synthesizes the
|
|
26
|
+
canonical desired paragraph, and delegates to the unchanged OOXML engine.
|
|
27
|
+
- **One-turn speculative apply:** `docx-redline apply --find ... --replace ...`
|
|
28
|
+
can resolve a globally unique source literal without preliminary extraction.
|
|
29
|
+
`--search` plus signed `--context-range START:END` scopes visible headings and
|
|
30
|
+
nearby content; `--around N` is symmetric shorthand. Longer, distinctive
|
|
31
|
+
anchors are recommended because generic or repeated phrases widen the unioned
|
|
32
|
+
scope and may cost an ambiguity-recovery turn.
|
|
33
|
+
- **Fail-closed selection:** Missing anchors and patch sources, multiple eligible
|
|
34
|
+
paragraphs, ambiguous occurrences, overlaps, conflicts, and unsupported
|
|
35
|
+
localized shapes refuse mutation. A failed speculative command never writes
|
|
36
|
+
or truncates its output path.
|
|
37
|
+
- **Verified change evidence:** Localized operation results include a compact
|
|
38
|
+
`change` object with target location, contextual anchor/range, exact
|
|
39
|
+
replacement entries, bounded before/after excerpts, commit disposition, and
|
|
40
|
+
post-mutation accepted-view verification. Atomic rollback marks the evidence
|
|
41
|
+
non-committed and `rolled_back`.
|
|
42
|
+
- **CLI contract version 8:** Adds `localized-replacements-v1`,
|
|
43
|
+
`speculative-search-apply-v1`, and `localized-change-summary-v1`. Skills and
|
|
44
|
+
harnesses should pin version 0.7.0 and negotiate only the capabilities used.
|
|
45
|
+
- **Measured workflow reduction:** The checked benchmark records 50% fewer tool
|
|
46
|
+
turns and a 64.77%–78.98% smaller deterministic request-token proxy across
|
|
47
|
+
three literal-edit cases. Median native engine/I/O time remained effectively
|
|
48
|
+
neutral; provider reasoning and network latency were not estimated.
|
|
49
|
+
|
|
50
|
+
### Compatibility
|
|
51
|
+
|
|
52
|
+
- Existing `modified` operations, strong targets, operations files/stdin,
|
|
53
|
+
tracked-change generation, package validation, rollback, comments,
|
|
54
|
+
Accept/Reject, and revision policies remain supported.
|
|
55
|
+
- Localized replacement fields and successful `change` evidence are additive.
|
|
56
|
+
Wrappers that adopt them must require CLI contract 8; integrations using only
|
|
57
|
+
earlier capabilities can continue using their existing operation shapes.
|
|
58
|
+
- The implementation remains OOXML-only and adds no runtime dependency or Word,
|
|
59
|
+
Office automation, COM, or proprietary document API requirement.
|
|
60
|
+
|
|
61
|
+
## 0.6.0–0.6.2
|
|
62
|
+
|
|
5
63
|
### Safety Fixes
|
|
6
64
|
|
|
7
65
|
- **Foreign deleted-paragraph resurrection guard**: Refuses non-empty same-paragraph edits when another author owns the paragraph-mark deletion and all existing paragraph content is deleted. The operation now returns `FOREIGN_PARAGRAPH_MARK_DELETION` with the owning author instead of emitting lifecycle-unsafe OOXML; atomic document operations roll back byte-for-byte. `validateRedlineOoxml` reports already-authored instances as warnings.
|
package/README.md
CHANGED
|
@@ -15,9 +15,26 @@ Converts AI-generated or programmatic text/markdown edits into valid Office Open
|
|
|
15
15
|
- Comment management: delete comments by author or for all authors
|
|
16
16
|
- Highlights: apply highlight colors to runs
|
|
17
17
|
- Markdown and OOXML conversion in both directions
|
|
18
|
-
- Status/error result fields for parse, targeting, and existing-revision failures
|
|
19
|
-
-
|
|
20
|
-
-
|
|
18
|
+
- Status/error result fields for parse, targeting, and existing-revision failures
|
|
19
|
+
- Localized exact replacements and fail-closed one-turn CLI edits with verified before/after evidence
|
|
20
|
+
- Package plumbing helpers for numbering.xml, comments.xml, content types, and relationships
|
|
21
|
+
- Zero host dependencies: works in Node.js, browsers, Deno, and similar JS runtimes with DOM parsing support
|
|
22
|
+
|
|
23
|
+
## What's New in 0.7.0
|
|
24
|
+
|
|
25
|
+
Version 0.7.0 adds a contract-8 fast path for exact mechanical edits. Agents can
|
|
26
|
+
send a small `find`/`replace` request instead of reproducing a complete legal
|
|
27
|
+
paragraph, and may omit a strong target when the source literal resolves to one
|
|
28
|
+
accepted-view paragraph. A longer, fairly unique nearby phrase can narrow the
|
|
29
|
+
attempt with a signed directional window. Generic or repeated anchors widen the
|
|
30
|
+
unioned scope and may cause a safe ambiguity failure and another tool turn.
|
|
31
|
+
|
|
32
|
+
Speculative edits fail without writing when the anchor, paragraph, or source
|
|
33
|
+
span is missing or ambiguous. Successful localized results include a committed
|
|
34
|
+
`change` object with the selected legal location, bounded before/after excerpts,
|
|
35
|
+
and actual accepted-view verification. Existing full-paragraph operations,
|
|
36
|
+
tracked-change semantics, validation, rollback, and review policies remain
|
|
37
|
+
available unchanged. See the [complete 0.7.0 release notes](./docs/releases/0.7.0.md).
|
|
21
38
|
## Documentation Index
|
|
22
39
|
|
|
23
40
|
| Document | Description |
|
|
@@ -151,6 +168,13 @@ limit output. Search is a case-insensitive substring match; `around` adds nearby
|
|
|
151
168
|
context, while `limit` and `after` page direct hits. When a search yields 0
|
|
152
169
|
matches in the active view, `selection.hint` provides guidance if matches exist
|
|
153
170
|
in the alternate revision view (such as searching for deleted text to restore).
|
|
171
|
+
Compact `extract --revised` output retains revision authors and marks paragraphs
|
|
172
|
+
whose content is wholly hidden in the selected view as `deleted` or `inserted`.
|
|
173
|
+
One such paragraph can be restored without restating it:
|
|
174
|
+
`docx-redline apply input.docx --restore --target-id ID --output reviewed.docx`.
|
|
175
|
+
Add one exact `--find`/`--replace` pair to make a localized correction while
|
|
176
|
+
restoring. The shortcut requires a strong rejected-view paragraph ID and does
|
|
177
|
+
not infer a range or adjacent content.
|
|
154
178
|
`revisionView` accepts `accepted`, `rejected`, or `current`. Returned
|
|
155
179
|
paragraphs identify matches versus context and include `humanReference` for
|
|
156
180
|
user-facing summaries.
|
|
@@ -215,9 +239,23 @@ benchmark explicitly does not claim to measure LLM reasoning or provider/tool
|
|
|
215
239
|
latency. Checked comparative results are in the
|
|
216
240
|
[agent protocol rollout audit](./docs/validation-reports/2026-09-12-agent-protocol-rollout.md).
|
|
217
241
|
|
|
242
|
+
> **Pre-1.0 integration warning:** Agent skills, MCP servers, and harnesses
|
|
243
|
+
> should pin the exact `@ansonlai/docx-redline-js` release they were tested
|
|
244
|
+
> against and declare the CLI contract version/capabilities they require. Do
|
|
245
|
+
> not treat a newly installed release or contract as verified until the
|
|
246
|
+
> integration's compatibility tests pass. See the
|
|
247
|
+
> [skill-authoring contract](./docs/SKILL_AUTHORING.md#runtime-negotiation).
|
|
248
|
+
|
|
218
249
|
### Agent CLI
|
|
219
|
-
|
|
250
|
+
|
|
220
251
|
```bash
|
|
252
|
+
# One-turn exact mechanical edit; fails closed unless one paragraph matches
|
|
253
|
+
docx-redline apply contract.docx --find "thirty (30) days" --replace "sixty (60) days" --profile agent --output reviewed.docx
|
|
254
|
+
|
|
255
|
+
# Directional context using a longer phrase with a higher chance of uniqueness
|
|
256
|
+
docx-redline apply contract.docx --search "distinctive nearby heading or phrase" --context-range 1:3 --find "thirty (30) days" --replace "sixty (60) days" --profile agent --output reviewed.docx
|
|
257
|
+
|
|
258
|
+
# Semantic drafting still starts with focused context
|
|
221
259
|
docx-redline extract contract.docx --search "termination" --around 3
|
|
222
260
|
docx-redline preflight contract.docx --operations operations.json --author "Editor"
|
|
223
261
|
docx-redline apply contract.docx --operations operations.json --author "Editor" --output reviewed.docx
|
|
@@ -252,6 +290,7 @@ All commands emit JSON on stdout. `apply` defaults:
|
|
|
252
290
|
- **Compact stdout**: `--compact` emits one-line mutation JSON. It changes serialization only, not operation semantics.
|
|
253
291
|
- **Tracked changes**: Defaults to `generateRedlines: true`. Pass `--no-redlines` when clean direct text edits are desired.
|
|
254
292
|
- **Inline edits**: Use `--target <text>` with `--modified <text>` or `--comment <text>` for quick one-liners without creating a JSON file.
|
|
293
|
+
- **Localized edits**: Use `--find`/`--replace` with a known strong target, or omit the target for fail-closed global resolution. Add a longer, fairly unique `--search` phrase with `--context-range 1:3` for directional scope; `--around 3` is symmetric. Generic or repeated anchors can widen the unioned scope until multiple paragraphs contain `find`, producing a safe `AMBIGUOUS_TARGET` failure and an extra recovery turn. On success, `results[i].change.context.anchorMatchCount > 1` signals a non-unique anchor; confirm the returned location and bounded before/after evidence.
|
|
255
294
|
- **Compact mutation results**: `apply`, `accept`, `reject`, and `delete-comments` omit full OOXML/package payloads and inspection text from stdout. CLI operation results omit duplicate nested receipt bodies; the ordered top-level `receipts` array is authoritative. Successful exact target-match diagnostics are omitted and equivalent-whitespace matches retain only mode/count. Node and standalone-runner results remain unchanged. Use `validate` when full issue arrays are needed.
|
|
256
295
|
|
|
257
296
|
Inspection commands default to 20 direct matches and a 48 KiB soft response
|
|
@@ -266,12 +305,15 @@ marker. Machine `index` and `ref` fields are for targeting and pagination, not
|
|
|
266
305
|
user-facing Word locations; use `humanReference`, `provision`, or
|
|
267
306
|
`nearestHeading` in reports.
|
|
268
307
|
|
|
269
|
-
`docx-redline version` reports contract version
|
|
308
|
+
`docx-redline version` reports contract version 8 and the additive
|
|
270
309
|
`command-help-v1`, `inspection-context-v1`, `bounded-inspection-v1`,
|
|
271
310
|
`human-document-references-v1`, `batch-start-source-binding`,
|
|
272
311
|
`recovery-envelope-v1`, `require-complete-exit`, `operations-stdin`,
|
|
273
312
|
`agent-safety-profile-v2`, `deduplicated-cli-receipts`, and
|
|
274
|
-
`compact-cli-json-v1`
|
|
313
|
+
`compact-cli-json-v1`, `localized-replacements-v1`,
|
|
314
|
+
`speculative-search-apply-v1`, `localized-change-summary-v1`, and
|
|
315
|
+
`restore-shortcuts-v1` capabilities.
|
|
316
|
+
Wrappers should negotiate only the
|
|
275
317
|
capabilities they use. Run `docx-redline <command> --help` for that command's
|
|
276
318
|
machine-readable options, behavior, exit codes, canonical GitHub documentation links, and compact examples.
|
|
277
319
|
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
// @ansonlai/docx-redline-js v0.
|
|
1
|
+
// @ansonlai/docx-redline-js v0.7.1 — https://github.com/AnsonLai/docx-redline-js
|
|
2
2
|
var __create = Object.create;
|
|
3
3
|
var __defProp = Object.defineProperty;
|
|
4
4
|
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
@@ -11609,9 +11609,8 @@ function inspectDocumentParts(parts, options = {}) {
|
|
|
11609
11609
|
if (options.range && (index < rangeStart || index > rangeEnd)) continue;
|
|
11610
11610
|
if (Array.isArray(options.indexes) && !options.indexes.includes(index)) continue;
|
|
11611
11611
|
const pNode = paragraphNodes[i];
|
|
11612
|
-
if (options.
|
|
11613
|
-
if (options.
|
|
11614
|
-
if (options.revised && revisionAuthors(pNode).length === 0) continue;
|
|
11612
|
+
if (options.inTable != null && hasAncestor(pNode, "tc") !== !!options.inTable) continue;
|
|
11613
|
+
if (options.revisedOnly && revisionAuthors(pNode).length === 0) continue;
|
|
11615
11614
|
const altText = extractCanonicalParagraphText(pNode, { revisionView: alternateView });
|
|
11616
11615
|
if (options.skipEmpty && altText.length === 0) continue;
|
|
11617
11616
|
if (altText.toLowerCase().includes(needle)) {
|