@heroiclands/package-build 23.12.6 → 23.12.8
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 +18 -0
- package/assets/styles/content-base.css +25 -0
- package/bin/content-commands.mjs +264 -3
- package/bin/package-build.mjs +25 -0
- package/content-config.mjs +72 -0
- package/docs/api.md +10 -9
- package/docs/authoring/assets.md +1 -1
- package/docs/authoring/links-and-markup.md +439 -47
- package/docs/commands.md +137 -3
- package/docs/configuration.md +73 -3
- package/docs/content-format.md +3 -1
- package/docs/guides/book.md +11 -0
- package/docs/guides/module-project.md +16 -0
- package/docs/guides/site.md +19 -0
- package/docs/reference/format-details.md +378 -6
- package/docs/reference/note-types.md +36 -11
- package/e2e.mjs +1 -1
- package/engine/asset-shipping.mjs +22 -8
- package/engine/base-compiler.mjs +2 -0
- package/engine/bundles.mjs +7 -2
- package/engine/compile-corpus.mjs +3 -1
- package/engine/content-charset.mjs +21 -2
- package/engine/content-format.yaml +1 -0
- package/engine/content-index.mjs +12 -0
- package/engine/content-poetry.mjs +22 -4
- package/engine/content-scripts.mjs +1219 -0
- package/engine/content-session.mjs +2 -0
- package/engine/data-keys.mjs +5 -1
- package/engine/dictionary-layout.mjs +18 -12
- package/engine/dictionary-rows.mjs +11 -2
- package/engine/helpers.mjs +8 -2
- package/engine/index-records.mjs +1 -0
- package/engine/journals.mjs +14 -3
- package/engine/language-data.mjs +137 -1
- package/engine/language-tag.mjs +103 -0
- package/engine/language-terms.mjs +16 -4
- package/engine/map-lexicon.mjs +762 -0
- package/engine/markup-validation.mjs +17 -3
- package/engine/names.mjs +1 -1
- package/engine/note-vocabulary.mjs +113 -0
- package/engine/pdf-build.mjs +28 -10
- package/engine/pdf-render.mjs +116 -11
- package/engine/run-rows.mjs +119 -0
- package/engine/run-words.mjs +266 -0
- package/engine/scenes.mjs +1 -0
- package/engine/script-font-delivery.mjs +321 -0
- package/engine/script-fonts.mjs +172 -0
- package/engine/site-build.mjs +10 -3
- package/engine/site-config.mjs +5 -0
- package/engine/site-root.mjs +19 -5
- package/engine/sql-tables.mjs +111 -1
- package/engine/text-maps.mjs +607 -0
- package/engine/verb-pattern.mjs +99 -0
- package/engine/word-pattern.mjs +27 -0
- package/engine/word-rows.mjs +8 -2
- package/engine/word-terms.mjs +44 -0
- package/hugo-theme/layouts/_default/baseof.html +3 -0
- package/hugo-theme/static/css/style.css +10 -0
- package/manifest.mjs +9 -1
- package/package.json +2 -2
- package/types/content-config.d.mts +26 -0
- package/types/e2e.d.mts +2 -2
- package/types/engine/address-fields.d.mts +1 -1
- package/types/engine/address-values.d.mts +1 -1
- package/types/engine/asset-shipping.d.mts +5 -0
- package/types/engine/compile-corpus.d.mts +2 -1
- package/types/engine/content-format-check.d.mts +1 -1
- package/types/engine/content-index.d.mts +11 -3
- package/types/engine/content-poetry.d.mts +7 -0
- package/types/engine/content-scripts.d.mts +226 -0
- package/types/engine/data-keys.d.mts +2 -2
- package/types/engine/dictionary-rows.d.mts +15 -0
- package/types/engine/helpers.d.mts +5 -1
- package/types/engine/journals.d.mts +7 -2
- package/types/engine/language-data.d.mts +2 -0
- package/types/engine/language-tag.d.mts +8 -0
- package/types/engine/language-terms.d.mts +2 -1
- package/types/engine/map-lexicon.d.mts +274 -0
- package/types/engine/markup-validation.d.mts +7 -2
- package/types/engine/note-vocabulary.d.mts +1 -1
- package/types/engine/pdf-build.d.mts +26 -3
- package/types/engine/pdf-coverage.d.mts +1 -1
- package/types/engine/pdf-render.d.mts +17 -2
- package/types/engine/run-rows.d.mts +89 -0
- package/types/engine/run-words.d.mts +86 -0
- package/types/engine/script-font-delivery.d.mts +134 -0
- package/types/engine/script-fonts.d.mts +168 -0
- package/types/engine/site-build.d.mts +2 -1
- package/types/engine/site-root.d.mts +11 -3
- package/types/engine/text-maps.d.mts +175 -0
- package/types/engine/verb-pattern.d.mts +65 -0
- package/types/engine/word-pattern.d.mts +13 -0
- package/types/engine/word-terms.d.mts +6 -0
- package/types/release.d.mts +1 -1
|
@@ -0,0 +1,99 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* This file is part of the Song of Heroic Lands (SoHL) system for Foundry VTT.
|
|
3
|
+
* Copyright (c) 2024-2026 Tom Rodriguez ("Toasty") — <toasty@heroiclands.org>
|
|
4
|
+
*
|
|
5
|
+
* This work is licensed under the GNU General Public License v3.0 (GPLv3).
|
|
6
|
+
* You may copy, modify, and distribute it under the terms of that license.
|
|
7
|
+
*
|
|
8
|
+
* For full terms, see the LICENSE.md file in the project root or visit:
|
|
9
|
+
* https://www.gnu.org/licenses/gpl-3.0.html
|
|
10
|
+
*
|
|
11
|
+
* SPDX-License-Identifier: GPL-3.0-or-later
|
|
12
|
+
*/
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* **A language's one regular verb pattern, read once for every reader.** A
|
|
16
|
+
* language's `data.grammar.verbs` is `{ invariant: true }` or six `persons`
|
|
17
|
+
* endings, optionally with `replaces`. A present form is the citation form
|
|
18
|
+
* with the ending added; where the pattern states `replaces`, a citation form
|
|
19
|
+
* closing on those letters has them swapped for the ending, and one closing
|
|
20
|
+
* otherwise takes the ending whole, as a suffix's `replaces` does.
|
|
21
|
+
*
|
|
22
|
+
* The dictionary's verb table and a mapped run's lexicon check both read the
|
|
23
|
+
* pattern through {@link verbPattern} and build forms with {@link verbForm}.
|
|
24
|
+
*
|
|
25
|
+
* @module
|
|
26
|
+
*/
|
|
27
|
+
|
|
28
|
+
import { VERB_PERSON_FIELDS } from "./language-terms.mjs";
|
|
29
|
+
|
|
30
|
+
/** Whether a value is a plain map. */
|
|
31
|
+
const isMap = (value) => value !== null && typeof value === "object" && !Array.isArray(value);
|
|
32
|
+
|
|
33
|
+
/**
|
|
34
|
+
* A stated verb pattern, as its readers use it.
|
|
35
|
+
*
|
|
36
|
+
* @typedef {object} VerbPattern
|
|
37
|
+
* @property {boolean} invariant - Whether verbs keep the citation form for
|
|
38
|
+
* every person.
|
|
39
|
+
* @property {string|undefined} replaces - The letters each ending takes the
|
|
40
|
+
* place of, where the pattern states them.
|
|
41
|
+
* @property {Array<{name: string, label: string, ending: string}>} endings -
|
|
42
|
+
* The six endings in presentation order; empty for an invariant pattern.
|
|
43
|
+
*/
|
|
44
|
+
|
|
45
|
+
/**
|
|
46
|
+
* Read a language's verb pattern.
|
|
47
|
+
*
|
|
48
|
+
* @param {unknown} verbs - The language's `data.grammar.verbs`, as authored or
|
|
49
|
+
* as a SQL row carries it (absent fields `null`).
|
|
50
|
+
* @returns {VerbPattern|undefined} The pattern, or `undefined` where none is
|
|
51
|
+
* stated in full.
|
|
52
|
+
*/
|
|
53
|
+
export function verbPattern(verbs) {
|
|
54
|
+
if (!isMap(verbs)) return undefined;
|
|
55
|
+
const replaces =
|
|
56
|
+
typeof verbs.replaces === "string" && verbs.replaces.trim() ? verbs.replaces : undefined;
|
|
57
|
+
if (verbs.invariant === true) return { invariant: true, replaces, endings: [] };
|
|
58
|
+
const persons = isMap(verbs.persons) ? verbs.persons : undefined;
|
|
59
|
+
if (!persons || !VERB_PERSON_FIELDS.every(({ name }) => typeof persons[name] === "string"))
|
|
60
|
+
return undefined;
|
|
61
|
+
return {
|
|
62
|
+
invariant: false,
|
|
63
|
+
replaces,
|
|
64
|
+
endings: VERB_PERSON_FIELDS.map(({ name, label }) => ({
|
|
65
|
+
name,
|
|
66
|
+
label,
|
|
67
|
+
ending: persons[name],
|
|
68
|
+
})),
|
|
69
|
+
};
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
/**
|
|
73
|
+
* A stem with its closing letters swapped for an ending, or with the ending
|
|
74
|
+
* added where the stem does not close on them.
|
|
75
|
+
*
|
|
76
|
+
* @param {string} stem - The stem.
|
|
77
|
+
* @param {string} ending - The ending.
|
|
78
|
+
* @param {string|undefined} letters - The closing letters the ending takes
|
|
79
|
+
* the place of; none adds the ending.
|
|
80
|
+
* @returns {string} The form.
|
|
81
|
+
*/
|
|
82
|
+
export function replaceClosing(stem, ending, letters) {
|
|
83
|
+
return letters && stem.endsWith(letters) ?
|
|
84
|
+
stem.slice(0, -letters.length) + ending
|
|
85
|
+
: stem + ending;
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
/**
|
|
89
|
+
* The present form of a verb for one ending.
|
|
90
|
+
*
|
|
91
|
+
* @param {string} citation - The citation form.
|
|
92
|
+
* @param {string} ending - The person's ending; empty leaves the citation
|
|
93
|
+
* form, less any closing `replaces`.
|
|
94
|
+
* @param {string} [replaces] - The pattern's `replaces`.
|
|
95
|
+
* @returns {string} The form.
|
|
96
|
+
*/
|
|
97
|
+
export function verbForm(citation, ending, replaces) {
|
|
98
|
+
return replaceClosing(citation, ending, replaces);
|
|
99
|
+
}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* This file is part of the Song of Heroic Lands (SoHL) system for Foundry VTT.
|
|
3
|
+
* Copyright (c) 2024-2026 Tom Rodriguez ("Toasty") — <toasty@heroiclands.org>
|
|
4
|
+
*
|
|
5
|
+
* This work is licensed under the GNU General Public License v3.0 (GPLv3).
|
|
6
|
+
* You may copy, modify, and distribute it under the terms of that license.
|
|
7
|
+
*
|
|
8
|
+
* For full terms, see the LICENSE.md file in the project root or visit:
|
|
9
|
+
* https://www.gnu.org/licenses/gpl-3.0.html
|
|
10
|
+
*
|
|
11
|
+
* SPDX-License-Identifier: GPL-3.0-or-later
|
|
12
|
+
*/
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* **What a word is in running text.** A word is a maximal run of letters,
|
|
16
|
+
* combining marks and digits, and an apostrophe (`'` or `’`), a hyphen or an
|
|
17
|
+
* en dash joins two such runs into one word: `k'aralzon`, `Arzen-Thalor`.
|
|
18
|
+
* Anything else, whitespace and punctuation included, sits between words.
|
|
19
|
+
*
|
|
20
|
+
* The name catalog reads a label's last word by it, and a mapped run reads
|
|
21
|
+
* each word it looks up in a lexicon by it.
|
|
22
|
+
*
|
|
23
|
+
* @module
|
|
24
|
+
*/
|
|
25
|
+
|
|
26
|
+
/** One word; global, so `matchAll` walks every word of a text. */
|
|
27
|
+
export const WORD = /[\p{L}\p{M}\p{N}]+(?:[’'–-][\p{L}\p{M}\p{N}]+)*/gu;
|
package/engine/word-rows.mjs
CHANGED
|
@@ -47,6 +47,12 @@ import {
|
|
|
47
47
|
glossText,
|
|
48
48
|
} from "./word-terms.mjs";
|
|
49
49
|
|
|
50
|
+
/**
|
|
51
|
+
* The word's own keys a word row carries: all but `native`, whose entries are
|
|
52
|
+
* rows of the `natives` relation.
|
|
53
|
+
*/
|
|
54
|
+
const WORD_ROW_KEYS = Object.freeze(WORD_KEYS.filter((key) => key !== "native"));
|
|
55
|
+
|
|
50
56
|
/** The columns a word row carries before the word's own keys. */
|
|
51
57
|
const WORD_IDENTITY_COLUMNS = Object.freeze(["language", "position"]);
|
|
52
58
|
|
|
@@ -56,7 +62,7 @@ const WORD_DERIVED_COLUMNS = Object.freeze(["built_text", "built_parts", "senses
|
|
|
56
62
|
/** Every column of the `words` relation, in order. */
|
|
57
63
|
export const WORD_COLUMNS = Object.freeze([
|
|
58
64
|
...WORD_IDENTITY_COLUMNS,
|
|
59
|
-
...
|
|
65
|
+
...WORD_ROW_KEYS,
|
|
60
66
|
...WORD_DERIVED_COLUMNS,
|
|
61
67
|
]);
|
|
62
68
|
|
|
@@ -260,7 +266,7 @@ export function wordRows(records, all = records) {
|
|
|
260
266
|
words.forEach((entry, position) => {
|
|
261
267
|
if (!isMap(entry)) return;
|
|
262
268
|
const row = { language, position };
|
|
263
|
-
for (const key of
|
|
269
|
+
for (const key of WORD_ROW_KEYS) row[key] = entry[key] ?? null;
|
|
264
270
|
if (row.name_sort === null) row.name_sort = row.form;
|
|
265
271
|
const built = Array.isArray(entry.built) ? entry.built.map(String) : [];
|
|
266
272
|
row.built_text = built.length ? built.join(" + ") : null;
|
package/engine/word-terms.mjs
CHANGED
|
@@ -99,6 +99,37 @@ export const WORD_SOURCE_FIELDS = Object.freeze([
|
|
|
99
99
|
}),
|
|
100
100
|
]);
|
|
101
101
|
|
|
102
|
+
/**
|
|
103
|
+
* The keys of one entry of a word's `native`.
|
|
104
|
+
*
|
|
105
|
+
* @type {readonly import("./data-keys.mjs").InnerKeySpec[]}
|
|
106
|
+
*/
|
|
107
|
+
export const WORD_NATIVE_FIELDS = Object.freeze([
|
|
108
|
+
Object.freeze({
|
|
109
|
+
name: "map",
|
|
110
|
+
kind: "string",
|
|
111
|
+
required: true,
|
|
112
|
+
shape: "a mapping note's `data.map.name`",
|
|
113
|
+
describe: "The map the native form is written for.",
|
|
114
|
+
}),
|
|
115
|
+
Object.freeze({
|
|
116
|
+
name: "font",
|
|
117
|
+
kind: "string",
|
|
118
|
+
shape: "a face the map lists",
|
|
119
|
+
describe:
|
|
120
|
+
"The one face the native form is for; unstated, it is for every face the map lists, " +
|
|
121
|
+
"and a form stated for a face wins over it there.",
|
|
122
|
+
}),
|
|
123
|
+
Object.freeze({
|
|
124
|
+
name: "text",
|
|
125
|
+
kind: "string",
|
|
126
|
+
required: true,
|
|
127
|
+
shape: "the word in the script, as the map's characters",
|
|
128
|
+
describe:
|
|
129
|
+
"The word as the script writes it, where the map's rows would write it otherwise.",
|
|
130
|
+
}),
|
|
131
|
+
]);
|
|
132
|
+
|
|
102
133
|
/**
|
|
103
134
|
* The keys one word of a language note's `data.words` carries.
|
|
104
135
|
*
|
|
@@ -209,6 +240,19 @@ export const WORD_FIELDS = Object.freeze([
|
|
|
209
240
|
shape: "a frame of the language's `sounds.frames`",
|
|
210
241
|
describe: "The frame a root is set in, named in the language's `sounds.frames`.",
|
|
211
242
|
}),
|
|
243
|
+
Object.freeze({
|
|
244
|
+
name: "native",
|
|
245
|
+
kind: "list",
|
|
246
|
+
shape: "a list of `{ map, font?, text }`",
|
|
247
|
+
entries: Object.freeze({
|
|
248
|
+
kind: "map",
|
|
249
|
+
shape: "a map — `{ map, font?, text }`",
|
|
250
|
+
fields: WORD_NATIVE_FIELDS,
|
|
251
|
+
}),
|
|
252
|
+
describe:
|
|
253
|
+
"The word's native form under a map, stated only where the map's rows spell it " +
|
|
254
|
+
"differently. Its derived forms are spelled by the rows.",
|
|
255
|
+
}),
|
|
212
256
|
]);
|
|
213
257
|
|
|
214
258
|
/** The keys of {@link WORD_FIELDS}, in declared order. */
|
|
@@ -9,6 +9,9 @@
|
|
|
9
9
|
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
|
10
10
|
<link href="https://fonts.googleapis.com/css2?family=Cinzel:wght@400;500;600;700&family=JetBrains+Mono:wght@400;500&family=Lora:ital,wght@0,400;0,500;0,600;0,700;1,400;1,500;1,600&display=swap" rel="stylesheet">
|
|
11
11
|
<link rel="stylesheet" href="{{ "css/style.css" | relURL }}">
|
|
12
|
+
{{/* Script fonts: the site build sets params.scriptFonts only when it has
|
|
13
|
+
copied them. */}}
|
|
14
|
+
{{ with .Site.Params.scriptFonts }}<link rel="stylesheet" href="{{ . | relURL }}">{{ end }}
|
|
12
15
|
{{/* Icon glyphs. SoHL documentation writes icons as <i class="fa-solid …">
|
|
13
16
|
or <i class="ginf-…">, the same markup the Foundry client renders, so a
|
|
14
17
|
page reads identically in a journal and here. Font Awesome's FREE set is
|
|
@@ -3022,3 +3022,13 @@ summary.info-sidebar-title::after {
|
|
|
3022
3022
|
.single-body .dictionary > div > dd > :is(p, ul, ol, dl, blockquote, pre, table, div) { text-indent:0; }
|
|
3023
3023
|
.single-body .dictionary > div > dd > p:first-child { display:inline; }
|
|
3024
3024
|
@media (max-width:600px) { .single-body .dictionary { --indent:100px; } }
|
|
3025
|
+
|
|
3026
|
+
/* ---- Text in one of the faces ----
|
|
3027
|
+
The font family and features come from the face's own class. A
|
|
3028
|
+
right-to-left block or verse reads from the right. `font=serif`, `sans`
|
|
3029
|
+
and `mono` set the site's own serif and mono, and the reader's sans. */
|
|
3030
|
+
.script-block { margin:1rem 0; line-height:1.7; }
|
|
3031
|
+
.script-block[dir="rtl"], .poetry[dir="rtl"] { text-align:start; }
|
|
3032
|
+
.font-serif { font-family:var(--font-body); }
|
|
3033
|
+
.font-sans { font-family:sans-serif; }
|
|
3034
|
+
.font-mono { font-family:var(--font-mono); }
|
package/manifest.mjs
CHANGED
|
@@ -54,6 +54,7 @@ import fsSync from "node:fs";
|
|
|
54
54
|
import path from "node:path";
|
|
55
55
|
|
|
56
56
|
import { withBaseStyle } from "./engine/base-styles.mjs";
|
|
57
|
+
import { scriptFontFiles, withScriptFontStyle } from "./engine/script-font-delivery.mjs";
|
|
57
58
|
import { emitDiagnostic, formatDiagnostic, positionOfYamlPath } from "./engine/diagnostics.mjs";
|
|
58
59
|
import { metadataFileName } from "./engine/metadata-index.mjs";
|
|
59
60
|
|
|
@@ -571,11 +572,18 @@ export function buildManifest({ config, packageJson, artifact, flags }) {
|
|
|
571
572
|
// the five that do have no stylesheet of their own to name it from. See
|
|
572
573
|
// `engine/base-styles.mjs` for the layer it loads into and why that is what
|
|
573
574
|
// lets a package override it.
|
|
574
|
-
const
|
|
575
|
+
const withBase = withBaseStyle({
|
|
575
576
|
declared: declared.styles,
|
|
576
577
|
artifact: /** @type {"system"|"module"} */ (artifact),
|
|
577
578
|
enabled: config.packageBuild?.baseStyles !== false,
|
|
578
579
|
});
|
|
580
|
+
// The installed script fonts' stylesheet follows it, when the module
|
|
581
|
+
// carries them: see `engine/script-font-delivery.mjs`.
|
|
582
|
+
const styles = withScriptFontStyle({
|
|
583
|
+
styles: withBase,
|
|
584
|
+
artifact: /** @type {"system"|"module"} */ (artifact),
|
|
585
|
+
delivered: scriptFontFiles(config, ["woff2"]) !== undefined,
|
|
586
|
+
});
|
|
579
587
|
if (styles !== undefined) merged.styles = styles;
|
|
580
588
|
|
|
581
589
|
// The index every consumer resolves this package's addresses through.
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@heroiclands/package-build",
|
|
3
|
-
"version": "23.12.
|
|
3
|
+
"version": "23.12.8",
|
|
4
4
|
"description": "Shared toolchain for building and shipping a HeroicLands Foundry VTT package — content compilation, manifest, localization, staging, bundle, release and deployment.",
|
|
5
5
|
"license": "GPL-3.0-or-later",
|
|
6
6
|
"type": "module",
|
|
@@ -160,7 +160,7 @@
|
|
|
160
160
|
"markdown-it": "^15.0.0",
|
|
161
161
|
"markdown-it-deflist": "^4.0.0",
|
|
162
162
|
"markdown-it-footnote": "^4.0.0",
|
|
163
|
-
"markdownlint": "^0.
|
|
163
|
+
"markdownlint": "^0.42.0",
|
|
164
164
|
"minimatch": "^10.2.6",
|
|
165
165
|
"pagefind": "^1.5.2",
|
|
166
166
|
"prettier": "^3.9.6",
|
|
@@ -703,6 +703,12 @@ export type ContentBuildConfigInput = {
|
|
|
703
703
|
* vocabulary is their union.
|
|
704
704
|
*/
|
|
705
705
|
itemBuilders?: Record<string, ItemBuilderEntry> | readonly ItemRegistrySpec[] | undefined;
|
|
706
|
+
/**
|
|
707
|
+
* The languages a
|
|
708
|
+
* note may tag text with, by short
|
|
709
|
+
* name. Default `{}`.
|
|
710
|
+
*/
|
|
711
|
+
languages?: Record<string, LanguageSpec> | undefined;
|
|
706
712
|
/**
|
|
707
713
|
* Packs to compile. More than one entry
|
|
708
714
|
* may share a `type`: a note then names
|
|
@@ -891,6 +897,10 @@ export type ContentBuildConfig = {
|
|
|
891
897
|
* none.
|
|
892
898
|
*/
|
|
893
899
|
icons: import("./engine/content-icons.mjs").IconRegistry;
|
|
900
|
+
/**
|
|
901
|
+
* Frozen; `{}` when absent.
|
|
902
|
+
*/
|
|
903
|
+
languages: Readonly<Record<string, Readonly<LanguageSpec>>>;
|
|
894
904
|
packs: readonly Readonly<ResolvedPackSpec>[];
|
|
895
905
|
/**
|
|
896
906
|
* Derived: every pack directory
|
|
@@ -918,3 +928,19 @@ export type ContentBuildConfig = {
|
|
|
918
928
|
relationships: Readonly<Relationships>;
|
|
919
929
|
publish: Readonly<PublishSwitches>;
|
|
920
930
|
};
|
|
931
|
+
/**
|
|
932
|
+
* One entry of `languages`.
|
|
933
|
+
*/
|
|
934
|
+
export type LanguageSpec = {
|
|
935
|
+
/**
|
|
936
|
+
* Its BCP 47 tag. A constructed language takes
|
|
937
|
+
* `art-x-<name>`.
|
|
938
|
+
*/
|
|
939
|
+
tag: string;
|
|
940
|
+
/**
|
|
941
|
+
* The Address of its language note, whose
|
|
942
|
+
* `data.words` is the lexicon a mapped run in the
|
|
943
|
+
* language reads first.
|
|
944
|
+
*/
|
|
945
|
+
note?: string | undefined;
|
|
946
|
+
};
|
package/types/e2e.d.mts
CHANGED
|
@@ -419,7 +419,7 @@ export function suiteCommand(config: object, mode: "run" | "open"): string[];
|
|
|
419
419
|
export function e2eRun({ config, packageJson, mode, suiteArgs, env, log, }: {
|
|
420
420
|
config: object;
|
|
421
421
|
packageJson: object;
|
|
422
|
-
mode?: "
|
|
422
|
+
mode?: "run" | "open" | undefined;
|
|
423
423
|
suiteArgs?: string[] | undefined;
|
|
424
424
|
env?: NodeJS.ProcessEnv | undefined;
|
|
425
425
|
log?: ((message: string) => void) | undefined;
|
|
@@ -494,7 +494,7 @@ export const E2E_SCENE_ID: "heroiclandsScene";
|
|
|
494
494
|
/** How the suite may be run. */
|
|
495
495
|
export const E2E_MODES: readonly string[];
|
|
496
496
|
/** The Chrome for Testing build shared by local and CI Cypress runs. */
|
|
497
|
-
export const CHROME_BUILD_ID: "
|
|
497
|
+
export const CHROME_BUILD_ID: "158.0.8110.0";
|
|
498
498
|
/**
|
|
499
499
|
* The disposable world's identity and credentials.
|
|
500
500
|
*/
|
|
@@ -69,7 +69,7 @@ export type AddressPosition = {
|
|
|
69
69
|
* - Where the Addresses are.
|
|
70
70
|
* Defaults to `value`.
|
|
71
71
|
*/
|
|
72
|
-
holds?: "keys" | "
|
|
72
|
+
holds?: "keys" | "items" | "value" | undefined;
|
|
73
73
|
/**
|
|
74
74
|
* - Resolve each exact target to its published Item UUID.
|
|
75
75
|
*/
|
|
@@ -75,7 +75,7 @@ export class AddressLink {
|
|
|
75
75
|
constructor(target: object, anchor: string, kind?: "prose" | "event" | null);
|
|
76
76
|
target: object;
|
|
77
77
|
anchor: string;
|
|
78
|
-
kind: "
|
|
78
|
+
kind: "prose" | "event" | null;
|
|
79
79
|
}
|
|
80
80
|
/** The keys of an Address as the published index writes it, and no others. */
|
|
81
81
|
export const PUBLISHED_ADDRESS_KEYS: readonly string[];
|
|
@@ -110,6 +110,11 @@ export function assetsManifest(staged: readonly object[], stageDir: string): Ass
|
|
|
110
110
|
* stage before a file is copied: a package whose provenance cannot be read is
|
|
111
111
|
* not one whose shipping can be decided.
|
|
112
112
|
*
|
|
113
|
+
* The pictures are written beside whatever a `packageBuild.assets` row already
|
|
114
|
+
* put under `icons/` and `images/`; nothing there is removed. A picture whose
|
|
115
|
+
* deployed path is already a file in the stage is a finding, and no picture is
|
|
116
|
+
* written. Clearing an earlier run's pictures is the stage reset's work.
|
|
117
|
+
*
|
|
113
118
|
* @param {object} opts - Options.
|
|
114
119
|
* @param {string} opts.assetsBase - The package's asset directory, the roots'
|
|
115
120
|
* parent.
|
|
@@ -16,7 +16,7 @@
|
|
|
16
16
|
* the index refuses is a note the compile must still *report*, exactly as the
|
|
17
17
|
* compile loop reported it when the loop was the first to see it.
|
|
18
18
|
* @param {import("./content-session.mjs").ContentSession} [opts.session] - Captured context shared with other operations.
|
|
19
|
-
* @returns {Promise<{currentDate: string, records: object[], parsed: Map<string, object>, linkIndex: object, sqlTables: Map<string, object[]>|undefined, problems: object[], syntax?: import("./content-session.mjs").ContentSyntax}>} The corpus,
|
|
19
|
+
* @returns {Promise<{currentDate: string, runs: import("./content-scripts.mjs").RunContext, records: object[], parsed: Map<string, object>, linkIndex: object, sqlTables: Map<string, object[]>|undefined, problems: object[], syntax?: import("./content-session.mjs").ContentSyntax}>} The corpus,
|
|
20
20
|
* its indexes, and the notes it could not record.
|
|
21
21
|
*/
|
|
22
22
|
export function buildCompileCorpus({ contentBase, assetsBase, skipDirectories, router, config, problems, session, }: {
|
|
@@ -29,6 +29,7 @@ export function buildCompileCorpus({ contentBase, assetsBase, skipDirectories, r
|
|
|
29
29
|
session?: import("./content-session.mjs").ContentSession | undefined;
|
|
30
30
|
}): Promise<{
|
|
31
31
|
currentDate: string;
|
|
32
|
+
runs: import("./content-scripts.mjs").RunContext;
|
|
32
33
|
records: object[];
|
|
33
34
|
parsed: Map<string, object>;
|
|
34
35
|
linkIndex: object;
|
|
@@ -117,7 +117,7 @@ export function checkDeclaredFields({ format, itemFields, system, severity }: {
|
|
|
117
117
|
format: import("./content-format.mjs").ContentFormat;
|
|
118
118
|
itemFields: Record<string, readonly object[]>;
|
|
119
119
|
system: string;
|
|
120
|
-
severity?: "
|
|
120
|
+
severity?: "warning" | "error" | undefined;
|
|
121
121
|
}): {
|
|
122
122
|
findings: object[];
|
|
123
123
|
coverage: object[];
|
|
@@ -81,6 +81,8 @@ export function asciiAliases(aliases: unknown): Array<string>;
|
|
|
81
81
|
* `name` reads `Map 1` rather than `Figure 1` where it is due — see
|
|
82
82
|
* {@link module:engine/content-figures.scanFigures}.
|
|
83
83
|
* @param {import("./content-session.mjs").ContentSyntax} [options.syntax] - Session scanner projections.
|
|
84
|
+
* @param {import("./content-scripts.mjs").RunContext} [options.runContext] -
|
|
85
|
+
* The configured languages, which give each run's `lang=` its tag.
|
|
84
86
|
* @returns {Record<string, any>} The record, keys sorted at every depth. A
|
|
85
87
|
* **stub** — a note with an empty body, on a type an empty body suppresses —
|
|
86
88
|
* carries `address` and `anchors` as `null`: it publishes no page, so it
|
|
@@ -92,7 +94,7 @@ export function asciiAliases(aliases: unknown): Array<string>;
|
|
|
92
94
|
* otherwise be overwritten without a word. `file` and, where the file was
|
|
93
95
|
* read, `position` ride on the error.
|
|
94
96
|
*/
|
|
95
|
-
export function buildIndexRecord({ frontmatter, relPath, absPath, raw, contentPackage, body, bodyLine, bodyColumn, nameTypes, manifest, addressContext, dateContext, resolveRole, syntax, }: {
|
|
97
|
+
export function buildIndexRecord({ frontmatter, relPath, absPath, raw, contentPackage, body, bodyLine, bodyColumn, nameTypes, manifest, addressContext, dateContext, resolveRole, syntax, runContext, }: {
|
|
96
98
|
frontmatter: Record<string, any>;
|
|
97
99
|
relPath: string;
|
|
98
100
|
absPath?: string | undefined;
|
|
@@ -107,12 +109,13 @@ export function buildIndexRecord({ frontmatter, relPath, absPath, raw, contentPa
|
|
|
107
109
|
dateContext?: object | undefined;
|
|
108
110
|
resolveRole?: ((address: string) => string | undefined) | undefined;
|
|
109
111
|
syntax?: import("./content-session.mjs").ContentSyntax | undefined;
|
|
112
|
+
runContext?: import("./content-scripts.mjs").RunContext | undefined;
|
|
110
113
|
}): Record<string, any>;
|
|
111
114
|
/**
|
|
112
115
|
* Derive every index record belonging to one parsed note.
|
|
113
116
|
* @param {Parameters<typeof buildIndexRecord>[0]} options - Authored note and its context.
|
|
114
117
|
*/
|
|
115
|
-
export function indexRecordsForNote({ frontmatter, body, bodyLine, bodyColumn, nameTypes, relPath, absPath, raw, contentPackage, manifest, addressContext, dateContext, resolveRole, syntax, }: Parameters<typeof buildIndexRecord>[0]): object[];
|
|
118
|
+
export function indexRecordsForNote({ frontmatter, body, bodyLine, bodyColumn, nameTypes, relPath, absPath, raw, contentPackage, manifest, addressContext, dateContext, resolveRole, syntax, runContext, }: Parameters<typeof buildIndexRecord>[0]): object[];
|
|
116
119
|
/**
|
|
117
120
|
* Write each note's resolved culture into its record, as `data.culture`.
|
|
118
121
|
*
|
|
@@ -209,6 +212,8 @@ export function resolveCultures(records: Array<Record<string, any>>, { contentPa
|
|
|
209
212
|
* calendar note's shortcode; see {@link module:engine/note-calendars}.
|
|
210
213
|
* @param {string} [options.configFile] - The configuration file, where an
|
|
211
214
|
* unknown `defaultCalendar` is reported.
|
|
215
|
+
* @param {Readonly<Record<string, {tag: string}>>} [options.languages] - The
|
|
216
|
+
* configured languages, which give each run's `lang=` its tag.
|
|
212
217
|
* @param {(key: string) => ({culture?: unknown}|undefined)} [options.foreignRecord] -
|
|
213
218
|
* Another package's entry for a canonical address, read for a parent that
|
|
214
219
|
* package publishes; see {@link resolveCultures}.
|
|
@@ -221,7 +226,7 @@ export function resolveCultures(records: Array<Record<string, any>>, { contentPa
|
|
|
221
226
|
* @returns {Array<Record<string, any>>} The records, in a total order that does
|
|
222
227
|
* not depend on directory-read order.
|
|
223
228
|
*/
|
|
224
|
-
export function collectContentIndex(contentBase: string, { contentPackage, currentDate, defaultCalendar, configFile, skipDirectories, assetsBase, manifest, problems, addressContext, foreignRecord, parsed, sources, syntax, nameTypes, }: {
|
|
229
|
+
export function collectContentIndex(contentBase: string, { contentPackage, currentDate, defaultCalendar, configFile, languages, skipDirectories, assetsBase, manifest, problems, addressContext, foreignRecord, parsed, sources, syntax, nameTypes, }: {
|
|
225
230
|
contentPackage: string;
|
|
226
231
|
skipDirectories: readonly string[];
|
|
227
232
|
assetsBase?: string | undefined;
|
|
@@ -231,6 +236,9 @@ export function collectContentIndex(contentBase: string, { contentPackage, curre
|
|
|
231
236
|
currentDate?: string | undefined;
|
|
232
237
|
defaultCalendar?: string | undefined;
|
|
233
238
|
configFile?: string | undefined;
|
|
239
|
+
languages?: Readonly<Record<string, {
|
|
240
|
+
tag: string;
|
|
241
|
+
}>> | undefined;
|
|
234
242
|
foreignRecord?: ((key: string) => ({
|
|
235
243
|
culture?: unknown;
|
|
236
244
|
} | undefined)) | undefined;
|
|
@@ -49,3 +49,10 @@ export function renderPoetry(source: string): {
|
|
|
49
49
|
message: string;
|
|
50
50
|
}[];
|
|
51
51
|
};
|
|
52
|
+
/**
|
|
53
|
+
* The keys a poetry fence's attribute block takes. `lang`, `font` and `map`
|
|
54
|
+
* are read by `scanRuns` in content-scripts.mjs; `dir`, and on the site
|
|
55
|
+
* `data-pagefind-ignore`, are written by its rewrite of a fence set in one of
|
|
56
|
+
* the faces, and reach the element as they are written.
|
|
57
|
+
*/
|
|
58
|
+
export const POETRY_KEYS: readonly string[];
|