@ingcreators/annot-product-docs-xlsx 0.2.1 → 0.2.2

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/CHANGELOG.md CHANGED
@@ -1,5 +1,15 @@
1
1
  # @ingcreators/annot-product-docs-xlsx
2
2
 
3
+ ## 0.2.2
4
+
5
+ ### Patch Changes
6
+
7
+ - Updated dependencies [b5d52f6]
8
+ - Updated dependencies [fa712fd]
9
+ - Updated dependencies [f09a6b1]
10
+ - Updated dependencies [0d19345]
11
+ - @ingcreators/annot-product-docs@0.4.0
12
+
3
13
  ## 0.2.1
4
14
 
5
15
  ### Patch Changes
package/dist/extract.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- import { AnnotFrontmatter, HistoryEntrySpec, OverlaySpec, ParsedMdx } from '@ingcreators/annot-product-docs';
1
+ import { AnnotationsFile, AnnotFrontmatter, HistoryEntrySpec, OverlaySpec, ParsedMdx } from '@ingcreators/annot-product-docs';
2
2
  export interface ExcelMdxBundle {
3
3
  /** Absolute or cwd-relative path to the source `.mdx` file. */
4
4
  mdxPath: string;
@@ -34,15 +34,43 @@ export interface NormalisedOverlay {
34
34
  /** Markdown body — caller renders to rich text. */
35
35
  body: string;
36
36
  }
37
+ /**
38
+ * Optional context for {@link extractFromParsed}. Phase 3d of
39
+ * `docs/plans/living-spec-authoring-roadmap.md`. When a `<Screen>`
40
+ * carries `annotations="…"`, the row generator wants the resolved
41
+ * yaml content — but we don't want `extractFromParsed` to do file
42
+ * I/O. The caller (`extractMdxFile`) pre-loads + parses each yaml
43
+ * keyed by the `annotations` path (relative to the MDX) and passes
44
+ * the map here. When the map is missing an entry (or this context
45
+ * isn't supplied), the extractor falls back to the legacy inline
46
+ * `<Overlay>` rows for that screen.
47
+ *
48
+ * `annotations[]` entries in the yaml are deliberately NOT
49
+ * surfaced as rows — they're image-only visual marking. The
50
+ * Astro Image Service composes them onto the PNG; the Excel
51
+ * adapter renders the resulting image in the spreadsheet's
52
+ * picture column and the items table stays scoped to overlays.
53
+ */
54
+ export interface ExtractFromParsedOptions {
55
+ /** Pre-loaded annotation yaml content keyed by the screen's `annotations` value. */
56
+ annotationsYamlByPath?: ReadonlyMap<string, AnnotationsFile>;
57
+ }
37
58
  /**
38
59
  * Extract a normalised bundle from a parsed MDX. Used directly
39
60
  * by `extractMdxFile` and re-exposed so tests can drive it
40
61
  * without filesystem I/O.
41
62
  */
42
- export declare function extractFromParsed(parsed: ParsedMdx, mdxPath: string): ExcelMdxBundle;
63
+ export declare function extractFromParsed(parsed: ParsedMdx, mdxPath: string, options?: ExtractFromParsedOptions): ExcelMdxBundle;
43
64
  /**
44
65
  * Convenience: parse the MDX file and normalise. Returns `null`
45
66
  * for files without `annot:` frontmatter so the bulk-extract
46
67
  * caller can keep its glob noise-free.
68
+ *
69
+ * Phase 3d: when the MDX contains `<Screen annotations="…">`
70
+ * blocks, the matching yaml files are loaded + parsed from disk
71
+ * before {@link extractFromParsed} runs. Missing yaml files are
72
+ * a loud failure (`throw`) — the same behaviour the Astro Image
73
+ * Service uses, on the same "explicit reference, but file gone"
74
+ * reasoning.
47
75
  */
48
76
  export declare function extractMdxFile(mdxPath: string): Promise<ExcelMdxBundle | null>;
package/dist/index.d.ts CHANGED
@@ -2,7 +2,7 @@ export type { CliOptions } from './cli.js';
2
2
  export { main, main as cliMain } from './cli.js';
3
3
  export type { ApplyDefaultLayoutInput } from './default-layout.js';
4
4
  export { applyDefaultLayout, sanitiseSheetName, sortBundlesForLayout, } from './default-layout.js';
5
- export type { ExcelMdxBundle, NormalisedOverlay, NormalisedScreen, } from './extract.js';
5
+ export type { ExcelMdxBundle, ExtractFromParsedOptions, NormalisedOverlay, NormalisedScreen, } from './extract.js';
6
6
  export { extractFromParsed, extractMdxFile } from './extract.js';
7
7
  export type { NamedRangeWriteInput } from './named-range.js';
8
8
  export { applyNamedRanges } from './named-range.js';
package/dist/index.js CHANGED
@@ -1,46 +1,46 @@
1
- import { mkdir as e, readdir as t, writeFile as n } from "node:fs/promises";
2
- import { join as r, resolve as i } from "node:path";
3
- import { pathToFileURL as a } from "node:url";
4
- import { parseMdxFile as o } from "@ingcreators/annot-product-docs";
5
- import s from "exceljs";
1
+ import { mkdir as e, readFile as t, readdir as n, writeFile as r } from "node:fs/promises";
2
+ import { dirname as i, isAbsolute as a, join as o, resolve as s } from "node:path";
3
+ import { pathToFileURL as c } from "node:url";
4
+ import { parseAnnotationsYaml as l, parseMdxFile as u } from "@ingcreators/annot-product-docs";
5
+ import d from "exceljs";
6
6
  //#region src/default-layout.ts
7
- var c = {
7
+ var f = {
8
8
  cover: 1,
9
9
  history: 2,
10
10
  list: 3,
11
11
  screen: 4,
12
12
  reference: 5
13
13
  };
14
- function l(e) {
15
- let t = u(e.bundles);
14
+ function p(e) {
15
+ let t = m(e.bundles);
16
16
  for (let n of t) {
17
- let t = n.frontmatter.xlsx?.role ?? "screen", r = g(n, t), i = e.workbook.addWorksheet(r);
17
+ let t = n.frontmatter.xlsx?.role ?? "screen", r = te(n, t), i = e.workbook.addWorksheet(r);
18
18
  switch (t) {
19
19
  case "cover":
20
- d(i, n);
20
+ h(i, n);
21
21
  break;
22
22
  case "history":
23
- f(i, n);
23
+ g(i, n);
24
24
  break;
25
25
  case "list":
26
- p(i, e.bundles);
26
+ _(i, e.bundles);
27
27
  break;
28
28
  case "reference":
29
- h(i, n);
29
+ v(i, n);
30
30
  break;
31
- default: m(i, n);
31
+ default: ee(i, n);
32
32
  }
33
33
  }
34
34
  }
35
- function u(e) {
35
+ function m(e) {
36
36
  return [...e].sort((e, t) => {
37
- let n = c[e.frontmatter.xlsx?.role ?? "screen"] ?? 99, r = c[t.frontmatter.xlsx?.role ?? "screen"] ?? 99;
37
+ let n = f[e.frontmatter.xlsx?.role ?? "screen"] ?? 99, r = f[t.frontmatter.xlsx?.role ?? "screen"] ?? 99;
38
38
  if (n !== r) return n - r;
39
39
  let i = e.frontmatter.xlsx?.order ?? 100, a = t.frontmatter.xlsx?.order ?? 100;
40
40
  return i === a ? e.mdxPath.localeCompare(t.mdxPath) : i - a;
41
41
  });
42
42
  }
43
- function d(e, t) {
43
+ function h(e, t) {
44
44
  let n = t.frontmatter;
45
45
  if (e.columns = [{
46
46
  key: "label",
@@ -63,7 +63,7 @@ function d(e, t) {
63
63
  });
64
64
  e.getColumn(1).font = { bold: !0 };
65
65
  }
66
- function f(e, t) {
66
+ function g(e, t) {
67
67
  e.columns = [
68
68
  {
69
69
  header: "Version",
@@ -94,7 +94,7 @@ function f(e, t) {
94
94
  });
95
95
  e.getRow(1).font = { bold: !0 };
96
96
  }
97
- function p(e, t) {
97
+ function _(e, t) {
98
98
  e.columns = [
99
99
  {
100
100
  header: "ID",
@@ -125,7 +125,7 @@ function p(e, t) {
125
125
  });
126
126
  e.getRow(1).font = { bold: !0 };
127
127
  }
128
- function m(e, t) {
128
+ function ee(e, t) {
129
129
  let n = t.frontmatter;
130
130
  e.addRow(["ID", n.id]), e.addRow(["Title", n.title ?? ""]), n.purpose && e.addRow(["Purpose", n.purpose]), e.addRow([]), e.addRow([
131
131
  "#",
@@ -145,97 +145,137 @@ function m(e, t) {
145
145
  ]);
146
146
  e.getColumn(1).width = 6, e.getColumn(2).width = 14, e.getColumn(3).width = 24, e.getColumn(4).width = 12, e.getColumn(5).width = 60, e.getColumn(1).font = { bold: !0 };
147
147
  }
148
- function h(e, t) {
148
+ function v(e, t) {
149
149
  e.addRow(["ID", t.frontmatter.id]), e.addRow(["Title", t.frontmatter.title ?? ""]), t.frontmatter.purpose && e.addRow(["Purpose", t.frontmatter.purpose]);
150
150
  }
151
- function g(e, t) {
151
+ function te(e, t) {
152
152
  let n = e.frontmatter.xlsx;
153
- return typeof n?.sheet == "string" && n.sheet.length > 0 ? _(n.sheet) : t === "cover" ? "Cover" : t === "history" ? "Revision history" : t === "list" ? "Screen list" : _(t === "reference" ? e.frontmatter.id : e.frontmatter.title ?? e.frontmatter.id);
153
+ return typeof n?.sheet == "string" && n.sheet.length > 0 ? y(n.sheet) : t === "cover" ? "Cover" : t === "history" ? "Revision history" : t === "list" ? "Screen list" : y(t === "reference" ? e.frontmatter.id : e.frontmatter.title ?? e.frontmatter.id);
154
154
  }
155
- function _(e) {
155
+ function y(e) {
156
156
  let t = e.replace(/[\\/?*[\]:]/g, "_").slice(0, 31);
157
157
  return t.length > 0 ? t : "Sheet";
158
158
  }
159
159
  //#endregion
160
160
  //#region src/extract.ts
161
- function v(e, t) {
162
- let n = e.screens.map((e) => ({
161
+ function b(e, t, n = {}) {
162
+ let r = n.annotationsYamlByPath, i = e.screens.map((e) => ({
163
163
  id: e.id,
164
164
  src: e.src,
165
- overlayCount: e.overlays.length
166
- })), r = [];
165
+ overlayCount: ne(e, r)
166
+ })), a = [];
167
167
  for (let t of e.screens) {
168
- let e = 1;
169
- for (let n of t.overlays) {
170
- let i = n.number ?? e++;
171
- r.push({
168
+ let e = S(t, r);
169
+ if (e) for (let n of e) {
170
+ let e = t.callouts.find((e) => e.for === n.id);
171
+ a.push({
172
172
  screenId: t.id,
173
- number: i,
173
+ number: n.number,
174
174
  intent: n.intent,
175
- matchLabel: ee(n),
175
+ matchLabel: T(n),
176
176
  matchRole: n.match.role,
177
177
  matchName: n.match.name,
178
- body: n.body
178
+ body: e?.body ?? ""
179
179
  });
180
180
  }
181
+ else {
182
+ let e = 1;
183
+ for (let n of t.overlays) {
184
+ let r = n.number ?? e++;
185
+ a.push({
186
+ screenId: t.id,
187
+ number: r,
188
+ intent: n.intent,
189
+ matchLabel: w(n),
190
+ matchRole: n.match.role,
191
+ matchName: n.match.name,
192
+ body: n.body
193
+ });
194
+ }
195
+ }
181
196
  }
182
197
  return {
183
198
  mdxPath: t,
184
199
  source: e.source,
185
200
  frontmatter: e.frontmatter,
186
- screens: n,
187
- overlays: r,
201
+ screens: i,
202
+ overlays: a,
188
203
  history: e.history,
189
204
  snapshotYaml: e.commentBlocks.snapshot ?? "",
190
205
  attributesYaml: e.commentBlocks.attributes ?? ""
191
206
  };
192
207
  }
193
- async function y(e) {
194
- let t = await o(e);
195
- return t ? v(t, e) : null;
208
+ async function x(e) {
209
+ let t = await u(e);
210
+ return t ? b(t, e, { annotationsYamlByPath: await C(t, e) }) : null;
211
+ }
212
+ function ne(e, t) {
213
+ let n = S(e, t);
214
+ return n ? n.length : e.overlays.length;
215
+ }
216
+ function S(e, t) {
217
+ return !t || !e.annotations ? null : t.get(e.annotations)?.overlays ?? null;
196
218
  }
197
- function ee(e) {
219
+ async function C(e, n) {
220
+ let r = /* @__PURE__ */ new Map(), o = i(n);
221
+ for (let n of e.screens) {
222
+ if (!n.annotations || r.has(n.annotations)) continue;
223
+ let e = a(n.annotations) ? n.annotations : s(o, n.annotations), i;
224
+ try {
225
+ i = await t(e, "utf8");
226
+ } catch (t) {
227
+ throw Error(`extractMdxFile: <Screen annotations="${n.annotations}"> — failed to read ${e}: ${t.message}`);
228
+ }
229
+ r.set(n.annotations, l(i));
230
+ }
231
+ return r;
232
+ }
233
+ function w(e) {
234
+ let t = `${e.match.role} "${e.match.name}"`;
235
+ return e.match.under ? `${t} under ${e.match.under.role} "${e.match.under.name}"` : t;
236
+ }
237
+ function T(e) {
198
238
  let t = `${e.match.role} "${e.match.name}"`;
199
239
  return e.match.under ? `${t} under ${e.match.under.role} "${e.match.under.name}"` : t;
200
240
  }
201
241
  //#endregion
202
242
  //#region src/placeholder.ts
203
- var te = /\{([^{}]+)\}/g, b = "annot:";
204
- function x(e, t, n = {}) {
243
+ var E = /\{([^{}]+)\}/g, D = "annot:";
244
+ function O(e, t, n = {}) {
205
245
  let r = n.totalSheets ?? e.worksheets.length;
206
246
  e.worksheets.forEach((e, i) => {
207
- S(e, t, {
247
+ k(e, t, {
208
248
  ...n,
209
249
  sheetIndex: n.sheetIndex ?? i + 1,
210
250
  totalSheets: r
211
251
  });
212
252
  });
213
253
  }
214
- function S(e, t, n = {}) {
254
+ function k(e, t, n = {}) {
215
255
  e.eachRow({ includeEmpty: !1 }, (e) => {
216
256
  e.eachCell({ includeEmpty: !1 }, (e) => {
217
257
  let r = e.value;
218
258
  if (typeof r != "string") return;
219
- let i = C(r, t, n);
259
+ let i = A(r, t, n);
220
260
  i !== r && (e.value = i);
221
261
  });
222
262
  });
223
263
  }
224
- function C(e, t, n = {}) {
225
- return e.replace(te, (e, r) => {
226
- let { key: i, format: a } = w(r), o = T(i, t, n);
227
- return o === void 0 ? e : a ? E(o, a) : o;
264
+ function A(e, t, n = {}) {
265
+ return e.replace(E, (e, r) => {
266
+ let { key: i, format: a } = j(r), o = M(i, t, n);
267
+ return o === void 0 ? e : a ? N(o, a) : o;
228
268
  });
229
269
  }
230
- function w(e) {
270
+ function j(e) {
231
271
  let t = e.trim();
232
- if (t.startsWith(b)) {
272
+ if (t.startsWith(D)) {
233
273
  let e = t.slice(6), n = e.indexOf(":");
234
274
  return n < 0 ? {
235
275
  key: t,
236
276
  format: void 0
237
277
  } : {
238
- key: b + e.slice(0, n),
278
+ key: D + e.slice(0, n),
239
279
  format: e.slice(n + 1)
240
280
  };
241
281
  }
@@ -248,11 +288,11 @@ function w(e) {
248
288
  format: t.slice(n + 1)
249
289
  };
250
290
  }
251
- function T(e, t, n) {
252
- if (e.startsWith(b)) {
291
+ function M(e, t, n) {
292
+ if (e.startsWith(D)) {
253
293
  let t = e.slice(6), r = n.renderTime ?? /* @__PURE__ */ new Date();
254
294
  switch (t) {
255
- case "date": return O(r, "yyyy-MM-dd");
295
+ case "date": return F(r, "yyyy-MM-dd");
256
296
  case "datetime": return r.toISOString();
257
297
  case "sheetIndex": return n.sheetIndex === void 0 ? void 0 : String(n.sheetIndex);
258
298
  case "totalSheets": return n.totalSheets === void 0 ? void 0 : String(n.totalSheets);
@@ -269,24 +309,24 @@ function T(e, t, n) {
269
309
  let r = n.projectMeta?.[e];
270
310
  if (r !== void 0) return String(r);
271
311
  }
272
- function E(e, t) {
273
- let n = D(e);
274
- return n ? O(n, t) : e;
312
+ function N(e, t) {
313
+ let n = P(e);
314
+ return n ? F(n, t) : e;
275
315
  }
276
- function D(e) {
316
+ function P(e) {
277
317
  let t = e.trim(), n = t.match(/^(\d{4})-(\d{2})-(\d{2})$/);
278
318
  if (n) return new Date(Number.parseInt(n[1], 10), Number.parseInt(n[2], 10) - 1, Number.parseInt(n[3], 10));
279
319
  let r = new Date(t);
280
320
  return Number.isNaN(r.getTime()) ? null : r;
281
321
  }
282
- function O(e, t) {
322
+ function F(e, t) {
283
323
  let n = String(e.getFullYear()).padStart(4, "0"), r = String(e.getMonth() + 1).padStart(2, "0"), i = String(e.getDate()).padStart(2, "0"), a = String(e.getHours()).padStart(2, "0"), o = String(e.getMinutes()).padStart(2, "0"), s = String(e.getSeconds()).padStart(2, "0");
284
324
  return t.replace(/yyyy/g, n).replace(/MM/g, r).replace(/dd/g, i).replace(/HH/g, a).replace(/mm/g, o).replace(/ss/g, s);
285
325
  }
286
326
  //#endregion
287
327
  //#region src/template.ts
288
- function k(e) {
289
- let t = u(e.bundles);
328
+ function I(e) {
329
+ let t = m(e.bundles);
290
330
  for (let n of t) {
291
331
  let t = n.frontmatter.xlsx?.role ?? "screen", r = e.bookConfig.templateSheets?.[t];
292
332
  if (!r) continue;
@@ -295,18 +335,18 @@ function k(e) {
295
335
  let a = n.frontmatter.xlsx?.sheets;
296
336
  if (a) {
297
337
  let t = Object.entries(a);
298
- for (let [, r] of t) S(j(e.workbook, i, _(r)), n, e.substitute ?? {});
338
+ for (let [, r] of t) k(R(e.workbook, i, y(r)), n, e.substitute ?? {});
299
339
  continue;
300
340
  }
301
- let o = _(n.frontmatter.xlsx?.sheet ?? n.frontmatter.title ?? n.frontmatter.id);
302
- S(j(e.workbook, i, o), n, e.substitute ?? {});
341
+ let o = y(n.frontmatter.xlsx?.sheet ?? n.frontmatter.title ?? n.frontmatter.id);
342
+ k(R(e.workbook, i, o), n, e.substitute ?? {});
303
343
  }
304
344
  }
305
- async function A(e) {
306
- let t = new s.Workbook();
345
+ async function L(e) {
346
+ let t = new d.Workbook();
307
347
  return await t.xlsx.readFile(e), t;
308
348
  }
309
- function j(e, t, n) {
349
+ function R(e, t, n) {
310
350
  let r = e.addWorksheet(n);
311
351
  r.columns = t.columns.map((e) => ({
312
352
  header: e.header,
@@ -320,23 +360,23 @@ function j(e, t, n) {
320
360
  r.value = e.value, e.style && (r.style = e.style);
321
361
  }), e.height !== void 0 && (n.height = e.height), n.commit();
322
362
  });
323
- for (let e of Object.values(M(t))) r.mergeCells(e);
363
+ for (let e of Object.values(z(t))) r.mergeCells(e);
324
364
  return r;
325
365
  }
326
- function M(e) {
366
+ function z(e) {
327
367
  return e._merges ?? {};
328
368
  }
329
369
  //#endregion
330
370
  //#region src/workbook.ts
331
- function N(e) {
332
- let t = new s.Workbook();
371
+ function B(e) {
372
+ let t = new d.Workbook();
333
373
  return t.creator = "@ingcreators/annot-product-docs-xlsx", t.created = /* @__PURE__ */ new Date(), t.title = e.book, t;
334
374
  }
335
- async function P(e) {
375
+ async function V(e) {
336
376
  let t = await e.xlsx.writeBuffer();
337
377
  return t instanceof Buffer ? new Uint8Array(t.buffer, t.byteOffset, t.byteLength) : new Uint8Array(t);
338
378
  }
339
- function F(e, t) {
379
+ function H(e, t) {
340
380
  let n = /* @__PURE__ */ new Map();
341
381
  for (let r of e) {
342
382
  let e = r.frontmatter.xlsx?.book ?? t;
@@ -348,7 +388,7 @@ function F(e, t) {
348
388
  }
349
389
  //#endregion
350
390
  //#region src/cli.ts
351
- var I = [
391
+ var U = [
352
392
  "annot-docs-xlsx <command> [options]",
353
393
  "",
354
394
  "Commands:",
@@ -361,17 +401,17 @@ var I = [
361
401
  " --config <file> Path to annot-docs.config.ts (default: ./annot-docs.config.ts)",
362
402
  " --help Show this help"
363
403
  ].join("\n");
364
- async function L(e, t = {}) {
404
+ async function W(e, t = {}) {
365
405
  let n = t.stdout ?? ((e) => process.stdout.write(`${e}\n`)), r = t.stderr ?? ((e) => process.stderr.write(`${e}\n`)), i = t.cwd ?? process.cwd(), [, , a, ...o] = e;
366
- if (a !== "render") return r(I), +!!a;
367
- let s = R(o);
406
+ if (a !== "render") return r(U), +!!a;
407
+ let s = G(o);
368
408
  try {
369
- return await z(i, s, n);
409
+ return await K(i, s, n);
370
410
  } catch (e) {
371
411
  return r(`annot-docs-xlsx render: ${e.message}`), 1;
372
412
  }
373
413
  }
374
- function R(e) {
414
+ function G(e) {
375
415
  let t = "docs", n = "dist/xlsx", r, i = "annot-docs.config.ts";
376
416
  for (let a = 0; a < e.length; a++) {
377
417
  let o = e[a];
@@ -384,99 +424,99 @@ function R(e) {
384
424
  config: i
385
425
  };
386
426
  }
387
- async function z(t, a, o) {
388
- let s = await B(i(t, a.config), o), c = await H(await V(i(t, a.root)));
389
- if (c.length === 0) return o(`annot-docs-xlsx render: no MDX files with \`annot:\` frontmatter under ${a.root}.`), 0;
390
- let u = F(c, s.xlsx?.defaultBook), d = i(t, a.out);
391
- await e(d, { recursive: !0 });
392
- let f = 0;
393
- for (let [e, c] of u.entries()) {
394
- if (a.book && e !== a.book) continue;
395
- let u = N({
427
+ async function K(t, n, i) {
428
+ let a = await q(s(t, n.config), i), c = await J(await re(s(t, n.root)));
429
+ if (c.length === 0) return i(`annot-docs-xlsx render: no MDX files with \`annot:\` frontmatter under ${n.root}.`), 0;
430
+ let l = H(c, a.xlsx?.defaultBook), u = s(t, n.out);
431
+ await e(u, { recursive: !0 });
432
+ let d = 0;
433
+ for (let [e, c] of l.entries()) {
434
+ if (n.book && e !== n.book) continue;
435
+ let l = B({
396
436
  book: e,
397
437
  bundles: c
398
- }), p = s.xlsx?.books?.[e], m = p?.template;
399
- m ? k({
400
- workbook: u,
401
- template: await A(i(t, m)),
402
- bookConfig: p,
438
+ }), f = a.xlsx?.books?.[e], m = f?.template;
439
+ m ? I({
440
+ workbook: l,
441
+ template: await L(s(t, m)),
442
+ bookConfig: f,
403
443
  bundles: c,
404
444
  substitute: {
405
- projectMeta: s.meta,
445
+ projectMeta: a.meta,
406
446
  renderTime: /* @__PURE__ */ new Date()
407
447
  }
408
- }) : l({
409
- workbook: u,
448
+ }) : p({
449
+ workbook: l,
410
450
  bundles: c
411
451
  });
412
- let h = await P(u), g = r(d, `${U(e)}.xlsx`);
413
- await n(g, h), o(` wrote ${g} (${c.length} MDX file(s))`), f++;
452
+ let h = await V(l), g = o(u, `${Y(e)}.xlsx`);
453
+ await r(g, h), i(` wrote ${g} (${c.length} MDX file(s))`), d++;
414
454
  }
415
- return a.book && f === 0 ? (o(`annot-docs-xlsx render: book "${a.book}" not found (had: ${[...u.keys()].join(", ")}).`), 1) : (o(`annot-docs-xlsx render: emitted ${f} workbook(s) to ${a.out}`), 0);
455
+ return n.book && d === 0 ? (i(`annot-docs-xlsx render: book "${n.book}" not found (had: ${[...l.keys()].join(", ")}).`), 1) : (i(`annot-docs-xlsx render: emitted ${d} workbook(s) to ${n.out}`), 0);
416
456
  }
417
- async function B(e, t) {
457
+ async function q(e, t) {
418
458
  try {
419
- let t = await import(a(e).href);
459
+ let t = await import(c(e).href);
420
460
  return t.default ?? t;
421
461
  } catch (n) {
422
462
  if (n.code === "ERR_MODULE_NOT_FOUND") return t(`annot-docs-xlsx render: no config at ${e} — using defaults.`), {};
423
463
  throw n;
424
464
  }
425
465
  }
426
- async function V(e) {
427
- let n = [], i = [e];
428
- for (; i.length > 0;) {
429
- let e = i.pop(), a;
466
+ async function re(e) {
467
+ let t = [], r = [e];
468
+ for (; r.length > 0;) {
469
+ let e = r.pop(), i;
430
470
  try {
431
- a = await t(e, { withFileTypes: !0 });
471
+ i = await n(e, { withFileTypes: !0 });
432
472
  } catch (e) {
433
473
  if (e.code === "ENOENT") continue;
434
474
  throw e;
435
475
  }
436
- for (let t of a) {
437
- let a = r(e, t.name);
438
- if (t.isDirectory()) {
439
- if (t.name === "node_modules" || t.name.startsWith(".")) continue;
440
- i.push(a);
441
- } else t.isFile() && t.name.endsWith(".mdx") && n.push(a);
476
+ for (let n of i) {
477
+ let i = o(e, n.name);
478
+ if (n.isDirectory()) {
479
+ if (n.name === "node_modules" || n.name.startsWith(".")) continue;
480
+ r.push(i);
481
+ } else n.isFile() && n.name.endsWith(".mdx") && t.push(i);
442
482
  }
443
483
  }
444
- return n.sort();
484
+ return t.sort();
445
485
  }
446
- async function H(e) {
486
+ async function J(e) {
447
487
  let t = [];
448
488
  for (let n of e) try {
449
- let e = await o(n);
450
- e && t.push(v(e, n));
489
+ let e = await u(n);
490
+ e && t.push(b(e, n));
451
491
  } catch {}
452
492
  return t;
453
493
  }
454
- function U(e) {
494
+ function Y(e) {
455
495
  return e.replace(/[\\/?*[\]:<>|"]/g, "_");
456
496
  }
457
497
  //#endregion
458
498
  //#region src/named-range.ts
459
- var W = "annot";
460
- function G(e) {
461
- for (let t of ie(e.workbook)) K(e, t);
499
+ var X = "annot";
500
+ function ie(e) {
501
+ for (let t of fe(e.workbook)) ae(e, t);
462
502
  }
463
- function K(e, t) {
464
- let [n, r] = q(t.name.replace(/^annot/, ""));
503
+ function ae(e, t) {
504
+ let [n, r] = oe(t.name.replace(/^annot/, ""));
465
505
  switch (n) {
466
506
  case "Image":
467
- J(e, t, r);
507
+ se(e, t, r);
468
508
  return;
469
509
  case "ItemTable":
470
- X(t, e.bundle);
510
+ ce(t, e.bundle);
471
511
  return;
472
512
  case "Transitions":
473
- Z(t, e.bundle);
513
+ le(t, e.bundle);
474
514
  return;
475
515
  case "History":
476
- ne(t, e.bundle);
516
+ ue(t, e.bundle);
477
517
  return;
478
518
  case "List":
479
- re(t, e.allBundles ?? [e.bundle]);
519
+ de(t, e.allBundles ?? [e.bundle]);
480
520
  return;
481
521
  case "Snapshot":
482
522
  Q(t, e.bundle.snapshotYaml);
@@ -486,11 +526,11 @@ function K(e, t) {
486
526
  return;
487
527
  }
488
528
  }
489
- function q(e) {
529
+ function oe(e) {
490
530
  let t = e.indexOf("_");
491
531
  return t < 0 ? [e, void 0] : [e.slice(0, t), e.slice(t + 1)];
492
532
  }
493
- function J(e, t, n) {
533
+ function se(e, t, n) {
494
534
  let r = n ? e.imagesByScreenId?.[n] : e.defaultImage ?? e.imagesByScreenId?.[e.bundle.screens[0]?.id ?? ""];
495
535
  if (!r) return;
496
536
  let i = e.workbook.addImage({
@@ -499,7 +539,7 @@ function J(e, t, n) {
499
539
  });
500
540
  t.sheet.addImage(i, t.address);
501
541
  }
502
- function Y(e, t, n) {
542
+ function Z(e, t, n) {
503
543
  let { sheet: r, box: i } = e;
504
544
  for (let e = 0; e < t.length; e++) {
505
545
  let n = r.getCell(i.startRow, i.startCol + e);
@@ -511,8 +551,8 @@ function Y(e, t, n) {
511
551
  for (let e = 0; e < t.length; e++) r.getCell(a, i.startCol + e).value = t[e] ?? "";
512
552
  }
513
553
  }
514
- function X(e, t) {
515
- Y(e, [
554
+ function ce(e, t) {
555
+ Z(e, [
516
556
  "#",
517
557
  "Role",
518
558
  "Name",
@@ -526,16 +566,16 @@ function X(e, t) {
526
566
  e.body
527
567
  ]));
528
568
  }
529
- function Z(e, t) {
530
- Y(e, [
569
+ function le(e, t) {
570
+ Z(e, [
531
571
  "Trigger",
532
572
  "Event",
533
573
  "Target",
534
574
  "Notes"
535
575
  ], []);
536
576
  }
537
- function ne(e, t) {
538
- Y(e, [
577
+ function ue(e, t) {
578
+ Z(e, [
539
579
  "Version",
540
580
  "Date",
541
581
  "Author",
@@ -547,8 +587,8 @@ function ne(e, t) {
547
587
  e.body
548
588
  ]));
549
589
  }
550
- function re(e, t) {
551
- Y(e, [
590
+ function de(e, t) {
591
+ Z(e, [
552
592
  "ID",
553
593
  "Title",
554
594
  "Screens",
@@ -567,13 +607,13 @@ function Q(e, t) {
567
607
  vertical: "top"
568
608
  };
569
609
  }
570
- function ie(e) {
610
+ function fe(e) {
571
611
  let t = /* @__PURE__ */ new Map();
572
612
  for (let n of e.worksheets) n.eachRow({ includeEmpty: !0 }, (e, r) => {
573
613
  e.eachCell({ includeEmpty: !0 }, (e, i) => {
574
- let a = ae(e);
614
+ let a = pe(e);
575
615
  for (let e of a) {
576
- if (!e.startsWith(W)) continue;
616
+ if (!e.startsWith(X)) continue;
577
617
  let a = `${n.name}|${e}`, o = t.get(a);
578
618
  o || (o = {
579
619
  sheet: n,
@@ -601,7 +641,7 @@ function ie(e) {
601
641
  };
602
642
  });
603
643
  }
604
- function ae(e) {
644
+ function pe(e) {
605
645
  return e.names ?? [];
606
646
  }
607
647
  function $(e) {
@@ -613,4 +653,4 @@ function $(e) {
613
653
  return n;
614
654
  }
615
655
  //#endregion
616
- export { l as applyDefaultLayout, G as applyNamedRanges, x as applyPlaceholders, S as applyPlaceholdersToSheet, k as applyTemplateLayout, N as buildEmptyWorkbook, L as cliMain, L as main, v as extractFromParsed, y as extractMdxFile, F as groupBundlesByBook, A as loadTemplateWorkbook, C as resolvePlaceholders, _ as sanitiseSheetName, u as sortBundlesForLayout, P as writeWorkbookToBytes };
656
+ export { p as applyDefaultLayout, ie as applyNamedRanges, O as applyPlaceholders, k as applyPlaceholdersToSheet, I as applyTemplateLayout, B as buildEmptyWorkbook, W as cliMain, W as main, b as extractFromParsed, x as extractMdxFile, H as groupBundlesByBook, L as loadTemplateWorkbook, A as resolvePlaceholders, y as sanitiseSheetName, m as sortBundlesForLayout, V as writeWorkbookToBytes };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@ingcreators/annot-product-docs-xlsx",
3
- "version": "0.2.1",
3
+ "version": "0.2.2",
4
4
  "description": "Excel adapter for `@ingcreators/annot-product-docs`. Walks MDX files with `annot:` frontmatter, fills customer-supplied Excel templates via `{var}` placeholders + named ranges, and emits one `.xlsx` per book. Phase 3 of docs/plans/living-product-docs.md.",
5
5
  "license": "Apache-2.0",
6
6
  "author": "ingcreators",
@@ -47,12 +47,12 @@
47
47
  },
48
48
  "devDependencies": {
49
49
  "typescript": "^6.0.3",
50
- "vite": "^8.0.13",
51
- "vite-plugin-dts": "^5.0.1"
50
+ "vite": "^8.0.16",
51
+ "vite-plugin-dts": "^5.0.3"
52
52
  },
53
53
  "dependencies": {
54
54
  "exceljs": "^4.4.0",
55
- "@ingcreators/annot-product-docs": "0.3.0"
55
+ "@ingcreators/annot-product-docs": "0.4.0"
56
56
  },
57
57
  "scripts": {
58
58
  "build": "vite build",