@shbernal/ts-xlsx 1.2.0 → 2.0.0
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 +5 -0
- package/dist/core/address.d.ts +49 -2
- package/dist/core/address.js +31 -3
- package/dist/core/autofilter.d.ts +2 -2
- package/dist/core/cell.d.ts +17 -16
- package/dist/core/cell.js +3 -7
- package/dist/core/color-resolution.d.ts +7 -7
- package/dist/core/column.d.ts +8 -9
- package/dist/core/column.js +2 -4
- package/dist/core/comment-thread.d.ts +32 -23
- package/dist/core/comment-thread.js +4 -4
- package/dist/core/conditional-formatting-overlay.d.ts +1 -1
- package/dist/core/conditional-formatting.d.ts +3 -3
- package/dist/core/data-validation-overlay.d.ts +1 -1
- package/dist/core/data-validation.d.ts +3 -3
- package/dist/core/date.d.ts +3 -3
- package/dist/core/formula.d.ts +6 -6
- package/dist/core/grid-edits.js +3 -3
- package/dist/core/image.d.ts +37 -2
- package/dist/core/image.js +6 -0
- package/dist/core/internal.d.ts +9 -1
- package/dist/core/limits.d.ts +4 -4
- package/dist/core/merge.d.ts +6 -12
- package/dist/core/merge.js +0 -3
- package/dist/core/page-setup.d.ts +4 -4
- package/dist/core/pivot-table.d.ts +2 -4
- package/dist/core/pivot-table.js +5 -5
- package/dist/core/preserved.d.ts +3 -3
- package/dist/core/protection.d.ts +4 -4
- package/dist/core/range.d.ts +16 -14
- package/dist/core/range.js +5 -5
- package/dist/core/row-input.d.ts +2 -8
- package/dist/core/row-input.js +2 -2
- package/dist/core/row.d.ts +7 -8
- package/dist/core/row.js +2 -4
- package/dist/core/style.d.ts +14 -14
- package/dist/core/table-style.d.ts +9 -9
- package/dist/core/table-style.js +1 -1
- package/dist/core/table.d.ts +30 -42
- package/dist/core/table.js +16 -10
- package/dist/core/theme.d.ts +13 -43
- package/dist/core/theme.js +2 -148
- package/dist/core/value.d.ts +7 -7
- package/dist/core/workbook-protection.d.ts +2 -2
- package/dist/core/workbook-styles.d.ts +26 -0
- package/dist/core/workbook-styles.js +48 -0
- package/dist/core/workbook-theme.d.ts +25 -0
- package/dist/core/workbook-theme.js +49 -0
- package/dist/core/workbook-vba.d.ts +17 -0
- package/dist/core/workbook-vba.js +79 -0
- package/dist/core/workbook.d.ts +141 -83
- package/dist/core/workbook.js +74 -133
- package/dist/core/worksheet-comments.d.ts +9 -0
- package/dist/core/worksheet-comments.js +52 -0
- package/dist/core/worksheet-model.d.ts +4 -4
- package/dist/core/worksheet-model.js +1 -0
- package/dist/core/worksheet-pictures.d.ts +29 -0
- package/dist/core/worksheet-pictures.js +42 -0
- package/dist/core/worksheet.d.ts +94 -77
- package/dist/core/worksheet.js +36 -95
- package/dist/customui/errors.d.ts +1 -1
- package/dist/customui/ribbon.d.ts +3 -3
- package/dist/entries/core.d.ts +4 -4
- package/dist/entries/core.js +1 -1
- package/dist/entries/vba.d.ts +1 -1
- package/dist/entries/vba.js +1 -1
- package/dist/entries/xlsx.d.ts +1 -0
- package/dist/entries/xlsx.js +1 -0
- package/dist/errors.d.ts +12 -12
- package/dist/io/csv/read.js +1 -2
- package/dist/io/csv/write.d.ts +8 -3
- package/dist/io/csv/write.js +17 -2
- package/dist/io/opc/errors.d.ts +6 -6
- package/dist/io/opc/inflate.d.ts +1 -1
- package/dist/io/opc/namespaces.d.ts +1 -1
- package/dist/io/opc/read-opc.d.ts +19 -3
- package/dist/io/opc/read-opc.js +14 -8
- package/dist/io/opc/read-options.d.ts +2 -2
- package/dist/io/opc/sniff-format.d.ts +2 -2
- package/dist/io/opc/zip-mtime.d.ts +5 -0
- package/dist/io/opc/zip-mtime.js +1 -0
- package/dist/io/style/xf-style.d.ts +38 -6
- package/dist/io/style/xf-style.js +22 -0
- package/dist/io/xlsb/errors.d.ts +1 -1
- package/dist/io/xlsb/formula.d.ts +4 -4
- package/dist/io/xlsb/primitives.d.ts +8 -8
- package/dist/io/xlsb/ptg-functions.d.ts +1 -1
- package/dist/io/xlsb/read-styles.js +2 -20
- package/dist/io/xlsb/read.d.ts +2 -2
- package/dist/io/xlsx/cell-accumulator.d.ts +25 -6
- package/dist/io/xlsx/cell-accumulator.js +111 -30
- package/dist/io/xlsx/cell-value.d.ts +2 -2
- package/dist/io/xlsx/cell-value.js +3 -3
- package/dist/io/xlsx/color-xml.js +11 -17
- package/dist/io/xlsx/comments.d.ts +5 -5
- package/dist/io/xlsx/comments.js +13 -6
- package/dist/io/xlsx/conditional-formatting.d.ts +3 -3
- package/dist/io/xlsx/conditional-formatting.js +7 -16
- package/dist/io/xlsx/data-validation.d.ts +2 -2
- package/dist/io/xlsx/data-validation.js +1 -1
- package/dist/io/xlsx/edit-vba.js +2 -1
- package/dist/io/xlsx/errors.d.ts +3 -3
- package/dist/io/xlsx/hyperlinks.d.ts +4 -2
- package/dist/io/xlsx/hyperlinks.js +5 -5
- package/dist/io/xlsx/images.d.ts +1 -1
- package/dist/io/xlsx/images.js +8 -8
- package/dist/io/xlsx/namespaces.d.ts +2 -2
- package/dist/io/xlsx/package-plan.js +5 -2
- package/dist/io/xlsx/read-pivot.js +2 -5
- package/dist/io/xlsx/read-rows.d.ts +13 -13
- package/dist/io/xlsx/read-rows.js +19 -55
- package/dist/io/xlsx/read-shared-strings.js +7 -5
- package/dist/io/xlsx/read-styles.d.ts +3 -3
- package/dist/io/xlsx/read-styles.js +40 -65
- package/dist/io/xlsx/read-worksheet.js +67 -115
- package/dist/io/xlsx/read.d.ts +3 -5
- package/dist/io/xlsx/read.js +94 -71
- package/dist/io/xlsx/rich-runs.d.ts +1 -1
- package/dist/io/xlsx/rich-runs.js +1 -1
- package/dist/io/xlsx/rich-text.d.ts +1 -1
- package/dist/io/xlsx/shared-strings.d.ts +2 -2
- package/dist/io/xlsx/sheet-properties.js +5 -4
- package/dist/io/xlsx/styles.d.ts +8 -9
- package/dist/io/xlsx/styles.js +4 -3
- package/dist/io/xlsx/tables.d.ts +2 -2
- package/dist/io/xlsx/tables.js +8 -13
- package/dist/io/xlsx/theme-xml.d.ts +37 -0
- package/dist/io/xlsx/theme-xml.js +142 -0
- package/dist/io/xlsx/threaded-comments.d.ts +18 -27
- package/dist/io/xlsx/threaded-comments.js +9 -21
- package/dist/io/xlsx/workbook-xml.d.ts +1 -1
- package/dist/io/xlsx/workbook-xml.js +6 -2
- package/dist/io/xlsx/worksheet-xml.d.ts +2 -2
- package/dist/io/xlsx/worksheet-xml.js +7 -12
- package/dist/io/xlsx/write-stream.d.ts +15 -15
- package/dist/io/xlsx/write-stream.js +5 -3
- package/dist/io/xlsx/write.d.ts +12 -7
- package/dist/io/xlsx/write.js +10 -6
- package/dist/io/xlsx/x14-ext.d.ts +1 -1
- package/dist/vba/bytes.d.ts +12 -0
- package/dist/vba/bytes.js +40 -0
- package/dist/vba/cfb-writer.d.ts +1 -1
- package/dist/vba/cfb.d.ts +1 -1
- package/dist/vba/cfb.js +15 -51
- package/dist/vba/codepage.d.ts +2 -2
- package/dist/vba/errors.d.ts +2 -2
- package/dist/vba/index.d.ts +2 -2
- package/dist/vba/index.js +2 -2
- package/dist/vba/ms-ovba.d.ts +1 -1
- package/dist/vba/ms-ovba.js +1 -3
- package/dist/vba/project-editor.d.ts +9 -9
- package/dist/vba/project-editor.js +2 -11
- package/dist/vba/project.d.ts +5 -5
- package/dist/vba/project.js +1 -10
- package/dist/vba/vba-encoding.d.ts +1 -1
- package/dist/xml/errors.d.ts +1 -1
- package/dist/xml/xml-read.d.ts +38 -9
- package/dist/xml/xml-read.js +23 -0
- package/dist/xml/xml.d.ts +31 -9
- package/dist/xml/xml.js +23 -3
- package/package.json +41 -35
package/dist/core/workbook.d.ts
CHANGED
|
@@ -1,24 +1,25 @@
|
|
|
1
1
|
import { type CustomUiDocument } from '../customui/index.ts';
|
|
2
2
|
import { type VbaLibraryReference, type VbaProject, type VbaProjectSignature } from '../vba/index.ts';
|
|
3
3
|
import { type Person } from './comment-thread.ts';
|
|
4
|
-
import { type WorkbookImage } from './image.ts';
|
|
4
|
+
import { type WorkbookImage, type WorksheetImages } from './image.ts';
|
|
5
5
|
import { INTERNAL } from './internal.ts';
|
|
6
6
|
import type { PreservedPart, PreservedRootReference } from './preserved.ts';
|
|
7
7
|
import type { Color, Font, NamedCellStyle, TableStyleTable } from './style.ts';
|
|
8
8
|
import { type TableStyle } from './table-style.ts';
|
|
9
9
|
import { type ThemeColorScheme, type ThemeFontScheme, type ThemeOverrides } from './theme.ts';
|
|
10
10
|
import type { WorkbookProtection } from './workbook-protection.ts';
|
|
11
|
+
import { type DeclaredThemeSchemes } from './workbook-theme.ts';
|
|
11
12
|
import { Worksheet, type WorksheetState } from './worksheet.ts';
|
|
12
13
|
/**
|
|
13
|
-
* A workbook-level reference to package content the model does not model
|
|
14
|
-
* (`pivotCacheDefinition`) or a slicer cache (`slicerCache`)
|
|
14
|
+
* A workbook-level reference to package content the model does not model: a pivot cache
|
|
15
|
+
* (`pivotCacheDefinition`) or a slicer cache (`slicerCache`), preserved verbatim across a round-trip
|
|
15
16
|
* instead of being dropped. `relType` is the workbook relationship Type URI to re-emit; `entryPath`
|
|
16
17
|
* is the part it points at; `parts` is the transitive closure that reference reaches (the entry
|
|
17
18
|
* included). `pivotCacheId` carries the `<pivotCache cacheId>` a pivot cache is registered under in
|
|
18
19
|
* the workbook's `<pivotCaches>`, so the wiring a pivot table resolves its cache through is re-emitted
|
|
19
20
|
* too; it is absent for a slicer cache, which the workbook lists in an extension block instead.
|
|
20
21
|
* `externalReferenceIndex` is the 0-based position of an `externalLink` within the workbook's
|
|
21
|
-
* `<externalReferences
|
|
22
|
+
* `<externalReferences>`, the `[n]` a formula or defined name resolves an external cell through, so
|
|
22
23
|
* the block is re-emitted in the original order and every `[n]` still points at the same linked
|
|
23
24
|
* workbook; it is absent for a pivot/slicer cache.
|
|
24
25
|
*/
|
|
@@ -30,14 +31,14 @@ export interface PreservedWorkbookReference {
|
|
|
30
31
|
readonly externalReferenceIndex?: number;
|
|
31
32
|
}
|
|
32
33
|
/**
|
|
33
|
-
* The workbook's theme part, captured verbatim from a source package
|
|
34
|
+
* The workbook's theme part, captured verbatim from a source package: the `<clrScheme>`,
|
|
34
35
|
* `<fontScheme>`, and `<fmtScheme>` every `theme="n"` colour reference and every `scheme="major|minor"`
|
|
35
36
|
* font in the file resolves against.
|
|
36
37
|
*
|
|
37
38
|
* Held opaquely, like {@link Workbook.restoreDifferentialStyles}'s `<dxf>` fragments: the model does
|
|
38
39
|
* not interpret the theme, it only refuses to destroy it. `entryPath` is where the source package held
|
|
39
40
|
* the part (reached through the workbook's `.../theme` relationship, so not necessarily
|
|
40
|
-
* `xl/theme/theme1.xml`), and `parts` is the transitive closure it reaches
|
|
41
|
+
* `xl/theme/theme1.xml`), and `parts` is the transitive closure it reaches, the entry included. The
|
|
41
42
|
* closure matters because a theme can carry its own relationships: a picture used as a themed fill is
|
|
42
43
|
* wired by an `r:embed` into the theme's rels part, and re-emitting the theme without it would leave
|
|
43
44
|
* that reference dangling.
|
|
@@ -47,14 +48,14 @@ export interface PreservedTheme {
|
|
|
47
48
|
readonly parts: readonly PreservedPart[];
|
|
48
49
|
}
|
|
49
50
|
/**
|
|
50
|
-
* The workbook's saved window state
|
|
51
|
+
* The workbook's saved window state: OOXML's `<workbookView>`, the single entry of `<bookViews>`.
|
|
51
52
|
*
|
|
52
53
|
* This is the rect a consumer restores the document window to, and the layout every pane geometry is
|
|
53
54
|
* computed against: a frozen split is positioned within it. `activeTab` names the sheet whose tab is
|
|
54
55
|
* selected on open.
|
|
55
56
|
*
|
|
56
57
|
* The position and size are in twips (1/20 of a point), Excel's window unit. A slightly negative
|
|
57
|
-
* `x`/`y` is normal and is what Excel itself writes
|
|
58
|
+
* `x`/`y` is normal and is what Excel itself writes: a maximised window's frame sits just outside the
|
|
58
59
|
* work area.
|
|
59
60
|
*/
|
|
60
61
|
export interface WorkbookView {
|
|
@@ -74,7 +75,7 @@ export interface WorkbookView {
|
|
|
74
75
|
minimized?: boolean;
|
|
75
76
|
}
|
|
76
77
|
/**
|
|
77
|
-
* The window geometry a workbook starts from
|
|
78
|
+
* The window geometry a workbook starts from: the values desktop Excel writes for its own default
|
|
78
79
|
* window.
|
|
79
80
|
*
|
|
80
81
|
* A default is emitted rather than the element left out because Excel writes `<bookViews>` into every
|
|
@@ -89,16 +90,28 @@ export declare const DEFAULT_WORKBOOK_VIEW: {
|
|
|
89
90
|
readonly height: 12220;
|
|
90
91
|
readonly activeTab: 0;
|
|
91
92
|
};
|
|
92
|
-
/**
|
|
93
|
+
/**
|
|
94
|
+
* Document-level metadata: what Excel's File ▸ Info panel shows. Mostly the package's core
|
|
95
|
+
* properties (`docProps/core.xml`); `company` is the exception and lives in the extended part,
|
|
96
|
+
* because that is where OOXML puts it. One interface either way: which part a field lands in is
|
|
97
|
+
* the format's business, not the caller's.
|
|
98
|
+
*/
|
|
93
99
|
export interface WorkbookProperties {
|
|
100
|
+
/** The document's title (`dc:title`), as Excel's File ▸ Info shows it. */
|
|
101
|
+
title?: string;
|
|
94
102
|
creator?: string;
|
|
95
103
|
lastModifiedBy?: string;
|
|
96
104
|
created?: Date;
|
|
97
105
|
modified?: Date;
|
|
106
|
+
/**
|
|
107
|
+
* `Company` in the extended properties (`docProps/app.xml`), not the core ones. It is the only
|
|
108
|
+
* field here that does not live beside the others, because OOXML puts it in the other part.
|
|
109
|
+
*/
|
|
110
|
+
company?: string;
|
|
98
111
|
}
|
|
99
112
|
/**
|
|
100
|
-
* A named reference in the workbook
|
|
101
|
-
* an identifier to a formula (`refersTo`), most often a cell range like `Sheet1!$A$1:$B$2` but
|
|
113
|
+
* A named reference in the workbook, one of the entries Excel surfaces in its Name Manager. A name
|
|
114
|
+
* maps an identifier to a formula (`refersTo`), most often a cell range like `Sheet1!$A$1:$B$2` but
|
|
102
115
|
* possibly any formula. A name is global to the workbook unless it names a sheet in {@link scope},
|
|
103
116
|
* which restricts it to that sheet and lets another sheet reuse the same name independently.
|
|
104
117
|
*/
|
|
@@ -121,7 +134,7 @@ export interface AddWorksheetOptions {
|
|
|
121
134
|
export interface AddImageOptions {
|
|
122
135
|
/** The image bytes. */
|
|
123
136
|
readonly buffer: Uint8Array;
|
|
124
|
-
/** The file kind
|
|
137
|
+
/** The file kind: `"png"`, `"jpeg"`/`"jpg"`, `"gif"`, … A leading dot or a URL query string is
|
|
125
138
|
* tolerated and stripped; omit it entirely to infer the kind from the bytes' magic number. */
|
|
126
139
|
readonly extension?: string;
|
|
127
140
|
}
|
|
@@ -129,7 +142,7 @@ export declare class Workbook {
|
|
|
129
142
|
#private;
|
|
130
143
|
readonly properties: WorkbookProperties;
|
|
131
144
|
/**
|
|
132
|
-
* The workbook's window state
|
|
145
|
+
* The workbook's window state: position, size, and the selected sheet. Always present (see
|
|
133
146
|
* {@link DEFAULT_WORKBOOK_VIEW} for why it is defaulted rather than left unset) and always written.
|
|
134
147
|
* Reading a file replaces it with that file's saved geometry, so a round-trip restores the window
|
|
135
148
|
* the author left rather than stamping ours over it.
|
|
@@ -138,12 +151,12 @@ export declare class Workbook {
|
|
|
138
151
|
/**
|
|
139
152
|
* Ask consuming spreadsheet apps to recalculate every formula when the file is opened, rather than
|
|
140
153
|
* trusting the cached results stored with each formula cell. Set this when the producer cannot
|
|
141
|
-
* compute formula results itself
|
|
142
|
-
* whose cached results are authoritative stays unmarked.
|
|
154
|
+
* compute formula results itself. This is the OOXML `fullCalcOnLoad` flag, off by default, so a
|
|
155
|
+
* workbook whose cached results are authoritative stays unmarked.
|
|
143
156
|
*/
|
|
144
157
|
fullCalcOnLoad: boolean;
|
|
145
158
|
/**
|
|
146
|
-
* Workbook-level structure/window protection
|
|
159
|
+
* Workbook-level structure/window protection: the OOXML `<workbookProtection>` element. Absent by
|
|
147
160
|
* default (an unprotected workbook). Set it to lock the workbook shell, or leave it as read from a
|
|
148
161
|
* file so a protected workbook stays locked across a passthrough save rather than being silently
|
|
149
162
|
* unlocked. Distinct from a worksheet's own `protect()`, which guards a single sheet's cells.
|
|
@@ -153,7 +166,7 @@ export declare class Workbook {
|
|
|
153
166
|
get worksheets(): readonly Worksheet[];
|
|
154
167
|
/**
|
|
155
168
|
* The 0-based index of the active sheet: {@link WorkbookView.activeTab} resolved against the sheets
|
|
156
|
-
* that actually exist. Exactly one sheet is always active
|
|
169
|
+
* that actually exist. Exactly one sheet is always active: an out-of-range tab (a caller's stale
|
|
157
170
|
* index, or a file whose sheet was removed after the view was saved) falls back to the first sheet
|
|
158
171
|
* rather than to none, because a package where no sheet is selected gives the consumer no view to
|
|
159
172
|
* initialise on open.
|
|
@@ -164,12 +177,12 @@ export declare class Workbook {
|
|
|
164
177
|
/** The package-root preserved references, in the order they were read. */
|
|
165
178
|
get preservedRootReferences(): readonly PreservedRootReference[];
|
|
166
179
|
/**
|
|
167
|
-
* The ribbon customisations decoded from this workbook's `customUI` parts
|
|
180
|
+
* The ribbon customisations decoded from this workbook's `customUI` parts: `customUI.xml` (Office
|
|
168
181
|
* 2007) and/or `customUI14.xml` (Office 2010+), in the order their root relationships were read. Each
|
|
169
182
|
* {@link CustomUiDocument} is tagged with its dialect and exposes the parsed `<ribbon>` tree. Empty
|
|
170
183
|
* for a workbook that customises no ribbon.
|
|
171
184
|
*
|
|
172
|
-
* This is a **read-only view** over parts the writer already round-trips verbatim
|
|
185
|
+
* This is a **read-only view** over parts the writer already round-trips verbatim. Mutating the
|
|
173
186
|
* returned objects changes nothing on write; the original `customUI` XML is re-emitted byte-for-byte
|
|
174
187
|
* regardless. Parsed lazily on first access and memoised.
|
|
175
188
|
*
|
|
@@ -179,15 +192,15 @@ export declare class Workbook {
|
|
|
179
192
|
/**
|
|
180
193
|
* The VBA project decoded from this workbook's preserved `vbaProject.bin`, or `undefined` for a
|
|
181
194
|
* workbook with no macros. This is a **read-only view** over the bytes the writer already round-trips
|
|
182
|
-
* verbatim
|
|
195
|
+
* verbatim. Mutating the returned object changes nothing on write; the original macro blob is
|
|
183
196
|
* re-emitted byte-for-byte regardless. Parsed lazily on first access and memoised.
|
|
184
197
|
*
|
|
185
198
|
* @throws {VbaParseError} if a macro project is present but its `vbaProject.bin` is malformed.
|
|
186
199
|
*/
|
|
187
200
|
get vbaProject(): VbaProject | undefined;
|
|
188
201
|
/**
|
|
189
|
-
* The raw `vbaProject.bin` bytes attached to this workbook
|
|
190
|
-
* embed
|
|
202
|
+
* The raw `vbaProject.bin` bytes attached to this workbook (the exact macro blob the writer will
|
|
203
|
+
* embed), or `undefined` for a workbook with no macros. The getter returns a defensive copy, so
|
|
191
204
|
* mutating it changes nothing on write.
|
|
192
205
|
*
|
|
193
206
|
* Assigning bytes attaches (or replaces) the macro project: the written package becomes
|
|
@@ -198,14 +211,14 @@ export declare class Workbook {
|
|
|
198
211
|
* `.bin` produced by another tool. Assigning `undefined` removes the project, reverting the workbook
|
|
199
212
|
* to a plain (non-macro) package.
|
|
200
213
|
*
|
|
201
|
-
* Replacing or removing the project also drops any digital signature the previous blob carried
|
|
202
|
-
* signature over the old bytes cannot validate new ones
|
|
203
|
-
* signature.
|
|
214
|
+
* Replacing or removing the project also drops any digital signature the previous blob carried,
|
|
215
|
+
* because a signature over the old bytes cannot validate new ones, so the result never advertises
|
|
216
|
+
* a broken signature.
|
|
204
217
|
*/
|
|
205
218
|
get vbaProjectBytes(): Uint8Array | undefined;
|
|
206
219
|
set vbaProjectBytes(bytes: Uint8Array | undefined);
|
|
207
220
|
/**
|
|
208
|
-
* Whether this workbook's VBA project carries a digital signature
|
|
221
|
+
* Whether this workbook's VBA project carries a digital signature: `true` if any signature part is
|
|
209
222
|
* attached, `false` for an unsigned project or a workbook with no macros.
|
|
210
223
|
*
|
|
211
224
|
* This reflects the **presence** of a signature blob, not its cryptographic validity: the library
|
|
@@ -219,20 +232,20 @@ export declare class Workbook {
|
|
|
219
232
|
get vbaProjectSigned(): boolean;
|
|
220
233
|
/**
|
|
221
234
|
* The digital signatures attached to this workbook's VBA project, in the order their relationships
|
|
222
|
-
* are wired off `vbaProject.bin
|
|
235
|
+
* are wired off `vbaProject.bin`. Up to three generations (legacy, agile, V3) can coexist over the
|
|
223
236
|
* same project bytes. Empty for an unsigned project or a workbook with no macros.
|
|
224
237
|
*
|
|
225
238
|
* Each entry's `bytes` are the raw signature blob passed through verbatim; the library does not parse
|
|
226
239
|
* or verify them (see {@link vbaProjectSigned} on presence-vs-validity). Hand a blob to an external
|
|
227
|
-
* verifier if you need cryptographic validation
|
|
240
|
+
* verifier if you need cryptographic validation; that is deliberately out of this library's scope.
|
|
228
241
|
*/
|
|
229
242
|
get vbaProjectSignatures(): readonly VbaProjectSignature[];
|
|
230
243
|
/**
|
|
231
|
-
* Remove a standard module from this workbook's existing macro project, in place
|
|
244
|
+
* Remove a standard module from this workbook's existing macro project, in place: a structural splice
|
|
232
245
|
* that leaves every remaining module's compiled p-code untouched (see {@link removeVbaModule}).
|
|
233
246
|
* Replacing the project also drops a stale signature, as {@link vbaProjectBytes} does.
|
|
234
247
|
*
|
|
235
|
-
* Only `procedural` and `class` modules can be removed this way
|
|
248
|
+
* Only `procedural` and `class` modules can be removed this way. See {@link removeVbaModule} for why.
|
|
236
249
|
* To author or edit module *source* (which needs real compiled p-code), use the offline
|
|
237
250
|
* `tools/vba-compiler`, then attach its output via {@link vbaProjectBytes}.
|
|
238
251
|
*
|
|
@@ -261,7 +274,7 @@ export declare class Workbook {
|
|
|
261
274
|
/** The preserved `<tableStyles>` block; `styles` is empty when the file declared no custom style. */
|
|
262
275
|
get tableStyles(): TableStyleTable;
|
|
263
276
|
/**
|
|
264
|
-
* Register a custom table style
|
|
277
|
+
* Register a custom table style: a named look a table applies to itself by putting that name in
|
|
265
278
|
* {@link TableStyleInfo.name}, exactly as it would name one of Excel's built-in gallery styles.
|
|
266
279
|
*
|
|
267
280
|
* ```ts
|
|
@@ -278,14 +291,15 @@ export declare class Workbook {
|
|
|
278
291
|
* ```
|
|
279
292
|
*
|
|
280
293
|
* Each element's formatting is interned into the workbook's shared differential-style table, so two
|
|
281
|
-
* elements
|
|
294
|
+
* elements, or a conditional-formatting rule, that paint the same way share one entry.
|
|
282
295
|
*
|
|
283
296
|
* Registering a name a source file already defined **overrides** that definition rather than adding
|
|
284
297
|
* a second one beside it.
|
|
285
298
|
*
|
|
286
|
-
* @throws {AuthoringError} if the name is empty, or an element carries a `size` outside the four
|
|
287
|
-
* types
|
|
288
|
-
*
|
|
299
|
+
* @throws {AuthoringError} if the name is empty, or an element carries a `size` outside the four
|
|
300
|
+
* stripe types. See {@link checkTableStyle} for why those are refused here rather than silently
|
|
301
|
+
* dropped.
|
|
302
|
+
* @throws {RangeError} if a `size` is not a positive integer.
|
|
289
303
|
*/
|
|
290
304
|
addTableStyle(style: TableStyle): void;
|
|
291
305
|
/** The table styles authored on this workbook, in registration order. */
|
|
@@ -297,24 +311,24 @@ export declare class Workbook {
|
|
|
297
311
|
* typefaces. Merges into what the workbook already has, so branding one accent leaves the other
|
|
298
312
|
* eleven slots alone, and calling it twice accumulates.
|
|
299
313
|
*
|
|
300
|
-
* This is the workbook-wide palette. A cell that names a colour as `theme="4"
|
|
301
|
-
* writes whenever a user picks from the theme row of the colour picker
|
|
314
|
+
* This is the workbook-wide palette. A cell that names a colour as `theme="4"`, which is what Excel
|
|
315
|
+
* writes whenever a user picks from the theme row of the colour picker, follows `accent1` here, so
|
|
302
316
|
* one call restyles every such cell, chart and table style at once. Colours are `RRGGBB`; a leading
|
|
303
317
|
* `#` and an 8-hex ARGB are both accepted and reduced, and anything else throws rather than writing
|
|
304
318
|
* a value Excel silently renders as flat black.
|
|
305
319
|
*
|
|
306
|
-
* What it does **not** touch: the theme's format scheme
|
|
307
|
-
* give a theme its texture. Those ride through from the source theme (or the library's
|
|
308
|
-
* untouched, because nobody hand-authors gradient stops from a spreadsheet API and
|
|
309
|
-
* would replace a designer's work with the Office default. For the same reason a
|
|
310
|
-
* unauthored keeps the source's own encoding, including the `<a:sysClr>` form Excel uses
|
|
311
|
-
* `dk1`/`lt1` so they follow the viewer's window colours.
|
|
320
|
+
* What it does **not** touch: the theme's format scheme, meaning the gradient, line and effect
|
|
321
|
+
* styles that give a theme its texture. Those ride through from the source theme (or the library's
|
|
322
|
+
* default) untouched, because nobody hand-authors gradient stops from a spreadsheet API and
|
|
323
|
+
* regenerating them would replace a designer's work with the Office default. For the same reason a
|
|
324
|
+
* slot left unauthored keeps the source's own encoding, including the `<a:sysClr>` form Excel uses
|
|
325
|
+
* for `dk1`/`lt1` so they follow the viewer's window colours.
|
|
312
326
|
*
|
|
313
327
|
* @throws {AuthoringError} if a colour is not 6 or 8 hexadecimal digits.
|
|
314
328
|
*/
|
|
315
329
|
setTheme(overrides: ThemeOverrides): void;
|
|
316
330
|
/**
|
|
317
|
-
* The colour scheme every `theme="n"` reference in this workbook resolves against
|
|
331
|
+
* The colour scheme every `theme="n"` reference in this workbook resolves against: anything
|
|
318
332
|
* {@link setTheme} authored, over the preserved theme's `<a:clrScheme>`, over the Office default.
|
|
319
333
|
*
|
|
320
334
|
* Note the slot *order*: `theme="0"` is `lt1` and `theme="1"` is `dk1`, which is not the order the
|
|
@@ -324,7 +338,7 @@ export declare class Workbook {
|
|
|
324
338
|
/** The theme's major (heading) and minor (body) typefaces, authored values over the source's. */
|
|
325
339
|
get themeFonts(): ThemeFontScheme;
|
|
326
340
|
/**
|
|
327
|
-
* The default font as the source package declared it
|
|
341
|
+
* The default font as the source package declared it: font id 0 of its styles part, the face every
|
|
328
342
|
* cell that names no font of its own renders in. `undefined` for a workbook authored from scratch or
|
|
329
343
|
* read from a package carrying no styles part: nothing was declared, and the library does not
|
|
330
344
|
* fabricate a declaration on the file's behalf.
|
|
@@ -334,23 +348,24 @@ export declare class Workbook {
|
|
|
334
348
|
*/
|
|
335
349
|
get declaredDefaultFont(): Font | undefined;
|
|
336
350
|
/**
|
|
337
|
-
* Author the workbook's default font
|
|
351
|
+
* Author the workbook's default font: the face, size and colour every cell with no font of its own
|
|
338
352
|
* renders in, **empty cells included**. Merges into whatever the workbook already had, so
|
|
339
353
|
* `setDefaultFont({size: 14})` keeps the resolved face and changes only the size, and calling it
|
|
340
354
|
* twice accumulates. This is the one knob that reaches a cell no row or column default can: an
|
|
341
355
|
* untouched cell in an unformatted column.
|
|
342
356
|
*
|
|
343
|
-
* It writes the styles part's font 0 and **nothing else
|
|
357
|
+
* It writes the styles part's font 0 and **nothing else**. In particular it does not rewrite the
|
|
344
358
|
* theme's body typeface. The dependency runs the other way: with no default font authored, font 0
|
|
345
359
|
* follows {@link themeFonts}'s minor face, so `setTheme({fonts: {minor}})` already reaches every
|
|
346
360
|
* unstyled cell and needs no second call here. See {@link defaultFont} for the full chain.
|
|
347
361
|
*
|
|
348
|
-
* @throws {
|
|
349
|
-
* produce a styles part Excel renders from some other font without ever reporting why.
|
|
362
|
+
* @throws {RangeError} if `size` is not a positive finite number, or `name` is empty. Both
|
|
363
|
+
* produce a styles part Excel renders from some other font without ever reporting why. Native
|
|
364
|
+
* rather than {@link AuthoringError}: one argument out of range is what `RangeError` is for.
|
|
350
365
|
*/
|
|
351
366
|
setDefaultFont(font: Font): void;
|
|
352
367
|
/**
|
|
353
|
-
* The font every cell that names none of its own renders in, resolved and complete
|
|
368
|
+
* The font every cell that names none of its own renders in, resolved and complete: what the writer
|
|
354
369
|
* emits as font id 0. Never `undefined`: a workbook always renders in *some* face, and the chain
|
|
355
370
|
* below always reaches one.
|
|
356
371
|
*
|
|
@@ -361,28 +376,28 @@ export declare class Workbook {
|
|
|
361
376
|
* The two authored levels outrank the file because authoring is an explicit act; between them
|
|
362
377
|
* {@link setDefaultFont} wins on the face because it names font 0 outright while
|
|
363
378
|
* {@link setTheme} names it only by implication. With **nothing** authored the file's own font 0
|
|
364
|
-
* passes through verbatim
|
|
365
|
-
* not: Excel writes `等线` as font 0 under a theme whose latin body face is `Calibri`, and
|
|
379
|
+
* passes through verbatim. That is deliberate, because a producer resolves that face by script and
|
|
380
|
+
* we do not: Excel writes `等线` as font 0 under a theme whose latin body face is `Calibri`, and
|
|
366
381
|
* re-deriving would silently rewrite it.
|
|
367
382
|
*
|
|
368
383
|
* `family` and `scheme` describe the *theme's* body face, so they are carried exactly while the
|
|
369
|
-
* resolved face still is that face and dropped when a caller names another
|
|
384
|
+
* resolved face still is that face and dropped when a caller names another, which is also what
|
|
370
385
|
* Excel writes: a font 0 naming a non-theme face carries no `<scheme>` at all. Either may be stated
|
|
371
386
|
* outright, in which case the caller's word stands.
|
|
372
387
|
*/
|
|
373
388
|
get defaultFont(): Font;
|
|
374
389
|
/**
|
|
375
|
-
* The
|
|
376
|
-
* source theme (or the writer's default)
|
|
390
|
+
* The colour slots and typefaces {@link setTheme} authored on this workbook, or `undefined` when
|
|
391
|
+
* none were, in which case the source theme (or the writer's default) rides through untouched.
|
|
377
392
|
*
|
|
378
|
-
*
|
|
379
|
-
*
|
|
380
|
-
*
|
|
393
|
+
* A serializer composes these *over* the existing part rather than generating one from scratch, so
|
|
394
|
+
* a preserved theme keeps its format scheme, its unauthored slots' exact encoding, and the
|
|
395
|
+
* relationships it carries.
|
|
381
396
|
*/
|
|
382
|
-
|
|
397
|
+
get themeOverrides(): ThemeOverrides | undefined;
|
|
383
398
|
/**
|
|
384
399
|
* Resolve a colour reference to a concrete 8-hex ARGB string, or `undefined` when it does not
|
|
385
|
-
* resolve to a fixed colour
|
|
400
|
+
* resolve to a fixed colour: an `auto` colour, one of the two system indexed colours, or a theme
|
|
386
401
|
* slot this workbook's scheme does not declare.
|
|
387
402
|
*
|
|
388
403
|
* This is a *derived* view, not a rewrite: the {@link Color} stays exactly as its file encoded it,
|
|
@@ -398,12 +413,12 @@ export declare class Workbook {
|
|
|
398
413
|
/** The named cell styles, in index order (index 0 is Normal); empty when only the default exists. */
|
|
399
414
|
get namedStyles(): readonly NamedCellStyle[];
|
|
400
415
|
/**
|
|
401
|
-
* Register an identity a threaded comment can name
|
|
416
|
+
* Register an identity a threaded comment can name: an author, or someone `@mentioned` in a message.
|
|
402
417
|
* A message reaches it by {@link Comment.personId}, a mention by {@link Mention.personId}.
|
|
403
418
|
*
|
|
404
419
|
* Keyed by {@link Person.id} alone, so registering the same id twice replaces the entry rather than
|
|
405
420
|
* adding a second: the id is the identity. Registering the same human twice under *different* ids is
|
|
406
|
-
* legitimate and is what Excel itself does
|
|
421
|
+
* legitimate and is what Excel itself does. See {@link restorePersons}. The id is normalised to the
|
|
407
422
|
* brace-wrapped upper-case GUID form the format requires, so a `crypto.randomUUID()` is accepted as-is.
|
|
408
423
|
*
|
|
409
424
|
* @throws {SyntaxError} if the id is not a GUID.
|
|
@@ -411,7 +426,8 @@ export declare class Workbook {
|
|
|
411
426
|
addPerson(person: Person): void;
|
|
412
427
|
/**
|
|
413
428
|
* The registered threaded-comment identities, in the order they were read. That order carries no
|
|
414
|
-
* meaning
|
|
429
|
+
* meaning, because Excel re-sorts the registry by person id when it saves, so nothing may depend
|
|
430
|
+
* on it.
|
|
415
431
|
*/
|
|
416
432
|
get persons(): readonly Person[];
|
|
417
433
|
/** Look up a registered identity by its {@link Person.id}, or `undefined` if the registry has none. */
|
|
@@ -426,13 +442,54 @@ export declare class Workbook {
|
|
|
426
442
|
get media(): readonly WorkbookImage[];
|
|
427
443
|
/** Look up a registered image by its id, or `undefined` if no image carries that id. */
|
|
428
444
|
getImage(id: number): WorkbookImage | undefined;
|
|
445
|
+
/**
|
|
446
|
+
* Every picture `sheet` shows, resolved out of this workbook's media registry into the
|
|
447
|
+
* workbook-independent form {@link importImages} consumes. `sheet` must belong to this workbook:
|
|
448
|
+
* that is whose registry its image ids index.
|
|
449
|
+
*
|
|
450
|
+
* This is the attached-part half of a sheet copy, and it is deliberately a separate call from
|
|
451
|
+
* {@link Worksheet.model}: a model is a serialisable value, an image is bytes on the workbook, and
|
|
452
|
+
* ADR-0005 keeps them apart. Carrying a sheet whole is therefore the two of them together:
|
|
453
|
+
*
|
|
454
|
+
* ```ts
|
|
455
|
+
* destination.model = source.model;
|
|
456
|
+
* destinationWorkbook.importImages(destination, sourceWorkbook.exportImages(source));
|
|
457
|
+
* ```
|
|
458
|
+
*
|
|
459
|
+
* The exported pictures share the registry's byte arrays rather than copying them: the library
|
|
460
|
+
* never mutates image bytes, and copying every picture would double the memory of an image-heavy
|
|
461
|
+
* workbook to defend against a mutation nothing performs.
|
|
462
|
+
*
|
|
463
|
+
* @throws {AuthoringError} if the sheet anchors an image id this workbook has not registered,
|
|
464
|
+
* which is what a sheet from *another* workbook looks like from here. Emitting a package with a
|
|
465
|
+
* drawing pointing at media that was never registered is the silently-broken-image failure this
|
|
466
|
+
* refuses to start.
|
|
467
|
+
*/
|
|
468
|
+
exportImages(sheet: Worksheet): WorksheetImages;
|
|
469
|
+
/**
|
|
470
|
+
* Show `images` on `sheet`, a worksheet of this workbook, registering each picture's bytes here
|
|
471
|
+
* and re-anchoring it against the id they land on. The counterpart to {@link exportImages}, and
|
|
472
|
+
* the affordance that lets a picture cross workbooks at all: an {@link AnchoredImage}'s `imageId`
|
|
473
|
+
* indexes one workbook's registry and means nothing in the next, so a raw anchor moved between
|
|
474
|
+
* workbooks points at media that does not exist there.
|
|
475
|
+
*
|
|
476
|
+
* The sheet's existing pictures are replaced, not appended to, so `importImages` is a transfer
|
|
477
|
+
* rather than an accumulation: the same direction {@link Worksheet.model} assignment goes, and
|
|
478
|
+
* what makes re-importing a sheet's own export leave it unchanged. An import whose `background` is
|
|
479
|
+
* absent clears the destination's background for the same reason.
|
|
480
|
+
*
|
|
481
|
+
* Registration is content-addressed: a picture whose bytes are already here is re-used at its
|
|
482
|
+
* existing id rather than stored twice, so importing the same sheet repeatedly, or twenty sheets
|
|
483
|
+
* sharing one logo, costs one media part.
|
|
484
|
+
*/
|
|
485
|
+
importImages(sheet: Worksheet, images: WorksheetImages): void;
|
|
429
486
|
/** The workbook's defined names, in the order they were registered. */
|
|
430
487
|
get definedNames(): readonly DefinedName[];
|
|
431
488
|
/**
|
|
432
489
|
* Register a defined name on the workbook.
|
|
433
490
|
*
|
|
434
491
|
* @throws {AuthoringError} if the name is empty, or if a {@link DefinedName.scope} is given that names no
|
|
435
|
-
* existing worksheet
|
|
492
|
+
* existing worksheet. A scoped name must target a sheet that is already part of the workbook.
|
|
436
493
|
*/
|
|
437
494
|
defineName(definedName: DefinedName): void;
|
|
438
495
|
/**
|
|
@@ -445,20 +502,20 @@ export declare class Workbook {
|
|
|
445
502
|
/** Look up a worksheet by name (case-insensitive) or by numeric id. */
|
|
446
503
|
getWorksheet(nameOrId: string | number): Worksheet | undefined;
|
|
447
504
|
/**
|
|
448
|
-
* {@link getWorksheet}, for a caller who knows the sheet is there
|
|
505
|
+
* {@link getWorksheet}, for a caller who knows the sheet is there: the miss throws instead of
|
|
449
506
|
* returning `undefined`, and the message names every sheet the workbook does have.
|
|
450
507
|
*
|
|
451
508
|
* The partial lookup is the right primitive for asking *whether* a sheet exists, and the wrong
|
|
452
509
|
* one for reaching a sheet a template is expected to carry: `undefined` flows on into a `?.`
|
|
453
510
|
* chain and fails several steps later with nothing left to say about which name was missing.
|
|
454
|
-
* That listing is the whole point
|
|
511
|
+
* That listing is the whole point: a lookup miss is a typo, a stale template or a renamed tab,
|
|
455
512
|
* and all three are answered by seeing the real names.
|
|
456
513
|
*
|
|
457
514
|
* @throws {AuthoringError} if no worksheet has that name (case-insensitive) or numeric id.
|
|
458
515
|
*/
|
|
459
516
|
requireWorksheet(nameOrId: string | number): Worksheet;
|
|
460
517
|
/**
|
|
461
|
-
* The codec's channel into this workbook
|
|
518
|
+
* The codec's channel into this workbook. See `core/internal.ts` for why these are not public
|
|
462
519
|
* methods. Declared last so every private field it closes over is already in scope.
|
|
463
520
|
*/
|
|
464
521
|
readonly [INTERNAL]: WorkbookInternals;
|
|
@@ -468,7 +525,7 @@ export declare class Workbook {
|
|
|
468
525
|
* the finished form the file stated it. Reached as `workbook[INTERNAL]`; see `core/internal.ts`.
|
|
469
526
|
*
|
|
470
527
|
* Every operation replaces what it restores rather than merging, because a reader states a table
|
|
471
|
-
* whole
|
|
528
|
+
* whole: a half-restored `<dxfs>` would leave existing `dxfId` references pointing into a mix of
|
|
472
529
|
* two files.
|
|
473
530
|
*/
|
|
474
531
|
export interface WorkbookInternals {
|
|
@@ -477,39 +534,40 @@ export interface WorkbookInternals {
|
|
|
477
534
|
/** Record a package-root preserved reference (a customUI ribbon part, custom props) read from a file. */
|
|
478
535
|
addPreservedRootReference(reference: PreservedRootReference): void;
|
|
479
536
|
/**
|
|
480
|
-
* Reinstate the differential-style (`<dxfs>`) table read from a file
|
|
537
|
+
* Reinstate the differential-style (`<dxfs>`) table read from a file: the deserialization
|
|
481
538
|
* counterpart the writer re-emits verbatim. Each entry is one `<dxf>…</dxf>` fragment, preserved as
|
|
482
539
|
* opaque XML so a conditional-formatting rule's `dxfId` (an index into this table) stays valid on
|
|
483
540
|
* re-write.
|
|
484
541
|
*/
|
|
485
542
|
restoreDifferentialStyles(fragments: readonly string[]): void;
|
|
486
543
|
/**
|
|
487
|
-
* Reinstate the custom indexed-color palette (`<colors><indexedColors>`) read from a file
|
|
488
|
-
* entry a verbatim `<rgbColor rgb="…"/>` fragment
|
|
544
|
+
* Reinstate the custom indexed-color palette (`<colors><indexedColors>`) read from a file, each
|
|
545
|
+
* entry a verbatim `<rgbColor rgb="…"/>` fragment, so a colour referenced by `indexed="…"` keeps
|
|
489
546
|
* its intended RGB on re-write instead of the palette being dropped and the colour shifting to a
|
|
490
547
|
* default-palette entry.
|
|
491
548
|
*/
|
|
492
549
|
restoreIndexedColors(fragments: readonly string[]): void;
|
|
493
550
|
/**
|
|
494
551
|
* Reinstate the most-recently-used colour swatches (`<colors><mruColors>`) read from a file, each
|
|
495
|
-
* entry a verbatim `<color rgb="…"/>` fragment
|
|
496
|
-
* offers, which is the author's own working set rather than anything the model
|
|
552
|
+
* entry a verbatim `<color rgb="…"/>` fragment. This is the "Recent Colors" row a spreadsheet
|
|
553
|
+
* application offers, which is the author's own working set rather than anything the model
|
|
554
|
+
* interprets.
|
|
497
555
|
*/
|
|
498
556
|
restoreMruColors(fragments: readonly string[]): void;
|
|
499
557
|
/**
|
|
500
|
-
* Reinstate the custom table-style definitions (`<tableStyles>`) read from a file
|
|
501
|
-
* {@link TableStyleTable}
|
|
558
|
+
* Reinstate the custom table-style definitions (`<tableStyles>`) read from a file (see
|
|
559
|
+
* {@link TableStyleTable}), so a table whose `styleName` names a custom style still resolves to a
|
|
502
560
|
* real definition on re-write instead of dangling, and the file's nominated default table/pivot
|
|
503
561
|
* styles survive.
|
|
504
562
|
*/
|
|
505
563
|
restoreTableStyles(table: TableStyleTable): void;
|
|
506
564
|
/**
|
|
507
|
-
* Reinstate the theme part read from a file
|
|
508
|
-
* reaches (see {@link PreservedTheme})
|
|
565
|
+
* Reinstate the theme part read from a file: opaque preserved XML plus the closure of parts it
|
|
566
|
+
* reaches (see {@link PreservedTheme}), so a workbook's colour and font schemes survive a re-write
|
|
509
567
|
* instead of being replaced by the library's default Office theme. Passing `undefined` drops back
|
|
510
568
|
* to that default.
|
|
511
569
|
*/
|
|
512
|
-
restoreThemePart(theme: PreservedTheme | undefined): void;
|
|
570
|
+
restoreThemePart(theme: PreservedTheme | undefined, declared: DeclaredThemeSchemes): void;
|
|
513
571
|
/**
|
|
514
572
|
* Reinstate the named cell styles (`cellStyleXfs`/`cellStyles`) read from a file, index for index,
|
|
515
573
|
* so a cell's link to a named style (its `xfId`) stays valid on re-write. Index 0 is the Normal
|
|
@@ -517,7 +575,7 @@ export interface WorkbookInternals {
|
|
|
517
575
|
*/
|
|
518
576
|
restoreNamedStyles(styles: readonly NamedCellStyle[]): void;
|
|
519
577
|
/**
|
|
520
|
-
* Reinstate font id 0 as a file declared it
|
|
578
|
+
* Reinstate font id 0 as a file declared it: the face its unstyled cells render in, and the metric
|
|
521
579
|
* its column widths are expressed in character units of. Restored rather than assumed because the
|
|
522
580
|
* library must not inject its own default ahead of one a file already states: doing so replaces the
|
|
523
581
|
* declared face on every empty cell and silently changes what every `<col width>` means.
|
|
@@ -526,13 +584,13 @@ export interface WorkbookInternals {
|
|
|
526
584
|
*/
|
|
527
585
|
restoreDefaultFont(font: Font | undefined): void;
|
|
528
586
|
/**
|
|
529
|
-
* Reinstate the threaded-comment identity registry (`xl/persons/person.xml`) read from a file
|
|
587
|
+
* Reinstate the threaded-comment identity registry (`xl/persons/person.xml`) read from a file: the
|
|
530
588
|
* authors and mentioned people a comment thread's messages point at.
|
|
531
589
|
*
|
|
532
590
|
* Entries are keyed by {@link Person.id} and by nothing else. A single human legitimately owns
|
|
533
591
|
* several entries: Excel interns a *mentioned* identity as its own `providerId="PeoplePicker"` entry
|
|
534
|
-
* beside that person's `providerId="AD"` authoring entry
|
|
535
|
-
* different id
|
|
592
|
+
* beside that person's `providerId="AD"` authoring entry (same `displayName`, same `userId`, a
|
|
593
|
+
* different id) and points the mention at the new one. Collapsing entries by name or `userId` would
|
|
536
594
|
* merge those two and silently re-point every mention at the wrong identity.
|
|
537
595
|
*
|
|
538
596
|
* {@link Workbook.addPerson} is the authoring verb.
|