@wonderwhy-er/desktop-commander 0.2.36 → 0.2.38
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/README.md +240 -100
- package/dist/command-manager.js +6 -3
- package/dist/config-field-definitions.d.ts +41 -0
- package/dist/config-field-definitions.js +37 -0
- package/dist/config-manager.d.ts +2 -0
- package/dist/config-manager.js +22 -2
- package/dist/handlers/filesystem-handlers.js +6 -11
- package/dist/handlers/macos-control-handlers.d.ts +16 -0
- package/dist/handlers/macos-control-handlers.js +81 -0
- package/dist/lib.d.ts +10 -0
- package/dist/lib.js +10 -0
- package/dist/remote-device/remote-channel.d.ts +8 -3
- package/dist/remote-device/remote-channel.js +68 -21
- package/dist/search-manager.d.ts +13 -0
- package/dist/search-manager.js +146 -0
- package/dist/server.js +29 -1
- package/dist/test-docx.d.ts +1 -0
- package/dist/tools/config.d.ts +71 -0
- package/dist/tools/config.js +117 -2
- package/dist/tools/docx/builders/table.d.ts +2 -0
- package/dist/tools/docx/builders/table.js +60 -16
- package/dist/tools/docx/dom.d.ts +74 -1
- package/dist/tools/docx/dom.js +221 -1
- package/dist/tools/docx/index.d.ts +2 -2
- package/dist/tools/docx/ops/index.js +3 -0
- package/dist/tools/docx/ops/replace-paragraph-text-exact.d.ts +15 -3
- package/dist/tools/docx/ops/replace-paragraph-text-exact.js +25 -10
- package/dist/tools/docx/ops/replace-table-cell-text.d.ts +25 -0
- package/dist/tools/docx/ops/replace-table-cell-text.js +85 -0
- package/dist/tools/docx/ops/set-color-for-paragraph-exact.d.ts +2 -1
- package/dist/tools/docx/ops/set-color-for-paragraph-exact.js +9 -8
- package/dist/tools/docx/ops/set-color-for-style.d.ts +4 -0
- package/dist/tools/docx/ops/set-color-for-style.js +11 -7
- package/dist/tools/docx/ops/table-set-cell-text.js +8 -40
- package/dist/tools/docx/read.d.ts +2 -2
- package/dist/tools/docx/read.js +137 -17
- package/dist/tools/docx/types.d.ts +32 -3
- package/dist/tools/docx/xml-view-test.d.ts +1 -0
- package/dist/tools/docx/xml-view-test.js +63 -0
- package/dist/tools/docx/xml-view.d.ts +56 -0
- package/dist/tools/docx/xml-view.js +169 -0
- package/dist/tools/edit.js +57 -27
- package/dist/tools/macos-control/ax-adapter.d.ts +55 -0
- package/dist/tools/macos-control/ax-adapter.js +438 -0
- package/dist/tools/macos-control/cdp-adapter.d.ts +23 -0
- package/dist/tools/macos-control/cdp-adapter.js +402 -0
- package/dist/tools/macos-control/orchestrator.d.ts +77 -0
- package/dist/tools/macos-control/orchestrator.js +136 -0
- package/dist/tools/macos-control/role-aliases.d.ts +5 -0
- package/dist/tools/macos-control/role-aliases.js +34 -0
- package/dist/tools/macos-control/types.d.ts +129 -0
- package/dist/tools/macos-control/types.js +1 -0
- package/dist/tools/schemas.d.ts +3 -0
- package/dist/tools/schemas.js +2 -1
- package/dist/types.d.ts +0 -1
- package/dist/ui/config-editor/config-editor-runtime.js +14181 -0
- package/dist/ui/config-editor/index.html +13 -0
- package/dist/ui/config-editor/src/app.d.ts +43 -0
- package/dist/ui/config-editor/src/app.js +840 -0
- package/dist/ui/config-editor/src/array-modal.d.ts +19 -0
- package/dist/ui/config-editor/src/array-modal.js +185 -0
- package/dist/ui/config-editor/src/main.d.ts +1 -0
- package/dist/ui/config-editor/src/main.js +2 -0
- package/dist/ui/config-editor/styles.css +586 -0
- package/dist/ui/file-preview/preview-runtime.js +13337 -752
- package/dist/ui/file-preview/shared/preview-file-types.js +3 -1
- package/dist/ui/file-preview/src/app.d.ts +5 -1
- package/dist/ui/file-preview/src/app.js +114 -200
- package/dist/ui/file-preview/src/components/html-renderer.d.ts +1 -5
- package/dist/ui/file-preview/src/components/html-renderer.js +11 -27
- package/dist/ui/file-preview/styles.css +117 -83
- package/dist/ui/resources.d.ts +7 -0
- package/dist/ui/resources.js +16 -2
- package/dist/ui/shared/compact-row.d.ts +11 -0
- package/dist/ui/shared/compact-row.js +18 -0
- package/dist/ui/shared/host-context.d.ts +15 -0
- package/dist/ui/shared/host-context.js +51 -0
- package/dist/ui/shared/tool-bridge.d.ts +30 -0
- package/dist/ui/shared/tool-bridge.js +137 -0
- package/dist/ui/shared/tool-shell.d.ts +9 -0
- package/dist/ui/shared/tool-shell.js +46 -4
- package/dist/ui/shared/ui-event-tracker.d.ts +9 -0
- package/dist/ui/shared/ui-event-tracker.js +27 -0
- package/dist/utils/capture.js +173 -11
- package/dist/utils/files/base.d.ts +3 -1
- package/dist/utils/files/docx.d.ts +28 -15
- package/dist/utils/files/docx.js +622 -88
- package/dist/utils/files/factory.d.ts +6 -5
- package/dist/utils/files/factory.js +18 -6
- package/dist/utils/system-info.js +1 -1
- package/dist/utils/usageTracker.js +5 -0
- package/dist/version.d.ts +1 -1
- package/dist/version.js +1 -1
- package/package.json +8 -3
package/dist/tools/config.d.ts
CHANGED
|
@@ -6,6 +6,77 @@ export declare function getConfig(): Promise<{
|
|
|
6
6
|
type: string;
|
|
7
7
|
text: string;
|
|
8
8
|
}[];
|
|
9
|
+
structuredContent: {
|
|
10
|
+
config: {
|
|
11
|
+
currentClient: {
|
|
12
|
+
name: string;
|
|
13
|
+
version: string;
|
|
14
|
+
};
|
|
15
|
+
featureFlags: Record<string, any>;
|
|
16
|
+
systemInfo: {
|
|
17
|
+
memory: {
|
|
18
|
+
rss: string;
|
|
19
|
+
heapTotal: string;
|
|
20
|
+
heapUsed: string;
|
|
21
|
+
external: string;
|
|
22
|
+
arrayBuffers: string;
|
|
23
|
+
};
|
|
24
|
+
platform: string;
|
|
25
|
+
platformName: string;
|
|
26
|
+
defaultShell: string;
|
|
27
|
+
pathSeparator: string;
|
|
28
|
+
isWindows: boolean;
|
|
29
|
+
isMacOS: boolean;
|
|
30
|
+
isLinux: boolean;
|
|
31
|
+
docker: import("../utils/system-info.js").ContainerInfo;
|
|
32
|
+
isDXT: boolean;
|
|
33
|
+
nodeInfo?: {
|
|
34
|
+
version: string;
|
|
35
|
+
path: string;
|
|
36
|
+
npmVersion?: string;
|
|
37
|
+
};
|
|
38
|
+
pythonInfo?: {
|
|
39
|
+
available: boolean;
|
|
40
|
+
command: string;
|
|
41
|
+
version?: string;
|
|
42
|
+
};
|
|
43
|
+
processInfo: {
|
|
44
|
+
pid: number;
|
|
45
|
+
arch: string;
|
|
46
|
+
platform: string;
|
|
47
|
+
versions: NodeJS.ProcessVersions;
|
|
48
|
+
};
|
|
49
|
+
examplePaths: {
|
|
50
|
+
home: string;
|
|
51
|
+
temp: string;
|
|
52
|
+
absolute: string;
|
|
53
|
+
accessible?: string[];
|
|
54
|
+
};
|
|
55
|
+
};
|
|
56
|
+
blockedCommands?: string[];
|
|
57
|
+
defaultShell?: string;
|
|
58
|
+
allowedDirectories?: string[];
|
|
59
|
+
telemetryEnabled?: boolean;
|
|
60
|
+
fileWriteLineLimit?: number;
|
|
61
|
+
fileReadLineLimit?: number;
|
|
62
|
+
clientId?: string;
|
|
63
|
+
};
|
|
64
|
+
uiHints: {
|
|
65
|
+
availableShells: string[];
|
|
66
|
+
};
|
|
67
|
+
entries: {
|
|
68
|
+
key: "defaultShell" | "blockedCommands" | "allowedDirectories" | "telemetryEnabled" | "fileReadLineLimit" | "fileWriteLineLimit";
|
|
69
|
+
value: unknown;
|
|
70
|
+
valueType: "string" | "number" | "boolean" | "array";
|
|
71
|
+
editable: boolean;
|
|
72
|
+
}[];
|
|
73
|
+
};
|
|
74
|
+
} | {
|
|
75
|
+
content: {
|
|
76
|
+
type: string;
|
|
77
|
+
text: string;
|
|
78
|
+
}[];
|
|
79
|
+
structuredContent?: undefined;
|
|
9
80
|
}>;
|
|
10
81
|
/**
|
|
11
82
|
* Set a specific config value
|
package/dist/tools/config.js
CHANGED
|
@@ -3,6 +3,74 @@ import { SetConfigValueArgsSchema } from './schemas.js';
|
|
|
3
3
|
import { getSystemInfo } from '../utils/system-info.js';
|
|
4
4
|
import { currentClient } from '../server.js';
|
|
5
5
|
import { featureFlagManager } from '../utils/feature-flags.js';
|
|
6
|
+
import { access, readFile } from 'node:fs/promises';
|
|
7
|
+
import { constants as fsConstants } from 'node:fs';
|
|
8
|
+
import { CONFIG_FIELD_DEFINITIONS, CONFIG_FIELD_KEYS, isConfigFieldKey, } from '../config-field-definitions.js';
|
|
9
|
+
const ALLOWED_CONFIG_KEYS = new Set(CONFIG_FIELD_KEYS);
|
|
10
|
+
async function pathExists(pathValue) {
|
|
11
|
+
try {
|
|
12
|
+
await access(pathValue, fsConstants.X_OK);
|
|
13
|
+
return true;
|
|
14
|
+
}
|
|
15
|
+
catch {
|
|
16
|
+
return false;
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
async function detectAvailableShells(systemInfo) {
|
|
20
|
+
const detected = new Set();
|
|
21
|
+
const add = (shell) => {
|
|
22
|
+
if (shell.trim().length > 0) {
|
|
23
|
+
detected.add(shell.trim());
|
|
24
|
+
}
|
|
25
|
+
};
|
|
26
|
+
add(systemInfo.defaultShell);
|
|
27
|
+
if (systemInfo.isWindows) {
|
|
28
|
+
add(process.env.ComSpec ?? '');
|
|
29
|
+
const systemRoot = process.env.SystemRoot ?? 'C:\\Windows';
|
|
30
|
+
const candidates = [
|
|
31
|
+
`${systemRoot}\\System32\\WindowsPowerShell\\v1.0\\powershell.exe`,
|
|
32
|
+
`${systemRoot}\\System32\\cmd.exe`,
|
|
33
|
+
`${systemRoot}\\System32\\bash.exe`,
|
|
34
|
+
'powershell.exe',
|
|
35
|
+
'pwsh.exe',
|
|
36
|
+
'cmd.exe',
|
|
37
|
+
'bash.exe',
|
|
38
|
+
];
|
|
39
|
+
for (const shell of candidates) {
|
|
40
|
+
if (shell.includes('\\')) {
|
|
41
|
+
if (await pathExists(shell)) {
|
|
42
|
+
add(shell);
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
else {
|
|
46
|
+
add(shell);
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
return [...detected];
|
|
50
|
+
}
|
|
51
|
+
add(process.env.SHELL ?? '');
|
|
52
|
+
const shellFiles = ['/etc/shells'];
|
|
53
|
+
for (const shellFile of shellFiles) {
|
|
54
|
+
try {
|
|
55
|
+
const content = await readFile(shellFile, 'utf8');
|
|
56
|
+
content
|
|
57
|
+
.split(/\r?\n/)
|
|
58
|
+
.map((line) => line.trim())
|
|
59
|
+
.filter((line) => line.length > 0 && !line.startsWith('#'))
|
|
60
|
+
.forEach(add);
|
|
61
|
+
}
|
|
62
|
+
catch {
|
|
63
|
+
// Best-effort discovery only.
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
const fallbackCandidates = ['/bin/zsh', '/bin/bash', '/bin/sh', '/usr/bin/fish'];
|
|
67
|
+
for (const shell of fallbackCandidates) {
|
|
68
|
+
if (await pathExists(shell)) {
|
|
69
|
+
add(shell);
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
return [...detected];
|
|
73
|
+
}
|
|
6
74
|
/**
|
|
7
75
|
* Get the entire config including system information
|
|
8
76
|
*/
|
|
@@ -30,12 +98,29 @@ export async function getConfig() {
|
|
|
30
98
|
memory
|
|
31
99
|
}
|
|
32
100
|
};
|
|
101
|
+
const availableShells = await detectAvailableShells(systemInfo);
|
|
33
102
|
console.error(`getConfig result: ${JSON.stringify(configWithSystemInfo, null, 2)}`);
|
|
34
103
|
return {
|
|
35
104
|
content: [{
|
|
36
105
|
type: "text",
|
|
37
106
|
text: `Current configuration:\n${JSON.stringify(configWithSystemInfo, null, 2)}`
|
|
38
107
|
}],
|
|
108
|
+
structuredContent: {
|
|
109
|
+
config: configWithSystemInfo,
|
|
110
|
+
uiHints: {
|
|
111
|
+
availableShells,
|
|
112
|
+
},
|
|
113
|
+
entries: CONFIG_FIELD_KEYS.map((key) => {
|
|
114
|
+
const definition = CONFIG_FIELD_DEFINITIONS[key];
|
|
115
|
+
const value = configWithSystemInfo[key];
|
|
116
|
+
return {
|
|
117
|
+
key,
|
|
118
|
+
value,
|
|
119
|
+
valueType: definition.valueType,
|
|
120
|
+
editable: true,
|
|
121
|
+
};
|
|
122
|
+
}),
|
|
123
|
+
},
|
|
39
124
|
};
|
|
40
125
|
}
|
|
41
126
|
catch (error) {
|
|
@@ -67,7 +152,17 @@ export async function setConfigValue(args) {
|
|
|
67
152
|
isError: true
|
|
68
153
|
};
|
|
69
154
|
}
|
|
155
|
+
if (!isConfigFieldKey(parsed.data.key)) {
|
|
156
|
+
return {
|
|
157
|
+
content: [{
|
|
158
|
+
type: "text",
|
|
159
|
+
text: `Key "${parsed.data.key}" is not configurable via this tool. Allowed keys: ${[...ALLOWED_CONFIG_KEYS].join(', ')}`
|
|
160
|
+
}],
|
|
161
|
+
isError: true
|
|
162
|
+
};
|
|
163
|
+
}
|
|
70
164
|
try {
|
|
165
|
+
const fieldDefinition = CONFIG_FIELD_DEFINITIONS[parsed.data.key];
|
|
71
166
|
// Parse string values that should be arrays or objects
|
|
72
167
|
let valueToStore = parsed.data.value;
|
|
73
168
|
// If the value is a string that looks like an array or object, try to parse it
|
|
@@ -82,8 +177,7 @@ export async function setConfigValue(args) {
|
|
|
82
177
|
}
|
|
83
178
|
}
|
|
84
179
|
// Special handling for known array configuration keys
|
|
85
|
-
if (
|
|
86
|
-
!Array.isArray(valueToStore)) {
|
|
180
|
+
if (fieldDefinition.valueType === 'array' && !Array.isArray(valueToStore)) {
|
|
87
181
|
if (typeof valueToStore === 'string') {
|
|
88
182
|
const originalString = valueToStore;
|
|
89
183
|
try {
|
|
@@ -108,6 +202,27 @@ export async function setConfigValue(args) {
|
|
|
108
202
|
valueToStore = [String(valueToStore)];
|
|
109
203
|
}
|
|
110
204
|
}
|
|
205
|
+
// Harden boolean fields against stringly-typed inputs like "false".
|
|
206
|
+
if (fieldDefinition.valueType === 'boolean') {
|
|
207
|
+
if (typeof valueToStore === 'string') {
|
|
208
|
+
const normalized = valueToStore.trim().toLowerCase();
|
|
209
|
+
if (normalized === 'true') {
|
|
210
|
+
valueToStore = true;
|
|
211
|
+
}
|
|
212
|
+
else if (normalized === 'false') {
|
|
213
|
+
valueToStore = false;
|
|
214
|
+
}
|
|
215
|
+
}
|
|
216
|
+
if (typeof valueToStore !== 'boolean') {
|
|
217
|
+
return {
|
|
218
|
+
content: [{
|
|
219
|
+
type: "text",
|
|
220
|
+
text: `Value for ${parsed.data.key} must be boolean true/false.`
|
|
221
|
+
}],
|
|
222
|
+
isError: true
|
|
223
|
+
};
|
|
224
|
+
}
|
|
225
|
+
}
|
|
111
226
|
await configManager.setValue(parsed.data.key, valueToStore);
|
|
112
227
|
// Get the updated configuration to show the user
|
|
113
228
|
const updatedConfig = await configManager.getConfig();
|
|
@@ -1,8 +1,10 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* Table builder — creates w:tbl elements with headers, rows, and styling.
|
|
3
|
+
* Supports multiple paragraphs per cell with different styles.
|
|
3
4
|
*/
|
|
4
5
|
import type { DocxContentTable, InsertTableOp } from '../types.js';
|
|
5
6
|
/**
|
|
6
7
|
* Build a table element from content structure or operation.
|
|
8
|
+
* Supports cells with multiple paragraphs, each with its own style.
|
|
7
9
|
*/
|
|
8
10
|
export declare function buildTable(doc: Document, spec: DocxContentTable | InsertTableOp): Element;
|
|
@@ -1,8 +1,11 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* Table builder — creates w:tbl elements with headers, rows, and styling.
|
|
3
|
+
* Supports multiple paragraphs per cell with different styles.
|
|
3
4
|
*/
|
|
5
|
+
import { buildParagraph } from './paragraph.js';
|
|
4
6
|
/**
|
|
5
7
|
* Build a table element from content structure or operation.
|
|
8
|
+
* Supports cells with multiple paragraphs, each with its own style.
|
|
6
9
|
*/
|
|
7
10
|
export function buildTable(doc, spec) {
|
|
8
11
|
const tbl = doc.createElement('w:tbl');
|
|
@@ -29,12 +32,13 @@ export function buildTable(doc, spec) {
|
|
|
29
32
|
}
|
|
30
33
|
tblPr.appendChild(tblBorders);
|
|
31
34
|
tbl.appendChild(tblPr);
|
|
32
|
-
//
|
|
35
|
+
// Determine column count
|
|
33
36
|
const colCount = spec.headers
|
|
34
37
|
? spec.headers.length
|
|
35
38
|
: spec.rows.length > 0
|
|
36
39
|
? spec.rows[0].length
|
|
37
40
|
: 0;
|
|
41
|
+
// Table grid
|
|
38
42
|
if (colCount > 0) {
|
|
39
43
|
const tblGrid = doc.createElement('w:tblGrid');
|
|
40
44
|
for (let c = 0; c < colCount; c++) {
|
|
@@ -45,9 +49,15 @@ export function buildTable(doc, spec) {
|
|
|
45
49
|
}
|
|
46
50
|
tbl.appendChild(tblGrid);
|
|
47
51
|
}
|
|
48
|
-
|
|
49
|
-
|
|
52
|
+
/**
|
|
53
|
+
* Build a cell from content.
|
|
54
|
+
* Content can be:
|
|
55
|
+
* - A string: creates one paragraph with that text
|
|
56
|
+
* - An array of DocxContentParagraph: creates multiple paragraphs, each with its own style
|
|
57
|
+
*/
|
|
58
|
+
const buildCell = (content, isHeader, widthTwips) => {
|
|
50
59
|
const tc = doc.createElement('w:tc');
|
|
60
|
+
// Cell properties (width)
|
|
51
61
|
if (widthTwips) {
|
|
52
62
|
const tcPr = doc.createElement('w:tcPr');
|
|
53
63
|
const tcW = doc.createElement('w:tcW');
|
|
@@ -56,20 +66,54 @@ export function buildTable(doc, spec) {
|
|
|
56
66
|
tcPr.appendChild(tcW);
|
|
57
67
|
tc.appendChild(tcPr);
|
|
58
68
|
}
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
const
|
|
63
|
-
const
|
|
64
|
-
|
|
65
|
-
|
|
69
|
+
// Handle content: string or array of paragraphs
|
|
70
|
+
if (typeof content === 'string') {
|
|
71
|
+
// Simple case: single paragraph
|
|
72
|
+
const p = doc.createElement('w:p');
|
|
73
|
+
const r = doc.createElement('w:r');
|
|
74
|
+
// Header cells get bold
|
|
75
|
+
if (isHeader) {
|
|
76
|
+
const rPr = doc.createElement('w:rPr');
|
|
77
|
+
const b = doc.createElement('w:b');
|
|
78
|
+
rPr.appendChild(b);
|
|
79
|
+
r.appendChild(rPr);
|
|
80
|
+
}
|
|
81
|
+
const t = doc.createElement('w:t');
|
|
82
|
+
t.setAttribute('xml:space', 'preserve');
|
|
83
|
+
t.textContent = content;
|
|
84
|
+
r.appendChild(t);
|
|
85
|
+
p.appendChild(r);
|
|
86
|
+
tc.appendChild(p);
|
|
87
|
+
}
|
|
88
|
+
else {
|
|
89
|
+
// Complex case: multiple paragraphs with different styles
|
|
90
|
+
for (const paraSpec of content) {
|
|
91
|
+
const p = buildParagraph(doc, paraSpec);
|
|
92
|
+
// If header and first paragraph, ensure bold on runs
|
|
93
|
+
if (isHeader) {
|
|
94
|
+
const runs = p.getElementsByTagName('w:r');
|
|
95
|
+
for (let i = 0; i < runs.length; i++) {
|
|
96
|
+
const run = runs.item(i);
|
|
97
|
+
let rPr = run.getElementsByTagName('w:rPr').item(0);
|
|
98
|
+
if (!rPr) {
|
|
99
|
+
rPr = doc.createElement('w:rPr');
|
|
100
|
+
if (run.firstChild) {
|
|
101
|
+
run.insertBefore(rPr, run.firstChild);
|
|
102
|
+
}
|
|
103
|
+
else {
|
|
104
|
+
run.appendChild(rPr);
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
// Add bold if not already present
|
|
108
|
+
if (!rPr.getElementsByTagName('w:b').length) {
|
|
109
|
+
const b = doc.createElement('w:b');
|
|
110
|
+
rPr.appendChild(b);
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
}
|
|
114
|
+
tc.appendChild(p);
|
|
115
|
+
}
|
|
66
116
|
}
|
|
67
|
-
const t = doc.createElement('w:t');
|
|
68
|
-
t.setAttribute('xml:space', 'preserve');
|
|
69
|
-
t.textContent = text;
|
|
70
|
-
r.appendChild(t);
|
|
71
|
-
p.appendChild(r);
|
|
72
|
-
tc.appendChild(p);
|
|
73
117
|
return tc;
|
|
74
118
|
};
|
|
75
119
|
// Header row
|
package/dist/tools/docx/dom.d.ts
CHANGED
|
@@ -23,6 +23,17 @@ export declare function getBody(doc: Document): Element;
|
|
|
23
23
|
* Includes w:p, w:tbl, w:sdt, w:sectPr, etc.
|
|
24
24
|
*/
|
|
25
25
|
export declare function getBodyChildren(body: Element): Element[];
|
|
26
|
+
/**
|
|
27
|
+
* Return ALL top‑level tables that are logically in the body, including those
|
|
28
|
+
* wrapped in structured document tags (w:sdt / w:sdtContent).
|
|
29
|
+
*
|
|
30
|
+
* Previous logic only saw tables that were direct children of <w:body>. That
|
|
31
|
+
* meant tables inside SDTs were invisible to table operations and readDocxOutline.
|
|
32
|
+
* This helper walks the body tree and collects any <w:tbl> that appears as a
|
|
33
|
+
* *first‑class* block (we do not recurse into tables themselves, so nested
|
|
34
|
+
* tables are not double‑counted).
|
|
35
|
+
*/
|
|
36
|
+
export declare function getAllBodyTables(body: Element): Element[];
|
|
26
37
|
/**
|
|
27
38
|
* Build a compact signature string from the body children array.
|
|
28
39
|
* Maps each node's qualified name to a short local name:
|
|
@@ -34,13 +45,75 @@ export declare function bodySignature(children: Element[]): string;
|
|
|
34
45
|
export declare function getParagraphText(p: Element): string;
|
|
35
46
|
/** Read the style id from w:pPr/w:pStyle/@w:val, or null if absent. */
|
|
36
47
|
export declare function getParagraphStyle(p: Element): string | null;
|
|
48
|
+
/**
|
|
49
|
+
* Extract all text content from a table cell (w:tc).
|
|
50
|
+
* Returns the concatenated text from all paragraphs in the cell.
|
|
51
|
+
*/
|
|
52
|
+
export declare function getCellText(tc: Element): string;
|
|
53
|
+
/**
|
|
54
|
+
* Extract all rows from a table (w:tbl).
|
|
55
|
+
* Returns an array of rows, where each row is an array of cell text strings.
|
|
56
|
+
* First row is treated as header if it exists.
|
|
57
|
+
*/
|
|
58
|
+
export declare function getTableContent(tbl: Element): {
|
|
59
|
+
headers?: string[];
|
|
60
|
+
rows: string[][];
|
|
61
|
+
};
|
|
62
|
+
/**
|
|
63
|
+
* Get table style from w:tblPr/w:tblStyle/@w:val, or null if absent.
|
|
64
|
+
*/
|
|
65
|
+
export declare function getTableStyle(tbl: Element): string | null;
|
|
66
|
+
/**
|
|
67
|
+
* Extract image reference from a w:drawing element.
|
|
68
|
+
* Returns the relationship ID (rId) and media file path if found.
|
|
69
|
+
*/
|
|
70
|
+
export declare function getImageReference(drawing: Element): {
|
|
71
|
+
rId: string | null;
|
|
72
|
+
mediaPath: string | null;
|
|
73
|
+
};
|
|
37
74
|
/**
|
|
38
75
|
* Replace the text of a paragraph with minimal DOM changes.
|
|
39
76
|
* Sets the FIRST w:t to `text`, clears every subsequent w:t.
|
|
40
77
|
* Sets xml:space="preserve" so leading/trailing spaces survive.
|
|
41
|
-
* Does NOT recreate runs or remove paragraph properties.
|
|
78
|
+
* Does NOT remove/recreate runs or remove paragraph properties.
|
|
79
|
+
*
|
|
80
|
+
* WARNING: This function does NOT preserve multiple runs with different styles.
|
|
81
|
+
* Use setParagraphTextPreservingStyles() for cells with multiple styled runs.
|
|
42
82
|
*/
|
|
43
83
|
export declare function setParagraphTextMinimal(p: Element, text: string): void;
|
|
84
|
+
/**
|
|
85
|
+
* Replace paragraph text while preserving all run styles.
|
|
86
|
+
*
|
|
87
|
+
* This function preserves the structure of all runs (w:r) and their
|
|
88
|
+
* properties (w:rPr), distributing the new text across existing runs.
|
|
89
|
+
*
|
|
90
|
+
* Strategy:
|
|
91
|
+
* 1. Collect all runs with their properties
|
|
92
|
+
* 2. Distribute new text across runs (preserving run count and styles)
|
|
93
|
+
* 3. If new text is longer, extend the last run
|
|
94
|
+
* 4. If new text is shorter, clear excess runs but keep their structure
|
|
95
|
+
*/
|
|
96
|
+
export declare function setParagraphTextPreservingStyles(p: Element, text: string): void;
|
|
97
|
+
/**
|
|
98
|
+
* Replace cell text while preserving ALL paragraphs and their styles.
|
|
99
|
+
*
|
|
100
|
+
* This function works at the cell level:
|
|
101
|
+
* - Preserves ALL paragraphs in the cell (doesn't remove any)
|
|
102
|
+
* - Updates text in the first paragraph while preserving its styles
|
|
103
|
+
* - Keeps all other paragraphs intact with their original text and styles
|
|
104
|
+
*
|
|
105
|
+
* This ensures that cells with multiple paragraphs (each with different
|
|
106
|
+
* styles, font sizes, etc.) maintain their structure after text replacement.
|
|
107
|
+
*
|
|
108
|
+
* Example: If a cell has:
|
|
109
|
+
* - Paragraph 1: "LAWN AND LANDSCAPE" (Heading1 style, large font, red color)
|
|
110
|
+
* - Paragraph 2: "Take your weekends back..." (Normal style, smaller font, black color)
|
|
111
|
+
*
|
|
112
|
+
* Replacing with "EARTH AND MOUNTAIN" will:
|
|
113
|
+
* - Update paragraph 1 to "EARTH AND MOUNTAIN" (preserving Heading1 style, large font, red color)
|
|
114
|
+
* - Keep paragraph 2 completely intact with its original text and style
|
|
115
|
+
*/
|
|
116
|
+
export declare function setCellTextPreservingStyles(tc: Element, text: string): void;
|
|
44
117
|
/**
|
|
45
118
|
* Ensure a <w:r> element has w:rPr/w:color[@w:val=hex].
|
|
46
119
|
* Creates w:rPr and w:color if they don't exist.
|