@pretextbook/pretext-html 0.3.0 → 0.4.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 +20 -9
- package/assets/preview-html.xsl +8 -4
- package/assets/upstream.json +1 -1
- package/assets/xsl/README.md +25 -24
- package/assets/xsl/entities.ent +20 -0
- package/assets/xsl/extract-biblio-csl.xsl +1 -1
- package/assets/xsl/extract-pg.xsl +111 -297
- package/assets/xsl/extract-qrcode.xsl +11 -1
- package/assets/xsl/extract-sageplot.xsl +1 -1
- package/assets/xsl/latex/pretext-latex-texstyle.xsl +1 -2
- package/assets/xsl/localizations/README.md +24 -24
- package/assets/xsl/pretext-assembly.xsl +101 -11
- package/assets/xsl/pretext-beamer.xsl +43 -146
- package/assets/xsl/pretext-braille-preprint.xsl +457 -201
- package/assets/xsl/pretext-common.xsl +388 -423
- package/assets/xsl/pretext-epub.xsl +301 -72
- package/assets/xsl/pretext-fo.xsl +70 -86
- package/assets/xsl/pretext-html.xsl +331 -259
- package/assets/xsl/pretext-jupyter.xsl +534 -322
- package/assets/xsl/pretext-latex-classic.xsl +14 -15
- package/assets/xsl/pretext-latex-common.xsl +385 -2389
- package/assets/xsl/pretext-latex.xsl +1995 -5
- package/assets/xsl/pretext-markdown.xsl +919 -0
- package/assets/xsl/pretext-numbers.xsl +22 -4
- package/assets/xsl/pretext-revealjs.xsl +241 -33
- package/assets/xsl/pretext-runestone-fitb.xsl +20 -22
- package/assets/xsl/pretext-runestone.xsl +3 -3
- package/assets/xsl/pretext-sage-doctest.xsl +2 -2
- package/assets/xsl/pretext-text-utilities.xsl +69 -1
- package/assets/xsl/pretext-text.xsl +1077 -107
- package/assets/xsl/publisher-variables.xsl +396 -452
- package/assets/xsl/support/play-button/README.md +1 -3
- package/assets/xsl/tests/README.md +1 -1
- package/assets/xsl/utilities/README.md +6 -8
- package/assets/xsl/utilities/report-publisher-variables.xsl +15 -0
- package/assets/xsl-bundle.json +1 -1
- package/dist/{cli-CzoinNle.js → cli-Cp6C0sif.js} +220 -205
- package/dist/cli.js +1 -1
- package/dist/index.browser.js +351 -342
- package/dist/index.js +1 -1
- package/dist/publication.d.ts +9 -1
- package/dist/renderer.d.ts +20 -0
- package/package.json +1 -1
|
@@ -1,48 +1,48 @@
|
|
|
1
|
-
import { readFile as
|
|
1
|
+
import { readFile as j, writeFile as _ } from "node:fs/promises";
|
|
2
2
|
import * as w from "node:process";
|
|
3
|
-
import * as
|
|
3
|
+
import * as c from "node:path";
|
|
4
4
|
import { fileURLToPath as fe } from "node:url";
|
|
5
5
|
import { fromXml as v } from "xast-util-from-xml";
|
|
6
|
-
import { toXml as
|
|
6
|
+
import { toXml as T } from "xast-util-to-xml";
|
|
7
7
|
import { injectThemeBridge as he } from "./theme.js";
|
|
8
|
-
async function
|
|
9
|
-
const t =
|
|
10
|
-
if (n !== t && !n.startsWith(t +
|
|
8
|
+
async function Z(e, r) {
|
|
9
|
+
const t = c.resolve(e), n = c.resolve(t, `.${c.posix.normalize(r)}`);
|
|
10
|
+
if (n !== t && !n.startsWith(t + c.sep)) {
|
|
11
11
|
console.error(
|
|
12
12
|
`pretext-html: refusing to serve ${r} from outside ${t}`
|
|
13
13
|
);
|
|
14
14
|
return;
|
|
15
15
|
}
|
|
16
16
|
try {
|
|
17
|
-
return new Uint8Array(await
|
|
17
|
+
return new Uint8Array(await j(n));
|
|
18
18
|
} catch {
|
|
19
19
|
return;
|
|
20
20
|
}
|
|
21
21
|
}
|
|
22
|
-
async function
|
|
22
|
+
async function F(e) {
|
|
23
23
|
try {
|
|
24
|
-
return await
|
|
24
|
+
return await j(e, "utf8");
|
|
25
25
|
} catch {
|
|
26
26
|
return;
|
|
27
27
|
}
|
|
28
28
|
}
|
|
29
|
-
let
|
|
30
|
-
function
|
|
31
|
-
|
|
29
|
+
let K;
|
|
30
|
+
function Qe(e) {
|
|
31
|
+
K = e;
|
|
32
32
|
}
|
|
33
33
|
function I() {
|
|
34
|
-
return
|
|
34
|
+
return K ?? process.env.PRETEXT_HTML_ASSETS ?? c.resolve(c.dirname(fe(import.meta.url)), "..", "assets");
|
|
35
35
|
}
|
|
36
36
|
function me(e, r) {
|
|
37
|
-
return
|
|
37
|
+
return c.join(e, r);
|
|
38
38
|
}
|
|
39
|
-
const
|
|
40
|
-
let M, pe = 0,
|
|
41
|
-
function
|
|
42
|
-
|
|
39
|
+
const L = /* @__PURE__ */ new Map(), ee = /* @__PURE__ */ new Map();
|
|
40
|
+
let M, pe = 0, te = Z;
|
|
41
|
+
function Ve(e) {
|
|
42
|
+
te = e;
|
|
43
43
|
}
|
|
44
44
|
function we(e, r) {
|
|
45
|
-
const t = typeof e == "string" ? e : e instanceof URL ? e.href : e.url, n =
|
|
45
|
+
const t = typeof e == "string" ? e : e instanceof URL ? e.href : e.url, n = ee.get(t);
|
|
46
46
|
if (n !== void 0)
|
|
47
47
|
return Promise.resolve(new Response(n, { status: 200 }));
|
|
48
48
|
let o;
|
|
@@ -51,32 +51,32 @@ function we(e, r) {
|
|
|
51
51
|
} catch {
|
|
52
52
|
o = "";
|
|
53
53
|
}
|
|
54
|
-
const i =
|
|
54
|
+
const i = L.get(o);
|
|
55
55
|
return i !== void 0 ? ge(i, t) : M(e, r);
|
|
56
56
|
}
|
|
57
57
|
const be = '<?xml version="1.0"?><pretext-preview-missing-file/>';
|
|
58
58
|
async function ge(e, r) {
|
|
59
|
-
const t = decodeURIComponent(new URL(r).pathname), n = await
|
|
59
|
+
const t = decodeURIComponent(new URL(r).pathname), n = await te(e, t);
|
|
60
60
|
if (n === void 0)
|
|
61
61
|
return new Response(be, { status: 200 });
|
|
62
62
|
const o = typeof n == "string" ? n : new Uint8Array(n);
|
|
63
63
|
return new Response(o, { status: 200 });
|
|
64
64
|
}
|
|
65
|
-
function
|
|
65
|
+
function re() {
|
|
66
66
|
M || (M = globalThis.fetch, globalThis.fetch = we);
|
|
67
67
|
}
|
|
68
|
-
function
|
|
69
|
-
|
|
68
|
+
function ne(e) {
|
|
69
|
+
re();
|
|
70
70
|
const r = `mnt${++pe}.ptx.invalid`;
|
|
71
|
-
return
|
|
71
|
+
return L.set(r, e), `http://${r}`;
|
|
72
72
|
}
|
|
73
73
|
function ye(e) {
|
|
74
|
-
|
|
74
|
+
L.delete(new URL(e).host);
|
|
75
75
|
}
|
|
76
76
|
function xe(e, r) {
|
|
77
|
-
|
|
77
|
+
re(), ee.set(e, r);
|
|
78
78
|
}
|
|
79
|
-
const
|
|
79
|
+
const A = `<?xml version="1.0" encoding="UTF-8"?>
|
|
80
80
|
<publication>
|
|
81
81
|
<source>
|
|
82
82
|
<directories external="../assets" generated="../generated-assets" />
|
|
@@ -85,67 +85,75 @@ const ne = `<?xml version="1.0" encoding="UTF-8"?>
|
|
|
85
85
|
<platform portable="yes"/>
|
|
86
86
|
</html>
|
|
87
87
|
</publication>
|
|
88
|
-
|
|
89
|
-
function
|
|
88
|
+
`, ve = ["theme", "style", "shell"];
|
|
89
|
+
function b(e, r) {
|
|
90
90
|
for (const t of e.children)
|
|
91
91
|
if (t.type === "element" && t.name === r)
|
|
92
92
|
return t;
|
|
93
93
|
}
|
|
94
|
-
function
|
|
95
|
-
let t =
|
|
94
|
+
function X(e, r) {
|
|
95
|
+
let t = b(e, r);
|
|
96
96
|
return t || (t = { type: "element", name: r, attributes: {}, children: [] }, e.children.push(t)), t;
|
|
97
97
|
}
|
|
98
|
-
function
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
98
|
+
function Ee(e, r) {
|
|
99
|
+
const t = b(e, "css");
|
|
100
|
+
if (t && ve.some((o) => t.attributes?.[o]))
|
|
101
|
+
return;
|
|
102
|
+
const n = t ?? X(e, "css");
|
|
103
|
+
n.attributes = { ...n.attributes, theme: r };
|
|
104
|
+
}
|
|
105
|
+
function Te(e, r) {
|
|
106
|
+
const t = r?.trim();
|
|
107
|
+
if (!e && !t)
|
|
108
|
+
return A;
|
|
109
|
+
const n = v(e ?? A), o = b(n, "publication");
|
|
110
|
+
if (!o)
|
|
103
111
|
throw new Error(
|
|
104
112
|
"Invalid publication file: no root <publication> element found"
|
|
105
113
|
);
|
|
106
|
-
const
|
|
107
|
-
return
|
|
114
|
+
const i = X(o, "html"), a = X(i, "platform");
|
|
115
|
+
return a.attributes = { ...a.attributes, portable: "yes" }, t && Ee(i, t), T(n);
|
|
108
116
|
}
|
|
109
|
-
function
|
|
117
|
+
function H(e) {
|
|
110
118
|
if (!(e === void 0 || e === "" || e.startsWith("/")))
|
|
111
119
|
return e.endsWith("/") ? e : `${e}/`;
|
|
112
120
|
}
|
|
113
|
-
function
|
|
114
|
-
const r = v(e ??
|
|
121
|
+
function $e(e) {
|
|
122
|
+
const r = v(e ?? A), t = b(r, "publication"), n = t && b(t, "source"), o = n && b(n, "directories"), i = H(
|
|
115
123
|
o?.attributes?.external ?? void 0
|
|
116
|
-
),
|
|
124
|
+
), a = H(
|
|
117
125
|
o?.attributes?.generated ?? void 0
|
|
118
126
|
);
|
|
119
127
|
return {
|
|
120
128
|
external: i,
|
|
121
|
-
generated:
|
|
122
|
-
managed: i !== void 0 &&
|
|
129
|
+
generated: a,
|
|
130
|
+
managed: i !== void 0 && a !== void 0
|
|
123
131
|
};
|
|
124
132
|
}
|
|
125
|
-
const oe = "http://www.w3.org/2001/XInclude",
|
|
126
|
-
async function
|
|
133
|
+
const oe = "http://www.w3.org/2001/XInclude", N = 64;
|
|
134
|
+
async function Pe(e, r, t) {
|
|
127
135
|
return e.includes("include") ? (await ie(e, r, t)).content : e;
|
|
128
136
|
}
|
|
129
137
|
async function ie(e, r, t) {
|
|
130
138
|
const n = v(e), o = {
|
|
131
|
-
projectDir:
|
|
132
|
-
stack: [
|
|
139
|
+
projectDir: c.resolve(t),
|
|
140
|
+
stack: [c.resolve(r)]
|
|
133
141
|
}, i = await x(
|
|
134
142
|
n,
|
|
135
|
-
|
|
143
|
+
c.dirname(c.resolve(r)),
|
|
136
144
|
{ "": "" },
|
|
137
145
|
o
|
|
138
146
|
);
|
|
139
|
-
return { tree: n, content: i ?
|
|
147
|
+
return { tree: n, content: i ? T(n) : e };
|
|
140
148
|
}
|
|
141
|
-
function
|
|
149
|
+
function ke(e) {
|
|
142
150
|
return e.data?.ptxIncludedFile;
|
|
143
151
|
}
|
|
144
|
-
function
|
|
152
|
+
function Se(e, r) {
|
|
145
153
|
const t = e.data ?? (e.data = {});
|
|
146
154
|
t.ptxIncludedFile = r;
|
|
147
155
|
}
|
|
148
|
-
function
|
|
156
|
+
function $(e, r) {
|
|
149
157
|
let t = e;
|
|
150
158
|
for (const [n, o] of Object.entries(r.attributes))
|
|
151
159
|
(n === "xmlns" || n.startsWith("xmlns:")) && (t === e && (t = { ...e }), t[n === "xmlns" ? "" : n.slice(6)] = o ?? "");
|
|
@@ -158,19 +166,19 @@ function se(e, r) {
|
|
|
158
166
|
async function x(e, r, t, n) {
|
|
159
167
|
let o = !1;
|
|
160
168
|
for (let i = 0; i < e.children.length; i++) {
|
|
161
|
-
const
|
|
162
|
-
if (
|
|
169
|
+
const a = e.children[i];
|
|
170
|
+
if (a.type !== "element")
|
|
163
171
|
continue;
|
|
164
|
-
const s =
|
|
165
|
-
if (se(
|
|
172
|
+
const s = $(t, a);
|
|
173
|
+
if (se(a, s)) {
|
|
166
174
|
const u = await ae(
|
|
167
|
-
|
|
175
|
+
a,
|
|
168
176
|
r,
|
|
169
177
|
s,
|
|
170
178
|
n
|
|
171
179
|
);
|
|
172
180
|
e.children.splice(i, 1, ...u), i += u.length - 1, o = !0;
|
|
173
|
-
} else await x(
|
|
181
|
+
} else await x(a, r, s, n) && (o = !0);
|
|
174
182
|
}
|
|
175
183
|
return o;
|
|
176
184
|
}
|
|
@@ -183,13 +191,13 @@ async function ae(e, r, t, n) {
|
|
|
183
191
|
const i = e.attributes.href;
|
|
184
192
|
if (!i)
|
|
185
193
|
throw new Error(`xi:include without href (in ${o})`);
|
|
186
|
-
let
|
|
194
|
+
let a = i;
|
|
187
195
|
try {
|
|
188
|
-
|
|
196
|
+
a = decodeURIComponent(i);
|
|
189
197
|
} catch {
|
|
190
198
|
}
|
|
191
|
-
const s =
|
|
192
|
-
if (s !== n.projectDir && !s.startsWith(n.projectDir +
|
|
199
|
+
const s = c.resolve(r, a);
|
|
200
|
+
if (s !== n.projectDir && !s.startsWith(n.projectDir + c.sep))
|
|
193
201
|
throw new Error(
|
|
194
202
|
`xi:include escapes the project directory: ${i} (in ${o})`
|
|
195
203
|
);
|
|
@@ -197,13 +205,13 @@ async function ae(e, r, t, n) {
|
|
|
197
205
|
throw new Error(
|
|
198
206
|
`Circular xi:include: ${[...n.stack, s].join(" -> ")}`
|
|
199
207
|
);
|
|
200
|
-
if (n.stack.length >=
|
|
201
|
-
throw new Error(`xi:include nesting exceeds ${
|
|
202
|
-
const u = await
|
|
208
|
+
if (n.stack.length >= N)
|
|
209
|
+
throw new Error(`xi:include nesting exceeds ${N} levels`);
|
|
210
|
+
const u = await F(s);
|
|
203
211
|
if (u === void 0) {
|
|
204
|
-
const
|
|
205
|
-
if (
|
|
206
|
-
return await x(
|
|
212
|
+
const d = Ie(e, t);
|
|
213
|
+
if (d)
|
|
214
|
+
return await x(d, r, t, n), d.children;
|
|
207
215
|
throw new Error(`xi:include target not found: ${i} (in ${o})`);
|
|
208
216
|
}
|
|
209
217
|
if (e.attributes.parse === "text")
|
|
@@ -211,55 +219,55 @@ async function ae(e, r, t, n) {
|
|
|
211
219
|
let l;
|
|
212
220
|
try {
|
|
213
221
|
l = v(u);
|
|
214
|
-
} catch (
|
|
222
|
+
} catch (d) {
|
|
215
223
|
throw new Error(
|
|
216
|
-
`Could not parse xi:include target ${s} as XML: ${
|
|
224
|
+
`Could not parse xi:include target ${s} as XML: ${d instanceof Error ? d.message : d}. (Included files must be well-formed, with a single root element.)`
|
|
217
225
|
);
|
|
218
226
|
}
|
|
219
227
|
n.stack.push(s);
|
|
220
228
|
try {
|
|
221
|
-
await x(l,
|
|
229
|
+
await x(l, c.dirname(s), { "": "" }, n);
|
|
222
230
|
} finally {
|
|
223
231
|
n.stack.pop();
|
|
224
232
|
}
|
|
225
|
-
const
|
|
226
|
-
(
|
|
233
|
+
const f = l.children.filter(
|
|
234
|
+
(d) => d.type === "element"
|
|
227
235
|
);
|
|
228
|
-
for (const
|
|
229
|
-
|
|
230
|
-
return
|
|
236
|
+
for (const d of f)
|
|
237
|
+
Se(d, s);
|
|
238
|
+
return f;
|
|
231
239
|
}
|
|
232
|
-
function
|
|
240
|
+
function J(e) {
|
|
233
241
|
return e.name === "docinfo";
|
|
234
242
|
}
|
|
235
|
-
async function
|
|
243
|
+
async function De(e, r, t) {
|
|
236
244
|
try {
|
|
237
245
|
const o = v(e).children.find(
|
|
238
246
|
(l) => l.type === "element"
|
|
239
247
|
);
|
|
240
248
|
if (!o)
|
|
241
249
|
return;
|
|
242
|
-
const i =
|
|
243
|
-
projectDir:
|
|
250
|
+
const i = c.resolve(r), a = c.dirname(i), s = {
|
|
251
|
+
projectDir: c.resolve(t),
|
|
244
252
|
stack: [i]
|
|
245
|
-
}, u =
|
|
253
|
+
}, u = $({ "": "" }, o);
|
|
246
254
|
for (const l of o.children) {
|
|
247
255
|
if (l.type !== "element")
|
|
248
256
|
continue;
|
|
249
|
-
const
|
|
250
|
-
if (
|
|
251
|
-
return await x(l,
|
|
252
|
-
if (se(l,
|
|
253
|
-
const
|
|
257
|
+
const f = $(u, l);
|
|
258
|
+
if (J(l))
|
|
259
|
+
return await x(l, a, f, s), T(l);
|
|
260
|
+
if (se(l, f)) {
|
|
261
|
+
const g = (await ae(
|
|
254
262
|
l,
|
|
255
|
-
|
|
256
|
-
|
|
263
|
+
a,
|
|
264
|
+
f,
|
|
257
265
|
s
|
|
258
266
|
)).find(
|
|
259
|
-
(
|
|
267
|
+
(m) => m.type === "element" && J(m)
|
|
260
268
|
);
|
|
261
|
-
if (
|
|
262
|
-
return
|
|
269
|
+
if (g)
|
|
270
|
+
return T(g);
|
|
263
271
|
continue;
|
|
264
272
|
}
|
|
265
273
|
break;
|
|
@@ -269,11 +277,11 @@ async function Te(e, r, t) {
|
|
|
269
277
|
return;
|
|
270
278
|
}
|
|
271
279
|
}
|
|
272
|
-
function
|
|
280
|
+
function Ie(e, r) {
|
|
273
281
|
for (const t of e.children) {
|
|
274
282
|
if (t.type !== "element")
|
|
275
283
|
continue;
|
|
276
|
-
const n =
|
|
284
|
+
const n = $(r, t), o = t.name.indexOf(":"), i = o === -1 ? "" : t.name.slice(0, o);
|
|
277
285
|
if ((o === -1 ? t.name : t.name.slice(o + 1)) === "fallback" && n[i] === oe)
|
|
278
286
|
return t;
|
|
279
287
|
}
|
|
@@ -281,10 +289,10 @@ function ke(e, r) {
|
|
|
281
289
|
function ce(e) {
|
|
282
290
|
return typeof e == "object" && e !== null && e.type === "element";
|
|
283
291
|
}
|
|
284
|
-
function
|
|
292
|
+
function Me(e) {
|
|
285
293
|
return /^(pf|xhtml):/.test(e.name);
|
|
286
294
|
}
|
|
287
|
-
function
|
|
295
|
+
function Ae(e, r, t) {
|
|
288
296
|
const n = [], o = e.children.find(ce);
|
|
289
297
|
if (o) {
|
|
290
298
|
const i = t?.parentId ?? "root";
|
|
@@ -293,15 +301,15 @@ function De(e, r, t) {
|
|
|
293
301
|
return n;
|
|
294
302
|
}
|
|
295
303
|
function le(e, r, t, n, o, i) {
|
|
296
|
-
const
|
|
304
|
+
const a = ke(e) ?? n;
|
|
297
305
|
let s, u;
|
|
298
|
-
if (
|
|
306
|
+
if (Me(e))
|
|
299
307
|
u = "root";
|
|
300
308
|
else {
|
|
301
|
-
const
|
|
302
|
-
s =
|
|
309
|
+
const f = e.attributes.label ?? e.attributes["xml:id"];
|
|
310
|
+
s = f ?? `${r}-${t}`, i.push({
|
|
303
311
|
id: s,
|
|
304
|
-
file:
|
|
312
|
+
file: a,
|
|
305
313
|
line: e.position?.start.line ?? 1,
|
|
306
314
|
column: e.position?.start.column ?? 1,
|
|
307
315
|
endLine: e.position?.end.line ?? e.position?.start.line ?? 1,
|
|
@@ -309,60 +317,60 @@ function le(e, r, t, n, o, i) {
|
|
|
309
317
|
}), u = s;
|
|
310
318
|
}
|
|
311
319
|
let l = 0;
|
|
312
|
-
for (const
|
|
313
|
-
ce(
|
|
314
|
-
|
|
320
|
+
for (const f of e.children)
|
|
321
|
+
ce(f) && (l += 1, le(
|
|
322
|
+
f,
|
|
315
323
|
u,
|
|
316
324
|
l,
|
|
317
|
-
|
|
325
|
+
a,
|
|
318
326
|
s ?? o,
|
|
319
327
|
i
|
|
320
328
|
));
|
|
321
329
|
}
|
|
322
|
-
function
|
|
330
|
+
function Ze(e, r) {
|
|
323
331
|
let t;
|
|
324
332
|
for (const n of e)
|
|
325
333
|
n.line <= r && (t = n);
|
|
326
334
|
return t ?? e[0];
|
|
327
335
|
}
|
|
328
|
-
function
|
|
336
|
+
function Xe() {
|
|
329
337
|
return me(I(), "xsl");
|
|
330
338
|
}
|
|
331
|
-
function
|
|
339
|
+
function je() {
|
|
332
340
|
return "Suspending" in WebAssembly;
|
|
333
341
|
}
|
|
334
|
-
function
|
|
335
|
-
if (!
|
|
342
|
+
function Fe() {
|
|
343
|
+
if (!je())
|
|
336
344
|
throw new Error(
|
|
337
345
|
"WebAssembly JSPI is not enabled. Run Node with --experimental-wasm-jspi (or use the pretext-html CLI, which re-launches itself with the flag)."
|
|
338
346
|
);
|
|
339
347
|
}
|
|
340
|
-
function
|
|
348
|
+
function z(e) {
|
|
341
349
|
return e.includes("'") ? e.includes('"') ? `concat(${e.split("'").map((t) => `'${t}'`).join(`, "'", `)})` : `"${e}"` : `'${e}'`;
|
|
342
350
|
}
|
|
343
|
-
function
|
|
351
|
+
function Le(e) {
|
|
344
352
|
return e.replace(
|
|
345
353
|
/from '\.\/(https:\/\/[^']+)'/g,
|
|
346
354
|
(r, t) => `from '${t}'`
|
|
347
355
|
);
|
|
348
356
|
}
|
|
349
|
-
function
|
|
357
|
+
function Re(e) {
|
|
350
358
|
return e.slice(0, 65536).replace(/<\?[\s\S]*?\?>/g, " ").replace(/<!--[\s\S]*?-->/g, " ").replace(/<!DOCTYPE[^>]*>/gi, " ").match(/<\s*([A-Za-z][\w:-]*)/)?.[1];
|
|
351
359
|
}
|
|
352
|
-
async function
|
|
353
|
-
const r = await
|
|
360
|
+
async function q(e) {
|
|
361
|
+
const r = await F(e);
|
|
354
362
|
if (r === void 0)
|
|
355
363
|
throw new Error(
|
|
356
364
|
`Could not read ${e}. (In the browser build only absolute URLs are readable — pass sourceContent instead of relying on sourcePath.)`
|
|
357
365
|
);
|
|
358
366
|
return r;
|
|
359
367
|
}
|
|
360
|
-
async function
|
|
361
|
-
const t =
|
|
368
|
+
async function Ue(e, r) {
|
|
369
|
+
const t = c.resolve(e), n = await F(t);
|
|
362
370
|
if (n !== void 0)
|
|
363
|
-
return
|
|
371
|
+
return De(n, t, r);
|
|
364
372
|
}
|
|
365
|
-
function
|
|
373
|
+
function Ce(e, r, t) {
|
|
366
374
|
const n = e.replace(/^\uFEFF/, "").replace(/<\?xml[\s\S]*?\?>/, "").replace(/<!DOCTYPE[^>]*>/i, ""), o = r === "chapter" || r === "part" ? "book" : "article";
|
|
367
375
|
return `<pretext>
|
|
368
376
|
${t?.trim() ? `${t.trim()}
|
|
@@ -374,25 +382,25 @@ ${n}
|
|
|
374
382
|
`;
|
|
375
383
|
}
|
|
376
384
|
let ue = !1;
|
|
377
|
-
function
|
|
385
|
+
function We(e) {
|
|
378
386
|
return e instanceof Error && /\bAborted\(/.test(e.message);
|
|
379
387
|
}
|
|
380
|
-
function
|
|
388
|
+
function Be(e) {
|
|
381
389
|
return e instanceof Error && /memory access|out of bounds/i.test(e.message);
|
|
382
390
|
}
|
|
383
|
-
function
|
|
391
|
+
function Oe() {
|
|
384
392
|
if (ue)
|
|
385
393
|
throw new Error(
|
|
386
394
|
"The WebAssembly renderer aborted earlier in this process and cannot be reused. Restart the process (or reload the page) to render again."
|
|
387
395
|
);
|
|
388
396
|
}
|
|
389
|
-
function
|
|
390
|
-
if (
|
|
397
|
+
function G(e) {
|
|
398
|
+
if (We(e))
|
|
391
399
|
throw ue = !0, new Error(
|
|
392
400
|
"The WebAssembly renderer aborted and cannot be reused. Restart the process (or reload the page) to render again.",
|
|
393
401
|
{ cause: e }
|
|
394
402
|
);
|
|
395
|
-
if (
|
|
403
|
+
if (Be(e))
|
|
396
404
|
throw new Error(
|
|
397
405
|
"The WebAssembly renderer hit a memory fault. Most often the document is too large for this build's stack — whole-book builds are a known limitation, so try a smaller document, or see the README about rebuilding libxslt-wasm with a larger stack. The same fault also results from running two renders concurrently against the shared libxslt state.",
|
|
398
406
|
{ cause: e }
|
|
@@ -409,115 +417,116 @@ async function de() {
|
|
|
409
417
|
})()), S;
|
|
410
418
|
}
|
|
411
419
|
const D = /* @__PURE__ */ new Map();
|
|
412
|
-
async function
|
|
420
|
+
async function _e(e) {
|
|
413
421
|
const r = e;
|
|
414
422
|
let t = D.get(r);
|
|
415
423
|
return t || (t = (async () => {
|
|
416
|
-
const { XmlDocument: n, XsltStylesheet: o } = await de(), i =
|
|
424
|
+
const { XmlDocument: n, XsltStylesheet: o } = await de(), i = ne(r), a = await Z(
|
|
417
425
|
I(),
|
|
418
426
|
"/preview-html.xsl"
|
|
419
427
|
);
|
|
420
|
-
if (
|
|
428
|
+
if (a === void 0)
|
|
421
429
|
throw new Error(
|
|
422
430
|
`Could not read preview-html.xsl from ${I()}. Check the assets location (PRETEXT_HTML_ASSETS under Node, setAssetsBase() in the browser).`
|
|
423
431
|
);
|
|
424
|
-
const s = new TextDecoder().decode(
|
|
432
|
+
const s = new TextDecoder().decode(a), u = await n.fromString(s, {
|
|
425
433
|
url: `${i}/preview-html.xsl`,
|
|
426
434
|
options: { noEnt: !0, dtdLoad: !0, huge: !0 }
|
|
427
435
|
});
|
|
428
436
|
return o.fromXmlDocument(u);
|
|
429
437
|
})(), D.set(r, t), t.catch(() => D.delete(r))), t;
|
|
430
438
|
}
|
|
431
|
-
let
|
|
432
|
-
function
|
|
433
|
-
const r =
|
|
434
|
-
() =>
|
|
435
|
-
() =>
|
|
439
|
+
let Y = Promise.resolve();
|
|
440
|
+
function He(e) {
|
|
441
|
+
const r = Y.then(
|
|
442
|
+
() => Q(e),
|
|
443
|
+
() => Q(e)
|
|
436
444
|
);
|
|
437
|
-
return
|
|
445
|
+
return Y = r.catch(() => {
|
|
438
446
|
}), r;
|
|
439
447
|
}
|
|
440
|
-
async function
|
|
441
|
-
|
|
442
|
-
const { XmlDocument: r } = await de(), t = await
|
|
443
|
-
e.projectDir ??
|
|
444
|
-
), i = e.sourceContent ?? await
|
|
445
|
-
if (
|
|
448
|
+
async function Q(e) {
|
|
449
|
+
Fe(), Oe();
|
|
450
|
+
const { XmlDocument: r } = await de(), t = await _e(e.xslDir ?? Xe()), n = c.resolve(e.sourcePath), o = c.resolve(
|
|
451
|
+
e.projectDir ?? c.dirname(n)
|
|
452
|
+
), i = e.sourceContent ?? await q(n), a = c.relative(o, n);
|
|
453
|
+
if (a.startsWith(".."))
|
|
446
454
|
throw new Error(
|
|
447
455
|
`sourcePath (${n}) must live inside projectDir (${o})`
|
|
448
456
|
);
|
|
449
|
-
const s =
|
|
457
|
+
const s = c.relative(
|
|
450
458
|
o,
|
|
451
|
-
|
|
452
|
-
), u = s.startsWith("..") ?
|
|
459
|
+
c.resolve(e.mainSourcePath ?? n)
|
|
460
|
+
), u = s.startsWith("..") ? a : s, l = ne(o);
|
|
453
461
|
try {
|
|
454
|
-
let
|
|
462
|
+
let f, d = `${l}/__pretext-preview-publication.xml`;
|
|
455
463
|
if (e.publicationPath) {
|
|
456
|
-
const h =
|
|
457
|
-
|
|
458
|
-
|
|
459
|
-
);
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
|
|
466
|
-
|
|
467
|
-
|
|
464
|
+
const h = c.resolve(e.publicationPath);
|
|
465
|
+
f = await q(h);
|
|
466
|
+
const y = c.relative(o, h);
|
|
467
|
+
y.startsWith("..") || (d = `${l}/${y.split(c.sep).join("/")}`);
|
|
468
|
+
}
|
|
469
|
+
const g = Te(
|
|
470
|
+
f,
|
|
471
|
+
e.cssTheme
|
|
472
|
+
);
|
|
473
|
+
xe(d, g);
|
|
474
|
+
const m = $e(g), R = c.dirname(c.resolve(o, u)), U = m.external !== void 0 && m.generated !== void 0 ? {
|
|
475
|
+
external: c.resolve(R, m.external),
|
|
476
|
+
generated: c.resolve(R, m.generated)
|
|
468
477
|
} : void 0;
|
|
469
|
-
let
|
|
478
|
+
let P, p;
|
|
470
479
|
if (e.sourceMap) {
|
|
471
480
|
const h = await ie(
|
|
472
481
|
i,
|
|
473
482
|
n,
|
|
474
483
|
o
|
|
475
484
|
);
|
|
476
|
-
|
|
485
|
+
P = h.tree, p = h.content;
|
|
477
486
|
} else
|
|
478
|
-
p = await
|
|
487
|
+
p = await Pe(
|
|
479
488
|
i,
|
|
480
489
|
n,
|
|
481
490
|
o
|
|
482
491
|
);
|
|
483
|
-
const E =
|
|
484
|
-
let
|
|
492
|
+
const E = Re(p);
|
|
493
|
+
let C = { parentId: "root", position: 1 };
|
|
485
494
|
if (E !== "pretext" && E !== "mathbook")
|
|
486
495
|
if (e.fragment) {
|
|
487
|
-
const h = e.docinfo ?? (e.docinfoSourcePath ? await
|
|
488
|
-
p =
|
|
496
|
+
const h = e.docinfo ?? (e.docinfoSourcePath ? await Ue(e.docinfoSourcePath, o) : void 0);
|
|
497
|
+
p = Ce(p, E, h), C = { parentId: h?.trim() ? "root-1-2" : "root-1-1", position: 2 };
|
|
489
498
|
} else
|
|
490
499
|
throw new Error(
|
|
491
500
|
`The document root is <${E ?? "?"}>, not <pretext> — this looks like an xi:included fragment. Render the project's main source file instead, or pass the fragment option.`
|
|
492
501
|
);
|
|
493
|
-
const
|
|
494
|
-
url: `${l}/${u.split(
|
|
502
|
+
const W = P ? Ae(P, n, C) : void 0, B = await r.fromString(p, {
|
|
503
|
+
url: `${l}/${u.split(c.sep).join("/")}`,
|
|
495
504
|
options: { noEnt: !0, dtdLoad: !0, huge: !0 }
|
|
496
|
-
}),
|
|
497
|
-
publisher:
|
|
505
|
+
}), O = {
|
|
506
|
+
publisher: z(d)
|
|
498
507
|
};
|
|
499
|
-
for (const [h,
|
|
500
|
-
|
|
508
|
+
for (const [h, y] of Object.entries(e.stringParams ?? {}))
|
|
509
|
+
O[h] = z(y);
|
|
501
510
|
let k;
|
|
502
511
|
try {
|
|
503
|
-
k = await t.apply(
|
|
512
|
+
k = await t.apply(B, O);
|
|
504
513
|
} catch (h) {
|
|
505
|
-
throw
|
|
514
|
+
throw G(h), new Error(
|
|
506
515
|
"PreTeXt XSLT transform failed; see the PTX:ERROR/PTX:FATAL messages on stderr for details.",
|
|
507
516
|
{ cause: h }
|
|
508
517
|
);
|
|
509
518
|
} finally {
|
|
510
|
-
|
|
519
|
+
B.delete();
|
|
511
520
|
}
|
|
512
521
|
try {
|
|
513
|
-
let h =
|
|
522
|
+
let h = Le(k.toHtmlString());
|
|
514
523
|
return e.theme && (h = he(h, e.theme)), {
|
|
515
524
|
html: h,
|
|
516
|
-
...
|
|
517
|
-
...
|
|
525
|
+
...W ? { sourceMap: W } : {},
|
|
526
|
+
...U ? { assetDirs: U } : {}
|
|
518
527
|
};
|
|
519
528
|
} catch (h) {
|
|
520
|
-
throw
|
|
529
|
+
throw G(h), h;
|
|
521
530
|
} finally {
|
|
522
531
|
k.delete();
|
|
523
532
|
}
|
|
@@ -525,7 +534,7 @@ async function Y(e) {
|
|
|
525
534
|
ye(l);
|
|
526
535
|
}
|
|
527
536
|
}
|
|
528
|
-
const
|
|
537
|
+
const V = `Usage: pretext-html <source.ptx> [options]
|
|
529
538
|
|
|
530
539
|
Render a PreTeXt document to a single standalone HTML page (portable build:
|
|
531
540
|
one page, css/js/MathJax from CDN). No PreTeXt installation required.
|
|
@@ -533,6 +542,9 @@ one page, css/js/MathJax from CDN). No PreTeXt installation required.
|
|
|
533
542
|
Options:
|
|
534
543
|
-o, --output <file> Write HTML to a file instead of stdout
|
|
535
544
|
--publication <file> Publication file (portable html is forced on)
|
|
545
|
+
--css-theme <name> HTML theme to use when the publication file names
|
|
546
|
+
none of its own: default-modern (PreTeXt's default),
|
|
547
|
+
denver, tacoma, salem, greeley or boulder
|
|
536
548
|
--project-dir <dir> Directory served to the transform for xi:includes
|
|
537
549
|
(default: the source file's directory)
|
|
538
550
|
--param <name=value> Extra XSLT string parameter (repeatable)
|
|
@@ -551,9 +563,9 @@ Options:
|
|
|
551
563
|
file/line for every element (for editor sync)
|
|
552
564
|
-h, --help Show this help
|
|
553
565
|
`;
|
|
554
|
-
function
|
|
566
|
+
function Ne(e) {
|
|
555
567
|
let r, t, n, o;
|
|
556
|
-
const i = {},
|
|
568
|
+
const i = {}, a = {};
|
|
557
569
|
for (let s = 0; s < e.length; s++) {
|
|
558
570
|
const u = e[s], l = () => {
|
|
559
571
|
if (s += 1, s >= e.length)
|
|
@@ -563,7 +575,7 @@ function Oe(e) {
|
|
|
563
575
|
switch (u) {
|
|
564
576
|
case "-h":
|
|
565
577
|
case "--help":
|
|
566
|
-
w.stdout.write(
|
|
578
|
+
w.stdout.write(V), w.exit(0);
|
|
567
579
|
break;
|
|
568
580
|
case "-o":
|
|
569
581
|
case "--output":
|
|
@@ -572,6 +584,9 @@ function Oe(e) {
|
|
|
572
584
|
case "--publication":
|
|
573
585
|
i.publicationPath = l();
|
|
574
586
|
break;
|
|
587
|
+
case "--css-theme":
|
|
588
|
+
i.cssTheme = l();
|
|
589
|
+
break;
|
|
575
590
|
case "--project-dir":
|
|
576
591
|
i.projectDir = l();
|
|
577
592
|
break;
|
|
@@ -591,10 +606,10 @@ function Oe(e) {
|
|
|
591
606
|
o = l(), i.sourceMap = !0;
|
|
592
607
|
break;
|
|
593
608
|
case "--param": {
|
|
594
|
-
const
|
|
595
|
-
if (
|
|
596
|
-
throw new Error(`--param expects name=value, got: ${
|
|
597
|
-
|
|
609
|
+
const f = l(), d = f.indexOf("=");
|
|
610
|
+
if (d === -1)
|
|
611
|
+
throw new Error(`--param expects name=value, got: ${f}`);
|
|
612
|
+
a[f.slice(0, d)] = f.slice(d + 1);
|
|
598
613
|
break;
|
|
599
614
|
}
|
|
600
615
|
default:
|
|
@@ -608,32 +623,32 @@ function Oe(e) {
|
|
|
608
623
|
if (!r)
|
|
609
624
|
throw new Error(`No source file given.
|
|
610
625
|
|
|
611
|
-
` +
|
|
612
|
-
return Object.keys(
|
|
626
|
+
` + V);
|
|
627
|
+
return Object.keys(a).length > 0 && (i.stringParams = a), {
|
|
613
628
|
options: { ...i, sourcePath: r },
|
|
614
629
|
output: t,
|
|
615
630
|
docinfoPath: n,
|
|
616
631
|
sourceMapPath: o
|
|
617
632
|
};
|
|
618
633
|
}
|
|
619
|
-
async function
|
|
620
|
-
const { options: r, output: t, docinfoPath: n, sourceMapPath: o } =
|
|
621
|
-
n && (r.docinfo = await
|
|
622
|
-
const i = Date.now(), { html:
|
|
634
|
+
async function Ke(e) {
|
|
635
|
+
const { options: r, output: t, docinfoPath: n, sourceMapPath: o } = Ne(e);
|
|
636
|
+
n && (r.docinfo = await j(n, "utf8"));
|
|
637
|
+
const i = Date.now(), { html: a, sourceMap: s } = await He(r);
|
|
623
638
|
w.stderr.write(`pretext-html: rendered in ${Date.now() - i}ms
|
|
624
|
-
`), o && s && (await
|
|
625
|
-
`)), t ? (await
|
|
626
|
-
`)) : w.stdout.write(
|
|
639
|
+
`), o && s && (await _(o, JSON.stringify(s, null, 2)), w.stderr.write(`pretext-html: wrote ${o}
|
|
640
|
+
`)), t ? (await _(t, a), w.stderr.write(`pretext-html: wrote ${t}
|
|
641
|
+
`)) : w.stdout.write(a);
|
|
627
642
|
}
|
|
628
643
|
export {
|
|
629
|
-
|
|
630
|
-
|
|
631
|
-
|
|
632
|
-
|
|
633
|
-
|
|
634
|
-
|
|
635
|
-
|
|
636
|
-
|
|
637
|
-
|
|
638
|
-
|
|
644
|
+
Te as a,
|
|
645
|
+
Ve as b,
|
|
646
|
+
Xe as d,
|
|
647
|
+
Ze as f,
|
|
648
|
+
je as i,
|
|
649
|
+
Ke as m,
|
|
650
|
+
Ne as p,
|
|
651
|
+
He as r,
|
|
652
|
+
Qe as s,
|
|
653
|
+
z as x
|
|
639
654
|
};
|