Skip to content

feat: dxedit — declarative docx edit CLI + library (manifest-driven, ooxml-swift direct, peer to che-word-mcp MCP front-end) #92

@kiki830621

Description

@kiki830621

Problem

che-word-mcp exposes ~218 OOXML editing tools over MCP stdio JSON-RPC. Two real-world workflows have hit the limits of going through the MCP transport:

  1. Replicable docx-edit pipelines — running the same edit plan against different docx baselines (e.g. template-population, content backfill, batch caption fix-ups) currently means either:
    • Manually re-driving 30+ MCP calls per run (lossy, error-prone), or
    • Writing one-off Python/Bash scripts that wrap MCP stdio (fragile, JSON-escape pain especially for CJK anchor text).
  2. che-word-mcp integration testingRealWorldDocxRoundTripSmokeTests covers open → save round-trip but not edit-path tests with non-trivial sequences (insert+replace+insert with anchors). A scriptable surface that drives the same ooxml-swift API che-word-mcp uses would let us assert end-to-end behaviour declaratively.

Both share the same need: a declarative way to describe a docx edit plan and execute it against ooxml-swift directly (no MCP transport overhead, no JSON escaping). MCP and this CLI become two front-ends on the same library.

Type

feature

Proposal

A new CLI + library inside macdoc/, sibling to mcp/che-word-mcp/:

macdoc/
├── mcp/che-word-mcp/         # existing (MCP front-end)
└── cli/dxedit/               # NEW
    ├── Package.swift         # depends on ooxml-swift (same dep as che-word-mcp)
    ├── Sources/
    │   ├── DxEditLib/        # library target — importable
    │   │   ├── Manifest.swift   # YAML/JSON decoding
    │   │   ├── Step.swift       # InsertImage / ReplaceText / InsertParagraph / InsertEquation / Verify
    │   │   ├── Executor.swift   # plan → execute → verify
    │   │   └── Verify.swift     # part-count, libxml2 validity, bookmark, font preservation checks
    │   └── dxedit/           # executable target — `dxedit` binary
    │       └── main.swift    # ArgumentParser → DxEditLib calls
    └── Tests/DxEditLibTests/

CLI surface

dxedit apply manifest.yaml --in baseline.docx --out output.docx
dxedit plan  manifest.yaml --in baseline.docx          # dry-run
dxedit verify --in baseline.docx --out output.docx     # post-condition assertions
dxedit diff a.docx b.docx                              # uses ooxml-swift compare API

Manifest sketch

baseline: archived/baseline.docx
output: docs/output.docx
steps:
  - insert_image:
      path: assets/figure_1.png
      anchor: { before_text: "<unique caption substring>" }
      width: 520
      name: fig_1
  - replace_text_batch:
      - { find: "<old>", replace: "<new>" }
  - insert_paragraph:
      anchor: { after_text: "<unique sentence>" }
      text: "<paragraph body>"
verify:
  expected_images: 23
  expected_bookmarks_min: 44
  libxml2_valid: true
  byte_preserved_parts:
    - word/header*.xml
    - word/footer*.xml
    - word/fontTable.xml
    - word/theme/*.xml

Why this lives in macdoc/ rather than a separate repo

  • Same SPM dep graph as che-word-mcp (both depend on ooxml-swift)
  • CLI changes often co-evolve with ooxml-swift API changes — atomic commits possible
  • che-word-mcp integration tests can shell out to dxedit for declarative E2E coverage
  • Workspace-style monorepo already established (macdoc/mcp/, macdoc/lib/, etc.)

A separate repo can be extracted later if the CLI grows beyond docx (e.g. unified dxedit / pxedit / pptedit toolkit), following the same pattern as #78 (NoteCore extraction) and #79 (pdf-to-latex-swift extraction).

Use cases

  1. Template population — given a docx template with anchor markers, populate with structured content from a manifest.
  2. Batch fix-up — apply caption format normalization across many docx files.
  3. Reproducible workflows — a docx-edit pipeline checked into a project repo (scripts/edit/manifest.yaml + dxedit apply) is replayable and version-controlled.
  4. che-word-mcp integration tests — declarative assertions about edit-path behaviour that supplement the existing round-trip XCTest suite.

Implementation phases

  • Phase 1: minimal apply command, supports insert_image, replace_text, replace_text_batch, insert_paragraph steps. YAML manifest. SPM library target.
  • Phase 2: verify command with post-condition harness (libxml2 validity, byte-preservation checks, content presence).
  • Phase 3: plan (dry-run), diff (using ooxml-swift compare), archive-first integration (auto-snapshot baseline before mutating writes).
  • Phase 4: extend step types as ooxml-swift API matures — insert_equation, wrap_caption_seq (depends on P2: helper to wrap plain-text captions in SEQ field for downstream TOF/TOT generation che-word-mcp#62), section/header/footer manipulation.

Caveats

Priority

P2 — useful for downstream replicable workflows; not blocking any current work.

Related


Current Status

Phase: diagnosed / Spectra proposal ready
Last updated: 2026-05-02 by Codex

Key Decisions

Spectra Proposal

  • Change: macdoc-docx-workflow-cli
  • PR: Propose macdoc docx workflow CLI #94
  • Files: openspec/changes/macdoc-docx-workflow-cli/proposal.md, design.md, tasks.md, and specs/docx-workflow-cli/spec.md
  • Validation passed: spectra analyze macdoc-docx-workflow-cli --json, spectra validate macdoc-docx-workflow-cli, and git diff --check -- openspec/changes/macdoc-docx-workflow-cli

Blocking

Commits

  • 08d55b0 docs: propose macdoc docx workflow spec

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions