docx-diff-editor 1.0.6 → 1.0.9

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/dist/index.js CHANGED
@@ -748,6 +748,8 @@ var DocxDiffEditor = react.forwardRef(
748
748
  rulers: showRulers,
749
749
  user: DEFAULT_SUPERDOC_USER,
750
750
  permissionResolver,
751
+ // Enable comments module for track changes sidebar
752
+ modules: { comments: {} },
751
753
  onReady: ({ superdoc: sd }) => {
752
754
  superdocRef.current = sd;
753
755
  readyRef.current = true;
@@ -964,6 +966,9 @@ var DocxDiffEditor = react.forwardRef(
964
966
  const merged = mergeDocuments(sourceJson, newJson, diff, author);
965
967
  setMergedJson(merged);
966
968
  if (superdocRef.current?.activeEditor) {
969
+ if (superdocRef.current.setDocumentMode) {
970
+ superdocRef.current.setDocumentMode("suggesting");
971
+ }
967
972
  setEditorContent(superdocRef.current.activeEditor, merged);
968
973
  enableReviewMode(superdocRef.current);
969
974
  }
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/constants.ts","../src/services/contentResolver.ts","../src/services/documentDiffer.ts","../src/services/trackChangeInjector.ts","../src/services/mergeDocuments.ts","../src/services/changeContextExtractor.ts","../src/DocxDiffEditor.tsx","../src/blankTemplate.ts"],"names":["DiffMatchPatch","uuidv4","forwardRef","DocxDiffEditor","useRef","useState","useCallback","error","useEffect","useImperativeHandle","jsxs","jsx"],"mappings":"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","file":"index.js","sourcesContent":["/**\n * Constants for DocxDiffEditor\n */\n\nimport type { TrackChangeAuthor } from './types';\n\n/**\n * Default author for track changes\n */\nexport const DEFAULT_AUTHOR: TrackChangeAuthor = {\n name: 'DocxDiff Editor',\n email: 'editor@docxdiff.local',\n};\n\n/**\n * Default SuperDoc user (used for editor initialization)\n */\nexport const DEFAULT_SUPERDOC_USER = {\n name: 'DocxDiff User',\n email: 'user@docxdiff.local',\n};\n\n/**\n * Permissions allowed for track change resolution\n */\nexport const TRACK_CHANGE_PERMISSIONS = [\n 'RESOLVE_OWN',\n 'RESOLVE_OTHER',\n 'REJECT_OWN',\n 'REJECT_OTHER',\n];\n\n/**\n * CSS class prefix for all component styles\n */\nexport const CSS_PREFIX = 'dde';\n\n/**\n * Timeouts\n */\nexport const TIMEOUTS = {\n /** Timeout for document parsing (ms) */\n PARSE_TIMEOUT: 30000,\n /** Small delay for React settling (ms) */\n INIT_DELAY: 100,\n /** Cleanup delay (ms) */\n CLEANUP_DELAY: 100,\n};\n\n","/**\n * Content Resolver Service\n * Detects content type and parses DOCX files to ProseMirror JSON.\n *\n * Supports three input formats:\n * - File: DOCX file parsed by SuperDoc\n * - string: HTML content (handled directly by SuperDoc in the component)\n * - object: Direct ProseMirror JSON (passed through)\n */\n\nimport type { DocxContent, ProseMirrorJSON } from '../types';\nimport { TIMEOUTS } from '../constants';\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\ntype SuperDocConstructor = any;\n\n/**\n * Detect the type of content provided\n */\nexport function detectContentType(content: DocxContent): 'file' | 'html' | 'json' {\n if (content instanceof File) {\n return 'file';\n }\n if (typeof content === 'string') {\n return 'html';\n }\n // Assume it's JSON if it's an object\n return 'json';\n}\n\n/**\n * Validate that content looks like ProseMirror JSON\n */\nexport function isProseMirrorJSON(content: unknown): boolean {\n if (!content || typeof content !== 'object') return false;\n const obj = content as Record<string, unknown>;\n return typeof obj.type === 'string' && (obj.type === 'doc' || Array.isArray(obj.content));\n}\n\n/**\n * Parse a DOCX File into ProseMirror JSON using a hidden SuperDoc instance.\n */\nexport async function parseDocxFile(\n file: File,\n SuperDoc: SuperDocConstructor\n): Promise<ProseMirrorJSON> {\n // Create a hidden container for the editor\n const container = document.createElement('div');\n container.style.cssText =\n 'position:absolute;top:-9999px;left:-9999px;width:800px;height:600px;visibility:hidden;';\n document.body.appendChild(container);\n\n return new Promise((resolve, reject) => {\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n let superdoc: any = null;\n let resolved = false;\n\n const cleanup = () => {\n setTimeout(() => {\n if (superdoc) {\n try {\n const sd = superdoc;\n superdoc = null;\n sd.destroy?.();\n } catch {\n // Ignore cleanup errors\n }\n }\n if (container.parentNode) {\n container.parentNode.removeChild(container);\n }\n }, TIMEOUTS.CLEANUP_DELAY);\n };\n\n setTimeout(async () => {\n if (resolved) return;\n\n try {\n superdoc = new SuperDoc({\n selector: container,\n document: file,\n documentMode: 'viewing',\n rulers: false,\n user: { name: 'Parser', email: 'parser@local' },\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n onReady: ({ superdoc: sd }: { superdoc: any }) => {\n if (resolved) return;\n try {\n const editor = sd?.activeEditor;\n if (!editor) {\n throw new Error('No active editor found');\n }\n\n const json = editor.getJSON();\n resolved = true;\n cleanup();\n resolve(json);\n } catch (err) {\n resolved = true;\n cleanup();\n reject(err);\n }\n },\n onException: ({ error: err }: { error: Error }) => {\n if (resolved) return;\n resolved = true;\n cleanup();\n reject(err);\n },\n });\n\n // Timeout\n setTimeout(() => {\n if (!resolved) {\n resolved = true;\n cleanup();\n reject(new Error('Document parsing timed out'));\n }\n }, TIMEOUTS.PARSE_TIMEOUT);\n } catch (err) {\n cleanup();\n reject(err);\n }\n }, 50);\n });\n}\n","/**\n * Document Differ Service\n * Diffs two ProseMirror JSON documents at the character level,\n * including text changes and formatting changes.\n */\n\nimport DiffMatchPatch from 'diff-match-patch';\nimport type {\n ProseMirrorJSON,\n ProseMirrorMark,\n DiffSegment,\n DiffResult,\n FormatChange,\n TextSpan,\n} from '../types';\n\nconst dmp = new DiffMatchPatch();\n\n// Diff operation types\nconst DIFF_DELETE = -1;\nconst DIFF_INSERT = 1;\nconst DIFF_EQUAL = 0;\n\n/**\n * Extract text spans with their marks from a ProseMirror node.\n */\nfunction extractTextSpans(node: ProseMirrorJSON, offset: number = 0): TextSpan[] {\n const spans: TextSpan[] = [];\n\n if (!node) return spans;\n\n if (node.type === 'text' && node.text) {\n spans.push({\n text: node.text,\n from: offset,\n to: offset + node.text.length,\n marks: node.marks || [],\n });\n return spans;\n }\n\n if (node.content && Array.isArray(node.content)) {\n let currentOffset = offset;\n for (const child of node.content) {\n const childSpans = extractTextSpans(child, currentOffset);\n spans.push(...childSpans);\n // Calculate consumed length\n for (const span of childSpans) {\n currentOffset = Math.max(currentOffset, span.to);\n }\n // If no spans, check if it's a text node for offset\n if (childSpans.length === 0 && child.type === 'text' && child.text) {\n currentOffset += child.text.length;\n }\n }\n }\n\n return spans;\n}\n\n/**\n * Extract text content from a ProseMirror node recursively.\n */\nfunction extractTextContent(node: ProseMirrorJSON): string {\n if (!node) return '';\n\n if (node.type === 'text' && node.text) {\n return node.text;\n }\n\n if (node.content && Array.isArray(node.content)) {\n return node.content.map(extractTextContent).join('');\n }\n\n return '';\n}\n\n/**\n * Deep compare two values.\n */\nfunction deepEqual(a: unknown, b: unknown): boolean {\n if (a === b) return true;\n if (typeof a !== typeof b) return false;\n if (typeof a !== 'object' || a === null || b === null) return false;\n\n const objA = a as Record<string, unknown>;\n const objB = b as Record<string, unknown>;\n const keysA = Object.keys(objA);\n const keysB = Object.keys(objB);\n\n if (keysA.length !== keysB.length) return false;\n\n for (const key of keysA) {\n if (!keysB.includes(key)) return false;\n if (!deepEqual(objA[key], objB[key])) return false;\n }\n\n return true;\n}\n\n/**\n * Compare marks arrays to check if they're equivalent.\n */\nfunction marksEqual(marksA: ProseMirrorMark[], marksB: ProseMirrorMark[]): boolean {\n if (marksA.length !== marksB.length) return false;\n\n // Sort by type for consistent comparison\n const sortedA = [...marksA].sort((a, b) => (a.type || '').localeCompare(b.type || ''));\n const sortedB = [...marksB].sort((a, b) => (a.type || '').localeCompare(b.type || ''));\n\n return deepEqual(sortedA, sortedB);\n}\n\n/**\n * Get marks at a specific character position from spans.\n */\nfunction getMarksAtPosition(spans: TextSpan[], pos: number): ProseMirrorMark[] {\n for (const span of spans) {\n if (pos >= span.from && pos < span.to) {\n return span.marks;\n }\n }\n return [];\n}\n\n/**\n * Detect format changes on equal text segments.\n */\nfunction detectFormatChanges(\n spansA: TextSpan[],\n spansB: TextSpan[],\n segments: DiffSegment[]\n): FormatChange[] {\n const formatChanges: FormatChange[] = [];\n\n let posA = 0;\n let posB = 0;\n\n for (const segment of segments) {\n if (segment.type === 'equal') {\n // For equal text, compare marks character by character\n // Group consecutive chars with same mark difference\n let i = 0;\n while (i < segment.text.length) {\n const marksA = getMarksAtPosition(spansA, posA + i);\n const marksB = getMarksAtPosition(spansB, posB + i);\n\n if (!marksEqual(marksA, marksB)) {\n // Found a format difference - find the extent\n const startI = i;\n const startMarksA = marksA;\n const startMarksB = marksB;\n\n // Extend while marks remain the same different pattern\n while (i < segment.text.length) {\n const currentMarksA = getMarksAtPosition(spansA, posA + i);\n const currentMarksB = getMarksAtPosition(spansB, posB + i);\n\n if (marksEqual(currentMarksA, startMarksA) && marksEqual(currentMarksB, startMarksB)) {\n i++;\n } else {\n break;\n }\n }\n\n formatChanges.push({\n from: posA + startI,\n to: posA + i,\n text: segment.text.substring(startI, i),\n before: startMarksA,\n after: startMarksB,\n });\n } else {\n i++;\n }\n }\n\n posA += segment.text.length;\n posB += segment.text.length;\n } else if (segment.type === 'delete') {\n // Deleted text exists only in docA, so only advance posA\n posA += segment.text.length;\n } else if (segment.type === 'insert') {\n // Inserted text exists only in docB, so only advance posB\n posB += segment.text.length;\n }\n }\n\n return formatChanges;\n}\n\n/**\n * Diff two ProseMirror JSON documents at the character level.\n * Detects both text changes and formatting changes.\n */\nexport function diffDocuments(\n docA: ProseMirrorJSON,\n docB: ProseMirrorJSON\n): DiffResult {\n // Extract full text from both documents\n const textA = extractTextContent(docA);\n const textB = extractTextContent(docB);\n\n // Perform character-level diff on the entire document\n const diffs = dmp.diff_main(textA, textB);\n dmp.diff_cleanupSemantic(diffs);\n\n // Convert to our DiffSegment format\n const segments: DiffSegment[] = [];\n let insertCount = 0;\n let deleteCount = 0;\n\n for (const [op, text] of diffs) {\n if (op === DIFF_EQUAL) {\n segments.push({ type: 'equal', text });\n } else if (op === DIFF_INSERT) {\n segments.push({ type: 'insert', text });\n insertCount++;\n } else if (op === DIFF_DELETE) {\n segments.push({ type: 'delete', text });\n deleteCount++;\n }\n }\n\n // Extract text spans with marks for format comparison\n const spansA = extractTextSpans(docA);\n const spansB = extractTextSpans(docB);\n\n // Detect format changes on equal segments\n const formatChanges = detectFormatChanges(spansA, spansB, segments);\n\n // Build summary\n const summary: string[] = [];\n if (insertCount > 0) {\n summary.push(`${insertCount} insertion(s)`);\n }\n if (deleteCount > 0) {\n summary.push(`${deleteCount} deletion(s)`);\n }\n if (formatChanges.length > 0) {\n summary.push(`${formatChanges.length} format change(s)`);\n }\n if (insertCount === 0 && deleteCount === 0 && formatChanges.length === 0) {\n summary.push('No changes detected');\n }\n\n return {\n segments,\n formatChanges,\n textA,\n textB,\n summary,\n };\n}\n\n","/**\n * Track Change Injector Service\n * Creates track change marks for insertions, deletions, and format changes.\n */\n\nimport { v4 as uuidv4 } from 'uuid';\nimport type { TrackChangeAuthor, ProseMirrorJSON, ProseMirrorMark } from '../types';\nimport { DEFAULT_AUTHOR } from '../constants';\n\n/**\n * Create a trackInsert mark.\n */\nexport function createTrackInsertMark(author: TrackChangeAuthor = DEFAULT_AUTHOR): ProseMirrorMark {\n return {\n type: 'trackInsert',\n attrs: {\n id: uuidv4(),\n author: author.name,\n authorEmail: author.email,\n authorImage: '',\n date: new Date().toISOString(),\n },\n };\n}\n\n/**\n * Create a trackDelete mark.\n */\nexport function createTrackDeleteMark(author: TrackChangeAuthor = DEFAULT_AUTHOR): ProseMirrorMark {\n return {\n type: 'trackDelete',\n attrs: {\n id: uuidv4(),\n author: author.name,\n authorEmail: author.email,\n authorImage: '',\n date: new Date().toISOString(),\n },\n };\n}\n\n/**\n * Create a trackFormat mark.\n */\nexport function createTrackFormatMark(\n before: ProseMirrorMark[],\n after: ProseMirrorMark[],\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorMark {\n return {\n type: 'trackFormat',\n attrs: {\n id: uuidv4(),\n author: author.name,\n authorEmail: author.email,\n authorImage: '',\n date: new Date().toISOString(),\n before,\n after,\n },\n };\n}\n\n/**\n * Add a mark to a text node, preserving existing marks.\n */\nexport function addMarkToTextNode(\n node: ProseMirrorJSON,\n mark: ProseMirrorMark\n): ProseMirrorJSON {\n if (node.type !== 'text') {\n return node;\n }\n\n return {\n ...node,\n marks: [...(node.marks || []), mark],\n };\n}\n\n/**\n * Create a text node with specific marks.\n */\nexport function createTextNode(\n text: string,\n marks: ProseMirrorMark[] = []\n): ProseMirrorJSON {\n const node: ProseMirrorJSON = {\n type: 'text',\n text,\n };\n\n if (marks.length > 0) {\n node.marks = marks;\n }\n\n return node;\n}\n\n/**\n * Apply trackDelete mark to all text in a node (recursively).\n */\nexport function markAllAsDeleted(\n node: ProseMirrorJSON,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorJSON {\n if (node.type === 'text') {\n return addMarkToTextNode(node, createTrackDeleteMark(author));\n }\n\n if (node.content && Array.isArray(node.content)) {\n return {\n ...node,\n content: node.content.map((child: ProseMirrorJSON) =>\n markAllAsDeleted(child, author)\n ),\n };\n }\n\n return node;\n}\n\n/**\n * Apply trackInsert mark to all text in a node (recursively).\n */\nexport function markAllAsInserted(\n node: ProseMirrorJSON,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorJSON {\n if (node.type === 'text') {\n return addMarkToTextNode(node, createTrackInsertMark(author));\n }\n\n if (node.content && Array.isArray(node.content)) {\n return {\n ...node,\n content: node.content.map((child: ProseMirrorJSON) =>\n markAllAsInserted(child, author)\n ),\n };\n }\n\n return node;\n}\n\n/**\n * Clone a node deeply.\n */\nexport function cloneNode(node: ProseMirrorJSON): ProseMirrorJSON {\n return JSON.parse(JSON.stringify(node));\n}\n\n","/**\n * Merge Documents Service\n * Applies track change marks to the original document structure\n * based on character-level diff segments.\n */\n\nimport type {\n ProseMirrorJSON,\n ProseMirrorNode,\n DiffResult,\n FormatChange,\n TrackChangeAuthor,\n} from '../types';\nimport {\n createTrackInsertMark,\n createTrackDeleteMark,\n createTrackFormatMark,\n} from './trackChangeInjector';\nimport { DEFAULT_AUTHOR } from '../constants';\n\n/**\n * Deep clone a node\n */\nfunction cloneNode(node: ProseMirrorNode): ProseMirrorNode {\n return JSON.parse(JSON.stringify(node));\n}\n\n/**\n * Character state during merge\n */\ninterface CharState {\n type: 'equal' | 'delete' | 'insert';\n insertText?: string;\n}\n\n/**\n * Insertion point during merge\n */\ninterface Insertion {\n afterOffset: number;\n text: string;\n}\n\n/**\n * Build a merged document by applying diff segments to the original structure.\n *\n * Strategy:\n * 1. Clone docA (original)\n * 2. Walk through diff segments\n * 3. For 'equal' segments: keep original content as-is\n * 4. For 'delete' segments: add trackDelete mark to the corresponding text\n * 5. For 'insert' segments: insert new text nodes with trackInsert mark\n */\nexport function mergeDocuments(\n docA: ProseMirrorNode,\n docB: ProseMirrorNode,\n diffResult: DiffResult,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorNode {\n // Clone the original document\n const merged = cloneNode(docA);\n\n // Build a map of character offset -> segment type\n // This tells us for each character what its state is\n const charStates: CharState[] = [];\n let insertions: Insertion[] = [];\n\n // Store format changes as array for range lookups\n const formatChanges: FormatChange[] = diffResult.formatChanges || [];\n\n // Helper to find format change at a position\n function getFormatChangeAt(pos: number): FormatChange | null {\n for (const fc of formatChanges) {\n if (pos >= fc.from && pos < fc.to) {\n return fc;\n }\n }\n return null;\n }\n\n let docAOffset = 0;\n for (const segment of diffResult.segments) {\n if (segment.type === 'equal') {\n // Mark these characters as equal\n for (let i = 0; i < segment.text.length; i++) {\n charStates[docAOffset + i] = { type: 'equal' };\n }\n docAOffset += segment.text.length;\n } else if (segment.type === 'delete') {\n // Mark these characters as deleted\n for (let i = 0; i < segment.text.length; i++) {\n charStates[docAOffset + i] = { type: 'delete' };\n }\n docAOffset += segment.text.length;\n } else if (segment.type === 'insert') {\n // Insert doesn't consume docA characters, it adds new text\n // We need to track where to insert\n insertions.push({\n afterOffset: docAOffset,\n text: segment.text,\n });\n }\n }\n\n // Now we need to transform the document\n // For each text span in the original:\n // 1. Split it based on character states (equal vs delete)\n // 2. Apply trackDelete marks to deleted parts\n // 3. Insert new content where insertions occur\n\n function transformNode(\n node: ProseMirrorNode,\n nodeOffset: number,\n path: number[]\n ): { nodes: ProseMirrorNode[]; consumedLength: number } {\n if (node.type === 'text' && node.text) {\n const text = node.text;\n const result: ProseMirrorNode[] = [];\n let i = 0;\n\n while (i < text.length) {\n const charOffset = nodeOffset + i;\n const charState = charStates[charOffset] || { type: 'equal' };\n\n // Check for insertions at this position\n const insertionsHere = insertions.filter((ins) => ins.afterOffset === charOffset);\n for (const ins of insertionsHere) {\n result.push({\n type: 'text',\n text: ins.text,\n marks: [...(node.marks || []), createTrackInsertMark(author)],\n });\n }\n\n // Find run of same state AND same format change status\n const currentFormatChange = getFormatChangeAt(nodeOffset + i);\n let j = i + 1;\n while (j < text.length) {\n const nextState = charStates[nodeOffset + j] || { type: 'equal' };\n if (nextState.type !== charState.type) break;\n // Also break if there's an insertion point here\n if (insertions.some((ins) => ins.afterOffset === nodeOffset + j)) break;\n // Break if format change status changes\n const nextFormatChange = getFormatChangeAt(nodeOffset + j);\n if (currentFormatChange !== nextFormatChange) break;\n j++;\n }\n\n const chunk = text.substring(i, j);\n let marks = [...(node.marks || [])];\n\n if (charState.type === 'delete') {\n marks.push(createTrackDeleteMark(author));\n } else if (charState.type === 'equal') {\n // Check if there's a format change at this position\n if (currentFormatChange) {\n // For format changes, use the NEW marks (after) plus trackFormat\n const trackFormatMark = createTrackFormatMark(\n currentFormatChange.before,\n currentFormatChange.after,\n author\n );\n marks = [...currentFormatChange.after, trackFormatMark];\n }\n }\n\n result.push({\n type: 'text',\n text: chunk,\n marks: marks.length > 0 ? marks : undefined,\n });\n\n i = j;\n }\n\n // Check for insertions at the end of this text node\n const endOffset = nodeOffset + text.length;\n const endInsertions = insertions.filter((ins) => ins.afterOffset === endOffset);\n for (const ins of endInsertions) {\n result.push({\n type: 'text',\n text: ins.text,\n marks: [...(node.marks || []), createTrackInsertMark(author)],\n });\n }\n\n // Remove processed insertions\n insertions = insertions.filter(\n (ins) => ins.afterOffset < nodeOffset || ins.afterOffset > endOffset\n );\n\n return { nodes: result, consumedLength: text.length };\n }\n\n // Non-text node: recursively transform children\n if (node.content && Array.isArray(node.content)) {\n const newContent: ProseMirrorNode[] = [];\n let offset = nodeOffset;\n\n for (const child of node.content) {\n const { nodes, consumedLength } = transformNode(child, offset, path);\n newContent.push(...nodes);\n offset += consumedLength;\n }\n\n return {\n nodes: [{ ...node, content: newContent }],\n consumedLength: offset - nodeOffset,\n };\n }\n\n // Node without content (like hard break)\n return { nodes: [node], consumedLength: 0 };\n }\n\n // Transform the document content\n if (merged.content && Array.isArray(merged.content)) {\n const newContent: ProseMirrorNode[] = [];\n let offset = 0;\n\n for (let i = 0; i < merged.content.length; i++) {\n const child = merged.content[i];\n const { nodes, consumedLength } = transformNode(child, offset, [i]);\n newContent.push(...nodes);\n offset += consumedLength;\n }\n\n merged.content = newContent;\n }\n\n // Handle any remaining insertions (at the very end)\n if (insertions.length > 0) {\n for (const ins of insertions) {\n const insertNode = {\n type: 'paragraph',\n content: [\n {\n type: 'run',\n content: [\n {\n type: 'text',\n text: ins.text,\n marks: [createTrackInsertMark(author)],\n },\n ],\n },\n ],\n };\n if (!merged.content) merged.content = [];\n merged.content.push(insertNode);\n }\n }\n\n return merged;\n}\n\n/**\n * Export for compatibility\n */\nexport function createSimpleMergedDocument(\n docA: ProseMirrorNode,\n docB: ProseMirrorNode,\n diffResult: DiffResult,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorNode {\n return mergeDocuments(docA, docB, diffResult, author);\n}\n\n","/**\n * Change Context Extractor\n * Extracts enriched changes with semantic context from merged document.\n * Provides surrounding text so the LLM can understand what the change is about.\n */\n\nimport type {\n ProseMirrorJSON,\n ProseMirrorNode,\n EnrichedChange,\n ChangeLocation,\n TraversalContext,\n} from '../types';\n\n/**\n * Main entry point - extract enriched changes from merged document\n */\nexport function extractEnrichedChanges(mergedJson: ProseMirrorJSON): EnrichedChange[] {\n const changes: EnrichedChange[] = [];\n const context: TraversalContext = {\n currentSection: null,\n currentParagraphText: '',\n currentNodeType: 'unknown',\n };\n\n traverseDocument(mergedJson, context, changes);\n return groupReplacements(changes);\n}\n\n/**\n * Recursively walk the document tree\n */\nfunction traverseDocument(\n node: ProseMirrorNode,\n context: TraversalContext,\n changes: EnrichedChange[]\n): void {\n if (!node) return;\n\n // Update context based on node type\n if (node.type === 'heading') {\n context.currentSection = extractAllText(node);\n context.headingLevel = node.attrs?.level || 1;\n context.currentNodeType = 'heading';\n context.currentParagraphText = context.currentSection;\n } else if (node.type === 'paragraph') {\n context.currentNodeType = 'paragraph';\n context.currentParagraphText = extractAllText(node);\n } else if (node.type === 'listItem') {\n context.currentNodeType = 'listItem';\n context.currentParagraphText = extractAllText(node);\n } else if (node.type === 'tableCell') {\n context.currentNodeType = 'tableCell';\n context.currentParagraphText = extractAllText(node);\n }\n\n // Check for track change marks on text nodes\n if (node.type === 'text' && node.marks) {\n const trackMark = findTrackChangeMark(node.marks);\n if (trackMark) {\n const change = createEnrichedChange(node, trackMark, context);\n if (change) changes.push(change);\n }\n }\n\n // Recurse into children\n if (node.content && Array.isArray(node.content)) {\n for (const child of node.content) {\n traverseDocument(child, context, changes);\n }\n }\n}\n\n/**\n * Extract ALL text from a node (including deleted text, for context)\n */\nfunction extractAllText(node: ProseMirrorNode): string {\n if (!node) return '';\n if (node.type === 'text') {\n return node.text || '';\n }\n if (node.content && Array.isArray(node.content)) {\n return node.content.map(extractAllText).join('');\n }\n return '';\n}\n\n/**\n * Find trackInsert, trackDelete, or trackFormat mark\n */\nfunction findTrackChangeMark(marks: ProseMirrorNode[]): ProseMirrorNode | null {\n return (\n marks.find(\n (m) =>\n m.type === 'trackInsert' || m.type === 'trackDelete' || m.type === 'trackFormat'\n ) || null\n );\n}\n\n/**\n * Create enriched change from node and track mark\n */\nfunction createEnrichedChange(\n node: ProseMirrorNode,\n trackMark: ProseMirrorNode,\n context: TraversalContext\n): EnrichedChange | null {\n const text = node.text || '';\n const location = buildLocation(context);\n const surroundingText = extractSurroundingSentence(text, context.currentParagraphText);\n\n if (trackMark.type === 'trackInsert') {\n return {\n type: 'insertion',\n text,\n location,\n surroundingText,\n charCount: text.length,\n };\n }\n\n if (trackMark.type === 'trackDelete') {\n return {\n type: 'deletion',\n text,\n location,\n surroundingText,\n charCount: text.length,\n };\n }\n\n if (trackMark.type === 'trackFormat') {\n const before = trackMark.attrs?.before || [];\n const after = trackMark.attrs?.after || [];\n return {\n type: 'format',\n text,\n location,\n surroundingText,\n formatDetails: {\n added: after\n .map((m: ProseMirrorNode) => m.type)\n .filter((t: string) => !before.some((b: ProseMirrorNode) => b.type === t)),\n removed: before\n .map((m: ProseMirrorNode) => m.type)\n .filter((t: string) => !after.some((a: ProseMirrorNode) => a.type === t)),\n },\n charCount: text.length,\n };\n }\n\n return null;\n}\n\n/**\n * Extract the sentence or clause containing the changed text\n */\nfunction extractSurroundingSentence(changedText: string, paragraphText: string): string {\n if (!paragraphText || !changedText) return '';\n\n // Find where the change is in the paragraph\n const changeIndex = paragraphText.indexOf(changedText);\n if (changeIndex === -1) {\n // If exact match not found, return truncated paragraph\n return truncate(paragraphText, 150);\n }\n\n // Split into sentences (by period, semicolon, or significant punctuation)\n // But keep the delimiters for context\n const sentenceBreaks = /([.;!?]\\s+)/g;\n const sentences: { text: string; start: number; end: number }[] = [];\n\n let lastEnd = 0;\n let match;\n\n while ((match = sentenceBreaks.exec(paragraphText)) !== null) {\n sentences.push({\n text: paragraphText.slice(lastEnd, match.index + match[0].length).trim(),\n start: lastEnd,\n end: match.index + match[0].length,\n });\n lastEnd = match.index + match[0].length;\n }\n\n // Add remaining text as final sentence\n if (lastEnd < paragraphText.length) {\n sentences.push({\n text: paragraphText.slice(lastEnd).trim(),\n start: lastEnd,\n end: paragraphText.length,\n });\n }\n\n // Find which sentence contains the change\n const changeEnd = changeIndex + changedText.length;\n for (const sentence of sentences) {\n if (changeIndex >= sentence.start && changeIndex < sentence.end) {\n // Found it - return this sentence (truncated if too long)\n return truncate(sentence.text, 200);\n }\n }\n\n // Fallback: return a window around the change\n const windowSize = 100;\n const start = Math.max(0, changeIndex - windowSize);\n const end = Math.min(paragraphText.length, changeEnd + windowSize);\n\n let result = paragraphText.slice(start, end);\n if (start > 0) result = '...' + result;\n if (end < paragraphText.length) result = result + '...';\n\n return result;\n}\n\n/**\n * Truncate text with ellipsis\n */\nfunction truncate(text: string, maxLen: number): string {\n if (!text) return '';\n const cleaned = text.replace(/\\s+/g, ' ').trim();\n if (cleaned.length <= maxLen) return cleaned;\n return cleaned.slice(0, maxLen - 3).trim() + '...';\n}\n\n/**\n * Build location info\n */\nfunction buildLocation(context: TraversalContext): ChangeLocation {\n const nodeType = context.currentNodeType as ChangeLocation['nodeType'];\n\n let description: string;\n if (nodeType === 'heading') {\n description = context.headingLevel === 1 ? 'document title' : 'section heading';\n } else if (context.currentSection) {\n description = `\"${truncate(context.currentSection, 50)}\" section`;\n } else {\n description = 'document body';\n }\n\n return {\n nodeType,\n headingLevel: context.headingLevel,\n sectionTitle: context.currentSection || undefined,\n description,\n };\n}\n\n/**\n * Combine adjacent delete+insert into replacements\n */\nfunction groupReplacements(changes: EnrichedChange[]): EnrichedChange[] {\n const result: EnrichedChange[] = [];\n let i = 0;\n\n while (i < changes.length) {\n const current = changes[i];\n const next = changes[i + 1];\n\n // Check if delete followed by insert (same section = likely replacement)\n if (\n current.type === 'deletion' &&\n next?.type === 'insertion' &&\n current.location.sectionTitle === next.location.sectionTitle\n ) {\n result.push({\n type: 'replacement',\n oldText: current.text,\n newText: next.text,\n location: current.location,\n surroundingText: current.surroundingText || next.surroundingText,\n charCount: (current.charCount || 0) + (next.charCount || 0),\n });\n i += 2;\n } else {\n result.push(current);\n i++;\n }\n }\n\n return result;\n}\n\n","/**\n * DocxDiffEditor Component\n *\n * A React component for DOCX document comparison with track changes visualization.\n * Wraps SuperDoc editor and provides methods for setting source, comparing documents,\n * and extracting change context for LLM processing.\n */\n\nimport {\n useCallback,\n useRef,\n useState,\n useEffect,\n useImperativeHandle,\n forwardRef,\n} from 'react';\n\nimport type {\n DocxDiffEditorProps,\n DocxDiffEditorRef,\n DocxContent,\n ProseMirrorJSON,\n SuperDocInstance,\n DiffSegment,\n DiffResult,\n ComparisonResult,\n EnrichedChange,\n} from './types';\n\nimport { parseDocxFile, detectContentType, isProseMirrorJSON } from './services/contentResolver';\nimport { diffDocuments } from './services/documentDiffer';\nimport { mergeDocuments } from './services/mergeDocuments';\nimport { extractEnrichedChanges } from './services/changeContextExtractor';\nimport { DEFAULT_AUTHOR, DEFAULT_SUPERDOC_USER, TRACK_CHANGE_PERMISSIONS, TIMEOUTS } from './constants';\n\n/**\n * Permission resolver that allows accepting/rejecting all track changes\n */\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\nconst permissionResolver = ({ permission }: any) => {\n return TRACK_CHANGE_PERMISSIONS.includes(permission) ? true : undefined;\n};\n\n/**\n * DocxDiffEditor Component\n */\nexport const DocxDiffEditor = forwardRef<DocxDiffEditorRef, DocxDiffEditorProps>(\n function DocxDiffEditor(\n {\n initialSource,\n templateDocx,\n showRulers = false,\n showToolbar = true,\n author = DEFAULT_AUTHOR,\n onReady,\n onSourceLoaded,\n onComparisonComplete,\n onError,\n className = '',\n toolbarClassName = '',\n editorClassName = '',\n },\n ref\n ) {\n // Refs\n const containerRef = useRef<HTMLDivElement>(null);\n const toolbarRef = useRef<HTMLDivElement>(null);\n const superdocRef = useRef<SuperDocInstance | null>(null);\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const SuperDocRef = useRef<any>(null);\n const mountedRef = useRef(true);\n const initRef = useRef(false);\n const readyRef = useRef(false);\n\n // State\n const [isLoading, setIsLoading] = useState(true);\n const [error, setError] = useState<string | null>(null);\n const [sourceJson, setSourceJson] = useState<ProseMirrorJSON | null>(null);\n const [mergedJson, setMergedJson] = useState<ProseMirrorJSON | null>(null);\n const [diffResult, setDiffResult] = useState<DiffResult | null>(null);\n\n // Generate unique IDs for this instance\n const instanceId = useRef(`dde-${Date.now()}-${Math.random().toString(36).substr(2, 9)}`);\n const editorId = `dde-editor-${instanceId.current}`;\n const toolbarId = `dde-toolbar-${instanceId.current}`;\n\n /**\n * Set content in the editor using available methods\n * Used only for JSON content and merged documents\n */\n const setEditorContent = useCallback((editor: SuperDocInstance, json: ProseMirrorJSON) => {\n if (editor.commands?.setContent) {\n editor.commands.setContent(json);\n } else if (editor.setContent) {\n editor.setContent(json);\n } else {\n const { state, view } = editor;\n if (state?.doc && view && json.content) {\n const newDoc = state.schema.nodeFromJSON(json);\n const tr = state.tr.replaceWith(0, state.doc.content.size, newDoc.content);\n view.dispatch(tr);\n }\n }\n }, []);\n\n /**\n * Enable track changes review mode\n */\n const enableReviewMode = useCallback((sd: SuperDocInstance) => {\n if (sd.setTrackedChangesPreferences) {\n sd.setTrackedChangesPreferences({ mode: 'review', enabled: true });\n } else if (sd.activeEditor?.commands?.enableTrackChanges) {\n sd.activeEditor.commands.enableTrackChanges();\n }\n }, []);\n\n /**\n * Set editing mode (normal mode - shows original without track changes)\n */\n const setEditingMode = useCallback((sd: SuperDocInstance) => {\n if (sd.setTrackedChangesPreferences) {\n // Use 'simple' mode with track changes disabled for clean editing view\n // Valid modes are: 'review', 'simple', 'original'\n sd.setTrackedChangesPreferences({ mode: 'simple', enabled: false });\n }\n }, []);\n\n /**\n * Handle errors\n */\n const handleError = useCallback(\n (err: Error | string) => {\n const error = err instanceof Error ? err : new Error(err);\n setError(error.message);\n onError?.(error);\n },\n [onError]\n );\n\n /**\n * Destroy current SuperDoc instance\n */\n const destroySuperdoc = useCallback(() => {\n if (superdocRef.current) {\n try {\n superdocRef.current.destroy?.();\n } catch {\n // Ignore cleanup errors\n }\n superdocRef.current = null;\n }\n readyRef.current = false;\n }, []);\n\n /**\n * Create a new SuperDoc instance with the given options\n */\n const createSuperdoc = useCallback(\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n async (options: { document?: File; html?: string }): Promise<{ superdoc: SuperDocInstance; json: ProseMirrorJSON }> => {\n if (!SuperDocRef.current) {\n throw new Error('SuperDoc not loaded');\n }\n if (!containerRef.current) {\n throw new Error('Container not available');\n }\n\n // Set IDs on DOM elements\n containerRef.current.id = editorId;\n if (toolbarRef.current) {\n toolbarRef.current.id = toolbarId;\n }\n\n return new Promise((resolve, reject) => {\n try {\n const superdoc = new SuperDocRef.current({\n selector: `#${editorId}`,\n toolbar: showToolbar ? `#${toolbarId}` : undefined,\n document: options.document,\n html: options.html,\n documentMode: 'editing',\n role: 'editor',\n rulers: showRulers,\n user: DEFAULT_SUPERDOC_USER,\n permissionResolver,\n onReady: ({ superdoc: sd }: { superdoc: SuperDocInstance }) => {\n superdocRef.current = sd;\n readyRef.current = true;\n\n // Extract JSON from the loaded document\n let json: ProseMirrorJSON = { type: 'doc', content: [] };\n if (sd?.activeEditor) {\n try {\n json = sd.activeEditor.getJSON();\n } catch (err) {\n console.error('Failed to extract JSON:', err);\n }\n }\n\n resolve({ superdoc: sd, json });\n },\n onException: ({ error: err }: { error: Error }) => {\n console.error('SuperDoc error:', err);\n reject(err);\n },\n });\n\n superdocRef.current = superdoc;\n\n // Timeout\n setTimeout(() => {\n if (!readyRef.current) {\n reject(new Error('SuperDoc initialization timed out'));\n }\n }, TIMEOUTS.PARSE_TIMEOUT);\n } catch (err) {\n reject(err);\n }\n });\n },\n [editorId, toolbarId, showToolbar, showRulers]\n );\n\n /**\n * Initialize SuperDoc instance\n */\n const initialize = useCallback(async () => {\n if (initRef.current || !containerRef.current || !mountedRef.current) return;\n if (!showToolbar && !toolbarRef.current) {\n // Continue without toolbar\n } else if (showToolbar && !toolbarRef.current) {\n return;\n }\n\n initRef.current = true;\n\n // Small delay for React to settle\n await new Promise((resolve) => setTimeout(resolve, TIMEOUTS.INIT_DELAY));\n\n if (!mountedRef.current || !containerRef.current) {\n initRef.current = false;\n return;\n }\n\n setIsLoading(true);\n setError(null);\n destroySuperdoc();\n\n try {\n // Note: superdoc CSS is bundled in dist/styles.css - user must import 'docx-diff-editor/styles.css'\n const { SuperDoc } = await import('superdoc');\n SuperDocRef.current = SuperDoc;\n\n // Determine initialization options based on initialSource\n let initOptions: { document?: File; html?: string } = {};\n\n if (initialSource) {\n const contentType = detectContentType(initialSource);\n if (contentType === 'file') {\n initOptions = { document: initialSource as File };\n } else if (contentType === 'html') {\n // Initialize directly with HTML - SuperDoc creates blank document internally\n initOptions = { html: initialSource as string };\n } else if (contentType === 'json') {\n // For JSON, we need a document first, then set content\n // Use template if provided, otherwise SuperDoc will create blank\n initOptions = templateDocx ? { document: templateDocx } : {};\n }\n } else if (templateDocx) {\n initOptions = { document: templateDocx };\n }\n // If no initialSource and no template, SuperDoc creates a blank document\n\n const { superdoc: sd, json } = await createSuperdoc(initOptions);\n\n // For JSON content, set it after initialization\n if (initialSource && detectContentType(initialSource) === 'json') {\n if (sd?.activeEditor && isProseMirrorJSON(initialSource)) {\n setEditorContent(sd.activeEditor, initialSource as ProseMirrorJSON);\n setSourceJson(initialSource as ProseMirrorJSON);\n onSourceLoaded?.(initialSource as ProseMirrorJSON);\n }\n } else {\n setSourceJson(json);\n onSourceLoaded?.(json);\n }\n\n setIsLoading(false);\n onReady?.();\n } catch (err) {\n console.error('Failed to initialize SuperDoc:', err);\n handleError(err instanceof Error ? err : new Error('Failed to load editor'));\n setIsLoading(false);\n }\n\n initRef.current = false;\n }, [\n initialSource,\n showRulers,\n showToolbar,\n templateDocx,\n onReady,\n onSourceLoaded,\n destroySuperdoc,\n createSuperdoc,\n setEditorContent,\n handleError,\n ]);\n\n // Initialize on mount\n useEffect(() => {\n mountedRef.current = true;\n initialize();\n\n return () => {\n mountedRef.current = false;\n destroySuperdoc();\n };\n }, [initialize, destroySuperdoc]);\n\n // =========================================================================\n // Imperative API\n // =========================================================================\n\n useImperativeHandle(\n ref,\n () => ({\n /**\n * Set the source/base document\n */\n async setSource(content: DocxContent): Promise<void> {\n if (!SuperDocRef.current) {\n throw new Error('Editor not initialized');\n }\n\n setIsLoading(true);\n setError(null);\n\n try {\n const contentType = detectContentType(content);\n let json: ProseMirrorJSON;\n\n // Destroy current instance and create new one\n destroySuperdoc();\n\n if (contentType === 'file') {\n // Initialize with DOCX file\n const result = await createSuperdoc({ document: content as File });\n json = result.json;\n } else if (contentType === 'html') {\n // Initialize directly with HTML - no template needed!\n // SuperDoc will create a blank document and apply HTML internally\n const result = await createSuperdoc({ html: content as string });\n json = result.json;\n } else {\n // JSON content - initialize blank then set content\n const result = await createSuperdoc(templateDocx ? { document: templateDocx } : {});\n if (result.superdoc?.activeEditor && isProseMirrorJSON(content)) {\n setEditorContent(result.superdoc.activeEditor, content as ProseMirrorJSON);\n json = content as ProseMirrorJSON;\n } else {\n json = result.json;\n }\n }\n\n setSourceJson(json);\n setMergedJson(null);\n setDiffResult(null);\n setEditingMode(superdocRef.current!);\n onSourceLoaded?.(json);\n } catch (err) {\n handleError(err instanceof Error ? err : new Error('Failed to set source'));\n throw err;\n } finally {\n setIsLoading(false);\n }\n },\n\n /**\n * Compare source with new content, show track changes\n */\n async compareWith(content: DocxContent): Promise<ComparisonResult> {\n if (!SuperDocRef.current) {\n throw new Error('Editor not initialized');\n }\n if (!sourceJson) {\n throw new Error('No source document set. Call setSource() first.');\n }\n\n setIsLoading(true);\n try {\n const contentType = detectContentType(content);\n let newJson: ProseMirrorJSON;\n\n if (contentType === 'file') {\n // Parse DOCX file using hidden SuperDoc instance\n newJson = await parseDocxFile(content as File, SuperDocRef.current);\n } else if (contentType === 'html') {\n // Parse HTML using a temporary SuperDoc instance\n const tempContainer = document.createElement('div');\n tempContainer.style.cssText = 'position:absolute;top:-9999px;left:-9999px;width:800px;height:600px;visibility:hidden;';\n document.body.appendChild(tempContainer);\n\n try {\n newJson = await new Promise((resolve, reject) => {\n const tempSuperdoc = new SuperDocRef.current({\n selector: tempContainer,\n html: content as string,\n documentMode: 'viewing',\n rulers: false,\n user: { name: 'Parser', email: 'parser@local' },\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n onReady: ({ superdoc: sd }: { superdoc: any }) => {\n try {\n const json = sd?.activeEditor?.getJSON() || { type: 'doc', content: [] };\n setTimeout(() => {\n try { sd?.destroy?.(); } catch { /* ignore */ }\n tempContainer.parentNode?.removeChild(tempContainer);\n }, 100);\n resolve(json);\n } catch (err) {\n reject(err);\n }\n },\n onException: ({ error: err }: { error: Error }) => {\n tempContainer.parentNode?.removeChild(tempContainer);\n reject(err);\n },\n });\n\n setTimeout(() => {\n try { tempSuperdoc?.destroy?.(); } catch { /* ignore */ }\n tempContainer.parentNode?.removeChild(tempContainer);\n reject(new Error('HTML parsing timed out'));\n }, TIMEOUTS.PARSE_TIMEOUT);\n });\n } catch (err) {\n tempContainer.parentNode?.removeChild(tempContainer);\n throw err;\n }\n } else {\n // JSON content - use directly\n if (!isProseMirrorJSON(content)) {\n throw new Error('Invalid ProseMirror JSON structure');\n }\n newJson = content as ProseMirrorJSON;\n }\n\n // Diff the documents\n const diff = diffDocuments(sourceJson, newJson);\n setDiffResult(diff);\n\n // Merge with track changes\n const merged = mergeDocuments(sourceJson, newJson, diff, author);\n setMergedJson(merged);\n\n // Update editor with merged content\n if (superdocRef.current?.activeEditor) {\n setEditorContent(superdocRef.current.activeEditor, merged);\n enableReviewMode(superdocRef.current);\n }\n\n // Build result\n const insertions = diff.segments.filter((s) => s.type === 'insert').length;\n const deletions = diff.segments.filter((s) => s.type === 'delete').length;\n const formatChanges = diff.formatChanges?.length || 0;\n\n const result: ComparisonResult = {\n totalChanges: insertions + deletions + formatChanges,\n insertions,\n deletions,\n formatChanges,\n summary: diff.summary,\n mergedJson: merged,\n };\n\n onComparisonComplete?.(result);\n return result;\n } catch (err) {\n handleError(err instanceof Error ? err : new Error('Comparison failed'));\n throw err;\n } finally {\n setIsLoading(false);\n }\n },\n\n /**\n * Get raw diff segments\n */\n getDiffSegments(): DiffSegment[] {\n return diffResult?.segments || [];\n },\n\n /**\n * Get enriched changes with context for LLM processing\n */\n getEnrichedChangesContext(): EnrichedChange[] {\n if (!mergedJson) return [];\n return extractEnrichedChanges(mergedJson);\n },\n\n /**\n * Get current document content as JSON\n */\n getContent(): ProseMirrorJSON {\n if (superdocRef.current?.activeEditor) {\n return superdocRef.current.activeEditor.getJSON();\n }\n return mergedJson || sourceJson || { type: 'doc', content: [] };\n },\n\n /**\n * Get source document JSON (before comparison)\n */\n getSourceContent(): ProseMirrorJSON | null {\n return sourceJson;\n },\n\n /**\n * Export current document to DOCX blob\n */\n async exportDocx(): Promise<Blob> {\n if (!superdocRef.current?.activeEditor) {\n throw new Error('Editor not ready');\n }\n\n const blob = await superdocRef.current.activeEditor.exportDocx({\n isFinalDoc: false,\n });\n\n if (!blob) {\n throw new Error('Export returned no data');\n }\n\n return blob;\n },\n\n /**\n * Reset to source state (clear comparison)\n */\n resetComparison(): void {\n if (sourceJson && superdocRef.current?.activeEditor) {\n setEditorContent(superdocRef.current.activeEditor, sourceJson);\n setEditingMode(superdocRef.current);\n setMergedJson(null);\n setDiffResult(null);\n }\n },\n\n /**\n * Check if editor is ready\n */\n isReady(): boolean {\n return readyRef.current;\n },\n }),\n [\n sourceJson,\n mergedJson,\n diffResult,\n templateDocx,\n author,\n destroySuperdoc,\n createSuperdoc,\n setEditorContent,\n enableReviewMode,\n setEditingMode,\n onSourceLoaded,\n onComparisonComplete,\n handleError,\n ]\n );\n\n // =========================================================================\n // Render\n // =========================================================================\n\n return (\n <div className={`dde-container ${className}`.trim()}>\n {/* Loading overlay */}\n {isLoading && (\n <div className=\"dde-loading\">\n <div className=\"dde-loading__spinner\" />\n <p className=\"dde-loading__text\">Loading document...</p>\n </div>\n )}\n\n {/* Error overlay */}\n {error && (\n <div className=\"dde-error\">\n <div className=\"dde-error__icon\">\n <svg\n className=\"dde-error__svg\"\n fill=\"none\"\n stroke=\"currentColor\"\n viewBox=\"0 0 24 24\"\n >\n <path\n strokeLinecap=\"round\"\n strokeLinejoin=\"round\"\n strokeWidth=\"2\"\n d=\"M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z\"\n />\n </svg>\n </div>\n <p className=\"dde-error__title\">Failed to load document</p>\n <p className=\"dde-error__message\">{error}</p>\n </div>\n )}\n\n {/* Toolbar */}\n {showToolbar && (\n <div\n ref={toolbarRef}\n className={`dde-toolbar ${toolbarClassName}`.trim()}\n />\n )}\n\n {/* Editor container */}\n <div\n ref={containerRef}\n className={`dde-editor ${editorClassName}`.trim()}\n />\n </div>\n );\n }\n);\n\nexport default DocxDiffEditor;\n","/**\n * Embedded DOCX template\n *\n * This is a base64-encoded blank DOCX file created with Microsoft Word.\n * It provides the complete schema, styles, themes, and fonts needed to\n * initialize SuperDoc when working with HTML or JSON content.\n *\n * The DOCX contains all standard Word document components:\n * - [Content_Types].xml\n * - _rels/.rels\n * - word/document.xml\n * - word/_rels/document.xml.rels\n * - word/styles.xml (full Word styles)\n * - word/settings.xml\n * - word/fontTable.xml\n * - word/webSettings.xml\n * - word/theme/theme1.xml\n * - docProps/core.xml\n * - docProps/app.xml\n */\n\n/**\n * Base64-encoded blank DOCX file created with Microsoft Word.\n */\nconst BLANK_DOCX_BASE64 = `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`;\n\n/**\n * Convert base64 string to Blob\n */\nfunction base64ToBlob(base64: string, mimeType: string): Blob {\n const byteCharacters = atob(base64.replace(/\\s/g, ''));\n const byteNumbers = new Array(byteCharacters.length);\n\n for (let i = 0; i < byteCharacters.length; i++) {\n byteNumbers[i] = byteCharacters.charCodeAt(i);\n }\n\n const byteArray = new Uint8Array(byteNumbers);\n return new Blob([byteArray], { type: mimeType });\n}\n\n/**\n * Convert base64 string to File\n */\nfunction base64ToFile(base64: string, filename: string, mimeType: string): File {\n const blob = base64ToBlob(base64, mimeType);\n return new File([blob], filename, { type: mimeType });\n}\n\n/**\n * Get the blank DOCX template as a File object\n */\nexport function getBlankTemplateFile(): File {\n return base64ToFile(\n BLANK_DOCX_BASE64,\n 'blank-template.docx',\n 'application/vnd.openxmlformats-officedocument.wordprocessingml.document'\n );\n}\n\n/**\n * Get the blank DOCX template as a Blob\n */\nexport function getBlankTemplateBlob(): Blob {\n return base64ToBlob(\n BLANK_DOCX_BASE64,\n 'application/vnd.openxmlformats-officedocument.wordprocessingml.document'\n );\n}\n\n/**\n * Check if a File is a valid DOCX file (basic check)\n */\nexport function isValidDocxFile(file: File): boolean {\n const validTypes = [\n 'application/vnd.openxmlformats-officedocument.wordprocessingml.document',\n 'application/msword',\n ];\n return validTypes.includes(file.type) || file.name.endsWith('.docx');\n}\n"]}
1
+ {"version":3,"sources":["../src/constants.ts","../src/services/contentResolver.ts","../src/services/documentDiffer.ts","../src/services/trackChangeInjector.ts","../src/services/mergeDocuments.ts","../src/services/changeContextExtractor.ts","../src/DocxDiffEditor.tsx","../src/blankTemplate.ts"],"names":["DiffMatchPatch","uuidv4","forwardRef","DocxDiffEditor","useRef","useState","useCallback","error","useEffect","useImperativeHandle","jsxs","jsx"],"mappings":"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","file":"index.js","sourcesContent":["/**\n * Constants for DocxDiffEditor\n */\n\nimport type { TrackChangeAuthor } from './types';\n\n/**\n * Default author for track changes\n */\nexport const DEFAULT_AUTHOR: TrackChangeAuthor = {\n name: 'DocxDiff Editor',\n email: 'editor@docxdiff.local',\n};\n\n/**\n * Default SuperDoc user (used for editor initialization)\n */\nexport const DEFAULT_SUPERDOC_USER = {\n name: 'DocxDiff User',\n email: 'user@docxdiff.local',\n};\n\n/**\n * Permissions allowed for track change resolution\n */\nexport const TRACK_CHANGE_PERMISSIONS = [\n 'RESOLVE_OWN',\n 'RESOLVE_OTHER',\n 'REJECT_OWN',\n 'REJECT_OTHER',\n];\n\n/**\n * CSS class prefix for all component styles\n */\nexport const CSS_PREFIX = 'dde';\n\n/**\n * Timeouts\n */\nexport const TIMEOUTS = {\n /** Timeout for document parsing (ms) */\n PARSE_TIMEOUT: 30000,\n /** Small delay for React settling (ms) */\n INIT_DELAY: 100,\n /** Cleanup delay (ms) */\n CLEANUP_DELAY: 100,\n};\n\n","/**\n * Content Resolver Service\n * Detects content type and parses DOCX files to ProseMirror JSON.\n *\n * Supports three input formats:\n * - File: DOCX file parsed by SuperDoc\n * - string: HTML content (handled directly by SuperDoc in the component)\n * - object: Direct ProseMirror JSON (passed through)\n */\n\nimport type { DocxContent, ProseMirrorJSON } from '../types';\nimport { TIMEOUTS } from '../constants';\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\ntype SuperDocConstructor = any;\n\n/**\n * Detect the type of content provided\n */\nexport function detectContentType(content: DocxContent): 'file' | 'html' | 'json' {\n if (content instanceof File) {\n return 'file';\n }\n if (typeof content === 'string') {\n return 'html';\n }\n // Assume it's JSON if it's an object\n return 'json';\n}\n\n/**\n * Validate that content looks like ProseMirror JSON\n */\nexport function isProseMirrorJSON(content: unknown): boolean {\n if (!content || typeof content !== 'object') return false;\n const obj = content as Record<string, unknown>;\n return typeof obj.type === 'string' && (obj.type === 'doc' || Array.isArray(obj.content));\n}\n\n/**\n * Parse a DOCX File into ProseMirror JSON using a hidden SuperDoc instance.\n */\nexport async function parseDocxFile(\n file: File,\n SuperDoc: SuperDocConstructor\n): Promise<ProseMirrorJSON> {\n // Create a hidden container for the editor\n const container = document.createElement('div');\n container.style.cssText =\n 'position:absolute;top:-9999px;left:-9999px;width:800px;height:600px;visibility:hidden;';\n document.body.appendChild(container);\n\n return new Promise((resolve, reject) => {\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n let superdoc: any = null;\n let resolved = false;\n\n const cleanup = () => {\n setTimeout(() => {\n if (superdoc) {\n try {\n const sd = superdoc;\n superdoc = null;\n sd.destroy?.();\n } catch {\n // Ignore cleanup errors\n }\n }\n if (container.parentNode) {\n container.parentNode.removeChild(container);\n }\n }, TIMEOUTS.CLEANUP_DELAY);\n };\n\n setTimeout(async () => {\n if (resolved) return;\n\n try {\n superdoc = new SuperDoc({\n selector: container,\n document: file,\n documentMode: 'viewing',\n rulers: false,\n user: { name: 'Parser', email: 'parser@local' },\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n onReady: ({ superdoc: sd }: { superdoc: any }) => {\n if (resolved) return;\n try {\n const editor = sd?.activeEditor;\n if (!editor) {\n throw new Error('No active editor found');\n }\n\n const json = editor.getJSON();\n resolved = true;\n cleanup();\n resolve(json);\n } catch (err) {\n resolved = true;\n cleanup();\n reject(err);\n }\n },\n onException: ({ error: err }: { error: Error }) => {\n if (resolved) return;\n resolved = true;\n cleanup();\n reject(err);\n },\n });\n\n // Timeout\n setTimeout(() => {\n if (!resolved) {\n resolved = true;\n cleanup();\n reject(new Error('Document parsing timed out'));\n }\n }, TIMEOUTS.PARSE_TIMEOUT);\n } catch (err) {\n cleanup();\n reject(err);\n }\n }, 50);\n });\n}\n","/**\n * Document Differ Service\n * Diffs two ProseMirror JSON documents at the character level,\n * including text changes and formatting changes.\n */\n\nimport DiffMatchPatch from 'diff-match-patch';\nimport type {\n ProseMirrorJSON,\n ProseMirrorMark,\n DiffSegment,\n DiffResult,\n FormatChange,\n TextSpan,\n} from '../types';\n\nconst dmp = new DiffMatchPatch();\n\n// Diff operation types\nconst DIFF_DELETE = -1;\nconst DIFF_INSERT = 1;\nconst DIFF_EQUAL = 0;\n\n/**\n * Extract text spans with their marks from a ProseMirror node.\n */\nfunction extractTextSpans(node: ProseMirrorJSON, offset: number = 0): TextSpan[] {\n const spans: TextSpan[] = [];\n\n if (!node) return spans;\n\n if (node.type === 'text' && node.text) {\n spans.push({\n text: node.text,\n from: offset,\n to: offset + node.text.length,\n marks: node.marks || [],\n });\n return spans;\n }\n\n if (node.content && Array.isArray(node.content)) {\n let currentOffset = offset;\n for (const child of node.content) {\n const childSpans = extractTextSpans(child, currentOffset);\n spans.push(...childSpans);\n // Calculate consumed length\n for (const span of childSpans) {\n currentOffset = Math.max(currentOffset, span.to);\n }\n // If no spans, check if it's a text node for offset\n if (childSpans.length === 0 && child.type === 'text' && child.text) {\n currentOffset += child.text.length;\n }\n }\n }\n\n return spans;\n}\n\n/**\n * Extract text content from a ProseMirror node recursively.\n */\nfunction extractTextContent(node: ProseMirrorJSON): string {\n if (!node) return '';\n\n if (node.type === 'text' && node.text) {\n return node.text;\n }\n\n if (node.content && Array.isArray(node.content)) {\n return node.content.map(extractTextContent).join('');\n }\n\n return '';\n}\n\n/**\n * Deep compare two values.\n */\nfunction deepEqual(a: unknown, b: unknown): boolean {\n if (a === b) return true;\n if (typeof a !== typeof b) return false;\n if (typeof a !== 'object' || a === null || b === null) return false;\n\n const objA = a as Record<string, unknown>;\n const objB = b as Record<string, unknown>;\n const keysA = Object.keys(objA);\n const keysB = Object.keys(objB);\n\n if (keysA.length !== keysB.length) return false;\n\n for (const key of keysA) {\n if (!keysB.includes(key)) return false;\n if (!deepEqual(objA[key], objB[key])) return false;\n }\n\n return true;\n}\n\n/**\n * Compare marks arrays to check if they're equivalent.\n */\nfunction marksEqual(marksA: ProseMirrorMark[], marksB: ProseMirrorMark[]): boolean {\n if (marksA.length !== marksB.length) return false;\n\n // Sort by type for consistent comparison\n const sortedA = [...marksA].sort((a, b) => (a.type || '').localeCompare(b.type || ''));\n const sortedB = [...marksB].sort((a, b) => (a.type || '').localeCompare(b.type || ''));\n\n return deepEqual(sortedA, sortedB);\n}\n\n/**\n * Get marks at a specific character position from spans.\n */\nfunction getMarksAtPosition(spans: TextSpan[], pos: number): ProseMirrorMark[] {\n for (const span of spans) {\n if (pos >= span.from && pos < span.to) {\n return span.marks;\n }\n }\n return [];\n}\n\n/**\n * Detect format changes on equal text segments.\n */\nfunction detectFormatChanges(\n spansA: TextSpan[],\n spansB: TextSpan[],\n segments: DiffSegment[]\n): FormatChange[] {\n const formatChanges: FormatChange[] = [];\n\n let posA = 0;\n let posB = 0;\n\n for (const segment of segments) {\n if (segment.type === 'equal') {\n // For equal text, compare marks character by character\n // Group consecutive chars with same mark difference\n let i = 0;\n while (i < segment.text.length) {\n const marksA = getMarksAtPosition(spansA, posA + i);\n const marksB = getMarksAtPosition(spansB, posB + i);\n\n if (!marksEqual(marksA, marksB)) {\n // Found a format difference - find the extent\n const startI = i;\n const startMarksA = marksA;\n const startMarksB = marksB;\n\n // Extend while marks remain the same different pattern\n while (i < segment.text.length) {\n const currentMarksA = getMarksAtPosition(spansA, posA + i);\n const currentMarksB = getMarksAtPosition(spansB, posB + i);\n\n if (marksEqual(currentMarksA, startMarksA) && marksEqual(currentMarksB, startMarksB)) {\n i++;\n } else {\n break;\n }\n }\n\n formatChanges.push({\n from: posA + startI,\n to: posA + i,\n text: segment.text.substring(startI, i),\n before: startMarksA,\n after: startMarksB,\n });\n } else {\n i++;\n }\n }\n\n posA += segment.text.length;\n posB += segment.text.length;\n } else if (segment.type === 'delete') {\n // Deleted text exists only in docA, so only advance posA\n posA += segment.text.length;\n } else if (segment.type === 'insert') {\n // Inserted text exists only in docB, so only advance posB\n posB += segment.text.length;\n }\n }\n\n return formatChanges;\n}\n\n/**\n * Diff two ProseMirror JSON documents at the character level.\n * Detects both text changes and formatting changes.\n */\nexport function diffDocuments(\n docA: ProseMirrorJSON,\n docB: ProseMirrorJSON\n): DiffResult {\n // Extract full text from both documents\n const textA = extractTextContent(docA);\n const textB = extractTextContent(docB);\n\n // Perform character-level diff on the entire document\n const diffs = dmp.diff_main(textA, textB);\n dmp.diff_cleanupSemantic(diffs);\n\n // Convert to our DiffSegment format\n const segments: DiffSegment[] = [];\n let insertCount = 0;\n let deleteCount = 0;\n\n for (const [op, text] of diffs) {\n if (op === DIFF_EQUAL) {\n segments.push({ type: 'equal', text });\n } else if (op === DIFF_INSERT) {\n segments.push({ type: 'insert', text });\n insertCount++;\n } else if (op === DIFF_DELETE) {\n segments.push({ type: 'delete', text });\n deleteCount++;\n }\n }\n\n // Extract text spans with marks for format comparison\n const spansA = extractTextSpans(docA);\n const spansB = extractTextSpans(docB);\n\n // Detect format changes on equal segments\n const formatChanges = detectFormatChanges(spansA, spansB, segments);\n\n // Build summary\n const summary: string[] = [];\n if (insertCount > 0) {\n summary.push(`${insertCount} insertion(s)`);\n }\n if (deleteCount > 0) {\n summary.push(`${deleteCount} deletion(s)`);\n }\n if (formatChanges.length > 0) {\n summary.push(`${formatChanges.length} format change(s)`);\n }\n if (insertCount === 0 && deleteCount === 0 && formatChanges.length === 0) {\n summary.push('No changes detected');\n }\n\n return {\n segments,\n formatChanges,\n textA,\n textB,\n summary,\n };\n}\n\n","/**\n * Track Change Injector Service\n * Creates track change marks for insertions, deletions, and format changes.\n */\n\nimport { v4 as uuidv4 } from 'uuid';\nimport type { TrackChangeAuthor, ProseMirrorJSON, ProseMirrorMark } from '../types';\nimport { DEFAULT_AUTHOR } from '../constants';\n\n/**\n * Create a trackInsert mark.\n */\nexport function createTrackInsertMark(author: TrackChangeAuthor = DEFAULT_AUTHOR): ProseMirrorMark {\n return {\n type: 'trackInsert',\n attrs: {\n id: uuidv4(),\n author: author.name,\n authorEmail: author.email,\n authorImage: '',\n date: new Date().toISOString(),\n },\n };\n}\n\n/**\n * Create a trackDelete mark.\n */\nexport function createTrackDeleteMark(author: TrackChangeAuthor = DEFAULT_AUTHOR): ProseMirrorMark {\n return {\n type: 'trackDelete',\n attrs: {\n id: uuidv4(),\n author: author.name,\n authorEmail: author.email,\n authorImage: '',\n date: new Date().toISOString(),\n },\n };\n}\n\n/**\n * Create a trackFormat mark.\n */\nexport function createTrackFormatMark(\n before: ProseMirrorMark[],\n after: ProseMirrorMark[],\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorMark {\n return {\n type: 'trackFormat',\n attrs: {\n id: uuidv4(),\n author: author.name,\n authorEmail: author.email,\n authorImage: '',\n date: new Date().toISOString(),\n before,\n after,\n },\n };\n}\n\n/**\n * Add a mark to a text node, preserving existing marks.\n */\nexport function addMarkToTextNode(\n node: ProseMirrorJSON,\n mark: ProseMirrorMark\n): ProseMirrorJSON {\n if (node.type !== 'text') {\n return node;\n }\n\n return {\n ...node,\n marks: [...(node.marks || []), mark],\n };\n}\n\n/**\n * Create a text node with specific marks.\n */\nexport function createTextNode(\n text: string,\n marks: ProseMirrorMark[] = []\n): ProseMirrorJSON {\n const node: ProseMirrorJSON = {\n type: 'text',\n text,\n };\n\n if (marks.length > 0) {\n node.marks = marks;\n }\n\n return node;\n}\n\n/**\n * Apply trackDelete mark to all text in a node (recursively).\n */\nexport function markAllAsDeleted(\n node: ProseMirrorJSON,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorJSON {\n if (node.type === 'text') {\n return addMarkToTextNode(node, createTrackDeleteMark(author));\n }\n\n if (node.content && Array.isArray(node.content)) {\n return {\n ...node,\n content: node.content.map((child: ProseMirrorJSON) =>\n markAllAsDeleted(child, author)\n ),\n };\n }\n\n return node;\n}\n\n/**\n * Apply trackInsert mark to all text in a node (recursively).\n */\nexport function markAllAsInserted(\n node: ProseMirrorJSON,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorJSON {\n if (node.type === 'text') {\n return addMarkToTextNode(node, createTrackInsertMark(author));\n }\n\n if (node.content && Array.isArray(node.content)) {\n return {\n ...node,\n content: node.content.map((child: ProseMirrorJSON) =>\n markAllAsInserted(child, author)\n ),\n };\n }\n\n return node;\n}\n\n/**\n * Clone a node deeply.\n */\nexport function cloneNode(node: ProseMirrorJSON): ProseMirrorJSON {\n return JSON.parse(JSON.stringify(node));\n}\n\n","/**\n * Merge Documents Service\n * Applies track change marks to the original document structure\n * based on character-level diff segments.\n */\n\nimport type {\n ProseMirrorJSON,\n ProseMirrorNode,\n DiffResult,\n FormatChange,\n TrackChangeAuthor,\n} from '../types';\nimport {\n createTrackInsertMark,\n createTrackDeleteMark,\n createTrackFormatMark,\n} from './trackChangeInjector';\nimport { DEFAULT_AUTHOR } from '../constants';\n\n/**\n * Deep clone a node\n */\nfunction cloneNode(node: ProseMirrorNode): ProseMirrorNode {\n return JSON.parse(JSON.stringify(node));\n}\n\n/**\n * Character state during merge\n */\ninterface CharState {\n type: 'equal' | 'delete' | 'insert';\n insertText?: string;\n}\n\n/**\n * Insertion point during merge\n */\ninterface Insertion {\n afterOffset: number;\n text: string;\n}\n\n/**\n * Build a merged document by applying diff segments to the original structure.\n *\n * Strategy:\n * 1. Clone docA (original)\n * 2. Walk through diff segments\n * 3. For 'equal' segments: keep original content as-is\n * 4. For 'delete' segments: add trackDelete mark to the corresponding text\n * 5. For 'insert' segments: insert new text nodes with trackInsert mark\n */\nexport function mergeDocuments(\n docA: ProseMirrorNode,\n docB: ProseMirrorNode,\n diffResult: DiffResult,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorNode {\n // Clone the original document\n const merged = cloneNode(docA);\n\n // Build a map of character offset -> segment type\n // This tells us for each character what its state is\n const charStates: CharState[] = [];\n let insertions: Insertion[] = [];\n\n // Store format changes as array for range lookups\n const formatChanges: FormatChange[] = diffResult.formatChanges || [];\n\n // Helper to find format change at a position\n function getFormatChangeAt(pos: number): FormatChange | null {\n for (const fc of formatChanges) {\n if (pos >= fc.from && pos < fc.to) {\n return fc;\n }\n }\n return null;\n }\n\n let docAOffset = 0;\n for (const segment of diffResult.segments) {\n if (segment.type === 'equal') {\n // Mark these characters as equal\n for (let i = 0; i < segment.text.length; i++) {\n charStates[docAOffset + i] = { type: 'equal' };\n }\n docAOffset += segment.text.length;\n } else if (segment.type === 'delete') {\n // Mark these characters as deleted\n for (let i = 0; i < segment.text.length; i++) {\n charStates[docAOffset + i] = { type: 'delete' };\n }\n docAOffset += segment.text.length;\n } else if (segment.type === 'insert') {\n // Insert doesn't consume docA characters, it adds new text\n // We need to track where to insert\n insertions.push({\n afterOffset: docAOffset,\n text: segment.text,\n });\n }\n }\n\n // Now we need to transform the document\n // For each text span in the original:\n // 1. Split it based on character states (equal vs delete)\n // 2. Apply trackDelete marks to deleted parts\n // 3. Insert new content where insertions occur\n\n function transformNode(\n node: ProseMirrorNode,\n nodeOffset: number,\n path: number[]\n ): { nodes: ProseMirrorNode[]; consumedLength: number } {\n if (node.type === 'text' && node.text) {\n const text = node.text;\n const result: ProseMirrorNode[] = [];\n let i = 0;\n\n while (i < text.length) {\n const charOffset = nodeOffset + i;\n const charState = charStates[charOffset] || { type: 'equal' };\n\n // Check for insertions at this position\n const insertionsHere = insertions.filter((ins) => ins.afterOffset === charOffset);\n for (const ins of insertionsHere) {\n result.push({\n type: 'text',\n text: ins.text,\n marks: [...(node.marks || []), createTrackInsertMark(author)],\n });\n }\n\n // Find run of same state AND same format change status\n const currentFormatChange = getFormatChangeAt(nodeOffset + i);\n let j = i + 1;\n while (j < text.length) {\n const nextState = charStates[nodeOffset + j] || { type: 'equal' };\n if (nextState.type !== charState.type) break;\n // Also break if there's an insertion point here\n if (insertions.some((ins) => ins.afterOffset === nodeOffset + j)) break;\n // Break if format change status changes\n const nextFormatChange = getFormatChangeAt(nodeOffset + j);\n if (currentFormatChange !== nextFormatChange) break;\n j++;\n }\n\n const chunk = text.substring(i, j);\n let marks = [...(node.marks || [])];\n\n if (charState.type === 'delete') {\n marks.push(createTrackDeleteMark(author));\n } else if (charState.type === 'equal') {\n // Check if there's a format change at this position\n if (currentFormatChange) {\n // For format changes, use the NEW marks (after) plus trackFormat\n const trackFormatMark = createTrackFormatMark(\n currentFormatChange.before,\n currentFormatChange.after,\n author\n );\n marks = [...currentFormatChange.after, trackFormatMark];\n }\n }\n\n result.push({\n type: 'text',\n text: chunk,\n marks: marks.length > 0 ? marks : undefined,\n });\n\n i = j;\n }\n\n // Check for insertions at the end of this text node\n const endOffset = nodeOffset + text.length;\n const endInsertions = insertions.filter((ins) => ins.afterOffset === endOffset);\n for (const ins of endInsertions) {\n result.push({\n type: 'text',\n text: ins.text,\n marks: [...(node.marks || []), createTrackInsertMark(author)],\n });\n }\n\n // Remove processed insertions\n insertions = insertions.filter(\n (ins) => ins.afterOffset < nodeOffset || ins.afterOffset > endOffset\n );\n\n return { nodes: result, consumedLength: text.length };\n }\n\n // Non-text node: recursively transform children\n if (node.content && Array.isArray(node.content)) {\n const newContent: ProseMirrorNode[] = [];\n let offset = nodeOffset;\n\n for (const child of node.content) {\n const { nodes, consumedLength } = transformNode(child, offset, path);\n newContent.push(...nodes);\n offset += consumedLength;\n }\n\n return {\n nodes: [{ ...node, content: newContent }],\n consumedLength: offset - nodeOffset,\n };\n }\n\n // Node without content (like hard break)\n return { nodes: [node], consumedLength: 0 };\n }\n\n // Transform the document content\n if (merged.content && Array.isArray(merged.content)) {\n const newContent: ProseMirrorNode[] = [];\n let offset = 0;\n\n for (let i = 0; i < merged.content.length; i++) {\n const child = merged.content[i];\n const { nodes, consumedLength } = transformNode(child, offset, [i]);\n newContent.push(...nodes);\n offset += consumedLength;\n }\n\n merged.content = newContent;\n }\n\n // Handle any remaining insertions (at the very end)\n if (insertions.length > 0) {\n for (const ins of insertions) {\n const insertNode = {\n type: 'paragraph',\n content: [\n {\n type: 'run',\n content: [\n {\n type: 'text',\n text: ins.text,\n marks: [createTrackInsertMark(author)],\n },\n ],\n },\n ],\n };\n if (!merged.content) merged.content = [];\n merged.content.push(insertNode);\n }\n }\n\n return merged;\n}\n\n/**\n * Export for compatibility\n */\nexport function createSimpleMergedDocument(\n docA: ProseMirrorNode,\n docB: ProseMirrorNode,\n diffResult: DiffResult,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorNode {\n return mergeDocuments(docA, docB, diffResult, author);\n}\n\n","/**\n * Change Context Extractor\n * Extracts enriched changes with semantic context from merged document.\n * Provides surrounding text so the LLM can understand what the change is about.\n */\n\nimport type {\n ProseMirrorJSON,\n ProseMirrorNode,\n EnrichedChange,\n ChangeLocation,\n TraversalContext,\n} from '../types';\n\n/**\n * Main entry point - extract enriched changes from merged document\n */\nexport function extractEnrichedChanges(mergedJson: ProseMirrorJSON): EnrichedChange[] {\n const changes: EnrichedChange[] = [];\n const context: TraversalContext = {\n currentSection: null,\n currentParagraphText: '',\n currentNodeType: 'unknown',\n };\n\n traverseDocument(mergedJson, context, changes);\n return groupReplacements(changes);\n}\n\n/**\n * Recursively walk the document tree\n */\nfunction traverseDocument(\n node: ProseMirrorNode,\n context: TraversalContext,\n changes: EnrichedChange[]\n): void {\n if (!node) return;\n\n // Update context based on node type\n if (node.type === 'heading') {\n context.currentSection = extractAllText(node);\n context.headingLevel = node.attrs?.level || 1;\n context.currentNodeType = 'heading';\n context.currentParagraphText = context.currentSection;\n } else if (node.type === 'paragraph') {\n context.currentNodeType = 'paragraph';\n context.currentParagraphText = extractAllText(node);\n } else if (node.type === 'listItem') {\n context.currentNodeType = 'listItem';\n context.currentParagraphText = extractAllText(node);\n } else if (node.type === 'tableCell') {\n context.currentNodeType = 'tableCell';\n context.currentParagraphText = extractAllText(node);\n }\n\n // Check for track change marks on text nodes\n if (node.type === 'text' && node.marks) {\n const trackMark = findTrackChangeMark(node.marks);\n if (trackMark) {\n const change = createEnrichedChange(node, trackMark, context);\n if (change) changes.push(change);\n }\n }\n\n // Recurse into children\n if (node.content && Array.isArray(node.content)) {\n for (const child of node.content) {\n traverseDocument(child, context, changes);\n }\n }\n}\n\n/**\n * Extract ALL text from a node (including deleted text, for context)\n */\nfunction extractAllText(node: ProseMirrorNode): string {\n if (!node) return '';\n if (node.type === 'text') {\n return node.text || '';\n }\n if (node.content && Array.isArray(node.content)) {\n return node.content.map(extractAllText).join('');\n }\n return '';\n}\n\n/**\n * Find trackInsert, trackDelete, or trackFormat mark\n */\nfunction findTrackChangeMark(marks: ProseMirrorNode[]): ProseMirrorNode | null {\n return (\n marks.find(\n (m) =>\n m.type === 'trackInsert' || m.type === 'trackDelete' || m.type === 'trackFormat'\n ) || null\n );\n}\n\n/**\n * Create enriched change from node and track mark\n */\nfunction createEnrichedChange(\n node: ProseMirrorNode,\n trackMark: ProseMirrorNode,\n context: TraversalContext\n): EnrichedChange | null {\n const text = node.text || '';\n const location = buildLocation(context);\n const surroundingText = extractSurroundingSentence(text, context.currentParagraphText);\n\n if (trackMark.type === 'trackInsert') {\n return {\n type: 'insertion',\n text,\n location,\n surroundingText,\n charCount: text.length,\n };\n }\n\n if (trackMark.type === 'trackDelete') {\n return {\n type: 'deletion',\n text,\n location,\n surroundingText,\n charCount: text.length,\n };\n }\n\n if (trackMark.type === 'trackFormat') {\n const before = trackMark.attrs?.before || [];\n const after = trackMark.attrs?.after || [];\n return {\n type: 'format',\n text,\n location,\n surroundingText,\n formatDetails: {\n added: after\n .map((m: ProseMirrorNode) => m.type)\n .filter((t: string) => !before.some((b: ProseMirrorNode) => b.type === t)),\n removed: before\n .map((m: ProseMirrorNode) => m.type)\n .filter((t: string) => !after.some((a: ProseMirrorNode) => a.type === t)),\n },\n charCount: text.length,\n };\n }\n\n return null;\n}\n\n/**\n * Extract the sentence or clause containing the changed text\n */\nfunction extractSurroundingSentence(changedText: string, paragraphText: string): string {\n if (!paragraphText || !changedText) return '';\n\n // Find where the change is in the paragraph\n const changeIndex = paragraphText.indexOf(changedText);\n if (changeIndex === -1) {\n // If exact match not found, return truncated paragraph\n return truncate(paragraphText, 150);\n }\n\n // Split into sentences (by period, semicolon, or significant punctuation)\n // But keep the delimiters for context\n const sentenceBreaks = /([.;!?]\\s+)/g;\n const sentences: { text: string; start: number; end: number }[] = [];\n\n let lastEnd = 0;\n let match;\n\n while ((match = sentenceBreaks.exec(paragraphText)) !== null) {\n sentences.push({\n text: paragraphText.slice(lastEnd, match.index + match[0].length).trim(),\n start: lastEnd,\n end: match.index + match[0].length,\n });\n lastEnd = match.index + match[0].length;\n }\n\n // Add remaining text as final sentence\n if (lastEnd < paragraphText.length) {\n sentences.push({\n text: paragraphText.slice(lastEnd).trim(),\n start: lastEnd,\n end: paragraphText.length,\n });\n }\n\n // Find which sentence contains the change\n const changeEnd = changeIndex + changedText.length;\n for (const sentence of sentences) {\n if (changeIndex >= sentence.start && changeIndex < sentence.end) {\n // Found it - return this sentence (truncated if too long)\n return truncate(sentence.text, 200);\n }\n }\n\n // Fallback: return a window around the change\n const windowSize = 100;\n const start = Math.max(0, changeIndex - windowSize);\n const end = Math.min(paragraphText.length, changeEnd + windowSize);\n\n let result = paragraphText.slice(start, end);\n if (start > 0) result = '...' + result;\n if (end < paragraphText.length) result = result + '...';\n\n return result;\n}\n\n/**\n * Truncate text with ellipsis\n */\nfunction truncate(text: string, maxLen: number): string {\n if (!text) return '';\n const cleaned = text.replace(/\\s+/g, ' ').trim();\n if (cleaned.length <= maxLen) return cleaned;\n return cleaned.slice(0, maxLen - 3).trim() + '...';\n}\n\n/**\n * Build location info\n */\nfunction buildLocation(context: TraversalContext): ChangeLocation {\n const nodeType = context.currentNodeType as ChangeLocation['nodeType'];\n\n let description: string;\n if (nodeType === 'heading') {\n description = context.headingLevel === 1 ? 'document title' : 'section heading';\n } else if (context.currentSection) {\n description = `\"${truncate(context.currentSection, 50)}\" section`;\n } else {\n description = 'document body';\n }\n\n return {\n nodeType,\n headingLevel: context.headingLevel,\n sectionTitle: context.currentSection || undefined,\n description,\n };\n}\n\n/**\n * Combine adjacent delete+insert into replacements\n */\nfunction groupReplacements(changes: EnrichedChange[]): EnrichedChange[] {\n const result: EnrichedChange[] = [];\n let i = 0;\n\n while (i < changes.length) {\n const current = changes[i];\n const next = changes[i + 1];\n\n // Check if delete followed by insert (same section = likely replacement)\n if (\n current.type === 'deletion' &&\n next?.type === 'insertion' &&\n current.location.sectionTitle === next.location.sectionTitle\n ) {\n result.push({\n type: 'replacement',\n oldText: current.text,\n newText: next.text,\n location: current.location,\n surroundingText: current.surroundingText || next.surroundingText,\n charCount: (current.charCount || 0) + (next.charCount || 0),\n });\n i += 2;\n } else {\n result.push(current);\n i++;\n }\n }\n\n return result;\n}\n\n","/**\n * DocxDiffEditor Component\n *\n * A React component for DOCX document comparison with track changes visualization.\n * Wraps SuperDoc editor and provides methods for setting source, comparing documents,\n * and extracting change context for LLM processing.\n */\n\nimport {\n useCallback,\n useRef,\n useState,\n useEffect,\n useImperativeHandle,\n forwardRef,\n} from 'react';\n\nimport type {\n DocxDiffEditorProps,\n DocxDiffEditorRef,\n DocxContent,\n ProseMirrorJSON,\n SuperDocInstance,\n DiffSegment,\n DiffResult,\n ComparisonResult,\n EnrichedChange,\n} from './types';\n\nimport { parseDocxFile, detectContentType, isProseMirrorJSON } from './services/contentResolver';\nimport { diffDocuments } from './services/documentDiffer';\nimport { mergeDocuments } from './services/mergeDocuments';\nimport { extractEnrichedChanges } from './services/changeContextExtractor';\nimport { DEFAULT_AUTHOR, DEFAULT_SUPERDOC_USER, TRACK_CHANGE_PERMISSIONS, TIMEOUTS } from './constants';\n\n/**\n * Permission resolver that allows accepting/rejecting all track changes\n */\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\nconst permissionResolver = ({ permission }: any) => {\n return TRACK_CHANGE_PERMISSIONS.includes(permission) ? true : undefined;\n};\n\n/**\n * DocxDiffEditor Component\n */\nexport const DocxDiffEditor = forwardRef<DocxDiffEditorRef, DocxDiffEditorProps>(\n function DocxDiffEditor(\n {\n initialSource,\n templateDocx,\n showRulers = false,\n showToolbar = true,\n author = DEFAULT_AUTHOR,\n onReady,\n onSourceLoaded,\n onComparisonComplete,\n onError,\n className = '',\n toolbarClassName = '',\n editorClassName = '',\n },\n ref\n ) {\n // Refs\n const containerRef = useRef<HTMLDivElement>(null);\n const toolbarRef = useRef<HTMLDivElement>(null);\n const superdocRef = useRef<SuperDocInstance | null>(null);\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const SuperDocRef = useRef<any>(null);\n const mountedRef = useRef(true);\n const initRef = useRef(false);\n const readyRef = useRef(false);\n\n // State\n const [isLoading, setIsLoading] = useState(true);\n const [error, setError] = useState<string | null>(null);\n const [sourceJson, setSourceJson] = useState<ProseMirrorJSON | null>(null);\n const [mergedJson, setMergedJson] = useState<ProseMirrorJSON | null>(null);\n const [diffResult, setDiffResult] = useState<DiffResult | null>(null);\n\n // Generate unique IDs for this instance\n const instanceId = useRef(`dde-${Date.now()}-${Math.random().toString(36).substr(2, 9)}`);\n const editorId = `dde-editor-${instanceId.current}`;\n const toolbarId = `dde-toolbar-${instanceId.current}`;\n\n /**\n * Set content in the editor using available methods\n * Used only for JSON content and merged documents\n */\n const setEditorContent = useCallback((editor: SuperDocInstance, json: ProseMirrorJSON) => {\n if (editor.commands?.setContent) {\n editor.commands.setContent(json);\n } else if (editor.setContent) {\n editor.setContent(json);\n } else {\n const { state, view } = editor;\n if (state?.doc && view && json.content) {\n const newDoc = state.schema.nodeFromJSON(json);\n const tr = state.tr.replaceWith(0, state.doc.content.size, newDoc.content);\n view.dispatch(tr);\n }\n }\n }, []);\n\n /**\n * Enable track changes review mode\n */\n const enableReviewMode = useCallback((sd: SuperDocInstance) => {\n if (sd.setTrackedChangesPreferences) {\n sd.setTrackedChangesPreferences({ mode: 'review', enabled: true });\n } else if (sd.activeEditor?.commands?.enableTrackChanges) {\n sd.activeEditor.commands.enableTrackChanges();\n }\n }, []);\n\n /**\n * Set editing mode (normal mode - shows original without track changes)\n */\n const setEditingMode = useCallback((sd: SuperDocInstance) => {\n if (sd.setTrackedChangesPreferences) {\n // Use 'simple' mode with track changes disabled for clean editing view\n // Valid modes are: 'review', 'simple', 'original'\n sd.setTrackedChangesPreferences({ mode: 'simple', enabled: false });\n }\n }, []);\n\n /**\n * Handle errors\n */\n const handleError = useCallback(\n (err: Error | string) => {\n const error = err instanceof Error ? err : new Error(err);\n setError(error.message);\n onError?.(error);\n },\n [onError]\n );\n\n /**\n * Destroy current SuperDoc instance\n */\n const destroySuperdoc = useCallback(() => {\n if (superdocRef.current) {\n try {\n superdocRef.current.destroy?.();\n } catch {\n // Ignore cleanup errors\n }\n superdocRef.current = null;\n }\n readyRef.current = false;\n }, []);\n\n /**\n * Create a new SuperDoc instance with the given options\n */\n const createSuperdoc = useCallback(\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n async (options: { document?: File; html?: string }): Promise<{ superdoc: SuperDocInstance; json: ProseMirrorJSON }> => {\n if (!SuperDocRef.current) {\n throw new Error('SuperDoc not loaded');\n }\n if (!containerRef.current) {\n throw new Error('Container not available');\n }\n\n // Set IDs on DOM elements\n containerRef.current.id = editorId;\n if (toolbarRef.current) {\n toolbarRef.current.id = toolbarId;\n }\n\n return new Promise((resolve, reject) => {\n try {\n const superdoc = new SuperDocRef.current({\n selector: `#${editorId}`,\n toolbar: showToolbar ? `#${toolbarId}` : undefined,\n document: options.document,\n html: options.html,\n documentMode: 'editing',\n role: 'editor',\n rulers: showRulers,\n user: DEFAULT_SUPERDOC_USER,\n permissionResolver,\n // Enable comments module for track changes sidebar\n modules: { comments: {} },\n onReady: ({ superdoc: sd }: { superdoc: SuperDocInstance }) => {\n superdocRef.current = sd;\n readyRef.current = true;\n\n // Extract JSON from the loaded document\n let json: ProseMirrorJSON = { type: 'doc', content: [] };\n if (sd?.activeEditor) {\n try {\n json = sd.activeEditor.getJSON();\n } catch (err) {\n console.error('Failed to extract JSON:', err);\n }\n }\n\n resolve({ superdoc: sd, json });\n },\n onException: ({ error: err }: { error: Error }) => {\n console.error('SuperDoc error:', err);\n reject(err);\n },\n });\n\n superdocRef.current = superdoc;\n\n // Timeout\n setTimeout(() => {\n if (!readyRef.current) {\n reject(new Error('SuperDoc initialization timed out'));\n }\n }, TIMEOUTS.PARSE_TIMEOUT);\n } catch (err) {\n reject(err);\n }\n });\n },\n [editorId, toolbarId, showToolbar, showRulers]\n );\n\n /**\n * Initialize SuperDoc instance\n */\n const initialize = useCallback(async () => {\n if (initRef.current || !containerRef.current || !mountedRef.current) return;\n if (!showToolbar && !toolbarRef.current) {\n // Continue without toolbar\n } else if (showToolbar && !toolbarRef.current) {\n return;\n }\n\n initRef.current = true;\n\n // Small delay for React to settle\n await new Promise((resolve) => setTimeout(resolve, TIMEOUTS.INIT_DELAY));\n\n if (!mountedRef.current || !containerRef.current) {\n initRef.current = false;\n return;\n }\n\n setIsLoading(true);\n setError(null);\n destroySuperdoc();\n\n try {\n // Note: superdoc CSS is bundled in dist/styles.css - user must import 'docx-diff-editor/styles.css'\n const { SuperDoc } = await import('superdoc');\n SuperDocRef.current = SuperDoc;\n\n // Determine initialization options based on initialSource\n let initOptions: { document?: File; html?: string } = {};\n\n if (initialSource) {\n const contentType = detectContentType(initialSource);\n if (contentType === 'file') {\n initOptions = { document: initialSource as File };\n } else if (contentType === 'html') {\n // Initialize directly with HTML - SuperDoc creates blank document internally\n initOptions = { html: initialSource as string };\n } else if (contentType === 'json') {\n // For JSON, we need a document first, then set content\n // Use template if provided, otherwise SuperDoc will create blank\n initOptions = templateDocx ? { document: templateDocx } : {};\n }\n } else if (templateDocx) {\n initOptions = { document: templateDocx };\n }\n // If no initialSource and no template, SuperDoc creates a blank document\n\n const { superdoc: sd, json } = await createSuperdoc(initOptions);\n\n // For JSON content, set it after initialization\n if (initialSource && detectContentType(initialSource) === 'json') {\n if (sd?.activeEditor && isProseMirrorJSON(initialSource)) {\n setEditorContent(sd.activeEditor, initialSource as ProseMirrorJSON);\n setSourceJson(initialSource as ProseMirrorJSON);\n onSourceLoaded?.(initialSource as ProseMirrorJSON);\n }\n } else {\n setSourceJson(json);\n onSourceLoaded?.(json);\n }\n\n setIsLoading(false);\n onReady?.();\n } catch (err) {\n console.error('Failed to initialize SuperDoc:', err);\n handleError(err instanceof Error ? err : new Error('Failed to load editor'));\n setIsLoading(false);\n }\n\n initRef.current = false;\n }, [\n initialSource,\n showRulers,\n showToolbar,\n templateDocx,\n onReady,\n onSourceLoaded,\n destroySuperdoc,\n createSuperdoc,\n setEditorContent,\n handleError,\n ]);\n\n // Initialize on mount\n useEffect(() => {\n mountedRef.current = true;\n initialize();\n\n return () => {\n mountedRef.current = false;\n destroySuperdoc();\n };\n }, [initialize, destroySuperdoc]);\n\n // =========================================================================\n // Imperative API\n // =========================================================================\n\n useImperativeHandle(\n ref,\n () => ({\n /**\n * Set the source/base document\n */\n async setSource(content: DocxContent): Promise<void> {\n if (!SuperDocRef.current) {\n throw new Error('Editor not initialized');\n }\n\n setIsLoading(true);\n setError(null);\n\n try {\n const contentType = detectContentType(content);\n let json: ProseMirrorJSON;\n\n // Destroy current instance and create new one\n destroySuperdoc();\n\n if (contentType === 'file') {\n // Initialize with DOCX file\n const result = await createSuperdoc({ document: content as File });\n json = result.json;\n } else if (contentType === 'html') {\n // Initialize directly with HTML - no template needed!\n // SuperDoc will create a blank document and apply HTML internally\n const result = await createSuperdoc({ html: content as string });\n json = result.json;\n } else {\n // JSON content - initialize blank then set content\n const result = await createSuperdoc(templateDocx ? { document: templateDocx } : {});\n if (result.superdoc?.activeEditor && isProseMirrorJSON(content)) {\n setEditorContent(result.superdoc.activeEditor, content as ProseMirrorJSON);\n json = content as ProseMirrorJSON;\n } else {\n json = result.json;\n }\n }\n\n setSourceJson(json);\n setMergedJson(null);\n setDiffResult(null);\n setEditingMode(superdocRef.current!);\n onSourceLoaded?.(json);\n } catch (err) {\n handleError(err instanceof Error ? err : new Error('Failed to set source'));\n throw err;\n } finally {\n setIsLoading(false);\n }\n },\n\n /**\n * Compare source with new content, show track changes\n */\n async compareWith(content: DocxContent): Promise<ComparisonResult> {\n if (!SuperDocRef.current) {\n throw new Error('Editor not initialized');\n }\n if (!sourceJson) {\n throw new Error('No source document set. Call setSource() first.');\n }\n\n setIsLoading(true);\n try {\n const contentType = detectContentType(content);\n let newJson: ProseMirrorJSON;\n\n if (contentType === 'file') {\n // Parse DOCX file using hidden SuperDoc instance\n newJson = await parseDocxFile(content as File, SuperDocRef.current);\n } else if (contentType === 'html') {\n // Parse HTML using a temporary SuperDoc instance\n const tempContainer = document.createElement('div');\n tempContainer.style.cssText = 'position:absolute;top:-9999px;left:-9999px;width:800px;height:600px;visibility:hidden;';\n document.body.appendChild(tempContainer);\n\n try {\n newJson = await new Promise((resolve, reject) => {\n const tempSuperdoc = new SuperDocRef.current({\n selector: tempContainer,\n html: content as string,\n documentMode: 'viewing',\n rulers: false,\n user: { name: 'Parser', email: 'parser@local' },\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n onReady: ({ superdoc: sd }: { superdoc: any }) => {\n try {\n const json = sd?.activeEditor?.getJSON() || { type: 'doc', content: [] };\n setTimeout(() => {\n try { sd?.destroy?.(); } catch { /* ignore */ }\n tempContainer.parentNode?.removeChild(tempContainer);\n }, 100);\n resolve(json);\n } catch (err) {\n reject(err);\n }\n },\n onException: ({ error: err }: { error: Error }) => {\n tempContainer.parentNode?.removeChild(tempContainer);\n reject(err);\n },\n });\n\n setTimeout(() => {\n try { tempSuperdoc?.destroy?.(); } catch { /* ignore */ }\n tempContainer.parentNode?.removeChild(tempContainer);\n reject(new Error('HTML parsing timed out'));\n }, TIMEOUTS.PARSE_TIMEOUT);\n });\n } catch (err) {\n tempContainer.parentNode?.removeChild(tempContainer);\n throw err;\n }\n } else {\n // JSON content - use directly\n if (!isProseMirrorJSON(content)) {\n throw new Error('Invalid ProseMirror JSON structure');\n }\n newJson = content as ProseMirrorJSON;\n }\n\n // Diff the documents\n const diff = diffDocuments(sourceJson, newJson);\n setDiffResult(diff);\n\n // Merge with track changes\n const merged = mergeDocuments(sourceJson, newJson, diff, author);\n setMergedJson(merged);\n\n // Update editor with merged content\n if (superdocRef.current?.activeEditor) {\n // Switch to suggesting mode to enable track bubbles sidebar\n if (superdocRef.current.setDocumentMode) {\n superdocRef.current.setDocumentMode('suggesting');\n }\n setEditorContent(superdocRef.current.activeEditor, merged);\n enableReviewMode(superdocRef.current);\n }\n\n // Build result\n const insertions = diff.segments.filter((s) => s.type === 'insert').length;\n const deletions = diff.segments.filter((s) => s.type === 'delete').length;\n const formatChanges = diff.formatChanges?.length || 0;\n\n const result: ComparisonResult = {\n totalChanges: insertions + deletions + formatChanges,\n insertions,\n deletions,\n formatChanges,\n summary: diff.summary,\n mergedJson: merged,\n };\n\n onComparisonComplete?.(result);\n return result;\n } catch (err) {\n handleError(err instanceof Error ? err : new Error('Comparison failed'));\n throw err;\n } finally {\n setIsLoading(false);\n }\n },\n\n /**\n * Get raw diff segments\n */\n getDiffSegments(): DiffSegment[] {\n return diffResult?.segments || [];\n },\n\n /**\n * Get enriched changes with context for LLM processing\n */\n getEnrichedChangesContext(): EnrichedChange[] {\n if (!mergedJson) return [];\n return extractEnrichedChanges(mergedJson);\n },\n\n /**\n * Get current document content as JSON\n */\n getContent(): ProseMirrorJSON {\n if (superdocRef.current?.activeEditor) {\n return superdocRef.current.activeEditor.getJSON();\n }\n return mergedJson || sourceJson || { type: 'doc', content: [] };\n },\n\n /**\n * Get source document JSON (before comparison)\n */\n getSourceContent(): ProseMirrorJSON | null {\n return sourceJson;\n },\n\n /**\n * Export current document to DOCX blob\n */\n async exportDocx(): Promise<Blob> {\n if (!superdocRef.current?.activeEditor) {\n throw new Error('Editor not ready');\n }\n\n const blob = await superdocRef.current.activeEditor.exportDocx({\n isFinalDoc: false,\n });\n\n if (!blob) {\n throw new Error('Export returned no data');\n }\n\n return blob;\n },\n\n /**\n * Reset to source state (clear comparison)\n */\n resetComparison(): void {\n if (sourceJson && superdocRef.current?.activeEditor) {\n setEditorContent(superdocRef.current.activeEditor, sourceJson);\n setEditingMode(superdocRef.current);\n setMergedJson(null);\n setDiffResult(null);\n }\n },\n\n /**\n * Check if editor is ready\n */\n isReady(): boolean {\n return readyRef.current;\n },\n }),\n [\n sourceJson,\n mergedJson,\n diffResult,\n templateDocx,\n author,\n destroySuperdoc,\n createSuperdoc,\n setEditorContent,\n enableReviewMode,\n setEditingMode,\n onSourceLoaded,\n onComparisonComplete,\n handleError,\n ]\n );\n\n // =========================================================================\n // Render\n // =========================================================================\n\n return (\n <div className={`dde-container ${className}`.trim()}>\n {/* Loading overlay */}\n {isLoading && (\n <div className=\"dde-loading\">\n <div className=\"dde-loading__spinner\" />\n <p className=\"dde-loading__text\">Loading document...</p>\n </div>\n )}\n\n {/* Error overlay */}\n {error && (\n <div className=\"dde-error\">\n <div className=\"dde-error__icon\">\n <svg\n className=\"dde-error__svg\"\n fill=\"none\"\n stroke=\"currentColor\"\n viewBox=\"0 0 24 24\"\n >\n <path\n strokeLinecap=\"round\"\n strokeLinejoin=\"round\"\n strokeWidth=\"2\"\n d=\"M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z\"\n />\n </svg>\n </div>\n <p className=\"dde-error__title\">Failed to load document</p>\n <p className=\"dde-error__message\">{error}</p>\n </div>\n )}\n\n {/* Toolbar */}\n {showToolbar && (\n <div\n ref={toolbarRef}\n className={`dde-toolbar ${toolbarClassName}`.trim()}\n />\n )}\n\n {/* Editor container */}\n <div\n ref={containerRef}\n className={`dde-editor ${editorClassName}`.trim()}\n />\n </div>\n );\n }\n);\n\nexport default DocxDiffEditor;\n","/**\n * Embedded DOCX template\n *\n * This is a base64-encoded blank DOCX file created with Microsoft Word.\n * It provides the complete schema, styles, themes, and fonts needed to\n * initialize SuperDoc when working with HTML or JSON content.\n *\n * The DOCX contains all standard Word document components:\n * - [Content_Types].xml\n * - _rels/.rels\n * - word/document.xml\n * - word/_rels/document.xml.rels\n * - word/styles.xml (full Word styles)\n * - word/settings.xml\n * - word/fontTable.xml\n * - word/webSettings.xml\n * - word/theme/theme1.xml\n * - docProps/core.xml\n * - docProps/app.xml\n */\n\n/**\n * Base64-encoded blank DOCX file created with Microsoft Word.\n */\nconst BLANK_DOCX_BASE64 = `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`;\n\n/**\n * Convert base64 string to Blob\n */\nfunction base64ToBlob(base64: string, mimeType: string): Blob {\n const byteCharacters = atob(base64.replace(/\\s/g, ''));\n const byteNumbers = new Array(byteCharacters.length);\n\n for (let i = 0; i < byteCharacters.length; i++) {\n byteNumbers[i] = byteCharacters.charCodeAt(i);\n }\n\n const byteArray = new Uint8Array(byteNumbers);\n return new Blob([byteArray], { type: mimeType });\n}\n\n/**\n * Convert base64 string to File\n */\nfunction base64ToFile(base64: string, filename: string, mimeType: string): File {\n const blob = base64ToBlob(base64, mimeType);\n return new File([blob], filename, { type: mimeType });\n}\n\n/**\n * Get the blank DOCX template as a File object\n */\nexport function getBlankTemplateFile(): File {\n return base64ToFile(\n BLANK_DOCX_BASE64,\n 'blank-template.docx',\n 'application/vnd.openxmlformats-officedocument.wordprocessingml.document'\n );\n}\n\n/**\n * Get the blank DOCX template as a Blob\n */\nexport function getBlankTemplateBlob(): Blob {\n return base64ToBlob(\n BLANK_DOCX_BASE64,\n 'application/vnd.openxmlformats-officedocument.wordprocessingml.document'\n );\n}\n\n/**\n * Check if a File is a valid DOCX file (basic check)\n */\nexport function isValidDocxFile(file: File): boolean {\n const validTypes = [\n 'application/vnd.openxmlformats-officedocument.wordprocessingml.document',\n 'application/msword',\n ];\n return validTypes.includes(file.type) || file.name.endsWith('.docx');\n}\n"]}
package/dist/index.mjs CHANGED
@@ -740,6 +740,8 @@ var DocxDiffEditor = forwardRef(
740
740
  rulers: showRulers,
741
741
  user: DEFAULT_SUPERDOC_USER,
742
742
  permissionResolver,
743
+ // Enable comments module for track changes sidebar
744
+ modules: { comments: {} },
743
745
  onReady: ({ superdoc: sd }) => {
744
746
  superdocRef.current = sd;
745
747
  readyRef.current = true;
@@ -956,6 +958,9 @@ var DocxDiffEditor = forwardRef(
956
958
  const merged = mergeDocuments(sourceJson, newJson, diff, author);
957
959
  setMergedJson(merged);
958
960
  if (superdocRef.current?.activeEditor) {
961
+ if (superdocRef.current.setDocumentMode) {
962
+ superdocRef.current.setDocumentMode("suggesting");
963
+ }
959
964
  setEditorContent(superdocRef.current.activeEditor, merged);
960
965
  enableReviewMode(superdocRef.current);
961
966
  }
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/constants.ts","../src/services/contentResolver.ts","../src/services/documentDiffer.ts","../src/services/trackChangeInjector.ts","../src/services/mergeDocuments.ts","../src/services/changeContextExtractor.ts","../src/DocxDiffEditor.tsx","../src/blankTemplate.ts"],"names":["uuidv4","DocxDiffEditor","error"],"mappings":"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","file":"index.mjs","sourcesContent":["/**\n * Constants for DocxDiffEditor\n */\n\nimport type { TrackChangeAuthor } from './types';\n\n/**\n * Default author for track changes\n */\nexport const DEFAULT_AUTHOR: TrackChangeAuthor = {\n name: 'DocxDiff Editor',\n email: 'editor@docxdiff.local',\n};\n\n/**\n * Default SuperDoc user (used for editor initialization)\n */\nexport const DEFAULT_SUPERDOC_USER = {\n name: 'DocxDiff User',\n email: 'user@docxdiff.local',\n};\n\n/**\n * Permissions allowed for track change resolution\n */\nexport const TRACK_CHANGE_PERMISSIONS = [\n 'RESOLVE_OWN',\n 'RESOLVE_OTHER',\n 'REJECT_OWN',\n 'REJECT_OTHER',\n];\n\n/**\n * CSS class prefix for all component styles\n */\nexport const CSS_PREFIX = 'dde';\n\n/**\n * Timeouts\n */\nexport const TIMEOUTS = {\n /** Timeout for document parsing (ms) */\n PARSE_TIMEOUT: 30000,\n /** Small delay for React settling (ms) */\n INIT_DELAY: 100,\n /** Cleanup delay (ms) */\n CLEANUP_DELAY: 100,\n};\n\n","/**\n * Content Resolver Service\n * Detects content type and parses DOCX files to ProseMirror JSON.\n *\n * Supports three input formats:\n * - File: DOCX file parsed by SuperDoc\n * - string: HTML content (handled directly by SuperDoc in the component)\n * - object: Direct ProseMirror JSON (passed through)\n */\n\nimport type { DocxContent, ProseMirrorJSON } from '../types';\nimport { TIMEOUTS } from '../constants';\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\ntype SuperDocConstructor = any;\n\n/**\n * Detect the type of content provided\n */\nexport function detectContentType(content: DocxContent): 'file' | 'html' | 'json' {\n if (content instanceof File) {\n return 'file';\n }\n if (typeof content === 'string') {\n return 'html';\n }\n // Assume it's JSON if it's an object\n return 'json';\n}\n\n/**\n * Validate that content looks like ProseMirror JSON\n */\nexport function isProseMirrorJSON(content: unknown): boolean {\n if (!content || typeof content !== 'object') return false;\n const obj = content as Record<string, unknown>;\n return typeof obj.type === 'string' && (obj.type === 'doc' || Array.isArray(obj.content));\n}\n\n/**\n * Parse a DOCX File into ProseMirror JSON using a hidden SuperDoc instance.\n */\nexport async function parseDocxFile(\n file: File,\n SuperDoc: SuperDocConstructor\n): Promise<ProseMirrorJSON> {\n // Create a hidden container for the editor\n const container = document.createElement('div');\n container.style.cssText =\n 'position:absolute;top:-9999px;left:-9999px;width:800px;height:600px;visibility:hidden;';\n document.body.appendChild(container);\n\n return new Promise((resolve, reject) => {\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n let superdoc: any = null;\n let resolved = false;\n\n const cleanup = () => {\n setTimeout(() => {\n if (superdoc) {\n try {\n const sd = superdoc;\n superdoc = null;\n sd.destroy?.();\n } catch {\n // Ignore cleanup errors\n }\n }\n if (container.parentNode) {\n container.parentNode.removeChild(container);\n }\n }, TIMEOUTS.CLEANUP_DELAY);\n };\n\n setTimeout(async () => {\n if (resolved) return;\n\n try {\n superdoc = new SuperDoc({\n selector: container,\n document: file,\n documentMode: 'viewing',\n rulers: false,\n user: { name: 'Parser', email: 'parser@local' },\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n onReady: ({ superdoc: sd }: { superdoc: any }) => {\n if (resolved) return;\n try {\n const editor = sd?.activeEditor;\n if (!editor) {\n throw new Error('No active editor found');\n }\n\n const json = editor.getJSON();\n resolved = true;\n cleanup();\n resolve(json);\n } catch (err) {\n resolved = true;\n cleanup();\n reject(err);\n }\n },\n onException: ({ error: err }: { error: Error }) => {\n if (resolved) return;\n resolved = true;\n cleanup();\n reject(err);\n },\n });\n\n // Timeout\n setTimeout(() => {\n if (!resolved) {\n resolved = true;\n cleanup();\n reject(new Error('Document parsing timed out'));\n }\n }, TIMEOUTS.PARSE_TIMEOUT);\n } catch (err) {\n cleanup();\n reject(err);\n }\n }, 50);\n });\n}\n","/**\n * Document Differ Service\n * Diffs two ProseMirror JSON documents at the character level,\n * including text changes and formatting changes.\n */\n\nimport DiffMatchPatch from 'diff-match-patch';\nimport type {\n ProseMirrorJSON,\n ProseMirrorMark,\n DiffSegment,\n DiffResult,\n FormatChange,\n TextSpan,\n} from '../types';\n\nconst dmp = new DiffMatchPatch();\n\n// Diff operation types\nconst DIFF_DELETE = -1;\nconst DIFF_INSERT = 1;\nconst DIFF_EQUAL = 0;\n\n/**\n * Extract text spans with their marks from a ProseMirror node.\n */\nfunction extractTextSpans(node: ProseMirrorJSON, offset: number = 0): TextSpan[] {\n const spans: TextSpan[] = [];\n\n if (!node) return spans;\n\n if (node.type === 'text' && node.text) {\n spans.push({\n text: node.text,\n from: offset,\n to: offset + node.text.length,\n marks: node.marks || [],\n });\n return spans;\n }\n\n if (node.content && Array.isArray(node.content)) {\n let currentOffset = offset;\n for (const child of node.content) {\n const childSpans = extractTextSpans(child, currentOffset);\n spans.push(...childSpans);\n // Calculate consumed length\n for (const span of childSpans) {\n currentOffset = Math.max(currentOffset, span.to);\n }\n // If no spans, check if it's a text node for offset\n if (childSpans.length === 0 && child.type === 'text' && child.text) {\n currentOffset += child.text.length;\n }\n }\n }\n\n return spans;\n}\n\n/**\n * Extract text content from a ProseMirror node recursively.\n */\nfunction extractTextContent(node: ProseMirrorJSON): string {\n if (!node) return '';\n\n if (node.type === 'text' && node.text) {\n return node.text;\n }\n\n if (node.content && Array.isArray(node.content)) {\n return node.content.map(extractTextContent).join('');\n }\n\n return '';\n}\n\n/**\n * Deep compare two values.\n */\nfunction deepEqual(a: unknown, b: unknown): boolean {\n if (a === b) return true;\n if (typeof a !== typeof b) return false;\n if (typeof a !== 'object' || a === null || b === null) return false;\n\n const objA = a as Record<string, unknown>;\n const objB = b as Record<string, unknown>;\n const keysA = Object.keys(objA);\n const keysB = Object.keys(objB);\n\n if (keysA.length !== keysB.length) return false;\n\n for (const key of keysA) {\n if (!keysB.includes(key)) return false;\n if (!deepEqual(objA[key], objB[key])) return false;\n }\n\n return true;\n}\n\n/**\n * Compare marks arrays to check if they're equivalent.\n */\nfunction marksEqual(marksA: ProseMirrorMark[], marksB: ProseMirrorMark[]): boolean {\n if (marksA.length !== marksB.length) return false;\n\n // Sort by type for consistent comparison\n const sortedA = [...marksA].sort((a, b) => (a.type || '').localeCompare(b.type || ''));\n const sortedB = [...marksB].sort((a, b) => (a.type || '').localeCompare(b.type || ''));\n\n return deepEqual(sortedA, sortedB);\n}\n\n/**\n * Get marks at a specific character position from spans.\n */\nfunction getMarksAtPosition(spans: TextSpan[], pos: number): ProseMirrorMark[] {\n for (const span of spans) {\n if (pos >= span.from && pos < span.to) {\n return span.marks;\n }\n }\n return [];\n}\n\n/**\n * Detect format changes on equal text segments.\n */\nfunction detectFormatChanges(\n spansA: TextSpan[],\n spansB: TextSpan[],\n segments: DiffSegment[]\n): FormatChange[] {\n const formatChanges: FormatChange[] = [];\n\n let posA = 0;\n let posB = 0;\n\n for (const segment of segments) {\n if (segment.type === 'equal') {\n // For equal text, compare marks character by character\n // Group consecutive chars with same mark difference\n let i = 0;\n while (i < segment.text.length) {\n const marksA = getMarksAtPosition(spansA, posA + i);\n const marksB = getMarksAtPosition(spansB, posB + i);\n\n if (!marksEqual(marksA, marksB)) {\n // Found a format difference - find the extent\n const startI = i;\n const startMarksA = marksA;\n const startMarksB = marksB;\n\n // Extend while marks remain the same different pattern\n while (i < segment.text.length) {\n const currentMarksA = getMarksAtPosition(spansA, posA + i);\n const currentMarksB = getMarksAtPosition(spansB, posB + i);\n\n if (marksEqual(currentMarksA, startMarksA) && marksEqual(currentMarksB, startMarksB)) {\n i++;\n } else {\n break;\n }\n }\n\n formatChanges.push({\n from: posA + startI,\n to: posA + i,\n text: segment.text.substring(startI, i),\n before: startMarksA,\n after: startMarksB,\n });\n } else {\n i++;\n }\n }\n\n posA += segment.text.length;\n posB += segment.text.length;\n } else if (segment.type === 'delete') {\n // Deleted text exists only in docA, so only advance posA\n posA += segment.text.length;\n } else if (segment.type === 'insert') {\n // Inserted text exists only in docB, so only advance posB\n posB += segment.text.length;\n }\n }\n\n return formatChanges;\n}\n\n/**\n * Diff two ProseMirror JSON documents at the character level.\n * Detects both text changes and formatting changes.\n */\nexport function diffDocuments(\n docA: ProseMirrorJSON,\n docB: ProseMirrorJSON\n): DiffResult {\n // Extract full text from both documents\n const textA = extractTextContent(docA);\n const textB = extractTextContent(docB);\n\n // Perform character-level diff on the entire document\n const diffs = dmp.diff_main(textA, textB);\n dmp.diff_cleanupSemantic(diffs);\n\n // Convert to our DiffSegment format\n const segments: DiffSegment[] = [];\n let insertCount = 0;\n let deleteCount = 0;\n\n for (const [op, text] of diffs) {\n if (op === DIFF_EQUAL) {\n segments.push({ type: 'equal', text });\n } else if (op === DIFF_INSERT) {\n segments.push({ type: 'insert', text });\n insertCount++;\n } else if (op === DIFF_DELETE) {\n segments.push({ type: 'delete', text });\n deleteCount++;\n }\n }\n\n // Extract text spans with marks for format comparison\n const spansA = extractTextSpans(docA);\n const spansB = extractTextSpans(docB);\n\n // Detect format changes on equal segments\n const formatChanges = detectFormatChanges(spansA, spansB, segments);\n\n // Build summary\n const summary: string[] = [];\n if (insertCount > 0) {\n summary.push(`${insertCount} insertion(s)`);\n }\n if (deleteCount > 0) {\n summary.push(`${deleteCount} deletion(s)`);\n }\n if (formatChanges.length > 0) {\n summary.push(`${formatChanges.length} format change(s)`);\n }\n if (insertCount === 0 && deleteCount === 0 && formatChanges.length === 0) {\n summary.push('No changes detected');\n }\n\n return {\n segments,\n formatChanges,\n textA,\n textB,\n summary,\n };\n}\n\n","/**\n * Track Change Injector Service\n * Creates track change marks for insertions, deletions, and format changes.\n */\n\nimport { v4 as uuidv4 } from 'uuid';\nimport type { TrackChangeAuthor, ProseMirrorJSON, ProseMirrorMark } from '../types';\nimport { DEFAULT_AUTHOR } from '../constants';\n\n/**\n * Create a trackInsert mark.\n */\nexport function createTrackInsertMark(author: TrackChangeAuthor = DEFAULT_AUTHOR): ProseMirrorMark {\n return {\n type: 'trackInsert',\n attrs: {\n id: uuidv4(),\n author: author.name,\n authorEmail: author.email,\n authorImage: '',\n date: new Date().toISOString(),\n },\n };\n}\n\n/**\n * Create a trackDelete mark.\n */\nexport function createTrackDeleteMark(author: TrackChangeAuthor = DEFAULT_AUTHOR): ProseMirrorMark {\n return {\n type: 'trackDelete',\n attrs: {\n id: uuidv4(),\n author: author.name,\n authorEmail: author.email,\n authorImage: '',\n date: new Date().toISOString(),\n },\n };\n}\n\n/**\n * Create a trackFormat mark.\n */\nexport function createTrackFormatMark(\n before: ProseMirrorMark[],\n after: ProseMirrorMark[],\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorMark {\n return {\n type: 'trackFormat',\n attrs: {\n id: uuidv4(),\n author: author.name,\n authorEmail: author.email,\n authorImage: '',\n date: new Date().toISOString(),\n before,\n after,\n },\n };\n}\n\n/**\n * Add a mark to a text node, preserving existing marks.\n */\nexport function addMarkToTextNode(\n node: ProseMirrorJSON,\n mark: ProseMirrorMark\n): ProseMirrorJSON {\n if (node.type !== 'text') {\n return node;\n }\n\n return {\n ...node,\n marks: [...(node.marks || []), mark],\n };\n}\n\n/**\n * Create a text node with specific marks.\n */\nexport function createTextNode(\n text: string,\n marks: ProseMirrorMark[] = []\n): ProseMirrorJSON {\n const node: ProseMirrorJSON = {\n type: 'text',\n text,\n };\n\n if (marks.length > 0) {\n node.marks = marks;\n }\n\n return node;\n}\n\n/**\n * Apply trackDelete mark to all text in a node (recursively).\n */\nexport function markAllAsDeleted(\n node: ProseMirrorJSON,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorJSON {\n if (node.type === 'text') {\n return addMarkToTextNode(node, createTrackDeleteMark(author));\n }\n\n if (node.content && Array.isArray(node.content)) {\n return {\n ...node,\n content: node.content.map((child: ProseMirrorJSON) =>\n markAllAsDeleted(child, author)\n ),\n };\n }\n\n return node;\n}\n\n/**\n * Apply trackInsert mark to all text in a node (recursively).\n */\nexport function markAllAsInserted(\n node: ProseMirrorJSON,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorJSON {\n if (node.type === 'text') {\n return addMarkToTextNode(node, createTrackInsertMark(author));\n }\n\n if (node.content && Array.isArray(node.content)) {\n return {\n ...node,\n content: node.content.map((child: ProseMirrorJSON) =>\n markAllAsInserted(child, author)\n ),\n };\n }\n\n return node;\n}\n\n/**\n * Clone a node deeply.\n */\nexport function cloneNode(node: ProseMirrorJSON): ProseMirrorJSON {\n return JSON.parse(JSON.stringify(node));\n}\n\n","/**\n * Merge Documents Service\n * Applies track change marks to the original document structure\n * based on character-level diff segments.\n */\n\nimport type {\n ProseMirrorJSON,\n ProseMirrorNode,\n DiffResult,\n FormatChange,\n TrackChangeAuthor,\n} from '../types';\nimport {\n createTrackInsertMark,\n createTrackDeleteMark,\n createTrackFormatMark,\n} from './trackChangeInjector';\nimport { DEFAULT_AUTHOR } from '../constants';\n\n/**\n * Deep clone a node\n */\nfunction cloneNode(node: ProseMirrorNode): ProseMirrorNode {\n return JSON.parse(JSON.stringify(node));\n}\n\n/**\n * Character state during merge\n */\ninterface CharState {\n type: 'equal' | 'delete' | 'insert';\n insertText?: string;\n}\n\n/**\n * Insertion point during merge\n */\ninterface Insertion {\n afterOffset: number;\n text: string;\n}\n\n/**\n * Build a merged document by applying diff segments to the original structure.\n *\n * Strategy:\n * 1. Clone docA (original)\n * 2. Walk through diff segments\n * 3. For 'equal' segments: keep original content as-is\n * 4. For 'delete' segments: add trackDelete mark to the corresponding text\n * 5. For 'insert' segments: insert new text nodes with trackInsert mark\n */\nexport function mergeDocuments(\n docA: ProseMirrorNode,\n docB: ProseMirrorNode,\n diffResult: DiffResult,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorNode {\n // Clone the original document\n const merged = cloneNode(docA);\n\n // Build a map of character offset -> segment type\n // This tells us for each character what its state is\n const charStates: CharState[] = [];\n let insertions: Insertion[] = [];\n\n // Store format changes as array for range lookups\n const formatChanges: FormatChange[] = diffResult.formatChanges || [];\n\n // Helper to find format change at a position\n function getFormatChangeAt(pos: number): FormatChange | null {\n for (const fc of formatChanges) {\n if (pos >= fc.from && pos < fc.to) {\n return fc;\n }\n }\n return null;\n }\n\n let docAOffset = 0;\n for (const segment of diffResult.segments) {\n if (segment.type === 'equal') {\n // Mark these characters as equal\n for (let i = 0; i < segment.text.length; i++) {\n charStates[docAOffset + i] = { type: 'equal' };\n }\n docAOffset += segment.text.length;\n } else if (segment.type === 'delete') {\n // Mark these characters as deleted\n for (let i = 0; i < segment.text.length; i++) {\n charStates[docAOffset + i] = { type: 'delete' };\n }\n docAOffset += segment.text.length;\n } else if (segment.type === 'insert') {\n // Insert doesn't consume docA characters, it adds new text\n // We need to track where to insert\n insertions.push({\n afterOffset: docAOffset,\n text: segment.text,\n });\n }\n }\n\n // Now we need to transform the document\n // For each text span in the original:\n // 1. Split it based on character states (equal vs delete)\n // 2. Apply trackDelete marks to deleted parts\n // 3. Insert new content where insertions occur\n\n function transformNode(\n node: ProseMirrorNode,\n nodeOffset: number,\n path: number[]\n ): { nodes: ProseMirrorNode[]; consumedLength: number } {\n if (node.type === 'text' && node.text) {\n const text = node.text;\n const result: ProseMirrorNode[] = [];\n let i = 0;\n\n while (i < text.length) {\n const charOffset = nodeOffset + i;\n const charState = charStates[charOffset] || { type: 'equal' };\n\n // Check for insertions at this position\n const insertionsHere = insertions.filter((ins) => ins.afterOffset === charOffset);\n for (const ins of insertionsHere) {\n result.push({\n type: 'text',\n text: ins.text,\n marks: [...(node.marks || []), createTrackInsertMark(author)],\n });\n }\n\n // Find run of same state AND same format change status\n const currentFormatChange = getFormatChangeAt(nodeOffset + i);\n let j = i + 1;\n while (j < text.length) {\n const nextState = charStates[nodeOffset + j] || { type: 'equal' };\n if (nextState.type !== charState.type) break;\n // Also break if there's an insertion point here\n if (insertions.some((ins) => ins.afterOffset === nodeOffset + j)) break;\n // Break if format change status changes\n const nextFormatChange = getFormatChangeAt(nodeOffset + j);\n if (currentFormatChange !== nextFormatChange) break;\n j++;\n }\n\n const chunk = text.substring(i, j);\n let marks = [...(node.marks || [])];\n\n if (charState.type === 'delete') {\n marks.push(createTrackDeleteMark(author));\n } else if (charState.type === 'equal') {\n // Check if there's a format change at this position\n if (currentFormatChange) {\n // For format changes, use the NEW marks (after) plus trackFormat\n const trackFormatMark = createTrackFormatMark(\n currentFormatChange.before,\n currentFormatChange.after,\n author\n );\n marks = [...currentFormatChange.after, trackFormatMark];\n }\n }\n\n result.push({\n type: 'text',\n text: chunk,\n marks: marks.length > 0 ? marks : undefined,\n });\n\n i = j;\n }\n\n // Check for insertions at the end of this text node\n const endOffset = nodeOffset + text.length;\n const endInsertions = insertions.filter((ins) => ins.afterOffset === endOffset);\n for (const ins of endInsertions) {\n result.push({\n type: 'text',\n text: ins.text,\n marks: [...(node.marks || []), createTrackInsertMark(author)],\n });\n }\n\n // Remove processed insertions\n insertions = insertions.filter(\n (ins) => ins.afterOffset < nodeOffset || ins.afterOffset > endOffset\n );\n\n return { nodes: result, consumedLength: text.length };\n }\n\n // Non-text node: recursively transform children\n if (node.content && Array.isArray(node.content)) {\n const newContent: ProseMirrorNode[] = [];\n let offset = nodeOffset;\n\n for (const child of node.content) {\n const { nodes, consumedLength } = transformNode(child, offset, path);\n newContent.push(...nodes);\n offset += consumedLength;\n }\n\n return {\n nodes: [{ ...node, content: newContent }],\n consumedLength: offset - nodeOffset,\n };\n }\n\n // Node without content (like hard break)\n return { nodes: [node], consumedLength: 0 };\n }\n\n // Transform the document content\n if (merged.content && Array.isArray(merged.content)) {\n const newContent: ProseMirrorNode[] = [];\n let offset = 0;\n\n for (let i = 0; i < merged.content.length; i++) {\n const child = merged.content[i];\n const { nodes, consumedLength } = transformNode(child, offset, [i]);\n newContent.push(...nodes);\n offset += consumedLength;\n }\n\n merged.content = newContent;\n }\n\n // Handle any remaining insertions (at the very end)\n if (insertions.length > 0) {\n for (const ins of insertions) {\n const insertNode = {\n type: 'paragraph',\n content: [\n {\n type: 'run',\n content: [\n {\n type: 'text',\n text: ins.text,\n marks: [createTrackInsertMark(author)],\n },\n ],\n },\n ],\n };\n if (!merged.content) merged.content = [];\n merged.content.push(insertNode);\n }\n }\n\n return merged;\n}\n\n/**\n * Export for compatibility\n */\nexport function createSimpleMergedDocument(\n docA: ProseMirrorNode,\n docB: ProseMirrorNode,\n diffResult: DiffResult,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorNode {\n return mergeDocuments(docA, docB, diffResult, author);\n}\n\n","/**\n * Change Context Extractor\n * Extracts enriched changes with semantic context from merged document.\n * Provides surrounding text so the LLM can understand what the change is about.\n */\n\nimport type {\n ProseMirrorJSON,\n ProseMirrorNode,\n EnrichedChange,\n ChangeLocation,\n TraversalContext,\n} from '../types';\n\n/**\n * Main entry point - extract enriched changes from merged document\n */\nexport function extractEnrichedChanges(mergedJson: ProseMirrorJSON): EnrichedChange[] {\n const changes: EnrichedChange[] = [];\n const context: TraversalContext = {\n currentSection: null,\n currentParagraphText: '',\n currentNodeType: 'unknown',\n };\n\n traverseDocument(mergedJson, context, changes);\n return groupReplacements(changes);\n}\n\n/**\n * Recursively walk the document tree\n */\nfunction traverseDocument(\n node: ProseMirrorNode,\n context: TraversalContext,\n changes: EnrichedChange[]\n): void {\n if (!node) return;\n\n // Update context based on node type\n if (node.type === 'heading') {\n context.currentSection = extractAllText(node);\n context.headingLevel = node.attrs?.level || 1;\n context.currentNodeType = 'heading';\n context.currentParagraphText = context.currentSection;\n } else if (node.type === 'paragraph') {\n context.currentNodeType = 'paragraph';\n context.currentParagraphText = extractAllText(node);\n } else if (node.type === 'listItem') {\n context.currentNodeType = 'listItem';\n context.currentParagraphText = extractAllText(node);\n } else if (node.type === 'tableCell') {\n context.currentNodeType = 'tableCell';\n context.currentParagraphText = extractAllText(node);\n }\n\n // Check for track change marks on text nodes\n if (node.type === 'text' && node.marks) {\n const trackMark = findTrackChangeMark(node.marks);\n if (trackMark) {\n const change = createEnrichedChange(node, trackMark, context);\n if (change) changes.push(change);\n }\n }\n\n // Recurse into children\n if (node.content && Array.isArray(node.content)) {\n for (const child of node.content) {\n traverseDocument(child, context, changes);\n }\n }\n}\n\n/**\n * Extract ALL text from a node (including deleted text, for context)\n */\nfunction extractAllText(node: ProseMirrorNode): string {\n if (!node) return '';\n if (node.type === 'text') {\n return node.text || '';\n }\n if (node.content && Array.isArray(node.content)) {\n return node.content.map(extractAllText).join('');\n }\n return '';\n}\n\n/**\n * Find trackInsert, trackDelete, or trackFormat mark\n */\nfunction findTrackChangeMark(marks: ProseMirrorNode[]): ProseMirrorNode | null {\n return (\n marks.find(\n (m) =>\n m.type === 'trackInsert' || m.type === 'trackDelete' || m.type === 'trackFormat'\n ) || null\n );\n}\n\n/**\n * Create enriched change from node and track mark\n */\nfunction createEnrichedChange(\n node: ProseMirrorNode,\n trackMark: ProseMirrorNode,\n context: TraversalContext\n): EnrichedChange | null {\n const text = node.text || '';\n const location = buildLocation(context);\n const surroundingText = extractSurroundingSentence(text, context.currentParagraphText);\n\n if (trackMark.type === 'trackInsert') {\n return {\n type: 'insertion',\n text,\n location,\n surroundingText,\n charCount: text.length,\n };\n }\n\n if (trackMark.type === 'trackDelete') {\n return {\n type: 'deletion',\n text,\n location,\n surroundingText,\n charCount: text.length,\n };\n }\n\n if (trackMark.type === 'trackFormat') {\n const before = trackMark.attrs?.before || [];\n const after = trackMark.attrs?.after || [];\n return {\n type: 'format',\n text,\n location,\n surroundingText,\n formatDetails: {\n added: after\n .map((m: ProseMirrorNode) => m.type)\n .filter((t: string) => !before.some((b: ProseMirrorNode) => b.type === t)),\n removed: before\n .map((m: ProseMirrorNode) => m.type)\n .filter((t: string) => !after.some((a: ProseMirrorNode) => a.type === t)),\n },\n charCount: text.length,\n };\n }\n\n return null;\n}\n\n/**\n * Extract the sentence or clause containing the changed text\n */\nfunction extractSurroundingSentence(changedText: string, paragraphText: string): string {\n if (!paragraphText || !changedText) return '';\n\n // Find where the change is in the paragraph\n const changeIndex = paragraphText.indexOf(changedText);\n if (changeIndex === -1) {\n // If exact match not found, return truncated paragraph\n return truncate(paragraphText, 150);\n }\n\n // Split into sentences (by period, semicolon, or significant punctuation)\n // But keep the delimiters for context\n const sentenceBreaks = /([.;!?]\\s+)/g;\n const sentences: { text: string; start: number; end: number }[] = [];\n\n let lastEnd = 0;\n let match;\n\n while ((match = sentenceBreaks.exec(paragraphText)) !== null) {\n sentences.push({\n text: paragraphText.slice(lastEnd, match.index + match[0].length).trim(),\n start: lastEnd,\n end: match.index + match[0].length,\n });\n lastEnd = match.index + match[0].length;\n }\n\n // Add remaining text as final sentence\n if (lastEnd < paragraphText.length) {\n sentences.push({\n text: paragraphText.slice(lastEnd).trim(),\n start: lastEnd,\n end: paragraphText.length,\n });\n }\n\n // Find which sentence contains the change\n const changeEnd = changeIndex + changedText.length;\n for (const sentence of sentences) {\n if (changeIndex >= sentence.start && changeIndex < sentence.end) {\n // Found it - return this sentence (truncated if too long)\n return truncate(sentence.text, 200);\n }\n }\n\n // Fallback: return a window around the change\n const windowSize = 100;\n const start = Math.max(0, changeIndex - windowSize);\n const end = Math.min(paragraphText.length, changeEnd + windowSize);\n\n let result = paragraphText.slice(start, end);\n if (start > 0) result = '...' + result;\n if (end < paragraphText.length) result = result + '...';\n\n return result;\n}\n\n/**\n * Truncate text with ellipsis\n */\nfunction truncate(text: string, maxLen: number): string {\n if (!text) return '';\n const cleaned = text.replace(/\\s+/g, ' ').trim();\n if (cleaned.length <= maxLen) return cleaned;\n return cleaned.slice(0, maxLen - 3).trim() + '...';\n}\n\n/**\n * Build location info\n */\nfunction buildLocation(context: TraversalContext): ChangeLocation {\n const nodeType = context.currentNodeType as ChangeLocation['nodeType'];\n\n let description: string;\n if (nodeType === 'heading') {\n description = context.headingLevel === 1 ? 'document title' : 'section heading';\n } else if (context.currentSection) {\n description = `\"${truncate(context.currentSection, 50)}\" section`;\n } else {\n description = 'document body';\n }\n\n return {\n nodeType,\n headingLevel: context.headingLevel,\n sectionTitle: context.currentSection || undefined,\n description,\n };\n}\n\n/**\n * Combine adjacent delete+insert into replacements\n */\nfunction groupReplacements(changes: EnrichedChange[]): EnrichedChange[] {\n const result: EnrichedChange[] = [];\n let i = 0;\n\n while (i < changes.length) {\n const current = changes[i];\n const next = changes[i + 1];\n\n // Check if delete followed by insert (same section = likely replacement)\n if (\n current.type === 'deletion' &&\n next?.type === 'insertion' &&\n current.location.sectionTitle === next.location.sectionTitle\n ) {\n result.push({\n type: 'replacement',\n oldText: current.text,\n newText: next.text,\n location: current.location,\n surroundingText: current.surroundingText || next.surroundingText,\n charCount: (current.charCount || 0) + (next.charCount || 0),\n });\n i += 2;\n } else {\n result.push(current);\n i++;\n }\n }\n\n return result;\n}\n\n","/**\n * DocxDiffEditor Component\n *\n * A React component for DOCX document comparison with track changes visualization.\n * Wraps SuperDoc editor and provides methods for setting source, comparing documents,\n * and extracting change context for LLM processing.\n */\n\nimport {\n useCallback,\n useRef,\n useState,\n useEffect,\n useImperativeHandle,\n forwardRef,\n} from 'react';\n\nimport type {\n DocxDiffEditorProps,\n DocxDiffEditorRef,\n DocxContent,\n ProseMirrorJSON,\n SuperDocInstance,\n DiffSegment,\n DiffResult,\n ComparisonResult,\n EnrichedChange,\n} from './types';\n\nimport { parseDocxFile, detectContentType, isProseMirrorJSON } from './services/contentResolver';\nimport { diffDocuments } from './services/documentDiffer';\nimport { mergeDocuments } from './services/mergeDocuments';\nimport { extractEnrichedChanges } from './services/changeContextExtractor';\nimport { DEFAULT_AUTHOR, DEFAULT_SUPERDOC_USER, TRACK_CHANGE_PERMISSIONS, TIMEOUTS } from './constants';\n\n/**\n * Permission resolver that allows accepting/rejecting all track changes\n */\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\nconst permissionResolver = ({ permission }: any) => {\n return TRACK_CHANGE_PERMISSIONS.includes(permission) ? true : undefined;\n};\n\n/**\n * DocxDiffEditor Component\n */\nexport const DocxDiffEditor = forwardRef<DocxDiffEditorRef, DocxDiffEditorProps>(\n function DocxDiffEditor(\n {\n initialSource,\n templateDocx,\n showRulers = false,\n showToolbar = true,\n author = DEFAULT_AUTHOR,\n onReady,\n onSourceLoaded,\n onComparisonComplete,\n onError,\n className = '',\n toolbarClassName = '',\n editorClassName = '',\n },\n ref\n ) {\n // Refs\n const containerRef = useRef<HTMLDivElement>(null);\n const toolbarRef = useRef<HTMLDivElement>(null);\n const superdocRef = useRef<SuperDocInstance | null>(null);\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const SuperDocRef = useRef<any>(null);\n const mountedRef = useRef(true);\n const initRef = useRef(false);\n const readyRef = useRef(false);\n\n // State\n const [isLoading, setIsLoading] = useState(true);\n const [error, setError] = useState<string | null>(null);\n const [sourceJson, setSourceJson] = useState<ProseMirrorJSON | null>(null);\n const [mergedJson, setMergedJson] = useState<ProseMirrorJSON | null>(null);\n const [diffResult, setDiffResult] = useState<DiffResult | null>(null);\n\n // Generate unique IDs for this instance\n const instanceId = useRef(`dde-${Date.now()}-${Math.random().toString(36).substr(2, 9)}`);\n const editorId = `dde-editor-${instanceId.current}`;\n const toolbarId = `dde-toolbar-${instanceId.current}`;\n\n /**\n * Set content in the editor using available methods\n * Used only for JSON content and merged documents\n */\n const setEditorContent = useCallback((editor: SuperDocInstance, json: ProseMirrorJSON) => {\n if (editor.commands?.setContent) {\n editor.commands.setContent(json);\n } else if (editor.setContent) {\n editor.setContent(json);\n } else {\n const { state, view } = editor;\n if (state?.doc && view && json.content) {\n const newDoc = state.schema.nodeFromJSON(json);\n const tr = state.tr.replaceWith(0, state.doc.content.size, newDoc.content);\n view.dispatch(tr);\n }\n }\n }, []);\n\n /**\n * Enable track changes review mode\n */\n const enableReviewMode = useCallback((sd: SuperDocInstance) => {\n if (sd.setTrackedChangesPreferences) {\n sd.setTrackedChangesPreferences({ mode: 'review', enabled: true });\n } else if (sd.activeEditor?.commands?.enableTrackChanges) {\n sd.activeEditor.commands.enableTrackChanges();\n }\n }, []);\n\n /**\n * Set editing mode (normal mode - shows original without track changes)\n */\n const setEditingMode = useCallback((sd: SuperDocInstance) => {\n if (sd.setTrackedChangesPreferences) {\n // Use 'simple' mode with track changes disabled for clean editing view\n // Valid modes are: 'review', 'simple', 'original'\n sd.setTrackedChangesPreferences({ mode: 'simple', enabled: false });\n }\n }, []);\n\n /**\n * Handle errors\n */\n const handleError = useCallback(\n (err: Error | string) => {\n const error = err instanceof Error ? err : new Error(err);\n setError(error.message);\n onError?.(error);\n },\n [onError]\n );\n\n /**\n * Destroy current SuperDoc instance\n */\n const destroySuperdoc = useCallback(() => {\n if (superdocRef.current) {\n try {\n superdocRef.current.destroy?.();\n } catch {\n // Ignore cleanup errors\n }\n superdocRef.current = null;\n }\n readyRef.current = false;\n }, []);\n\n /**\n * Create a new SuperDoc instance with the given options\n */\n const createSuperdoc = useCallback(\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n async (options: { document?: File; html?: string }): Promise<{ superdoc: SuperDocInstance; json: ProseMirrorJSON }> => {\n if (!SuperDocRef.current) {\n throw new Error('SuperDoc not loaded');\n }\n if (!containerRef.current) {\n throw new Error('Container not available');\n }\n\n // Set IDs on DOM elements\n containerRef.current.id = editorId;\n if (toolbarRef.current) {\n toolbarRef.current.id = toolbarId;\n }\n\n return new Promise((resolve, reject) => {\n try {\n const superdoc = new SuperDocRef.current({\n selector: `#${editorId}`,\n toolbar: showToolbar ? `#${toolbarId}` : undefined,\n document: options.document,\n html: options.html,\n documentMode: 'editing',\n role: 'editor',\n rulers: showRulers,\n user: DEFAULT_SUPERDOC_USER,\n permissionResolver,\n onReady: ({ superdoc: sd }: { superdoc: SuperDocInstance }) => {\n superdocRef.current = sd;\n readyRef.current = true;\n\n // Extract JSON from the loaded document\n let json: ProseMirrorJSON = { type: 'doc', content: [] };\n if (sd?.activeEditor) {\n try {\n json = sd.activeEditor.getJSON();\n } catch (err) {\n console.error('Failed to extract JSON:', err);\n }\n }\n\n resolve({ superdoc: sd, json });\n },\n onException: ({ error: err }: { error: Error }) => {\n console.error('SuperDoc error:', err);\n reject(err);\n },\n });\n\n superdocRef.current = superdoc;\n\n // Timeout\n setTimeout(() => {\n if (!readyRef.current) {\n reject(new Error('SuperDoc initialization timed out'));\n }\n }, TIMEOUTS.PARSE_TIMEOUT);\n } catch (err) {\n reject(err);\n }\n });\n },\n [editorId, toolbarId, showToolbar, showRulers]\n );\n\n /**\n * Initialize SuperDoc instance\n */\n const initialize = useCallback(async () => {\n if (initRef.current || !containerRef.current || !mountedRef.current) return;\n if (!showToolbar && !toolbarRef.current) {\n // Continue without toolbar\n } else if (showToolbar && !toolbarRef.current) {\n return;\n }\n\n initRef.current = true;\n\n // Small delay for React to settle\n await new Promise((resolve) => setTimeout(resolve, TIMEOUTS.INIT_DELAY));\n\n if (!mountedRef.current || !containerRef.current) {\n initRef.current = false;\n return;\n }\n\n setIsLoading(true);\n setError(null);\n destroySuperdoc();\n\n try {\n // Note: superdoc CSS is bundled in dist/styles.css - user must import 'docx-diff-editor/styles.css'\n const { SuperDoc } = await import('superdoc');\n SuperDocRef.current = SuperDoc;\n\n // Determine initialization options based on initialSource\n let initOptions: { document?: File; html?: string } = {};\n\n if (initialSource) {\n const contentType = detectContentType(initialSource);\n if (contentType === 'file') {\n initOptions = { document: initialSource as File };\n } else if (contentType === 'html') {\n // Initialize directly with HTML - SuperDoc creates blank document internally\n initOptions = { html: initialSource as string };\n } else if (contentType === 'json') {\n // For JSON, we need a document first, then set content\n // Use template if provided, otherwise SuperDoc will create blank\n initOptions = templateDocx ? { document: templateDocx } : {};\n }\n } else if (templateDocx) {\n initOptions = { document: templateDocx };\n }\n // If no initialSource and no template, SuperDoc creates a blank document\n\n const { superdoc: sd, json } = await createSuperdoc(initOptions);\n\n // For JSON content, set it after initialization\n if (initialSource && detectContentType(initialSource) === 'json') {\n if (sd?.activeEditor && isProseMirrorJSON(initialSource)) {\n setEditorContent(sd.activeEditor, initialSource as ProseMirrorJSON);\n setSourceJson(initialSource as ProseMirrorJSON);\n onSourceLoaded?.(initialSource as ProseMirrorJSON);\n }\n } else {\n setSourceJson(json);\n onSourceLoaded?.(json);\n }\n\n setIsLoading(false);\n onReady?.();\n } catch (err) {\n console.error('Failed to initialize SuperDoc:', err);\n handleError(err instanceof Error ? err : new Error('Failed to load editor'));\n setIsLoading(false);\n }\n\n initRef.current = false;\n }, [\n initialSource,\n showRulers,\n showToolbar,\n templateDocx,\n onReady,\n onSourceLoaded,\n destroySuperdoc,\n createSuperdoc,\n setEditorContent,\n handleError,\n ]);\n\n // Initialize on mount\n useEffect(() => {\n mountedRef.current = true;\n initialize();\n\n return () => {\n mountedRef.current = false;\n destroySuperdoc();\n };\n }, [initialize, destroySuperdoc]);\n\n // =========================================================================\n // Imperative API\n // =========================================================================\n\n useImperativeHandle(\n ref,\n () => ({\n /**\n * Set the source/base document\n */\n async setSource(content: DocxContent): Promise<void> {\n if (!SuperDocRef.current) {\n throw new Error('Editor not initialized');\n }\n\n setIsLoading(true);\n setError(null);\n\n try {\n const contentType = detectContentType(content);\n let json: ProseMirrorJSON;\n\n // Destroy current instance and create new one\n destroySuperdoc();\n\n if (contentType === 'file') {\n // Initialize with DOCX file\n const result = await createSuperdoc({ document: content as File });\n json = result.json;\n } else if (contentType === 'html') {\n // Initialize directly with HTML - no template needed!\n // SuperDoc will create a blank document and apply HTML internally\n const result = await createSuperdoc({ html: content as string });\n json = result.json;\n } else {\n // JSON content - initialize blank then set content\n const result = await createSuperdoc(templateDocx ? { document: templateDocx } : {});\n if (result.superdoc?.activeEditor && isProseMirrorJSON(content)) {\n setEditorContent(result.superdoc.activeEditor, content as ProseMirrorJSON);\n json = content as ProseMirrorJSON;\n } else {\n json = result.json;\n }\n }\n\n setSourceJson(json);\n setMergedJson(null);\n setDiffResult(null);\n setEditingMode(superdocRef.current!);\n onSourceLoaded?.(json);\n } catch (err) {\n handleError(err instanceof Error ? err : new Error('Failed to set source'));\n throw err;\n } finally {\n setIsLoading(false);\n }\n },\n\n /**\n * Compare source with new content, show track changes\n */\n async compareWith(content: DocxContent): Promise<ComparisonResult> {\n if (!SuperDocRef.current) {\n throw new Error('Editor not initialized');\n }\n if (!sourceJson) {\n throw new Error('No source document set. Call setSource() first.');\n }\n\n setIsLoading(true);\n try {\n const contentType = detectContentType(content);\n let newJson: ProseMirrorJSON;\n\n if (contentType === 'file') {\n // Parse DOCX file using hidden SuperDoc instance\n newJson = await parseDocxFile(content as File, SuperDocRef.current);\n } else if (contentType === 'html') {\n // Parse HTML using a temporary SuperDoc instance\n const tempContainer = document.createElement('div');\n tempContainer.style.cssText = 'position:absolute;top:-9999px;left:-9999px;width:800px;height:600px;visibility:hidden;';\n document.body.appendChild(tempContainer);\n\n try {\n newJson = await new Promise((resolve, reject) => {\n const tempSuperdoc = new SuperDocRef.current({\n selector: tempContainer,\n html: content as string,\n documentMode: 'viewing',\n rulers: false,\n user: { name: 'Parser', email: 'parser@local' },\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n onReady: ({ superdoc: sd }: { superdoc: any }) => {\n try {\n const json = sd?.activeEditor?.getJSON() || { type: 'doc', content: [] };\n setTimeout(() => {\n try { sd?.destroy?.(); } catch { /* ignore */ }\n tempContainer.parentNode?.removeChild(tempContainer);\n }, 100);\n resolve(json);\n } catch (err) {\n reject(err);\n }\n },\n onException: ({ error: err }: { error: Error }) => {\n tempContainer.parentNode?.removeChild(tempContainer);\n reject(err);\n },\n });\n\n setTimeout(() => {\n try { tempSuperdoc?.destroy?.(); } catch { /* ignore */ }\n tempContainer.parentNode?.removeChild(tempContainer);\n reject(new Error('HTML parsing timed out'));\n }, TIMEOUTS.PARSE_TIMEOUT);\n });\n } catch (err) {\n tempContainer.parentNode?.removeChild(tempContainer);\n throw err;\n }\n } else {\n // JSON content - use directly\n if (!isProseMirrorJSON(content)) {\n throw new Error('Invalid ProseMirror JSON structure');\n }\n newJson = content as ProseMirrorJSON;\n }\n\n // Diff the documents\n const diff = diffDocuments(sourceJson, newJson);\n setDiffResult(diff);\n\n // Merge with track changes\n const merged = mergeDocuments(sourceJson, newJson, diff, author);\n setMergedJson(merged);\n\n // Update editor with merged content\n if (superdocRef.current?.activeEditor) {\n setEditorContent(superdocRef.current.activeEditor, merged);\n enableReviewMode(superdocRef.current);\n }\n\n // Build result\n const insertions = diff.segments.filter((s) => s.type === 'insert').length;\n const deletions = diff.segments.filter((s) => s.type === 'delete').length;\n const formatChanges = diff.formatChanges?.length || 0;\n\n const result: ComparisonResult = {\n totalChanges: insertions + deletions + formatChanges,\n insertions,\n deletions,\n formatChanges,\n summary: diff.summary,\n mergedJson: merged,\n };\n\n onComparisonComplete?.(result);\n return result;\n } catch (err) {\n handleError(err instanceof Error ? err : new Error('Comparison failed'));\n throw err;\n } finally {\n setIsLoading(false);\n }\n },\n\n /**\n * Get raw diff segments\n */\n getDiffSegments(): DiffSegment[] {\n return diffResult?.segments || [];\n },\n\n /**\n * Get enriched changes with context for LLM processing\n */\n getEnrichedChangesContext(): EnrichedChange[] {\n if (!mergedJson) return [];\n return extractEnrichedChanges(mergedJson);\n },\n\n /**\n * Get current document content as JSON\n */\n getContent(): ProseMirrorJSON {\n if (superdocRef.current?.activeEditor) {\n return superdocRef.current.activeEditor.getJSON();\n }\n return mergedJson || sourceJson || { type: 'doc', content: [] };\n },\n\n /**\n * Get source document JSON (before comparison)\n */\n getSourceContent(): ProseMirrorJSON | null {\n return sourceJson;\n },\n\n /**\n * Export current document to DOCX blob\n */\n async exportDocx(): Promise<Blob> {\n if (!superdocRef.current?.activeEditor) {\n throw new Error('Editor not ready');\n }\n\n const blob = await superdocRef.current.activeEditor.exportDocx({\n isFinalDoc: false,\n });\n\n if (!blob) {\n throw new Error('Export returned no data');\n }\n\n return blob;\n },\n\n /**\n * Reset to source state (clear comparison)\n */\n resetComparison(): void {\n if (sourceJson && superdocRef.current?.activeEditor) {\n setEditorContent(superdocRef.current.activeEditor, sourceJson);\n setEditingMode(superdocRef.current);\n setMergedJson(null);\n setDiffResult(null);\n }\n },\n\n /**\n * Check if editor is ready\n */\n isReady(): boolean {\n return readyRef.current;\n },\n }),\n [\n sourceJson,\n mergedJson,\n diffResult,\n templateDocx,\n author,\n destroySuperdoc,\n createSuperdoc,\n setEditorContent,\n enableReviewMode,\n setEditingMode,\n onSourceLoaded,\n onComparisonComplete,\n handleError,\n ]\n );\n\n // =========================================================================\n // Render\n // =========================================================================\n\n return (\n <div className={`dde-container ${className}`.trim()}>\n {/* Loading overlay */}\n {isLoading && (\n <div className=\"dde-loading\">\n <div className=\"dde-loading__spinner\" />\n <p className=\"dde-loading__text\">Loading document...</p>\n </div>\n )}\n\n {/* Error overlay */}\n {error && (\n <div className=\"dde-error\">\n <div className=\"dde-error__icon\">\n <svg\n className=\"dde-error__svg\"\n fill=\"none\"\n stroke=\"currentColor\"\n viewBox=\"0 0 24 24\"\n >\n <path\n strokeLinecap=\"round\"\n strokeLinejoin=\"round\"\n strokeWidth=\"2\"\n d=\"M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z\"\n />\n </svg>\n </div>\n <p className=\"dde-error__title\">Failed to load document</p>\n <p className=\"dde-error__message\">{error}</p>\n </div>\n )}\n\n {/* Toolbar */}\n {showToolbar && (\n <div\n ref={toolbarRef}\n className={`dde-toolbar ${toolbarClassName}`.trim()}\n />\n )}\n\n {/* Editor container */}\n <div\n ref={containerRef}\n className={`dde-editor ${editorClassName}`.trim()}\n />\n </div>\n );\n }\n);\n\nexport default DocxDiffEditor;\n","/**\n * Embedded DOCX template\n *\n * This is a base64-encoded blank DOCX file created with Microsoft Word.\n * It provides the complete schema, styles, themes, and fonts needed to\n * initialize SuperDoc when working with HTML or JSON content.\n *\n * The DOCX contains all standard Word document components:\n * - [Content_Types].xml\n * - _rels/.rels\n * - word/document.xml\n * - word/_rels/document.xml.rels\n * - word/styles.xml (full Word styles)\n * - word/settings.xml\n * - word/fontTable.xml\n * - word/webSettings.xml\n * - word/theme/theme1.xml\n * - docProps/core.xml\n * - docProps/app.xml\n */\n\n/**\n * Base64-encoded blank DOCX file created with Microsoft Word.\n */\nconst BLANK_DOCX_BASE64 = `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`;\n\n/**\n * Convert base64 string to Blob\n */\nfunction base64ToBlob(base64: string, mimeType: string): Blob {\n const byteCharacters = atob(base64.replace(/\\s/g, ''));\n const byteNumbers = new Array(byteCharacters.length);\n\n for (let i = 0; i < byteCharacters.length; i++) {\n byteNumbers[i] = byteCharacters.charCodeAt(i);\n }\n\n const byteArray = new Uint8Array(byteNumbers);\n return new Blob([byteArray], { type: mimeType });\n}\n\n/**\n * Convert base64 string to File\n */\nfunction base64ToFile(base64: string, filename: string, mimeType: string): File {\n const blob = base64ToBlob(base64, mimeType);\n return new File([blob], filename, { type: mimeType });\n}\n\n/**\n * Get the blank DOCX template as a File object\n */\nexport function getBlankTemplateFile(): File {\n return base64ToFile(\n BLANK_DOCX_BASE64,\n 'blank-template.docx',\n 'application/vnd.openxmlformats-officedocument.wordprocessingml.document'\n );\n}\n\n/**\n * Get the blank DOCX template as a Blob\n */\nexport function getBlankTemplateBlob(): Blob {\n return base64ToBlob(\n BLANK_DOCX_BASE64,\n 'application/vnd.openxmlformats-officedocument.wordprocessingml.document'\n );\n}\n\n/**\n * Check if a File is a valid DOCX file (basic check)\n */\nexport function isValidDocxFile(file: File): boolean {\n const validTypes = [\n 'application/vnd.openxmlformats-officedocument.wordprocessingml.document',\n 'application/msword',\n ];\n return validTypes.includes(file.type) || file.name.endsWith('.docx');\n}\n"]}
1
+ {"version":3,"sources":["../src/constants.ts","../src/services/contentResolver.ts","../src/services/documentDiffer.ts","../src/services/trackChangeInjector.ts","../src/services/mergeDocuments.ts","../src/services/changeContextExtractor.ts","../src/DocxDiffEditor.tsx","../src/blankTemplate.ts"],"names":["uuidv4","DocxDiffEditor","error"],"mappings":"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","file":"index.mjs","sourcesContent":["/**\n * Constants for DocxDiffEditor\n */\n\nimport type { TrackChangeAuthor } from './types';\n\n/**\n * Default author for track changes\n */\nexport const DEFAULT_AUTHOR: TrackChangeAuthor = {\n name: 'DocxDiff Editor',\n email: 'editor@docxdiff.local',\n};\n\n/**\n * Default SuperDoc user (used for editor initialization)\n */\nexport const DEFAULT_SUPERDOC_USER = {\n name: 'DocxDiff User',\n email: 'user@docxdiff.local',\n};\n\n/**\n * Permissions allowed for track change resolution\n */\nexport const TRACK_CHANGE_PERMISSIONS = [\n 'RESOLVE_OWN',\n 'RESOLVE_OTHER',\n 'REJECT_OWN',\n 'REJECT_OTHER',\n];\n\n/**\n * CSS class prefix for all component styles\n */\nexport const CSS_PREFIX = 'dde';\n\n/**\n * Timeouts\n */\nexport const TIMEOUTS = {\n /** Timeout for document parsing (ms) */\n PARSE_TIMEOUT: 30000,\n /** Small delay for React settling (ms) */\n INIT_DELAY: 100,\n /** Cleanup delay (ms) */\n CLEANUP_DELAY: 100,\n};\n\n","/**\n * Content Resolver Service\n * Detects content type and parses DOCX files to ProseMirror JSON.\n *\n * Supports three input formats:\n * - File: DOCX file parsed by SuperDoc\n * - string: HTML content (handled directly by SuperDoc in the component)\n * - object: Direct ProseMirror JSON (passed through)\n */\n\nimport type { DocxContent, ProseMirrorJSON } from '../types';\nimport { TIMEOUTS } from '../constants';\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\ntype SuperDocConstructor = any;\n\n/**\n * Detect the type of content provided\n */\nexport function detectContentType(content: DocxContent): 'file' | 'html' | 'json' {\n if (content instanceof File) {\n return 'file';\n }\n if (typeof content === 'string') {\n return 'html';\n }\n // Assume it's JSON if it's an object\n return 'json';\n}\n\n/**\n * Validate that content looks like ProseMirror JSON\n */\nexport function isProseMirrorJSON(content: unknown): boolean {\n if (!content || typeof content !== 'object') return false;\n const obj = content as Record<string, unknown>;\n return typeof obj.type === 'string' && (obj.type === 'doc' || Array.isArray(obj.content));\n}\n\n/**\n * Parse a DOCX File into ProseMirror JSON using a hidden SuperDoc instance.\n */\nexport async function parseDocxFile(\n file: File,\n SuperDoc: SuperDocConstructor\n): Promise<ProseMirrorJSON> {\n // Create a hidden container for the editor\n const container = document.createElement('div');\n container.style.cssText =\n 'position:absolute;top:-9999px;left:-9999px;width:800px;height:600px;visibility:hidden;';\n document.body.appendChild(container);\n\n return new Promise((resolve, reject) => {\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n let superdoc: any = null;\n let resolved = false;\n\n const cleanup = () => {\n setTimeout(() => {\n if (superdoc) {\n try {\n const sd = superdoc;\n superdoc = null;\n sd.destroy?.();\n } catch {\n // Ignore cleanup errors\n }\n }\n if (container.parentNode) {\n container.parentNode.removeChild(container);\n }\n }, TIMEOUTS.CLEANUP_DELAY);\n };\n\n setTimeout(async () => {\n if (resolved) return;\n\n try {\n superdoc = new SuperDoc({\n selector: container,\n document: file,\n documentMode: 'viewing',\n rulers: false,\n user: { name: 'Parser', email: 'parser@local' },\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n onReady: ({ superdoc: sd }: { superdoc: any }) => {\n if (resolved) return;\n try {\n const editor = sd?.activeEditor;\n if (!editor) {\n throw new Error('No active editor found');\n }\n\n const json = editor.getJSON();\n resolved = true;\n cleanup();\n resolve(json);\n } catch (err) {\n resolved = true;\n cleanup();\n reject(err);\n }\n },\n onException: ({ error: err }: { error: Error }) => {\n if (resolved) return;\n resolved = true;\n cleanup();\n reject(err);\n },\n });\n\n // Timeout\n setTimeout(() => {\n if (!resolved) {\n resolved = true;\n cleanup();\n reject(new Error('Document parsing timed out'));\n }\n }, TIMEOUTS.PARSE_TIMEOUT);\n } catch (err) {\n cleanup();\n reject(err);\n }\n }, 50);\n });\n}\n","/**\n * Document Differ Service\n * Diffs two ProseMirror JSON documents at the character level,\n * including text changes and formatting changes.\n */\n\nimport DiffMatchPatch from 'diff-match-patch';\nimport type {\n ProseMirrorJSON,\n ProseMirrorMark,\n DiffSegment,\n DiffResult,\n FormatChange,\n TextSpan,\n} from '../types';\n\nconst dmp = new DiffMatchPatch();\n\n// Diff operation types\nconst DIFF_DELETE = -1;\nconst DIFF_INSERT = 1;\nconst DIFF_EQUAL = 0;\n\n/**\n * Extract text spans with their marks from a ProseMirror node.\n */\nfunction extractTextSpans(node: ProseMirrorJSON, offset: number = 0): TextSpan[] {\n const spans: TextSpan[] = [];\n\n if (!node) return spans;\n\n if (node.type === 'text' && node.text) {\n spans.push({\n text: node.text,\n from: offset,\n to: offset + node.text.length,\n marks: node.marks || [],\n });\n return spans;\n }\n\n if (node.content && Array.isArray(node.content)) {\n let currentOffset = offset;\n for (const child of node.content) {\n const childSpans = extractTextSpans(child, currentOffset);\n spans.push(...childSpans);\n // Calculate consumed length\n for (const span of childSpans) {\n currentOffset = Math.max(currentOffset, span.to);\n }\n // If no spans, check if it's a text node for offset\n if (childSpans.length === 0 && child.type === 'text' && child.text) {\n currentOffset += child.text.length;\n }\n }\n }\n\n return spans;\n}\n\n/**\n * Extract text content from a ProseMirror node recursively.\n */\nfunction extractTextContent(node: ProseMirrorJSON): string {\n if (!node) return '';\n\n if (node.type === 'text' && node.text) {\n return node.text;\n }\n\n if (node.content && Array.isArray(node.content)) {\n return node.content.map(extractTextContent).join('');\n }\n\n return '';\n}\n\n/**\n * Deep compare two values.\n */\nfunction deepEqual(a: unknown, b: unknown): boolean {\n if (a === b) return true;\n if (typeof a !== typeof b) return false;\n if (typeof a !== 'object' || a === null || b === null) return false;\n\n const objA = a as Record<string, unknown>;\n const objB = b as Record<string, unknown>;\n const keysA = Object.keys(objA);\n const keysB = Object.keys(objB);\n\n if (keysA.length !== keysB.length) return false;\n\n for (const key of keysA) {\n if (!keysB.includes(key)) return false;\n if (!deepEqual(objA[key], objB[key])) return false;\n }\n\n return true;\n}\n\n/**\n * Compare marks arrays to check if they're equivalent.\n */\nfunction marksEqual(marksA: ProseMirrorMark[], marksB: ProseMirrorMark[]): boolean {\n if (marksA.length !== marksB.length) return false;\n\n // Sort by type for consistent comparison\n const sortedA = [...marksA].sort((a, b) => (a.type || '').localeCompare(b.type || ''));\n const sortedB = [...marksB].sort((a, b) => (a.type || '').localeCompare(b.type || ''));\n\n return deepEqual(sortedA, sortedB);\n}\n\n/**\n * Get marks at a specific character position from spans.\n */\nfunction getMarksAtPosition(spans: TextSpan[], pos: number): ProseMirrorMark[] {\n for (const span of spans) {\n if (pos >= span.from && pos < span.to) {\n return span.marks;\n }\n }\n return [];\n}\n\n/**\n * Detect format changes on equal text segments.\n */\nfunction detectFormatChanges(\n spansA: TextSpan[],\n spansB: TextSpan[],\n segments: DiffSegment[]\n): FormatChange[] {\n const formatChanges: FormatChange[] = [];\n\n let posA = 0;\n let posB = 0;\n\n for (const segment of segments) {\n if (segment.type === 'equal') {\n // For equal text, compare marks character by character\n // Group consecutive chars with same mark difference\n let i = 0;\n while (i < segment.text.length) {\n const marksA = getMarksAtPosition(spansA, posA + i);\n const marksB = getMarksAtPosition(spansB, posB + i);\n\n if (!marksEqual(marksA, marksB)) {\n // Found a format difference - find the extent\n const startI = i;\n const startMarksA = marksA;\n const startMarksB = marksB;\n\n // Extend while marks remain the same different pattern\n while (i < segment.text.length) {\n const currentMarksA = getMarksAtPosition(spansA, posA + i);\n const currentMarksB = getMarksAtPosition(spansB, posB + i);\n\n if (marksEqual(currentMarksA, startMarksA) && marksEqual(currentMarksB, startMarksB)) {\n i++;\n } else {\n break;\n }\n }\n\n formatChanges.push({\n from: posA + startI,\n to: posA + i,\n text: segment.text.substring(startI, i),\n before: startMarksA,\n after: startMarksB,\n });\n } else {\n i++;\n }\n }\n\n posA += segment.text.length;\n posB += segment.text.length;\n } else if (segment.type === 'delete') {\n // Deleted text exists only in docA, so only advance posA\n posA += segment.text.length;\n } else if (segment.type === 'insert') {\n // Inserted text exists only in docB, so only advance posB\n posB += segment.text.length;\n }\n }\n\n return formatChanges;\n}\n\n/**\n * Diff two ProseMirror JSON documents at the character level.\n * Detects both text changes and formatting changes.\n */\nexport function diffDocuments(\n docA: ProseMirrorJSON,\n docB: ProseMirrorJSON\n): DiffResult {\n // Extract full text from both documents\n const textA = extractTextContent(docA);\n const textB = extractTextContent(docB);\n\n // Perform character-level diff on the entire document\n const diffs = dmp.diff_main(textA, textB);\n dmp.diff_cleanupSemantic(diffs);\n\n // Convert to our DiffSegment format\n const segments: DiffSegment[] = [];\n let insertCount = 0;\n let deleteCount = 0;\n\n for (const [op, text] of diffs) {\n if (op === DIFF_EQUAL) {\n segments.push({ type: 'equal', text });\n } else if (op === DIFF_INSERT) {\n segments.push({ type: 'insert', text });\n insertCount++;\n } else if (op === DIFF_DELETE) {\n segments.push({ type: 'delete', text });\n deleteCount++;\n }\n }\n\n // Extract text spans with marks for format comparison\n const spansA = extractTextSpans(docA);\n const spansB = extractTextSpans(docB);\n\n // Detect format changes on equal segments\n const formatChanges = detectFormatChanges(spansA, spansB, segments);\n\n // Build summary\n const summary: string[] = [];\n if (insertCount > 0) {\n summary.push(`${insertCount} insertion(s)`);\n }\n if (deleteCount > 0) {\n summary.push(`${deleteCount} deletion(s)`);\n }\n if (formatChanges.length > 0) {\n summary.push(`${formatChanges.length} format change(s)`);\n }\n if (insertCount === 0 && deleteCount === 0 && formatChanges.length === 0) {\n summary.push('No changes detected');\n }\n\n return {\n segments,\n formatChanges,\n textA,\n textB,\n summary,\n };\n}\n\n","/**\n * Track Change Injector Service\n * Creates track change marks for insertions, deletions, and format changes.\n */\n\nimport { v4 as uuidv4 } from 'uuid';\nimport type { TrackChangeAuthor, ProseMirrorJSON, ProseMirrorMark } from '../types';\nimport { DEFAULT_AUTHOR } from '../constants';\n\n/**\n * Create a trackInsert mark.\n */\nexport function createTrackInsertMark(author: TrackChangeAuthor = DEFAULT_AUTHOR): ProseMirrorMark {\n return {\n type: 'trackInsert',\n attrs: {\n id: uuidv4(),\n author: author.name,\n authorEmail: author.email,\n authorImage: '',\n date: new Date().toISOString(),\n },\n };\n}\n\n/**\n * Create a trackDelete mark.\n */\nexport function createTrackDeleteMark(author: TrackChangeAuthor = DEFAULT_AUTHOR): ProseMirrorMark {\n return {\n type: 'trackDelete',\n attrs: {\n id: uuidv4(),\n author: author.name,\n authorEmail: author.email,\n authorImage: '',\n date: new Date().toISOString(),\n },\n };\n}\n\n/**\n * Create a trackFormat mark.\n */\nexport function createTrackFormatMark(\n before: ProseMirrorMark[],\n after: ProseMirrorMark[],\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorMark {\n return {\n type: 'trackFormat',\n attrs: {\n id: uuidv4(),\n author: author.name,\n authorEmail: author.email,\n authorImage: '',\n date: new Date().toISOString(),\n before,\n after,\n },\n };\n}\n\n/**\n * Add a mark to a text node, preserving existing marks.\n */\nexport function addMarkToTextNode(\n node: ProseMirrorJSON,\n mark: ProseMirrorMark\n): ProseMirrorJSON {\n if (node.type !== 'text') {\n return node;\n }\n\n return {\n ...node,\n marks: [...(node.marks || []), mark],\n };\n}\n\n/**\n * Create a text node with specific marks.\n */\nexport function createTextNode(\n text: string,\n marks: ProseMirrorMark[] = []\n): ProseMirrorJSON {\n const node: ProseMirrorJSON = {\n type: 'text',\n text,\n };\n\n if (marks.length > 0) {\n node.marks = marks;\n }\n\n return node;\n}\n\n/**\n * Apply trackDelete mark to all text in a node (recursively).\n */\nexport function markAllAsDeleted(\n node: ProseMirrorJSON,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorJSON {\n if (node.type === 'text') {\n return addMarkToTextNode(node, createTrackDeleteMark(author));\n }\n\n if (node.content && Array.isArray(node.content)) {\n return {\n ...node,\n content: node.content.map((child: ProseMirrorJSON) =>\n markAllAsDeleted(child, author)\n ),\n };\n }\n\n return node;\n}\n\n/**\n * Apply trackInsert mark to all text in a node (recursively).\n */\nexport function markAllAsInserted(\n node: ProseMirrorJSON,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorJSON {\n if (node.type === 'text') {\n return addMarkToTextNode(node, createTrackInsertMark(author));\n }\n\n if (node.content && Array.isArray(node.content)) {\n return {\n ...node,\n content: node.content.map((child: ProseMirrorJSON) =>\n markAllAsInserted(child, author)\n ),\n };\n }\n\n return node;\n}\n\n/**\n * Clone a node deeply.\n */\nexport function cloneNode(node: ProseMirrorJSON): ProseMirrorJSON {\n return JSON.parse(JSON.stringify(node));\n}\n\n","/**\n * Merge Documents Service\n * Applies track change marks to the original document structure\n * based on character-level diff segments.\n */\n\nimport type {\n ProseMirrorJSON,\n ProseMirrorNode,\n DiffResult,\n FormatChange,\n TrackChangeAuthor,\n} from '../types';\nimport {\n createTrackInsertMark,\n createTrackDeleteMark,\n createTrackFormatMark,\n} from './trackChangeInjector';\nimport { DEFAULT_AUTHOR } from '../constants';\n\n/**\n * Deep clone a node\n */\nfunction cloneNode(node: ProseMirrorNode): ProseMirrorNode {\n return JSON.parse(JSON.stringify(node));\n}\n\n/**\n * Character state during merge\n */\ninterface CharState {\n type: 'equal' | 'delete' | 'insert';\n insertText?: string;\n}\n\n/**\n * Insertion point during merge\n */\ninterface Insertion {\n afterOffset: number;\n text: string;\n}\n\n/**\n * Build a merged document by applying diff segments to the original structure.\n *\n * Strategy:\n * 1. Clone docA (original)\n * 2. Walk through diff segments\n * 3. For 'equal' segments: keep original content as-is\n * 4. For 'delete' segments: add trackDelete mark to the corresponding text\n * 5. For 'insert' segments: insert new text nodes with trackInsert mark\n */\nexport function mergeDocuments(\n docA: ProseMirrorNode,\n docB: ProseMirrorNode,\n diffResult: DiffResult,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorNode {\n // Clone the original document\n const merged = cloneNode(docA);\n\n // Build a map of character offset -> segment type\n // This tells us for each character what its state is\n const charStates: CharState[] = [];\n let insertions: Insertion[] = [];\n\n // Store format changes as array for range lookups\n const formatChanges: FormatChange[] = diffResult.formatChanges || [];\n\n // Helper to find format change at a position\n function getFormatChangeAt(pos: number): FormatChange | null {\n for (const fc of formatChanges) {\n if (pos >= fc.from && pos < fc.to) {\n return fc;\n }\n }\n return null;\n }\n\n let docAOffset = 0;\n for (const segment of diffResult.segments) {\n if (segment.type === 'equal') {\n // Mark these characters as equal\n for (let i = 0; i < segment.text.length; i++) {\n charStates[docAOffset + i] = { type: 'equal' };\n }\n docAOffset += segment.text.length;\n } else if (segment.type === 'delete') {\n // Mark these characters as deleted\n for (let i = 0; i < segment.text.length; i++) {\n charStates[docAOffset + i] = { type: 'delete' };\n }\n docAOffset += segment.text.length;\n } else if (segment.type === 'insert') {\n // Insert doesn't consume docA characters, it adds new text\n // We need to track where to insert\n insertions.push({\n afterOffset: docAOffset,\n text: segment.text,\n });\n }\n }\n\n // Now we need to transform the document\n // For each text span in the original:\n // 1. Split it based on character states (equal vs delete)\n // 2. Apply trackDelete marks to deleted parts\n // 3. Insert new content where insertions occur\n\n function transformNode(\n node: ProseMirrorNode,\n nodeOffset: number,\n path: number[]\n ): { nodes: ProseMirrorNode[]; consumedLength: number } {\n if (node.type === 'text' && node.text) {\n const text = node.text;\n const result: ProseMirrorNode[] = [];\n let i = 0;\n\n while (i < text.length) {\n const charOffset = nodeOffset + i;\n const charState = charStates[charOffset] || { type: 'equal' };\n\n // Check for insertions at this position\n const insertionsHere = insertions.filter((ins) => ins.afterOffset === charOffset);\n for (const ins of insertionsHere) {\n result.push({\n type: 'text',\n text: ins.text,\n marks: [...(node.marks || []), createTrackInsertMark(author)],\n });\n }\n\n // Find run of same state AND same format change status\n const currentFormatChange = getFormatChangeAt(nodeOffset + i);\n let j = i + 1;\n while (j < text.length) {\n const nextState = charStates[nodeOffset + j] || { type: 'equal' };\n if (nextState.type !== charState.type) break;\n // Also break if there's an insertion point here\n if (insertions.some((ins) => ins.afterOffset === nodeOffset + j)) break;\n // Break if format change status changes\n const nextFormatChange = getFormatChangeAt(nodeOffset + j);\n if (currentFormatChange !== nextFormatChange) break;\n j++;\n }\n\n const chunk = text.substring(i, j);\n let marks = [...(node.marks || [])];\n\n if (charState.type === 'delete') {\n marks.push(createTrackDeleteMark(author));\n } else if (charState.type === 'equal') {\n // Check if there's a format change at this position\n if (currentFormatChange) {\n // For format changes, use the NEW marks (after) plus trackFormat\n const trackFormatMark = createTrackFormatMark(\n currentFormatChange.before,\n currentFormatChange.after,\n author\n );\n marks = [...currentFormatChange.after, trackFormatMark];\n }\n }\n\n result.push({\n type: 'text',\n text: chunk,\n marks: marks.length > 0 ? marks : undefined,\n });\n\n i = j;\n }\n\n // Check for insertions at the end of this text node\n const endOffset = nodeOffset + text.length;\n const endInsertions = insertions.filter((ins) => ins.afterOffset === endOffset);\n for (const ins of endInsertions) {\n result.push({\n type: 'text',\n text: ins.text,\n marks: [...(node.marks || []), createTrackInsertMark(author)],\n });\n }\n\n // Remove processed insertions\n insertions = insertions.filter(\n (ins) => ins.afterOffset < nodeOffset || ins.afterOffset > endOffset\n );\n\n return { nodes: result, consumedLength: text.length };\n }\n\n // Non-text node: recursively transform children\n if (node.content && Array.isArray(node.content)) {\n const newContent: ProseMirrorNode[] = [];\n let offset = nodeOffset;\n\n for (const child of node.content) {\n const { nodes, consumedLength } = transformNode(child, offset, path);\n newContent.push(...nodes);\n offset += consumedLength;\n }\n\n return {\n nodes: [{ ...node, content: newContent }],\n consumedLength: offset - nodeOffset,\n };\n }\n\n // Node without content (like hard break)\n return { nodes: [node], consumedLength: 0 };\n }\n\n // Transform the document content\n if (merged.content && Array.isArray(merged.content)) {\n const newContent: ProseMirrorNode[] = [];\n let offset = 0;\n\n for (let i = 0; i < merged.content.length; i++) {\n const child = merged.content[i];\n const { nodes, consumedLength } = transformNode(child, offset, [i]);\n newContent.push(...nodes);\n offset += consumedLength;\n }\n\n merged.content = newContent;\n }\n\n // Handle any remaining insertions (at the very end)\n if (insertions.length > 0) {\n for (const ins of insertions) {\n const insertNode = {\n type: 'paragraph',\n content: [\n {\n type: 'run',\n content: [\n {\n type: 'text',\n text: ins.text,\n marks: [createTrackInsertMark(author)],\n },\n ],\n },\n ],\n };\n if (!merged.content) merged.content = [];\n merged.content.push(insertNode);\n }\n }\n\n return merged;\n}\n\n/**\n * Export for compatibility\n */\nexport function createSimpleMergedDocument(\n docA: ProseMirrorNode,\n docB: ProseMirrorNode,\n diffResult: DiffResult,\n author: TrackChangeAuthor = DEFAULT_AUTHOR\n): ProseMirrorNode {\n return mergeDocuments(docA, docB, diffResult, author);\n}\n\n","/**\n * Change Context Extractor\n * Extracts enriched changes with semantic context from merged document.\n * Provides surrounding text so the LLM can understand what the change is about.\n */\n\nimport type {\n ProseMirrorJSON,\n ProseMirrorNode,\n EnrichedChange,\n ChangeLocation,\n TraversalContext,\n} from '../types';\n\n/**\n * Main entry point - extract enriched changes from merged document\n */\nexport function extractEnrichedChanges(mergedJson: ProseMirrorJSON): EnrichedChange[] {\n const changes: EnrichedChange[] = [];\n const context: TraversalContext = {\n currentSection: null,\n currentParagraphText: '',\n currentNodeType: 'unknown',\n };\n\n traverseDocument(mergedJson, context, changes);\n return groupReplacements(changes);\n}\n\n/**\n * Recursively walk the document tree\n */\nfunction traverseDocument(\n node: ProseMirrorNode,\n context: TraversalContext,\n changes: EnrichedChange[]\n): void {\n if (!node) return;\n\n // Update context based on node type\n if (node.type === 'heading') {\n context.currentSection = extractAllText(node);\n context.headingLevel = node.attrs?.level || 1;\n context.currentNodeType = 'heading';\n context.currentParagraphText = context.currentSection;\n } else if (node.type === 'paragraph') {\n context.currentNodeType = 'paragraph';\n context.currentParagraphText = extractAllText(node);\n } else if (node.type === 'listItem') {\n context.currentNodeType = 'listItem';\n context.currentParagraphText = extractAllText(node);\n } else if (node.type === 'tableCell') {\n context.currentNodeType = 'tableCell';\n context.currentParagraphText = extractAllText(node);\n }\n\n // Check for track change marks on text nodes\n if (node.type === 'text' && node.marks) {\n const trackMark = findTrackChangeMark(node.marks);\n if (trackMark) {\n const change = createEnrichedChange(node, trackMark, context);\n if (change) changes.push(change);\n }\n }\n\n // Recurse into children\n if (node.content && Array.isArray(node.content)) {\n for (const child of node.content) {\n traverseDocument(child, context, changes);\n }\n }\n}\n\n/**\n * Extract ALL text from a node (including deleted text, for context)\n */\nfunction extractAllText(node: ProseMirrorNode): string {\n if (!node) return '';\n if (node.type === 'text') {\n return node.text || '';\n }\n if (node.content && Array.isArray(node.content)) {\n return node.content.map(extractAllText).join('');\n }\n return '';\n}\n\n/**\n * Find trackInsert, trackDelete, or trackFormat mark\n */\nfunction findTrackChangeMark(marks: ProseMirrorNode[]): ProseMirrorNode | null {\n return (\n marks.find(\n (m) =>\n m.type === 'trackInsert' || m.type === 'trackDelete' || m.type === 'trackFormat'\n ) || null\n );\n}\n\n/**\n * Create enriched change from node and track mark\n */\nfunction createEnrichedChange(\n node: ProseMirrorNode,\n trackMark: ProseMirrorNode,\n context: TraversalContext\n): EnrichedChange | null {\n const text = node.text || '';\n const location = buildLocation(context);\n const surroundingText = extractSurroundingSentence(text, context.currentParagraphText);\n\n if (trackMark.type === 'trackInsert') {\n return {\n type: 'insertion',\n text,\n location,\n surroundingText,\n charCount: text.length,\n };\n }\n\n if (trackMark.type === 'trackDelete') {\n return {\n type: 'deletion',\n text,\n location,\n surroundingText,\n charCount: text.length,\n };\n }\n\n if (trackMark.type === 'trackFormat') {\n const before = trackMark.attrs?.before || [];\n const after = trackMark.attrs?.after || [];\n return {\n type: 'format',\n text,\n location,\n surroundingText,\n formatDetails: {\n added: after\n .map((m: ProseMirrorNode) => m.type)\n .filter((t: string) => !before.some((b: ProseMirrorNode) => b.type === t)),\n removed: before\n .map((m: ProseMirrorNode) => m.type)\n .filter((t: string) => !after.some((a: ProseMirrorNode) => a.type === t)),\n },\n charCount: text.length,\n };\n }\n\n return null;\n}\n\n/**\n * Extract the sentence or clause containing the changed text\n */\nfunction extractSurroundingSentence(changedText: string, paragraphText: string): string {\n if (!paragraphText || !changedText) return '';\n\n // Find where the change is in the paragraph\n const changeIndex = paragraphText.indexOf(changedText);\n if (changeIndex === -1) {\n // If exact match not found, return truncated paragraph\n return truncate(paragraphText, 150);\n }\n\n // Split into sentences (by period, semicolon, or significant punctuation)\n // But keep the delimiters for context\n const sentenceBreaks = /([.;!?]\\s+)/g;\n const sentences: { text: string; start: number; end: number }[] = [];\n\n let lastEnd = 0;\n let match;\n\n while ((match = sentenceBreaks.exec(paragraphText)) !== null) {\n sentences.push({\n text: paragraphText.slice(lastEnd, match.index + match[0].length).trim(),\n start: lastEnd,\n end: match.index + match[0].length,\n });\n lastEnd = match.index + match[0].length;\n }\n\n // Add remaining text as final sentence\n if (lastEnd < paragraphText.length) {\n sentences.push({\n text: paragraphText.slice(lastEnd).trim(),\n start: lastEnd,\n end: paragraphText.length,\n });\n }\n\n // Find which sentence contains the change\n const changeEnd = changeIndex + changedText.length;\n for (const sentence of sentences) {\n if (changeIndex >= sentence.start && changeIndex < sentence.end) {\n // Found it - return this sentence (truncated if too long)\n return truncate(sentence.text, 200);\n }\n }\n\n // Fallback: return a window around the change\n const windowSize = 100;\n const start = Math.max(0, changeIndex - windowSize);\n const end = Math.min(paragraphText.length, changeEnd + windowSize);\n\n let result = paragraphText.slice(start, end);\n if (start > 0) result = '...' + result;\n if (end < paragraphText.length) result = result + '...';\n\n return result;\n}\n\n/**\n * Truncate text with ellipsis\n */\nfunction truncate(text: string, maxLen: number): string {\n if (!text) return '';\n const cleaned = text.replace(/\\s+/g, ' ').trim();\n if (cleaned.length <= maxLen) return cleaned;\n return cleaned.slice(0, maxLen - 3).trim() + '...';\n}\n\n/**\n * Build location info\n */\nfunction buildLocation(context: TraversalContext): ChangeLocation {\n const nodeType = context.currentNodeType as ChangeLocation['nodeType'];\n\n let description: string;\n if (nodeType === 'heading') {\n description = context.headingLevel === 1 ? 'document title' : 'section heading';\n } else if (context.currentSection) {\n description = `\"${truncate(context.currentSection, 50)}\" section`;\n } else {\n description = 'document body';\n }\n\n return {\n nodeType,\n headingLevel: context.headingLevel,\n sectionTitle: context.currentSection || undefined,\n description,\n };\n}\n\n/**\n * Combine adjacent delete+insert into replacements\n */\nfunction groupReplacements(changes: EnrichedChange[]): EnrichedChange[] {\n const result: EnrichedChange[] = [];\n let i = 0;\n\n while (i < changes.length) {\n const current = changes[i];\n const next = changes[i + 1];\n\n // Check if delete followed by insert (same section = likely replacement)\n if (\n current.type === 'deletion' &&\n next?.type === 'insertion' &&\n current.location.sectionTitle === next.location.sectionTitle\n ) {\n result.push({\n type: 'replacement',\n oldText: current.text,\n newText: next.text,\n location: current.location,\n surroundingText: current.surroundingText || next.surroundingText,\n charCount: (current.charCount || 0) + (next.charCount || 0),\n });\n i += 2;\n } else {\n result.push(current);\n i++;\n }\n }\n\n return result;\n}\n\n","/**\n * DocxDiffEditor Component\n *\n * A React component for DOCX document comparison with track changes visualization.\n * Wraps SuperDoc editor and provides methods for setting source, comparing documents,\n * and extracting change context for LLM processing.\n */\n\nimport {\n useCallback,\n useRef,\n useState,\n useEffect,\n useImperativeHandle,\n forwardRef,\n} from 'react';\n\nimport type {\n DocxDiffEditorProps,\n DocxDiffEditorRef,\n DocxContent,\n ProseMirrorJSON,\n SuperDocInstance,\n DiffSegment,\n DiffResult,\n ComparisonResult,\n EnrichedChange,\n} from './types';\n\nimport { parseDocxFile, detectContentType, isProseMirrorJSON } from './services/contentResolver';\nimport { diffDocuments } from './services/documentDiffer';\nimport { mergeDocuments } from './services/mergeDocuments';\nimport { extractEnrichedChanges } from './services/changeContextExtractor';\nimport { DEFAULT_AUTHOR, DEFAULT_SUPERDOC_USER, TRACK_CHANGE_PERMISSIONS, TIMEOUTS } from './constants';\n\n/**\n * Permission resolver that allows accepting/rejecting all track changes\n */\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\nconst permissionResolver = ({ permission }: any) => {\n return TRACK_CHANGE_PERMISSIONS.includes(permission) ? true : undefined;\n};\n\n/**\n * DocxDiffEditor Component\n */\nexport const DocxDiffEditor = forwardRef<DocxDiffEditorRef, DocxDiffEditorProps>(\n function DocxDiffEditor(\n {\n initialSource,\n templateDocx,\n showRulers = false,\n showToolbar = true,\n author = DEFAULT_AUTHOR,\n onReady,\n onSourceLoaded,\n onComparisonComplete,\n onError,\n className = '',\n toolbarClassName = '',\n editorClassName = '',\n },\n ref\n ) {\n // Refs\n const containerRef = useRef<HTMLDivElement>(null);\n const toolbarRef = useRef<HTMLDivElement>(null);\n const superdocRef = useRef<SuperDocInstance | null>(null);\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const SuperDocRef = useRef<any>(null);\n const mountedRef = useRef(true);\n const initRef = useRef(false);\n const readyRef = useRef(false);\n\n // State\n const [isLoading, setIsLoading] = useState(true);\n const [error, setError] = useState<string | null>(null);\n const [sourceJson, setSourceJson] = useState<ProseMirrorJSON | null>(null);\n const [mergedJson, setMergedJson] = useState<ProseMirrorJSON | null>(null);\n const [diffResult, setDiffResult] = useState<DiffResult | null>(null);\n\n // Generate unique IDs for this instance\n const instanceId = useRef(`dde-${Date.now()}-${Math.random().toString(36).substr(2, 9)}`);\n const editorId = `dde-editor-${instanceId.current}`;\n const toolbarId = `dde-toolbar-${instanceId.current}`;\n\n /**\n * Set content in the editor using available methods\n * Used only for JSON content and merged documents\n */\n const setEditorContent = useCallback((editor: SuperDocInstance, json: ProseMirrorJSON) => {\n if (editor.commands?.setContent) {\n editor.commands.setContent(json);\n } else if (editor.setContent) {\n editor.setContent(json);\n } else {\n const { state, view } = editor;\n if (state?.doc && view && json.content) {\n const newDoc = state.schema.nodeFromJSON(json);\n const tr = state.tr.replaceWith(0, state.doc.content.size, newDoc.content);\n view.dispatch(tr);\n }\n }\n }, []);\n\n /**\n * Enable track changes review mode\n */\n const enableReviewMode = useCallback((sd: SuperDocInstance) => {\n if (sd.setTrackedChangesPreferences) {\n sd.setTrackedChangesPreferences({ mode: 'review', enabled: true });\n } else if (sd.activeEditor?.commands?.enableTrackChanges) {\n sd.activeEditor.commands.enableTrackChanges();\n }\n }, []);\n\n /**\n * Set editing mode (normal mode - shows original without track changes)\n */\n const setEditingMode = useCallback((sd: SuperDocInstance) => {\n if (sd.setTrackedChangesPreferences) {\n // Use 'simple' mode with track changes disabled for clean editing view\n // Valid modes are: 'review', 'simple', 'original'\n sd.setTrackedChangesPreferences({ mode: 'simple', enabled: false });\n }\n }, []);\n\n /**\n * Handle errors\n */\n const handleError = useCallback(\n (err: Error | string) => {\n const error = err instanceof Error ? err : new Error(err);\n setError(error.message);\n onError?.(error);\n },\n [onError]\n );\n\n /**\n * Destroy current SuperDoc instance\n */\n const destroySuperdoc = useCallback(() => {\n if (superdocRef.current) {\n try {\n superdocRef.current.destroy?.();\n } catch {\n // Ignore cleanup errors\n }\n superdocRef.current = null;\n }\n readyRef.current = false;\n }, []);\n\n /**\n * Create a new SuperDoc instance with the given options\n */\n const createSuperdoc = useCallback(\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n async (options: { document?: File; html?: string }): Promise<{ superdoc: SuperDocInstance; json: ProseMirrorJSON }> => {\n if (!SuperDocRef.current) {\n throw new Error('SuperDoc not loaded');\n }\n if (!containerRef.current) {\n throw new Error('Container not available');\n }\n\n // Set IDs on DOM elements\n containerRef.current.id = editorId;\n if (toolbarRef.current) {\n toolbarRef.current.id = toolbarId;\n }\n\n return new Promise((resolve, reject) => {\n try {\n const superdoc = new SuperDocRef.current({\n selector: `#${editorId}`,\n toolbar: showToolbar ? `#${toolbarId}` : undefined,\n document: options.document,\n html: options.html,\n documentMode: 'editing',\n role: 'editor',\n rulers: showRulers,\n user: DEFAULT_SUPERDOC_USER,\n permissionResolver,\n // Enable comments module for track changes sidebar\n modules: { comments: {} },\n onReady: ({ superdoc: sd }: { superdoc: SuperDocInstance }) => {\n superdocRef.current = sd;\n readyRef.current = true;\n\n // Extract JSON from the loaded document\n let json: ProseMirrorJSON = { type: 'doc', content: [] };\n if (sd?.activeEditor) {\n try {\n json = sd.activeEditor.getJSON();\n } catch (err) {\n console.error('Failed to extract JSON:', err);\n }\n }\n\n resolve({ superdoc: sd, json });\n },\n onException: ({ error: err }: { error: Error }) => {\n console.error('SuperDoc error:', err);\n reject(err);\n },\n });\n\n superdocRef.current = superdoc;\n\n // Timeout\n setTimeout(() => {\n if (!readyRef.current) {\n reject(new Error('SuperDoc initialization timed out'));\n }\n }, TIMEOUTS.PARSE_TIMEOUT);\n } catch (err) {\n reject(err);\n }\n });\n },\n [editorId, toolbarId, showToolbar, showRulers]\n );\n\n /**\n * Initialize SuperDoc instance\n */\n const initialize = useCallback(async () => {\n if (initRef.current || !containerRef.current || !mountedRef.current) return;\n if (!showToolbar && !toolbarRef.current) {\n // Continue without toolbar\n } else if (showToolbar && !toolbarRef.current) {\n return;\n }\n\n initRef.current = true;\n\n // Small delay for React to settle\n await new Promise((resolve) => setTimeout(resolve, TIMEOUTS.INIT_DELAY));\n\n if (!mountedRef.current || !containerRef.current) {\n initRef.current = false;\n return;\n }\n\n setIsLoading(true);\n setError(null);\n destroySuperdoc();\n\n try {\n // Note: superdoc CSS is bundled in dist/styles.css - user must import 'docx-diff-editor/styles.css'\n const { SuperDoc } = await import('superdoc');\n SuperDocRef.current = SuperDoc;\n\n // Determine initialization options based on initialSource\n let initOptions: { document?: File; html?: string } = {};\n\n if (initialSource) {\n const contentType = detectContentType(initialSource);\n if (contentType === 'file') {\n initOptions = { document: initialSource as File };\n } else if (contentType === 'html') {\n // Initialize directly with HTML - SuperDoc creates blank document internally\n initOptions = { html: initialSource as string };\n } else if (contentType === 'json') {\n // For JSON, we need a document first, then set content\n // Use template if provided, otherwise SuperDoc will create blank\n initOptions = templateDocx ? { document: templateDocx } : {};\n }\n } else if (templateDocx) {\n initOptions = { document: templateDocx };\n }\n // If no initialSource and no template, SuperDoc creates a blank document\n\n const { superdoc: sd, json } = await createSuperdoc(initOptions);\n\n // For JSON content, set it after initialization\n if (initialSource && detectContentType(initialSource) === 'json') {\n if (sd?.activeEditor && isProseMirrorJSON(initialSource)) {\n setEditorContent(sd.activeEditor, initialSource as ProseMirrorJSON);\n setSourceJson(initialSource as ProseMirrorJSON);\n onSourceLoaded?.(initialSource as ProseMirrorJSON);\n }\n } else {\n setSourceJson(json);\n onSourceLoaded?.(json);\n }\n\n setIsLoading(false);\n onReady?.();\n } catch (err) {\n console.error('Failed to initialize SuperDoc:', err);\n handleError(err instanceof Error ? err : new Error('Failed to load editor'));\n setIsLoading(false);\n }\n\n initRef.current = false;\n }, [\n initialSource,\n showRulers,\n showToolbar,\n templateDocx,\n onReady,\n onSourceLoaded,\n destroySuperdoc,\n createSuperdoc,\n setEditorContent,\n handleError,\n ]);\n\n // Initialize on mount\n useEffect(() => {\n mountedRef.current = true;\n initialize();\n\n return () => {\n mountedRef.current = false;\n destroySuperdoc();\n };\n }, [initialize, destroySuperdoc]);\n\n // =========================================================================\n // Imperative API\n // =========================================================================\n\n useImperativeHandle(\n ref,\n () => ({\n /**\n * Set the source/base document\n */\n async setSource(content: DocxContent): Promise<void> {\n if (!SuperDocRef.current) {\n throw new Error('Editor not initialized');\n }\n\n setIsLoading(true);\n setError(null);\n\n try {\n const contentType = detectContentType(content);\n let json: ProseMirrorJSON;\n\n // Destroy current instance and create new one\n destroySuperdoc();\n\n if (contentType === 'file') {\n // Initialize with DOCX file\n const result = await createSuperdoc({ document: content as File });\n json = result.json;\n } else if (contentType === 'html') {\n // Initialize directly with HTML - no template needed!\n // SuperDoc will create a blank document and apply HTML internally\n const result = await createSuperdoc({ html: content as string });\n json = result.json;\n } else {\n // JSON content - initialize blank then set content\n const result = await createSuperdoc(templateDocx ? { document: templateDocx } : {});\n if (result.superdoc?.activeEditor && isProseMirrorJSON(content)) {\n setEditorContent(result.superdoc.activeEditor, content as ProseMirrorJSON);\n json = content as ProseMirrorJSON;\n } else {\n json = result.json;\n }\n }\n\n setSourceJson(json);\n setMergedJson(null);\n setDiffResult(null);\n setEditingMode(superdocRef.current!);\n onSourceLoaded?.(json);\n } catch (err) {\n handleError(err instanceof Error ? err : new Error('Failed to set source'));\n throw err;\n } finally {\n setIsLoading(false);\n }\n },\n\n /**\n * Compare source with new content, show track changes\n */\n async compareWith(content: DocxContent): Promise<ComparisonResult> {\n if (!SuperDocRef.current) {\n throw new Error('Editor not initialized');\n }\n if (!sourceJson) {\n throw new Error('No source document set. Call setSource() first.');\n }\n\n setIsLoading(true);\n try {\n const contentType = detectContentType(content);\n let newJson: ProseMirrorJSON;\n\n if (contentType === 'file') {\n // Parse DOCX file using hidden SuperDoc instance\n newJson = await parseDocxFile(content as File, SuperDocRef.current);\n } else if (contentType === 'html') {\n // Parse HTML using a temporary SuperDoc instance\n const tempContainer = document.createElement('div');\n tempContainer.style.cssText = 'position:absolute;top:-9999px;left:-9999px;width:800px;height:600px;visibility:hidden;';\n document.body.appendChild(tempContainer);\n\n try {\n newJson = await new Promise((resolve, reject) => {\n const tempSuperdoc = new SuperDocRef.current({\n selector: tempContainer,\n html: content as string,\n documentMode: 'viewing',\n rulers: false,\n user: { name: 'Parser', email: 'parser@local' },\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n onReady: ({ superdoc: sd }: { superdoc: any }) => {\n try {\n const json = sd?.activeEditor?.getJSON() || { type: 'doc', content: [] };\n setTimeout(() => {\n try { sd?.destroy?.(); } catch { /* ignore */ }\n tempContainer.parentNode?.removeChild(tempContainer);\n }, 100);\n resolve(json);\n } catch (err) {\n reject(err);\n }\n },\n onException: ({ error: err }: { error: Error }) => {\n tempContainer.parentNode?.removeChild(tempContainer);\n reject(err);\n },\n });\n\n setTimeout(() => {\n try { tempSuperdoc?.destroy?.(); } catch { /* ignore */ }\n tempContainer.parentNode?.removeChild(tempContainer);\n reject(new Error('HTML parsing timed out'));\n }, TIMEOUTS.PARSE_TIMEOUT);\n });\n } catch (err) {\n tempContainer.parentNode?.removeChild(tempContainer);\n throw err;\n }\n } else {\n // JSON content - use directly\n if (!isProseMirrorJSON(content)) {\n throw new Error('Invalid ProseMirror JSON structure');\n }\n newJson = content as ProseMirrorJSON;\n }\n\n // Diff the documents\n const diff = diffDocuments(sourceJson, newJson);\n setDiffResult(diff);\n\n // Merge with track changes\n const merged = mergeDocuments(sourceJson, newJson, diff, author);\n setMergedJson(merged);\n\n // Update editor with merged content\n if (superdocRef.current?.activeEditor) {\n // Switch to suggesting mode to enable track bubbles sidebar\n if (superdocRef.current.setDocumentMode) {\n superdocRef.current.setDocumentMode('suggesting');\n }\n setEditorContent(superdocRef.current.activeEditor, merged);\n enableReviewMode(superdocRef.current);\n }\n\n // Build result\n const insertions = diff.segments.filter((s) => s.type === 'insert').length;\n const deletions = diff.segments.filter((s) => s.type === 'delete').length;\n const formatChanges = diff.formatChanges?.length || 0;\n\n const result: ComparisonResult = {\n totalChanges: insertions + deletions + formatChanges,\n insertions,\n deletions,\n formatChanges,\n summary: diff.summary,\n mergedJson: merged,\n };\n\n onComparisonComplete?.(result);\n return result;\n } catch (err) {\n handleError(err instanceof Error ? err : new Error('Comparison failed'));\n throw err;\n } finally {\n setIsLoading(false);\n }\n },\n\n /**\n * Get raw diff segments\n */\n getDiffSegments(): DiffSegment[] {\n return diffResult?.segments || [];\n },\n\n /**\n * Get enriched changes with context for LLM processing\n */\n getEnrichedChangesContext(): EnrichedChange[] {\n if (!mergedJson) return [];\n return extractEnrichedChanges(mergedJson);\n },\n\n /**\n * Get current document content as JSON\n */\n getContent(): ProseMirrorJSON {\n if (superdocRef.current?.activeEditor) {\n return superdocRef.current.activeEditor.getJSON();\n }\n return mergedJson || sourceJson || { type: 'doc', content: [] };\n },\n\n /**\n * Get source document JSON (before comparison)\n */\n getSourceContent(): ProseMirrorJSON | null {\n return sourceJson;\n },\n\n /**\n * Export current document to DOCX blob\n */\n async exportDocx(): Promise<Blob> {\n if (!superdocRef.current?.activeEditor) {\n throw new Error('Editor not ready');\n }\n\n const blob = await superdocRef.current.activeEditor.exportDocx({\n isFinalDoc: false,\n });\n\n if (!blob) {\n throw new Error('Export returned no data');\n }\n\n return blob;\n },\n\n /**\n * Reset to source state (clear comparison)\n */\n resetComparison(): void {\n if (sourceJson && superdocRef.current?.activeEditor) {\n setEditorContent(superdocRef.current.activeEditor, sourceJson);\n setEditingMode(superdocRef.current);\n setMergedJson(null);\n setDiffResult(null);\n }\n },\n\n /**\n * Check if editor is ready\n */\n isReady(): boolean {\n return readyRef.current;\n },\n }),\n [\n sourceJson,\n mergedJson,\n diffResult,\n templateDocx,\n author,\n destroySuperdoc,\n createSuperdoc,\n setEditorContent,\n enableReviewMode,\n setEditingMode,\n onSourceLoaded,\n onComparisonComplete,\n handleError,\n ]\n );\n\n // =========================================================================\n // Render\n // =========================================================================\n\n return (\n <div className={`dde-container ${className}`.trim()}>\n {/* Loading overlay */}\n {isLoading && (\n <div className=\"dde-loading\">\n <div className=\"dde-loading__spinner\" />\n <p className=\"dde-loading__text\">Loading document...</p>\n </div>\n )}\n\n {/* Error overlay */}\n {error && (\n <div className=\"dde-error\">\n <div className=\"dde-error__icon\">\n <svg\n className=\"dde-error__svg\"\n fill=\"none\"\n stroke=\"currentColor\"\n viewBox=\"0 0 24 24\"\n >\n <path\n strokeLinecap=\"round\"\n strokeLinejoin=\"round\"\n strokeWidth=\"2\"\n d=\"M12 8v4m0 4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z\"\n />\n </svg>\n </div>\n <p className=\"dde-error__title\">Failed to load document</p>\n <p className=\"dde-error__message\">{error}</p>\n </div>\n )}\n\n {/* Toolbar */}\n {showToolbar && (\n <div\n ref={toolbarRef}\n className={`dde-toolbar ${toolbarClassName}`.trim()}\n />\n )}\n\n {/* Editor container */}\n <div\n ref={containerRef}\n className={`dde-editor ${editorClassName}`.trim()}\n />\n </div>\n );\n }\n);\n\nexport default DocxDiffEditor;\n","/**\n * Embedded DOCX template\n *\n * This is a base64-encoded blank DOCX file created with Microsoft Word.\n * It provides the complete schema, styles, themes, and fonts needed to\n * initialize SuperDoc when working with HTML or JSON content.\n *\n * The DOCX contains all standard Word document components:\n * - [Content_Types].xml\n * - _rels/.rels\n * - word/document.xml\n * - word/_rels/document.xml.rels\n * - word/styles.xml (full Word styles)\n * - word/settings.xml\n * - word/fontTable.xml\n * - word/webSettings.xml\n * - word/theme/theme1.xml\n * - docProps/core.xml\n * - docProps/app.xml\n */\n\n/**\n * Base64-encoded blank DOCX file created with Microsoft Word.\n */\nconst BLANK_DOCX_BASE64 = `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`;\n\n/**\n * Convert base64 string to Blob\n */\nfunction base64ToBlob(base64: string, mimeType: string): Blob {\n const byteCharacters = atob(base64.replace(/\\s/g, ''));\n const byteNumbers = new Array(byteCharacters.length);\n\n for (let i = 0; i < byteCharacters.length; i++) {\n byteNumbers[i] = byteCharacters.charCodeAt(i);\n }\n\n const byteArray = new Uint8Array(byteNumbers);\n return new Blob([byteArray], { type: mimeType });\n}\n\n/**\n * Convert base64 string to File\n */\nfunction base64ToFile(base64: string, filename: string, mimeType: string): File {\n const blob = base64ToBlob(base64, mimeType);\n return new File([blob], filename, { type: mimeType });\n}\n\n/**\n * Get the blank DOCX template as a File object\n */\nexport function getBlankTemplateFile(): File {\n return base64ToFile(\n BLANK_DOCX_BASE64,\n 'blank-template.docx',\n 'application/vnd.openxmlformats-officedocument.wordprocessingml.document'\n );\n}\n\n/**\n * Get the blank DOCX template as a Blob\n */\nexport function getBlankTemplateBlob(): Blob {\n return base64ToBlob(\n BLANK_DOCX_BASE64,\n 'application/vnd.openxmlformats-officedocument.wordprocessingml.document'\n );\n}\n\n/**\n * Check if a File is a valid DOCX file (basic check)\n */\nexport function isValidDocxFile(file: File): boolean {\n const validTypes = [\n 'application/vnd.openxmlformats-officedocument.wordprocessingml.document',\n 'application/msword',\n ];\n return validTypes.includes(file.type) || file.name.endsWith('.docx');\n}\n"]}
package/dist/styles.css CHANGED
@@ -1,3 +1,20 @@
1
+ /* ==========================================================================
2
+ DocxDiffEditor Styles
3
+
4
+ This CSS uses @layer to ensure proper specificity over CSS frameworks
5
+ like Tailwind that use aggressive resets.
6
+
7
+ Layer order (lowest to highest priority):
8
+ 1. base - CSS framework base/reset styles
9
+ 2. superdoc - SuperDoc editor styles
10
+ 3. dde - DocxDiffEditor custom styles
11
+ ========================================================================== */
12
+
13
+ /* Define layer order - later layers have higher priority */
14
+ @layer base, superdoc, dde;
15
+
16
+ /* SuperDoc styles in their own layer */
17
+ @layer superdoc {
1
18
  :root {
2
19
  /* CSS variables */
3
20
  }
@@ -5417,6 +5434,11 @@ img[data-v-7dd69850] {
5417
5434
  background-color: #1355ff66;
5418
5435
  mix-blend-mode: difference;
5419
5436
  }
5437
+
5438
+ }
5439
+
5440
+ /* DocxDiffEditor custom styles */
5441
+ @layer dde {
5420
5442
  /**
5421
5443
  * DocxDiffEditor Styles
5422
5444
  *
@@ -5453,6 +5475,7 @@ img[data-v-7dd69850] {
5453
5475
  /* Track Changes - SuperDoc track change styling */
5454
5476
  /* @import './track-changes.css'; */
5455
5477
 
5478
+
5456
5479
  /**
5457
5480
  * CSS Variables for DocxDiffEditor
5458
5481
  * Users can override these in their own CSS to customize the component.
@@ -5518,6 +5541,7 @@ img[data-v-7dd69850] {
5518
5541
  --dde-z-error: 100;
5519
5542
  }
5520
5543
 
5544
+
5521
5545
  /**
5522
5546
  * Base styles for DocxDiffEditor
5523
5547
  * Container layout and structure.
@@ -5555,6 +5579,7 @@ img[data-v-7dd69850] {
5555
5579
  height: 100%;
5556
5580
  }
5557
5581
 
5582
+
5558
5583
  /**
5559
5584
  * Loading state styles for DocxDiffEditor
5560
5585
  */
@@ -5599,6 +5624,7 @@ img[data-v-7dd69850] {
5599
5624
  }
5600
5625
  }
5601
5626
 
5627
+
5602
5628
  /**
5603
5629
  * Error state styles for DocxDiffEditor
5604
5630
  */
@@ -5645,6 +5671,7 @@ img[data-v-7dd69850] {
5645
5671
  max-width: 400px;
5646
5672
  }
5647
5673
 
5674
+
5648
5675
  /**
5649
5676
  * Track Changes styles for DocxDiffEditor
5650
5677
  * Styles for SuperDoc track change marks (insert, delete, format).
@@ -5801,3 +5828,5 @@ img[data-v-7dd69850] {
5801
5828
  outline-offset: 1px;
5802
5829
  }
5803
5830
 
5831
+
5832
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "docx-diff-editor",
3
- "version": "1.0.6",
3
+ "version": "1.0.9",
4
4
  "description": "React component for DOCX document comparison with track changes visualization",
5
5
  "license": "Apache-2.0",
6
6
  "author": "Pablo Schaffner",
@@ -45,7 +45,7 @@
45
45
  ],
46
46
  "scripts": {
47
47
  "build": "tsup && npm run build:css",
48
- "build:css": "cat node_modules/superdoc/dist/style.css src/styles/index.css src/styles/variables.css src/styles/base.css src/styles/loading.css src/styles/error.css src/styles/track-changes.css > dist/styles.css",
48
+ "build:css": "node scripts/build-css.js",
49
49
  "dev": "tsup --watch",
50
50
  "clean": "rm -rf dist",
51
51
  "prepublishOnly": "npm run build",