@moku-labs/web 1.11.0 → 1.12.1
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/dist/browser.d.mts +72 -1
- package/dist/browser.mjs +29 -14
- package/dist/index.cjs +1137 -23
- package/dist/index.d.cts +93 -2
- package/dist/index.d.mts +93 -2
- package/dist/index.mjs +1139 -26
- package/package.json +1 -1
package/dist/index.cjs
CHANGED
|
@@ -40,6 +40,7 @@ let preact_jsx_runtime = require("preact/jsx-runtime");
|
|
|
40
40
|
let hast_util_sanitize = require("hast-util-sanitize");
|
|
41
41
|
let reading_time = require("reading-time");
|
|
42
42
|
reading_time = require_convention.__toESM(reading_time, 1);
|
|
43
|
+
let node_process = require("node:process");
|
|
43
44
|
//#region src/plugins/env/api.ts
|
|
44
45
|
/** Error prefix for all env API failures. */
|
|
45
46
|
const ERROR_PREFIX$16 = "[web]";
|
|
@@ -1583,14 +1584,15 @@ function validateContentConfig(config) {
|
|
|
1583
1584
|
}
|
|
1584
1585
|
/**
|
|
1585
1586
|
* Validates the `fileSystemContent` provider options (fail-fast at provider
|
|
1586
|
-
* construction). Throws when `mermaid` or `
|
|
1587
|
-
* `trustedContent: true`:
|
|
1588
|
-
* which the sanitize pass (the untrusted-content XSS
|
|
1589
|
-
* the combination can never work. Errors use the
|
|
1587
|
+
* construction). Throws when `mermaid`, `embed`, or `gallery` is enabled without
|
|
1588
|
+
* `trustedContent: true`: each emits raw HTML (inline SVG / the embed facade /
|
|
1589
|
+
* the gallery markup), which the sanitize pass (the untrusted-content XSS
|
|
1590
|
+
* boundary) would strip — so the combination can never work. Errors use the
|
|
1591
|
+
* `[web]` prefix.
|
|
1590
1592
|
*
|
|
1591
1593
|
* @param options - The provider options to validate.
|
|
1592
|
-
* @throws {Error} If `mermaid` or `
|
|
1593
|
-
* not `true`.
|
|
1594
|
+
* @throws {Error} If `mermaid`, `embed`, or `gallery` is enabled while
|
|
1595
|
+
* `trustedContent` is not `true`.
|
|
1594
1596
|
* @example
|
|
1595
1597
|
* ```ts
|
|
1596
1598
|
* validateFileSystemContentOptions({ contentDir: "./content", trustedContent: true, mermaid: true });
|
|
@@ -1599,6 +1601,7 @@ function validateContentConfig(config) {
|
|
|
1599
1601
|
function validateFileSystemContentOptions(options) {
|
|
1600
1602
|
if (Boolean(options.mermaid) && options.trustedContent !== true) throw new Error("[web] content: `mermaid` requires `trustedContent: true`.\n Mermaid diagrams render to raw inline SVG, which the sanitize pass would strip.\n Set trustedContent: true ONLY for fully author-controlled Markdown.");
|
|
1601
1603
|
if (Boolean(options.embed) && options.trustedContent !== true) throw new Error("[web] content: `embed` requires `trustedContent: true`.\n Embed directives render to a raw-HTML facade, which the sanitize pass would strip\n (and embedding third-party iframes is never safe for untrusted Markdown).\n Set trustedContent: true ONLY for fully author-controlled Markdown.");
|
|
1604
|
+
if (Boolean(options.gallery) && options.trustedContent !== true) throw new Error("[web] content: `gallery` requires `trustedContent: true`.\n Gallery directives render to raw-HTML markup, which the sanitize pass would strip.\n Set trustedContent: true ONLY for fully author-controlled Markdown.");
|
|
1602
1605
|
}
|
|
1603
1606
|
//#endregion
|
|
1604
1607
|
//#region src/plugins/content/index.ts
|
|
@@ -10636,6 +10639,17 @@ async function performNavigation(pathname, handlers, signal) {
|
|
|
10636
10639
|
}
|
|
10637
10640
|
}
|
|
10638
10641
|
/**
|
|
10642
|
+
* Whether the user has asked the platform to minimise motion.
|
|
10643
|
+
*
|
|
10644
|
+
* @returns `true` when `(prefers-reduced-motion: reduce)` currently matches; `false` when
|
|
10645
|
+
* it does not, or when `matchMedia` is absent (guards SSR/test environments).
|
|
10646
|
+
* @example
|
|
10647
|
+
* const behavior: ScrollBehavior = prefersReducedMotion() ? "instant" : "smooth";
|
|
10648
|
+
*/
|
|
10649
|
+
function prefersReducedMotion() {
|
|
10650
|
+
return typeof globalThis.matchMedia === "function" && globalThis.matchMedia("(prefers-reduced-motion: reduce)").matches;
|
|
10651
|
+
}
|
|
10652
|
+
/**
|
|
10639
10653
|
* Run a DOM-mutating swap, optionally wrapped in the View Transitions API when
|
|
10640
10654
|
* enabled and supported (instant swap otherwise — never throws).
|
|
10641
10655
|
*
|
|
@@ -10656,7 +10670,7 @@ async function performNavigation(pathname, handlers, signal) {
|
|
|
10656
10670
|
* runSwap(() => current.replaceWith(next), true, () => scrollTo({ top: 0, behavior: "instant" }));
|
|
10657
10671
|
*/
|
|
10658
10672
|
function runSwap(doSwap, viewTransitions, beforeCapture) {
|
|
10659
|
-
const reduced =
|
|
10673
|
+
const reduced = prefersReducedMotion();
|
|
10660
10674
|
const docWithVt = document;
|
|
10661
10675
|
const canUseViewTransitions = viewTransitions && !reduced && typeof docWithVt.startViewTransition === "function";
|
|
10662
10676
|
beforeCapture?.();
|
|
@@ -10754,7 +10768,7 @@ function attachHistoryFallback(handlers, navigate = (pathname, _scrollToTop, sig
|
|
|
10754
10768
|
if (pathWithSearch(url) === pathWithSearch(location)) {
|
|
10755
10769
|
window.scrollTo({
|
|
10756
10770
|
top: 0,
|
|
10757
|
-
behavior: "smooth"
|
|
10771
|
+
behavior: prefersReducedMotion() ? "instant" : "smooth"
|
|
10758
10772
|
});
|
|
10759
10773
|
return;
|
|
10760
10774
|
}
|
|
@@ -10808,7 +10822,7 @@ function attachNavigationApi(navigation, handlers, navigate = (pathname, _scroll
|
|
|
10808
10822
|
navEvent.intercept({ handler: () => {
|
|
10809
10823
|
window.scrollTo({
|
|
10810
10824
|
top: 0,
|
|
10811
|
-
behavior: "smooth"
|
|
10825
|
+
behavior: prefersReducedMotion() ? "instant" : "smooth"
|
|
10812
10826
|
});
|
|
10813
10827
|
return Promise.resolve();
|
|
10814
10828
|
} });
|
|
@@ -10985,26 +10999,30 @@ function createSpaKernel(state, config, emit, deps) {
|
|
|
10985
10999
|
let pendingScrollToTop = true;
|
|
10986
11000
|
/**
|
|
10987
11001
|
* Apply the in-flight navigation's scroll intent — the swap's `beforeCapture` hook.
|
|
10988
|
-
* For a forward nav it scrolls to top BEFORE the
|
|
10989
|
-
*
|
|
10990
|
-
* no
|
|
10991
|
-
*
|
|
11002
|
+
* For a forward nav it scrolls to top BEFORE the swap (and, with view transitions on,
|
|
11003
|
+
* before the "old" snapshot is captured), so the old and new states share scrollY=0:
|
|
11004
|
+
* no delta for a transition to animate → a `position: sticky` header never un-pins.
|
|
11005
|
+
* Traverse (back/forward) sets `pendingScrollToTop = false` and restores its saved
|
|
11006
|
+
* position after the swap instead.
|
|
10992
11007
|
*
|
|
10993
|
-
*
|
|
10994
|
-
*
|
|
10995
|
-
*
|
|
10996
|
-
*
|
|
10997
|
-
*
|
|
11008
|
+
* The reset is ALWAYS `"instant"`, never the CSS-driven `"auto"`. It runs synchronously
|
|
11009
|
+
* immediately before the swap, and the swap mutates document height (the outgoing page is
|
|
11010
|
+
* usually taller than the incoming one). A smooth scroll — from `behavior: "smooth"` or a
|
|
11011
|
+
* page `scroll-behavior: smooth` that `"auto"` would inherit — is still animating when that
|
|
11012
|
+
* height change lands; the browser clamps scrollY to the new, smaller maximum and cancels
|
|
11013
|
+
* the in-flight animation there (worst on WebKit), stranding the page near the OLD position
|
|
11014
|
+
* instead of the top. Instant lands scrollY=0 before the swap, every time. (A smooth
|
|
11015
|
+
* scroll-to-top on the SAME page is unaffected — the router's same-page handler animates
|
|
11016
|
+
* it, where there is no swap to race.)
|
|
10998
11017
|
*
|
|
10999
11018
|
* @example
|
|
11000
11019
|
* runSwap(renderAndMount, viewTransitions, applyPendingScroll);
|
|
11001
11020
|
*/
|
|
11002
11021
|
const applyPendingScroll = () => {
|
|
11003
11022
|
if (!pendingScrollToTop) return;
|
|
11004
|
-
const behavior = resolved.viewTransitions ? "instant" : "auto";
|
|
11005
11023
|
window.scrollTo({
|
|
11006
11024
|
top: 0,
|
|
11007
|
-
behavior
|
|
11025
|
+
behavior: "instant"
|
|
11008
11026
|
});
|
|
11009
11027
|
};
|
|
11010
11028
|
/**
|
|
@@ -11638,6 +11656,857 @@ function cloudflareBindings() {
|
|
|
11638
11656
|
};
|
|
11639
11657
|
}
|
|
11640
11658
|
//#endregion
|
|
11659
|
+
//#region node_modules/unist-util-stringify-position/lib/index.js
|
|
11660
|
+
/**
|
|
11661
|
+
* @typedef {import('unist').Node} Node
|
|
11662
|
+
* @typedef {import('unist').Point} Point
|
|
11663
|
+
* @typedef {import('unist').Position} Position
|
|
11664
|
+
*/
|
|
11665
|
+
/**
|
|
11666
|
+
* @typedef NodeLike
|
|
11667
|
+
* @property {string} type
|
|
11668
|
+
* @property {PositionLike | null | undefined} [position]
|
|
11669
|
+
*
|
|
11670
|
+
* @typedef PointLike
|
|
11671
|
+
* @property {number | null | undefined} [line]
|
|
11672
|
+
* @property {number | null | undefined} [column]
|
|
11673
|
+
* @property {number | null | undefined} [offset]
|
|
11674
|
+
*
|
|
11675
|
+
* @typedef PositionLike
|
|
11676
|
+
* @property {PointLike | null | undefined} [start]
|
|
11677
|
+
* @property {PointLike | null | undefined} [end]
|
|
11678
|
+
*/
|
|
11679
|
+
/**
|
|
11680
|
+
* Serialize the positional info of a point, position (start and end points),
|
|
11681
|
+
* or node.
|
|
11682
|
+
*
|
|
11683
|
+
* @param {Node | NodeLike | Point | PointLike | Position | PositionLike | null | undefined} [value]
|
|
11684
|
+
* Node, position, or point.
|
|
11685
|
+
* @returns {string}
|
|
11686
|
+
* Pretty printed positional info of a node (`string`).
|
|
11687
|
+
*
|
|
11688
|
+
* In the format of a range `ls:cs-le:ce` (when given `node` or `position`)
|
|
11689
|
+
* or a point `l:c` (when given `point`), where `l` stands for line, `c` for
|
|
11690
|
+
* column, `s` for `start`, and `e` for end.
|
|
11691
|
+
* An empty string (`''`) is returned if the given value is neither `node`,
|
|
11692
|
+
* `position`, nor `point`.
|
|
11693
|
+
*/
|
|
11694
|
+
function stringifyPosition(value) {
|
|
11695
|
+
if (!value || typeof value !== "object") return "";
|
|
11696
|
+
if ("position" in value || "type" in value) return position(value.position);
|
|
11697
|
+
if ("start" in value || "end" in value) return position(value);
|
|
11698
|
+
if ("line" in value || "column" in value) return point(value);
|
|
11699
|
+
return "";
|
|
11700
|
+
}
|
|
11701
|
+
/**
|
|
11702
|
+
* @param {Point | PointLike | null | undefined} point
|
|
11703
|
+
* @returns {string}
|
|
11704
|
+
*/
|
|
11705
|
+
function point(point) {
|
|
11706
|
+
return index(point && point.line) + ":" + index(point && point.column);
|
|
11707
|
+
}
|
|
11708
|
+
/**
|
|
11709
|
+
* @param {Position | PositionLike | null | undefined} pos
|
|
11710
|
+
* @returns {string}
|
|
11711
|
+
*/
|
|
11712
|
+
function position(pos) {
|
|
11713
|
+
return point(pos && pos.start) + "-" + point(pos && pos.end);
|
|
11714
|
+
}
|
|
11715
|
+
/**
|
|
11716
|
+
* @param {number | null | undefined} value
|
|
11717
|
+
* @returns {number}
|
|
11718
|
+
*/
|
|
11719
|
+
function index(value) {
|
|
11720
|
+
return value && typeof value === "number" ? value : 1;
|
|
11721
|
+
}
|
|
11722
|
+
//#endregion
|
|
11723
|
+
//#region node_modules/vfile-message/lib/index.js
|
|
11724
|
+
/**
|
|
11725
|
+
* @import {Node, Point, Position} from 'unist'
|
|
11726
|
+
*/
|
|
11727
|
+
/**
|
|
11728
|
+
* @typedef {object & {type: string, position?: Position | undefined}} NodeLike
|
|
11729
|
+
*
|
|
11730
|
+
* @typedef Options
|
|
11731
|
+
* Configuration.
|
|
11732
|
+
* @property {Array<Node> | null | undefined} [ancestors]
|
|
11733
|
+
* Stack of (inclusive) ancestor nodes surrounding the message (optional).
|
|
11734
|
+
* @property {Error | null | undefined} [cause]
|
|
11735
|
+
* Original error cause of the message (optional).
|
|
11736
|
+
* @property {Point | Position | null | undefined} [place]
|
|
11737
|
+
* Place of message (optional).
|
|
11738
|
+
* @property {string | null | undefined} [ruleId]
|
|
11739
|
+
* Category of message (optional, example: `'my-rule'`).
|
|
11740
|
+
* @property {string | null | undefined} [source]
|
|
11741
|
+
* Namespace of who sent the message (optional, example: `'my-package'`).
|
|
11742
|
+
*/
|
|
11743
|
+
/**
|
|
11744
|
+
* Message.
|
|
11745
|
+
*/
|
|
11746
|
+
var VFileMessage = class extends Error {
|
|
11747
|
+
/**
|
|
11748
|
+
* Create a message for `reason`.
|
|
11749
|
+
*
|
|
11750
|
+
* > 🪦 **Note**: also has obsolete signatures.
|
|
11751
|
+
*
|
|
11752
|
+
* @overload
|
|
11753
|
+
* @param {string} reason
|
|
11754
|
+
* @param {Options | null | undefined} [options]
|
|
11755
|
+
* @returns
|
|
11756
|
+
*
|
|
11757
|
+
* @overload
|
|
11758
|
+
* @param {string} reason
|
|
11759
|
+
* @param {Node | NodeLike | null | undefined} parent
|
|
11760
|
+
* @param {string | null | undefined} [origin]
|
|
11761
|
+
* @returns
|
|
11762
|
+
*
|
|
11763
|
+
* @overload
|
|
11764
|
+
* @param {string} reason
|
|
11765
|
+
* @param {Point | Position | null | undefined} place
|
|
11766
|
+
* @param {string | null | undefined} [origin]
|
|
11767
|
+
* @returns
|
|
11768
|
+
*
|
|
11769
|
+
* @overload
|
|
11770
|
+
* @param {string} reason
|
|
11771
|
+
* @param {string | null | undefined} [origin]
|
|
11772
|
+
* @returns
|
|
11773
|
+
*
|
|
11774
|
+
* @overload
|
|
11775
|
+
* @param {Error | VFileMessage} cause
|
|
11776
|
+
* @param {Node | NodeLike | null | undefined} parent
|
|
11777
|
+
* @param {string | null | undefined} [origin]
|
|
11778
|
+
* @returns
|
|
11779
|
+
*
|
|
11780
|
+
* @overload
|
|
11781
|
+
* @param {Error | VFileMessage} cause
|
|
11782
|
+
* @param {Point | Position | null | undefined} place
|
|
11783
|
+
* @param {string | null | undefined} [origin]
|
|
11784
|
+
* @returns
|
|
11785
|
+
*
|
|
11786
|
+
* @overload
|
|
11787
|
+
* @param {Error | VFileMessage} cause
|
|
11788
|
+
* @param {string | null | undefined} [origin]
|
|
11789
|
+
* @returns
|
|
11790
|
+
*
|
|
11791
|
+
* @param {Error | VFileMessage | string} causeOrReason
|
|
11792
|
+
* Reason for message, should use markdown.
|
|
11793
|
+
* @param {Node | NodeLike | Options | Point | Position | string | null | undefined} [optionsOrParentOrPlace]
|
|
11794
|
+
* Configuration (optional).
|
|
11795
|
+
* @param {string | null | undefined} [origin]
|
|
11796
|
+
* Place in code where the message originates (example:
|
|
11797
|
+
* `'my-package:my-rule'` or `'my-rule'`).
|
|
11798
|
+
* @returns
|
|
11799
|
+
* Instance of `VFileMessage`.
|
|
11800
|
+
*/
|
|
11801
|
+
constructor(causeOrReason, optionsOrParentOrPlace, origin) {
|
|
11802
|
+
super();
|
|
11803
|
+
if (typeof optionsOrParentOrPlace === "string") {
|
|
11804
|
+
origin = optionsOrParentOrPlace;
|
|
11805
|
+
optionsOrParentOrPlace = void 0;
|
|
11806
|
+
}
|
|
11807
|
+
/** @type {string} */
|
|
11808
|
+
let reason = "";
|
|
11809
|
+
/** @type {Options} */
|
|
11810
|
+
let options = {};
|
|
11811
|
+
let legacyCause = false;
|
|
11812
|
+
if (optionsOrParentOrPlace) if ("line" in optionsOrParentOrPlace && "column" in optionsOrParentOrPlace) options = { place: optionsOrParentOrPlace };
|
|
11813
|
+
else if ("start" in optionsOrParentOrPlace && "end" in optionsOrParentOrPlace) options = { place: optionsOrParentOrPlace };
|
|
11814
|
+
else if ("type" in optionsOrParentOrPlace) options = {
|
|
11815
|
+
ancestors: [optionsOrParentOrPlace],
|
|
11816
|
+
place: optionsOrParentOrPlace.position
|
|
11817
|
+
};
|
|
11818
|
+
else options = { ...optionsOrParentOrPlace };
|
|
11819
|
+
if (typeof causeOrReason === "string") reason = causeOrReason;
|
|
11820
|
+
else if (!options.cause && causeOrReason) {
|
|
11821
|
+
legacyCause = true;
|
|
11822
|
+
reason = causeOrReason.message;
|
|
11823
|
+
options.cause = causeOrReason;
|
|
11824
|
+
}
|
|
11825
|
+
if (!options.ruleId && !options.source && typeof origin === "string") {
|
|
11826
|
+
const index = origin.indexOf(":");
|
|
11827
|
+
if (index === -1) options.ruleId = origin;
|
|
11828
|
+
else {
|
|
11829
|
+
options.source = origin.slice(0, index);
|
|
11830
|
+
options.ruleId = origin.slice(index + 1);
|
|
11831
|
+
}
|
|
11832
|
+
}
|
|
11833
|
+
if (!options.place && options.ancestors && options.ancestors) {
|
|
11834
|
+
const parent = options.ancestors[options.ancestors.length - 1];
|
|
11835
|
+
if (parent) options.place = parent.position;
|
|
11836
|
+
}
|
|
11837
|
+
const start = options.place && "start" in options.place ? options.place.start : options.place;
|
|
11838
|
+
/**
|
|
11839
|
+
* Stack of ancestor nodes surrounding the message.
|
|
11840
|
+
*
|
|
11841
|
+
* @type {Array<Node> | undefined}
|
|
11842
|
+
*/
|
|
11843
|
+
this.ancestors = options.ancestors || void 0;
|
|
11844
|
+
/**
|
|
11845
|
+
* Original error cause of the message.
|
|
11846
|
+
*
|
|
11847
|
+
* @type {Error | undefined}
|
|
11848
|
+
*/
|
|
11849
|
+
this.cause = options.cause || void 0;
|
|
11850
|
+
/**
|
|
11851
|
+
* Starting column of message.
|
|
11852
|
+
*
|
|
11853
|
+
* @type {number | undefined}
|
|
11854
|
+
*/
|
|
11855
|
+
this.column = start ? start.column : void 0;
|
|
11856
|
+
/**
|
|
11857
|
+
* State of problem.
|
|
11858
|
+
*
|
|
11859
|
+
* * `true` — error, file not usable
|
|
11860
|
+
* * `false` — warning, change may be needed
|
|
11861
|
+
* * `undefined` — change likely not needed
|
|
11862
|
+
*
|
|
11863
|
+
* @type {boolean | null | undefined}
|
|
11864
|
+
*/
|
|
11865
|
+
this.fatal = void 0;
|
|
11866
|
+
/**
|
|
11867
|
+
* Path of a file (used throughout the `VFile` ecosystem).
|
|
11868
|
+
*
|
|
11869
|
+
* @type {string | undefined}
|
|
11870
|
+
*/
|
|
11871
|
+
this.file = "";
|
|
11872
|
+
/**
|
|
11873
|
+
* Reason for message.
|
|
11874
|
+
*
|
|
11875
|
+
* @type {string}
|
|
11876
|
+
*/
|
|
11877
|
+
this.message = reason;
|
|
11878
|
+
/**
|
|
11879
|
+
* Starting line of error.
|
|
11880
|
+
*
|
|
11881
|
+
* @type {number | undefined}
|
|
11882
|
+
*/
|
|
11883
|
+
this.line = start ? start.line : void 0;
|
|
11884
|
+
/**
|
|
11885
|
+
* Serialized positional info of message.
|
|
11886
|
+
*
|
|
11887
|
+
* On normal errors, this would be something like `ParseError`, buit in
|
|
11888
|
+
* `VFile` messages we use this space to show where an error happened.
|
|
11889
|
+
*/
|
|
11890
|
+
this.name = stringifyPosition(options.place) || "1:1";
|
|
11891
|
+
/**
|
|
11892
|
+
* Place of message.
|
|
11893
|
+
*
|
|
11894
|
+
* @type {Point | Position | undefined}
|
|
11895
|
+
*/
|
|
11896
|
+
this.place = options.place || void 0;
|
|
11897
|
+
/**
|
|
11898
|
+
* Reason for message, should use markdown.
|
|
11899
|
+
*
|
|
11900
|
+
* @type {string}
|
|
11901
|
+
*/
|
|
11902
|
+
this.reason = this.message;
|
|
11903
|
+
/**
|
|
11904
|
+
* Category of message (example: `'my-rule'`).
|
|
11905
|
+
*
|
|
11906
|
+
* @type {string | undefined}
|
|
11907
|
+
*/
|
|
11908
|
+
this.ruleId = options.ruleId || void 0;
|
|
11909
|
+
/**
|
|
11910
|
+
* Namespace of message (example: `'my-package'`).
|
|
11911
|
+
*
|
|
11912
|
+
* @type {string | undefined}
|
|
11913
|
+
*/
|
|
11914
|
+
this.source = options.source || void 0;
|
|
11915
|
+
/**
|
|
11916
|
+
* Stack of message.
|
|
11917
|
+
*
|
|
11918
|
+
* This is used by normal errors to show where something happened in
|
|
11919
|
+
* programming code, irrelevant for `VFile` messages,
|
|
11920
|
+
*
|
|
11921
|
+
* @type {string}
|
|
11922
|
+
*/
|
|
11923
|
+
this.stack = legacyCause && options.cause && typeof options.cause.stack === "string" ? options.cause.stack : "";
|
|
11924
|
+
/**
|
|
11925
|
+
* Specify the source value that’s being reported, which is deemed
|
|
11926
|
+
* incorrect.
|
|
11927
|
+
*
|
|
11928
|
+
* @type {string | undefined}
|
|
11929
|
+
*/
|
|
11930
|
+
this.actual = void 0;
|
|
11931
|
+
/**
|
|
11932
|
+
* Suggest acceptable values that can be used instead of `actual`.
|
|
11933
|
+
*
|
|
11934
|
+
* @type {Array<string> | undefined}
|
|
11935
|
+
*/
|
|
11936
|
+
this.expected = void 0;
|
|
11937
|
+
/**
|
|
11938
|
+
* Long form description of the message (you should use markdown).
|
|
11939
|
+
*
|
|
11940
|
+
* @type {string | undefined}
|
|
11941
|
+
*/
|
|
11942
|
+
this.note = void 0;
|
|
11943
|
+
/**
|
|
11944
|
+
* Link to docs for the message.
|
|
11945
|
+
*
|
|
11946
|
+
* > 👉 **Note**: this must be an absolute URL that can be passed as `x`
|
|
11947
|
+
* > to `new URL(x)`.
|
|
11948
|
+
*
|
|
11949
|
+
* @type {string | undefined}
|
|
11950
|
+
*/
|
|
11951
|
+
this.url = void 0;
|
|
11952
|
+
}
|
|
11953
|
+
};
|
|
11954
|
+
VFileMessage.prototype.file = "";
|
|
11955
|
+
VFileMessage.prototype.name = "";
|
|
11956
|
+
VFileMessage.prototype.reason = "";
|
|
11957
|
+
VFileMessage.prototype.message = "";
|
|
11958
|
+
VFileMessage.prototype.stack = "";
|
|
11959
|
+
VFileMessage.prototype.column = void 0;
|
|
11960
|
+
VFileMessage.prototype.line = void 0;
|
|
11961
|
+
VFileMessage.prototype.ancestors = void 0;
|
|
11962
|
+
VFileMessage.prototype.cause = void 0;
|
|
11963
|
+
VFileMessage.prototype.fatal = void 0;
|
|
11964
|
+
VFileMessage.prototype.place = void 0;
|
|
11965
|
+
VFileMessage.prototype.ruleId = void 0;
|
|
11966
|
+
VFileMessage.prototype.source = void 0;
|
|
11967
|
+
//#endregion
|
|
11968
|
+
//#region node_modules/vfile/lib/minurl.shared.js
|
|
11969
|
+
/**
|
|
11970
|
+
* Checks if a value has the shape of a WHATWG URL object.
|
|
11971
|
+
*
|
|
11972
|
+
* Using a symbol or instanceof would not be able to recognize URL objects
|
|
11973
|
+
* coming from other implementations (e.g. in Electron), so instead we are
|
|
11974
|
+
* checking some well known properties for a lack of a better test.
|
|
11975
|
+
*
|
|
11976
|
+
* We use `href` and `protocol` as they are the only properties that are
|
|
11977
|
+
* easy to retrieve and calculate due to the lazy nature of the getters.
|
|
11978
|
+
*
|
|
11979
|
+
* We check for auth attribute to distinguish legacy url instance with
|
|
11980
|
+
* WHATWG URL instance.
|
|
11981
|
+
*
|
|
11982
|
+
* @param {unknown} fileUrlOrPath
|
|
11983
|
+
* File path or URL.
|
|
11984
|
+
* @returns {fileUrlOrPath is URL}
|
|
11985
|
+
* Whether it’s a URL.
|
|
11986
|
+
*/
|
|
11987
|
+
function isUrl(fileUrlOrPath) {
|
|
11988
|
+
return Boolean(fileUrlOrPath !== null && typeof fileUrlOrPath === "object" && "href" in fileUrlOrPath && fileUrlOrPath.href && "protocol" in fileUrlOrPath && fileUrlOrPath.protocol && fileUrlOrPath.auth === void 0);
|
|
11989
|
+
}
|
|
11990
|
+
//#endregion
|
|
11991
|
+
//#region node_modules/vfile/lib/index.js
|
|
11992
|
+
/**
|
|
11993
|
+
* @import {Node, Point, Position} from 'unist'
|
|
11994
|
+
* @import {Options as MessageOptions} from 'vfile-message'
|
|
11995
|
+
* @import {Compatible, Data, Map, Options, Value} from 'vfile'
|
|
11996
|
+
*/
|
|
11997
|
+
/**
|
|
11998
|
+
* @typedef {object & {type: string, position?: Position | undefined}} NodeLike
|
|
11999
|
+
*/
|
|
12000
|
+
/**
|
|
12001
|
+
* Order of setting (least specific to most), we need this because otherwise
|
|
12002
|
+
* `{stem: 'a', path: '~/b.js'}` would throw, as a path is needed before a
|
|
12003
|
+
* stem can be set.
|
|
12004
|
+
*/
|
|
12005
|
+
const order = [
|
|
12006
|
+
"history",
|
|
12007
|
+
"path",
|
|
12008
|
+
"basename",
|
|
12009
|
+
"stem",
|
|
12010
|
+
"extname",
|
|
12011
|
+
"dirname"
|
|
12012
|
+
];
|
|
12013
|
+
var VFile = class {
|
|
12014
|
+
/**
|
|
12015
|
+
* Create a new virtual file.
|
|
12016
|
+
*
|
|
12017
|
+
* `options` is treated as:
|
|
12018
|
+
*
|
|
12019
|
+
* * `string` or `Uint8Array` — `{value: options}`
|
|
12020
|
+
* * `URL` — `{path: options}`
|
|
12021
|
+
* * `VFile` — shallow copies its data over to the new file
|
|
12022
|
+
* * `object` — all fields are shallow copied over to the new file
|
|
12023
|
+
*
|
|
12024
|
+
* Path related fields are set in the following order (least specific to
|
|
12025
|
+
* most specific): `history`, `path`, `basename`, `stem`, `extname`,
|
|
12026
|
+
* `dirname`.
|
|
12027
|
+
*
|
|
12028
|
+
* You cannot set `dirname` or `extname` without setting either `history`,
|
|
12029
|
+
* `path`, `basename`, or `stem` too.
|
|
12030
|
+
*
|
|
12031
|
+
* @param {Compatible | null | undefined} [value]
|
|
12032
|
+
* File value.
|
|
12033
|
+
* @returns
|
|
12034
|
+
* New instance.
|
|
12035
|
+
*/
|
|
12036
|
+
constructor(value) {
|
|
12037
|
+
/** @type {Options | VFile} */
|
|
12038
|
+
let options;
|
|
12039
|
+
if (!value) options = {};
|
|
12040
|
+
else if (isUrl(value)) options = { path: value };
|
|
12041
|
+
else if (typeof value === "string" || isUint8Array(value)) options = { value };
|
|
12042
|
+
else options = value;
|
|
12043
|
+
/**
|
|
12044
|
+
* Base of `path` (default: `process.cwd()` or `'/'` in browsers).
|
|
12045
|
+
*
|
|
12046
|
+
* @type {string}
|
|
12047
|
+
*/
|
|
12048
|
+
this.cwd = "cwd" in options ? "" : node_process.default.cwd();
|
|
12049
|
+
/**
|
|
12050
|
+
* Place to store custom info (default: `{}`).
|
|
12051
|
+
*
|
|
12052
|
+
* It’s OK to store custom data directly on the file but moving it to
|
|
12053
|
+
* `data` is recommended.
|
|
12054
|
+
*
|
|
12055
|
+
* @type {Data}
|
|
12056
|
+
*/
|
|
12057
|
+
this.data = {};
|
|
12058
|
+
/**
|
|
12059
|
+
* List of file paths the file moved between.
|
|
12060
|
+
*
|
|
12061
|
+
* The first is the original path and the last is the current path.
|
|
12062
|
+
*
|
|
12063
|
+
* @type {Array<string>}
|
|
12064
|
+
*/
|
|
12065
|
+
this.history = [];
|
|
12066
|
+
/**
|
|
12067
|
+
* List of messages associated with the file.
|
|
12068
|
+
*
|
|
12069
|
+
* @type {Array<VFileMessage>}
|
|
12070
|
+
*/
|
|
12071
|
+
this.messages = [];
|
|
12072
|
+
/**
|
|
12073
|
+
* Raw value.
|
|
12074
|
+
*
|
|
12075
|
+
* @type {Value}
|
|
12076
|
+
*/
|
|
12077
|
+
this.value;
|
|
12078
|
+
/**
|
|
12079
|
+
* Source map.
|
|
12080
|
+
*
|
|
12081
|
+
* This type is equivalent to the `RawSourceMap` type from the `source-map`
|
|
12082
|
+
* module.
|
|
12083
|
+
*
|
|
12084
|
+
* @type {Map | null | undefined}
|
|
12085
|
+
*/
|
|
12086
|
+
this.map;
|
|
12087
|
+
/**
|
|
12088
|
+
* Custom, non-string, compiled, representation.
|
|
12089
|
+
*
|
|
12090
|
+
* This is used by unified to store non-string results.
|
|
12091
|
+
* One example is when turning markdown into React nodes.
|
|
12092
|
+
*
|
|
12093
|
+
* @type {unknown}
|
|
12094
|
+
*/
|
|
12095
|
+
this.result;
|
|
12096
|
+
/**
|
|
12097
|
+
* Whether a file was saved to disk.
|
|
12098
|
+
*
|
|
12099
|
+
* This is used by vfile reporters.
|
|
12100
|
+
*
|
|
12101
|
+
* @type {boolean}
|
|
12102
|
+
*/
|
|
12103
|
+
this.stored;
|
|
12104
|
+
let index = -1;
|
|
12105
|
+
while (++index < order.length) {
|
|
12106
|
+
const field = order[index];
|
|
12107
|
+
if (field in options && options[field] !== void 0 && options[field] !== null) this[field] = field === "history" ? [...options[field]] : options[field];
|
|
12108
|
+
}
|
|
12109
|
+
/** @type {string} */
|
|
12110
|
+
let field;
|
|
12111
|
+
for (field in options) if (!order.includes(field)) this[field] = options[field];
|
|
12112
|
+
}
|
|
12113
|
+
/**
|
|
12114
|
+
* Get the basename (including extname) (example: `'index.min.js'`).
|
|
12115
|
+
*
|
|
12116
|
+
* @returns {string | undefined}
|
|
12117
|
+
* Basename.
|
|
12118
|
+
*/
|
|
12119
|
+
get basename() {
|
|
12120
|
+
return typeof this.path === "string" ? node_path$1.default.basename(this.path) : void 0;
|
|
12121
|
+
}
|
|
12122
|
+
/**
|
|
12123
|
+
* Set basename (including extname) (`'index.min.js'`).
|
|
12124
|
+
*
|
|
12125
|
+
* Cannot contain path separators (`'/'` on unix, macOS, and browsers, `'\'`
|
|
12126
|
+
* on windows).
|
|
12127
|
+
* Cannot be nullified (use `file.path = file.dirname` instead).
|
|
12128
|
+
*
|
|
12129
|
+
* @param {string} basename
|
|
12130
|
+
* Basename.
|
|
12131
|
+
* @returns {undefined}
|
|
12132
|
+
* Nothing.
|
|
12133
|
+
*/
|
|
12134
|
+
set basename(basename) {
|
|
12135
|
+
assertNonEmpty(basename, "basename");
|
|
12136
|
+
assertPart(basename, "basename");
|
|
12137
|
+
this.path = node_path$1.default.join(this.dirname || "", basename);
|
|
12138
|
+
}
|
|
12139
|
+
/**
|
|
12140
|
+
* Get the parent path (example: `'~'`).
|
|
12141
|
+
*
|
|
12142
|
+
* @returns {string | undefined}
|
|
12143
|
+
* Dirname.
|
|
12144
|
+
*/
|
|
12145
|
+
get dirname() {
|
|
12146
|
+
return typeof this.path === "string" ? node_path$1.default.dirname(this.path) : void 0;
|
|
12147
|
+
}
|
|
12148
|
+
/**
|
|
12149
|
+
* Set the parent path (example: `'~'`).
|
|
12150
|
+
*
|
|
12151
|
+
* Cannot be set if there’s no `path` yet.
|
|
12152
|
+
*
|
|
12153
|
+
* @param {string | undefined} dirname
|
|
12154
|
+
* Dirname.
|
|
12155
|
+
* @returns {undefined}
|
|
12156
|
+
* Nothing.
|
|
12157
|
+
*/
|
|
12158
|
+
set dirname(dirname) {
|
|
12159
|
+
assertPath(this.basename, "dirname");
|
|
12160
|
+
this.path = node_path$1.default.join(dirname || "", this.basename);
|
|
12161
|
+
}
|
|
12162
|
+
/**
|
|
12163
|
+
* Get the extname (including dot) (example: `'.js'`).
|
|
12164
|
+
*
|
|
12165
|
+
* @returns {string | undefined}
|
|
12166
|
+
* Extname.
|
|
12167
|
+
*/
|
|
12168
|
+
get extname() {
|
|
12169
|
+
return typeof this.path === "string" ? node_path$1.default.extname(this.path) : void 0;
|
|
12170
|
+
}
|
|
12171
|
+
/**
|
|
12172
|
+
* Set the extname (including dot) (example: `'.js'`).
|
|
12173
|
+
*
|
|
12174
|
+
* Cannot contain path separators (`'/'` on unix, macOS, and browsers, `'\'`
|
|
12175
|
+
* on windows).
|
|
12176
|
+
* Cannot be set if there’s no `path` yet.
|
|
12177
|
+
*
|
|
12178
|
+
* @param {string | undefined} extname
|
|
12179
|
+
* Extname.
|
|
12180
|
+
* @returns {undefined}
|
|
12181
|
+
* Nothing.
|
|
12182
|
+
*/
|
|
12183
|
+
set extname(extname) {
|
|
12184
|
+
assertPart(extname, "extname");
|
|
12185
|
+
assertPath(this.dirname, "extname");
|
|
12186
|
+
if (extname) {
|
|
12187
|
+
if (extname.codePointAt(0) !== 46) throw new Error("`extname` must start with `.`");
|
|
12188
|
+
if (extname.includes(".", 1)) throw new Error("`extname` cannot contain multiple dots");
|
|
12189
|
+
}
|
|
12190
|
+
this.path = node_path$1.default.join(this.dirname, this.stem + (extname || ""));
|
|
12191
|
+
}
|
|
12192
|
+
/**
|
|
12193
|
+
* Get the full path (example: `'~/index.min.js'`).
|
|
12194
|
+
*
|
|
12195
|
+
* @returns {string}
|
|
12196
|
+
* Path.
|
|
12197
|
+
*/
|
|
12198
|
+
get path() {
|
|
12199
|
+
return this.history[this.history.length - 1];
|
|
12200
|
+
}
|
|
12201
|
+
/**
|
|
12202
|
+
* Set the full path (example: `'~/index.min.js'`).
|
|
12203
|
+
*
|
|
12204
|
+
* Cannot be nullified.
|
|
12205
|
+
* You can set a file URL (a `URL` object with a `file:` protocol) which will
|
|
12206
|
+
* be turned into a path with `url.fileURLToPath`.
|
|
12207
|
+
*
|
|
12208
|
+
* @param {URL | string} path
|
|
12209
|
+
* Path.
|
|
12210
|
+
* @returns {undefined}
|
|
12211
|
+
* Nothing.
|
|
12212
|
+
*/
|
|
12213
|
+
set path(path) {
|
|
12214
|
+
if (isUrl(path)) path = (0, node_url.fileURLToPath)(path);
|
|
12215
|
+
assertNonEmpty(path, "path");
|
|
12216
|
+
if (this.path !== path) this.history.push(path);
|
|
12217
|
+
}
|
|
12218
|
+
/**
|
|
12219
|
+
* Get the stem (basename w/o extname) (example: `'index.min'`).
|
|
12220
|
+
*
|
|
12221
|
+
* @returns {string | undefined}
|
|
12222
|
+
* Stem.
|
|
12223
|
+
*/
|
|
12224
|
+
get stem() {
|
|
12225
|
+
return typeof this.path === "string" ? node_path$1.default.basename(this.path, this.extname) : void 0;
|
|
12226
|
+
}
|
|
12227
|
+
/**
|
|
12228
|
+
* Set the stem (basename w/o extname) (example: `'index.min'`).
|
|
12229
|
+
*
|
|
12230
|
+
* Cannot contain path separators (`'/'` on unix, macOS, and browsers, `'\'`
|
|
12231
|
+
* on windows).
|
|
12232
|
+
* Cannot be nullified (use `file.path = file.dirname` instead).
|
|
12233
|
+
*
|
|
12234
|
+
* @param {string} stem
|
|
12235
|
+
* Stem.
|
|
12236
|
+
* @returns {undefined}
|
|
12237
|
+
* Nothing.
|
|
12238
|
+
*/
|
|
12239
|
+
set stem(stem) {
|
|
12240
|
+
assertNonEmpty(stem, "stem");
|
|
12241
|
+
assertPart(stem, "stem");
|
|
12242
|
+
this.path = node_path$1.default.join(this.dirname || "", stem + (this.extname || ""));
|
|
12243
|
+
}
|
|
12244
|
+
/**
|
|
12245
|
+
* Create a fatal message for `reason` associated with the file.
|
|
12246
|
+
*
|
|
12247
|
+
* The `fatal` field of the message is set to `true` (error; file not usable)
|
|
12248
|
+
* and the `file` field is set to the current file path.
|
|
12249
|
+
* The message is added to the `messages` field on `file`.
|
|
12250
|
+
*
|
|
12251
|
+
* > 🪦 **Note**: also has obsolete signatures.
|
|
12252
|
+
*
|
|
12253
|
+
* @overload
|
|
12254
|
+
* @param {string} reason
|
|
12255
|
+
* @param {MessageOptions | null | undefined} [options]
|
|
12256
|
+
* @returns {never}
|
|
12257
|
+
*
|
|
12258
|
+
* @overload
|
|
12259
|
+
* @param {string} reason
|
|
12260
|
+
* @param {Node | NodeLike | null | undefined} parent
|
|
12261
|
+
* @param {string | null | undefined} [origin]
|
|
12262
|
+
* @returns {never}
|
|
12263
|
+
*
|
|
12264
|
+
* @overload
|
|
12265
|
+
* @param {string} reason
|
|
12266
|
+
* @param {Point | Position | null | undefined} place
|
|
12267
|
+
* @param {string | null | undefined} [origin]
|
|
12268
|
+
* @returns {never}
|
|
12269
|
+
*
|
|
12270
|
+
* @overload
|
|
12271
|
+
* @param {string} reason
|
|
12272
|
+
* @param {string | null | undefined} [origin]
|
|
12273
|
+
* @returns {never}
|
|
12274
|
+
*
|
|
12275
|
+
* @overload
|
|
12276
|
+
* @param {Error | VFileMessage} cause
|
|
12277
|
+
* @param {Node | NodeLike | null | undefined} parent
|
|
12278
|
+
* @param {string | null | undefined} [origin]
|
|
12279
|
+
* @returns {never}
|
|
12280
|
+
*
|
|
12281
|
+
* @overload
|
|
12282
|
+
* @param {Error | VFileMessage} cause
|
|
12283
|
+
* @param {Point | Position | null | undefined} place
|
|
12284
|
+
* @param {string | null | undefined} [origin]
|
|
12285
|
+
* @returns {never}
|
|
12286
|
+
*
|
|
12287
|
+
* @overload
|
|
12288
|
+
* @param {Error | VFileMessage} cause
|
|
12289
|
+
* @param {string | null | undefined} [origin]
|
|
12290
|
+
* @returns {never}
|
|
12291
|
+
*
|
|
12292
|
+
* @param {Error | VFileMessage | string} causeOrReason
|
|
12293
|
+
* Reason for message, should use markdown.
|
|
12294
|
+
* @param {Node | NodeLike | MessageOptions | Point | Position | string | null | undefined} [optionsOrParentOrPlace]
|
|
12295
|
+
* Configuration (optional).
|
|
12296
|
+
* @param {string | null | undefined} [origin]
|
|
12297
|
+
* Place in code where the message originates (example:
|
|
12298
|
+
* `'my-package:my-rule'` or `'my-rule'`).
|
|
12299
|
+
* @returns {never}
|
|
12300
|
+
* Never.
|
|
12301
|
+
* @throws {VFileMessage}
|
|
12302
|
+
* Message.
|
|
12303
|
+
*/
|
|
12304
|
+
fail(causeOrReason, optionsOrParentOrPlace, origin) {
|
|
12305
|
+
const message = this.message(causeOrReason, optionsOrParentOrPlace, origin);
|
|
12306
|
+
message.fatal = true;
|
|
12307
|
+
throw message;
|
|
12308
|
+
}
|
|
12309
|
+
/**
|
|
12310
|
+
* Create an info message for `reason` associated with the file.
|
|
12311
|
+
*
|
|
12312
|
+
* The `fatal` field of the message is set to `undefined` (info; change
|
|
12313
|
+
* likely not needed) and the `file` field is set to the current file path.
|
|
12314
|
+
* The message is added to the `messages` field on `file`.
|
|
12315
|
+
*
|
|
12316
|
+
* > 🪦 **Note**: also has obsolete signatures.
|
|
12317
|
+
*
|
|
12318
|
+
* @overload
|
|
12319
|
+
* @param {string} reason
|
|
12320
|
+
* @param {MessageOptions | null | undefined} [options]
|
|
12321
|
+
* @returns {VFileMessage}
|
|
12322
|
+
*
|
|
12323
|
+
* @overload
|
|
12324
|
+
* @param {string} reason
|
|
12325
|
+
* @param {Node | NodeLike | null | undefined} parent
|
|
12326
|
+
* @param {string | null | undefined} [origin]
|
|
12327
|
+
* @returns {VFileMessage}
|
|
12328
|
+
*
|
|
12329
|
+
* @overload
|
|
12330
|
+
* @param {string} reason
|
|
12331
|
+
* @param {Point | Position | null | undefined} place
|
|
12332
|
+
* @param {string | null | undefined} [origin]
|
|
12333
|
+
* @returns {VFileMessage}
|
|
12334
|
+
*
|
|
12335
|
+
* @overload
|
|
12336
|
+
* @param {string} reason
|
|
12337
|
+
* @param {string | null | undefined} [origin]
|
|
12338
|
+
* @returns {VFileMessage}
|
|
12339
|
+
*
|
|
12340
|
+
* @overload
|
|
12341
|
+
* @param {Error | VFileMessage} cause
|
|
12342
|
+
* @param {Node | NodeLike | null | undefined} parent
|
|
12343
|
+
* @param {string | null | undefined} [origin]
|
|
12344
|
+
* @returns {VFileMessage}
|
|
12345
|
+
*
|
|
12346
|
+
* @overload
|
|
12347
|
+
* @param {Error | VFileMessage} cause
|
|
12348
|
+
* @param {Point | Position | null | undefined} place
|
|
12349
|
+
* @param {string | null | undefined} [origin]
|
|
12350
|
+
* @returns {VFileMessage}
|
|
12351
|
+
*
|
|
12352
|
+
* @overload
|
|
12353
|
+
* @param {Error | VFileMessage} cause
|
|
12354
|
+
* @param {string | null | undefined} [origin]
|
|
12355
|
+
* @returns {VFileMessage}
|
|
12356
|
+
*
|
|
12357
|
+
* @param {Error | VFileMessage | string} causeOrReason
|
|
12358
|
+
* Reason for message, should use markdown.
|
|
12359
|
+
* @param {Node | NodeLike | MessageOptions | Point | Position | string | null | undefined} [optionsOrParentOrPlace]
|
|
12360
|
+
* Configuration (optional).
|
|
12361
|
+
* @param {string | null | undefined} [origin]
|
|
12362
|
+
* Place in code where the message originates (example:
|
|
12363
|
+
* `'my-package:my-rule'` or `'my-rule'`).
|
|
12364
|
+
* @returns {VFileMessage}
|
|
12365
|
+
* Message.
|
|
12366
|
+
*/
|
|
12367
|
+
info(causeOrReason, optionsOrParentOrPlace, origin) {
|
|
12368
|
+
const message = this.message(causeOrReason, optionsOrParentOrPlace, origin);
|
|
12369
|
+
message.fatal = void 0;
|
|
12370
|
+
return message;
|
|
12371
|
+
}
|
|
12372
|
+
/**
|
|
12373
|
+
* Create a message for `reason` associated with the file.
|
|
12374
|
+
*
|
|
12375
|
+
* The `fatal` field of the message is set to `false` (warning; change may be
|
|
12376
|
+
* needed) and the `file` field is set to the current file path.
|
|
12377
|
+
* The message is added to the `messages` field on `file`.
|
|
12378
|
+
*
|
|
12379
|
+
* > 🪦 **Note**: also has obsolete signatures.
|
|
12380
|
+
*
|
|
12381
|
+
* @overload
|
|
12382
|
+
* @param {string} reason
|
|
12383
|
+
* @param {MessageOptions | null | undefined} [options]
|
|
12384
|
+
* @returns {VFileMessage}
|
|
12385
|
+
*
|
|
12386
|
+
* @overload
|
|
12387
|
+
* @param {string} reason
|
|
12388
|
+
* @param {Node | NodeLike | null | undefined} parent
|
|
12389
|
+
* @param {string | null | undefined} [origin]
|
|
12390
|
+
* @returns {VFileMessage}
|
|
12391
|
+
*
|
|
12392
|
+
* @overload
|
|
12393
|
+
* @param {string} reason
|
|
12394
|
+
* @param {Point | Position | null | undefined} place
|
|
12395
|
+
* @param {string | null | undefined} [origin]
|
|
12396
|
+
* @returns {VFileMessage}
|
|
12397
|
+
*
|
|
12398
|
+
* @overload
|
|
12399
|
+
* @param {string} reason
|
|
12400
|
+
* @param {string | null | undefined} [origin]
|
|
12401
|
+
* @returns {VFileMessage}
|
|
12402
|
+
*
|
|
12403
|
+
* @overload
|
|
12404
|
+
* @param {Error | VFileMessage} cause
|
|
12405
|
+
* @param {Node | NodeLike | null | undefined} parent
|
|
12406
|
+
* @param {string | null | undefined} [origin]
|
|
12407
|
+
* @returns {VFileMessage}
|
|
12408
|
+
*
|
|
12409
|
+
* @overload
|
|
12410
|
+
* @param {Error | VFileMessage} cause
|
|
12411
|
+
* @param {Point | Position | null | undefined} place
|
|
12412
|
+
* @param {string | null | undefined} [origin]
|
|
12413
|
+
* @returns {VFileMessage}
|
|
12414
|
+
*
|
|
12415
|
+
* @overload
|
|
12416
|
+
* @param {Error | VFileMessage} cause
|
|
12417
|
+
* @param {string | null | undefined} [origin]
|
|
12418
|
+
* @returns {VFileMessage}
|
|
12419
|
+
*
|
|
12420
|
+
* @param {Error | VFileMessage | string} causeOrReason
|
|
12421
|
+
* Reason for message, should use markdown.
|
|
12422
|
+
* @param {Node | NodeLike | MessageOptions | Point | Position | string | null | undefined} [optionsOrParentOrPlace]
|
|
12423
|
+
* Configuration (optional).
|
|
12424
|
+
* @param {string | null | undefined} [origin]
|
|
12425
|
+
* Place in code where the message originates (example:
|
|
12426
|
+
* `'my-package:my-rule'` or `'my-rule'`).
|
|
12427
|
+
* @returns {VFileMessage}
|
|
12428
|
+
* Message.
|
|
12429
|
+
*/
|
|
12430
|
+
message(causeOrReason, optionsOrParentOrPlace, origin) {
|
|
12431
|
+
const message = new VFileMessage(causeOrReason, optionsOrParentOrPlace, origin);
|
|
12432
|
+
if (this.path) {
|
|
12433
|
+
message.name = this.path + ":" + message.name;
|
|
12434
|
+
message.file = this.path;
|
|
12435
|
+
}
|
|
12436
|
+
message.fatal = false;
|
|
12437
|
+
this.messages.push(message);
|
|
12438
|
+
return message;
|
|
12439
|
+
}
|
|
12440
|
+
/**
|
|
12441
|
+
* Serialize the file.
|
|
12442
|
+
*
|
|
12443
|
+
* > **Note**: which encodings are supported depends on the engine.
|
|
12444
|
+
* > For info on Node.js, see:
|
|
12445
|
+
* > <https://nodejs.org/api/util.html#whatwg-supported-encodings>.
|
|
12446
|
+
*
|
|
12447
|
+
* @param {string | null | undefined} [encoding='utf8']
|
|
12448
|
+
* Character encoding to understand `value` as when it’s a `Uint8Array`
|
|
12449
|
+
* (default: `'utf-8'`).
|
|
12450
|
+
* @returns {string}
|
|
12451
|
+
* Serialized file.
|
|
12452
|
+
*/
|
|
12453
|
+
toString(encoding) {
|
|
12454
|
+
if (this.value === void 0) return "";
|
|
12455
|
+
if (typeof this.value === "string") return this.value;
|
|
12456
|
+
return new TextDecoder(encoding || void 0).decode(this.value);
|
|
12457
|
+
}
|
|
12458
|
+
};
|
|
12459
|
+
/**
|
|
12460
|
+
* Assert that `part` is not a path (as in, does not contain `path.sep`).
|
|
12461
|
+
*
|
|
12462
|
+
* @param {string | null | undefined} part
|
|
12463
|
+
* File path part.
|
|
12464
|
+
* @param {string} name
|
|
12465
|
+
* Part name.
|
|
12466
|
+
* @returns {undefined}
|
|
12467
|
+
* Nothing.
|
|
12468
|
+
*/
|
|
12469
|
+
function assertPart(part, name) {
|
|
12470
|
+
if (part && part.includes(node_path$1.default.sep)) throw new Error("`" + name + "` cannot be a path: did not expect `" + node_path$1.default.sep + "`");
|
|
12471
|
+
}
|
|
12472
|
+
/**
|
|
12473
|
+
* Assert that `part` is not empty.
|
|
12474
|
+
*
|
|
12475
|
+
* @param {string | undefined} part
|
|
12476
|
+
* Thing.
|
|
12477
|
+
* @param {string} name
|
|
12478
|
+
* Part name.
|
|
12479
|
+
* @returns {asserts part is string}
|
|
12480
|
+
* Nothing.
|
|
12481
|
+
*/
|
|
12482
|
+
function assertNonEmpty(part, name) {
|
|
12483
|
+
if (!part) throw new Error("`" + name + "` cannot be empty");
|
|
12484
|
+
}
|
|
12485
|
+
/**
|
|
12486
|
+
* Assert `path` exists.
|
|
12487
|
+
*
|
|
12488
|
+
* @param {string | undefined} path
|
|
12489
|
+
* Path.
|
|
12490
|
+
* @param {string} name
|
|
12491
|
+
* Dependency name.
|
|
12492
|
+
* @returns {asserts path is string}
|
|
12493
|
+
* Nothing.
|
|
12494
|
+
*/
|
|
12495
|
+
function assertPath(path, name) {
|
|
12496
|
+
if (!path) throw new Error("Setting `" + name + "` requires `path` to be set too");
|
|
12497
|
+
}
|
|
12498
|
+
/**
|
|
12499
|
+
* Assert `value` is an `Uint8Array`.
|
|
12500
|
+
*
|
|
12501
|
+
* @param {unknown} value
|
|
12502
|
+
* thing.
|
|
12503
|
+
* @returns {value is Uint8Array}
|
|
12504
|
+
* Whether `value` is an `Uint8Array`.
|
|
12505
|
+
*/
|
|
12506
|
+
function isUint8Array(value) {
|
|
12507
|
+
return Boolean(value && typeof value === "object" && "byteLength" in value && "byteOffset" in value);
|
|
12508
|
+
}
|
|
12509
|
+
//#endregion
|
|
11641
12510
|
//#region src/plugins/content/pipeline/frontmatter.ts
|
|
11642
12511
|
/**
|
|
11643
12512
|
* @file content pipeline — frontmatter parsing.
|
|
@@ -11808,7 +12677,7 @@ function parseDimensions(width, height) {
|
|
|
11808
12677
|
* collectAttributes({ src: "x", poster: "/p.jpg", flag: null }); // { src: "x", poster: "/p.jpg" }
|
|
11809
12678
|
* ```
|
|
11810
12679
|
*/
|
|
11811
|
-
function collectAttributes(attributes) {
|
|
12680
|
+
function collectAttributes$1(attributes) {
|
|
11812
12681
|
const out = {};
|
|
11813
12682
|
for (const [key, value] of Object.entries(attributes ?? {})) if (typeof value === "string") out[key] = value;
|
|
11814
12683
|
return out;
|
|
@@ -11881,7 +12750,7 @@ function embedTransform(facade, tree) {
|
|
|
11881
12750
|
width: dimensions.width,
|
|
11882
12751
|
height: dimensions.height
|
|
11883
12752
|
} : {},
|
|
11884
|
-
attributes: collectAttributes(node.attributes)
|
|
12753
|
+
attributes: collectAttributes$1(node.attributes)
|
|
11885
12754
|
}, dimensions)
|
|
11886
12755
|
};
|
|
11887
12756
|
parent.children[index] = html;
|
|
@@ -11907,6 +12776,246 @@ function embedPlugin(options = {}) {
|
|
|
11907
12776
|
return (tree) => embedTransform(facade, tree);
|
|
11908
12777
|
}
|
|
11909
12778
|
//#endregion
|
|
12779
|
+
//#region src/plugins/content/pipeline/gallery-default.tsx
|
|
12780
|
+
/** CSS class on the gallery's slide track. */
|
|
12781
|
+
const GALLERY_TRACK_CLASS = "gallery-track";
|
|
12782
|
+
/**
|
|
12783
|
+
* Default `::gallery` inner content: a single track holding every slide `<img>`
|
|
12784
|
+
* in folder order. A companion gallery island (consumer-provided) can enhance
|
|
12785
|
+
* the track with swipe/keyboard/lightbox; with no island and no CSS it is still
|
|
12786
|
+
* a plain horizontally-scrollable image strip. Provided as the default and as a
|
|
12787
|
+
* composable building block for custom galleries.
|
|
12788
|
+
*
|
|
12789
|
+
* @param props - The gallery props (the resolved `slides`).
|
|
12790
|
+
* @returns The gallery inner-content VNode.
|
|
12791
|
+
* @example
|
|
12792
|
+
* ```tsx
|
|
12793
|
+
* // Compose the default inside a richer custom gallery:
|
|
12794
|
+
* const MyGallery = (p: GalleryProps) => (
|
|
12795
|
+
* <figure><GalleryTrack {...p} /><figcaption>{p.caption}</figcaption></figure>
|
|
12796
|
+
* );
|
|
12797
|
+
* ```
|
|
12798
|
+
*/
|
|
12799
|
+
function GalleryTrack(props) {
|
|
12800
|
+
return /* @__PURE__ */ (0, preact_jsx_runtime.jsx)("div", {
|
|
12801
|
+
class: GALLERY_TRACK_CLASS,
|
|
12802
|
+
"data-gallery-track": true,
|
|
12803
|
+
children: props.slides.map((slide) => /* @__PURE__ */ (0, preact_jsx_runtime.jsx)("img", {
|
|
12804
|
+
src: slide.src,
|
|
12805
|
+
alt: slide.alt
|
|
12806
|
+
}, slide.src))
|
|
12807
|
+
});
|
|
12808
|
+
}
|
|
12809
|
+
//#endregion
|
|
12810
|
+
//#region src/plugins/content/pipeline/gallery.ts
|
|
12811
|
+
/**
|
|
12812
|
+
* @file content pipeline — `::gallery` folder galleries.
|
|
12813
|
+
*
|
|
12814
|
+
* Rewrites `::gallery{src="./images/dir/" caption="…"}` leaf directives into a
|
|
12815
|
+
* static swipeable image set at the mdast stage (BEFORE the remark-rehype bridge):
|
|
12816
|
+
* a framework-owned `<div class="gallery" data-component="gallery">` carrying the
|
|
12817
|
+
* island hook, wrapping inner content rendered (at build time, to static markup)
|
|
12818
|
+
* by a Preact component — the built-in {@link GalleryTrack} by default, or a
|
|
12819
|
+
* consumer component via `gallery.component`.
|
|
12820
|
+
*
|
|
12821
|
+
* Unlike `::embed` (one src resolved later by the provider), a gallery's `src` is a
|
|
12822
|
+
* co-located FOLDER that must be listed at build time, which needs the article's
|
|
12823
|
+
* source path. The provider supplies the article `slug` via the VFile `data`
|
|
12824
|
+
* (providers.ts), and the `contentDir` is bound at pipeline-build time — so this
|
|
12825
|
+
* transform reads `<contentDir>/<slug>/<src>` from disk, sorts its images, and
|
|
12826
|
+
* resolves each to its shared `/<slug>/<dir>/<file>` URL (identical from every
|
|
12827
|
+
* locale page, mirroring co-located images). The companion gallery SPA island
|
|
12828
|
+
* (consumer-provided) wires swipe/keyboard/lightbox on `[data-component="gallery"]`.
|
|
12829
|
+
*/
|
|
12830
|
+
/** CSS class on the `<div>` wrapping each gallery. */
|
|
12831
|
+
const GALLERY_WRAPPER_CLASS = "gallery";
|
|
12832
|
+
/** `data-component` name binding the gallery to its SPA island. */
|
|
12833
|
+
const GALLERY_COMPONENT_NAME = "gallery";
|
|
12834
|
+
/** Image file extensions a gallery folder expands over. */
|
|
12835
|
+
const IMAGE_EXTENSIONS = new Set([
|
|
12836
|
+
".webp",
|
|
12837
|
+
".jpg",
|
|
12838
|
+
".jpeg",
|
|
12839
|
+
".png",
|
|
12840
|
+
".gif",
|
|
12841
|
+
".avif"
|
|
12842
|
+
]);
|
|
12843
|
+
/**
|
|
12844
|
+
* Type guard for a `::gallery` leaf directive.
|
|
12845
|
+
*
|
|
12846
|
+
* @param node - AST node to test.
|
|
12847
|
+
* @returns `true` when the node is a `::gallery` leaf directive.
|
|
12848
|
+
* @example
|
|
12849
|
+
* ```ts
|
|
12850
|
+
* if (isGalleryDirective(node)) console.log(node.attributes?.src);
|
|
12851
|
+
* ```
|
|
12852
|
+
*/
|
|
12853
|
+
function isGalleryDirective(node) {
|
|
12854
|
+
return node.type === "leafDirective" && node.name === "gallery";
|
|
12855
|
+
}
|
|
12856
|
+
/**
|
|
12857
|
+
* Resolve `.`/`..` segments of a path built from `slug/src/file` into the single
|
|
12858
|
+
* shared absolute URL the content-assets build phase copies the folder to.
|
|
12859
|
+
*
|
|
12860
|
+
* @param slug - Article directory name.
|
|
12861
|
+
* @param src - The directive `src` (co-located relative folder, e.g. `./images/dir/`).
|
|
12862
|
+
* @param file - One image file name inside the folder.
|
|
12863
|
+
* @returns The shared absolute slide URL (`/<slug>/<dir>/<file>`).
|
|
12864
|
+
* @example
|
|
12865
|
+
* ```ts
|
|
12866
|
+
* slideUrl("post", "./images/mk/", "a.webp"); // "/post/images/mk/a.webp"
|
|
12867
|
+
* ```
|
|
12868
|
+
*/
|
|
12869
|
+
function slideUrl(slug, src, file) {
|
|
12870
|
+
const resolved = [];
|
|
12871
|
+
for (const segment of `${slug}/${src}/${file}`.split("/")) {
|
|
12872
|
+
if (segment === "" || segment === ".") continue;
|
|
12873
|
+
if (segment === "..") resolved.pop();
|
|
12874
|
+
else resolved.push(segment);
|
|
12875
|
+
}
|
|
12876
|
+
return `/${resolved.join("/")}`;
|
|
12877
|
+
}
|
|
12878
|
+
/**
|
|
12879
|
+
* Read a gallery folder from disk and build its sorted slide list. Each slide
|
|
12880
|
+
* gets the directive `caption` plus a ` · N` index suffix as alt (or just `N`).
|
|
12881
|
+
*
|
|
12882
|
+
* @param contentDir - The provider's content directory.
|
|
12883
|
+
* @param slug - Article directory name (from the VFile data).
|
|
12884
|
+
* @param src - The directive `src` (co-located relative folder).
|
|
12885
|
+
* @param caption - The directive `caption` attribute (may be empty).
|
|
12886
|
+
* @returns The sorted slides.
|
|
12887
|
+
* @throws {Error} When the folder is missing or holds no images.
|
|
12888
|
+
* @example
|
|
12889
|
+
* ```ts
|
|
12890
|
+
* resolveSlides("./content", "post", "./images/mk/", "Our game");
|
|
12891
|
+
* ```
|
|
12892
|
+
*/
|
|
12893
|
+
function resolveSlides(contentDir, slug, src, caption) {
|
|
12894
|
+
const folder = node_path$1.default.join(contentDir, slug, src);
|
|
12895
|
+
let entries;
|
|
12896
|
+
try {
|
|
12897
|
+
entries = (0, node_fs.readdirSync)(folder);
|
|
12898
|
+
} catch {
|
|
12899
|
+
throw new Error(`[web] content: \`::gallery\` folder not found: "${src}" (looked in ${folder}).`);
|
|
12900
|
+
}
|
|
12901
|
+
const files = entries.filter((name) => IMAGE_EXTENSIONS.has(node_path$1.default.extname(name).toLowerCase())).toSorted((a, b) => a.localeCompare(b, "en"));
|
|
12902
|
+
if (files.length === 0) throw new Error(`[web] content: \`::gallery\` folder has no images: "${src}" (${folder}).`);
|
|
12903
|
+
return files.map((file, index) => ({
|
|
12904
|
+
src: slideUrl(slug, src, file),
|
|
12905
|
+
alt: caption ? `${caption} · ${index + 1}` : `${index + 1}`
|
|
12906
|
+
}));
|
|
12907
|
+
}
|
|
12908
|
+
/**
|
|
12909
|
+
* Collect the directive's raw attribute bag into a plain string record, dropping
|
|
12910
|
+
* `null`/`undefined` values (so a custom component can read arbitrary extra options).
|
|
12911
|
+
*
|
|
12912
|
+
* @param attributes - The raw directive attributes (or undefined).
|
|
12913
|
+
* @returns A string-valued attribute record.
|
|
12914
|
+
* @example
|
|
12915
|
+
* ```ts
|
|
12916
|
+
* collectAttributes({ src: "x", layout: "dots", flag: null }); // { src: "x", layout: "dots" }
|
|
12917
|
+
* ```
|
|
12918
|
+
*/
|
|
12919
|
+
function collectAttributes(attributes) {
|
|
12920
|
+
const out = {};
|
|
12921
|
+
for (const [key, value] of Object.entries(attributes ?? {})) if (typeof value === "string") out[key] = value;
|
|
12922
|
+
return out;
|
|
12923
|
+
}
|
|
12924
|
+
/**
|
|
12925
|
+
* Build the static gallery HTML for one directive: the framework-owned `<div>`
|
|
12926
|
+
* (island hook in `data-component`) wrapping the component's inner content, SSR'd
|
|
12927
|
+
* to static markup.
|
|
12928
|
+
*
|
|
12929
|
+
* @param component - The gallery component (default {@link GalleryTrack}).
|
|
12930
|
+
* @param slides - The resolved slides.
|
|
12931
|
+
* @param caption - The directive `caption` attribute.
|
|
12932
|
+
* @param attributes - The raw directive attribute bag.
|
|
12933
|
+
* @returns The gallery HTML string.
|
|
12934
|
+
* @example
|
|
12935
|
+
* ```ts
|
|
12936
|
+
* galleryHtml(GalleryTrack, slides, "Our game", { src: "./images/mk/" });
|
|
12937
|
+
* ```
|
|
12938
|
+
*/
|
|
12939
|
+
function galleryHtml(component, slides, caption, attributes) {
|
|
12940
|
+
return `<div class="${GALLERY_WRAPPER_CLASS}" data-component="${GALLERY_COMPONENT_NAME}">${(0, preact_render_to_string.renderToString)((0, preact.h)(component, {
|
|
12941
|
+
slides,
|
|
12942
|
+
caption,
|
|
12943
|
+
attributes
|
|
12944
|
+
}))}</div>`;
|
|
12945
|
+
}
|
|
12946
|
+
/**
|
|
12947
|
+
* Mdast transformer rewriting every `::gallery` leaf directive to its gallery
|
|
12948
|
+
* HTML node. A directive missing `src`, or pointing at a missing/empty folder,
|
|
12949
|
+
* fails the build with the offending value quoted. Skipped entirely when the
|
|
12950
|
+
* VFile carries no `slug` (the standalone `render()` path has no article context).
|
|
12951
|
+
*
|
|
12952
|
+
* @param options - Resolved transform options (component + contentDir).
|
|
12953
|
+
* @param tree - The mdast tree to mutate.
|
|
12954
|
+
* @param file - The VFile (its `data.slug` locates the article on disk).
|
|
12955
|
+
* @throws {Error} When a `::gallery` directive is missing `src`, or its folder is
|
|
12956
|
+
* missing/empty.
|
|
12957
|
+
* @example
|
|
12958
|
+
* ```ts
|
|
12959
|
+
* galleryTransform({ component: GalleryTrack, contentDir: "./content" }, tree, file);
|
|
12960
|
+
* ```
|
|
12961
|
+
*/
|
|
12962
|
+
function galleryTransform(options, tree, file) {
|
|
12963
|
+
const slug = typeof file.data.slug === "string" ? file.data.slug : void 0;
|
|
12964
|
+
const component = options.component ?? GalleryTrack;
|
|
12965
|
+
(0, unist_util_visit.visit)(tree, (node, index, parent) => {
|
|
12966
|
+
if (!isGalleryDirective(node)) return;
|
|
12967
|
+
if (parent === void 0 || index === void 0) return;
|
|
12968
|
+
if (slug === void 0) return;
|
|
12969
|
+
const src = node.attributes?.src ?? "";
|
|
12970
|
+
if (src === "") throw new Error("[web] content: `::gallery` requires a `src` folder, e.g. ::gallery{src=\"./images/dir/\"}.");
|
|
12971
|
+
const caption = node.attributes?.caption ?? "";
|
|
12972
|
+
const html = {
|
|
12973
|
+
type: "html",
|
|
12974
|
+
value: galleryHtml(component, resolveSlides(options.contentDir, slug, src, caption), caption, collectAttributes(node.attributes))
|
|
12975
|
+
};
|
|
12976
|
+
parent.children[index] = html;
|
|
12977
|
+
});
|
|
12978
|
+
}
|
|
12979
|
+
/**
|
|
12980
|
+
* Normalize the provider's `gallery` config value (`boolean | options`) plus the
|
|
12981
|
+
* provider `contentDir` into the resolved {@link GalleryTransformOptions} the
|
|
12982
|
+
* transform factory needs.
|
|
12983
|
+
*
|
|
12984
|
+
* @param gallery - The raw `FileSystemContentOptions.gallery` value (truthy).
|
|
12985
|
+
* @param contentDir - The provider's content directory.
|
|
12986
|
+
* @returns The resolved transform options.
|
|
12987
|
+
* @example
|
|
12988
|
+
* ```ts
|
|
12989
|
+
* normalizeGalleryOptions(true, "./content"); // { contentDir: "./content" }
|
|
12990
|
+
* normalizeGalleryOptions({ component: MyGallery }, "./content");
|
|
12991
|
+
* ```
|
|
12992
|
+
*/
|
|
12993
|
+
function normalizeGalleryOptions(gallery, contentDir) {
|
|
12994
|
+
return typeof gallery === "boolean" ? { contentDir } : {
|
|
12995
|
+
...gallery,
|
|
12996
|
+
contentDir
|
|
12997
|
+
};
|
|
12998
|
+
}
|
|
12999
|
+
/**
|
|
13000
|
+
* Remark transform factory: rewrites `::gallery{src="…"}` leaf directives into
|
|
13001
|
+
* static swipeable galleries (see the file header). Opt-in via the provider's
|
|
13002
|
+
* `gallery` option; requires `trustedContent: true` because the markup is raw HTML
|
|
13003
|
+
* the sanitize pass would strip. The inner content is rendered by
|
|
13004
|
+
* `options.component` (a consumer Preact component) or the built-in
|
|
13005
|
+
* {@link GalleryTrack}; folders are read from `options.contentDir` against the
|
|
13006
|
+
* per-article `slug` on the VFile.
|
|
13007
|
+
*
|
|
13008
|
+
* @param options - Resolved transform options (component + contentDir).
|
|
13009
|
+
* @returns An mdast tree transformer.
|
|
13010
|
+
* @example
|
|
13011
|
+
* ```ts
|
|
13012
|
+
* unified().use(galleryPlugin, { component: MyGallery, contentDir: "./content" });
|
|
13013
|
+
* ```
|
|
13014
|
+
*/
|
|
13015
|
+
function galleryPlugin(options) {
|
|
13016
|
+
return (tree, file) => galleryTransform(options, tree, file);
|
|
13017
|
+
}
|
|
13018
|
+
//#endregion
|
|
11910
13019
|
//#region src/plugins/content/pipeline/mermaid.ts
|
|
11911
13020
|
/** CSS class on the `<figure>` wrapper around each rendered diagram. */
|
|
11912
13021
|
const MERMAID_FIGURE_CLASS = "mermaid-diagram";
|
|
@@ -12216,6 +13325,7 @@ function defaultRemarkPlugins(config) {
|
|
|
12216
13325
|
pullQuotePlugin
|
|
12217
13326
|
];
|
|
12218
13327
|
if (config?.embed) plugins.push([embedPlugin, normalizeEmbedOptions(config.embed)]);
|
|
13328
|
+
if (config?.gallery) plugins.push([galleryPlugin, normalizeGalleryOptions(config.gallery, config.contentDir)]);
|
|
12219
13329
|
if (config?.mermaid) plugins.push([remarkMermaidDiagrams, normalizeMermaidOptions(config.mermaid)]);
|
|
12220
13330
|
plugins.push([remark_rehype.default, { allowDangerousHtml: true }]);
|
|
12221
13331
|
return plugins;
|
|
@@ -12617,7 +13727,10 @@ function fileSystemContent(options) {
|
|
|
12617
13727
|
state.dirtyPaths.delete(filePath);
|
|
12618
13728
|
const { frontmatter, body } = parseFrontmatter(raw, options);
|
|
12619
13729
|
const processor = ensureProcessor(state, options);
|
|
12620
|
-
const html = rewriteEmbedUrls(rewriteImageUrls(String(await processor.process(
|
|
13730
|
+
const html = rewriteEmbedUrls(rewriteImageUrls(String(await processor.process(new VFile({
|
|
13731
|
+
value: body,
|
|
13732
|
+
data: { slug }
|
|
13733
|
+
}))), slug), slug);
|
|
12621
13734
|
const { readingTime, wordCount } = calculateReadingTime(body);
|
|
12622
13735
|
return {
|
|
12623
13736
|
frontmatter,
|
|
@@ -12778,6 +13891,7 @@ Object.defineProperty(exports, "Env", {
|
|
|
12778
13891
|
return types_exports$5;
|
|
12779
13892
|
}
|
|
12780
13893
|
});
|
|
13894
|
+
exports.GalleryTrack = GalleryTrack;
|
|
12781
13895
|
Object.defineProperty(exports, "Head", {
|
|
12782
13896
|
enumerable: true,
|
|
12783
13897
|
get: function() {
|