docx-footnotes
Use when DOCX footnotes are broken after Google Docs or Word Online round-trips, when converting hardcoded 'supra note N' cross-references to auto-updating NOTEREF fields, or for any OOXML-level footnote surgery on a Word document — even if the user doesn't say 'OOXML' but describes footnote formatting problems in a .docx edited in a cloud editor.
Best use case
docx-footnotes is best used when you need a repeatable AI agent workflow instead of a one-off prompt.
Use when DOCX footnotes are broken after Google Docs or Word Online round-trips, when converting hardcoded 'supra note N' cross-references to auto-updating NOTEREF fields, or for any OOXML-level footnote surgery on a Word document — even if the user doesn't say 'OOXML' but describes footnote formatting problems in a .docx edited in a cloud editor.
Teams using docx-footnotes should expect a more consistent output, faster repeated execution, less prompt rewriting.
When to use this skill
- You want a reusable workflow that can be run more than once with consistent structure.
When not to use this skill
- You only need a quick one-off answer and do not need a reusable workflow.
- You cannot install or maintain the underlying files, dependencies, or repository context.
Installation
Claude Code / Cursor / Codex
Manual Installation
- Download SKILL.md from GitHub
- Place it in
.claude/skills/docx-footnotes/SKILL.mdinside your project - Restart your AI agent — it will auto-discover the skill
How docx-footnotes Compares
| Feature / Agent | docx-footnotes | Standard Approach |
|---|---|---|
| Platform Support | Not specified | Limited / Varies |
| Context Awareness | High | Baseline |
| Installation Complexity | Unknown | N/A |
Frequently Asked Questions
What does this skill do?
Use when DOCX footnotes are broken after Google Docs or Word Online round-trips, when converting hardcoded 'supra note N' cross-references to auto-updating NOTEREF fields, or for any OOXML-level footnote surgery on a Word document — even if the user doesn't say 'OOXML' but describes footnote formatting problems in a .docx edited in a cloud editor.
Where can I find the source code?
You can find the source code on GitHub using the link provided at the top of the page.
SKILL.md Source
# DOCX Footnote Repair & Cross-References Fix footnote formatting damage caused by Google Docs and Word Online, and convert hardcoded supra note references to NOTEREF field codes. ## When This Applies Common symptoms in `.docx` files round-tripped through Google Docs or Word Online: - Missing footnote separator lines - Stripped paragraph styles (pStyle) on footnote bodies - Stripped style *definitions* (`FNStyleBest` etc.) — the pStyle reference points at an undefined style and Word silently falls back to Normal - Author bio custom marks (`*`, `†`, `‡`) replaced with numbers - Footnote numbering starting at the wrong number (offset from `customMarkFollows` bio footnotes) - TOC separator paragraphs that inflate to fill a whole page - Hardcoded "supra note N" / "infra note N" references that need to become auto-updating NOTEREF fields ## Quick Start Scripts are in this skill's `scripts/` directory. Use `$SKILL_DIR` below as a placeholder for the absolute path to this skill (the directory containing this SKILL.md). ```bash # Fix all cloud editor damage + convert cross-references uv run --with lxml python3 \ "$SKILL_DIR/scripts/fix_footnotes.py" path/to/file.docx --crossrefs # Dry run (show what would change) uv run --with lxml python3 \ "$SKILL_DIR/scripts/fix_footnotes.py" path/to/file.docx --dry-run # Cross-references only uv run --with lxml python3 \ "$SKILL_DIR/scripts/create_crossrefs.py" --docx path/to/file.docx # Refresh stale NOTEREF cross-ref numbers after a coauthor inserted/moved # footnotes in Word (render-based, ground-truth; needs x2t or LibreOffice) "$SKILL_DIR/scripts/refresh_noteref_caches.py" path/to/file.docx --verify ``` **Which script do I want?** - Footnotes look broken after a **Google Docs / Word Online** round-trip (missing separators, wrong styles, mark/number mix-ups) → **`fix_footnotes.py`**. - The doc still has **hardcoded** "supra note 42" **text** that should become auto-updating fields → **`create_crossrefs.py`**. - The doc **already uses NOTEREF fields** but a coauthor **inserted/moved/deleted footnotes in Word** and the cross-reference **numbers are now wrong** → **`refresh_noteref_caches.py`** (this is the common "Nadya emailed back tracked edits and the numbering is off" case). ## Scripts ### fix_footnotes.py Detects and repairs OOXML footnote damage. Handles multiple sources. Idempotent. **Google Docs / Word Online round-trip damage:** - Missing separator/continuation footnotes (id=-1, 0) - Custom mark restoration for author bio footnotes (*, dagger, double-dagger) - Footnote ID renumbering (shifted by missing system footnotes) - Missing paragraph styles (adds configurable pStyle to all footnotes) - Wrong paragraph styles — reassigns `pStyle="FootnoteText"` (the Google Docs default) to `FNStyleBest` on every footnote paragraph so the whole doc uses the canonical law-review style. - Missing style *definitions* — restores `FNStyleBest` (and the basedOn/link styles it depends on) from the canonical law-review reference template when a round-trip stripped them from `styles.xml`. The template is the same `writing-legal/templates/law_review_template.docx` that `law-review-docx`'s `build_docx.py` feeds to pandoc, so style definitions stay consistent. - Mutated style *definitions* — when the `FNStyleBest` / `FNStyleBestChar` block survives the round-trip but picks up Google Docs hyperlink-renderer residue (link-blue underline color `<w:u w:color="0077CC"/>` or white paragraph shading), the whole block is replaced from the template. - TOC separator paragraph inflation (shrinks to near-zero height) **Pandoc-citeproc wrap parens:** - Strips the ` (...)` wrapper pandoc adds around mid-footnote bracketed citations while preserving author-written explanatory parentheticals (which lack the double-whitespace XML signature). **Flags:** - `--output` / `-o`: Output path (default: overwrite input) - `--dry-run`: Show what would change without modifying - `--bio-footnotes N`: Number of author bio footnotes (default: 3) - `--crossrefs`: Chain to create_crossrefs.py after fixing - `--fix-numbering`: Fix numbering offset from customMarkFollows bio footnotes (adds numRestart, updates NOTEREFs and supra references) - `--template PATH`: Reference template (.docx) to restore missing footnote style definitions from (default: bundled `writing-legal/templates/law_review_template.docx`) ### create_crossrefs.py Converts hardcoded "supra note N" references to NOTEREF field codes that auto-update. **What it does:** - Finds all `supra note <number>` patterns in document body and footnotes - Creates bookmark targets on referenced footnotes - Replaces hardcoded numbers with `NOTEREF _RefFN<id> \h` field codes - Preserves italic formatting on "supra" ### refresh_noteref_caches.py Refreshes the cached numbers on existing `NOTEREF` cross-reference fields after footnotes were inserted/moved/deleted in Word. Use when cross-references already ARE fields (not hardcoded text) but their numbers went stale. **Why the naive approaches fail (and this script's method):** - The offset is **not uniform** — `+N to everything` is wrong. - Computing numbering from `document.xml` order is wrong: the 3 `customMarkFollows` author-bio footnotes are **not** counted in the numeric sequence, and a tracked footnote **move** makes XML order diverge from rendered order. - LibreOffice's **inline cross-ref render lies** — it always recomputes NOTEREF on load and **excludes unaccepted tracked-inserted footnotes**, so it shows xrefs ~2 low even though it numbers the page-bottom markers correctly. So the script uses the **rendered page-bottom footnote markers as ground truth**: render → extract markers → fingerprint-match each footnote to its true marker (longest-common-prefix, one-to-one, most-distinctive first) → set every NOTEREF cache to its target's marker. It also repairs NOTEREF field codes left dangling by Word's **40-char bookmark-name truncation** (`_RefBib_...2024` → the real `_RefBib_...20`). It deliberately does **not** add `updateFields` (that re-triggers the buggy recompute). Verify with a **changes-accepted** render — once inserts are accepted every engine agrees and the inline xrefs render correctly. **Requires:** ONLYOFFICE `x2t` (preferred; `onlyoffice-x2t` nix package) or LibreOffice (`soffice`) as fallback, plus `pymupdf` (auto-installed via the inline script deps; run the file directly, e.g. `./refresh_noteref_caches.py file.docx`). **Flags:** - `-o` / `--output`: Output path (default: overwrite input) - `--dry-run`: Report the cache changes without writing - `--verify`: Also emit a changes-accepted `*_ACCEPTED_preview.pdf` proof - `--soffice PATH`: Path to the LibreOffice binary, used only when `x2t` is not on PATH (auto-discovered if omitted) **Scope (intentional):** refreshes numbers only. It does **not** do editorial retargeting (e.g. "this xref should point to notes 210–212 instead of its current target"). That is a human decision — move the bookmark / change the NOTEREF target first, then re-run this to refresh. ## Reference See [`footnotes-reference.md`](footnotes-reference.md) for detailed technical reference covering: 1. Run-level editing gotchas (NBSP, cross-run matching, xml:space) 2. Cloud editor damage patterns (what gets destroyed and why) 3. Direct ZIP surgery patterns (bypassing Document libraries) ### Footnote Numbering Offset Fix When author bio footnotes use `customMarkFollows` (*, †, ‡), they consume auto-numbers 1–3, causing body footnotes to start at 4. Fix by adding `numRestart=eachSect` to `settings.xml` and updating NOTEREF cached values. **Requires:** A section break between title page and body. Render PDF with **Word** or **x2t** (`scripts/x2t_convert.py` at plugin root) — both honor numRestart; **LibreOffice does not** (renders restart numbering wrong; verified 2026-06-10, x2t restarts at 1 per section where soffice numbers continuously). See [`footnotes-reference.md`](footnotes-reference.md) § 4 for details, code patterns, and the critical rule: numRestart goes in `settings.xml` ONLY (not in sectPr — causes all-zeros).
Related Skills
law-review-docx
Use this skill when the user asks to 'generate a docx', 'create the Word file', 'export to docx', 'apply the law review template', 'build the document', 'make a Word version', or wants to convert their law review markdown drafts into a formatted .docx file.
writing
This skill should be used when the user asks to 'write a paper', 'start a writing project', 'draft an article', 'write about', 'brainstorm writing topics', 'gather sources for a paper', 'what should I write about', or needs the writing workflow entry point for any writing task.
writing-validate
Validate draft sections cover all PRECIS claims before review.
writing-setup
Internal skill for creating PRECIS.md, OUTLINE.md, and ACTIVE_WORKFLOW.md. Called after brainstorm sources are gathered.
writing-revise
This skill should be used when the user asks to 'revise writing', 'fix review issues', 'polish draft', 'apply review feedback', 'complete writing workflow', or after /writing-review produces REVIEW.md with issues to fix.
writing-review
Internal skill for hierarchical document review. Called by writing-validate after claim validation passes.
writing-precis-reviewer
Internal skill used by writing-setup at exit gate. Dispatches a reviewer subagent to verify PRECIS.md quality before outlining. NOT user-facing.
writing-outline
Internal skill for creating detailed section outlines. Called by /writing workflow after PRECIS and master OUTLINE are complete.
writing-outline-reviewer
Internal skill used by writing-outline at exit gate. Dispatches a reviewer subagent to verify OUTLINE.md quality before drafting. NOT user-facing.
writing-lit-review
Internal skill for literature review and source materialization. Called after brainstorm, before setup. NOT user-facing.
writing-legal
Internal skill for academic legal writing. Loaded by /writing when style=legal. Based on Volokh's "Academic Legal Writing".
writing-handoff
Create structured handoff document for writing workflow session pause/resume.