diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 29e83aa..bbc412d 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -45,9 +45,24 @@ jobs: - run: pnpm install --frozen-lockfile + - name: Validate docs links + run: pnpm docs:check-links + + - name: Validate learning-path docs structure + run: pnpm docs:verify-learning-path + + - name: Run release evidence unit tests + run: pnpm release-evidence:test + + - name: Validate README quickstart script wiring + run: node tools/release-evidence/verify-readme-quickstart.mjs --skip-install --skip-emsdk-setup --skip-smoke-tests --skip-browser-tasks --skip-evidence + - name: Install emsdk (pinned 3.1.56) run: bash tools/scripts/setup-emsdk.sh + - name: Verify generated gas schedule docs are in sync + run: node tools/gas-spec/render-gas-artifacts.mjs --check + - name: Reset Nx state (just in case) run: pnpm exec nx reset @@ -57,8 +72,24 @@ jobs: # - run: pnpm exec nx-cloud record -- echo Hello World - run: pnpm exec nx affected -t lint test build typecheck - - name: Install Playwright browsers (Chromium) - run: pnpm exec playwright install --with-deps chromium + - name: Verify generated playground data is fresh + run: pnpm playground:check-generated + + - name: Install Playwright browsers (Chromium + Firefox) + run: pnpm exec playwright install --with-deps chromium firefox - name: Run smoke-web e2e run: pnpm nx run smoke-web:e2e + + - name: Run ecosystem certifier e2e + run: pnpm nx run ecosystem-certifier:e2e + + - name: Run BlueQuickjs playground e2e + run: pnpm nx run bluequickjs-playground:e2e + + - name: Generate workload certification sanity artifacts + run: | + node apps/ecosystem-certifier/scripts/check-builder-determinism.mjs --out-dir artifacts/workload-certification-ci + node apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs --out-dir artifacts/workload-certification-ci + node apps/ecosystem-certifier/scripts/run-oog-boundary-certification.mjs --out-dir artifacts/workload-certification-ci --fixtures green-semver,green-markdown-it + node apps/ecosystem-certifier/scripts/run-seeded-property-corpus.mjs --out-dir artifacts/workload-certification-ci --seed-count 12 diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index f178e05..11dc343 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -17,7 +17,7 @@ jobs: release: name: Release runs-on: ubuntu-latest - timeout-minutes: 10 + timeout-minutes: 45 steps: - name: Checkout repository uses: actions/checkout@v4 @@ -51,9 +51,153 @@ jobs: - name: Install emsdk (pinned 3.1.56) run: bash tools/scripts/setup-emsdk.sh + - name: Verify generated gas schedule docs are in sync + run: node tools/gas-spec/render-gas-artifacts.mjs --check + + - name: Verify learning-path docs + run: | + pnpm docs:verify-learning-path + + - name: Generate SBOM and dependency license reports + run: | + pnpm release-evidence:sbom -- --out-dir artifacts/security + pnpm release-evidence:licenses -- --out-dir artifacts/security + + - name: Install Playwright browsers (Chromium + Firefox) + run: pnpm exec playwright install --with-deps chromium firefox + - name: Print Environment Info run: pnpm exec nx report + - name: Run strict parity release gates (consensus executors) + run: | + pnpm nx test quickjs-runtime + pnpm nx test smoke-node + pnpm nx test test-harness + pnpm nx test bluequickjs-playground + pnpm nx run smoke-web:e2e + pnpm nx test ecosystem-certifier + pnpm nx run ecosystem-certifier:e2e + pnpm nx run bluequickjs-playground:e2e + + - name: Generate consensus reproducibility report artifacts (Chromium + Firefox) + run: | + node tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs --out-dir artifacts/reproducibility-consensus/chromium --browser chromium + node tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs --out-dir artifacts/reproducibility-consensus/firefox --browser firefox + + - name: Generate workload certification artifacts + run: | + node apps/ecosystem-certifier/scripts/check-builder-determinism.mjs --out-dir artifacts/workload-certification + node apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs --out-dir artifacts/workload-certification + node apps/ecosystem-certifier/scripts/generate-compatibility-delta-report.mjs --current-dir artifacts/workload-certification --out-dir artifacts/workload-certification + node apps/ecosystem-certifier/scripts/run-oog-boundary-certification.mjs --out-dir artifacts/workload-certification + node apps/ecosystem-certifier/scripts/run-seeded-property-corpus.mjs --out-dir artifacts/workload-certification --seed-count 80 + node apps/ecosystem-certifier/scripts/run-repeatability-certification.mjs --out-dir artifacts/workload-certification --iterations 100 --flagship-iterations 40 + + - name: Validate public package release alignment + run: | + pnpm workload:check-public-package-versions + pnpm workload:check-pack-manifests -- --out-dir artifacts/consumer-proof/pack-manifests + + - name: Run Verdaccio publish/install rehearsal (primary) + run: pnpm publish-rehearsal:verdaccio -- --out-dir artifacts/consumer-proof/verdaccio + + - name: Generate downstream tarball reproducibility artifacts (secondary) + run: | + node tools/workload-certification/pack-public-tarballs.mjs --out-dir artifacts/consumer-proof/tarballs + pnpm --dir e2e/consumer-proof-app run install:tarballs -- --tarball-dir ../../artifacts/consumer-proof/tarballs + pnpm --dir e2e/consumer-proof-app exec playwright install --with-deps chromium + pnpm --dir e2e/consumer-proof-app run repro + + - name: Run native diagnostics (non-blocking) + continue-on-error: true + run: | + pnpm nx build quickjs-native-harness + pnpm nx test quickjs-native-harness + + - name: Generate native diagnostic reproducibility report artifact (non-blocking) + continue-on-error: true + run: node tools/quickjs-native-harness/scripts/archive-reproducibility-report.mjs + + - name: Synthesize release evidence bundle + run: pnpm release-evidence:synthesize -- --out-dir artifacts/release-evidence + + - name: Validate generated release evidence and docs freshness + run: | + EXPECTED_DATE=$(node -e "const fs=require('fs');console.log(JSON.parse(fs.readFileSync('artifacts/release-evidence/release-evidence-manifest.json','utf8')).date)") + pnpm docs:check-links + pnpm docs:verify-learning-path + pnpm docs:check-freshness -- --expected-branch "${GITHUB_REF_NAME}" --expected-date "${EXPECTED_DATE}" + pnpm playground:check-generated + pnpm release-evidence:synthesize -- --out-dir artifacts/release-evidence --check + pnpm release-evidence:verify -- --evidence-dir artifacts/release-evidence --expected-branch "${GITHUB_REF_NAME}" --expected-date "${EXPECTED_DATE}" + + - name: Upload reproducibility artifacts + uses: actions/upload-artifact@v4 + with: + name: consensus-reproducibility-report + path: | + artifacts/reproducibility-consensus/**/*.json* + artifacts/reproducibility-consensus/**/*.md* + artifacts/reproducibility-consensus/**/*.sig + if-no-files-found: error + + - name: Upload native diagnostic reproducibility artifacts + uses: actions/upload-artifact@v4 + with: + name: native-diagnostic-reproducibility-report + path: | + artifacts/reproducibility/*.json* + artifacts/reproducibility/*.md* + artifacts/reproducibility/*.sig + if-no-files-found: warn + + - name: Upload workload certification artifacts + uses: actions/upload-artifact@v4 + with: + name: workload-certification-artifacts + path: artifacts/workload-certification/* + if-no-files-found: error + + - name: Upload consumer-proof artifacts + uses: actions/upload-artifact@v4 + with: + name: consumer-proof-artifacts + path: | + artifacts/consumer-proof/tarballs/tarball-manifest.json + artifacts/consumer-proof/pack-manifests/pack-manifest.json + artifacts/consumer-proof/verdaccio/*.json + artifacts/consumer-proof/verdaccio/*.log + e2e/consumer-proof-app/reports/*.json* + if-no-files-found: error + + - name: Upload release evidence bundle + uses: actions/upload-artifact@v4 + with: + name: release-evidence-bundle + path: | + artifacts/release-evidence/release-evidence-summary.json + artifacts/release-evidence/release-evidence-summary.json.sha256 + artifacts/release-evidence/release-evidence-summary.json.sig + artifacts/release-evidence/release-evidence-summary.md + artifacts/release-evidence/release-evidence-summary.md.sha256 + artifacts/release-evidence/release-evidence-summary.md.sig + artifacts/release-evidence/release-evidence-manifest.json + artifacts/release-evidence/release-evidence-manifest.json.sha256 + artifacts/release-evidence/release-evidence-manifest.json.sig + artifacts/release-evidence/inputs/* + if-no-files-found: error + + - name: Upload security artifacts + uses: actions/upload-artifact@v4 + with: + name: release-security-artifacts + path: | + artifacts/security/sbom.cdx.json + artifacts/security/license-report.json + artifacts/security/license-report.md + if-no-files-found: error + - name: Configure Git run: | git config --global user.email "github-actions[bot]@users.noreply.github.com" @@ -63,3 +207,48 @@ jobs: - name: Release run: pnpm exec nx release --skip-publish --first-release shell: bash + + verify-release-evidence: + name: Verify release evidence bundle + runs-on: ubuntu-latest + needs: + - release + steps: + - uses: actions/checkout@v4 + with: + fetch-depth: 0 + submodules: recursive + + - uses: pnpm/action-setup@v4 + with: + version: 9.8.0 + run_install: false + + - uses: actions/setup-node@v4 + with: + node-version-file: '.nvmrc' + cache: 'pnpm' + + - name: Install dependencies + run: pnpm install --frozen-lockfile + + - name: Download release evidence bundle + uses: actions/download-artifact@v4 + with: + name: release-evidence-bundle + path: artifacts/release-evidence + + - name: Verify evidence checksums and signatures + run: | + EXPECTED_DATE=$(node -e "const fs=require('fs');console.log(JSON.parse(fs.readFileSync('artifacts/release-evidence/release-evidence-manifest.json','utf8')).date)") + pnpm release-evidence:verify -- --evidence-dir artifacts/release-evidence --expected-branch "${GITHUB_REF_NAME}" --expected-date "${EXPECTED_DATE}" + + - name: Assert tamper detection fails verification + run: | + cp -R artifacts/release-evidence artifacts/release-evidence-tampered + node -e "const fs=require('fs');fs.appendFileSync('artifacts/release-evidence-tampered/inputs/consumer-reproducibility.json','\n')" + EXPECTED_DATE=$(node -e "const fs=require('fs');console.log(JSON.parse(fs.readFileSync('artifacts/release-evidence-tampered/release-evidence-manifest.json','utf8')).date)") + if pnpm release-evidence:verify -- --evidence-dir artifacts/release-evidence-tampered --expected-branch "${GITHUB_REF_NAME}" --expected-date "${EXPECTED_DATE}"; then + echo "tamper verification unexpectedly passed" + exit 1 + fi diff --git a/.github/workflows/workload-certification.yml b/.github/workflows/workload-certification.yml new file mode 100644 index 0000000..61bb971 --- /dev/null +++ b/.github/workflows/workload-certification.yml @@ -0,0 +1,295 @@ +name: Workload Certification + +on: + pull_request: + workflow_dispatch: + schedule: + - cron: '0 5 * * *' + +permissions: + actions: read + contents: read + +jobs: + certifier-browser-matrix: + name: Certifier (Linux parity, ${{ matrix.browser }}) + runs-on: ubuntu-latest + strategy: + fail-fast: false + matrix: + browser: + - chromium + - firefox + timeout-minutes: 45 + steps: + - uses: actions/checkout@v4 + with: + fetch-depth: 0 + submodules: recursive + + - uses: pnpm/action-setup@v4 + with: + version: 9.8.0 + run_install: false + + - uses: actions/setup-node@v4 + with: + node-version-file: '.nvmrc' + cache: 'pnpm' + + - name: Cache emsdk + uses: actions/cache@v4 + with: + path: tools/emsdk + key: emsdk-${{ runner.os }}-${{ hashFiles('tools/scripts/emsdk-version.txt') }} + + - name: Install dependencies + run: pnpm install --frozen-lockfile + + - name: Install emsdk + run: bash tools/scripts/setup-emsdk.sh + + - name: Install Playwright browser + run: pnpm exec playwright install --with-deps ${{ matrix.browser }} + + - name: Run ecosystem certifier tests + run: | + pnpm nx test ecosystem-certifier + pnpm nx run ecosystem-certifier:e2e + + - name: Generate workload certification artifacts + run: | + ITERATIONS=50 + FLAGSHIP_ITERATIONS=20 + SEED_COUNT=40 + if [ "${{ github.event_name }}" = "schedule" ] && [ "${{ matrix.browser }}" = "chromium" ]; then + ITERATIONS=100 + FLAGSHIP_ITERATIONS=40 + SEED_COUNT=120 + fi + node apps/ecosystem-certifier/scripts/check-builder-determinism.mjs --out-dir artifacts/workload-certification + node apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs --out-dir artifacts/workload-certification --browser ${{ matrix.browser }} + node apps/ecosystem-certifier/scripts/generate-compatibility-delta-report.mjs --current-dir artifacts/workload-certification --out-dir artifacts/workload-certification + node apps/ecosystem-certifier/scripts/run-oog-boundary-certification.mjs --out-dir artifacts/workload-certification --browser ${{ matrix.browser }} + node apps/ecosystem-certifier/scripts/run-seeded-property-corpus.mjs --out-dir artifacts/workload-certification --seed-count "${SEED_COUNT}" --browser ${{ matrix.browser }} + node apps/ecosystem-certifier/scripts/run-repeatability-certification.mjs --out-dir artifacts/workload-certification --iterations "${ITERATIONS}" --flagship-iterations "${FLAGSHIP_ITERATIONS}" --browser ${{ matrix.browser }} + + - name: Upload workload certification artifacts + uses: actions/upload-artifact@v4 + with: + name: workload-certification-${{ matrix.browser }}-artifacts + path: artifacts/workload-certification/* + if-no-files-found: error + + certifier-webkit-diagnostic: + name: Certifier (Linux diagnostic, webkit) + if: github.event_name == 'schedule' || github.event_name == 'workflow_dispatch' + runs-on: ubuntu-latest + timeout-minutes: 45 + continue-on-error: true + steps: + - uses: actions/checkout@v4 + with: + fetch-depth: 0 + submodules: recursive + + - uses: pnpm/action-setup@v4 + with: + version: 9.8.0 + run_install: false + + - uses: actions/setup-node@v4 + with: + node-version-file: '.nvmrc' + cache: 'pnpm' + + - name: Cache emsdk + uses: actions/cache@v4 + with: + path: tools/emsdk + key: emsdk-${{ runner.os }}-${{ hashFiles('tools/scripts/emsdk-version.txt') }} + + - name: Install dependencies + run: pnpm install --frozen-lockfile + + - name: Install emsdk + run: bash tools/scripts/setup-emsdk.sh + + - name: Install Playwright browser (WebKit) + run: pnpm exec playwright install --with-deps webkit + + - name: Run webkit diagnostic workload report + run: node apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs --out-dir artifacts/workload-certification-webkit --browser webkit + + - name: Upload webkit diagnostic artifacts + uses: actions/upload-artifact@v4 + with: + name: workload-certification-webkit-diagnostic-artifacts + path: artifacts/workload-certification-webkit/* + if-no-files-found: warn + + consumer-proof-matrix: + name: Consumer proof (${{ matrix.os }}, node${{ matrix.node }}) + runs-on: ${{ matrix.os }} + strategy: + fail-fast: false + matrix: + os: + - ubuntu-latest + - windows-latest + node: + - 20 + - 22 + timeout-minutes: 35 + steps: + - uses: actions/checkout@v4 + with: + fetch-depth: 0 + submodules: recursive + + - uses: pnpm/action-setup@v4 + with: + version: 9.8.0 + run_install: false + + - uses: actions/setup-node@v4 + with: + node-version: ${{ matrix.node }} + cache: 'pnpm' + + - name: Install dependencies + run: pnpm install --frozen-lockfile + + - name: Pack public tarballs + run: node tools/workload-certification/pack-public-tarballs.mjs --out-dir artifacts/consumer-proof/tarballs + + - name: Validate public package version alignment + run: pnpm workload:check-public-package-versions + + - name: Validate npm pack manifests + run: pnpm workload:check-pack-manifests -- --out-dir artifacts/consumer-proof/pack-manifests + + - name: Install tarballs in consumer app + run: pnpm --dir e2e/consumer-proof-app run install:tarballs -- --tarball-dir ../../artifacts/consumer-proof/tarballs + + - name: Install Playwright browser (Linux) + if: matrix.os == 'ubuntu-latest' + run: pnpm --dir e2e/consumer-proof-app exec playwright install --with-deps chromium + + - name: Install Playwright browser (non-Linux) + if: matrix.os != 'ubuntu-latest' + run: pnpm --dir e2e/consumer-proof-app exec playwright install chromium + + - name: Run consumer reproducibility proof + run: pnpm --dir e2e/consumer-proof-app run repro + + - name: Upload consumer-proof matrix artifacts + uses: actions/upload-artifact@v4 + with: + name: consumer-proof-${{ matrix.os }}-node${{ matrix.node }}-artifacts + path: | + artifacts/consumer-proof/tarballs/tarball-manifest.json + artifacts/consumer-proof/pack-manifests/pack-manifest.json + e2e/consumer-proof-app/reports/*.json* + if-no-files-found: error + + publish-rehearsal-verdaccio: + name: Publish rehearsal (Verdaccio) + runs-on: ubuntu-latest + timeout-minutes: 45 + steps: + - uses: actions/checkout@v4 + with: + fetch-depth: 0 + submodules: recursive + + - uses: pnpm/action-setup@v4 + with: + version: 9.8.0 + run_install: false + + - uses: actions/setup-node@v4 + with: + node-version: 22 + cache: 'pnpm' + + - name: Install dependencies + run: pnpm install --frozen-lockfile + + - name: Run Verdaccio publish/install rehearsal + run: pnpm publish-rehearsal:verdaccio -- --out-dir artifacts/consumer-proof/verdaccio + + - name: Upload Verdaccio rehearsal artifacts + uses: actions/upload-artifact@v4 + with: + name: consumer-proof-verdaccio-rehearsal-artifacts + path: | + artifacts/consumer-proof/verdaccio/*.json + artifacts/consumer-proof/verdaccio/*.log + e2e/consumer-proof-app/reports/*.json* + if-no-files-found: error + + builder-determinism-matrix: + name: Builder determinism (${{ matrix.os }}) + runs-on: ${{ matrix.os }} + strategy: + fail-fast: false + matrix: + os: + - ubuntu-latest + - macos-latest + - windows-latest + timeout-minutes: 20 + steps: + - uses: actions/checkout@v4 + with: + fetch-depth: 0 + + - uses: pnpm/action-setup@v4 + with: + version: 9.8.0 + run_install: false + + - uses: actions/setup-node@v4 + with: + node-version-file: '.nvmrc' + cache: 'pnpm' + + - name: Install dependencies + run: pnpm install --frozen-lockfile + + - name: Run builder path determinism check + run: node apps/ecosystem-certifier/scripts/check-builder-determinism.mjs --out-dir artifacts/workload-certification-matrix + + - name: Upload builder determinism artifact + uses: actions/upload-artifact@v4 + with: + name: builder-determinism-${{ matrix.os }}-artifacts + path: artifacts/workload-certification-matrix/* + if-no-files-found: error + + builder-determinism-compare: + name: Compare builder determinism matrix + runs-on: ubuntu-latest + needs: + - builder-determinism-matrix + steps: + - uses: actions/checkout@v4 + with: + fetch-depth: 0 + + - uses: actions/download-artifact@v4 + with: + pattern: builder-determinism-* + path: artifacts/workload-certification-matrix + merge-multiple: false + + - name: Compare matrix reports + run: node tools/workload-certification/compare-builder-determinism-matrix.mjs --input-dir artifacts/workload-certification-matrix > artifacts/workload-certification-matrix-comparison.json + + - name: Upload matrix comparison artifact + uses: actions/upload-artifact@v4 + with: + name: builder-determinism-matrix-comparison + path: artifacts/workload-certification-matrix-comparison.json + if-no-files-found: error diff --git a/.gitignore b/.gitignore index 19e2874..aea96ef 100644 --- a/.gitignore +++ b/.gitignore @@ -48,4 +48,14 @@ Thumbs.db vite.config.*.timestamp* vitest.config.*.timestamp* -.repomix \ No newline at end of file +.repomix + +# Playwright outputs +test-results +playwright-report + +# Downstream consumer proof outputs +e2e/consumer-proof-app/node_modules/ +e2e/consumer-proof-app/reports/ +e2e/consumer-proof-app/package-lock.json +artifacts/ \ No newline at end of file diff --git a/.verdaccio/config.yml b/.verdaccio/config.yml index f74420f..96049fa 100644 --- a/.verdaccio/config.yml +++ b/.verdaccio/config.yml @@ -8,6 +8,11 @@ uplinks: maxage: 60m packages: + '@blue-quickjs/*': + access: $all + publish: $all + unpublish: $all + '**': # give all users (including non-authenticated users) full access # because it is a local registry diff --git a/CHANGELOG.md b/CHANGELOG.md index 8b14f8b..8b48e53 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,29 @@ +## 0.5.0-rc.0 (2026-03-19) + +### 🚀 Features + +- **release-policy:** promote strict gas/OOG parity to release-critical + consensus contract for `wasm-node` vs `wasm-browser`. +- **ecosystem-certifier:** add flagship workload certification, deterministic + green/red compatibility matrix, builder determinism evidence, and downstream + consumer-proof integration. +- **ecosystem-certifier:** expand green corpus to 25 fixtures, add + compatibility delta reporting, and raise repeatability/seeded workload + intensity for release/nightly runs. +- **release-workflow:** run strict consensus parity gates and archive workload + + consumer evidence artifacts in release workflow. +- **playground:** add an in-repo BlueQuickjs playground backed by generated + certified examples, red fixtures, and OOG boundary data. + +### 📚 Documentation + +- Promote README into a product/release landing page with consensus-safe scope, + execution profiles, and quickstart. +- Add architecture overview, guided learning path, glossary/FAQ/support pages, + and playground docs. +- Refresh docs index, head verification note, and release-facing checklists for + release-readiness and verification-oriented navigation. + ## 0.4.1 (2026-03-13) ### 🚀 Features diff --git a/README.md b/README.md index dc9a1d5..10c213e 100644 --- a/README.md +++ b/README.md @@ -1,10 +1,144 @@ # BlueQuickjs -Deterministic QuickJS-in-Wasm evaluator monorepo (Nx + pnpm), tracking a hardened QuickJS fork and SDK/tooling to run it. +BlueQuickjs is a deterministic JavaScript execution stack built on a hardened +QuickJS engine compiled to Wasm. It is designed for **consensus-critical +execution** where independent runtimes must agree on: + +- value or error, +- gas used and gas remaining, +- host-call tape, +- exact out-of-gas boundaries. + +## Consensus-safe scope + +Current consensus-safe release scope is intentionally explicit: + +- **consensus executors:** `wasm-node` vs `wasm-browser` +- **canonical engine:** `wasm32` release artifact only +- **release-critical parity:** exact + - value/error parity, + - gas used parity, + - gas remaining parity, + - host-call tape parity, + - OOG boundary parity +- **native status:** diagnostic-only unless separately promoted by policy + +Use these docs for the current release contract: + +- [Consensus-safe vs diagnostic-only](docs/consensus-safe-vs-diagnostic-only.md) +- [Release policy](docs/release-policy.md) +- [HEAD verification note](docs/head-verification-note.md) + +## What “deterministic” means here + +For a fixed program artifact `P`, input envelope `I`, and gas limit `G`, +BlueQuickjs expects the same consensus executors to produce the same: + +- result bytes or deterministic error, +- gas accounting, +- host-call tape, +- OOG transition point. + +That is why the product centers on pinned artifacts, profiles, manifests, and +generated evidence instead of ad hoc runtime behavior. + +## Execution profiles + +| Profile | Purpose | Deterministic capability scope | +| --- | --- | --- | +| `baseline-v1` | Minimal consensus baseline | No Promise jobs/microtasks, no typed arrays/ArrayBuffer/DataView, no dynamic import/time/random/fs/network | +| `compat-general-v1` | Real-world JS compatibility | `baseline-v1` + deterministic RegExp + Promise jobs + `queueMicrotask` + deterministic console shim + stable sort | +| `compat-binary-v1` | Binary-heavy deterministic workloads | `compat-general-v1` + typed arrays/ArrayBuffer/DataView + DV2 bytes boundary | + +Profile details: + +- [`docs/execution-profiles.md`](docs/execution-profiles.md) +- [`docs/determinism-profile.md`](docs/determinism-profile.md) + +## 5-step first-success path + +1. **Install dependencies + the pinned Wasm toolchain** + + ```bash + pnpm install + git submodule update --init --recursive vendor/quickjs + bash tools/scripts/setup-emsdk.sh + source tools/emsdk/emsdk_env.sh + ``` + +2. **Run the current consensus smoke checks** + + ```bash + pnpm exec playwright install --with-deps chromium + source tools/emsdk/emsdk_env.sh + pnpm nx test smoke-node + pnpm nx run smoke-web:e2e + ``` + +3. **Generate parity and certification evidence** + + ```bash + source tools/emsdk/emsdk_env.sh + node tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs --out-dir artifacts/reproducibility-consensus + node apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs --out-dir artifacts/workload-certification + ``` + +4. **Verify the release evidence bundle** + + ```bash + pnpm release-evidence:synthesize -- --out-dir artifacts/release-evidence + pnpm release-evidence:verify -- --evidence-dir artifacts/release-evidence + ``` + +5. **Open the in-repo browser playground** + + ```bash + bash apps/bluequickjs-playground/scripts/dev.sh + ``` + +## Start here + +### Learn the product + +- [Documentation hub](docs/README.md) +- [Learning path](docs/learn/README.md) +- [Architecture overview](docs/architecture-overview.md) +- [Examples corpus](examples/README.md) +- [Glossary](docs/glossary.md) +- [FAQ](docs/faq.md) + +### Use the product + +- [Playground](docs/playground.md) +- [Playground recipes](docs/playground-recipes.md) +- [TypeScript SDK usage](docs/sdk.md) +- [Production embedder checklist](docs/production-embedder-checklist.md) + +### Trust and verify the product + +- [HEAD verification snapshot](docs/head-verification-note.md) +- [Workload certification](docs/workload-certification.md) +- [Ecosystem compatibility report](docs/ecosystem-compatibility-report.md) +- [Release-readiness report](docs/release-readiness-report.md) +- [Release checklist](docs/release-checklist.md) + +## Consumer and operator proof paths + +BlueQuickjs already exercises both public-consumer rehearsal flows: + +- **tarball flow** — pack public tarballs and install them into the consumer + proof app +- **registry/Verdaccio rehearsal flow** — publish to a local registry and run + the same consumer proof against that path + +See: + +- [Workload certification](docs/workload-certification.md) +- [Release checklist](docs/release-checklist.md) ## QuickJS fork -- Submodule at `vendor/quickjs` (origin `git@blue.github.com:mjwebblue/quickjs.git`). +- Submodule at `vendor/quickjs` (origin `git@github.com:bluecontract/quickjs.git`). - Fresh checkout: `git submodule update --init --recursive`. - Update the pin after landing changes in the fork: `cd vendor/quickjs && git fetch origin && git checkout ` then `cd .. && git add vendor/quickjs && git commit -m "chore: bump quickjs submodule"`. - Do QuickJS edits in the fork repository and only commit the pinned SHA here. @@ -18,25 +152,15 @@ Deterministic QuickJS-in-Wasm evaluator monorepo (Nx + pnpm), tracking a hardene ## Toolchain -- Emscripten is pinned to `3.1.56`; install via `tools/scripts/setup-emsdk.sh`, then `source tools/emsdk/emsdk_env.sh`. See `docs/toolchain.md` for details and CI cache notes. - -## Docs - -- Baselines (start here): - - Baseline #1 — Deterministic execution + canonical gas: `docs/baseline-1.md` - - Baseline #2 — Host ABI (manifest-locked) + DV wire format: `docs/baseline-2.md` -- Determinism profile: `docs/determinism-profile.md` -- Gas schedule: `docs/gas-schedule.md` -- DV wire format: `docs/dv-wire-format.md` -- ABI manifest: `docs/abi-manifest.md` -- Host call ABI: `docs/host-call-abi.md` -- Release policy: `docs/release-policy.md` -- Release checklist: `docs/release-checklist.md` +- Emscripten is pinned to `3.1.56`; install via `tools/scripts/setup-emsdk.sh`, + then `source tools/emsdk/emsdk_env.sh`. See `docs/toolchain.md` for details + and CI cache notes. ## Determinism checklist -- Same `(P, I, G)` yields identical result bytes, gas used/remaining, and host-call tape hashes across Node and browser. -- Deterministic capability profile: time/random/async/IO/typed arrays/WebAssembly disabled; use `Host.v1` for IO (`docs/determinism-profile.md`). -- Canonical gas: opcode/builtin/allocation/GC charges plus two-phase host-call gas (`docs/gas-schedule.md`). -- DV and manifest: canonical DV encoding, safe numeric range, sorted keys, size caps, manifest hash pinning (`docs/dv-wire-format.md`, `docs/abi-manifest.md`). -- Host ABI: `host_call` envelope, deterministic error mapping, and reentrancy rules (`docs/host-call-abi.md`). +- Same `(P, I, G)` yields identical result bytes, gas used/remaining, and + host-call tape hashes across Node and browser. +- Deterministic capability profiles enforce explicit contracts per profile. +- Canonical gas is metered inside the engine, including host-call gas. +- DV and manifest hashes pin the host boundary contract. +- Release evidence is generated and verified, not hand-maintained. diff --git a/apps/bluequickjs-playground/eslint.config.mjs b/apps/bluequickjs-playground/eslint.config.mjs new file mode 100644 index 0000000..0232736 --- /dev/null +++ b/apps/bluequickjs-playground/eslint.config.mjs @@ -0,0 +1,8 @@ +import baseConfig from '../../eslint.config.mjs'; + +export default [ + ...baseConfig, + { + ignores: ['**/out-tsc'], + }, +]; diff --git a/apps/bluequickjs-playground/index.html b/apps/bluequickjs-playground/index.html new file mode 100644 index 0000000..0f552ce --- /dev/null +++ b/apps/bluequickjs-playground/index.html @@ -0,0 +1,12 @@ + + + + + + BlueQuickjs Playground + + +
Loading BlueQuickjs Playground…
+ + + diff --git a/apps/bluequickjs-playground/package.json b/apps/bluequickjs-playground/package.json new file mode 100644 index 0000000..50f7d50 --- /dev/null +++ b/apps/bluequickjs-playground/package.json @@ -0,0 +1,46 @@ +{ + "name": "@blue-quickjs/bluequickjs-playground", + "version": "0.0.1", + "type": "module", + "private": true, + "dependencies": { + "@blue-quickjs/abi-manifest": "workspace:*", + "@blue-quickjs/deterministic-builder": "workspace:*", + "@blue-quickjs/dv": "workspace:*", + "@blue-quickjs/execution-profiles": "workspace:*", + "@blue-quickjs/quickjs-runtime": "workspace:*", + "@blue-quickjs/quickjs-wasm": "workspace:*", + "@blue-quickjs/test-harness": "workspace:*", + "monaco-editor": "^0.55.1", + "tslib": "^2.3.0" + }, + "nx": { + "name": "bluequickjs-playground", + "targets": { + "e2e": { + "dependsOn": [ + "^build" + ], + "executor": "nx:run-commands", + "options": { + "command": "pnpm playwright test apps/bluequickjs-playground/tests --config apps/bluequickjs-playground/playwright.config.cts", + "cwd": "." + } + }, + "generate-data": { + "executor": "nx:run-commands", + "options": { + "command": "node apps/bluequickjs-playground/scripts/generate-playground-data.mjs", + "cwd": "." + } + }, + "check-generated": { + "executor": "nx:run-commands", + "options": { + "command": "node apps/bluequickjs-playground/scripts/generate-playground-data.mjs --check", + "cwd": "." + } + } + } + } +} diff --git a/apps/bluequickjs-playground/playwright.config.cts b/apps/bluequickjs-playground/playwright.config.cts new file mode 100644 index 0000000..3f80282 --- /dev/null +++ b/apps/bluequickjs-playground/playwright.config.cts @@ -0,0 +1,30 @@ +import { defineConfig } from '@playwright/test'; + +const projectRoot = __dirname; + +export default defineConfig({ + testDir: './tests', + fullyParallel: false, + timeout: 120000, + use: { + headless: true, + baseURL: 'http://localhost:4325', + }, + projects: [ + { + name: 'chromium', + use: { browserName: 'chromium' }, + }, + { + name: 'firefox', + use: { browserName: 'firefox' }, + }, + ], + webServer: { + command: 'pnpm vite --host --port 4325 --config vite.config.mts', + cwd: projectRoot, + url: 'http://localhost:4325', + reuseExistingServer: !process.env.CI, + timeout: 120000, + }, +}); diff --git a/apps/bluequickjs-playground/public/generated/playground-evidence.json b/apps/bluequickjs-playground/public/generated/playground-evidence.json new file mode 100644 index 0000000..fbaf827 --- /dev/null +++ b/apps/bluequickjs-playground/public/generated/playground-evidence.json @@ -0,0 +1,287 @@ +{ + "generatedAt": "current-worktree", + "metadata": { + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8 + }, + "evidence": { + "example-basic-script": { + "stage": "success", + "resultHash": "4bf5122f344554c53bde2ebb8cd2b7e3d1600ad631c385a5d7cce23c7785459a", + "errorCode": null, + "errorTag": null, + "gasUsed": "74", + "gasRemaining": "999926", + "tapeHash": null, + "tapeLength": 0, + "certified": true, + "reportSource": "examples/01-basic-script", + "fixtureCoverage": [ + { + "suite": "gas-sample", + "fixtureName": "return-1" + } + ] + }, + "example-module-pack": { + "stage": "success", + "resultHash": "ca358758f6d27e6cf45272937977a748fd88391db679ceda7dc7bf1f005ee879", + "errorCode": null, + "errorTag": null, + "gasUsed": "147", + "gasRemaining": "49853", + "tapeHash": null, + "tapeLength": 0, + "certified": true, + "reportSource": "examples/02-module-pack", + "fixtureCoverage": [ + { + "suite": "module-pack", + "fixtureName": "module-pack-default-export" + } + ] + }, + "example-library-reuse": { + "stage": "success", + "resultHash": "2017ff3461395672aa0aa4f64894fd2f95a4b120e2690e8951656d79adc2eed2", + "errorCode": null, + "errorTag": null, + "gasUsed": "2070505", + "gasRemaining": "2929495", + "tapeHash": null, + "tapeLength": 0, + "certified": true, + "reportSource": "examples/03-library-reuse", + "fixtureCoverage": [ + { + "suite": "chess-library", + "fixtureName": "chess-e2e6" + }, + { + "suite": "binary-library", + "fixtureName": "base64-js-roundtrip" + }, + { + "suite": "binary-library", + "fixtureName": "noble-sha256-hex" + } + ] + }, + "example-promises-async": { + "stage": "success", + "resultHash": "7f83f7bda2d63959d34767689f06d47576683d378d9eb8d09386c9a020395c53", + "errorCode": null, + "errorTag": null, + "gasUsed": "128", + "gasRemaining": "49872", + "tapeHash": null, + "tapeLength": 0, + "certified": true, + "reportSource": "examples/04-promises-async", + "fixtureCoverage": [ + { + "suite": "determinism", + "fixtureName": "async-promise-chain" + } + ] + }, + "example-promises-library-host": { + "stage": "success", + "resultHash": "7f83f7bda2d63959d34767689f06d47576683d378d9eb8d09386c9a020395c53", + "errorCode": null, + "errorTag": null, + "gasUsed": "290", + "gasRemaining": "99710", + "tapeHash": "a60c7561730c64206ffefbef8a581959560436b8e06f481d25131684ce529790", + "tapeLength": 1, + "certified": true, + "reportSource": "examples/05-promises-library-host", + "fixtureCoverage": [ + { + "suite": "module-pack", + "fixtureName": "module-pack-async-import-host-call" + } + ] + }, + "example-binary-host-v2": { + "stage": "success", + "resultHash": "a538717d219fa0484c601ef7b5b63704c90cb9ae0406495b9f0083989a9fb2f8", + "errorCode": null, + "errorTag": null, + "gasUsed": "253", + "gasRemaining": "49747", + "tapeHash": "b2d3a3b07a1be6b39cd854077910a2bc839c281281275c2c137f6a704723a734", + "tapeLength": 2, + "certified": true, + "reportSource": "examples/06-binary-host-v2", + "fixtureCoverage": [ + { + "suite": "determinism", + "fixtureName": "compat-binary-host-v2-bytes-roundtrip" + } + ] + }, + "example-console-shim": { + "stage": "success", + "resultHash": "20a934991093b3d9bfcb5f3c05871eb1db002d19469c29ea3ae1ff7e4a29cd02", + "errorCode": null, + "errorTag": null, + "gasUsed": "139", + "gasRemaining": "49861", + "tapeHash": "c481a1396ab5097cc8aa68fd11c1bb6e96d63259dba00b560bf49489fe5b2e3f", + "tapeLength": 1, + "certified": true, + "reportSource": "examples/07-console-shim", + "fixtureCoverage": [ + { + "suite": "determinism", + "fixtureName": "compat-console-shim" + } + ] + }, + "example-stable-sort": { + "stage": "success", + "resultHash": "950f57b0bb4280b09b5a63004acc9c50811ca16cea7c932494f47cb3cfb23c04", + "errorCode": null, + "errorTag": null, + "gasUsed": "1020", + "gasRemaining": "98980", + "tapeHash": null, + "tapeLength": 0, + "certified": true, + "reportSource": "examples/08-stable-sort", + "fixtureCoverage": [ + { + "suite": "determinism", + "fixtureName": "compat-stable-sort" + } + ] + }, + "example-kitchen-sink": { + "stage": "success", + "resultHash": "81c484749a779eed55f5556d116e42d167df403c6800f9a543228d459d2cee75", + "errorCode": null, + "errorTag": null, + "gasUsed": "1390", + "gasRemaining": "198610", + "tapeHash": "39a88fa80e264d1836759dd547e397ea79508e761caea5b4e393f9aeeb5cdee3", + "tapeLength": 3, + "certified": true, + "reportSource": "examples/09-kitchen-sink", + "fixtureCoverage": [ + { + "suite": "module-pack", + "fixtureName": "module-pack-kitchen-sink" + } + ] + }, + "example-max-gas-policy": { + "stage": "success", + "resultHash": "a3fa3495623f19996818ce7b196fc524e687ef2cc4910a6ff628a76460c4e557", + "errorCode": null, + "errorTag": null, + "gasUsed": "170099", + "gasRemaining": "829901", + "tapeHash": null, + "tapeLength": 0, + "certified": true, + "reportSource": "examples/10-max-gas-policy", + "fixtureCoverage": [ + { + "suite": "gas-boundary", + "fixtureName": "loop-10k" + } + ] + }, + "green-semver": { + "stage": "success", + "resultHash": "0f772d5874a1d5da187a42d18a36eef020a8a20be43e106cccd6b35bd7589913", + "errorCode": null, + "errorTag": null, + "gasUsed": "36886", + "gasRemaining": "963114", + "tapeHash": "cb2a385dddf91f104061c25073236d1518b4d87ff10a4c8a40deda856410deb0", + "tapeLength": 1, + "certified": true, + "reportSource": "ecosystem-certifier:green-semver", + "fixtureCoverage": [ + { + "suite": "ecosystem-certifier", + "fixtureName": "green-semver" + } + ] + }, + "green-base64": { + "stage": "success", + "resultHash": "87dbcca4f5403c38f1d4259ba4d152240ab993b6d54d2bc5be615294634398d2", + "errorCode": null, + "errorTag": null, + "gasUsed": "3378", + "gasRemaining": "4996622", + "tapeHash": null, + "tapeLength": 0, + "certified": true, + "reportSource": "ecosystem-certifier:green-base64", + "fixtureCoverage": [ + { + "suite": "ecosystem-certifier", + "fixtureName": "green-base64" + } + ] + }, + "green-markdown-it": { + "stage": "success", + "resultHash": "e066b59858afb2601fec42a0a29527508545e9e21b84770d5dfb092d70da85d0", + "errorCode": null, + "errorTag": null, + "gasUsed": "212292", + "gasRemaining": "787708", + "tapeHash": "c8bebb3029ad855bc4972ad0a6de535daf1b7f13e1ca3ddbd458038afb4f2904", + "tapeLength": 1, + "certified": true, + "reportSource": "ecosystem-certifier:green-markdown-it", + "fixtureCoverage": [ + { + "suite": "ecosystem-certifier", + "fixtureName": "green-markdown-it" + } + ] + }, + "green-noble-sha": { + "stage": "success", + "resultHash": "137c77da6a39cb7439836094805726f43751c3d4df281f9268ba4bf03b523afd", + "errorCode": null, + "errorTag": null, + "gasUsed": "25631", + "gasRemaining": "4974369", + "tapeHash": null, + "tapeLength": 0, + "certified": true, + "reportSource": "ecosystem-certifier:green-noble-sha", + "fixtureCoverage": [ + { + "suite": "ecosystem-certifier", + "fixtureName": "green-noble-sha" + } + ] + }, + "flagship-knowledge-pack": { + "stage": "success", + "resultHash": "098e33e655dc8d5539e5628bcb03649cc952103b12ebd942a99e5dba0e2417b8", + "errorCode": null, + "errorTag": null, + "gasUsed": "3280236", + "gasRemaining": "4719764", + "tapeHash": "1f5a6804fd52594adfbab5c3292076aeeaec340c2232eb7cdbe5d90dfd1560b7", + "tapeLength": 12, + "certified": true, + "reportSource": "ecosystem-certifier:flagship-knowledge-pack", + "fixtureCoverage": [ + { + "suite": "ecosystem-certifier", + "fixtureName": "flagship-knowledge-pack" + } + ] + } + } +} diff --git a/apps/bluequickjs-playground/public/generated/playground-examples.json b/apps/bluequickjs-playground/public/generated/playground-examples.json new file mode 100644 index 0000000..cbd6ce2 --- /dev/null +++ b/apps/bluequickjs-playground/public/generated/playground-examples.json @@ -0,0 +1,3054 @@ +{ + "generatedAt": "current-worktree", + "metadata": { + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8, + "wasmVariant": "wasm32", + "wasmBuildType": "release" + }, + "examples": [ + { + "id": "example-basic-script", + "title": "Basic deterministic script", + "kind": "example", + "badge": "Example 1", + "description": "Smallest possible deterministic script-mode example.", + "certified": true, + "executionProfile": "baseline-v1", + "sourceKind": "script", + "abiId": "Host.v1", + "gasLimit": "1000000", + "sourcePaths": [ + "examples/01-basic-script/program.js" + ], + "sourceText": "(() => 1)();\n", + "hostPreset": "determinism", + "hostSummary": { + "label": "Determinism fixture host", + "description": "Provides stable Host.v1/Host.v2 document responses plus deterministic emit tape capture.", + "documents": [ + "path/to/doc", + "path/to/canonical", + "path/to/first", + "path/to/second", + "path/to/third", + "bytes/payload" + ] + }, + "docsLinks": [ + { + "label": "Learn path", + "href": "/docs/learn/README.md" + }, + { + "label": "Examples corpus", + "href": "/examples/README.md" + } + ], + "supportsOogSearch": true, + "program": { + "version": 2, + "abiId": "Host.v1", + "abiVersion": 1, + "abiManifestHash": "e23b0b2ee169900bbde7aff78e6ce20fead1715c60f8a8e3106d9959450a3d34", + "executionProfile": "baseline-v1", + "sourceKind": "script", + "source": { + "code": "(() => 1)();\n" + }, + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8 + }, + "manifest": { + "abi_id": "Host.v1", + "abi_version": 1, + "functions": [ + { + "fn_id": 1, + "js_path": [ + "document", + "get" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 2, + "js_path": [ + "document", + "getCanonical" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 3, + "js_path": [ + "emit" + ], + "effect": "EMIT", + "arity": 1, + "arg_schema": [ + { + "type": "dv" + } + ], + "return_schema": { + "type": "null" + }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [ + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + } + ] + } + ] + } + }, + { + "id": "example-module-pack", + "title": "Standard ESM module-pack", + "kind": "example", + "badge": "Example 2", + "description": "Static ESM module-pack example with a deterministic graph hash.", + "certified": true, + "executionProfile": "baseline-v1", + "sourceKind": "module-pack", + "abiId": "Host.v1", + "gasLimit": "50000", + "sourcePaths": [ + "examples/02-module-pack/entry.js", + "examples/02-module-pack/values.js" + ], + "sourceText": "import { base } from './values.js';\n\nexport default base + 1;\n", + "hostPreset": "determinism", + "hostSummary": { + "label": "Determinism fixture host", + "description": "Provides stable Host.v1/Host.v2 document responses plus deterministic emit tape capture.", + "documents": [ + "path/to/doc", + "path/to/canonical", + "path/to/first", + "path/to/second", + "path/to/third", + "bytes/payload" + ] + }, + "docsLinks": [ + { + "label": "Learn path", + "href": "/docs/learn/README.md" + }, + { + "label": "Examples corpus", + "href": "/examples/README.md" + }, + { + "label": "Module packs", + "href": "/docs/learn/03-module-packs-and-imports.md" + } + ], + "supportsOogSearch": true, + "program": { + "version": 2, + "abiId": "Host.v1", + "abiVersion": 1, + "abiManifestHash": "e23b0b2ee169900bbde7aff78e6ce20fead1715c60f8a8e3106d9959450a3d34", + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8, + "executionProfile": "baseline-v1", + "sourceKind": "module-pack", + "source": { + "modulePack": { + "version": 1, + "entrySpecifier": "./entry.js", + "entryExport": "default", + "modules": [ + { + "specifier": "./entry.js", + "source": "// examples/02-module-pack/values.js\nvar base = 6;\n\n// examples/02-module-pack/entry.js\nvar entry_default = base + 1;\nexport {\n entry_default as default\n};\n", + "sourceMap": "{\"mappings\":\";AAAO,IAAM,OAAO;;;ACEpB,IAAO,gBAAQ,OAAO;\",\"names\":[],\"sources\":[\"../examples/02-module-pack/values.js\",\"../examples/02-module-pack/entry.js\"],\"sourcesContent\":[\"export const base = 6;\\n\",\"import { base } from './values.js';\\n\\nexport default base + 1;\\n\"],\"version\":3}", + "originMeta": { + "originalPath": "examples/02-module-pack/entry.js" + } + } + ], + "builderVersion": "deterministic-builder-v1", + "dependencyIntegrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562", + "diagnosticsMeta": { + "entryPath": "/workspace/examples/02-module-pack/entry.js", + "modulePaths": [ + "./entry.js" + ] + }, + "graphHash": "73f5f34c3f965a90d50b923534cb9afd11cbcee8e9b28111724f1b5c73e7c712" + } + } + }, + "manifest": { + "abi_id": "Host.v1", + "abi_version": 1, + "functions": [ + { + "fn_id": 1, + "js_path": [ + "document", + "get" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 2, + "js_path": [ + "document", + "getCanonical" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 3, + "js_path": [ + "emit" + ], + "effect": "EMIT", + "arity": 1, + "arg_schema": [ + { + "type": "dv" + } + ], + "return_schema": { + "type": "null" + }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [ + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + } + ] + } + ] + } + }, + { + "id": "example-library-reuse", + "title": "Real npm library reuse", + "kind": "example", + "badge": "Example 3", + "description": "Real library reuse through a deterministic module-pack instead of runtime imports. The binary base64 companion source remains listed alongside the chess.js entry for comparison.", + "certified": true, + "executionProfile": "compat-general-v1", + "sourceKind": "module-pack", + "abiId": "Host.v1", + "gasLimit": "5000000", + "sourcePaths": [ + "examples/03-library-reuse/chess-entry.ts", + "examples/03-library-reuse/binary-base64-entry.ts" + ], + "sourceText": "import { Chess } from 'chess.js';\n\nconst game = new Chess();\ngame.move('e4');\ngame.move('e5');\n\nexport default game.move('e2e6') !== null;\n", + "hostPreset": "determinism", + "hostSummary": { + "label": "Determinism fixture host", + "description": "Provides stable Host.v1/Host.v2 document responses plus deterministic emit tape capture.", + "documents": [ + "path/to/doc", + "path/to/canonical", + "path/to/first", + "path/to/second", + "path/to/third", + "bytes/payload" + ] + }, + "docsLinks": [ + { + "label": "Learn path", + "href": "/docs/learn/README.md" + }, + { + "label": "Examples corpus", + "href": "/examples/README.md" + } + ], + "supportsOogSearch": true, + "program": { + "version": 2, + "abiId": "Host.v1", + "abiVersion": 1, + "abiManifestHash": "e23b0b2ee169900bbde7aff78e6ce20fead1715c60f8a8e3106d9959450a3d34", + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8, + "executionProfile": "compat-general-v1", + "sourceKind": "module-pack", + "source": { + "modulePack": { + "version": 1, + "entrySpecifier": "./chess-entry.js", + "entryExport": "default", + "modules": [ + { + "specifier": "./chess-entry.js", + "source": "var __defProp = Object.defineProperty;\nvar __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;\nvar __publicField = (obj, key, value) => __defNormalProp(obj, typeof key !== \"symbol\" ? key + \"\" : key, value);\n\n// node_modules/.pnpm/chess.js@1.4.0/node_modules/chess.js/dist/esm/chess.js\nfunction rootNode(comment) {\n return comment !== null ? { comment, variations: [] } : { variations: [] };\n}\nfunction node(move, suffix, nag, comment, variations) {\n const node2 = { move, variations };\n if (suffix) {\n node2.suffix = suffix;\n }\n if (nag) {\n node2.nag = nag;\n }\n if (comment !== null) {\n node2.comment = comment;\n }\n return node2;\n}\nfunction lineToTree(...nodes) {\n const [root, ...rest] = nodes;\n let parent = root;\n for (const child of rest) {\n if (child !== null) {\n parent.variations = [child, ...child.variations];\n child.variations = [];\n parent = child;\n }\n }\n return root;\n}\nfunction pgn(headers, game) {\n if (game.marker && game.marker.comment) {\n let node2 = game.root;\n while (true) {\n const next = node2.variations[0];\n if (!next) {\n node2.comment = game.marker.comment;\n break;\n }\n node2 = next;\n }\n }\n return {\n headers,\n root: game.root,\n result: (game.marker && game.marker.result) ?? void 0\n };\n}\nfunction peg$subclass(child, parent) {\n function C() {\n this.constructor = child;\n }\n C.prototype = parent.prototype;\n child.prototype = new C();\n}\nfunction peg$SyntaxError(message, expected, found, location) {\n var self = Error.call(this, message);\n if (Object.setPrototypeOf) {\n Object.setPrototypeOf(self, peg$SyntaxError.prototype);\n }\n self.expected = expected;\n self.found = found;\n self.location = location;\n self.name = \"SyntaxError\";\n return self;\n}\npeg$subclass(peg$SyntaxError, Error);\nfunction peg$padEnd(str, targetLength, padString) {\n padString = padString || \" \";\n if (str.length > targetLength) {\n return str;\n }\n targetLength -= str.length;\n padString += padString.repeat(targetLength);\n return str + padString.slice(0, targetLength);\n}\npeg$SyntaxError.prototype.format = function(sources) {\n var str = \"Error: \" + this.message;\n if (this.location) {\n var src = null;\n var k;\n for (k = 0; k < sources.length; k++) {\n if (sources[k].source === this.location.source) {\n src = sources[k].text.split(/\\r\\n|\\n|\\r/g);\n break;\n }\n }\n var s = this.location.start;\n var offset_s = this.location.source && typeof this.location.source.offset === \"function\" ? this.location.source.offset(s) : s;\n var loc = this.location.source + \":\" + offset_s.line + \":\" + offset_s.column;\n if (src) {\n var e = this.location.end;\n var filler = peg$padEnd(\"\", offset_s.line.toString().length, \" \");\n var line = src[s.line - 1];\n var last = s.line === e.line ? e.column : line.length + 1;\n var hatLen = last - s.column || 1;\n str += \"\\n --> \" + loc + \"\\n\" + filler + \" |\\n\" + offset_s.line + \" | \" + line + \"\\n\" + filler + \" | \" + peg$padEnd(\"\", s.column - 1, \" \") + peg$padEnd(\"\", hatLen, \"^\");\n } else {\n str += \"\\n at \" + loc;\n }\n }\n return str;\n};\npeg$SyntaxError.buildMessage = function(expected, found) {\n var DESCRIBE_EXPECTATION_FNS = {\n literal: function(expectation) {\n return '\"' + literalEscape(expectation.text) + '\"';\n },\n class: function(expectation) {\n var escapedParts = expectation.parts.map(function(part) {\n return Array.isArray(part) ? classEscape(part[0]) + \"-\" + classEscape(part[1]) : classEscape(part);\n });\n return \"[\" + (expectation.inverted ? \"^\" : \"\") + escapedParts.join(\"\") + \"]\";\n },\n any: function() {\n return \"any character\";\n },\n end: function() {\n return \"end of input\";\n },\n other: function(expectation) {\n return expectation.description;\n }\n };\n function hex(ch) {\n return ch.charCodeAt(0).toString(16).toUpperCase();\n }\n function literalEscape(s) {\n return s.replace(/\\\\/g, \"\\\\\\\\\").replace(/\"/g, '\\\\\"').replace(/\\0/g, \"\\\\0\").replace(/\\t/g, \"\\\\t\").replace(/\\n/g, \"\\\\n\").replace(/\\r/g, \"\\\\r\").replace(/[\\x00-\\x0F]/g, function(ch) {\n return \"\\\\x0\" + hex(ch);\n }).replace(/[\\x10-\\x1F\\x7F-\\x9F]/g, function(ch) {\n return \"\\\\x\" + hex(ch);\n });\n }\n function classEscape(s) {\n return s.replace(/\\\\/g, \"\\\\\\\\\").replace(/\\]/g, \"\\\\]\").replace(/\\^/g, \"\\\\^\").replace(/-/g, \"\\\\-\").replace(/\\0/g, \"\\\\0\").replace(/\\t/g, \"\\\\t\").replace(/\\n/g, \"\\\\n\").replace(/\\r/g, \"\\\\r\").replace(/[\\x00-\\x0F]/g, function(ch) {\n return \"\\\\x0\" + hex(ch);\n }).replace(/[\\x10-\\x1F\\x7F-\\x9F]/g, function(ch) {\n return \"\\\\x\" + hex(ch);\n });\n }\n function describeExpectation(expectation) {\n return DESCRIBE_EXPECTATION_FNS[expectation.type](expectation);\n }\n function describeExpected(expected2) {\n var descriptions = expected2.map(describeExpectation);\n var i, j;\n descriptions.sort();\n if (descriptions.length > 0) {\n for (i = 1, j = 1; i < descriptions.length; i++) {\n if (descriptions[i - 1] !== descriptions[i]) {\n descriptions[j] = descriptions[i];\n j++;\n }\n }\n descriptions.length = j;\n }\n switch (descriptions.length) {\n case 1:\n return descriptions[0];\n case 2:\n return descriptions[0] + \" or \" + descriptions[1];\n default:\n return descriptions.slice(0, -1).join(\", \") + \", or \" + descriptions[descriptions.length - 1];\n }\n }\n function describeFound(found2) {\n return found2 ? '\"' + literalEscape(found2) + '\"' : \"end of input\";\n }\n return \"Expected \" + describeExpected(expected) + \" but \" + describeFound(found) + \" found.\";\n};\nfunction peg$parse(input, options) {\n options = options !== void 0 ? options : {};\n var peg$FAILED = {};\n var peg$source = options.grammarSource;\n var peg$startRuleFunctions = { pgn: peg$parsepgn };\n var peg$startRuleFunction = peg$parsepgn;\n var peg$c0 = \"[\";\n var peg$c1 = '\"';\n var peg$c2 = \"]\";\n var peg$c3 = \".\";\n var peg$c4 = \"O-O-O\";\n var peg$c5 = \"O-O\";\n var peg$c6 = \"0-0-0\";\n var peg$c7 = \"0-0\";\n var peg$c8 = \"$\";\n var peg$c9 = \"{\";\n var peg$c10 = \"}\";\n var peg$c11 = \";\";\n var peg$c12 = \"(\";\n var peg$c13 = \")\";\n var peg$c14 = \"1-0\";\n var peg$c15 = \"0-1\";\n var peg$c16 = \"1/2-1/2\";\n var peg$c17 = \"*\";\n var peg$r0 = /^[a-zA-Z]/;\n var peg$r1 = /^[^\"]/;\n var peg$r2 = /^[0-9]/;\n var peg$r3 = /^[.]/;\n var peg$r4 = /^[a-zA-Z1-8\\-=]/;\n var peg$r5 = /^[+#]/;\n var peg$r6 = /^[!?]/;\n var peg$r7 = /^[^}]/;\n var peg$r8 = /^[^\\r\\n]/;\n var peg$r9 = /^[ \\t\\r\\n]/;\n var peg$e0 = peg$otherExpectation(\"tag pair\");\n var peg$e1 = peg$literalExpectation(\"[\", false);\n var peg$e2 = peg$literalExpectation('\"', false);\n var peg$e3 = peg$literalExpectation(\"]\", false);\n var peg$e4 = peg$otherExpectation(\"tag name\");\n var peg$e5 = peg$classExpectation([[\"a\", \"z\"], [\"A\", \"Z\"]], false, false);\n var peg$e6 = peg$otherExpectation(\"tag value\");\n var peg$e7 = peg$classExpectation(['\"'], true, false);\n var peg$e8 = peg$otherExpectation(\"move number\");\n var peg$e9 = peg$classExpectation([[\"0\", \"9\"]], false, false);\n var peg$e10 = peg$literalExpectation(\".\", false);\n var peg$e11 = peg$classExpectation([\".\"], false, false);\n var peg$e12 = peg$otherExpectation(\"standard algebraic notation\");\n var peg$e13 = peg$literalExpectation(\"O-O-O\", false);\n var peg$e14 = peg$literalExpectation(\"O-O\", false);\n var peg$e15 = peg$literalExpectation(\"0-0-0\", false);\n var peg$e16 = peg$literalExpectation(\"0-0\", false);\n var peg$e17 = peg$classExpectation([[\"a\", \"z\"], [\"A\", \"Z\"], [\"1\", \"8\"], \"-\", \"=\"], false, false);\n var peg$e18 = peg$classExpectation([\"+\", \"#\"], false, false);\n var peg$e19 = peg$otherExpectation(\"suffix annotation\");\n var peg$e20 = peg$classExpectation([\"!\", \"?\"], false, false);\n var peg$e21 = peg$otherExpectation(\"NAG\");\n var peg$e22 = peg$literalExpectation(\"$\", false);\n var peg$e23 = peg$otherExpectation(\"brace comment\");\n var peg$e24 = peg$literalExpectation(\"{\", false);\n var peg$e25 = peg$classExpectation([\"}\"], true, false);\n var peg$e26 = peg$literalExpectation(\"}\", false);\n var peg$e27 = peg$otherExpectation(\"rest of line comment\");\n var peg$e28 = peg$literalExpectation(\";\", false);\n var peg$e29 = peg$classExpectation([\"\\r\", \"\\n\"], true, false);\n var peg$e30 = peg$otherExpectation(\"variation\");\n var peg$e31 = peg$literalExpectation(\"(\", false);\n var peg$e32 = peg$literalExpectation(\")\", false);\n var peg$e33 = peg$otherExpectation(\"game termination marker\");\n var peg$e34 = peg$literalExpectation(\"1-0\", false);\n var peg$e35 = peg$literalExpectation(\"0-1\", false);\n var peg$e36 = peg$literalExpectation(\"1/2-1/2\", false);\n var peg$e37 = peg$literalExpectation(\"*\", false);\n var peg$e38 = peg$otherExpectation(\"whitespace\");\n var peg$e39 = peg$classExpectation([\" \", \"\t\", \"\\r\", \"\\n\"], false, false);\n var peg$f0 = function(headers, game) {\n return pgn(headers, game);\n };\n var peg$f1 = function(tagPairs) {\n return Object.fromEntries(tagPairs);\n };\n var peg$f2 = function(tagName, tagValue) {\n return [tagName, tagValue];\n };\n var peg$f3 = function(root, marker) {\n return { root, marker };\n };\n var peg$f4 = function(comment, moves) {\n return lineToTree(rootNode(comment), ...moves.flat());\n };\n var peg$f5 = function(san, suffix, nag, comment, variations) {\n return node(san, suffix, nag, comment, variations);\n };\n var peg$f6 = function(nag) {\n return nag;\n };\n var peg$f7 = function(comment) {\n return comment.replace(/[\\r\\n]+/g, \" \");\n };\n var peg$f8 = function(comment) {\n return comment.trim();\n };\n var peg$f9 = function(line) {\n return line;\n };\n var peg$f10 = function(result, comment) {\n return { result, comment };\n };\n var peg$currPos = options.peg$currPos | 0;\n var peg$posDetailsCache = [{ line: 1, column: 1 }];\n var peg$maxFailPos = peg$currPos;\n var peg$maxFailExpected = options.peg$maxFailExpected || [];\n var peg$silentFails = options.peg$silentFails | 0;\n var peg$result;\n if (options.startRule) {\n if (!(options.startRule in peg$startRuleFunctions)) {\n throw new Error(`Can't start parsing from rule \"` + options.startRule + '\".');\n }\n peg$startRuleFunction = peg$startRuleFunctions[options.startRule];\n }\n function peg$literalExpectation(text, ignoreCase) {\n return { type: \"literal\", text, ignoreCase };\n }\n function peg$classExpectation(parts, inverted, ignoreCase) {\n return { type: \"class\", parts, inverted, ignoreCase };\n }\n function peg$endExpectation() {\n return { type: \"end\" };\n }\n function peg$otherExpectation(description) {\n return { type: \"other\", description };\n }\n function peg$computePosDetails(pos) {\n var details = peg$posDetailsCache[pos];\n var p;\n if (details) {\n return details;\n } else {\n if (pos >= peg$posDetailsCache.length) {\n p = peg$posDetailsCache.length - 1;\n } else {\n p = pos;\n while (!peg$posDetailsCache[--p]) {\n }\n }\n details = peg$posDetailsCache[p];\n details = {\n line: details.line,\n column: details.column\n };\n while (p < pos) {\n if (input.charCodeAt(p) === 10) {\n details.line++;\n details.column = 1;\n } else {\n details.column++;\n }\n p++;\n }\n peg$posDetailsCache[pos] = details;\n return details;\n }\n }\n function peg$computeLocation(startPos, endPos, offset) {\n var startPosDetails = peg$computePosDetails(startPos);\n var endPosDetails = peg$computePosDetails(endPos);\n var res = {\n source: peg$source,\n start: {\n offset: startPos,\n line: startPosDetails.line,\n column: startPosDetails.column\n },\n end: {\n offset: endPos,\n line: endPosDetails.line,\n column: endPosDetails.column\n }\n };\n return res;\n }\n function peg$fail(expected) {\n if (peg$currPos < peg$maxFailPos) {\n return;\n }\n if (peg$currPos > peg$maxFailPos) {\n peg$maxFailPos = peg$currPos;\n peg$maxFailExpected = [];\n }\n peg$maxFailExpected.push(expected);\n }\n function peg$buildStructuredError(expected, found, location) {\n return new peg$SyntaxError(\n peg$SyntaxError.buildMessage(expected, found),\n expected,\n found,\n location\n );\n }\n function peg$parsepgn() {\n var s0, s1, s2;\n s0 = peg$currPos;\n s1 = peg$parsetagPairSection();\n s2 = peg$parsemoveTextSection();\n s0 = peg$f0(s1, s2);\n return s0;\n }\n function peg$parsetagPairSection() {\n var s0, s1, s2;\n s0 = peg$currPos;\n s1 = [];\n s2 = peg$parsetagPair();\n while (s2 !== peg$FAILED) {\n s1.push(s2);\n s2 = peg$parsetagPair();\n }\n s2 = peg$parse_();\n s0 = peg$f1(s1);\n return s0;\n }\n function peg$parsetagPair() {\n var s0, s2, s4, s6, s7, s8, s10;\n peg$silentFails++;\n s0 = peg$currPos;\n peg$parse_();\n if (input.charCodeAt(peg$currPos) === 91) {\n s2 = peg$c0;\n peg$currPos++;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e1);\n }\n }\n if (s2 !== peg$FAILED) {\n peg$parse_();\n s4 = peg$parsetagName();\n if (s4 !== peg$FAILED) {\n peg$parse_();\n if (input.charCodeAt(peg$currPos) === 34) {\n s6 = peg$c1;\n peg$currPos++;\n } else {\n s6 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e2);\n }\n }\n if (s6 !== peg$FAILED) {\n s7 = peg$parsetagValue();\n if (input.charCodeAt(peg$currPos) === 34) {\n s8 = peg$c1;\n peg$currPos++;\n } else {\n s8 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e2);\n }\n }\n if (s8 !== peg$FAILED) {\n peg$parse_();\n if (input.charCodeAt(peg$currPos) === 93) {\n s10 = peg$c2;\n peg$currPos++;\n } else {\n s10 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e3);\n }\n }\n if (s10 !== peg$FAILED) {\n s0 = peg$f2(s4, s7);\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n peg$silentFails--;\n if (s0 === peg$FAILED) {\n if (peg$silentFails === 0) {\n peg$fail(peg$e0);\n }\n }\n return s0;\n }\n function peg$parsetagName() {\n var s0, s1, s2;\n peg$silentFails++;\n s0 = peg$currPos;\n s1 = [];\n s2 = input.charAt(peg$currPos);\n if (peg$r0.test(s2)) {\n peg$currPos++;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e5);\n }\n }\n if (s2 !== peg$FAILED) {\n while (s2 !== peg$FAILED) {\n s1.push(s2);\n s2 = input.charAt(peg$currPos);\n if (peg$r0.test(s2)) {\n peg$currPos++;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e5);\n }\n }\n }\n } else {\n s1 = peg$FAILED;\n }\n if (s1 !== peg$FAILED) {\n s0 = input.substring(s0, peg$currPos);\n } else {\n s0 = s1;\n }\n peg$silentFails--;\n if (s0 === peg$FAILED) {\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e4);\n }\n }\n return s0;\n }\n function peg$parsetagValue() {\n var s0, s1, s2;\n peg$silentFails++;\n s0 = peg$currPos;\n s1 = [];\n s2 = input.charAt(peg$currPos);\n if (peg$r1.test(s2)) {\n peg$currPos++;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e7);\n }\n }\n while (s2 !== peg$FAILED) {\n s1.push(s2);\n s2 = input.charAt(peg$currPos);\n if (peg$r1.test(s2)) {\n peg$currPos++;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e7);\n }\n }\n }\n s0 = input.substring(s0, peg$currPos);\n peg$silentFails--;\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e6);\n }\n return s0;\n }\n function peg$parsemoveTextSection() {\n var s0, s1, s3;\n s0 = peg$currPos;\n s1 = peg$parseline();\n peg$parse_();\n s3 = peg$parsegameTerminationMarker();\n if (s3 === peg$FAILED) {\n s3 = null;\n }\n peg$parse_();\n s0 = peg$f3(s1, s3);\n return s0;\n }\n function peg$parseline() {\n var s0, s1, s2, s3;\n s0 = peg$currPos;\n s1 = peg$parsecomment();\n if (s1 === peg$FAILED) {\n s1 = null;\n }\n s2 = [];\n s3 = peg$parsemove();\n while (s3 !== peg$FAILED) {\n s2.push(s3);\n s3 = peg$parsemove();\n }\n s0 = peg$f4(s1, s2);\n return s0;\n }\n function peg$parsemove() {\n var s0, s4, s5, s6, s7, s8, s9, s10;\n s0 = peg$currPos;\n peg$parse_();\n peg$parsemoveNumber();\n peg$parse_();\n s4 = peg$parsesan();\n if (s4 !== peg$FAILED) {\n s5 = peg$parsesuffixAnnotation();\n if (s5 === peg$FAILED) {\n s5 = null;\n }\n s6 = [];\n s7 = peg$parsenag();\n while (s7 !== peg$FAILED) {\n s6.push(s7);\n s7 = peg$parsenag();\n }\n s7 = peg$parse_();\n s8 = peg$parsecomment();\n if (s8 === peg$FAILED) {\n s8 = null;\n }\n s9 = [];\n s10 = peg$parsevariation();\n while (s10 !== peg$FAILED) {\n s9.push(s10);\n s10 = peg$parsevariation();\n }\n s0 = peg$f5(s4, s5, s6, s8, s9);\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n return s0;\n }\n function peg$parsemoveNumber() {\n var s0, s1, s2, s3, s4, s5;\n peg$silentFails++;\n s0 = peg$currPos;\n s1 = [];\n s2 = input.charAt(peg$currPos);\n if (peg$r2.test(s2)) {\n peg$currPos++;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e9);\n }\n }\n while (s2 !== peg$FAILED) {\n s1.push(s2);\n s2 = input.charAt(peg$currPos);\n if (peg$r2.test(s2)) {\n peg$currPos++;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e9);\n }\n }\n }\n if (input.charCodeAt(peg$currPos) === 46) {\n s2 = peg$c3;\n peg$currPos++;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e10);\n }\n }\n if (s2 !== peg$FAILED) {\n s3 = peg$parse_();\n s4 = [];\n s5 = input.charAt(peg$currPos);\n if (peg$r3.test(s5)) {\n peg$currPos++;\n } else {\n s5 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e11);\n }\n }\n while (s5 !== peg$FAILED) {\n s4.push(s5);\n s5 = input.charAt(peg$currPos);\n if (peg$r3.test(s5)) {\n peg$currPos++;\n } else {\n s5 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e11);\n }\n }\n }\n s1 = [s1, s2, s3, s4];\n s0 = s1;\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n peg$silentFails--;\n if (s0 === peg$FAILED) {\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e8);\n }\n }\n return s0;\n }\n function peg$parsesan() {\n var s0, s1, s2, s3, s4, s5;\n peg$silentFails++;\n s0 = peg$currPos;\n s1 = peg$currPos;\n if (input.substr(peg$currPos, 5) === peg$c4) {\n s2 = peg$c4;\n peg$currPos += 5;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e13);\n }\n }\n if (s2 === peg$FAILED) {\n if (input.substr(peg$currPos, 3) === peg$c5) {\n s2 = peg$c5;\n peg$currPos += 3;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e14);\n }\n }\n if (s2 === peg$FAILED) {\n if (input.substr(peg$currPos, 5) === peg$c6) {\n s2 = peg$c6;\n peg$currPos += 5;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e15);\n }\n }\n if (s2 === peg$FAILED) {\n if (input.substr(peg$currPos, 3) === peg$c7) {\n s2 = peg$c7;\n peg$currPos += 3;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e16);\n }\n }\n if (s2 === peg$FAILED) {\n s2 = peg$currPos;\n s3 = input.charAt(peg$currPos);\n if (peg$r0.test(s3)) {\n peg$currPos++;\n } else {\n s3 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e5);\n }\n }\n if (s3 !== peg$FAILED) {\n s4 = [];\n s5 = input.charAt(peg$currPos);\n if (peg$r4.test(s5)) {\n peg$currPos++;\n } else {\n s5 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e17);\n }\n }\n if (s5 !== peg$FAILED) {\n while (s5 !== peg$FAILED) {\n s4.push(s5);\n s5 = input.charAt(peg$currPos);\n if (peg$r4.test(s5)) {\n peg$currPos++;\n } else {\n s5 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e17);\n }\n }\n }\n } else {\n s4 = peg$FAILED;\n }\n if (s4 !== peg$FAILED) {\n s3 = [s3, s4];\n s2 = s3;\n } else {\n peg$currPos = s2;\n s2 = peg$FAILED;\n }\n } else {\n peg$currPos = s2;\n s2 = peg$FAILED;\n }\n }\n }\n }\n }\n if (s2 !== peg$FAILED) {\n s3 = input.charAt(peg$currPos);\n if (peg$r5.test(s3)) {\n peg$currPos++;\n } else {\n s3 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e18);\n }\n }\n if (s3 === peg$FAILED) {\n s3 = null;\n }\n s2 = [s2, s3];\n s1 = s2;\n } else {\n peg$currPos = s1;\n s1 = peg$FAILED;\n }\n if (s1 !== peg$FAILED) {\n s0 = input.substring(s0, peg$currPos);\n } else {\n s0 = s1;\n }\n peg$silentFails--;\n if (s0 === peg$FAILED) {\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e12);\n }\n }\n return s0;\n }\n function peg$parsesuffixAnnotation() {\n var s0, s1, s2;\n peg$silentFails++;\n s0 = peg$currPos;\n s1 = [];\n s2 = input.charAt(peg$currPos);\n if (peg$r6.test(s2)) {\n peg$currPos++;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e20);\n }\n }\n while (s2 !== peg$FAILED) {\n s1.push(s2);\n if (s1.length >= 2) {\n s2 = peg$FAILED;\n } else {\n s2 = input.charAt(peg$currPos);\n if (peg$r6.test(s2)) {\n peg$currPos++;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e20);\n }\n }\n }\n }\n if (s1.length < 1) {\n peg$currPos = s0;\n s0 = peg$FAILED;\n } else {\n s0 = s1;\n }\n peg$silentFails--;\n if (s0 === peg$FAILED) {\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e19);\n }\n }\n return s0;\n }\n function peg$parsenag() {\n var s0, s2, s3, s4, s5;\n peg$silentFails++;\n s0 = peg$currPos;\n peg$parse_();\n if (input.charCodeAt(peg$currPos) === 36) {\n s2 = peg$c8;\n peg$currPos++;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e22);\n }\n }\n if (s2 !== peg$FAILED) {\n s3 = peg$currPos;\n s4 = [];\n s5 = input.charAt(peg$currPos);\n if (peg$r2.test(s5)) {\n peg$currPos++;\n } else {\n s5 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e9);\n }\n }\n if (s5 !== peg$FAILED) {\n while (s5 !== peg$FAILED) {\n s4.push(s5);\n s5 = input.charAt(peg$currPos);\n if (peg$r2.test(s5)) {\n peg$currPos++;\n } else {\n s5 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e9);\n }\n }\n }\n } else {\n s4 = peg$FAILED;\n }\n if (s4 !== peg$FAILED) {\n s3 = input.substring(s3, peg$currPos);\n } else {\n s3 = s4;\n }\n if (s3 !== peg$FAILED) {\n s0 = peg$f6(s3);\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n peg$silentFails--;\n if (s0 === peg$FAILED) {\n if (peg$silentFails === 0) {\n peg$fail(peg$e21);\n }\n }\n return s0;\n }\n function peg$parsecomment() {\n var s0;\n s0 = peg$parsebraceComment();\n if (s0 === peg$FAILED) {\n s0 = peg$parserestOfLineComment();\n }\n return s0;\n }\n function peg$parsebraceComment() {\n var s0, s1, s2, s3, s4;\n peg$silentFails++;\n s0 = peg$currPos;\n if (input.charCodeAt(peg$currPos) === 123) {\n s1 = peg$c9;\n peg$currPos++;\n } else {\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e24);\n }\n }\n if (s1 !== peg$FAILED) {\n s2 = peg$currPos;\n s3 = [];\n s4 = input.charAt(peg$currPos);\n if (peg$r7.test(s4)) {\n peg$currPos++;\n } else {\n s4 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e25);\n }\n }\n while (s4 !== peg$FAILED) {\n s3.push(s4);\n s4 = input.charAt(peg$currPos);\n if (peg$r7.test(s4)) {\n peg$currPos++;\n } else {\n s4 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e25);\n }\n }\n }\n s2 = input.substring(s2, peg$currPos);\n if (input.charCodeAt(peg$currPos) === 125) {\n s3 = peg$c10;\n peg$currPos++;\n } else {\n s3 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e26);\n }\n }\n if (s3 !== peg$FAILED) {\n s0 = peg$f7(s2);\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n peg$silentFails--;\n if (s0 === peg$FAILED) {\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e23);\n }\n }\n return s0;\n }\n function peg$parserestOfLineComment() {\n var s0, s1, s2, s3, s4;\n peg$silentFails++;\n s0 = peg$currPos;\n if (input.charCodeAt(peg$currPos) === 59) {\n s1 = peg$c11;\n peg$currPos++;\n } else {\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e28);\n }\n }\n if (s1 !== peg$FAILED) {\n s2 = peg$currPos;\n s3 = [];\n s4 = input.charAt(peg$currPos);\n if (peg$r8.test(s4)) {\n peg$currPos++;\n } else {\n s4 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e29);\n }\n }\n while (s4 !== peg$FAILED) {\n s3.push(s4);\n s4 = input.charAt(peg$currPos);\n if (peg$r8.test(s4)) {\n peg$currPos++;\n } else {\n s4 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e29);\n }\n }\n }\n s2 = input.substring(s2, peg$currPos);\n s0 = peg$f8(s2);\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n peg$silentFails--;\n if (s0 === peg$FAILED) {\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e27);\n }\n }\n return s0;\n }\n function peg$parsevariation() {\n var s0, s2, s3, s5;\n peg$silentFails++;\n s0 = peg$currPos;\n peg$parse_();\n if (input.charCodeAt(peg$currPos) === 40) {\n s2 = peg$c12;\n peg$currPos++;\n } else {\n s2 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e31);\n }\n }\n if (s2 !== peg$FAILED) {\n s3 = peg$parseline();\n if (s3 !== peg$FAILED) {\n peg$parse_();\n if (input.charCodeAt(peg$currPos) === 41) {\n s5 = peg$c13;\n peg$currPos++;\n } else {\n s5 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e32);\n }\n }\n if (s5 !== peg$FAILED) {\n s0 = peg$f9(s3);\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n peg$silentFails--;\n if (s0 === peg$FAILED) {\n if (peg$silentFails === 0) {\n peg$fail(peg$e30);\n }\n }\n return s0;\n }\n function peg$parsegameTerminationMarker() {\n var s0, s1, s3;\n peg$silentFails++;\n s0 = peg$currPos;\n if (input.substr(peg$currPos, 3) === peg$c14) {\n s1 = peg$c14;\n peg$currPos += 3;\n } else {\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e34);\n }\n }\n if (s1 === peg$FAILED) {\n if (input.substr(peg$currPos, 3) === peg$c15) {\n s1 = peg$c15;\n peg$currPos += 3;\n } else {\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e35);\n }\n }\n if (s1 === peg$FAILED) {\n if (input.substr(peg$currPos, 7) === peg$c16) {\n s1 = peg$c16;\n peg$currPos += 7;\n } else {\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e36);\n }\n }\n if (s1 === peg$FAILED) {\n if (input.charCodeAt(peg$currPos) === 42) {\n s1 = peg$c17;\n peg$currPos++;\n } else {\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e37);\n }\n }\n }\n }\n }\n if (s1 !== peg$FAILED) {\n peg$parse_();\n s3 = peg$parsecomment();\n if (s3 === peg$FAILED) {\n s3 = null;\n }\n s0 = peg$f10(s1, s3);\n } else {\n peg$currPos = s0;\n s0 = peg$FAILED;\n }\n peg$silentFails--;\n if (s0 === peg$FAILED) {\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e33);\n }\n }\n return s0;\n }\n function peg$parse_() {\n var s0, s1;\n peg$silentFails++;\n s0 = [];\n s1 = input.charAt(peg$currPos);\n if (peg$r9.test(s1)) {\n peg$currPos++;\n } else {\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e39);\n }\n }\n while (s1 !== peg$FAILED) {\n s0.push(s1);\n s1 = input.charAt(peg$currPos);\n if (peg$r9.test(s1)) {\n peg$currPos++;\n } else {\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e39);\n }\n }\n }\n peg$silentFails--;\n s1 = peg$FAILED;\n if (peg$silentFails === 0) {\n peg$fail(peg$e38);\n }\n return s0;\n }\n peg$result = peg$startRuleFunction();\n if (options.peg$library) {\n return (\n /** @type {any} */\n {\n peg$result,\n peg$currPos,\n peg$FAILED,\n peg$maxFailExpected,\n peg$maxFailPos\n }\n );\n }\n if (peg$result !== peg$FAILED && peg$currPos === input.length) {\n return peg$result;\n } else {\n if (peg$result !== peg$FAILED && peg$currPos < input.length) {\n peg$fail(peg$endExpectation());\n }\n throw peg$buildStructuredError(\n peg$maxFailExpected,\n peg$maxFailPos < input.length ? input.charAt(peg$maxFailPos) : null,\n peg$maxFailPos < input.length ? peg$computeLocation(peg$maxFailPos, peg$maxFailPos + 1) : peg$computeLocation(peg$maxFailPos, peg$maxFailPos)\n );\n }\n}\nvar MASK64 = 0xffffffffffffffffn;\nfunction rotl(x, k) {\n return (x << k | x >> 64n - k) & 0xffffffffffffffffn;\n}\nfunction wrappingMul(x, y) {\n return x * y & MASK64;\n}\nfunction xoroshiro128(state) {\n return function() {\n let s0 = BigInt(state & MASK64);\n let s1 = BigInt(state >> 64n & MASK64);\n const result = wrappingMul(rotl(wrappingMul(s0, 5n), 7n), 9n);\n s1 ^= s0;\n s0 = (rotl(s0, 24n) ^ s1 ^ s1 << 16n) & MASK64;\n s1 = rotl(s1, 37n);\n state = s1 << 64n | s0;\n return result;\n };\n}\nvar rand = xoroshiro128(0xa187eb39cdcaed8f31c4b365b102e01en);\nvar PIECE_KEYS = Array.from({ length: 2 }, () => Array.from({ length: 6 }, () => Array.from({ length: 128 }, () => rand())));\nvar EP_KEYS = Array.from({ length: 8 }, () => rand());\nvar CASTLING_KEYS = Array.from({ length: 16 }, () => rand());\nvar SIDE_KEY = rand();\nvar WHITE = \"w\";\nvar BLACK = \"b\";\nvar PAWN = \"p\";\nvar KNIGHT = \"n\";\nvar BISHOP = \"b\";\nvar ROOK = \"r\";\nvar QUEEN = \"q\";\nvar KING = \"k\";\nvar DEFAULT_POSITION = \"rnbqkbnr/pppppppp/8/8/8/8/PPPPPPPP/RNBQKBNR w KQkq - 0 1\";\nvar Move = class {\n constructor(chess2, internal) {\n __publicField(this, \"color\");\n __publicField(this, \"from\");\n __publicField(this, \"to\");\n __publicField(this, \"piece\");\n __publicField(this, \"captured\");\n __publicField(this, \"promotion\");\n /**\n * @deprecated This field is deprecated and will be removed in version 2.0.0.\n * Please use move descriptor functions instead: `isCapture`, `isPromotion`,\n * `isEnPassant`, `isKingsideCastle`, `isQueensideCastle`, `isCastle`, and\n * `isBigPawn`\n */\n __publicField(this, \"flags\");\n __publicField(this, \"san\");\n __publicField(this, \"lan\");\n __publicField(this, \"before\");\n __publicField(this, \"after\");\n const { color, piece, from, to, flags, captured, promotion } = internal;\n const fromAlgebraic = algebraic(from);\n const toAlgebraic = algebraic(to);\n this.color = color;\n this.piece = piece;\n this.from = fromAlgebraic;\n this.to = toAlgebraic;\n this.san = chess2[\"_moveToSan\"](internal, chess2[\"_moves\"]({ legal: true }));\n this.lan = fromAlgebraic + toAlgebraic;\n this.before = chess2.fen();\n chess2[\"_makeMove\"](internal);\n this.after = chess2.fen();\n chess2[\"_undoMove\"]();\n this.flags = \"\";\n for (const flag in BITS) {\n if (BITS[flag] & flags) {\n this.flags += FLAGS[flag];\n }\n }\n if (captured) {\n this.captured = captured;\n }\n if (promotion) {\n this.promotion = promotion;\n this.lan += promotion;\n }\n }\n isCapture() {\n return this.flags.indexOf(FLAGS[\"CAPTURE\"]) > -1;\n }\n isPromotion() {\n return this.flags.indexOf(FLAGS[\"PROMOTION\"]) > -1;\n }\n isEnPassant() {\n return this.flags.indexOf(FLAGS[\"EP_CAPTURE\"]) > -1;\n }\n isKingsideCastle() {\n return this.flags.indexOf(FLAGS[\"KSIDE_CASTLE\"]) > -1;\n }\n isQueensideCastle() {\n return this.flags.indexOf(FLAGS[\"QSIDE_CASTLE\"]) > -1;\n }\n isBigPawn() {\n return this.flags.indexOf(FLAGS[\"BIG_PAWN\"]) > -1;\n }\n};\nvar EMPTY = -1;\nvar FLAGS = {\n NORMAL: \"n\",\n CAPTURE: \"c\",\n BIG_PAWN: \"b\",\n EP_CAPTURE: \"e\",\n PROMOTION: \"p\",\n KSIDE_CASTLE: \"k\",\n QSIDE_CASTLE: \"q\",\n NULL_MOVE: \"-\"\n};\nvar BITS = {\n NORMAL: 1,\n CAPTURE: 2,\n BIG_PAWN: 4,\n EP_CAPTURE: 8,\n PROMOTION: 16,\n KSIDE_CASTLE: 32,\n QSIDE_CASTLE: 64,\n NULL_MOVE: 128\n};\nvar SEVEN_TAG_ROSTER = {\n Event: \"?\",\n Site: \"?\",\n Date: \"????.??.??\",\n Round: \"?\",\n White: \"?\",\n Black: \"?\",\n Result: \"*\"\n};\nvar SUPLEMENTAL_TAGS = {\n WhiteTitle: null,\n BlackTitle: null,\n WhiteElo: null,\n BlackElo: null,\n WhiteUSCF: null,\n BlackUSCF: null,\n WhiteNA: null,\n BlackNA: null,\n WhiteType: null,\n BlackType: null,\n EventDate: null,\n EventSponsor: null,\n Section: null,\n Stage: null,\n Board: null,\n Opening: null,\n Variation: null,\n SubVariation: null,\n ECO: null,\n NIC: null,\n Time: null,\n UTCTime: null,\n UTCDate: null,\n TimeControl: null,\n SetUp: null,\n FEN: null,\n Termination: null,\n Annotator: null,\n Mode: null,\n PlyCount: null\n};\nvar HEADER_TEMPLATE = {\n ...SEVEN_TAG_ROSTER,\n ...SUPLEMENTAL_TAGS\n};\nvar Ox88 = {\n a8: 0,\n b8: 1,\n c8: 2,\n d8: 3,\n e8: 4,\n f8: 5,\n g8: 6,\n h8: 7,\n a7: 16,\n b7: 17,\n c7: 18,\n d7: 19,\n e7: 20,\n f7: 21,\n g7: 22,\n h7: 23,\n a6: 32,\n b6: 33,\n c6: 34,\n d6: 35,\n e6: 36,\n f6: 37,\n g6: 38,\n h6: 39,\n a5: 48,\n b5: 49,\n c5: 50,\n d5: 51,\n e5: 52,\n f5: 53,\n g5: 54,\n h5: 55,\n a4: 64,\n b4: 65,\n c4: 66,\n d4: 67,\n e4: 68,\n f4: 69,\n g4: 70,\n h4: 71,\n a3: 80,\n b3: 81,\n c3: 82,\n d3: 83,\n e3: 84,\n f3: 85,\n g3: 86,\n h3: 87,\n a2: 96,\n b2: 97,\n c2: 98,\n d2: 99,\n e2: 100,\n f2: 101,\n g2: 102,\n h2: 103,\n a1: 112,\n b1: 113,\n c1: 114,\n d1: 115,\n e1: 116,\n f1: 117,\n g1: 118,\n h1: 119\n};\nvar PAWN_OFFSETS = {\n b: [16, 32, 17, 15],\n w: [-16, -32, -17, -15]\n};\nvar PIECE_OFFSETS = {\n n: [-18, -33, -31, -14, 18, 33, 31, 14],\n b: [-17, -15, 17, 15],\n r: [-16, 1, 16, -1],\n q: [-17, -16, -15, 1, 17, 16, 15, -1],\n k: [-17, -16, -15, 1, 17, 16, 15, -1]\n};\nvar ATTACKS = [\n 20,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 24,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 20,\n 0,\n 0,\n 20,\n 0,\n 0,\n 0,\n 0,\n 0,\n 24,\n 0,\n 0,\n 0,\n 0,\n 0,\n 20,\n 0,\n 0,\n 0,\n 0,\n 20,\n 0,\n 0,\n 0,\n 0,\n 24,\n 0,\n 0,\n 0,\n 0,\n 20,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 20,\n 0,\n 0,\n 0,\n 24,\n 0,\n 0,\n 0,\n 20,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 20,\n 0,\n 0,\n 24,\n 0,\n 0,\n 20,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 20,\n 2,\n 24,\n 2,\n 20,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 2,\n 53,\n 56,\n 53,\n 2,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 24,\n 24,\n 24,\n 24,\n 24,\n 24,\n 56,\n 0,\n 56,\n 24,\n 24,\n 24,\n 24,\n 24,\n 24,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 2,\n 53,\n 56,\n 53,\n 2,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 20,\n 2,\n 24,\n 2,\n 20,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 20,\n 0,\n 0,\n 24,\n 0,\n 0,\n 20,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 20,\n 0,\n 0,\n 0,\n 24,\n 0,\n 0,\n 0,\n 20,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 20,\n 0,\n 0,\n 0,\n 0,\n 24,\n 0,\n 0,\n 0,\n 0,\n 20,\n 0,\n 0,\n 0,\n 0,\n 20,\n 0,\n 0,\n 0,\n 0,\n 0,\n 24,\n 0,\n 0,\n 0,\n 0,\n 0,\n 20,\n 0,\n 0,\n 20,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 24,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 20\n];\nvar RAYS = [\n 17,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 16,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 15,\n 0,\n 0,\n 17,\n 0,\n 0,\n 0,\n 0,\n 0,\n 16,\n 0,\n 0,\n 0,\n 0,\n 0,\n 15,\n 0,\n 0,\n 0,\n 0,\n 17,\n 0,\n 0,\n 0,\n 0,\n 16,\n 0,\n 0,\n 0,\n 0,\n 15,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 17,\n 0,\n 0,\n 0,\n 16,\n 0,\n 0,\n 0,\n 15,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 17,\n 0,\n 0,\n 16,\n 0,\n 0,\n 15,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 17,\n 0,\n 16,\n 0,\n 15,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 17,\n 16,\n 15,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 1,\n 1,\n 1,\n 1,\n 1,\n 1,\n 1,\n 0,\n -1,\n -1,\n -1,\n -1,\n -1,\n -1,\n -1,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n -15,\n -16,\n -17,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n -15,\n 0,\n -16,\n 0,\n -17,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n -15,\n 0,\n 0,\n -16,\n 0,\n 0,\n -17,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n -15,\n 0,\n 0,\n 0,\n -16,\n 0,\n 0,\n 0,\n -17,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n -15,\n 0,\n 0,\n 0,\n 0,\n -16,\n 0,\n 0,\n 0,\n 0,\n -17,\n 0,\n 0,\n 0,\n 0,\n -15,\n 0,\n 0,\n 0,\n 0,\n 0,\n -16,\n 0,\n 0,\n 0,\n 0,\n 0,\n -17,\n 0,\n 0,\n -15,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n -16,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n -17\n];\nvar PIECE_MASKS = { p: 1, n: 2, b: 4, r: 8, q: 16, k: 32 };\nvar SYMBOLS = \"pnbrqkPNBRQK\";\nvar PROMOTIONS = [KNIGHT, BISHOP, ROOK, QUEEN];\nvar RANK_1 = 7;\nvar RANK_2 = 6;\nvar RANK_7 = 1;\nvar RANK_8 = 0;\nvar SIDES = {\n [KING]: BITS.KSIDE_CASTLE,\n [QUEEN]: BITS.QSIDE_CASTLE\n};\nvar ROOKS = {\n w: [\n { square: Ox88.a1, flag: BITS.QSIDE_CASTLE },\n { square: Ox88.h1, flag: BITS.KSIDE_CASTLE }\n ],\n b: [\n { square: Ox88.a8, flag: BITS.QSIDE_CASTLE },\n { square: Ox88.h8, flag: BITS.KSIDE_CASTLE }\n ]\n};\nvar SECOND_RANK = { b: RANK_7, w: RANK_2 };\nvar SAN_NULLMOVE = \"--\";\nfunction rank(square) {\n return square >> 4;\n}\nfunction file(square) {\n return square & 15;\n}\nfunction isDigit(c) {\n return \"0123456789\".indexOf(c) !== -1;\n}\nfunction algebraic(square) {\n const f = file(square);\n const r = rank(square);\n return \"abcdefgh\".substring(f, f + 1) + \"87654321\".substring(r, r + 1);\n}\nfunction swapColor(color) {\n return color === WHITE ? BLACK : WHITE;\n}\nfunction validateFen(fen) {\n const tokens = fen.split(/\\s+/);\n if (tokens.length !== 6) {\n return {\n ok: false,\n error: \"Invalid FEN: must contain six space-delimited fields\"\n };\n }\n const moveNumber = parseInt(tokens[5], 10);\n if (isNaN(moveNumber) || moveNumber <= 0) {\n return {\n ok: false,\n error: \"Invalid FEN: move number must be a positive integer\"\n };\n }\n const halfMoves = parseInt(tokens[4], 10);\n if (isNaN(halfMoves) || halfMoves < 0) {\n return {\n ok: false,\n error: \"Invalid FEN: half move counter number must be a non-negative integer\"\n };\n }\n if (!/^(-|[abcdefgh][36])$/.test(tokens[3])) {\n return { ok: false, error: \"Invalid FEN: en-passant square is invalid\" };\n }\n if (/[^kKqQ-]/.test(tokens[2])) {\n return { ok: false, error: \"Invalid FEN: castling availability is invalid\" };\n }\n if (!/^(w|b)$/.test(tokens[1])) {\n return { ok: false, error: \"Invalid FEN: side-to-move is invalid\" };\n }\n const rows = tokens[0].split(\"/\");\n if (rows.length !== 8) {\n return {\n ok: false,\n error: \"Invalid FEN: piece data does not contain 8 '/'-delimited rows\"\n };\n }\n for (let i = 0; i < rows.length; i++) {\n let sumFields = 0;\n let previousWasNumber = false;\n for (let k = 0; k < rows[i].length; k++) {\n if (isDigit(rows[i][k])) {\n if (previousWasNumber) {\n return {\n ok: false,\n error: \"Invalid FEN: piece data is invalid (consecutive number)\"\n };\n }\n sumFields += parseInt(rows[i][k], 10);\n previousWasNumber = true;\n } else {\n if (!/^[prnbqkPRNBQK]$/.test(rows[i][k])) {\n return {\n ok: false,\n error: \"Invalid FEN: piece data is invalid (invalid piece)\"\n };\n }\n sumFields += 1;\n previousWasNumber = false;\n }\n }\n if (sumFields !== 8) {\n return {\n ok: false,\n error: \"Invalid FEN: piece data is invalid (too many squares in rank)\"\n };\n }\n }\n if (tokens[3][1] == \"3\" && tokens[1] == \"w\" || tokens[3][1] == \"6\" && tokens[1] == \"b\") {\n return { ok: false, error: \"Invalid FEN: illegal en-passant square\" };\n }\n const kings = [\n { color: \"white\", regex: /K/g },\n { color: \"black\", regex: /k/g }\n ];\n for (const { color, regex } of kings) {\n if (!regex.test(tokens[0])) {\n return { ok: false, error: `Invalid FEN: missing ${color} king` };\n }\n if ((tokens[0].match(regex) || []).length > 1) {\n return { ok: false, error: `Invalid FEN: too many ${color} kings` };\n }\n }\n if (Array.from(rows[0] + rows[7]).some((char) => char.toUpperCase() === \"P\")) {\n return {\n ok: false,\n error: \"Invalid FEN: some pawns are on the edge rows\"\n };\n }\n return { ok: true };\n}\nfunction getDisambiguator(move, moves) {\n const from = move.from;\n const to = move.to;\n const piece = move.piece;\n let ambiguities = 0;\n let sameRank = 0;\n let sameFile = 0;\n for (let i = 0, len = moves.length; i < len; i++) {\n const ambigFrom = moves[i].from;\n const ambigTo = moves[i].to;\n const ambigPiece = moves[i].piece;\n if (piece === ambigPiece && from !== ambigFrom && to === ambigTo) {\n ambiguities++;\n if (rank(from) === rank(ambigFrom)) {\n sameRank++;\n }\n if (file(from) === file(ambigFrom)) {\n sameFile++;\n }\n }\n }\n if (ambiguities > 0) {\n if (sameRank > 0 && sameFile > 0) {\n return algebraic(from);\n } else if (sameFile > 0) {\n return algebraic(from).charAt(1);\n } else {\n return algebraic(from).charAt(0);\n }\n }\n return \"\";\n}\nfunction addMove(moves, color, from, to, piece, captured = void 0, flags = BITS.NORMAL) {\n const r = rank(to);\n if (piece === PAWN && (r === RANK_1 || r === RANK_8)) {\n for (let i = 0; i < PROMOTIONS.length; i++) {\n const promotion = PROMOTIONS[i];\n moves.push({\n color,\n from,\n to,\n piece,\n captured,\n promotion,\n flags: flags | BITS.PROMOTION\n });\n }\n } else {\n moves.push({\n color,\n from,\n to,\n piece,\n captured,\n flags\n });\n }\n}\nfunction inferPieceType(san) {\n let pieceType = san.charAt(0);\n if (pieceType >= \"a\" && pieceType <= \"h\") {\n const matches = san.match(/[a-h]\\d.*[a-h]\\d/);\n if (matches) {\n return void 0;\n }\n return PAWN;\n }\n pieceType = pieceType.toLowerCase();\n if (pieceType === \"o\") {\n return KING;\n }\n return pieceType;\n}\nfunction strippedSan(move) {\n return move.replace(/=/, \"\").replace(/[+#]?[?!]*$/, \"\");\n}\nvar Chess = class {\n constructor(fen = DEFAULT_POSITION, { skipValidation = false } = {}) {\n __publicField(this, \"_board\", new Array(128));\n __publicField(this, \"_turn\", WHITE);\n __publicField(this, \"_header\", {});\n __publicField(this, \"_kings\", { w: EMPTY, b: EMPTY });\n __publicField(this, \"_epSquare\", -1);\n __publicField(this, \"_halfMoves\", 0);\n __publicField(this, \"_moveNumber\", 0);\n __publicField(this, \"_history\", []);\n __publicField(this, \"_comments\", {});\n __publicField(this, \"_castling\", { w: 0, b: 0 });\n __publicField(this, \"_hash\", 0n);\n // tracks number of times a position has been seen for repetition checking\n __publicField(this, \"_positionCount\", /* @__PURE__ */ new Map());\n this.load(fen, { skipValidation });\n }\n clear({ preserveHeaders = false } = {}) {\n this._board = new Array(128);\n this._kings = { w: EMPTY, b: EMPTY };\n this._turn = WHITE;\n this._castling = { w: 0, b: 0 };\n this._epSquare = EMPTY;\n this._halfMoves = 0;\n this._moveNumber = 1;\n this._history = [];\n this._comments = {};\n this._header = preserveHeaders ? this._header : { ...HEADER_TEMPLATE };\n this._hash = this._computeHash();\n this._positionCount = /* @__PURE__ */ new Map();\n this._header[\"SetUp\"] = null;\n this._header[\"FEN\"] = null;\n }\n load(fen, { skipValidation = false, preserveHeaders = false } = {}) {\n let tokens = fen.split(/\\s+/);\n if (tokens.length >= 2 && tokens.length < 6) {\n const adjustments = [\"-\", \"-\", \"0\", \"1\"];\n fen = tokens.concat(adjustments.slice(-(6 - tokens.length))).join(\" \");\n }\n tokens = fen.split(/\\s+/);\n if (!skipValidation) {\n const { ok, error } = validateFen(fen);\n if (!ok) {\n throw new Error(error);\n }\n }\n const position = tokens[0];\n let square = 0;\n this.clear({ preserveHeaders });\n for (let i = 0; i < position.length; i++) {\n const piece = position.charAt(i);\n if (piece === \"/\") {\n square += 8;\n } else if (isDigit(piece)) {\n square += parseInt(piece, 10);\n } else {\n const color = piece < \"a\" ? WHITE : BLACK;\n this._put({ type: piece.toLowerCase(), color }, algebraic(square));\n square++;\n }\n }\n this._turn = tokens[1];\n if (tokens[2].indexOf(\"K\") > -1) {\n this._castling.w |= BITS.KSIDE_CASTLE;\n }\n if (tokens[2].indexOf(\"Q\") > -1) {\n this._castling.w |= BITS.QSIDE_CASTLE;\n }\n if (tokens[2].indexOf(\"k\") > -1) {\n this._castling.b |= BITS.KSIDE_CASTLE;\n }\n if (tokens[2].indexOf(\"q\") > -1) {\n this._castling.b |= BITS.QSIDE_CASTLE;\n }\n this._epSquare = tokens[3] === \"-\" ? EMPTY : Ox88[tokens[3]];\n this._halfMoves = parseInt(tokens[4], 10);\n this._moveNumber = parseInt(tokens[5], 10);\n this._hash = this._computeHash();\n this._updateSetup(fen);\n this._incPositionCount();\n }\n fen({ forceEnpassantSquare = false } = {}) {\n let empty = 0;\n let fen = \"\";\n for (let i = Ox88.a8; i <= Ox88.h1; i++) {\n if (this._board[i]) {\n if (empty > 0) {\n fen += empty;\n empty = 0;\n }\n const { color, type: piece } = this._board[i];\n fen += color === WHITE ? piece.toUpperCase() : piece.toLowerCase();\n } else {\n empty++;\n }\n if (i + 1 & 136) {\n if (empty > 0) {\n fen += empty;\n }\n if (i !== Ox88.h1) {\n fen += \"/\";\n }\n empty = 0;\n i += 8;\n }\n }\n let castling = \"\";\n if (this._castling[WHITE] & BITS.KSIDE_CASTLE) {\n castling += \"K\";\n }\n if (this._castling[WHITE] & BITS.QSIDE_CASTLE) {\n castling += \"Q\";\n }\n if (this._castling[BLACK] & BITS.KSIDE_CASTLE) {\n castling += \"k\";\n }\n if (this._castling[BLACK] & BITS.QSIDE_CASTLE) {\n castling += \"q\";\n }\n castling = castling || \"-\";\n let epSquare = \"-\";\n if (this._epSquare !== EMPTY) {\n if (forceEnpassantSquare) {\n epSquare = algebraic(this._epSquare);\n } else {\n const bigPawnSquare = this._epSquare + (this._turn === WHITE ? 16 : -16);\n const squares = [bigPawnSquare + 1, bigPawnSquare - 1];\n for (const square of squares) {\n if (square & 136) {\n continue;\n }\n const color = this._turn;\n if (this._board[square]?.color === color && this._board[square]?.type === PAWN) {\n this._makeMove({\n color,\n from: square,\n to: this._epSquare,\n piece: PAWN,\n captured: PAWN,\n flags: BITS.EP_CAPTURE\n });\n const isLegal = !this._isKingAttacked(color);\n this._undoMove();\n if (isLegal) {\n epSquare = algebraic(this._epSquare);\n break;\n }\n }\n }\n }\n }\n return [\n fen,\n this._turn,\n castling,\n epSquare,\n this._halfMoves,\n this._moveNumber\n ].join(\" \");\n }\n _pieceKey(i) {\n if (!this._board[i]) {\n return 0n;\n }\n const { color, type } = this._board[i];\n const colorIndex = {\n w: 0,\n b: 1\n }[color];\n const typeIndex = {\n p: 0,\n n: 1,\n b: 2,\n r: 3,\n q: 4,\n k: 5\n }[type];\n return PIECE_KEYS[colorIndex][typeIndex][i];\n }\n _epKey() {\n return this._epSquare === EMPTY ? 0n : EP_KEYS[this._epSquare & 7];\n }\n _castlingKey() {\n const index = this._castling.w >> 5 | this._castling.b >> 3;\n return CASTLING_KEYS[index];\n }\n _computeHash() {\n let hash = 0n;\n for (let i = Ox88.a8; i <= Ox88.h1; i++) {\n if (i & 136) {\n i += 7;\n continue;\n }\n if (this._board[i]) {\n hash ^= this._pieceKey(i);\n }\n }\n hash ^= this._epKey();\n hash ^= this._castlingKey();\n if (this._turn === \"b\") {\n hash ^= SIDE_KEY;\n }\n return hash;\n }\n /*\n * Called when the initial board setup is changed with put() or remove().\n * modifies the SetUp and FEN properties of the header object. If the FEN\n * is equal to the default position, the SetUp and FEN are deleted the setup\n * is only updated if history.length is zero, ie moves haven't been made.\n */\n _updateSetup(fen) {\n if (this._history.length > 0)\n return;\n if (fen !== DEFAULT_POSITION) {\n this._header[\"SetUp\"] = \"1\";\n this._header[\"FEN\"] = fen;\n } else {\n this._header[\"SetUp\"] = null;\n this._header[\"FEN\"] = null;\n }\n }\n reset() {\n this.load(DEFAULT_POSITION);\n }\n get(square) {\n return this._board[Ox88[square]];\n }\n findPiece(piece) {\n const squares = [];\n for (let i = Ox88.a8; i <= Ox88.h1; i++) {\n if (i & 136) {\n i += 7;\n continue;\n }\n if (!this._board[i] || this._board[i]?.color !== piece.color) {\n continue;\n }\n if (this._board[i].color === piece.color && this._board[i].type === piece.type) {\n squares.push(algebraic(i));\n }\n }\n return squares;\n }\n put({ type, color }, square) {\n if (this._put({ type, color }, square)) {\n this._updateCastlingRights();\n this._updateEnPassantSquare();\n this._updateSetup(this.fen());\n return true;\n }\n return false;\n }\n _set(sq, piece) {\n this._hash ^= this._pieceKey(sq);\n this._board[sq] = piece;\n this._hash ^= this._pieceKey(sq);\n }\n _put({ type, color }, square) {\n if (SYMBOLS.indexOf(type.toLowerCase()) === -1) {\n return false;\n }\n if (!(square in Ox88)) {\n return false;\n }\n const sq = Ox88[square];\n if (type == KING && !(this._kings[color] == EMPTY || this._kings[color] == sq)) {\n return false;\n }\n const currentPieceOnSquare = this._board[sq];\n if (currentPieceOnSquare && currentPieceOnSquare.type === KING) {\n this._kings[currentPieceOnSquare.color] = EMPTY;\n }\n this._set(sq, { type, color });\n if (type === KING) {\n this._kings[color] = sq;\n }\n return true;\n }\n _clear(sq) {\n this._hash ^= this._pieceKey(sq);\n delete this._board[sq];\n }\n remove(square) {\n const piece = this.get(square);\n this._clear(Ox88[square]);\n if (piece && piece.type === KING) {\n this._kings[piece.color] = EMPTY;\n }\n this._updateCastlingRights();\n this._updateEnPassantSquare();\n this._updateSetup(this.fen());\n return piece;\n }\n _updateCastlingRights() {\n this._hash ^= this._castlingKey();\n const whiteKingInPlace = this._board[Ox88.e1]?.type === KING && this._board[Ox88.e1]?.color === WHITE;\n const blackKingInPlace = this._board[Ox88.e8]?.type === KING && this._board[Ox88.e8]?.color === BLACK;\n if (!whiteKingInPlace || this._board[Ox88.a1]?.type !== ROOK || this._board[Ox88.a1]?.color !== WHITE) {\n this._castling.w &= -65;\n }\n if (!whiteKingInPlace || this._board[Ox88.h1]?.type !== ROOK || this._board[Ox88.h1]?.color !== WHITE) {\n this._castling.w &= -33;\n }\n if (!blackKingInPlace || this._board[Ox88.a8]?.type !== ROOK || this._board[Ox88.a8]?.color !== BLACK) {\n this._castling.b &= -65;\n }\n if (!blackKingInPlace || this._board[Ox88.h8]?.type !== ROOK || this._board[Ox88.h8]?.color !== BLACK) {\n this._castling.b &= -33;\n }\n this._hash ^= this._castlingKey();\n }\n _updateEnPassantSquare() {\n if (this._epSquare === EMPTY) {\n return;\n }\n const startSquare = this._epSquare + (this._turn === WHITE ? -16 : 16);\n const currentSquare = this._epSquare + (this._turn === WHITE ? 16 : -16);\n const attackers = [currentSquare + 1, currentSquare - 1];\n if (this._board[startSquare] !== null || this._board[this._epSquare] !== null || this._board[currentSquare]?.color !== swapColor(this._turn) || this._board[currentSquare]?.type !== PAWN) {\n this._hash ^= this._epKey();\n this._epSquare = EMPTY;\n return;\n }\n const canCapture = (square) => !(square & 136) && this._board[square]?.color === this._turn && this._board[square]?.type === PAWN;\n if (!attackers.some(canCapture)) {\n this._hash ^= this._epKey();\n this._epSquare = EMPTY;\n }\n }\n _attacked(color, square, verbose) {\n const attackers = [];\n for (let i = Ox88.a8; i <= Ox88.h1; i++) {\n if (i & 136) {\n i += 7;\n continue;\n }\n if (this._board[i] === void 0 || this._board[i].color !== color) {\n continue;\n }\n const piece = this._board[i];\n const difference = i - square;\n if (difference === 0) {\n continue;\n }\n const index = difference + 119;\n if (ATTACKS[index] & PIECE_MASKS[piece.type]) {\n if (piece.type === PAWN) {\n if (difference > 0 && piece.color === WHITE || difference <= 0 && piece.color === BLACK) {\n if (!verbose) {\n return true;\n } else {\n attackers.push(algebraic(i));\n }\n }\n continue;\n }\n if (piece.type === \"n\" || piece.type === \"k\") {\n if (!verbose) {\n return true;\n } else {\n attackers.push(algebraic(i));\n continue;\n }\n }\n const offset = RAYS[index];\n let j = i + offset;\n let blocked = false;\n while (j !== square) {\n if (this._board[j] != null) {\n blocked = true;\n break;\n }\n j += offset;\n }\n if (!blocked) {\n if (!verbose) {\n return true;\n } else {\n attackers.push(algebraic(i));\n continue;\n }\n }\n }\n }\n if (verbose) {\n return attackers;\n } else {\n return false;\n }\n }\n attackers(square, attackedBy) {\n if (!attackedBy) {\n return this._attacked(this._turn, Ox88[square], true);\n } else {\n return this._attacked(attackedBy, Ox88[square], true);\n }\n }\n _isKingAttacked(color) {\n const square = this._kings[color];\n return square === -1 ? false : this._attacked(swapColor(color), square);\n }\n hash() {\n return this._hash.toString(16);\n }\n isAttacked(square, attackedBy) {\n return this._attacked(attackedBy, Ox88[square]);\n }\n isCheck() {\n return this._isKingAttacked(this._turn);\n }\n inCheck() {\n return this.isCheck();\n }\n isCheckmate() {\n return this.isCheck() && this._moves().length === 0;\n }\n isStalemate() {\n return !this.isCheck() && this._moves().length === 0;\n }\n isInsufficientMaterial() {\n const pieces = {\n b: 0,\n n: 0,\n r: 0,\n q: 0,\n k: 0,\n p: 0\n };\n const bishops = [];\n let numPieces = 0;\n let squareColor = 0;\n for (let i = Ox88.a8; i <= Ox88.h1; i++) {\n squareColor = (squareColor + 1) % 2;\n if (i & 136) {\n i += 7;\n continue;\n }\n const piece = this._board[i];\n if (piece) {\n pieces[piece.type] = piece.type in pieces ? pieces[piece.type] + 1 : 1;\n if (piece.type === BISHOP) {\n bishops.push(squareColor);\n }\n numPieces++;\n }\n }\n if (numPieces === 2) {\n return true;\n } else if (\n // k vs. kn .... or .... k vs. kb\n numPieces === 3 && (pieces[BISHOP] === 1 || pieces[KNIGHT] === 1)\n ) {\n return true;\n } else if (numPieces === pieces[BISHOP] + 2) {\n let sum = 0;\n const len = bishops.length;\n for (let i = 0; i < len; i++) {\n sum += bishops[i];\n }\n if (sum === 0 || sum === len) {\n return true;\n }\n }\n return false;\n }\n isThreefoldRepetition() {\n return this._getPositionCount(this._hash) >= 3;\n }\n isDrawByFiftyMoves() {\n return this._halfMoves >= 100;\n }\n isDraw() {\n return this.isDrawByFiftyMoves() || this.isStalemate() || this.isInsufficientMaterial() || this.isThreefoldRepetition();\n }\n isGameOver() {\n return this.isCheckmate() || this.isDraw();\n }\n moves({ verbose = false, square = void 0, piece = void 0 } = {}) {\n const moves = this._moves({ square, piece });\n if (verbose) {\n return moves.map((move) => new Move(this, move));\n } else {\n return moves.map((move) => this._moveToSan(move, moves));\n }\n }\n _moves({ legal = true, piece = void 0, square = void 0 } = {}) {\n const forSquare = square ? square.toLowerCase() : void 0;\n const forPiece = piece?.toLowerCase();\n const moves = [];\n const us = this._turn;\n const them = swapColor(us);\n let firstSquare = Ox88.a8;\n let lastSquare = Ox88.h1;\n let singleSquare = false;\n if (forSquare) {\n if (!(forSquare in Ox88)) {\n return [];\n } else {\n firstSquare = lastSquare = Ox88[forSquare];\n singleSquare = true;\n }\n }\n for (let from = firstSquare; from <= lastSquare; from++) {\n if (from & 136) {\n from += 7;\n continue;\n }\n if (!this._board[from] || this._board[from].color === them) {\n continue;\n }\n const { type } = this._board[from];\n let to;\n if (type === PAWN) {\n if (forPiece && forPiece !== type)\n continue;\n to = from + PAWN_OFFSETS[us][0];\n if (!this._board[to]) {\n addMove(moves, us, from, to, PAWN);\n to = from + PAWN_OFFSETS[us][1];\n if (SECOND_RANK[us] === rank(from) && !this._board[to]) {\n addMove(moves, us, from, to, PAWN, void 0, BITS.BIG_PAWN);\n }\n }\n for (let j = 2; j < 4; j++) {\n to = from + PAWN_OFFSETS[us][j];\n if (to & 136)\n continue;\n if (this._board[to]?.color === them) {\n addMove(moves, us, from, to, PAWN, this._board[to].type, BITS.CAPTURE);\n } else if (to === this._epSquare) {\n addMove(moves, us, from, to, PAWN, PAWN, BITS.EP_CAPTURE);\n }\n }\n } else {\n if (forPiece && forPiece !== type)\n continue;\n for (let j = 0, len = PIECE_OFFSETS[type].length; j < len; j++) {\n const offset = PIECE_OFFSETS[type][j];\n to = from;\n while (true) {\n to += offset;\n if (to & 136)\n break;\n if (!this._board[to]) {\n addMove(moves, us, from, to, type);\n } else {\n if (this._board[to].color === us)\n break;\n addMove(moves, us, from, to, type, this._board[to].type, BITS.CAPTURE);\n break;\n }\n if (type === KNIGHT || type === KING)\n break;\n }\n }\n }\n }\n if (forPiece === void 0 || forPiece === KING) {\n if (!singleSquare || lastSquare === this._kings[us]) {\n if (this._castling[us] & BITS.KSIDE_CASTLE) {\n const castlingFrom = this._kings[us];\n const castlingTo = castlingFrom + 2;\n if (!this._board[castlingFrom + 1] && !this._board[castlingTo] && !this._attacked(them, this._kings[us]) && !this._attacked(them, castlingFrom + 1) && !this._attacked(them, castlingTo)) {\n addMove(moves, us, this._kings[us], castlingTo, KING, void 0, BITS.KSIDE_CASTLE);\n }\n }\n if (this._castling[us] & BITS.QSIDE_CASTLE) {\n const castlingFrom = this._kings[us];\n const castlingTo = castlingFrom - 2;\n if (!this._board[castlingFrom - 1] && !this._board[castlingFrom - 2] && !this._board[castlingFrom - 3] && !this._attacked(them, this._kings[us]) && !this._attacked(them, castlingFrom - 1) && !this._attacked(them, castlingTo)) {\n addMove(moves, us, this._kings[us], castlingTo, KING, void 0, BITS.QSIDE_CASTLE);\n }\n }\n }\n }\n if (!legal || this._kings[us] === -1) {\n return moves;\n }\n const legalMoves2 = [];\n for (let i = 0, len = moves.length; i < len; i++) {\n this._makeMove(moves[i]);\n if (!this._isKingAttacked(us)) {\n legalMoves2.push(moves[i]);\n }\n this._undoMove();\n }\n return legalMoves2;\n }\n move(move, { strict = false } = {}) {\n let moveObj = null;\n if (typeof move === \"string\") {\n moveObj = this._moveFromSan(move, strict);\n } else if (move === null) {\n moveObj = this._moveFromSan(SAN_NULLMOVE, strict);\n } else if (typeof move === \"object\") {\n const moves = this._moves();\n for (let i = 0, len = moves.length; i < len; i++) {\n if (move.from === algebraic(moves[i].from) && move.to === algebraic(moves[i].to) && (!(\"promotion\" in moves[i]) || move.promotion === moves[i].promotion)) {\n moveObj = moves[i];\n break;\n }\n }\n }\n if (!moveObj) {\n if (typeof move === \"string\") {\n throw new Error(`Invalid move: ${move}`);\n } else {\n throw new Error(`Invalid move: ${JSON.stringify(move)}`);\n }\n }\n if (this.isCheck() && moveObj.flags & BITS.NULL_MOVE) {\n throw new Error(\"Null move not allowed when in check\");\n }\n const prettyMove = new Move(this, moveObj);\n this._makeMove(moveObj);\n this._incPositionCount();\n return prettyMove;\n }\n _push(move) {\n this._history.push({\n move,\n kings: { b: this._kings.b, w: this._kings.w },\n turn: this._turn,\n castling: { b: this._castling.b, w: this._castling.w },\n epSquare: this._epSquare,\n halfMoves: this._halfMoves,\n moveNumber: this._moveNumber\n });\n }\n _movePiece(from, to) {\n this._hash ^= this._pieceKey(from);\n this._board[to] = this._board[from];\n delete this._board[from];\n this._hash ^= this._pieceKey(to);\n }\n _makeMove(move) {\n const us = this._turn;\n const them = swapColor(us);\n this._push(move);\n if (move.flags & BITS.NULL_MOVE) {\n if (us === BLACK) {\n this._moveNumber++;\n }\n this._halfMoves++;\n this._turn = them;\n this._epSquare = EMPTY;\n return;\n }\n this._hash ^= this._epKey();\n this._hash ^= this._castlingKey();\n if (move.captured) {\n this._hash ^= this._pieceKey(move.to);\n }\n this._movePiece(move.from, move.to);\n if (move.flags & BITS.EP_CAPTURE) {\n if (this._turn === BLACK) {\n this._clear(move.to - 16);\n } else {\n this._clear(move.to + 16);\n }\n }\n if (move.promotion) {\n this._clear(move.to);\n this._set(move.to, { type: move.promotion, color: us });\n }\n if (this._board[move.to].type === KING) {\n this._kings[us] = move.to;\n if (move.flags & BITS.KSIDE_CASTLE) {\n const castlingTo = move.to - 1;\n const castlingFrom = move.to + 1;\n this._movePiece(castlingFrom, castlingTo);\n } else if (move.flags & BITS.QSIDE_CASTLE) {\n const castlingTo = move.to + 1;\n const castlingFrom = move.to - 2;\n this._movePiece(castlingFrom, castlingTo);\n }\n this._castling[us] = 0;\n }\n if (this._castling[us]) {\n for (let i = 0, len = ROOKS[us].length; i < len; i++) {\n if (move.from === ROOKS[us][i].square && this._castling[us] & ROOKS[us][i].flag) {\n this._castling[us] ^= ROOKS[us][i].flag;\n break;\n }\n }\n }\n if (this._castling[them]) {\n for (let i = 0, len = ROOKS[them].length; i < len; i++) {\n if (move.to === ROOKS[them][i].square && this._castling[them] & ROOKS[them][i].flag) {\n this._castling[them] ^= ROOKS[them][i].flag;\n break;\n }\n }\n }\n this._hash ^= this._castlingKey();\n if (move.flags & BITS.BIG_PAWN) {\n let epSquare;\n if (us === BLACK) {\n epSquare = move.to - 16;\n } else {\n epSquare = move.to + 16;\n }\n if (!(move.to - 1 & 136) && this._board[move.to - 1]?.type === PAWN && this._board[move.to - 1]?.color === them || !(move.to + 1 & 136) && this._board[move.to + 1]?.type === PAWN && this._board[move.to + 1]?.color === them) {\n this._epSquare = epSquare;\n this._hash ^= this._epKey();\n } else {\n this._epSquare = EMPTY;\n }\n } else {\n this._epSquare = EMPTY;\n }\n if (move.piece === PAWN) {\n this._halfMoves = 0;\n } else if (move.flags & (BITS.CAPTURE | BITS.EP_CAPTURE)) {\n this._halfMoves = 0;\n } else {\n this._halfMoves++;\n }\n if (us === BLACK) {\n this._moveNumber++;\n }\n this._turn = them;\n this._hash ^= SIDE_KEY;\n }\n undo() {\n const hash = this._hash;\n const move = this._undoMove();\n if (move) {\n const prettyMove = new Move(this, move);\n this._decPositionCount(hash);\n return prettyMove;\n }\n return null;\n }\n _undoMove() {\n const old = this._history.pop();\n if (old === void 0) {\n return null;\n }\n this._hash ^= this._epKey();\n this._hash ^= this._castlingKey();\n const move = old.move;\n this._kings = old.kings;\n this._turn = old.turn;\n this._castling = old.castling;\n this._epSquare = old.epSquare;\n this._halfMoves = old.halfMoves;\n this._moveNumber = old.moveNumber;\n this._hash ^= this._epKey();\n this._hash ^= this._castlingKey();\n this._hash ^= SIDE_KEY;\n const us = this._turn;\n const them = swapColor(us);\n if (move.flags & BITS.NULL_MOVE) {\n return move;\n }\n this._movePiece(move.to, move.from);\n if (move.piece) {\n this._clear(move.from);\n this._set(move.from, { type: move.piece, color: us });\n }\n if (move.captured) {\n if (move.flags & BITS.EP_CAPTURE) {\n let index;\n if (us === BLACK) {\n index = move.to - 16;\n } else {\n index = move.to + 16;\n }\n this._set(index, { type: PAWN, color: them });\n } else {\n this._set(move.to, { type: move.captured, color: them });\n }\n }\n if (move.flags & (BITS.KSIDE_CASTLE | BITS.QSIDE_CASTLE)) {\n let castlingTo, castlingFrom;\n if (move.flags & BITS.KSIDE_CASTLE) {\n castlingTo = move.to + 1;\n castlingFrom = move.to - 1;\n } else {\n castlingTo = move.to - 2;\n castlingFrom = move.to + 1;\n }\n this._movePiece(castlingFrom, castlingTo);\n }\n return move;\n }\n pgn({ newline = \"\\n\", maxWidth = 0 } = {}) {\n const result = [];\n let headerExists = false;\n for (const i in this._header) {\n const headerTag = this._header[i];\n if (headerTag)\n result.push(`[${i} \"${this._header[i]}\"]` + newline);\n headerExists = true;\n }\n if (headerExists && this._history.length) {\n result.push(newline);\n }\n const appendComment = (moveString2) => {\n const comment = this._comments[this.fen()];\n if (typeof comment !== \"undefined\") {\n const delimiter = moveString2.length > 0 ? \" \" : \"\";\n moveString2 = `${moveString2}${delimiter}{${comment}}`;\n }\n return moveString2;\n };\n const reversedHistory = [];\n while (this._history.length > 0) {\n reversedHistory.push(this._undoMove());\n }\n const moves = [];\n let moveString = \"\";\n if (reversedHistory.length === 0) {\n moves.push(appendComment(\"\"));\n }\n while (reversedHistory.length > 0) {\n moveString = appendComment(moveString);\n const move = reversedHistory.pop();\n if (!move) {\n break;\n }\n if (!this._history.length && move.color === \"b\") {\n const prefix = `${this._moveNumber}. ...`;\n moveString = moveString ? `${moveString} ${prefix}` : prefix;\n } else if (move.color === \"w\") {\n if (moveString.length) {\n moves.push(moveString);\n }\n moveString = this._moveNumber + \".\";\n }\n moveString = moveString + \" \" + this._moveToSan(move, this._moves({ legal: true }));\n this._makeMove(move);\n }\n if (moveString.length) {\n moves.push(appendComment(moveString));\n }\n moves.push(this._header.Result || \"*\");\n if (maxWidth === 0) {\n return result.join(\"\") + moves.join(\" \");\n }\n const strip = function() {\n if (result.length > 0 && result[result.length - 1] === \" \") {\n result.pop();\n return true;\n }\n return false;\n };\n const wrapComment = function(width, move) {\n for (const token of move.split(\" \")) {\n if (!token) {\n continue;\n }\n if (width + token.length > maxWidth) {\n while (strip()) {\n width--;\n }\n result.push(newline);\n width = 0;\n }\n result.push(token);\n width += token.length;\n result.push(\" \");\n width++;\n }\n if (strip()) {\n width--;\n }\n return width;\n };\n let currentWidth = 0;\n for (let i = 0; i < moves.length; i++) {\n if (currentWidth + moves[i].length > maxWidth) {\n if (moves[i].includes(\"{\")) {\n currentWidth = wrapComment(currentWidth, moves[i]);\n continue;\n }\n }\n if (currentWidth + moves[i].length > maxWidth && i !== 0) {\n if (result[result.length - 1] === \" \") {\n result.pop();\n }\n result.push(newline);\n currentWidth = 0;\n } else if (i !== 0) {\n result.push(\" \");\n currentWidth++;\n }\n result.push(moves[i]);\n currentWidth += moves[i].length;\n }\n return result.join(\"\");\n }\n /**\n * @deprecated Use `setHeader` and `getHeaders` instead. This method will return null header tags (which is not what you want)\n */\n header(...args) {\n for (let i = 0; i < args.length; i += 2) {\n if (typeof args[i] === \"string\" && typeof args[i + 1] === \"string\") {\n this._header[args[i]] = args[i + 1];\n }\n }\n return this._header;\n }\n // TODO: value validation per spec\n setHeader(key, value) {\n this._header[key] = value ?? SEVEN_TAG_ROSTER[key] ?? null;\n return this.getHeaders();\n }\n removeHeader(key) {\n if (key in this._header) {\n this._header[key] = SEVEN_TAG_ROSTER[key] || null;\n return true;\n }\n return false;\n }\n // return only non-null headers (omit placemarker nulls)\n getHeaders() {\n const nonNullHeaders = {};\n for (const [key, value] of Object.entries(this._header)) {\n if (value !== null) {\n nonNullHeaders[key] = value;\n }\n }\n return nonNullHeaders;\n }\n loadPgn(pgn2, { strict = false, newlineChar = \"\\r?\\n\" } = {}) {\n if (newlineChar !== \"\\r?\\n\") {\n pgn2 = pgn2.replace(new RegExp(newlineChar, \"g\"), \"\\n\");\n }\n const parsedPgn = peg$parse(pgn2);\n this.reset();\n const headers = parsedPgn.headers;\n let fen = \"\";\n for (const key in headers) {\n if (key.toLowerCase() === \"fen\") {\n fen = headers[key];\n }\n this.header(key, headers[key]);\n }\n if (!strict) {\n if (fen) {\n this.load(fen, { preserveHeaders: true });\n }\n } else {\n if (headers[\"SetUp\"] === \"1\") {\n if (!(\"FEN\" in headers)) {\n throw new Error(\"Invalid PGN: FEN tag must be supplied with SetUp tag\");\n }\n this.load(headers[\"FEN\"], { preserveHeaders: true });\n }\n }\n let node2 = parsedPgn.root;\n while (node2) {\n if (node2.move) {\n const move = this._moveFromSan(node2.move, strict);\n if (move == null) {\n throw new Error(`Invalid move in PGN: ${node2.move}`);\n } else {\n this._makeMove(move);\n this._incPositionCount();\n }\n }\n if (node2.comment !== void 0) {\n this._comments[this.fen()] = node2.comment;\n }\n node2 = node2.variations[0];\n }\n const result = parsedPgn.result;\n if (result && Object.keys(this._header).length && this._header[\"Result\"] !== result) {\n this.setHeader(\"Result\", result);\n }\n }\n /*\n * Convert a move from 0x88 coordinates to Standard Algebraic Notation\n * (SAN)\n *\n * @param {boolean} strict Use the strict SAN parser. It will throw errors\n * on overly disambiguated moves (see below):\n *\n * r1bqkbnr/ppp2ppp/2n5/1B1pP3/4P3/8/PPPP2PP/RNBQK1NR b KQkq - 2 4\n * 4. ... Nge7 is overly disambiguated because the knight on c6 is pinned\n * 4. ... Ne7 is technically the valid SAN\n */\n _moveToSan(move, moves) {\n let output = \"\";\n if (move.flags & BITS.KSIDE_CASTLE) {\n output = \"O-O\";\n } else if (move.flags & BITS.QSIDE_CASTLE) {\n output = \"O-O-O\";\n } else if (move.flags & BITS.NULL_MOVE) {\n return SAN_NULLMOVE;\n } else {\n if (move.piece !== PAWN) {\n const disambiguator = getDisambiguator(move, moves);\n output += move.piece.toUpperCase() + disambiguator;\n }\n if (move.flags & (BITS.CAPTURE | BITS.EP_CAPTURE)) {\n if (move.piece === PAWN) {\n output += algebraic(move.from)[0];\n }\n output += \"x\";\n }\n output += algebraic(move.to);\n if (move.promotion) {\n output += \"=\" + move.promotion.toUpperCase();\n }\n }\n this._makeMove(move);\n if (this.isCheck()) {\n if (this.isCheckmate()) {\n output += \"#\";\n } else {\n output += \"+\";\n }\n }\n this._undoMove();\n return output;\n }\n // convert a move from Standard Algebraic Notation (SAN) to 0x88 coordinates\n _moveFromSan(move, strict = false) {\n let cleanMove = strippedSan(move);\n if (!strict) {\n if (cleanMove === \"0-0\") {\n cleanMove = \"O-O\";\n } else if (cleanMove === \"0-0-0\") {\n cleanMove = \"O-O-O\";\n }\n }\n if (cleanMove == SAN_NULLMOVE) {\n const res = {\n color: this._turn,\n from: 0,\n to: 0,\n piece: \"k\",\n flags: BITS.NULL_MOVE\n };\n return res;\n }\n let pieceType = inferPieceType(cleanMove);\n let moves = this._moves({ legal: true, piece: pieceType });\n for (let i = 0, len = moves.length; i < len; i++) {\n if (cleanMove === strippedSan(this._moveToSan(moves[i], moves))) {\n return moves[i];\n }\n }\n if (strict) {\n return null;\n }\n let piece = void 0;\n let matches = void 0;\n let from = void 0;\n let to = void 0;\n let promotion = void 0;\n let overlyDisambiguated = false;\n matches = cleanMove.match(/([pnbrqkPNBRQK])?([a-h][1-8])x?-?([a-h][1-8])([qrbnQRBN])?/);\n if (matches) {\n piece = matches[1];\n from = matches[2];\n to = matches[3];\n promotion = matches[4];\n if (from.length == 1) {\n overlyDisambiguated = true;\n }\n } else {\n matches = cleanMove.match(/([pnbrqkPNBRQK])?([a-h]?[1-8]?)x?-?([a-h][1-8])([qrbnQRBN])?/);\n if (matches) {\n piece = matches[1];\n from = matches[2];\n to = matches[3];\n promotion = matches[4];\n if (from.length == 1) {\n overlyDisambiguated = true;\n }\n }\n }\n pieceType = inferPieceType(cleanMove);\n moves = this._moves({\n legal: true,\n piece: piece ? piece : pieceType\n });\n if (!to) {\n return null;\n }\n for (let i = 0, len = moves.length; i < len; i++) {\n if (!from) {\n if (cleanMove === strippedSan(this._moveToSan(moves[i], moves)).replace(\"x\", \"\")) {\n return moves[i];\n }\n } else if ((!piece || piece.toLowerCase() == moves[i].piece) && Ox88[from] == moves[i].from && Ox88[to] == moves[i].to && (!promotion || promotion.toLowerCase() == moves[i].promotion)) {\n return moves[i];\n } else if (overlyDisambiguated) {\n const square = algebraic(moves[i].from);\n if ((!piece || piece.toLowerCase() == moves[i].piece) && Ox88[to] == moves[i].to && (from == square[0] || from == square[1]) && (!promotion || promotion.toLowerCase() == moves[i].promotion)) {\n return moves[i];\n }\n }\n }\n return null;\n }\n ascii() {\n let s = \" +------------------------+\\n\";\n for (let i = Ox88.a8; i <= Ox88.h1; i++) {\n if (file(i) === 0) {\n s += \" \" + \"87654321\"[rank(i)] + \" |\";\n }\n if (this._board[i]) {\n const piece = this._board[i].type;\n const color = this._board[i].color;\n const symbol = color === WHITE ? piece.toUpperCase() : piece.toLowerCase();\n s += \" \" + symbol + \" \";\n } else {\n s += \" . \";\n }\n if (i + 1 & 136) {\n s += \"|\\n\";\n i += 8;\n }\n }\n s += \" +------------------------+\\n\";\n s += \" a b c d e f g h\";\n return s;\n }\n perft(depth) {\n const moves = this._moves({ legal: false });\n let nodes = 0;\n const color = this._turn;\n for (let i = 0, len = moves.length; i < len; i++) {\n this._makeMove(moves[i]);\n if (!this._isKingAttacked(color)) {\n if (depth - 1 > 0) {\n nodes += this.perft(depth - 1);\n } else {\n nodes++;\n }\n }\n this._undoMove();\n }\n return nodes;\n }\n setTurn(color) {\n if (this._turn == color) {\n return false;\n }\n this.move(\"--\");\n return true;\n }\n turn() {\n return this._turn;\n }\n board() {\n const output = [];\n let row = [];\n for (let i = Ox88.a8; i <= Ox88.h1; i++) {\n if (this._board[i] == null) {\n row.push(null);\n } else {\n row.push({\n square: algebraic(i),\n type: this._board[i].type,\n color: this._board[i].color\n });\n }\n if (i + 1 & 136) {\n output.push(row);\n row = [];\n i += 8;\n }\n }\n return output;\n }\n squareColor(square) {\n if (square in Ox88) {\n const sq = Ox88[square];\n return (rank(sq) + file(sq)) % 2 === 0 ? \"light\" : \"dark\";\n }\n return null;\n }\n history({ verbose = false } = {}) {\n const reversedHistory = [];\n const moveHistory = [];\n while (this._history.length > 0) {\n reversedHistory.push(this._undoMove());\n }\n while (true) {\n const move = reversedHistory.pop();\n if (!move) {\n break;\n }\n if (verbose) {\n moveHistory.push(new Move(this, move));\n } else {\n moveHistory.push(this._moveToSan(move, this._moves()));\n }\n this._makeMove(move);\n }\n return moveHistory;\n }\n /*\n * Keeps track of position occurrence counts for the purpose of repetition\n * checking. Old positions are removed from the map if their counts are reduced to 0.\n */\n _getPositionCount(hash) {\n return this._positionCount.get(hash) ?? 0;\n }\n _incPositionCount() {\n this._positionCount.set(this._hash, (this._positionCount.get(this._hash) ?? 0) + 1);\n }\n _decPositionCount(hash) {\n const currentCount = this._positionCount.get(hash) ?? 0;\n if (currentCount === 1) {\n this._positionCount.delete(hash);\n } else {\n this._positionCount.set(hash, currentCount - 1);\n }\n }\n _pruneComments() {\n const reversedHistory = [];\n const currentComments = {};\n const copyComment = (fen) => {\n if (fen in this._comments) {\n currentComments[fen] = this._comments[fen];\n }\n };\n while (this._history.length > 0) {\n reversedHistory.push(this._undoMove());\n }\n copyComment(this.fen());\n while (true) {\n const move = reversedHistory.pop();\n if (!move) {\n break;\n }\n this._makeMove(move);\n copyComment(this.fen());\n }\n this._comments = currentComments;\n }\n getComment() {\n return this._comments[this.fen()];\n }\n setComment(comment) {\n this._comments[this.fen()] = comment.replace(\"{\", \"[\").replace(\"}\", \"]\");\n }\n /**\n * @deprecated Renamed to `removeComment` for consistency\n */\n deleteComment() {\n return this.removeComment();\n }\n removeComment() {\n const comment = this._comments[this.fen()];\n delete this._comments[this.fen()];\n return comment;\n }\n getComments() {\n this._pruneComments();\n return Object.keys(this._comments).map((fen) => {\n return { fen, comment: this._comments[fen] };\n });\n }\n /**\n * @deprecated Renamed to `removeComments` for consistency\n */\n deleteComments() {\n return this.removeComments();\n }\n removeComments() {\n this._pruneComments();\n return Object.keys(this._comments).map((fen) => {\n const comment = this._comments[fen];\n delete this._comments[fen];\n return { fen, comment };\n });\n }\n setCastlingRights(color, rights) {\n for (const side of [KING, QUEEN]) {\n if (rights[side] !== void 0) {\n if (rights[side]) {\n this._castling[color] |= SIDES[side];\n } else {\n this._castling[color] &= ~SIDES[side];\n }\n }\n }\n this._updateCastlingRights();\n const result = this.getCastlingRights(color);\n return (rights[KING] === void 0 || rights[KING] === result[KING]) && (rights[QUEEN] === void 0 || rights[QUEEN] === result[QUEEN]);\n }\n getCastlingRights(color) {\n return {\n [KING]: (this._castling[color] & SIDES[KING]) !== 0,\n [QUEEN]: (this._castling[color] & SIDES[QUEEN]) !== 0\n };\n }\n moveNumber() {\n return this._moveNumber;\n }\n};\n\n// libs/test-harness/fixtures/library-reuse/chess-entry.ts\nvar chess = new Chess();\nvar legalMoves = chess.moves({ verbose: true });\nvar chess_entry_default = legalMoves.some(\n (move) => move.from === \"e2\" && move.to === \"e6\"\n);\nexport {\n chess_entry_default as default\n};\n", + "sourceMap": "{\"mappings\":\"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\",\"names\":[\"node\",\"expected\",\"found\",\"chess\",\"legalMoves\",\"moveString\",\"pgn\",\"parse\",\"node\"],\"sources\":[\"../node_modules/.pnpm/chess.js@1.4.0/node_modules/chess.js/src/pgn.js\",\"../node_modules/.pnpm/chess.js@1.4.0/node_modules/src/chess.ts\",\"../libs/test-harness/fixtures/library-reuse/chess-entry.ts\"],\"sourcesContent\":[\"// @generated by Peggy 4.2.0.\\n//\\n// https://peggyjs.org/\\n\\n\\n\\n function rootNode(comment) {\\n \\treturn comment !== null ? { comment, variations: [] } : { variations: []}\\n }\\n\\n function node(move, suffix, nag, comment, variations) {\\n \\tconst node = { move, variations }\\n\\n if (suffix) {\\n \\tnode.suffix = suffix\\n }\\n\\n if (nag) {\\n \\tnode.nag = nag\\n }\\n\\n if (comment !== null) {\\n \\tnode.comment = comment\\n }\\n\\n return node\\n }\\n\\n function lineToTree(...nodes) {\\n \\tconst [root, ...rest] = nodes;\\n\\n let parent = root\\n\\n for (const child of rest) {\\n \\tif (child !== null) {\\n \\tparent.variations = [child, ...child.variations]\\n child.variations = []\\n parent = child\\n }\\n }\\n\\n \\treturn root\\n }\\n\\n function pgn(headers, game) {\\n \\tif (game.marker && game.marker.comment) {\\n \\tlet node = game.root\\n while (true) {\\n \\tconst next = node.variations[0]\\n if (!next) {\\n \\tnode.comment = game.marker.comment\\n \\tbreak\\n }\\n node = next\\n }\\n }\\n\\n \\treturn {\\n \\theaders,\\n root: game.root,\\n result: (game.marker && game.marker.result) ?? undefined\\n }\\n }\\n\\nfunction peg$subclass(child, parent) {\\n function C() { this.constructor = child; }\\n C.prototype = parent.prototype;\\n child.prototype = new C();\\n}\\n\\nfunction peg$SyntaxError(message, expected, found, location) {\\n var self = Error.call(this, message);\\n // istanbul ignore next Check is a necessary evil to support older environments\\n if (Object.setPrototypeOf) {\\n Object.setPrototypeOf(self, peg$SyntaxError.prototype);\\n }\\n self.expected = expected;\\n self.found = found;\\n self.location = location;\\n self.name = \\\"SyntaxError\\\";\\n return self;\\n}\\n\\npeg$subclass(peg$SyntaxError, Error);\\n\\nfunction peg$padEnd(str, targetLength, padString) {\\n padString = padString || \\\" \\\";\\n if (str.length > targetLength) { return str; }\\n targetLength -= str.length;\\n padString += padString.repeat(targetLength);\\n return str + padString.slice(0, targetLength);\\n}\\n\\npeg$SyntaxError.prototype.format = function(sources) {\\n var str = \\\"Error: \\\" + this.message;\\n if (this.location) {\\n var src = null;\\n var k;\\n for (k = 0; k < sources.length; k++) {\\n if (sources[k].source === this.location.source) {\\n src = sources[k].text.split(/\\\\r\\\\n|\\\\n|\\\\r/g);\\n break;\\n }\\n }\\n var s = this.location.start;\\n var offset_s = (this.location.source && (typeof this.location.source.offset === \\\"function\\\"))\\n ? this.location.source.offset(s)\\n : s;\\n var loc = this.location.source + \\\":\\\" + offset_s.line + \\\":\\\" + offset_s.column;\\n if (src) {\\n var e = this.location.end;\\n var filler = peg$padEnd(\\\"\\\", offset_s.line.toString().length, ' ');\\n var line = src[s.line - 1];\\n var last = s.line === e.line ? e.column : line.length + 1;\\n var hatLen = (last - s.column) || 1;\\n str += \\\"\\\\n --> \\\" + loc + \\\"\\\\n\\\"\\n + filler + \\\" |\\\\n\\\"\\n + offset_s.line + \\\" | \\\" + line + \\\"\\\\n\\\"\\n + filler + \\\" | \\\" + peg$padEnd(\\\"\\\", s.column - 1, ' ')\\n + peg$padEnd(\\\"\\\", hatLen, \\\"^\\\");\\n } else {\\n str += \\\"\\\\n at \\\" + loc;\\n }\\n }\\n return str;\\n};\\n\\npeg$SyntaxError.buildMessage = function(expected, found) {\\n var DESCRIBE_EXPECTATION_FNS = {\\n literal: function(expectation) {\\n return \\\"\\\\\\\"\\\" + literalEscape(expectation.text) + \\\"\\\\\\\"\\\";\\n },\\n\\n class: function(expectation) {\\n var escapedParts = expectation.parts.map(function(part) {\\n return Array.isArray(part)\\n ? classEscape(part[0]) + \\\"-\\\" + classEscape(part[1])\\n : classEscape(part);\\n });\\n\\n return \\\"[\\\" + (expectation.inverted ? \\\"^\\\" : \\\"\\\") + escapedParts.join(\\\"\\\") + \\\"]\\\";\\n },\\n\\n any: function() {\\n return \\\"any character\\\";\\n },\\n\\n end: function() {\\n return \\\"end of input\\\";\\n },\\n\\n other: function(expectation) {\\n return expectation.description;\\n }\\n };\\n\\n function hex(ch) {\\n return ch.charCodeAt(0).toString(16).toUpperCase();\\n }\\n\\n function literalEscape(s) {\\n return s\\n .replace(/\\\\\\\\/g, \\\"\\\\\\\\\\\\\\\\\\\")\\n .replace(/\\\"/g, \\\"\\\\\\\\\\\\\\\"\\\")\\n .replace(/\\\\0/g, \\\"\\\\\\\\0\\\")\\n .replace(/\\\\t/g, \\\"\\\\\\\\t\\\")\\n .replace(/\\\\n/g, \\\"\\\\\\\\n\\\")\\n .replace(/\\\\r/g, \\\"\\\\\\\\r\\\")\\n .replace(/[\\\\x00-\\\\x0F]/g, function(ch) { return \\\"\\\\\\\\x0\\\" + hex(ch); })\\n .replace(/[\\\\x10-\\\\x1F\\\\x7F-\\\\x9F]/g, function(ch) { return \\\"\\\\\\\\x\\\" + hex(ch); });\\n }\\n\\n function classEscape(s) {\\n return s\\n .replace(/\\\\\\\\/g, \\\"\\\\\\\\\\\\\\\\\\\")\\n .replace(/\\\\]/g, \\\"\\\\\\\\]\\\")\\n .replace(/\\\\^/g, \\\"\\\\\\\\^\\\")\\n .replace(/-/g, \\\"\\\\\\\\-\\\")\\n .replace(/\\\\0/g, \\\"\\\\\\\\0\\\")\\n .replace(/\\\\t/g, \\\"\\\\\\\\t\\\")\\n .replace(/\\\\n/g, \\\"\\\\\\\\n\\\")\\n .replace(/\\\\r/g, \\\"\\\\\\\\r\\\")\\n .replace(/[\\\\x00-\\\\x0F]/g, function(ch) { return \\\"\\\\\\\\x0\\\" + hex(ch); })\\n .replace(/[\\\\x10-\\\\x1F\\\\x7F-\\\\x9F]/g, function(ch) { return \\\"\\\\\\\\x\\\" + hex(ch); });\\n }\\n\\n function describeExpectation(expectation) {\\n return DESCRIBE_EXPECTATION_FNS[expectation.type](expectation);\\n }\\n\\n function describeExpected(expected) {\\n var descriptions = expected.map(describeExpectation);\\n var i, j;\\n\\n descriptions.sort();\\n\\n if (descriptions.length > 0) {\\n for (i = 1, j = 1; i < descriptions.length; i++) {\\n if (descriptions[i - 1] !== descriptions[i]) {\\n descriptions[j] = descriptions[i];\\n j++;\\n }\\n }\\n descriptions.length = j;\\n }\\n\\n switch (descriptions.length) {\\n case 1:\\n return descriptions[0];\\n\\n case 2:\\n return descriptions[0] + \\\" or \\\" + descriptions[1];\\n\\n default:\\n return descriptions.slice(0, -1).join(\\\", \\\")\\n + \\\", or \\\"\\n + descriptions[descriptions.length - 1];\\n }\\n }\\n\\n function describeFound(found) {\\n return found ? \\\"\\\\\\\"\\\" + literalEscape(found) + \\\"\\\\\\\"\\\" : \\\"end of input\\\";\\n }\\n\\n return \\\"Expected \\\" + describeExpected(expected) + \\\" but \\\" + describeFound(found) + \\\" found.\\\";\\n};\\n\\nfunction peg$parse(input, options) {\\n options = options !== undefined ? options : {};\\n\\n var peg$FAILED = {};\\n var peg$source = options.grammarSource;\\n\\n var peg$startRuleFunctions = { pgn: peg$parsepgn };\\n var peg$startRuleFunction = peg$parsepgn;\\n\\n var peg$c0 = \\\"[\\\";\\n var peg$c1 = \\\"\\\\\\\"\\\";\\n var peg$c2 = \\\"]\\\";\\n var peg$c3 = \\\".\\\";\\n var peg$c4 = \\\"O-O-O\\\";\\n var peg$c5 = \\\"O-O\\\";\\n var peg$c6 = \\\"0-0-0\\\";\\n var peg$c7 = \\\"0-0\\\";\\n var peg$c8 = \\\"$\\\";\\n var peg$c9 = \\\"{\\\";\\n var peg$c10 = \\\"}\\\";\\n var peg$c11 = \\\";\\\";\\n var peg$c12 = \\\"(\\\";\\n var peg$c13 = \\\")\\\";\\n var peg$c14 = \\\"1-0\\\";\\n var peg$c15 = \\\"0-1\\\";\\n var peg$c16 = \\\"1/2-1/2\\\";\\n var peg$c17 = \\\"*\\\";\\n\\n var peg$r0 = /^[a-zA-Z]/;\\n var peg$r1 = /^[^\\\"]/;\\n var peg$r2 = /^[0-9]/;\\n var peg$r3 = /^[.]/;\\n var peg$r4 = /^[a-zA-Z1-8\\\\-=]/;\\n var peg$r5 = /^[+#]/;\\n var peg$r6 = /^[!?]/;\\n var peg$r7 = /^[^}]/;\\n var peg$r8 = /^[^\\\\r\\\\n]/;\\n var peg$r9 = /^[ \\\\t\\\\r\\\\n]/;\\n\\n var peg$e0 = peg$otherExpectation(\\\"tag pair\\\");\\n var peg$e1 = peg$literalExpectation(\\\"[\\\", false);\\n var peg$e2 = peg$literalExpectation(\\\"\\\\\\\"\\\", false);\\n var peg$e3 = peg$literalExpectation(\\\"]\\\", false);\\n var peg$e4 = peg$otherExpectation(\\\"tag name\\\");\\n var peg$e5 = peg$classExpectation([[\\\"a\\\", \\\"z\\\"], [\\\"A\\\", \\\"Z\\\"]], false, false);\\n var peg$e6 = peg$otherExpectation(\\\"tag value\\\");\\n var peg$e7 = peg$classExpectation([\\\"\\\\\\\"\\\"], true, false);\\n var peg$e8 = peg$otherExpectation(\\\"move number\\\");\\n var peg$e9 = peg$classExpectation([[\\\"0\\\", \\\"9\\\"]], false, false);\\n var peg$e10 = peg$literalExpectation(\\\".\\\", false);\\n var peg$e11 = peg$classExpectation([\\\".\\\"], false, false);\\n var peg$e12 = peg$otherExpectation(\\\"standard algebraic notation\\\");\\n var peg$e13 = peg$literalExpectation(\\\"O-O-O\\\", false);\\n var peg$e14 = peg$literalExpectation(\\\"O-O\\\", false);\\n var peg$e15 = peg$literalExpectation(\\\"0-0-0\\\", false);\\n var peg$e16 = peg$literalExpectation(\\\"0-0\\\", false);\\n var peg$e17 = peg$classExpectation([[\\\"a\\\", \\\"z\\\"], [\\\"A\\\", \\\"Z\\\"], [\\\"1\\\", \\\"8\\\"], \\\"-\\\", \\\"=\\\"], false, false);\\n var peg$e18 = peg$classExpectation([\\\"+\\\", \\\"#\\\"], false, false);\\n var peg$e19 = peg$otherExpectation(\\\"suffix annotation\\\");\\n var peg$e20 = peg$classExpectation([\\\"!\\\", \\\"?\\\"], false, false);\\n var peg$e21 = peg$otherExpectation(\\\"NAG\\\");\\n var peg$e22 = peg$literalExpectation(\\\"$\\\", false);\\n var peg$e23 = peg$otherExpectation(\\\"brace comment\\\");\\n var peg$e24 = peg$literalExpectation(\\\"{\\\", false);\\n var peg$e25 = peg$classExpectation([\\\"}\\\"], true, false);\\n var peg$e26 = peg$literalExpectation(\\\"}\\\", false);\\n var peg$e27 = peg$otherExpectation(\\\"rest of line comment\\\");\\n var peg$e28 = peg$literalExpectation(\\\";\\\", false);\\n var peg$e29 = peg$classExpectation([\\\"\\\\r\\\", \\\"\\\\n\\\"], true, false);\\n var peg$e30 = peg$otherExpectation(\\\"variation\\\");\\n var peg$e31 = peg$literalExpectation(\\\"(\\\", false);\\n var peg$e32 = peg$literalExpectation(\\\")\\\", false);\\n var peg$e33 = peg$otherExpectation(\\\"game termination marker\\\");\\n var peg$e34 = peg$literalExpectation(\\\"1-0\\\", false);\\n var peg$e35 = peg$literalExpectation(\\\"0-1\\\", false);\\n var peg$e36 = peg$literalExpectation(\\\"1/2-1/2\\\", false);\\n var peg$e37 = peg$literalExpectation(\\\"*\\\", false);\\n var peg$e38 = peg$otherExpectation(\\\"whitespace\\\");\\n var peg$e39 = peg$classExpectation([\\\" \\\", \\\"\\\\t\\\", \\\"\\\\r\\\", \\\"\\\\n\\\"], false, false);\\n\\n var peg$f0 = function(headers, game) { return pgn(headers, game) };\\n var peg$f1 = function(tagPairs) { return Object.fromEntries(tagPairs) };\\n var peg$f2 = function(tagName, tagValue) { return [tagName, tagValue] };\\n var peg$f3 = function(root, marker) { return { root, marker} };\\n var peg$f4 = function(comment, moves) { return lineToTree(rootNode(comment), ...moves.flat()) };\\n var peg$f5 = function(san, suffix, nag, comment, variations) { return node(san, suffix, nag, comment, variations) };\\n var peg$f6 = function(nag) { return nag };\\n var peg$f7 = function(comment) { return comment.replace(/[\\\\r\\\\n]+/g, \\\" \\\") };\\n var peg$f8 = function(comment) { return comment.trim() };\\n var peg$f9 = function(line) { return line };\\n var peg$f10 = function(result, comment) { return { result, comment } };\\n var peg$currPos = options.peg$currPos | 0;\\n var peg$savedPos = peg$currPos;\\n var peg$posDetailsCache = [{ line: 1, column: 1 }];\\n var peg$maxFailPos = peg$currPos;\\n var peg$maxFailExpected = options.peg$maxFailExpected || [];\\n var peg$silentFails = options.peg$silentFails | 0;\\n\\n var peg$result;\\n\\n if (options.startRule) {\\n if (!(options.startRule in peg$startRuleFunctions)) {\\n throw new Error(\\\"Can't start parsing from rule \\\\\\\"\\\" + options.startRule + \\\"\\\\\\\".\\\");\\n }\\n\\n peg$startRuleFunction = peg$startRuleFunctions[options.startRule];\\n }\\n\\n function text() {\\n return input.substring(peg$savedPos, peg$currPos);\\n }\\n\\n function offset() {\\n return peg$savedPos;\\n }\\n\\n function range() {\\n return {\\n source: peg$source,\\n start: peg$savedPos,\\n end: peg$currPos\\n };\\n }\\n\\n function location() {\\n return peg$computeLocation(peg$savedPos, peg$currPos);\\n }\\n\\n function expected(description, location) {\\n location = location !== undefined\\n ? location\\n : peg$computeLocation(peg$savedPos, peg$currPos);\\n\\n throw peg$buildStructuredError(\\n [peg$otherExpectation(description)],\\n input.substring(peg$savedPos, peg$currPos),\\n location\\n );\\n }\\n\\n function error(message, location) {\\n location = location !== undefined\\n ? location\\n : peg$computeLocation(peg$savedPos, peg$currPos);\\n\\n throw peg$buildSimpleError(message, location);\\n }\\n\\n function peg$literalExpectation(text, ignoreCase) {\\n return { type: \\\"literal\\\", text: text, ignoreCase: ignoreCase };\\n }\\n\\n function peg$classExpectation(parts, inverted, ignoreCase) {\\n return { type: \\\"class\\\", parts: parts, inverted: inverted, ignoreCase: ignoreCase };\\n }\\n\\n function peg$anyExpectation() {\\n return { type: \\\"any\\\" };\\n }\\n\\n function peg$endExpectation() {\\n return { type: \\\"end\\\" };\\n }\\n\\n function peg$otherExpectation(description) {\\n return { type: \\\"other\\\", description: description };\\n }\\n\\n function peg$computePosDetails(pos) {\\n var details = peg$posDetailsCache[pos];\\n var p;\\n\\n if (details) {\\n return details;\\n } else {\\n if (pos >= peg$posDetailsCache.length) {\\n p = peg$posDetailsCache.length - 1;\\n } else {\\n p = pos;\\n while (!peg$posDetailsCache[--p]) {}\\n }\\n\\n details = peg$posDetailsCache[p];\\n details = {\\n line: details.line,\\n column: details.column\\n };\\n\\n while (p < pos) {\\n if (input.charCodeAt(p) === 10) {\\n details.line++;\\n details.column = 1;\\n } else {\\n details.column++;\\n }\\n\\n p++;\\n }\\n\\n peg$posDetailsCache[pos] = details;\\n\\n return details;\\n }\\n }\\n\\n function peg$computeLocation(startPos, endPos, offset) {\\n var startPosDetails = peg$computePosDetails(startPos);\\n var endPosDetails = peg$computePosDetails(endPos);\\n\\n var res = {\\n source: peg$source,\\n start: {\\n offset: startPos,\\n line: startPosDetails.line,\\n column: startPosDetails.column\\n },\\n end: {\\n offset: endPos,\\n line: endPosDetails.line,\\n column: endPosDetails.column\\n }\\n };\\n if (offset && peg$source && (typeof peg$source.offset === \\\"function\\\")) {\\n res.start = peg$source.offset(res.start);\\n res.end = peg$source.offset(res.end);\\n }\\n return res;\\n }\\n\\n function peg$fail(expected) {\\n if (peg$currPos < peg$maxFailPos) { return; }\\n\\n if (peg$currPos > peg$maxFailPos) {\\n peg$maxFailPos = peg$currPos;\\n peg$maxFailExpected = [];\\n }\\n\\n peg$maxFailExpected.push(expected);\\n }\\n\\n function peg$buildSimpleError(message, location) {\\n return new peg$SyntaxError(message, null, null, location);\\n }\\n\\n function peg$buildStructuredError(expected, found, location) {\\n return new peg$SyntaxError(\\n peg$SyntaxError.buildMessage(expected, found),\\n expected,\\n found,\\n location\\n );\\n }\\n\\n function peg$parsepgn() {\\n var s0, s1, s2;\\n\\n s0 = peg$currPos;\\n s1 = peg$parsetagPairSection();\\n s2 = peg$parsemoveTextSection();\\n peg$savedPos = s0;\\n s0 = peg$f0(s1, s2);\\n\\n return s0;\\n }\\n\\n function peg$parsetagPairSection() {\\n var s0, s1, s2;\\n\\n s0 = peg$currPos;\\n s1 = [];\\n s2 = peg$parsetagPair();\\n while (s2 !== peg$FAILED) {\\n s1.push(s2);\\n s2 = peg$parsetagPair();\\n }\\n s2 = peg$parse_();\\n peg$savedPos = s0;\\n s0 = peg$f1(s1);\\n\\n return s0;\\n }\\n\\n function peg$parsetagPair() {\\n var s0, s1, s2, s3, s4, s5, s6, s7, s8, s9, s10;\\n\\n peg$silentFails++;\\n s0 = peg$currPos;\\n s1 = peg$parse_();\\n if (input.charCodeAt(peg$currPos) === 91) {\\n s2 = peg$c0;\\n peg$currPos++;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e1); }\\n }\\n if (s2 !== peg$FAILED) {\\n s3 = peg$parse_();\\n s4 = peg$parsetagName();\\n if (s4 !== peg$FAILED) {\\n s5 = peg$parse_();\\n if (input.charCodeAt(peg$currPos) === 34) {\\n s6 = peg$c1;\\n peg$currPos++;\\n } else {\\n s6 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e2); }\\n }\\n if (s6 !== peg$FAILED) {\\n s7 = peg$parsetagValue();\\n if (input.charCodeAt(peg$currPos) === 34) {\\n s8 = peg$c1;\\n peg$currPos++;\\n } else {\\n s8 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e2); }\\n }\\n if (s8 !== peg$FAILED) {\\n s9 = peg$parse_();\\n if (input.charCodeAt(peg$currPos) === 93) {\\n s10 = peg$c2;\\n peg$currPos++;\\n } else {\\n s10 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e3); }\\n }\\n if (s10 !== peg$FAILED) {\\n peg$savedPos = s0;\\n s0 = peg$f2(s4, s7);\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n peg$silentFails--;\\n if (s0 === peg$FAILED) {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e0); }\\n }\\n\\n return s0;\\n }\\n\\n function peg$parsetagName() {\\n var s0, s1, s2;\\n\\n peg$silentFails++;\\n s0 = peg$currPos;\\n s1 = [];\\n s2 = input.charAt(peg$currPos);\\n if (peg$r0.test(s2)) {\\n peg$currPos++;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e5); }\\n }\\n if (s2 !== peg$FAILED) {\\n while (s2 !== peg$FAILED) {\\n s1.push(s2);\\n s2 = input.charAt(peg$currPos);\\n if (peg$r0.test(s2)) {\\n peg$currPos++;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e5); }\\n }\\n }\\n } else {\\n s1 = peg$FAILED;\\n }\\n if (s1 !== peg$FAILED) {\\n s0 = input.substring(s0, peg$currPos);\\n } else {\\n s0 = s1;\\n }\\n peg$silentFails--;\\n if (s0 === peg$FAILED) {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e4); }\\n }\\n\\n return s0;\\n }\\n\\n function peg$parsetagValue() {\\n var s0, s1, s2;\\n\\n peg$silentFails++;\\n s0 = peg$currPos;\\n s1 = [];\\n s2 = input.charAt(peg$currPos);\\n if (peg$r1.test(s2)) {\\n peg$currPos++;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e7); }\\n }\\n while (s2 !== peg$FAILED) {\\n s1.push(s2);\\n s2 = input.charAt(peg$currPos);\\n if (peg$r1.test(s2)) {\\n peg$currPos++;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e7); }\\n }\\n }\\n s0 = input.substring(s0, peg$currPos);\\n peg$silentFails--;\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e6); }\\n\\n return s0;\\n }\\n\\n function peg$parsemoveTextSection() {\\n var s0, s1, s2, s3, s4;\\n\\n s0 = peg$currPos;\\n s1 = peg$parseline();\\n s2 = peg$parse_();\\n s3 = peg$parsegameTerminationMarker();\\n if (s3 === peg$FAILED) {\\n s3 = null;\\n }\\n s4 = peg$parse_();\\n peg$savedPos = s0;\\n s0 = peg$f3(s1, s3);\\n\\n return s0;\\n }\\n\\n function peg$parseline() {\\n var s0, s1, s2, s3;\\n\\n s0 = peg$currPos;\\n s1 = peg$parsecomment();\\n if (s1 === peg$FAILED) {\\n s1 = null;\\n }\\n s2 = [];\\n s3 = peg$parsemove();\\n while (s3 !== peg$FAILED) {\\n s2.push(s3);\\n s3 = peg$parsemove();\\n }\\n peg$savedPos = s0;\\n s0 = peg$f4(s1, s2);\\n\\n return s0;\\n }\\n\\n function peg$parsemove() {\\n var s0, s1, s2, s3, s4, s5, s6, s7, s8, s9, s10;\\n\\n s0 = peg$currPos;\\n s1 = peg$parse_();\\n s2 = peg$parsemoveNumber();\\n if (s2 === peg$FAILED) {\\n s2 = null;\\n }\\n s3 = peg$parse_();\\n s4 = peg$parsesan();\\n if (s4 !== peg$FAILED) {\\n s5 = peg$parsesuffixAnnotation();\\n if (s5 === peg$FAILED) {\\n s5 = null;\\n }\\n s6 = [];\\n s7 = peg$parsenag();\\n while (s7 !== peg$FAILED) {\\n s6.push(s7);\\n s7 = peg$parsenag();\\n }\\n s7 = peg$parse_();\\n s8 = peg$parsecomment();\\n if (s8 === peg$FAILED) {\\n s8 = null;\\n }\\n s9 = [];\\n s10 = peg$parsevariation();\\n while (s10 !== peg$FAILED) {\\n s9.push(s10);\\n s10 = peg$parsevariation();\\n }\\n peg$savedPos = s0;\\n s0 = peg$f5(s4, s5, s6, s8, s9);\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n\\n return s0;\\n }\\n\\n function peg$parsemoveNumber() {\\n var s0, s1, s2, s3, s4, s5;\\n\\n peg$silentFails++;\\n s0 = peg$currPos;\\n s1 = [];\\n s2 = input.charAt(peg$currPos);\\n if (peg$r2.test(s2)) {\\n peg$currPos++;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e9); }\\n }\\n while (s2 !== peg$FAILED) {\\n s1.push(s2);\\n s2 = input.charAt(peg$currPos);\\n if (peg$r2.test(s2)) {\\n peg$currPos++;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e9); }\\n }\\n }\\n if (input.charCodeAt(peg$currPos) === 46) {\\n s2 = peg$c3;\\n peg$currPos++;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e10); }\\n }\\n if (s2 !== peg$FAILED) {\\n s3 = peg$parse_();\\n s4 = [];\\n s5 = input.charAt(peg$currPos);\\n if (peg$r3.test(s5)) {\\n peg$currPos++;\\n } else {\\n s5 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e11); }\\n }\\n while (s5 !== peg$FAILED) {\\n s4.push(s5);\\n s5 = input.charAt(peg$currPos);\\n if (peg$r3.test(s5)) {\\n peg$currPos++;\\n } else {\\n s5 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e11); }\\n }\\n }\\n s1 = [s1, s2, s3, s4];\\n s0 = s1;\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n peg$silentFails--;\\n if (s0 === peg$FAILED) {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e8); }\\n }\\n\\n return s0;\\n }\\n\\n function peg$parsesan() {\\n var s0, s1, s2, s3, s4, s5;\\n\\n peg$silentFails++;\\n s0 = peg$currPos;\\n s1 = peg$currPos;\\n if (input.substr(peg$currPos, 5) === peg$c4) {\\n s2 = peg$c4;\\n peg$currPos += 5;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e13); }\\n }\\n if (s2 === peg$FAILED) {\\n if (input.substr(peg$currPos, 3) === peg$c5) {\\n s2 = peg$c5;\\n peg$currPos += 3;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e14); }\\n }\\n if (s2 === peg$FAILED) {\\n if (input.substr(peg$currPos, 5) === peg$c6) {\\n s2 = peg$c6;\\n peg$currPos += 5;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e15); }\\n }\\n if (s2 === peg$FAILED) {\\n if (input.substr(peg$currPos, 3) === peg$c7) {\\n s2 = peg$c7;\\n peg$currPos += 3;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e16); }\\n }\\n if (s2 === peg$FAILED) {\\n s2 = peg$currPos;\\n s3 = input.charAt(peg$currPos);\\n if (peg$r0.test(s3)) {\\n peg$currPos++;\\n } else {\\n s3 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e5); }\\n }\\n if (s3 !== peg$FAILED) {\\n s4 = [];\\n s5 = input.charAt(peg$currPos);\\n if (peg$r4.test(s5)) {\\n peg$currPos++;\\n } else {\\n s5 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e17); }\\n }\\n if (s5 !== peg$FAILED) {\\n while (s5 !== peg$FAILED) {\\n s4.push(s5);\\n s5 = input.charAt(peg$currPos);\\n if (peg$r4.test(s5)) {\\n peg$currPos++;\\n } else {\\n s5 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e17); }\\n }\\n }\\n } else {\\n s4 = peg$FAILED;\\n }\\n if (s4 !== peg$FAILED) {\\n s3 = [s3, s4];\\n s2 = s3;\\n } else {\\n peg$currPos = s2;\\n s2 = peg$FAILED;\\n }\\n } else {\\n peg$currPos = s2;\\n s2 = peg$FAILED;\\n }\\n }\\n }\\n }\\n }\\n if (s2 !== peg$FAILED) {\\n s3 = input.charAt(peg$currPos);\\n if (peg$r5.test(s3)) {\\n peg$currPos++;\\n } else {\\n s3 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e18); }\\n }\\n if (s3 === peg$FAILED) {\\n s3 = null;\\n }\\n s2 = [s2, s3];\\n s1 = s2;\\n } else {\\n peg$currPos = s1;\\n s1 = peg$FAILED;\\n }\\n if (s1 !== peg$FAILED) {\\n s0 = input.substring(s0, peg$currPos);\\n } else {\\n s0 = s1;\\n }\\n peg$silentFails--;\\n if (s0 === peg$FAILED) {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e12); }\\n }\\n\\n return s0;\\n }\\n\\n function peg$parsesuffixAnnotation() {\\n var s0, s1, s2;\\n\\n peg$silentFails++;\\n s0 = peg$currPos;\\n s1 = [];\\n s2 = input.charAt(peg$currPos);\\n if (peg$r6.test(s2)) {\\n peg$currPos++;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e20); }\\n }\\n while (s2 !== peg$FAILED) {\\n s1.push(s2);\\n if (s1.length >= 2) {\\n s2 = peg$FAILED;\\n } else {\\n s2 = input.charAt(peg$currPos);\\n if (peg$r6.test(s2)) {\\n peg$currPos++;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e20); }\\n }\\n }\\n }\\n if (s1.length < 1) {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n } else {\\n s0 = s1;\\n }\\n peg$silentFails--;\\n if (s0 === peg$FAILED) {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e19); }\\n }\\n\\n return s0;\\n }\\n\\n function peg$parsenag() {\\n var s0, s1, s2, s3, s4, s5;\\n\\n peg$silentFails++;\\n s0 = peg$currPos;\\n s1 = peg$parse_();\\n if (input.charCodeAt(peg$currPos) === 36) {\\n s2 = peg$c8;\\n peg$currPos++;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e22); }\\n }\\n if (s2 !== peg$FAILED) {\\n s3 = peg$currPos;\\n s4 = [];\\n s5 = input.charAt(peg$currPos);\\n if (peg$r2.test(s5)) {\\n peg$currPos++;\\n } else {\\n s5 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e9); }\\n }\\n if (s5 !== peg$FAILED) {\\n while (s5 !== peg$FAILED) {\\n s4.push(s5);\\n s5 = input.charAt(peg$currPos);\\n if (peg$r2.test(s5)) {\\n peg$currPos++;\\n } else {\\n s5 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e9); }\\n }\\n }\\n } else {\\n s4 = peg$FAILED;\\n }\\n if (s4 !== peg$FAILED) {\\n s3 = input.substring(s3, peg$currPos);\\n } else {\\n s3 = s4;\\n }\\n if (s3 !== peg$FAILED) {\\n peg$savedPos = s0;\\n s0 = peg$f6(s3);\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n peg$silentFails--;\\n if (s0 === peg$FAILED) {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e21); }\\n }\\n\\n return s0;\\n }\\n\\n function peg$parsecomment() {\\n var s0;\\n\\n s0 = peg$parsebraceComment();\\n if (s0 === peg$FAILED) {\\n s0 = peg$parserestOfLineComment();\\n }\\n\\n return s0;\\n }\\n\\n function peg$parsebraceComment() {\\n var s0, s1, s2, s3, s4;\\n\\n peg$silentFails++;\\n s0 = peg$currPos;\\n if (input.charCodeAt(peg$currPos) === 123) {\\n s1 = peg$c9;\\n peg$currPos++;\\n } else {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e24); }\\n }\\n if (s1 !== peg$FAILED) {\\n s2 = peg$currPos;\\n s3 = [];\\n s4 = input.charAt(peg$currPos);\\n if (peg$r7.test(s4)) {\\n peg$currPos++;\\n } else {\\n s4 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e25); }\\n }\\n while (s4 !== peg$FAILED) {\\n s3.push(s4);\\n s4 = input.charAt(peg$currPos);\\n if (peg$r7.test(s4)) {\\n peg$currPos++;\\n } else {\\n s4 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e25); }\\n }\\n }\\n s2 = input.substring(s2, peg$currPos);\\n if (input.charCodeAt(peg$currPos) === 125) {\\n s3 = peg$c10;\\n peg$currPos++;\\n } else {\\n s3 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e26); }\\n }\\n if (s3 !== peg$FAILED) {\\n peg$savedPos = s0;\\n s0 = peg$f7(s2);\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n peg$silentFails--;\\n if (s0 === peg$FAILED) {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e23); }\\n }\\n\\n return s0;\\n }\\n\\n function peg$parserestOfLineComment() {\\n var s0, s1, s2, s3, s4;\\n\\n peg$silentFails++;\\n s0 = peg$currPos;\\n if (input.charCodeAt(peg$currPos) === 59) {\\n s1 = peg$c11;\\n peg$currPos++;\\n } else {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e28); }\\n }\\n if (s1 !== peg$FAILED) {\\n s2 = peg$currPos;\\n s3 = [];\\n s4 = input.charAt(peg$currPos);\\n if (peg$r8.test(s4)) {\\n peg$currPos++;\\n } else {\\n s4 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e29); }\\n }\\n while (s4 !== peg$FAILED) {\\n s3.push(s4);\\n s4 = input.charAt(peg$currPos);\\n if (peg$r8.test(s4)) {\\n peg$currPos++;\\n } else {\\n s4 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e29); }\\n }\\n }\\n s2 = input.substring(s2, peg$currPos);\\n peg$savedPos = s0;\\n s0 = peg$f8(s2);\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n peg$silentFails--;\\n if (s0 === peg$FAILED) {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e27); }\\n }\\n\\n return s0;\\n }\\n\\n function peg$parsevariation() {\\n var s0, s1, s2, s3, s4, s5;\\n\\n peg$silentFails++;\\n s0 = peg$currPos;\\n s1 = peg$parse_();\\n if (input.charCodeAt(peg$currPos) === 40) {\\n s2 = peg$c12;\\n peg$currPos++;\\n } else {\\n s2 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e31); }\\n }\\n if (s2 !== peg$FAILED) {\\n s3 = peg$parseline();\\n if (s3 !== peg$FAILED) {\\n s4 = peg$parse_();\\n if (input.charCodeAt(peg$currPos) === 41) {\\n s5 = peg$c13;\\n peg$currPos++;\\n } else {\\n s5 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e32); }\\n }\\n if (s5 !== peg$FAILED) {\\n peg$savedPos = s0;\\n s0 = peg$f9(s3);\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n peg$silentFails--;\\n if (s0 === peg$FAILED) {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e30); }\\n }\\n\\n return s0;\\n }\\n\\n function peg$parsegameTerminationMarker() {\\n var s0, s1, s2, s3;\\n\\n peg$silentFails++;\\n s0 = peg$currPos;\\n if (input.substr(peg$currPos, 3) === peg$c14) {\\n s1 = peg$c14;\\n peg$currPos += 3;\\n } else {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e34); }\\n }\\n if (s1 === peg$FAILED) {\\n if (input.substr(peg$currPos, 3) === peg$c15) {\\n s1 = peg$c15;\\n peg$currPos += 3;\\n } else {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e35); }\\n }\\n if (s1 === peg$FAILED) {\\n if (input.substr(peg$currPos, 7) === peg$c16) {\\n s1 = peg$c16;\\n peg$currPos += 7;\\n } else {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e36); }\\n }\\n if (s1 === peg$FAILED) {\\n if (input.charCodeAt(peg$currPos) === 42) {\\n s1 = peg$c17;\\n peg$currPos++;\\n } else {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e37); }\\n }\\n }\\n }\\n }\\n if (s1 !== peg$FAILED) {\\n s2 = peg$parse_();\\n s3 = peg$parsecomment();\\n if (s3 === peg$FAILED) {\\n s3 = null;\\n }\\n peg$savedPos = s0;\\n s0 = peg$f10(s1, s3);\\n } else {\\n peg$currPos = s0;\\n s0 = peg$FAILED;\\n }\\n peg$silentFails--;\\n if (s0 === peg$FAILED) {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e33); }\\n }\\n\\n return s0;\\n }\\n\\n function peg$parse_() {\\n var s0, s1;\\n\\n peg$silentFails++;\\n s0 = [];\\n s1 = input.charAt(peg$currPos);\\n if (peg$r9.test(s1)) {\\n peg$currPos++;\\n } else {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e39); }\\n }\\n while (s1 !== peg$FAILED) {\\n s0.push(s1);\\n s1 = input.charAt(peg$currPos);\\n if (peg$r9.test(s1)) {\\n peg$currPos++;\\n } else {\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e39); }\\n }\\n }\\n peg$silentFails--;\\n s1 = peg$FAILED;\\n if (peg$silentFails === 0) { peg$fail(peg$e38); }\\n\\n return s0;\\n }\\n\\n peg$result = peg$startRuleFunction();\\n\\n if (options.peg$library) {\\n return /** @type {any} */ ({\\n peg$result,\\n peg$currPos,\\n peg$FAILED,\\n peg$maxFailExpected,\\n peg$maxFailPos\\n });\\n }\\n if (peg$result !== peg$FAILED && peg$currPos === input.length) {\\n return peg$result;\\n } else {\\n if (peg$result !== peg$FAILED && peg$currPos < input.length) {\\n peg$fail(peg$endExpectation());\\n }\\n\\n throw peg$buildStructuredError(\\n peg$maxFailExpected,\\n peg$maxFailPos < input.length ? input.charAt(peg$maxFailPos) : null,\\n peg$maxFailPos < input.length\\n ? peg$computeLocation(peg$maxFailPos, peg$maxFailPos + 1)\\n : peg$computeLocation(peg$maxFailPos, peg$maxFailPos)\\n );\\n }\\n}\\n\\nconst peg$allowedStartRules = [\\n \\\"pgn\\\"\\n];\\n\\nexport {\\n peg$allowedStartRules as StartRules,\\n peg$SyntaxError as SyntaxError,\\n peg$parse as parse\\n};\\n\",null,\"import { Chess } from 'chess.js';\\n\\nconst chess = new Chess();\\nconst legalMoves = chess.moves({ verbose: true });\\n\\nexport default legalMoves.some(\\n (move) => move.from === 'e2' && move.to === 'e6',\\n);\\n\"],\"version\":3}", + "originMeta": { + "originalPath": "node_modules/.pnpm/chess.js@1.4.0/node_modules/chess.js/dist/esm/chess.js", + "packageName": "chess.js", + "packageVersion": "1.4.0", + "integrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562" + } + } + ], + "builderVersion": "deterministic-builder-v1", + "dependencyIntegrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562", + "diagnosticsMeta": { + "entryPath": "/workspace/libs/test-harness/fixtures/library-reuse/chess-entry.ts", + "modulePaths": [ + "./chess-entry.js" + ] + }, + "graphHash": "689f4980e43e34c287819a4445a4a2f32b61ea8714e9ff3edc909b76496de91f" + } + } + }, + "manifest": { + "abi_id": "Host.v1", + "abi_version": 1, + "functions": [ + { + "fn_id": 1, + "js_path": [ + "document", + "get" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 2, + "js_path": [ + "document", + "getCanonical" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 3, + "js_path": [ + "emit" + ], + "effect": "EMIT", + "arity": 1, + "arg_schema": [ + { + "type": "dv" + } + ], + "return_schema": { + "type": "null" + }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [ + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + } + ] + } + ] + } + }, + { + "id": "example-promises-async", + "title": "Promises / async / microtasks", + "kind": "example", + "badge": "Example 4", + "description": "Promise job draining under an explicitly compatible profile.", + "certified": true, + "executionProfile": "compat-general-v1", + "sourceKind": "script", + "abiId": "Host.v1", + "gasLimit": "50000", + "sourcePaths": [ + "examples/04-promises-async/program.js" + ], + "sourceText": "(() => Promise.resolve(40).then((value) => value + 2))();\n", + "hostPreset": "determinism", + "hostSummary": { + "label": "Determinism fixture host", + "description": "Provides stable Host.v1/Host.v2 document responses plus deterministic emit tape capture.", + "documents": [ + "path/to/doc", + "path/to/canonical", + "path/to/first", + "path/to/second", + "path/to/third", + "bytes/payload" + ] + }, + "docsLinks": [ + { + "label": "Learn path", + "href": "/docs/learn/README.md" + }, + { + "label": "Examples corpus", + "href": "/examples/README.md" + }, + { + "label": "Promises and microtasks", + "href": "/docs/learn/04-promises-async-and-microtasks.md" + } + ], + "supportsOogSearch": true, + "program": { + "version": 2, + "abiId": "Host.v1", + "abiVersion": 1, + "abiManifestHash": "e23b0b2ee169900bbde7aff78e6ce20fead1715c60f8a8e3106d9959450a3d34", + "executionProfile": "compat-general-v1", + "sourceKind": "script", + "source": { + "code": "(() => Promise.resolve(40).then((value) => value + 2))();\n" + }, + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8 + }, + "manifest": { + "abi_id": "Host.v1", + "abi_version": 1, + "functions": [ + { + "fn_id": 1, + "js_path": [ + "document", + "get" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 2, + "js_path": [ + "document", + "getCanonical" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 3, + "js_path": [ + "emit" + ], + "effect": "EMIT", + "arity": 1, + "arg_schema": [ + { + "type": "dv" + } + ], + "return_schema": { + "type": "null" + }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [ + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + } + ] + } + ] + } + }, + { + "id": "example-promises-library-host", + "title": "Promises + imported library + host call", + "kind": "example", + "badge": "Example 5", + "description": "Imported module code plus Promise jobs plus host interaction.", + "certified": true, + "executionProfile": "compat-general-v1", + "sourceKind": "module-pack", + "abiId": "Host.v1", + "gasLimit": "100000", + "sourcePaths": [ + "examples/05-promises-library-host/entry.js", + "examples/05-promises-library-host/lib.js" + ], + "sourceText": "import { plusOne } from './lib.js';\n\nexport default Promise.resolve(plusOne(41)).then((value) => {\n Host.v1.emit({ phase: 'async-lib', value });\n return value;\n});\n", + "hostPreset": "determinism", + "hostSummary": { + "label": "Determinism fixture host", + "description": "Provides stable Host.v1/Host.v2 document responses plus deterministic emit tape capture.", + "documents": [ + "path/to/doc", + "path/to/canonical", + "path/to/first", + "path/to/second", + "path/to/third", + "bytes/payload" + ] + }, + "docsLinks": [ + { + "label": "Learn path", + "href": "/docs/learn/README.md" + }, + { + "label": "Examples corpus", + "href": "/examples/README.md" + }, + { + "label": "Promises and microtasks", + "href": "/docs/learn/04-promises-async-and-microtasks.md" + } + ], + "supportsOogSearch": true, + "program": { + "version": 2, + "abiId": "Host.v1", + "abiVersion": 1, + "abiManifestHash": "e23b0b2ee169900bbde7aff78e6ce20fead1715c60f8a8e3106d9959450a3d34", + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8, + "executionProfile": "compat-general-v1", + "sourceKind": "module-pack", + "source": { + "modulePack": { + "version": 1, + "entrySpecifier": "./entry.js", + "entryExport": "default", + "modules": [ + { + "specifier": "./entry.js", + "source": "// examples/05-promises-library-host/lib.js\nvar plusOne = (value) => value + 1;\n\n// examples/05-promises-library-host/entry.js\nvar entry_default = Promise.resolve(plusOne(41)).then((value) => {\n Host.v1.emit({ phase: \"async-lib\", value });\n return value;\n});\nexport {\n entry_default as default\n};\n", + "sourceMap": "{\"mappings\":\";AAAO,IAAM,UAAU,CAAC,UAAU,QAAQ;;;ACE1C,IAAO,gBAAQ,QAAQ,QAAQ,QAAQ,EAAE,CAAC,EAAE,KAAK,CAAC,UAAU;AAC1D,OAAK,GAAG,KAAK,EAAE,OAAO,aAAa,MAAM,CAAC;AAC1C,SAAO;AACT,CAAC;\",\"names\":[],\"sources\":[\"../examples/05-promises-library-host/lib.js\",\"../examples/05-promises-library-host/entry.js\"],\"sourcesContent\":[\"export const plusOne = (value) => value + 1;\\n\",\"import { plusOne } from './lib.js';\\n\\nexport default Promise.resolve(plusOne(41)).then((value) => {\\n Host.v1.emit({ phase: 'async-lib', value });\\n return value;\\n});\\n\"],\"version\":3}", + "originMeta": { + "originalPath": "examples/05-promises-library-host/entry.js" + } + } + ], + "builderVersion": "deterministic-builder-v1", + "dependencyIntegrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562", + "diagnosticsMeta": { + "entryPath": "/workspace/examples/05-promises-library-host/entry.js", + "modulePaths": [ + "./entry.js" + ] + }, + "graphHash": "2cbcc7bf38d7b998a6e4e855e5f5a7bb9f77b0bb2f8434982409678812d39ec7" + } + } + }, + "manifest": { + "abi_id": "Host.v1", + "abi_version": 1, + "functions": [ + { + "fn_id": 1, + "js_path": [ + "document", + "get" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 2, + "js_path": [ + "document", + "getCanonical" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 3, + "js_path": [ + "emit" + ], + "effect": "EMIT", + "arity": 1, + "arg_schema": [ + { + "type": "dv" + } + ], + "return_schema": { + "type": "null" + }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [ + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + } + ] + } + ] + } + }, + { + "id": "example-binary-host-v2", + "title": "Binary / typed arrays / Host.v2 DV2", + "kind": "example", + "badge": "Example 6", + "description": "Typed-array and bytes boundary example using Host.v2 and DV2.", + "certified": true, + "executionProfile": "compat-binary-v1", + "sourceKind": "script", + "abiId": "Host.v2", + "gasLimit": "50000", + "sourcePaths": [ + "examples/06-binary-host-v2/program.js" + ], + "sourceText": "(() => {\n const payload = Host.v2.document.get('bytes/payload');\n Host.v2.emit(payload);\n let sum = 0;\n for (const byte of payload) {\n sum += byte;\n }\n return {\n length: payload.byteLength,\n first: payload[0],\n last: payload[payload.byteLength - 1],\n sum,\n };\n})();\n", + "hostPreset": "determinism", + "hostSummary": { + "label": "Determinism fixture host", + "description": "Provides stable Host.v1/Host.v2 document responses plus deterministic emit tape capture.", + "documents": [ + "path/to/doc", + "path/to/canonical", + "path/to/first", + "path/to/second", + "path/to/third", + "bytes/payload" + ] + }, + "docsLinks": [ + { + "label": "Learn path", + "href": "/docs/learn/README.md" + }, + { + "label": "Examples corpus", + "href": "/examples/README.md" + }, + { + "label": "Binary mode and Host.v2", + "href": "/docs/learn/05-binary-and-host-v2.md" + } + ], + "supportsOogSearch": true, + "program": { + "version": 2, + "abiId": "Host.v2", + "abiVersion": 2, + "abiManifestHash": "ec5c3df99a1b0ab84b692996193707ae6c931382e75c96c7c14b4f8baaae5af2", + "executionProfile": "compat-binary-v1", + "sourceKind": "script", + "source": { + "code": "(() => {\n const payload = Host.v2.document.get('bytes/payload');\n Host.v2.emit(payload);\n let sum = 0;\n for (const byte of payload) {\n sum += byte;\n }\n return {\n length: payload.byteLength,\n first: payload[0],\n last: payload[payload.byteLength - 1],\n sum,\n };\n})();\n" + }, + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8 + }, + "manifest": { + "abi_id": "Host.v2", + "abi_version": 2, + "functions": [ + { + "fn_id": 1, + "js_path": [ + "document", + "get" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 2, + "js_path": [ + "document", + "getCanonical" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 3, + "js_path": [ + "emit" + ], + "effect": "EMIT", + "arity": 1, + "arg_schema": [ + { + "type": "dv" + } + ], + "return_schema": { + "type": "null" + }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [ + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + } + ] + } + ] + } + }, + { + "id": "example-console-shim", + "title": "Console shim determinism", + "kind": "example", + "badge": "Example 7", + "description": "Deterministic console shimming routed through host tape.", + "certified": true, + "executionProfile": "compat-general-v1", + "sourceKind": "script", + "abiId": "Host.v1", + "gasLimit": "50000", + "sourcePaths": [ + "examples/07-console-shim/program.js" + ], + "sourceText": "(() => {\n console.info('deterministic', 7);\n return { ok: true };\n})();\n", + "hostPreset": "determinism", + "hostSummary": { + "label": "Determinism fixture host", + "description": "Provides stable Host.v1/Host.v2 document responses plus deterministic emit tape capture.", + "documents": [ + "path/to/doc", + "path/to/canonical", + "path/to/first", + "path/to/second", + "path/to/third", + "bytes/payload" + ] + }, + "docsLinks": [ + { + "label": "Learn path", + "href": "/docs/learn/README.md" + }, + { + "label": "Examples corpus", + "href": "/examples/README.md" + } + ], + "supportsOogSearch": true, + "program": { + "version": 2, + "abiId": "Host.v1", + "abiVersion": 1, + "abiManifestHash": "e23b0b2ee169900bbde7aff78e6ce20fead1715c60f8a8e3106d9959450a3d34", + "executionProfile": "compat-general-v1", + "sourceKind": "script", + "source": { + "code": "(() => {\n console.info('deterministic', 7);\n return { ok: true };\n})();\n" + }, + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8 + }, + "manifest": { + "abi_id": "Host.v1", + "abi_version": 1, + "functions": [ + { + "fn_id": 1, + "js_path": [ + "document", + "get" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 2, + "js_path": [ + "document", + "getCanonical" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 3, + "js_path": [ + "emit" + ], + "effect": "EMIT", + "arity": 1, + "arg_schema": [ + { + "type": "dv" + } + ], + "return_schema": { + "type": "null" + }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [ + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + } + ] + } + ] + } + }, + { + "id": "example-stable-sort", + "title": "Stable sort determinism", + "kind": "example", + "badge": "Example 8", + "description": "Compatibility profile example showing deterministic stable sort.", + "certified": true, + "executionProfile": "compat-general-v1", + "sourceKind": "script", + "abiId": "Host.v1", + "gasLimit": "100000", + "sourcePaths": [ + "examples/08-stable-sort/program.js" + ], + "sourceText": "(() => {\n const records = [\n { id: 'a', group: 1 },\n { id: 'b', group: 1 },\n { id: 'c', group: 2 },\n { id: 'd', group: 1 },\n ];\n records.sort((left, right) => left.group - right.group);\n return records.map((record) => record.id);\n})();\n", + "hostPreset": "determinism", + "hostSummary": { + "label": "Determinism fixture host", + "description": "Provides stable Host.v1/Host.v2 document responses plus deterministic emit tape capture.", + "documents": [ + "path/to/doc", + "path/to/canonical", + "path/to/first", + "path/to/second", + "path/to/third", + "bytes/payload" + ] + }, + "docsLinks": [ + { + "label": "Learn path", + "href": "/docs/learn/README.md" + }, + { + "label": "Examples corpus", + "href": "/examples/README.md" + } + ], + "supportsOogSearch": true, + "program": { + "version": 2, + "abiId": "Host.v1", + "abiVersion": 1, + "abiManifestHash": "e23b0b2ee169900bbde7aff78e6ce20fead1715c60f8a8e3106d9959450a3d34", + "executionProfile": "compat-general-v1", + "sourceKind": "script", + "source": { + "code": "(() => {\n const records = [\n { id: 'a', group: 1 },\n { id: 'b', group: 1 },\n { id: 'c', group: 2 },\n { id: 'd', group: 1 },\n ];\n records.sort((left, right) => left.group - right.group);\n return records.map((record) => record.id);\n})();\n" + }, + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8 + }, + "manifest": { + "abi_id": "Host.v1", + "abi_version": 1, + "functions": [ + { + "fn_id": 1, + "js_path": [ + "document", + "get" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 2, + "js_path": [ + "document", + "getCanonical" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 3, + "js_path": [ + "emit" + ], + "effect": "EMIT", + "arity": 1, + "arg_schema": [ + { + "type": "dv" + } + ], + "return_schema": { + "type": "null" + }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [ + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + } + ] + } + ] + } + }, + { + "id": "example-kitchen-sink", + "title": "Kitchen sink app", + "kind": "example", + "badge": "Example 9", + "description": "Composite example mixing modules, Promise jobs, host calls, and stable sort.", + "certified": true, + "executionProfile": "compat-general-v1", + "sourceKind": "module-pack", + "abiId": "Host.v1", + "gasLimit": "200000", + "sourcePaths": [ + "examples/09-kitchen-sink/entry.js", + "examples/09-kitchen-sink/workflow.js" + ], + "sourceText": "import { summarize } from './workflow.js';\n\nexport default (async () => {\n const doc = document('path/to/doc');\n const canonical = document.canonical('path/to/doc');\n const result = await summarize(doc.path, canonical.canonical);\n Host.v1.emit({ kind: 'kitchen', result });\n return result;\n})();\n", + "hostPreset": "determinism", + "hostSummary": { + "label": "Determinism fixture host", + "description": "Provides stable Host.v1/Host.v2 document responses plus deterministic emit tape capture.", + "documents": [ + "path/to/doc", + "path/to/canonical", + "path/to/first", + "path/to/second", + "path/to/third", + "bytes/payload" + ] + }, + "docsLinks": [ + { + "label": "Learn path", + "href": "/docs/learn/README.md" + }, + { + "label": "Examples corpus", + "href": "/examples/README.md" + } + ], + "supportsOogSearch": true, + "program": { + "version": 2, + "abiId": "Host.v1", + "abiVersion": 1, + "abiManifestHash": "e23b0b2ee169900bbde7aff78e6ce20fead1715c60f8a8e3106d9959450a3d34", + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8, + "executionProfile": "compat-general-v1", + "sourceKind": "module-pack", + "source": { + "modulePack": { + "version": 1, + "entrySpecifier": "./entry.js", + "entryExport": "default", + "modules": [ + { + "specifier": "./entry.js", + "source": "// examples/09-kitchen-sink/workflow.js\nasync function summarize(path, canonical) {\n const queue = [];\n queueMicrotask(() => queue.push(\"micro\"));\n await Promise.resolve();\n const records = [\n { id: \"b\", rank: 2 },\n { id: \"a\", rank: 1 },\n { id: \"c\", rank: 2 }\n ];\n records.sort((left, right) => left.rank - right.rank);\n return {\n path,\n canonical,\n order: records.map((record) => record.id).join(\",\"),\n queue: queue.join(\",\")\n };\n}\n\n// examples/09-kitchen-sink/entry.js\nvar entry_default = (async () => {\n const doc = document(\"path/to/doc\");\n const canonical = document.canonical(\"path/to/doc\");\n const result = await summarize(doc.path, canonical.canonical);\n Host.v1.emit({ kind: \"kitchen\", result });\n return result;\n})();\nexport {\n entry_default as default\n};\n", + "sourceMap": "{\"mappings\":\";AAAA,eAAsB,UAAU,MAAM,WAAW;AAC/C,QAAM,QAAQ,CAAC;AACf,iBAAe,MAAM,MAAM,KAAK,OAAO,CAAC;AACxC,QAAM,QAAQ,QAAQ;AACtB,QAAM,UAAU;AAAA,IACd,EAAE,IAAI,KAAK,MAAM,EAAE;AAAA,IACnB,EAAE,IAAI,KAAK,MAAM,EAAE;AAAA,IACnB,EAAE,IAAI,KAAK,MAAM,EAAE;AAAA,EACrB;AACA,UAAQ,KAAK,CAAC,MAAM,UAAU,KAAK,OAAO,MAAM,IAAI;AACpD,SAAO;AAAA,IACL;AAAA,IACA;AAAA,IACA,OAAO,QAAQ,IAAI,CAAC,WAAW,OAAO,EAAE,EAAE,KAAK,GAAG;AAAA,IAClD,OAAO,MAAM,KAAK,GAAG;AAAA,EACvB;AACF;;;ACdA,IAAO,iBAAS,YAAY;AAC1B,QAAM,MAAM,SAAS,aAAa;AAClC,QAAM,YAAY,SAAS,UAAU,aAAa;AAClD,QAAM,SAAS,MAAM,UAAU,IAAI,MAAM,UAAU,SAAS;AAC5D,OAAK,GAAG,KAAK,EAAE,MAAM,WAAW,OAAO,CAAC;AACxC,SAAO;AACT,GAAG;\",\"names\":[],\"sources\":[\"../examples/09-kitchen-sink/workflow.js\",\"../examples/09-kitchen-sink/entry.js\"],\"sourcesContent\":[\"export async function summarize(path, canonical) {\\n const queue = [];\\n queueMicrotask(() => queue.push('micro'));\\n await Promise.resolve();\\n const records = [\\n { id: 'b', rank: 2 },\\n { id: 'a', rank: 1 },\\n { id: 'c', rank: 2 },\\n ];\\n records.sort((left, right) => left.rank - right.rank);\\n return {\\n path,\\n canonical,\\n order: records.map((record) => record.id).join(','),\\n queue: queue.join(','),\\n };\\n}\\n\",\"import { summarize } from './workflow.js';\\n\\nexport default (async () => {\\n const doc = document('path/to/doc');\\n const canonical = document.canonical('path/to/doc');\\n const result = await summarize(doc.path, canonical.canonical);\\n Host.v1.emit({ kind: 'kitchen', result });\\n return result;\\n})();\\n\"],\"version\":3}", + "originMeta": { + "originalPath": "examples/09-kitchen-sink/entry.js" + } + } + ], + "builderVersion": "deterministic-builder-v1", + "dependencyIntegrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562", + "diagnosticsMeta": { + "entryPath": "/workspace/examples/09-kitchen-sink/entry.js", + "modulePaths": [ + "./entry.js" + ] + }, + "graphHash": "d79be16d156f0ee1669d4d6d7d422e08d8c1d287039e46fad9aa65c81d754d91" + } + } + }, + "manifest": { + "abi_id": "Host.v1", + "abi_version": 1, + "functions": [ + { + "fn_id": 1, + "js_path": [ + "document", + "get" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 2, + "js_path": [ + "document", + "getCanonical" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 3, + "js_path": [ + "emit" + ], + "effect": "EMIT", + "arity": 1, + "arg_schema": [ + { + "type": "dv" + } + ], + "return_schema": { + "type": "null" + }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [ + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + } + ] + } + ] + } + }, + { + "id": "example-max-gas-policy", + "title": "Max-gas policy / OOG boundary", + "kind": "example", + "badge": "Example 10", + "description": "Shows how exact OOG boundaries are part of the release contract.", + "certified": true, + "executionProfile": "baseline-v1", + "sourceKind": "script", + "abiId": "Host.v1", + "gasLimit": "1000000", + "sourcePaths": [ + "examples/10-max-gas-policy/program.js" + ], + "sourceText": "(() => {\n let sum = 0;\n for (let i = 0; i < 10000; i += 1) {\n sum += i;\n }\n return sum;\n})();\n", + "hostPreset": "determinism", + "hostSummary": { + "label": "Determinism fixture host", + "description": "Provides stable Host.v1/Host.v2 document responses plus deterministic emit tape capture.", + "documents": [ + "path/to/doc", + "path/to/canonical", + "path/to/first", + "path/to/second", + "path/to/third", + "bytes/payload" + ] + }, + "docsLinks": [ + { + "label": "Learn path", + "href": "/docs/learn/README.md" + }, + { + "label": "Examples corpus", + "href": "/examples/README.md" + }, + { + "label": "Gas and OOG", + "href": "/docs/learn/06-gas-oog-and-max-gas-policies.md" + } + ], + "supportsOogSearch": true, + "program": { + "version": 2, + "abiId": "Host.v1", + "abiVersion": 1, + "abiManifestHash": "e23b0b2ee169900bbde7aff78e6ce20fead1715c60f8a8e3106d9959450a3d34", + "executionProfile": "baseline-v1", + "sourceKind": "script", + "source": { + "code": "(() => {\n let sum = 0;\n for (let i = 0; i < 10000; i += 1) {\n sum += i;\n }\n return sum;\n})();\n" + }, + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8 + }, + "manifest": { + "abi_id": "Host.v1", + "abi_version": 1, + "functions": [ + { + "fn_id": 1, + "js_path": [ + "document", + "get" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 2, + "js_path": [ + "document", + "getCanonical" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 3, + "js_path": [ + "emit" + ], + "effect": "EMIT", + "arity": 1, + "arg_schema": [ + { + "type": "dv" + } + ], + "return_schema": { + "type": "null" + }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [ + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + } + ] + } + ] + } + }, + { + "id": "green-semver", + "title": "semver constraint evaluation", + "kind": "ecosystem-green", + "badge": "Green ecosystem fixture", + "description": "Semver constraint evaluation from the certified green ecosystem corpus.", + "certified": true, + "executionProfile": "compat-general-v1", + "sourceKind": "module-pack", + "abiId": "Host.v1", + "gasLimit": "1000000", + "sourcePaths": [ + "apps/ecosystem-certifier/fixtures/positive/semver-entry.ts" + ], + "sourceText": "import { satisfies, valid } from 'semver';\n\nconst version = Host.v1.document.get('text/semver-case');\nconst ranges = ['>=1.2.0 <2.0.0', '^1.2.0', '~1.2.3'];\n\nexport default {\n version,\n valid: valid(version) !== null,\n checks: ranges.map((range) => ({ range, ok: satisfies(version, range) })),\n};\n", + "hostPreset": "certification", + "hostSummary": { + "label": "Certification host", + "description": "Provides the ecosystem-certifier text and binary documents used for workload certification.", + "documents": [ + "pack/metadata.json", + "pack/metadata.yaml", + "docs/a.md", + "docs/b.md", + "docs/c.md", + "docs/d.md", + "bytes/payload", + "bytes/flagship-extra", + "pack/attachment.deflated" + ] + }, + "docsLinks": [ + { + "label": "Workload certification", + "href": "/docs/workload-certification.md" + }, + { + "label": "Compatibility report", + "href": "/docs/ecosystem-compatibility-report.md" + } + ], + "supportsOogSearch": false, + "program": { + "version": 2, + "abiId": "Host.v1", + "abiVersion": 1, + "abiManifestHash": "e23b0b2ee169900bbde7aff78e6ce20fead1715c60f8a8e3106d9959450a3d34", + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8, + "executionProfile": "compat-general-v1", + "sourceKind": "module-pack", + "source": { + "modulePack": { + "version": 1, + "entrySpecifier": "./semver-entry.js", + "entryExport": "default", + "modules": [ + { + "specifier": "./semver-entry.js", + "source": "var __create = Object.create;\nvar __defProp = Object.defineProperty;\nvar __getOwnPropDesc = Object.getOwnPropertyDescriptor;\nvar __getOwnPropNames = Object.getOwnPropertyNames;\nvar __getProtoOf = Object.getPrototypeOf;\nvar __hasOwnProp = Object.prototype.hasOwnProperty;\nvar __commonJS = (cb, mod) => function __require() {\n return mod || (0, cb[__getOwnPropNames(cb)[0]])((mod = { exports: {} }).exports, mod), mod.exports;\n};\nvar __copyProps = (to, from, except, desc) => {\n if (from && typeof from === \"object\" || typeof from === \"function\") {\n for (let key of __getOwnPropNames(from))\n if (!__hasOwnProp.call(to, key) && key !== except)\n __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });\n }\n return to;\n};\nvar __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(\n // If the importer is in node compatibility mode or this is not an ESM\n // file that has been converted to a CommonJS file using a Babel-\n // compatible transform (i.e. \"__esModule\" has not been set), then set\n // \"default\" to the CommonJS \"module.exports\" for node compatibility.\n isNodeMode || !mod || !mod.__esModule ? __defProp(target, \"default\", { value: mod, enumerable: true }) : target,\n mod\n));\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/constants.js\nvar require_constants = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/constants.js\"(exports, module) {\n \"use strict\";\n var SEMVER_SPEC_VERSION = \"2.0.0\";\n var MAX_LENGTH = 256;\n var MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER || /* istanbul ignore next */\n 9007199254740991;\n var MAX_SAFE_COMPONENT_LENGTH = 16;\n var MAX_SAFE_BUILD_LENGTH = MAX_LENGTH - 6;\n var RELEASE_TYPES = [\n \"major\",\n \"premajor\",\n \"minor\",\n \"preminor\",\n \"patch\",\n \"prepatch\",\n \"prerelease\"\n ];\n module.exports = {\n MAX_LENGTH,\n MAX_SAFE_COMPONENT_LENGTH,\n MAX_SAFE_BUILD_LENGTH,\n MAX_SAFE_INTEGER,\n RELEASE_TYPES,\n SEMVER_SPEC_VERSION,\n FLAG_INCLUDE_PRERELEASE: 1,\n FLAG_LOOSE: 2\n };\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/debug.js\nvar require_debug = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/debug.js\"(exports, module) {\n \"use strict\";\n var debug = typeof process === \"object\" && process.env && process.env.NODE_DEBUG && /\\bsemver\\b/i.test(process.env.NODE_DEBUG) ? (...args) => console.error(\"SEMVER\", ...args) : () => {\n };\n module.exports = debug;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/re.js\nvar require_re = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/re.js\"(exports, module) {\n \"use strict\";\n var {\n MAX_SAFE_COMPONENT_LENGTH,\n MAX_SAFE_BUILD_LENGTH,\n MAX_LENGTH\n } = require_constants();\n var debug = require_debug();\n exports = module.exports = {};\n var re = exports.re = [];\n var safeRe = exports.safeRe = [];\n var src = exports.src = [];\n var safeSrc = exports.safeSrc = [];\n var t = exports.t = {};\n var R = 0;\n var LETTERDASHNUMBER = \"[a-zA-Z0-9-]\";\n var safeRegexReplacements = [\n [\"\\\\s\", 1],\n [\"\\\\d\", MAX_LENGTH],\n [LETTERDASHNUMBER, MAX_SAFE_BUILD_LENGTH]\n ];\n var makeSafeRegex = (value) => {\n for (const [token, max] of safeRegexReplacements) {\n value = value.split(`${token}*`).join(`${token}{0,${max}}`).split(`${token}+`).join(`${token}{1,${max}}`);\n }\n return value;\n };\n var createToken = (name, value, isGlobal) => {\n const safe = makeSafeRegex(value);\n const index = R++;\n debug(name, index, value);\n t[name] = index;\n src[index] = value;\n safeSrc[index] = safe;\n re[index] = new RegExp(value, isGlobal ? \"g\" : void 0);\n safeRe[index] = new RegExp(safe, isGlobal ? \"g\" : void 0);\n };\n createToken(\"NUMERICIDENTIFIER\", \"0|[1-9]\\\\d*\");\n createToken(\"NUMERICIDENTIFIERLOOSE\", \"\\\\d+\");\n createToken(\"NONNUMERICIDENTIFIER\", `\\\\d*[a-zA-Z-]${LETTERDASHNUMBER}*`);\n createToken(\"MAINVERSION\", `(${src[t.NUMERICIDENTIFIER]})\\\\.(${src[t.NUMERICIDENTIFIER]})\\\\.(${src[t.NUMERICIDENTIFIER]})`);\n createToken(\"MAINVERSIONLOOSE\", `(${src[t.NUMERICIDENTIFIERLOOSE]})\\\\.(${src[t.NUMERICIDENTIFIERLOOSE]})\\\\.(${src[t.NUMERICIDENTIFIERLOOSE]})`);\n createToken(\"PRERELEASEIDENTIFIER\", `(?:${src[t.NONNUMERICIDENTIFIER]}|${src[t.NUMERICIDENTIFIER]})`);\n createToken(\"PRERELEASEIDENTIFIERLOOSE\", `(?:${src[t.NONNUMERICIDENTIFIER]}|${src[t.NUMERICIDENTIFIERLOOSE]})`);\n createToken(\"PRERELEASE\", `(?:-(${src[t.PRERELEASEIDENTIFIER]}(?:\\\\.${src[t.PRERELEASEIDENTIFIER]})*))`);\n createToken(\"PRERELEASELOOSE\", `(?:-?(${src[t.PRERELEASEIDENTIFIERLOOSE]}(?:\\\\.${src[t.PRERELEASEIDENTIFIERLOOSE]})*))`);\n createToken(\"BUILDIDENTIFIER\", `${LETTERDASHNUMBER}+`);\n createToken(\"BUILD\", `(?:\\\\+(${src[t.BUILDIDENTIFIER]}(?:\\\\.${src[t.BUILDIDENTIFIER]})*))`);\n createToken(\"FULLPLAIN\", `v?${src[t.MAINVERSION]}${src[t.PRERELEASE]}?${src[t.BUILD]}?`);\n createToken(\"FULL\", `^${src[t.FULLPLAIN]}$`);\n createToken(\"LOOSEPLAIN\", `[v=\\\\s]*${src[t.MAINVERSIONLOOSE]}${src[t.PRERELEASELOOSE]}?${src[t.BUILD]}?`);\n createToken(\"LOOSE\", `^${src[t.LOOSEPLAIN]}$`);\n createToken(\"GTLT\", \"((?:<|>)?=?)\");\n createToken(\"XRANGEIDENTIFIERLOOSE\", `${src[t.NUMERICIDENTIFIERLOOSE]}|x|X|\\\\*`);\n createToken(\"XRANGEIDENTIFIER\", `${src[t.NUMERICIDENTIFIER]}|x|X|\\\\*`);\n createToken(\"XRANGEPLAIN\", `[v=\\\\s]*(${src[t.XRANGEIDENTIFIER]})(?:\\\\.(${src[t.XRANGEIDENTIFIER]})(?:\\\\.(${src[t.XRANGEIDENTIFIER]})(?:${src[t.PRERELEASE]})?${src[t.BUILD]}?)?)?`);\n createToken(\"XRANGEPLAINLOOSE\", `[v=\\\\s]*(${src[t.XRANGEIDENTIFIERLOOSE]})(?:\\\\.(${src[t.XRANGEIDENTIFIERLOOSE]})(?:\\\\.(${src[t.XRANGEIDENTIFIERLOOSE]})(?:${src[t.PRERELEASELOOSE]})?${src[t.BUILD]}?)?)?`);\n createToken(\"XRANGE\", `^${src[t.GTLT]}\\\\s*${src[t.XRANGEPLAIN]}$`);\n createToken(\"XRANGELOOSE\", `^${src[t.GTLT]}\\\\s*${src[t.XRANGEPLAINLOOSE]}$`);\n createToken(\"COERCEPLAIN\", `${\"(^|[^\\\\d])(\\\\d{1,\"}${MAX_SAFE_COMPONENT_LENGTH}})(?:\\\\.(\\\\d{1,${MAX_SAFE_COMPONENT_LENGTH}}))?(?:\\\\.(\\\\d{1,${MAX_SAFE_COMPONENT_LENGTH}}))?`);\n createToken(\"COERCE\", `${src[t.COERCEPLAIN]}(?:$|[^\\\\d])`);\n createToken(\"COERCEFULL\", src[t.COERCEPLAIN] + `(?:${src[t.PRERELEASE]})?(?:${src[t.BUILD]})?(?:$|[^\\\\d])`);\n createToken(\"COERCERTL\", src[t.COERCE], true);\n createToken(\"COERCERTLFULL\", src[t.COERCEFULL], true);\n createToken(\"LONETILDE\", \"(?:~>?)\");\n createToken(\"TILDETRIM\", `(\\\\s*)${src[t.LONETILDE]}\\\\s+`, true);\n exports.tildeTrimReplace = \"$1~\";\n createToken(\"TILDE\", `^${src[t.LONETILDE]}${src[t.XRANGEPLAIN]}$`);\n createToken(\"TILDELOOSE\", `^${src[t.LONETILDE]}${src[t.XRANGEPLAINLOOSE]}$`);\n createToken(\"LONECARET\", \"(?:\\\\^)\");\n createToken(\"CARETTRIM\", `(\\\\s*)${src[t.LONECARET]}\\\\s+`, true);\n exports.caretTrimReplace = \"$1^\";\n createToken(\"CARET\", `^${src[t.LONECARET]}${src[t.XRANGEPLAIN]}$`);\n createToken(\"CARETLOOSE\", `^${src[t.LONECARET]}${src[t.XRANGEPLAINLOOSE]}$`);\n createToken(\"COMPARATORLOOSE\", `^${src[t.GTLT]}\\\\s*(${src[t.LOOSEPLAIN]})$|^$`);\n createToken(\"COMPARATOR\", `^${src[t.GTLT]}\\\\s*(${src[t.FULLPLAIN]})$|^$`);\n createToken(\"COMPARATORTRIM\", `(\\\\s*)${src[t.GTLT]}\\\\s*(${src[t.LOOSEPLAIN]}|${src[t.XRANGEPLAIN]})`, true);\n exports.comparatorTrimReplace = \"$1$2$3\";\n createToken(\"HYPHENRANGE\", `^\\\\s*(${src[t.XRANGEPLAIN]})\\\\s+-\\\\s+(${src[t.XRANGEPLAIN]})\\\\s*$`);\n createToken(\"HYPHENRANGELOOSE\", `^\\\\s*(${src[t.XRANGEPLAINLOOSE]})\\\\s+-\\\\s+(${src[t.XRANGEPLAINLOOSE]})\\\\s*$`);\n createToken(\"STAR\", \"(<|>)?=?\\\\s*\\\\*\");\n createToken(\"GTE0\", \"^\\\\s*>=\\\\s*0\\\\.0\\\\.0\\\\s*$\");\n createToken(\"GTE0PRE\", \"^\\\\s*>=\\\\s*0\\\\.0\\\\.0-0\\\\s*$\");\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/parse-options.js\nvar require_parse_options = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/parse-options.js\"(exports, module) {\n \"use strict\";\n var looseOption = Object.freeze({ loose: true });\n var emptyOpts = Object.freeze({});\n var parseOptions = (options) => {\n if (!options) {\n return emptyOpts;\n }\n if (typeof options !== \"object\") {\n return looseOption;\n }\n return options;\n };\n module.exports = parseOptions;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/identifiers.js\nvar require_identifiers = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/identifiers.js\"(exports, module) {\n \"use strict\";\n var numeric = /^[0-9]+$/;\n var compareIdentifiers = (a, b) => {\n if (typeof a === \"number\" && typeof b === \"number\") {\n return a === b ? 0 : a < b ? -1 : 1;\n }\n const anum = numeric.test(a);\n const bnum = numeric.test(b);\n if (anum && bnum) {\n a = +a;\n b = +b;\n }\n return a === b ? 0 : anum && !bnum ? -1 : bnum && !anum ? 1 : a < b ? -1 : 1;\n };\n var rcompareIdentifiers = (a, b) => compareIdentifiers(b, a);\n module.exports = {\n compareIdentifiers,\n rcompareIdentifiers\n };\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/semver.js\nvar require_semver = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/semver.js\"(exports, module) {\n \"use strict\";\n var debug = require_debug();\n var { MAX_LENGTH, MAX_SAFE_INTEGER } = require_constants();\n var { safeRe: re, t } = require_re();\n var parseOptions = require_parse_options();\n var { compareIdentifiers } = require_identifiers();\n var SemVer = class _SemVer {\n constructor(version2, options) {\n options = parseOptions(options);\n if (version2 instanceof _SemVer) {\n if (version2.loose === !!options.loose && version2.includePrerelease === !!options.includePrerelease) {\n return version2;\n } else {\n version2 = version2.version;\n }\n } else if (typeof version2 !== \"string\") {\n throw new TypeError(`Invalid version. Must be a string. Got type \"${typeof version2}\".`);\n }\n if (version2.length > MAX_LENGTH) {\n throw new TypeError(\n `version is longer than ${MAX_LENGTH} characters`\n );\n }\n debug(\"SemVer\", version2, options);\n this.options = options;\n this.loose = !!options.loose;\n this.includePrerelease = !!options.includePrerelease;\n const m = version2.trim().match(options.loose ? re[t.LOOSE] : re[t.FULL]);\n if (!m) {\n throw new TypeError(`Invalid Version: ${version2}`);\n }\n this.raw = version2;\n this.major = +m[1];\n this.minor = +m[2];\n this.patch = +m[3];\n if (this.major > MAX_SAFE_INTEGER || this.major < 0) {\n throw new TypeError(\"Invalid major version\");\n }\n if (this.minor > MAX_SAFE_INTEGER || this.minor < 0) {\n throw new TypeError(\"Invalid minor version\");\n }\n if (this.patch > MAX_SAFE_INTEGER || this.patch < 0) {\n throw new TypeError(\"Invalid patch version\");\n }\n if (!m[4]) {\n this.prerelease = [];\n } else {\n this.prerelease = m[4].split(\".\").map((id) => {\n if (/^[0-9]+$/.test(id)) {\n const num = +id;\n if (num >= 0 && num < MAX_SAFE_INTEGER) {\n return num;\n }\n }\n return id;\n });\n }\n this.build = m[5] ? m[5].split(\".\") : [];\n this.format();\n }\n format() {\n this.version = `${this.major}.${this.minor}.${this.patch}`;\n if (this.prerelease.length) {\n this.version += `-${this.prerelease.join(\".\")}`;\n }\n return this.version;\n }\n toString() {\n return this.version;\n }\n compare(other) {\n debug(\"SemVer.compare\", this.version, this.options, other);\n if (!(other instanceof _SemVer)) {\n if (typeof other === \"string\" && other === this.version) {\n return 0;\n }\n other = new _SemVer(other, this.options);\n }\n if (other.version === this.version) {\n return 0;\n }\n return this.compareMain(other) || this.comparePre(other);\n }\n compareMain(other) {\n if (!(other instanceof _SemVer)) {\n other = new _SemVer(other, this.options);\n }\n if (this.major < other.major) {\n return -1;\n }\n if (this.major > other.major) {\n return 1;\n }\n if (this.minor < other.minor) {\n return -1;\n }\n if (this.minor > other.minor) {\n return 1;\n }\n if (this.patch < other.patch) {\n return -1;\n }\n if (this.patch > other.patch) {\n return 1;\n }\n return 0;\n }\n comparePre(other) {\n if (!(other instanceof _SemVer)) {\n other = new _SemVer(other, this.options);\n }\n if (this.prerelease.length && !other.prerelease.length) {\n return -1;\n } else if (!this.prerelease.length && other.prerelease.length) {\n return 1;\n } else if (!this.prerelease.length && !other.prerelease.length) {\n return 0;\n }\n let i = 0;\n do {\n const a = this.prerelease[i];\n const b = other.prerelease[i];\n debug(\"prerelease compare\", i, a, b);\n if (a === void 0 && b === void 0) {\n return 0;\n } else if (b === void 0) {\n return 1;\n } else if (a === void 0) {\n return -1;\n } else if (a === b) {\n continue;\n } else {\n return compareIdentifiers(a, b);\n }\n } while (++i);\n }\n compareBuild(other) {\n if (!(other instanceof _SemVer)) {\n other = new _SemVer(other, this.options);\n }\n let i = 0;\n do {\n const a = this.build[i];\n const b = other.build[i];\n debug(\"build compare\", i, a, b);\n if (a === void 0 && b === void 0) {\n return 0;\n } else if (b === void 0) {\n return 1;\n } else if (a === void 0) {\n return -1;\n } else if (a === b) {\n continue;\n } else {\n return compareIdentifiers(a, b);\n }\n } while (++i);\n }\n // preminor will bump the version up to the next minor release, and immediately\n // down to pre-release. premajor and prepatch work the same way.\n inc(release, identifier, identifierBase) {\n if (release.startsWith(\"pre\")) {\n if (!identifier && identifierBase === false) {\n throw new Error(\"invalid increment argument: identifier is empty\");\n }\n if (identifier) {\n const match = `-${identifier}`.match(this.options.loose ? re[t.PRERELEASELOOSE] : re[t.PRERELEASE]);\n if (!match || match[1] !== identifier) {\n throw new Error(`invalid identifier: ${identifier}`);\n }\n }\n }\n switch (release) {\n case \"premajor\":\n this.prerelease.length = 0;\n this.patch = 0;\n this.minor = 0;\n this.major++;\n this.inc(\"pre\", identifier, identifierBase);\n break;\n case \"preminor\":\n this.prerelease.length = 0;\n this.patch = 0;\n this.minor++;\n this.inc(\"pre\", identifier, identifierBase);\n break;\n case \"prepatch\":\n this.prerelease.length = 0;\n this.inc(\"patch\", identifier, identifierBase);\n this.inc(\"pre\", identifier, identifierBase);\n break;\n // If the input is a non-prerelease version, this acts the same as\n // prepatch.\n case \"prerelease\":\n if (this.prerelease.length === 0) {\n this.inc(\"patch\", identifier, identifierBase);\n }\n this.inc(\"pre\", identifier, identifierBase);\n break;\n case \"release\":\n if (this.prerelease.length === 0) {\n throw new Error(`version ${this.raw} is not a prerelease`);\n }\n this.prerelease.length = 0;\n break;\n case \"major\":\n if (this.minor !== 0 || this.patch !== 0 || this.prerelease.length === 0) {\n this.major++;\n }\n this.minor = 0;\n this.patch = 0;\n this.prerelease = [];\n break;\n case \"minor\":\n if (this.patch !== 0 || this.prerelease.length === 0) {\n this.minor++;\n }\n this.patch = 0;\n this.prerelease = [];\n break;\n case \"patch\":\n if (this.prerelease.length === 0) {\n this.patch++;\n }\n this.prerelease = [];\n break;\n // This probably shouldn't be used publicly.\n // 1.0.0 'pre' would become 1.0.0-0 which is the wrong direction.\n case \"pre\": {\n const base = Number(identifierBase) ? 1 : 0;\n if (this.prerelease.length === 0) {\n this.prerelease = [base];\n } else {\n let i = this.prerelease.length;\n while (--i >= 0) {\n if (typeof this.prerelease[i] === \"number\") {\n this.prerelease[i]++;\n i = -2;\n }\n }\n if (i === -1) {\n if (identifier === this.prerelease.join(\".\") && identifierBase === false) {\n throw new Error(\"invalid increment argument: identifier already exists\");\n }\n this.prerelease.push(base);\n }\n }\n if (identifier) {\n let prerelease = [identifier, base];\n if (identifierBase === false) {\n prerelease = [identifier];\n }\n if (compareIdentifiers(this.prerelease[0], identifier) === 0) {\n if (isNaN(this.prerelease[1])) {\n this.prerelease = prerelease;\n }\n } else {\n this.prerelease = prerelease;\n }\n }\n break;\n }\n default:\n throw new Error(`invalid increment argument: ${release}`);\n }\n this.raw = this.format();\n if (this.build.length) {\n this.raw += `+${this.build.join(\".\")}`;\n }\n return this;\n }\n };\n module.exports = SemVer;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/parse.js\nvar require_parse = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/parse.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var parse = (version2, options, throwErrors = false) => {\n if (version2 instanceof SemVer) {\n return version2;\n }\n try {\n return new SemVer(version2, options);\n } catch (er) {\n if (!throwErrors) {\n return null;\n }\n throw er;\n }\n };\n module.exports = parse;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/valid.js\nvar require_valid = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/valid.js\"(exports, module) {\n \"use strict\";\n var parse = require_parse();\n var valid2 = (version2, options) => {\n const v = parse(version2, options);\n return v ? v.version : null;\n };\n module.exports = valid2;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/clean.js\nvar require_clean = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/clean.js\"(exports, module) {\n \"use strict\";\n var parse = require_parse();\n var clean = (version2, options) => {\n const s = parse(version2.trim().replace(/^[=v]+/, \"\"), options);\n return s ? s.version : null;\n };\n module.exports = clean;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/inc.js\nvar require_inc = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/inc.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var inc = (version2, release, options, identifier, identifierBase) => {\n if (typeof options === \"string\") {\n identifierBase = identifier;\n identifier = options;\n options = void 0;\n }\n try {\n return new SemVer(\n version2 instanceof SemVer ? version2.version : version2,\n options\n ).inc(release, identifier, identifierBase).version;\n } catch (er) {\n return null;\n }\n };\n module.exports = inc;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/diff.js\nvar require_diff = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/diff.js\"(exports, module) {\n \"use strict\";\n var parse = require_parse();\n var diff = (version1, version2) => {\n const v1 = parse(version1, null, true);\n const v2 = parse(version2, null, true);\n const comparison = v1.compare(v2);\n if (comparison === 0) {\n return null;\n }\n const v1Higher = comparison > 0;\n const highVersion = v1Higher ? v1 : v2;\n const lowVersion = v1Higher ? v2 : v1;\n const highHasPre = !!highVersion.prerelease.length;\n const lowHasPre = !!lowVersion.prerelease.length;\n if (lowHasPre && !highHasPre) {\n if (!lowVersion.patch && !lowVersion.minor) {\n return \"major\";\n }\n if (lowVersion.compareMain(highVersion) === 0) {\n if (lowVersion.minor && !lowVersion.patch) {\n return \"minor\";\n }\n return \"patch\";\n }\n }\n const prefix = highHasPre ? \"pre\" : \"\";\n if (v1.major !== v2.major) {\n return prefix + \"major\";\n }\n if (v1.minor !== v2.minor) {\n return prefix + \"minor\";\n }\n if (v1.patch !== v2.patch) {\n return prefix + \"patch\";\n }\n return \"prerelease\";\n };\n module.exports = diff;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/major.js\nvar require_major = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/major.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var major = (a, loose) => new SemVer(a, loose).major;\n module.exports = major;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/minor.js\nvar require_minor = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/minor.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var minor = (a, loose) => new SemVer(a, loose).minor;\n module.exports = minor;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/patch.js\nvar require_patch = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/patch.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var patch = (a, loose) => new SemVer(a, loose).patch;\n module.exports = patch;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/prerelease.js\nvar require_prerelease = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/prerelease.js\"(exports, module) {\n \"use strict\";\n var parse = require_parse();\n var prerelease = (version2, options) => {\n const parsed = parse(version2, options);\n return parsed && parsed.prerelease.length ? parsed.prerelease : null;\n };\n module.exports = prerelease;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare.js\nvar require_compare = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var compare = (a, b, loose) => new SemVer(a, loose).compare(new SemVer(b, loose));\n module.exports = compare;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/rcompare.js\nvar require_rcompare = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/rcompare.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var rcompare = (a, b, loose) => compare(b, a, loose);\n module.exports = rcompare;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare-loose.js\nvar require_compare_loose = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare-loose.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var compareLoose = (a, b) => compare(a, b, true);\n module.exports = compareLoose;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare-build.js\nvar require_compare_build = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare-build.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var compareBuild = (a, b, loose) => {\n const versionA = new SemVer(a, loose);\n const versionB = new SemVer(b, loose);\n return versionA.compare(versionB) || versionA.compareBuild(versionB);\n };\n module.exports = compareBuild;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/sort.js\nvar require_sort = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/sort.js\"(exports, module) {\n \"use strict\";\n var compareBuild = require_compare_build();\n var sort = (list, loose) => list.sort((a, b) => compareBuild(a, b, loose));\n module.exports = sort;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/rsort.js\nvar require_rsort = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/rsort.js\"(exports, module) {\n \"use strict\";\n var compareBuild = require_compare_build();\n var rsort = (list, loose) => list.sort((a, b) => compareBuild(b, a, loose));\n module.exports = rsort;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/gt.js\nvar require_gt = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/gt.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var gt = (a, b, loose) => compare(a, b, loose) > 0;\n module.exports = gt;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/lt.js\nvar require_lt = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/lt.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var lt = (a, b, loose) => compare(a, b, loose) < 0;\n module.exports = lt;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/eq.js\nvar require_eq = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/eq.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var eq = (a, b, loose) => compare(a, b, loose) === 0;\n module.exports = eq;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/neq.js\nvar require_neq = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/neq.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var neq = (a, b, loose) => compare(a, b, loose) !== 0;\n module.exports = neq;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/gte.js\nvar require_gte = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/gte.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var gte = (a, b, loose) => compare(a, b, loose) >= 0;\n module.exports = gte;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/lte.js\nvar require_lte = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/lte.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var lte = (a, b, loose) => compare(a, b, loose) <= 0;\n module.exports = lte;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/cmp.js\nvar require_cmp = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/cmp.js\"(exports, module) {\n \"use strict\";\n var eq = require_eq();\n var neq = require_neq();\n var gt = require_gt();\n var gte = require_gte();\n var lt = require_lt();\n var lte = require_lte();\n var cmp = (a, op, b, loose) => {\n switch (op) {\n case \"===\":\n if (typeof a === \"object\") {\n a = a.version;\n }\n if (typeof b === \"object\") {\n b = b.version;\n }\n return a === b;\n case \"!==\":\n if (typeof a === \"object\") {\n a = a.version;\n }\n if (typeof b === \"object\") {\n b = b.version;\n }\n return a !== b;\n case \"\":\n case \"=\":\n case \"==\":\n return eq(a, b, loose);\n case \"!=\":\n return neq(a, b, loose);\n case \">\":\n return gt(a, b, loose);\n case \">=\":\n return gte(a, b, loose);\n case \"<\":\n return lt(a, b, loose);\n case \"<=\":\n return lte(a, b, loose);\n default:\n throw new TypeError(`Invalid operator: ${op}`);\n }\n };\n module.exports = cmp;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/coerce.js\nvar require_coerce = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/coerce.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var parse = require_parse();\n var { safeRe: re, t } = require_re();\n var coerce = (version2, options) => {\n if (version2 instanceof SemVer) {\n return version2;\n }\n if (typeof version2 === \"number\") {\n version2 = String(version2);\n }\n if (typeof version2 !== \"string\") {\n return null;\n }\n options = options || {};\n let match = null;\n if (!options.rtl) {\n match = version2.match(options.includePrerelease ? re[t.COERCEFULL] : re[t.COERCE]);\n } else {\n const coerceRtlRegex = options.includePrerelease ? re[t.COERCERTLFULL] : re[t.COERCERTL];\n let next;\n while ((next = coerceRtlRegex.exec(version2)) && (!match || match.index + match[0].length !== version2.length)) {\n if (!match || next.index + next[0].length !== match.index + match[0].length) {\n match = next;\n }\n coerceRtlRegex.lastIndex = next.index + next[1].length + next[2].length;\n }\n coerceRtlRegex.lastIndex = -1;\n }\n if (match === null) {\n return null;\n }\n const major = match[2];\n const minor = match[3] || \"0\";\n const patch = match[4] || \"0\";\n const prerelease = options.includePrerelease && match[5] ? `-${match[5]}` : \"\";\n const build = options.includePrerelease && match[6] ? `+${match[6]}` : \"\";\n return parse(`${major}.${minor}.${patch}${prerelease}${build}`, options);\n };\n module.exports = coerce;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/lrucache.js\nvar require_lrucache = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/lrucache.js\"(exports, module) {\n \"use strict\";\n var LRUCache = class {\n constructor() {\n this.max = 1e3;\n this.map = /* @__PURE__ */ new Map();\n }\n get(key) {\n const value = this.map.get(key);\n if (value === void 0) {\n return void 0;\n } else {\n this.map.delete(key);\n this.map.set(key, value);\n return value;\n }\n }\n delete(key) {\n return this.map.delete(key);\n }\n set(key, value) {\n const deleted = this.delete(key);\n if (!deleted && value !== void 0) {\n if (this.map.size >= this.max) {\n const firstKey = this.map.keys().next().value;\n this.delete(firstKey);\n }\n this.map.set(key, value);\n }\n return this;\n }\n };\n module.exports = LRUCache;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/range.js\nvar require_range = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/range.js\"(exports, module) {\n \"use strict\";\n var SPACE_CHARACTERS = /\\s+/g;\n var Range = class _Range {\n constructor(range, options) {\n options = parseOptions(options);\n if (range instanceof _Range) {\n if (range.loose === !!options.loose && range.includePrerelease === !!options.includePrerelease) {\n return range;\n } else {\n return new _Range(range.raw, options);\n }\n }\n if (range instanceof Comparator) {\n this.raw = range.value;\n this.set = [[range]];\n this.formatted = void 0;\n return this;\n }\n this.options = options;\n this.loose = !!options.loose;\n this.includePrerelease = !!options.includePrerelease;\n this.raw = range.trim().replace(SPACE_CHARACTERS, \" \");\n this.set = this.raw.split(\"||\").map((r) => this.parseRange(r.trim())).filter((c) => c.length);\n if (!this.set.length) {\n throw new TypeError(`Invalid SemVer Range: ${this.raw}`);\n }\n if (this.set.length > 1) {\n const first = this.set[0];\n this.set = this.set.filter((c) => !isNullSet(c[0]));\n if (this.set.length === 0) {\n this.set = [first];\n } else if (this.set.length > 1) {\n for (const c of this.set) {\n if (c.length === 1 && isAny(c[0])) {\n this.set = [c];\n break;\n }\n }\n }\n }\n this.formatted = void 0;\n }\n get range() {\n if (this.formatted === void 0) {\n this.formatted = \"\";\n for (let i = 0; i < this.set.length; i++) {\n if (i > 0) {\n this.formatted += \"||\";\n }\n const comps = this.set[i];\n for (let k = 0; k < comps.length; k++) {\n if (k > 0) {\n this.formatted += \" \";\n }\n this.formatted += comps[k].toString().trim();\n }\n }\n }\n return this.formatted;\n }\n format() {\n return this.range;\n }\n toString() {\n return this.range;\n }\n parseRange(range) {\n const memoOpts = (this.options.includePrerelease && FLAG_INCLUDE_PRERELEASE) | (this.options.loose && FLAG_LOOSE);\n const memoKey = memoOpts + \":\" + range;\n const cached = cache.get(memoKey);\n if (cached) {\n return cached;\n }\n const loose = this.options.loose;\n const hr = loose ? re[t.HYPHENRANGELOOSE] : re[t.HYPHENRANGE];\n range = range.replace(hr, hyphenReplace(this.options.includePrerelease));\n debug(\"hyphen replace\", range);\n range = range.replace(re[t.COMPARATORTRIM], comparatorTrimReplace);\n debug(\"comparator trim\", range);\n range = range.replace(re[t.TILDETRIM], tildeTrimReplace);\n debug(\"tilde trim\", range);\n range = range.replace(re[t.CARETTRIM], caretTrimReplace);\n debug(\"caret trim\", range);\n let rangeList = range.split(\" \").map((comp) => parseComparator(comp, this.options)).join(\" \").split(/\\s+/).map((comp) => replaceGTE0(comp, this.options));\n if (loose) {\n rangeList = rangeList.filter((comp) => {\n debug(\"loose invalid filter\", comp, this.options);\n return !!comp.match(re[t.COMPARATORLOOSE]);\n });\n }\n debug(\"range list\", rangeList);\n const rangeMap = /* @__PURE__ */ new Map();\n const comparators = rangeList.map((comp) => new Comparator(comp, this.options));\n for (const comp of comparators) {\n if (isNullSet(comp)) {\n return [comp];\n }\n rangeMap.set(comp.value, comp);\n }\n if (rangeMap.size > 1 && rangeMap.has(\"\")) {\n rangeMap.delete(\"\");\n }\n const result = [...rangeMap.values()];\n cache.set(memoKey, result);\n return result;\n }\n intersects(range, options) {\n if (!(range instanceof _Range)) {\n throw new TypeError(\"a Range is required\");\n }\n return this.set.some((thisComparators) => {\n return isSatisfiable(thisComparators, options) && range.set.some((rangeComparators) => {\n return isSatisfiable(rangeComparators, options) && thisComparators.every((thisComparator) => {\n return rangeComparators.every((rangeComparator) => {\n return thisComparator.intersects(rangeComparator, options);\n });\n });\n });\n });\n }\n // if ANY of the sets match ALL of its comparators, then pass\n test(version2) {\n if (!version2) {\n return false;\n }\n if (typeof version2 === \"string\") {\n try {\n version2 = new SemVer(version2, this.options);\n } catch (er) {\n return false;\n }\n }\n for (let i = 0; i < this.set.length; i++) {\n if (testSet(this.set[i], version2, this.options)) {\n return true;\n }\n }\n return false;\n }\n };\n module.exports = Range;\n var LRU = require_lrucache();\n var cache = new LRU();\n var parseOptions = require_parse_options();\n var Comparator = require_comparator();\n var debug = require_debug();\n var SemVer = require_semver();\n var {\n safeRe: re,\n t,\n comparatorTrimReplace,\n tildeTrimReplace,\n caretTrimReplace\n } = require_re();\n var { FLAG_INCLUDE_PRERELEASE, FLAG_LOOSE } = require_constants();\n var isNullSet = (c) => c.value === \"<0.0.0-0\";\n var isAny = (c) => c.value === \"\";\n var isSatisfiable = (comparators, options) => {\n let result = true;\n const remainingComparators = comparators.slice();\n let testComparator = remainingComparators.pop();\n while (result && remainingComparators.length) {\n result = remainingComparators.every((otherComparator) => {\n return testComparator.intersects(otherComparator, options);\n });\n testComparator = remainingComparators.pop();\n }\n return result;\n };\n var parseComparator = (comp, options) => {\n comp = comp.replace(re[t.BUILD], \"\");\n debug(\"comp\", comp, options);\n comp = replaceCarets(comp, options);\n debug(\"caret\", comp);\n comp = replaceTildes(comp, options);\n debug(\"tildes\", comp);\n comp = replaceXRanges(comp, options);\n debug(\"xrange\", comp);\n comp = replaceStars(comp, options);\n debug(\"stars\", comp);\n return comp;\n };\n var isX = (id) => !id || id.toLowerCase() === \"x\" || id === \"*\";\n var replaceTildes = (comp, options) => {\n return comp.trim().split(/\\s+/).map((c) => replaceTilde(c, options)).join(\" \");\n };\n var replaceTilde = (comp, options) => {\n const r = options.loose ? re[t.TILDELOOSE] : re[t.TILDE];\n return comp.replace(r, (_, M, m, p, pr) => {\n debug(\"tilde\", comp, _, M, m, p, pr);\n let ret;\n if (isX(M)) {\n ret = \"\";\n } else if (isX(m)) {\n ret = `>=${M}.0.0 <${+M + 1}.0.0-0`;\n } else if (isX(p)) {\n ret = `>=${M}.${m}.0 <${M}.${+m + 1}.0-0`;\n } else if (pr) {\n debug(\"replaceTilde pr\", pr);\n ret = `>=${M}.${m}.${p}-${pr} <${M}.${+m + 1}.0-0`;\n } else {\n ret = `>=${M}.${m}.${p} <${M}.${+m + 1}.0-0`;\n }\n debug(\"tilde return\", ret);\n return ret;\n });\n };\n var replaceCarets = (comp, options) => {\n return comp.trim().split(/\\s+/).map((c) => replaceCaret(c, options)).join(\" \");\n };\n var replaceCaret = (comp, options) => {\n debug(\"caret\", comp, options);\n const r = options.loose ? re[t.CARETLOOSE] : re[t.CARET];\n const z = options.includePrerelease ? \"-0\" : \"\";\n return comp.replace(r, (_, M, m, p, pr) => {\n debug(\"caret\", comp, _, M, m, p, pr);\n let ret;\n if (isX(M)) {\n ret = \"\";\n } else if (isX(m)) {\n ret = `>=${M}.0.0${z} <${+M + 1}.0.0-0`;\n } else if (isX(p)) {\n if (M === \"0\") {\n ret = `>=${M}.${m}.0${z} <${M}.${+m + 1}.0-0`;\n } else {\n ret = `>=${M}.${m}.0${z} <${+M + 1}.0.0-0`;\n }\n } else if (pr) {\n debug(\"replaceCaret pr\", pr);\n if (M === \"0\") {\n if (m === \"0\") {\n ret = `>=${M}.${m}.${p}-${pr} <${M}.${m}.${+p + 1}-0`;\n } else {\n ret = `>=${M}.${m}.${p}-${pr} <${M}.${+m + 1}.0-0`;\n }\n } else {\n ret = `>=${M}.${m}.${p}-${pr} <${+M + 1}.0.0-0`;\n }\n } else {\n debug(\"no pr\");\n if (M === \"0\") {\n if (m === \"0\") {\n ret = `>=${M}.${m}.${p}${z} <${M}.${m}.${+p + 1}-0`;\n } else {\n ret = `>=${M}.${m}.${p}${z} <${M}.${+m + 1}.0-0`;\n }\n } else {\n ret = `>=${M}.${m}.${p} <${+M + 1}.0.0-0`;\n }\n }\n debug(\"caret return\", ret);\n return ret;\n });\n };\n var replaceXRanges = (comp, options) => {\n debug(\"replaceXRanges\", comp, options);\n return comp.split(/\\s+/).map((c) => replaceXRange(c, options)).join(\" \");\n };\n var replaceXRange = (comp, options) => {\n comp = comp.trim();\n const r = options.loose ? re[t.XRANGELOOSE] : re[t.XRANGE];\n return comp.replace(r, (ret, gtlt, M, m, p, pr) => {\n debug(\"xRange\", comp, ret, gtlt, M, m, p, pr);\n const xM = isX(M);\n const xm = xM || isX(m);\n const xp = xm || isX(p);\n const anyX = xp;\n if (gtlt === \"=\" && anyX) {\n gtlt = \"\";\n }\n pr = options.includePrerelease ? \"-0\" : \"\";\n if (xM) {\n if (gtlt === \">\" || gtlt === \"<\") {\n ret = \"<0.0.0-0\";\n } else {\n ret = \"*\";\n }\n } else if (gtlt && anyX) {\n if (xm) {\n m = 0;\n }\n p = 0;\n if (gtlt === \">\") {\n gtlt = \">=\";\n if (xm) {\n M = +M + 1;\n m = 0;\n p = 0;\n } else {\n m = +m + 1;\n p = 0;\n }\n } else if (gtlt === \"<=\") {\n gtlt = \"<\";\n if (xm) {\n M = +M + 1;\n } else {\n m = +m + 1;\n }\n }\n if (gtlt === \"<\") {\n pr = \"-0\";\n }\n ret = `${gtlt + M}.${m}.${p}${pr}`;\n } else if (xm) {\n ret = `>=${M}.0.0${pr} <${+M + 1}.0.0-0`;\n } else if (xp) {\n ret = `>=${M}.${m}.0${pr} <${M}.${+m + 1}.0-0`;\n }\n debug(\"xRange return\", ret);\n return ret;\n });\n };\n var replaceStars = (comp, options) => {\n debug(\"replaceStars\", comp, options);\n return comp.trim().replace(re[t.STAR], \"\");\n };\n var replaceGTE0 = (comp, options) => {\n debug(\"replaceGTE0\", comp, options);\n return comp.trim().replace(re[options.includePrerelease ? t.GTE0PRE : t.GTE0], \"\");\n };\n var hyphenReplace = (incPr) => ($0, from, fM, fm, fp, fpr, fb, to, tM, tm, tp, tpr) => {\n if (isX(fM)) {\n from = \"\";\n } else if (isX(fm)) {\n from = `>=${fM}.0.0${incPr ? \"-0\" : \"\"}`;\n } else if (isX(fp)) {\n from = `>=${fM}.${fm}.0${incPr ? \"-0\" : \"\"}`;\n } else if (fpr) {\n from = `>=${from}`;\n } else {\n from = `>=${from}${incPr ? \"-0\" : \"\"}`;\n }\n if (isX(tM)) {\n to = \"\";\n } else if (isX(tm)) {\n to = `<${+tM + 1}.0.0-0`;\n } else if (isX(tp)) {\n to = `<${tM}.${+tm + 1}.0-0`;\n } else if (tpr) {\n to = `<=${tM}.${tm}.${tp}-${tpr}`;\n } else if (incPr) {\n to = `<${tM}.${tm}.${+tp + 1}-0`;\n } else {\n to = `<=${to}`;\n }\n return `${from} ${to}`.trim();\n };\n var testSet = (set, version2, options) => {\n for (let i = 0; i < set.length; i++) {\n if (!set[i].test(version2)) {\n return false;\n }\n }\n if (version2.prerelease.length && !options.includePrerelease) {\n for (let i = 0; i < set.length; i++) {\n debug(set[i].semver);\n if (set[i].semver === Comparator.ANY) {\n continue;\n }\n if (set[i].semver.prerelease.length > 0) {\n const allowed = set[i].semver;\n if (allowed.major === version2.major && allowed.minor === version2.minor && allowed.patch === version2.patch) {\n return true;\n }\n }\n }\n return false;\n }\n return true;\n };\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/comparator.js\nvar require_comparator = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/comparator.js\"(exports, module) {\n \"use strict\";\n var ANY = /* @__PURE__ */ Symbol(\"SemVer ANY\");\n var Comparator = class _Comparator {\n static get ANY() {\n return ANY;\n }\n constructor(comp, options) {\n options = parseOptions(options);\n if (comp instanceof _Comparator) {\n if (comp.loose === !!options.loose) {\n return comp;\n } else {\n comp = comp.value;\n }\n }\n comp = comp.trim().split(/\\s+/).join(\" \");\n debug(\"comparator\", comp, options);\n this.options = options;\n this.loose = !!options.loose;\n this.parse(comp);\n if (this.semver === ANY) {\n this.value = \"\";\n } else {\n this.value = this.operator + this.semver.version;\n }\n debug(\"comp\", this);\n }\n parse(comp) {\n const r = this.options.loose ? re[t.COMPARATORLOOSE] : re[t.COMPARATOR];\n const m = comp.match(r);\n if (!m) {\n throw new TypeError(`Invalid comparator: ${comp}`);\n }\n this.operator = m[1] !== void 0 ? m[1] : \"\";\n if (this.operator === \"=\") {\n this.operator = \"\";\n }\n if (!m[2]) {\n this.semver = ANY;\n } else {\n this.semver = new SemVer(m[2], this.options.loose);\n }\n }\n toString() {\n return this.value;\n }\n test(version2) {\n debug(\"Comparator.test\", version2, this.options.loose);\n if (this.semver === ANY || version2 === ANY) {\n return true;\n }\n if (typeof version2 === \"string\") {\n try {\n version2 = new SemVer(version2, this.options);\n } catch (er) {\n return false;\n }\n }\n return cmp(version2, this.operator, this.semver, this.options);\n }\n intersects(comp, options) {\n if (!(comp instanceof _Comparator)) {\n throw new TypeError(\"a Comparator is required\");\n }\n if (this.operator === \"\") {\n if (this.value === \"\") {\n return true;\n }\n return new Range(comp.value, options).test(this.value);\n } else if (comp.operator === \"\") {\n if (comp.value === \"\") {\n return true;\n }\n return new Range(this.value, options).test(comp.semver);\n }\n options = parseOptions(options);\n if (options.includePrerelease && (this.value === \"<0.0.0-0\" || comp.value === \"<0.0.0-0\")) {\n return false;\n }\n if (!options.includePrerelease && (this.value.startsWith(\"<0.0.0\") || comp.value.startsWith(\"<0.0.0\"))) {\n return false;\n }\n if (this.operator.startsWith(\">\") && comp.operator.startsWith(\">\")) {\n return true;\n }\n if (this.operator.startsWith(\"<\") && comp.operator.startsWith(\"<\")) {\n return true;\n }\n if (this.semver.version === comp.semver.version && this.operator.includes(\"=\") && comp.operator.includes(\"=\")) {\n return true;\n }\n if (cmp(this.semver, \"<\", comp.semver, options) && this.operator.startsWith(\">\") && comp.operator.startsWith(\"<\")) {\n return true;\n }\n if (cmp(this.semver, \">\", comp.semver, options) && this.operator.startsWith(\"<\") && comp.operator.startsWith(\">\")) {\n return true;\n }\n return false;\n }\n };\n module.exports = Comparator;\n var parseOptions = require_parse_options();\n var { safeRe: re, t } = require_re();\n var cmp = require_cmp();\n var debug = require_debug();\n var SemVer = require_semver();\n var Range = require_range();\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/satisfies.js\nvar require_satisfies = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/satisfies.js\"(exports, module) {\n \"use strict\";\n var Range = require_range();\n var satisfies2 = (version2, range, options) => {\n try {\n range = new Range(range, options);\n } catch (er) {\n return false;\n }\n return range.test(version2);\n };\n module.exports = satisfies2;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/to-comparators.js\nvar require_to_comparators = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/to-comparators.js\"(exports, module) {\n \"use strict\";\n var Range = require_range();\n var toComparators = (range, options) => new Range(range, options).set.map((comp) => comp.map((c) => c.value).join(\" \").trim().split(\" \"));\n module.exports = toComparators;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/max-satisfying.js\nvar require_max_satisfying = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/max-satisfying.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var Range = require_range();\n var maxSatisfying = (versions, range, options) => {\n let max = null;\n let maxSV = null;\n let rangeObj = null;\n try {\n rangeObj = new Range(range, options);\n } catch (er) {\n return null;\n }\n versions.forEach((v) => {\n if (rangeObj.test(v)) {\n if (!max || maxSV.compare(v) === -1) {\n max = v;\n maxSV = new SemVer(max, options);\n }\n }\n });\n return max;\n };\n module.exports = maxSatisfying;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/min-satisfying.js\nvar require_min_satisfying = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/min-satisfying.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var Range = require_range();\n var minSatisfying = (versions, range, options) => {\n let min = null;\n let minSV = null;\n let rangeObj = null;\n try {\n rangeObj = new Range(range, options);\n } catch (er) {\n return null;\n }\n versions.forEach((v) => {\n if (rangeObj.test(v)) {\n if (!min || minSV.compare(v) === 1) {\n min = v;\n minSV = new SemVer(min, options);\n }\n }\n });\n return min;\n };\n module.exports = minSatisfying;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/min-version.js\nvar require_min_version = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/min-version.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var Range = require_range();\n var gt = require_gt();\n var minVersion = (range, loose) => {\n range = new Range(range, loose);\n let minver = new SemVer(\"0.0.0\");\n if (range.test(minver)) {\n return minver;\n }\n minver = new SemVer(\"0.0.0-0\");\n if (range.test(minver)) {\n return minver;\n }\n minver = null;\n for (let i = 0; i < range.set.length; ++i) {\n const comparators = range.set[i];\n let setMin = null;\n comparators.forEach((comparator) => {\n const compver = new SemVer(comparator.semver.version);\n switch (comparator.operator) {\n case \">\":\n if (compver.prerelease.length === 0) {\n compver.patch++;\n } else {\n compver.prerelease.push(0);\n }\n compver.raw = compver.format();\n /* fallthrough */\n case \"\":\n case \">=\":\n if (!setMin || gt(compver, setMin)) {\n setMin = compver;\n }\n break;\n case \"<\":\n case \"<=\":\n break;\n /* istanbul ignore next */\n default:\n throw new Error(`Unexpected operation: ${comparator.operator}`);\n }\n });\n if (setMin && (!minver || gt(minver, setMin))) {\n minver = setMin;\n }\n }\n if (minver && range.test(minver)) {\n return minver;\n }\n return null;\n };\n module.exports = minVersion;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/valid.js\nvar require_valid2 = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/valid.js\"(exports, module) {\n \"use strict\";\n var Range = require_range();\n var validRange = (range, options) => {\n try {\n return new Range(range, options).range || \"*\";\n } catch (er) {\n return null;\n }\n };\n module.exports = validRange;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/outside.js\nvar require_outside = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/outside.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var Comparator = require_comparator();\n var { ANY } = Comparator;\n var Range = require_range();\n var satisfies2 = require_satisfies();\n var gt = require_gt();\n var lt = require_lt();\n var lte = require_lte();\n var gte = require_gte();\n var outside = (version2, range, hilo, options) => {\n version2 = new SemVer(version2, options);\n range = new Range(range, options);\n let gtfn, ltefn, ltfn, comp, ecomp;\n switch (hilo) {\n case \">\":\n gtfn = gt;\n ltefn = lte;\n ltfn = lt;\n comp = \">\";\n ecomp = \">=\";\n break;\n case \"<\":\n gtfn = lt;\n ltefn = gte;\n ltfn = gt;\n comp = \"<\";\n ecomp = \"<=\";\n break;\n default:\n throw new TypeError('Must provide a hilo val of \"<\" or \">\"');\n }\n if (satisfies2(version2, range, options)) {\n return false;\n }\n for (let i = 0; i < range.set.length; ++i) {\n const comparators = range.set[i];\n let high = null;\n let low = null;\n comparators.forEach((comparator) => {\n if (comparator.semver === ANY) {\n comparator = new Comparator(\">=0.0.0\");\n }\n high = high || comparator;\n low = low || comparator;\n if (gtfn(comparator.semver, high.semver, options)) {\n high = comparator;\n } else if (ltfn(comparator.semver, low.semver, options)) {\n low = comparator;\n }\n });\n if (high.operator === comp || high.operator === ecomp) {\n return false;\n }\n if ((!low.operator || low.operator === comp) && ltefn(version2, low.semver)) {\n return false;\n } else if (low.operator === ecomp && ltfn(version2, low.semver)) {\n return false;\n }\n }\n return true;\n };\n module.exports = outside;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/gtr.js\nvar require_gtr = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/gtr.js\"(exports, module) {\n \"use strict\";\n var outside = require_outside();\n var gtr = (version2, range, options) => outside(version2, range, \">\", options);\n module.exports = gtr;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/ltr.js\nvar require_ltr = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/ltr.js\"(exports, module) {\n \"use strict\";\n var outside = require_outside();\n var ltr = (version2, range, options) => outside(version2, range, \"<\", options);\n module.exports = ltr;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/intersects.js\nvar require_intersects = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/intersects.js\"(exports, module) {\n \"use strict\";\n var Range = require_range();\n var intersects = (r1, r2, options) => {\n r1 = new Range(r1, options);\n r2 = new Range(r2, options);\n return r1.intersects(r2, options);\n };\n module.exports = intersects;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/simplify.js\nvar require_simplify = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/simplify.js\"(exports, module) {\n \"use strict\";\n var satisfies2 = require_satisfies();\n var compare = require_compare();\n module.exports = (versions, range, options) => {\n const set = [];\n let first = null;\n let prev = null;\n const v = versions.sort((a, b) => compare(a, b, options));\n for (const version2 of v) {\n const included = satisfies2(version2, range, options);\n if (included) {\n prev = version2;\n if (!first) {\n first = version2;\n }\n } else {\n if (prev) {\n set.push([first, prev]);\n }\n prev = null;\n first = null;\n }\n }\n if (first) {\n set.push([first, null]);\n }\n const ranges2 = [];\n for (const [min, max] of set) {\n if (min === max) {\n ranges2.push(min);\n } else if (!max && min === v[0]) {\n ranges2.push(\"*\");\n } else if (!max) {\n ranges2.push(`>=${min}`);\n } else if (min === v[0]) {\n ranges2.push(`<=${max}`);\n } else {\n ranges2.push(`${min} - ${max}`);\n }\n }\n const simplified = ranges2.join(\" || \");\n const original = typeof range.raw === \"string\" ? range.raw : String(range);\n return simplified.length < original.length ? simplified : range;\n };\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/subset.js\nvar require_subset = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/subset.js\"(exports, module) {\n \"use strict\";\n var Range = require_range();\n var Comparator = require_comparator();\n var { ANY } = Comparator;\n var satisfies2 = require_satisfies();\n var compare = require_compare();\n var subset = (sub, dom, options = {}) => {\n if (sub === dom) {\n return true;\n }\n sub = new Range(sub, options);\n dom = new Range(dom, options);\n let sawNonNull = false;\n OUTER: for (const simpleSub of sub.set) {\n for (const simpleDom of dom.set) {\n const isSub = simpleSubset(simpleSub, simpleDom, options);\n sawNonNull = sawNonNull || isSub !== null;\n if (isSub) {\n continue OUTER;\n }\n }\n if (sawNonNull) {\n return false;\n }\n }\n return true;\n };\n var minimumVersionWithPreRelease = [new Comparator(\">=0.0.0-0\")];\n var minimumVersion = [new Comparator(\">=0.0.0\")];\n var simpleSubset = (sub, dom, options) => {\n if (sub === dom) {\n return true;\n }\n if (sub.length === 1 && sub[0].semver === ANY) {\n if (dom.length === 1 && dom[0].semver === ANY) {\n return true;\n } else if (options.includePrerelease) {\n sub = minimumVersionWithPreRelease;\n } else {\n sub = minimumVersion;\n }\n }\n if (dom.length === 1 && dom[0].semver === ANY) {\n if (options.includePrerelease) {\n return true;\n } else {\n dom = minimumVersion;\n }\n }\n const eqSet = /* @__PURE__ */ new Set();\n let gt, lt;\n for (const c of sub) {\n if (c.operator === \">\" || c.operator === \">=\") {\n gt = higherGT(gt, c, options);\n } else if (c.operator === \"<\" || c.operator === \"<=\") {\n lt = lowerLT(lt, c, options);\n } else {\n eqSet.add(c.semver);\n }\n }\n if (eqSet.size > 1) {\n return null;\n }\n let gtltComp;\n if (gt && lt) {\n gtltComp = compare(gt.semver, lt.semver, options);\n if (gtltComp > 0) {\n return null;\n } else if (gtltComp === 0 && (gt.operator !== \">=\" || lt.operator !== \"<=\")) {\n return null;\n }\n }\n for (const eq of eqSet) {\n if (gt && !satisfies2(eq, String(gt), options)) {\n return null;\n }\n if (lt && !satisfies2(eq, String(lt), options)) {\n return null;\n }\n for (const c of dom) {\n if (!satisfies2(eq, String(c), options)) {\n return false;\n }\n }\n return true;\n }\n let higher, lower;\n let hasDomLT, hasDomGT;\n let needDomLTPre = lt && !options.includePrerelease && lt.semver.prerelease.length ? lt.semver : false;\n let needDomGTPre = gt && !options.includePrerelease && gt.semver.prerelease.length ? gt.semver : false;\n if (needDomLTPre && needDomLTPre.prerelease.length === 1 && lt.operator === \"<\" && needDomLTPre.prerelease[0] === 0) {\n needDomLTPre = false;\n }\n for (const c of dom) {\n hasDomGT = hasDomGT || c.operator === \">\" || c.operator === \">=\";\n hasDomLT = hasDomLT || c.operator === \"<\" || c.operator === \"<=\";\n if (gt) {\n if (needDomGTPre) {\n if (c.semver.prerelease && c.semver.prerelease.length && c.semver.major === needDomGTPre.major && c.semver.minor === needDomGTPre.minor && c.semver.patch === needDomGTPre.patch) {\n needDomGTPre = false;\n }\n }\n if (c.operator === \">\" || c.operator === \">=\") {\n higher = higherGT(gt, c, options);\n if (higher === c && higher !== gt) {\n return false;\n }\n } else if (gt.operator === \">=\" && !satisfies2(gt.semver, String(c), options)) {\n return false;\n }\n }\n if (lt) {\n if (needDomLTPre) {\n if (c.semver.prerelease && c.semver.prerelease.length && c.semver.major === needDomLTPre.major && c.semver.minor === needDomLTPre.minor && c.semver.patch === needDomLTPre.patch) {\n needDomLTPre = false;\n }\n }\n if (c.operator === \"<\" || c.operator === \"<=\") {\n lower = lowerLT(lt, c, options);\n if (lower === c && lower !== lt) {\n return false;\n }\n } else if (lt.operator === \"<=\" && !satisfies2(lt.semver, String(c), options)) {\n return false;\n }\n }\n if (!c.operator && (lt || gt) && gtltComp !== 0) {\n return false;\n }\n }\n if (gt && hasDomLT && !lt && gtltComp !== 0) {\n return false;\n }\n if (lt && hasDomGT && !gt && gtltComp !== 0) {\n return false;\n }\n if (needDomGTPre || needDomLTPre) {\n return false;\n }\n return true;\n };\n var higherGT = (a, b, options) => {\n if (!a) {\n return b;\n }\n const comp = compare(a.semver, b.semver, options);\n return comp > 0 ? a : comp < 0 ? b : b.operator === \">\" && a.operator === \">=\" ? b : a;\n };\n var lowerLT = (a, b, options) => {\n if (!a) {\n return b;\n }\n const comp = compare(a.semver, b.semver, options);\n return comp < 0 ? a : comp > 0 ? b : b.operator === \"<\" && a.operator === \"<=\" ? b : a;\n };\n module.exports = subset;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/index.js\nvar require_semver2 = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/index.js\"(exports, module) {\n \"use strict\";\n var internalRe = require_re();\n var constants = require_constants();\n var SemVer = require_semver();\n var identifiers = require_identifiers();\n var parse = require_parse();\n var valid2 = require_valid();\n var clean = require_clean();\n var inc = require_inc();\n var diff = require_diff();\n var major = require_major();\n var minor = require_minor();\n var patch = require_patch();\n var prerelease = require_prerelease();\n var compare = require_compare();\n var rcompare = require_rcompare();\n var compareLoose = require_compare_loose();\n var compareBuild = require_compare_build();\n var sort = require_sort();\n var rsort = require_rsort();\n var gt = require_gt();\n var lt = require_lt();\n var eq = require_eq();\n var neq = require_neq();\n var gte = require_gte();\n var lte = require_lte();\n var cmp = require_cmp();\n var coerce = require_coerce();\n var Comparator = require_comparator();\n var Range = require_range();\n var satisfies2 = require_satisfies();\n var toComparators = require_to_comparators();\n var maxSatisfying = require_max_satisfying();\n var minSatisfying = require_min_satisfying();\n var minVersion = require_min_version();\n var validRange = require_valid2();\n var outside = require_outside();\n var gtr = require_gtr();\n var ltr = require_ltr();\n var intersects = require_intersects();\n var simplifyRange = require_simplify();\n var subset = require_subset();\n module.exports = {\n parse,\n valid: valid2,\n clean,\n inc,\n diff,\n major,\n minor,\n patch,\n prerelease,\n compare,\n rcompare,\n compareLoose,\n compareBuild,\n sort,\n rsort,\n gt,\n lt,\n eq,\n neq,\n gte,\n lte,\n cmp,\n coerce,\n Comparator,\n Range,\n satisfies: satisfies2,\n toComparators,\n maxSatisfying,\n minSatisfying,\n minVersion,\n validRange,\n outside,\n gtr,\n ltr,\n intersects,\n simplifyRange,\n subset,\n SemVer,\n re: internalRe.re,\n src: internalRe.src,\n tokens: internalRe.t,\n SEMVER_SPEC_VERSION: constants.SEMVER_SPEC_VERSION,\n RELEASE_TYPES: constants.RELEASE_TYPES,\n compareIdentifiers: identifiers.compareIdentifiers,\n rcompareIdentifiers: identifiers.rcompareIdentifiers\n };\n }\n});\n\n// apps/ecosystem-certifier/fixtures/positive/semver-entry.ts\nvar import_semver = __toESM(require_semver2(), 1);\nvar version = Host.v1.document.get(\"text/semver-case\");\nvar ranges = [\">=1.2.0 <2.0.0\", \"^1.2.0\", \"~1.2.3\"];\nvar semver_entry_default = {\n version,\n valid: (0, import_semver.valid)(version) !== null,\n checks: ranges.map((range) => ({ range, ok: (0, import_semver.satisfies)(version, range) }))\n};\nexport {\n semver_entry_default as default\n};\n", + "sourceMap": "{\"mappings\":\"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\",\"names\":[\"version\",\"version\",\"valid\",\"version\",\"version\",\"version\",\"version\",\"version\",\"version\",\"version\",\"satisfies\",\"version\",\"require_valid\",\"satisfies\",\"version\",\"version\",\"version\",\"satisfies\",\"version\",\"ranges\",\"satisfies\",\"require_semver\",\"valid\",\"satisfies\"],\"sources\":[\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/constants.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/debug.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/re.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/parse-options.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/identifiers.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/semver.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/parse.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/valid.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/clean.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/inc.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/diff.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/major.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/minor.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/patch.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/prerelease.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/rcompare.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare-loose.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare-build.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/sort.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/rsort.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/gt.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/lt.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/eq.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/neq.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/gte.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/lte.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/cmp.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/coerce.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/lrucache.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/range.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/comparator.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/satisfies.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/to-comparators.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/max-satisfying.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/min-satisfying.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/min-version.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/valid.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/outside.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/gtr.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/ltr.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/intersects.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/simplify.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/subset.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/index.js\",\"../apps/ecosystem-certifier/fixtures/positive/semver-entry.ts\"],\"sourcesContent\":[\"'use strict'\\n\\n// Note: this is the semver.org version of the spec that it implements\\n// Not necessarily the package version of this code.\\nconst SEMVER_SPEC_VERSION = '2.0.0'\\n\\nconst MAX_LENGTH = 256\\nconst MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER ||\\n/* istanbul ignore next */ 9007199254740991\\n\\n// Max safe segment length for coercion.\\nconst MAX_SAFE_COMPONENT_LENGTH = 16\\n\\n// Max safe length for a build identifier. The max length minus 6 characters for\\n// the shortest version with a build 0.0.0+BUILD.\\nconst MAX_SAFE_BUILD_LENGTH = MAX_LENGTH - 6\\n\\nconst RELEASE_TYPES = [\\n 'major',\\n 'premajor',\\n 'minor',\\n 'preminor',\\n 'patch',\\n 'prepatch',\\n 'prerelease',\\n]\\n\\nmodule.exports = {\\n MAX_LENGTH,\\n MAX_SAFE_COMPONENT_LENGTH,\\n MAX_SAFE_BUILD_LENGTH,\\n MAX_SAFE_INTEGER,\\n RELEASE_TYPES,\\n SEMVER_SPEC_VERSION,\\n FLAG_INCLUDE_PRERELEASE: 0b001,\\n FLAG_LOOSE: 0b010,\\n}\\n\",\"'use strict'\\n\\nconst debug = (\\n typeof process === 'object' &&\\n process.env &&\\n process.env.NODE_DEBUG &&\\n /\\\\bsemver\\\\b/i.test(process.env.NODE_DEBUG)\\n) ? (...args) => console.error('SEMVER', ...args)\\n : () => {}\\n\\nmodule.exports = debug\\n\",\"'use strict'\\n\\nconst {\\n MAX_SAFE_COMPONENT_LENGTH,\\n MAX_SAFE_BUILD_LENGTH,\\n MAX_LENGTH,\\n} = require('./constants')\\nconst debug = require('./debug')\\nexports = module.exports = {}\\n\\n// The actual regexps go on exports.re\\nconst re = exports.re = []\\nconst safeRe = exports.safeRe = []\\nconst src = exports.src = []\\nconst safeSrc = exports.safeSrc = []\\nconst t = exports.t = {}\\nlet R = 0\\n\\nconst LETTERDASHNUMBER = '[a-zA-Z0-9-]'\\n\\n// Replace some greedy regex tokens to prevent regex dos issues. These regex are\\n// used internally via the safeRe object since all inputs in this library get\\n// normalized first to trim and collapse all extra whitespace. The original\\n// regexes are exported for userland consumption and lower level usage. A\\n// future breaking change could export the safer regex only with a note that\\n// all input should have extra whitespace removed.\\nconst safeRegexReplacements = [\\n ['\\\\\\\\s', 1],\\n ['\\\\\\\\d', MAX_LENGTH],\\n [LETTERDASHNUMBER, MAX_SAFE_BUILD_LENGTH],\\n]\\n\\nconst makeSafeRegex = (value) => {\\n for (const [token, max] of safeRegexReplacements) {\\n value = value\\n .split(`${token}*`).join(`${token}{0,${max}}`)\\n .split(`${token}+`).join(`${token}{1,${max}}`)\\n }\\n return value\\n}\\n\\nconst createToken = (name, value, isGlobal) => {\\n const safe = makeSafeRegex(value)\\n const index = R++\\n debug(name, index, value)\\n t[name] = index\\n src[index] = value\\n safeSrc[index] = safe\\n re[index] = new RegExp(value, isGlobal ? 'g' : undefined)\\n safeRe[index] = new RegExp(safe, isGlobal ? 'g' : undefined)\\n}\\n\\n// The following Regular Expressions can be used for tokenizing,\\n// validating, and parsing SemVer version strings.\\n\\n// ## Numeric Identifier\\n// A single `0`, or a non-zero digit followed by zero or more digits.\\n\\ncreateToken('NUMERICIDENTIFIER', '0|[1-9]\\\\\\\\d*')\\ncreateToken('NUMERICIDENTIFIERLOOSE', '\\\\\\\\d+')\\n\\n// ## Non-numeric Identifier\\n// Zero or more digits, followed by a letter or hyphen, and then zero or\\n// more letters, digits, or hyphens.\\n\\ncreateToken('NONNUMERICIDENTIFIER', `\\\\\\\\d*[a-zA-Z-]${LETTERDASHNUMBER}*`)\\n\\n// ## Main Version\\n// Three dot-separated numeric identifiers.\\n\\ncreateToken('MAINVERSION', `(${src[t.NUMERICIDENTIFIER]})\\\\\\\\.` +\\n `(${src[t.NUMERICIDENTIFIER]})\\\\\\\\.` +\\n `(${src[t.NUMERICIDENTIFIER]})`)\\n\\ncreateToken('MAINVERSIONLOOSE', `(${src[t.NUMERICIDENTIFIERLOOSE]})\\\\\\\\.` +\\n `(${src[t.NUMERICIDENTIFIERLOOSE]})\\\\\\\\.` +\\n `(${src[t.NUMERICIDENTIFIERLOOSE]})`)\\n\\n// ## Pre-release Version Identifier\\n// A numeric identifier, or a non-numeric identifier.\\n// Non-numberic identifiers include numberic identifiers but can be longer.\\n// Therefore non-numberic identifiers must go first.\\n\\ncreateToken('PRERELEASEIDENTIFIER', `(?:${src[t.NONNUMERICIDENTIFIER]\\n}|${src[t.NUMERICIDENTIFIER]})`)\\n\\ncreateToken('PRERELEASEIDENTIFIERLOOSE', `(?:${src[t.NONNUMERICIDENTIFIER]\\n}|${src[t.NUMERICIDENTIFIERLOOSE]})`)\\n\\n// ## Pre-release Version\\n// Hyphen, followed by one or more dot-separated pre-release version\\n// identifiers.\\n\\ncreateToken('PRERELEASE', `(?:-(${src[t.PRERELEASEIDENTIFIER]\\n}(?:\\\\\\\\.${src[t.PRERELEASEIDENTIFIER]})*))`)\\n\\ncreateToken('PRERELEASELOOSE', `(?:-?(${src[t.PRERELEASEIDENTIFIERLOOSE]\\n}(?:\\\\\\\\.${src[t.PRERELEASEIDENTIFIERLOOSE]})*))`)\\n\\n// ## Build Metadata Identifier\\n// Any combination of digits, letters, or hyphens.\\n\\ncreateToken('BUILDIDENTIFIER', `${LETTERDASHNUMBER}+`)\\n\\n// ## Build Metadata\\n// Plus sign, followed by one or more period-separated build metadata\\n// identifiers.\\n\\ncreateToken('BUILD', `(?:\\\\\\\\+(${src[t.BUILDIDENTIFIER]\\n}(?:\\\\\\\\.${src[t.BUILDIDENTIFIER]})*))`)\\n\\n// ## Full Version String\\n// A main version, followed optionally by a pre-release version and\\n// build metadata.\\n\\n// Note that the only major, minor, patch, and pre-release sections of\\n// the version string are capturing groups. The build metadata is not a\\n// capturing group, because it should not ever be used in version\\n// comparison.\\n\\ncreateToken('FULLPLAIN', `v?${src[t.MAINVERSION]\\n}${src[t.PRERELEASE]}?${\\n src[t.BUILD]}?`)\\n\\ncreateToken('FULL', `^${src[t.FULLPLAIN]}$`)\\n\\n// like full, but allows v1.2.3 and =1.2.3, which people do sometimes.\\n// also, 1.0.0alpha1 (prerelease without the hyphen) which is pretty\\n// common in the npm registry.\\ncreateToken('LOOSEPLAIN', `[v=\\\\\\\\s]*${src[t.MAINVERSIONLOOSE]\\n}${src[t.PRERELEASELOOSE]}?${\\n src[t.BUILD]}?`)\\n\\ncreateToken('LOOSE', `^${src[t.LOOSEPLAIN]}$`)\\n\\ncreateToken('GTLT', '((?:<|>)?=?)')\\n\\n// Something like \\\"2.*\\\" or \\\"1.2.x\\\".\\n// Note that \\\"x.x\\\" is a valid xRange identifer, meaning \\\"any version\\\"\\n// Only the first item is strictly required.\\ncreateToken('XRANGEIDENTIFIERLOOSE', `${src[t.NUMERICIDENTIFIERLOOSE]}|x|X|\\\\\\\\*`)\\ncreateToken('XRANGEIDENTIFIER', `${src[t.NUMERICIDENTIFIER]}|x|X|\\\\\\\\*`)\\n\\ncreateToken('XRANGEPLAIN', `[v=\\\\\\\\s]*(${src[t.XRANGEIDENTIFIER]})` +\\n `(?:\\\\\\\\.(${src[t.XRANGEIDENTIFIER]})` +\\n `(?:\\\\\\\\.(${src[t.XRANGEIDENTIFIER]})` +\\n `(?:${src[t.PRERELEASE]})?${\\n src[t.BUILD]}?` +\\n `)?)?`)\\n\\ncreateToken('XRANGEPLAINLOOSE', `[v=\\\\\\\\s]*(${src[t.XRANGEIDENTIFIERLOOSE]})` +\\n `(?:\\\\\\\\.(${src[t.XRANGEIDENTIFIERLOOSE]})` +\\n `(?:\\\\\\\\.(${src[t.XRANGEIDENTIFIERLOOSE]})` +\\n `(?:${src[t.PRERELEASELOOSE]})?${\\n src[t.BUILD]}?` +\\n `)?)?`)\\n\\ncreateToken('XRANGE', `^${src[t.GTLT]}\\\\\\\\s*${src[t.XRANGEPLAIN]}$`)\\ncreateToken('XRANGELOOSE', `^${src[t.GTLT]}\\\\\\\\s*${src[t.XRANGEPLAINLOOSE]}$`)\\n\\n// Coercion.\\n// Extract anything that could conceivably be a part of a valid semver\\ncreateToken('COERCEPLAIN', `${'(^|[^\\\\\\\\d])' +\\n '(\\\\\\\\d{1,'}${MAX_SAFE_COMPONENT_LENGTH}})` +\\n `(?:\\\\\\\\.(\\\\\\\\d{1,${MAX_SAFE_COMPONENT_LENGTH}}))?` +\\n `(?:\\\\\\\\.(\\\\\\\\d{1,${MAX_SAFE_COMPONENT_LENGTH}}))?`)\\ncreateToken('COERCE', `${src[t.COERCEPLAIN]}(?:$|[^\\\\\\\\d])`)\\ncreateToken('COERCEFULL', src[t.COERCEPLAIN] +\\n `(?:${src[t.PRERELEASE]})?` +\\n `(?:${src[t.BUILD]})?` +\\n `(?:$|[^\\\\\\\\d])`)\\ncreateToken('COERCERTL', src[t.COERCE], true)\\ncreateToken('COERCERTLFULL', src[t.COERCEFULL], true)\\n\\n// Tilde ranges.\\n// Meaning is \\\"reasonably at or greater than\\\"\\ncreateToken('LONETILDE', '(?:~>?)')\\n\\ncreateToken('TILDETRIM', `(\\\\\\\\s*)${src[t.LONETILDE]}\\\\\\\\s+`, true)\\nexports.tildeTrimReplace = '$1~'\\n\\ncreateToken('TILDE', `^${src[t.LONETILDE]}${src[t.XRANGEPLAIN]}$`)\\ncreateToken('TILDELOOSE', `^${src[t.LONETILDE]}${src[t.XRANGEPLAINLOOSE]}$`)\\n\\n// Caret ranges.\\n// Meaning is \\\"at least and backwards compatible with\\\"\\ncreateToken('LONECARET', '(?:\\\\\\\\^)')\\n\\ncreateToken('CARETTRIM', `(\\\\\\\\s*)${src[t.LONECARET]}\\\\\\\\s+`, true)\\nexports.caretTrimReplace = '$1^'\\n\\ncreateToken('CARET', `^${src[t.LONECARET]}${src[t.XRANGEPLAIN]}$`)\\ncreateToken('CARETLOOSE', `^${src[t.LONECARET]}${src[t.XRANGEPLAINLOOSE]}$`)\\n\\n// A simple gt/lt/eq thing, or just \\\"\\\" to indicate \\\"any version\\\"\\ncreateToken('COMPARATORLOOSE', `^${src[t.GTLT]}\\\\\\\\s*(${src[t.LOOSEPLAIN]})$|^$`)\\ncreateToken('COMPARATOR', `^${src[t.GTLT]}\\\\\\\\s*(${src[t.FULLPLAIN]})$|^$`)\\n\\n// An expression to strip any whitespace between the gtlt and the thing\\n// it modifies, so that `> 1.2.3` ==> `>1.2.3`\\ncreateToken('COMPARATORTRIM', `(\\\\\\\\s*)${src[t.GTLT]\\n}\\\\\\\\s*(${src[t.LOOSEPLAIN]}|${src[t.XRANGEPLAIN]})`, true)\\nexports.comparatorTrimReplace = '$1$2$3'\\n\\n// Something like `1.2.3 - 1.2.4`\\n// Note that these all use the loose form, because they'll be\\n// checked against either the strict or loose comparator form\\n// later.\\ncreateToken('HYPHENRANGE', `^\\\\\\\\s*(${src[t.XRANGEPLAIN]})` +\\n `\\\\\\\\s+-\\\\\\\\s+` +\\n `(${src[t.XRANGEPLAIN]})` +\\n `\\\\\\\\s*$`)\\n\\ncreateToken('HYPHENRANGELOOSE', `^\\\\\\\\s*(${src[t.XRANGEPLAINLOOSE]})` +\\n `\\\\\\\\s+-\\\\\\\\s+` +\\n `(${src[t.XRANGEPLAINLOOSE]})` +\\n `\\\\\\\\s*$`)\\n\\n// Star ranges basically just allow anything at all.\\ncreateToken('STAR', '(<|>)?=?\\\\\\\\s*\\\\\\\\*')\\n// >=0.0.0 is like a star\\ncreateToken('GTE0', '^\\\\\\\\s*>=\\\\\\\\s*0\\\\\\\\.0\\\\\\\\.0\\\\\\\\s*$')\\ncreateToken('GTE0PRE', '^\\\\\\\\s*>=\\\\\\\\s*0\\\\\\\\.0\\\\\\\\.0-0\\\\\\\\s*$')\\n\",\"'use strict'\\n\\n// parse out just the options we care about\\nconst looseOption = Object.freeze({ loose: true })\\nconst emptyOpts = Object.freeze({ })\\nconst parseOptions = options => {\\n if (!options) {\\n return emptyOpts\\n }\\n\\n if (typeof options !== 'object') {\\n return looseOption\\n }\\n\\n return options\\n}\\nmodule.exports = parseOptions\\n\",\"'use strict'\\n\\nconst numeric = /^[0-9]+$/\\nconst compareIdentifiers = (a, b) => {\\n if (typeof a === 'number' && typeof b === 'number') {\\n return a === b ? 0 : a < b ? -1 : 1\\n }\\n\\n const anum = numeric.test(a)\\n const bnum = numeric.test(b)\\n\\n if (anum && bnum) {\\n a = +a\\n b = +b\\n }\\n\\n return a === b ? 0\\n : (anum && !bnum) ? -1\\n : (bnum && !anum) ? 1\\n : a < b ? -1\\n : 1\\n}\\n\\nconst rcompareIdentifiers = (a, b) => compareIdentifiers(b, a)\\n\\nmodule.exports = {\\n compareIdentifiers,\\n rcompareIdentifiers,\\n}\\n\",\"'use strict'\\n\\nconst debug = require('../internal/debug')\\nconst { MAX_LENGTH, MAX_SAFE_INTEGER } = require('../internal/constants')\\nconst { safeRe: re, t } = require('../internal/re')\\n\\nconst parseOptions = require('../internal/parse-options')\\nconst { compareIdentifiers } = require('../internal/identifiers')\\nclass SemVer {\\n constructor (version, options) {\\n options = parseOptions(options)\\n\\n if (version instanceof SemVer) {\\n if (version.loose === !!options.loose &&\\n version.includePrerelease === !!options.includePrerelease) {\\n return version\\n } else {\\n version = version.version\\n }\\n } else if (typeof version !== 'string') {\\n throw new TypeError(`Invalid version. Must be a string. Got type \\\"${typeof version}\\\".`)\\n }\\n\\n if (version.length > MAX_LENGTH) {\\n throw new TypeError(\\n `version is longer than ${MAX_LENGTH} characters`\\n )\\n }\\n\\n debug('SemVer', version, options)\\n this.options = options\\n this.loose = !!options.loose\\n // this isn't actually relevant for versions, but keep it so that we\\n // don't run into trouble passing this.options around.\\n this.includePrerelease = !!options.includePrerelease\\n\\n const m = version.trim().match(options.loose ? re[t.LOOSE] : re[t.FULL])\\n\\n if (!m) {\\n throw new TypeError(`Invalid Version: ${version}`)\\n }\\n\\n this.raw = version\\n\\n // these are actually numbers\\n this.major = +m[1]\\n this.minor = +m[2]\\n this.patch = +m[3]\\n\\n if (this.major > MAX_SAFE_INTEGER || this.major < 0) {\\n throw new TypeError('Invalid major version')\\n }\\n\\n if (this.minor > MAX_SAFE_INTEGER || this.minor < 0) {\\n throw new TypeError('Invalid minor version')\\n }\\n\\n if (this.patch > MAX_SAFE_INTEGER || this.patch < 0) {\\n throw new TypeError('Invalid patch version')\\n }\\n\\n // numberify any prerelease numeric ids\\n if (!m[4]) {\\n this.prerelease = []\\n } else {\\n this.prerelease = m[4].split('.').map((id) => {\\n if (/^[0-9]+$/.test(id)) {\\n const num = +id\\n if (num >= 0 && num < MAX_SAFE_INTEGER) {\\n return num\\n }\\n }\\n return id\\n })\\n }\\n\\n this.build = m[5] ? m[5].split('.') : []\\n this.format()\\n }\\n\\n format () {\\n this.version = `${this.major}.${this.minor}.${this.patch}`\\n if (this.prerelease.length) {\\n this.version += `-${this.prerelease.join('.')}`\\n }\\n return this.version\\n }\\n\\n toString () {\\n return this.version\\n }\\n\\n compare (other) {\\n debug('SemVer.compare', this.version, this.options, other)\\n if (!(other instanceof SemVer)) {\\n if (typeof other === 'string' && other === this.version) {\\n return 0\\n }\\n other = new SemVer(other, this.options)\\n }\\n\\n if (other.version === this.version) {\\n return 0\\n }\\n\\n return this.compareMain(other) || this.comparePre(other)\\n }\\n\\n compareMain (other) {\\n if (!(other instanceof SemVer)) {\\n other = new SemVer(other, this.options)\\n }\\n\\n if (this.major < other.major) {\\n return -1\\n }\\n if (this.major > other.major) {\\n return 1\\n }\\n if (this.minor < other.minor) {\\n return -1\\n }\\n if (this.minor > other.minor) {\\n return 1\\n }\\n if (this.patch < other.patch) {\\n return -1\\n }\\n if (this.patch > other.patch) {\\n return 1\\n }\\n return 0\\n }\\n\\n comparePre (other) {\\n if (!(other instanceof SemVer)) {\\n other = new SemVer(other, this.options)\\n }\\n\\n // NOT having a prerelease is > having one\\n if (this.prerelease.length && !other.prerelease.length) {\\n return -1\\n } else if (!this.prerelease.length && other.prerelease.length) {\\n return 1\\n } else if (!this.prerelease.length && !other.prerelease.length) {\\n return 0\\n }\\n\\n let i = 0\\n do {\\n const a = this.prerelease[i]\\n const b = other.prerelease[i]\\n debug('prerelease compare', i, a, b)\\n if (a === undefined && b === undefined) {\\n return 0\\n } else if (b === undefined) {\\n return 1\\n } else if (a === undefined) {\\n return -1\\n } else if (a === b) {\\n continue\\n } else {\\n return compareIdentifiers(a, b)\\n }\\n } while (++i)\\n }\\n\\n compareBuild (other) {\\n if (!(other instanceof SemVer)) {\\n other = new SemVer(other, this.options)\\n }\\n\\n let i = 0\\n do {\\n const a = this.build[i]\\n const b = other.build[i]\\n debug('build compare', i, a, b)\\n if (a === undefined && b === undefined) {\\n return 0\\n } else if (b === undefined) {\\n return 1\\n } else if (a === undefined) {\\n return -1\\n } else if (a === b) {\\n continue\\n } else {\\n return compareIdentifiers(a, b)\\n }\\n } while (++i)\\n }\\n\\n // preminor will bump the version up to the next minor release, and immediately\\n // down to pre-release. premajor and prepatch work the same way.\\n inc (release, identifier, identifierBase) {\\n if (release.startsWith('pre')) {\\n if (!identifier && identifierBase === false) {\\n throw new Error('invalid increment argument: identifier is empty')\\n }\\n // Avoid an invalid semver results\\n if (identifier) {\\n const match = `-${identifier}`.match(this.options.loose ? re[t.PRERELEASELOOSE] : re[t.PRERELEASE])\\n if (!match || match[1] !== identifier) {\\n throw new Error(`invalid identifier: ${identifier}`)\\n }\\n }\\n }\\n\\n switch (release) {\\n case 'premajor':\\n this.prerelease.length = 0\\n this.patch = 0\\n this.minor = 0\\n this.major++\\n this.inc('pre', identifier, identifierBase)\\n break\\n case 'preminor':\\n this.prerelease.length = 0\\n this.patch = 0\\n this.minor++\\n this.inc('pre', identifier, identifierBase)\\n break\\n case 'prepatch':\\n // If this is already a prerelease, it will bump to the next version\\n // drop any prereleases that might already exist, since they are not\\n // relevant at this point.\\n this.prerelease.length = 0\\n this.inc('patch', identifier, identifierBase)\\n this.inc('pre', identifier, identifierBase)\\n break\\n // If the input is a non-prerelease version, this acts the same as\\n // prepatch.\\n case 'prerelease':\\n if (this.prerelease.length === 0) {\\n this.inc('patch', identifier, identifierBase)\\n }\\n this.inc('pre', identifier, identifierBase)\\n break\\n case 'release':\\n if (this.prerelease.length === 0) {\\n throw new Error(`version ${this.raw} is not a prerelease`)\\n }\\n this.prerelease.length = 0\\n break\\n\\n case 'major':\\n // If this is a pre-major version, bump up to the same major version.\\n // Otherwise increment major.\\n // 1.0.0-5 bumps to 1.0.0\\n // 1.1.0 bumps to 2.0.0\\n if (\\n this.minor !== 0 ||\\n this.patch !== 0 ||\\n this.prerelease.length === 0\\n ) {\\n this.major++\\n }\\n this.minor = 0\\n this.patch = 0\\n this.prerelease = []\\n break\\n case 'minor':\\n // If this is a pre-minor version, bump up to the same minor version.\\n // Otherwise increment minor.\\n // 1.2.0-5 bumps to 1.2.0\\n // 1.2.1 bumps to 1.3.0\\n if (this.patch !== 0 || this.prerelease.length === 0) {\\n this.minor++\\n }\\n this.patch = 0\\n this.prerelease = []\\n break\\n case 'patch':\\n // If this is not a pre-release version, it will increment the patch.\\n // If it is a pre-release it will bump up to the same patch version.\\n // 1.2.0-5 patches to 1.2.0\\n // 1.2.0 patches to 1.2.1\\n if (this.prerelease.length === 0) {\\n this.patch++\\n }\\n this.prerelease = []\\n break\\n // This probably shouldn't be used publicly.\\n // 1.0.0 'pre' would become 1.0.0-0 which is the wrong direction.\\n case 'pre': {\\n const base = Number(identifierBase) ? 1 : 0\\n\\n if (this.prerelease.length === 0) {\\n this.prerelease = [base]\\n } else {\\n let i = this.prerelease.length\\n while (--i >= 0) {\\n if (typeof this.prerelease[i] === 'number') {\\n this.prerelease[i]++\\n i = -2\\n }\\n }\\n if (i === -1) {\\n // didn't increment anything\\n if (identifier === this.prerelease.join('.') && identifierBase === false) {\\n throw new Error('invalid increment argument: identifier already exists')\\n }\\n this.prerelease.push(base)\\n }\\n }\\n if (identifier) {\\n // 1.2.0-beta.1 bumps to 1.2.0-beta.2,\\n // 1.2.0-beta.fooblz or 1.2.0-beta bumps to 1.2.0-beta.0\\n let prerelease = [identifier, base]\\n if (identifierBase === false) {\\n prerelease = [identifier]\\n }\\n if (compareIdentifiers(this.prerelease[0], identifier) === 0) {\\n if (isNaN(this.prerelease[1])) {\\n this.prerelease = prerelease\\n }\\n } else {\\n this.prerelease = prerelease\\n }\\n }\\n break\\n }\\n default:\\n throw new Error(`invalid increment argument: ${release}`)\\n }\\n this.raw = this.format()\\n if (this.build.length) {\\n this.raw += `+${this.build.join('.')}`\\n }\\n return this\\n }\\n}\\n\\nmodule.exports = SemVer\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst parse = (version, options, throwErrors = false) => {\\n if (version instanceof SemVer) {\\n return version\\n }\\n try {\\n return new SemVer(version, options)\\n } catch (er) {\\n if (!throwErrors) {\\n return null\\n }\\n throw er\\n }\\n}\\n\\nmodule.exports = parse\\n\",\"'use strict'\\n\\nconst parse = require('./parse')\\nconst valid = (version, options) => {\\n const v = parse(version, options)\\n return v ? v.version : null\\n}\\nmodule.exports = valid\\n\",\"'use strict'\\n\\nconst parse = require('./parse')\\nconst clean = (version, options) => {\\n const s = parse(version.trim().replace(/^[=v]+/, ''), options)\\n return s ? s.version : null\\n}\\nmodule.exports = clean\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\n\\nconst inc = (version, release, options, identifier, identifierBase) => {\\n if (typeof (options) === 'string') {\\n identifierBase = identifier\\n identifier = options\\n options = undefined\\n }\\n\\n try {\\n return new SemVer(\\n version instanceof SemVer ? version.version : version,\\n options\\n ).inc(release, identifier, identifierBase).version\\n } catch (er) {\\n return null\\n }\\n}\\nmodule.exports = inc\\n\",\"'use strict'\\n\\nconst parse = require('./parse.js')\\n\\nconst diff = (version1, version2) => {\\n const v1 = parse(version1, null, true)\\n const v2 = parse(version2, null, true)\\n const comparison = v1.compare(v2)\\n\\n if (comparison === 0) {\\n return null\\n }\\n\\n const v1Higher = comparison > 0\\n const highVersion = v1Higher ? v1 : v2\\n const lowVersion = v1Higher ? v2 : v1\\n const highHasPre = !!highVersion.prerelease.length\\n const lowHasPre = !!lowVersion.prerelease.length\\n\\n if (lowHasPre && !highHasPre) {\\n // Going from prerelease -> no prerelease requires some special casing\\n\\n // If the low version has only a major, then it will always be a major\\n // Some examples:\\n // 1.0.0-1 -> 1.0.0\\n // 1.0.0-1 -> 1.1.1\\n // 1.0.0-1 -> 2.0.0\\n if (!lowVersion.patch && !lowVersion.minor) {\\n return 'major'\\n }\\n\\n // If the main part has no difference\\n if (lowVersion.compareMain(highVersion) === 0) {\\n if (lowVersion.minor && !lowVersion.patch) {\\n return 'minor'\\n }\\n return 'patch'\\n }\\n }\\n\\n // add the `pre` prefix if we are going to a prerelease version\\n const prefix = highHasPre ? 'pre' : ''\\n\\n if (v1.major !== v2.major) {\\n return prefix + 'major'\\n }\\n\\n if (v1.minor !== v2.minor) {\\n return prefix + 'minor'\\n }\\n\\n if (v1.patch !== v2.patch) {\\n return prefix + 'patch'\\n }\\n\\n // high and low are preleases\\n return 'prerelease'\\n}\\n\\nmodule.exports = diff\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst major = (a, loose) => new SemVer(a, loose).major\\nmodule.exports = major\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst minor = (a, loose) => new SemVer(a, loose).minor\\nmodule.exports = minor\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst patch = (a, loose) => new SemVer(a, loose).patch\\nmodule.exports = patch\\n\",\"'use strict'\\n\\nconst parse = require('./parse')\\nconst prerelease = (version, options) => {\\n const parsed = parse(version, options)\\n return (parsed && parsed.prerelease.length) ? parsed.prerelease : null\\n}\\nmodule.exports = prerelease\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst compare = (a, b, loose) =>\\n new SemVer(a, loose).compare(new SemVer(b, loose))\\n\\nmodule.exports = compare\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst rcompare = (a, b, loose) => compare(b, a, loose)\\nmodule.exports = rcompare\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst compareLoose = (a, b) => compare(a, b, true)\\nmodule.exports = compareLoose\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst compareBuild = (a, b, loose) => {\\n const versionA = new SemVer(a, loose)\\n const versionB = new SemVer(b, loose)\\n return versionA.compare(versionB) || versionA.compareBuild(versionB)\\n}\\nmodule.exports = compareBuild\\n\",\"'use strict'\\n\\nconst compareBuild = require('./compare-build')\\nconst sort = (list, loose) => list.sort((a, b) => compareBuild(a, b, loose))\\nmodule.exports = sort\\n\",\"'use strict'\\n\\nconst compareBuild = require('./compare-build')\\nconst rsort = (list, loose) => list.sort((a, b) => compareBuild(b, a, loose))\\nmodule.exports = rsort\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst gt = (a, b, loose) => compare(a, b, loose) > 0\\nmodule.exports = gt\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst lt = (a, b, loose) => compare(a, b, loose) < 0\\nmodule.exports = lt\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst eq = (a, b, loose) => compare(a, b, loose) === 0\\nmodule.exports = eq\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst neq = (a, b, loose) => compare(a, b, loose) !== 0\\nmodule.exports = neq\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst gte = (a, b, loose) => compare(a, b, loose) >= 0\\nmodule.exports = gte\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst lte = (a, b, loose) => compare(a, b, loose) <= 0\\nmodule.exports = lte\\n\",\"'use strict'\\n\\nconst eq = require('./eq')\\nconst neq = require('./neq')\\nconst gt = require('./gt')\\nconst gte = require('./gte')\\nconst lt = require('./lt')\\nconst lte = require('./lte')\\n\\nconst cmp = (a, op, b, loose) => {\\n switch (op) {\\n case '===':\\n if (typeof a === 'object') {\\n a = a.version\\n }\\n if (typeof b === 'object') {\\n b = b.version\\n }\\n return a === b\\n\\n case '!==':\\n if (typeof a === 'object') {\\n a = a.version\\n }\\n if (typeof b === 'object') {\\n b = b.version\\n }\\n return a !== b\\n\\n case '':\\n case '=':\\n case '==':\\n return eq(a, b, loose)\\n\\n case '!=':\\n return neq(a, b, loose)\\n\\n case '>':\\n return gt(a, b, loose)\\n\\n case '>=':\\n return gte(a, b, loose)\\n\\n case '<':\\n return lt(a, b, loose)\\n\\n case '<=':\\n return lte(a, b, loose)\\n\\n default:\\n throw new TypeError(`Invalid operator: ${op}`)\\n }\\n}\\nmodule.exports = cmp\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst parse = require('./parse')\\nconst { safeRe: re, t } = require('../internal/re')\\n\\nconst coerce = (version, options) => {\\n if (version instanceof SemVer) {\\n return version\\n }\\n\\n if (typeof version === 'number') {\\n version = String(version)\\n }\\n\\n if (typeof version !== 'string') {\\n return null\\n }\\n\\n options = options || {}\\n\\n let match = null\\n if (!options.rtl) {\\n match = version.match(options.includePrerelease ? re[t.COERCEFULL] : re[t.COERCE])\\n } else {\\n // Find the right-most coercible string that does not share\\n // a terminus with a more left-ward coercible string.\\n // Eg, '1.2.3.4' wants to coerce '2.3.4', not '3.4' or '4'\\n // With includePrerelease option set, '1.2.3.4-rc' wants to coerce '2.3.4-rc', not '2.3.4'\\n //\\n // Walk through the string checking with a /g regexp\\n // Manually set the index so as to pick up overlapping matches.\\n // Stop when we get a match that ends at the string end, since no\\n // coercible string can be more right-ward without the same terminus.\\n const coerceRtlRegex = options.includePrerelease ? re[t.COERCERTLFULL] : re[t.COERCERTL]\\n let next\\n while ((next = coerceRtlRegex.exec(version)) &&\\n (!match || match.index + match[0].length !== version.length)\\n ) {\\n if (!match ||\\n next.index + next[0].length !== match.index + match[0].length) {\\n match = next\\n }\\n coerceRtlRegex.lastIndex = next.index + next[1].length + next[2].length\\n }\\n // leave it in a clean state\\n coerceRtlRegex.lastIndex = -1\\n }\\n\\n if (match === null) {\\n return null\\n }\\n\\n const major = match[2]\\n const minor = match[3] || '0'\\n const patch = match[4] || '0'\\n const prerelease = options.includePrerelease && match[5] ? `-${match[5]}` : ''\\n const build = options.includePrerelease && match[6] ? `+${match[6]}` : ''\\n\\n return parse(`${major}.${minor}.${patch}${prerelease}${build}`, options)\\n}\\nmodule.exports = coerce\\n\",\"'use strict'\\n\\nclass LRUCache {\\n constructor () {\\n this.max = 1000\\n this.map = new Map()\\n }\\n\\n get (key) {\\n const value = this.map.get(key)\\n if (value === undefined) {\\n return undefined\\n } else {\\n // Remove the key from the map and add it to the end\\n this.map.delete(key)\\n this.map.set(key, value)\\n return value\\n }\\n }\\n\\n delete (key) {\\n return this.map.delete(key)\\n }\\n\\n set (key, value) {\\n const deleted = this.delete(key)\\n\\n if (!deleted && value !== undefined) {\\n // If cache is full, delete the least recently used item\\n if (this.map.size >= this.max) {\\n const firstKey = this.map.keys().next().value\\n this.delete(firstKey)\\n }\\n\\n this.map.set(key, value)\\n }\\n\\n return this\\n }\\n}\\n\\nmodule.exports = LRUCache\\n\",\"'use strict'\\n\\nconst SPACE_CHARACTERS = /\\\\s+/g\\n\\n// hoisted class for cyclic dependency\\nclass Range {\\n constructor (range, options) {\\n options = parseOptions(options)\\n\\n if (range instanceof Range) {\\n if (\\n range.loose === !!options.loose &&\\n range.includePrerelease === !!options.includePrerelease\\n ) {\\n return range\\n } else {\\n return new Range(range.raw, options)\\n }\\n }\\n\\n if (range instanceof Comparator) {\\n // just put it in the set and return\\n this.raw = range.value\\n this.set = [[range]]\\n this.formatted = undefined\\n return this\\n }\\n\\n this.options = options\\n this.loose = !!options.loose\\n this.includePrerelease = !!options.includePrerelease\\n\\n // First reduce all whitespace as much as possible so we do not have to rely\\n // on potentially slow regexes like \\\\s*. This is then stored and used for\\n // future error messages as well.\\n this.raw = range.trim().replace(SPACE_CHARACTERS, ' ')\\n\\n // First, split on ||\\n this.set = this.raw\\n .split('||')\\n // map the range to a 2d array of comparators\\n .map(r => this.parseRange(r.trim()))\\n // throw out any comparator lists that are empty\\n // this generally means that it was not a valid range, which is allowed\\n // in loose mode, but will still throw if the WHOLE range is invalid.\\n .filter(c => c.length)\\n\\n if (!this.set.length) {\\n throw new TypeError(`Invalid SemVer Range: ${this.raw}`)\\n }\\n\\n // if we have any that are not the null set, throw out null sets.\\n if (this.set.length > 1) {\\n // keep the first one, in case they're all null sets\\n const first = this.set[0]\\n this.set = this.set.filter(c => !isNullSet(c[0]))\\n if (this.set.length === 0) {\\n this.set = [first]\\n } else if (this.set.length > 1) {\\n // if we have any that are *, then the range is just *\\n for (const c of this.set) {\\n if (c.length === 1 && isAny(c[0])) {\\n this.set = [c]\\n break\\n }\\n }\\n }\\n }\\n\\n this.formatted = undefined\\n }\\n\\n get range () {\\n if (this.formatted === undefined) {\\n this.formatted = ''\\n for (let i = 0; i < this.set.length; i++) {\\n if (i > 0) {\\n this.formatted += '||'\\n }\\n const comps = this.set[i]\\n for (let k = 0; k < comps.length; k++) {\\n if (k > 0) {\\n this.formatted += ' '\\n }\\n this.formatted += comps[k].toString().trim()\\n }\\n }\\n }\\n return this.formatted\\n }\\n\\n format () {\\n return this.range\\n }\\n\\n toString () {\\n return this.range\\n }\\n\\n parseRange (range) {\\n // memoize range parsing for performance.\\n // this is a very hot path, and fully deterministic.\\n const memoOpts =\\n (this.options.includePrerelease && FLAG_INCLUDE_PRERELEASE) |\\n (this.options.loose && FLAG_LOOSE)\\n const memoKey = memoOpts + ':' + range\\n const cached = cache.get(memoKey)\\n if (cached) {\\n return cached\\n }\\n\\n const loose = this.options.loose\\n // `1.2.3 - 1.2.4` => `>=1.2.3 <=1.2.4`\\n const hr = loose ? re[t.HYPHENRANGELOOSE] : re[t.HYPHENRANGE]\\n range = range.replace(hr, hyphenReplace(this.options.includePrerelease))\\n debug('hyphen replace', range)\\n\\n // `> 1.2.3 < 1.2.5` => `>1.2.3 <1.2.5`\\n range = range.replace(re[t.COMPARATORTRIM], comparatorTrimReplace)\\n debug('comparator trim', range)\\n\\n // `~ 1.2.3` => `~1.2.3`\\n range = range.replace(re[t.TILDETRIM], tildeTrimReplace)\\n debug('tilde trim', range)\\n\\n // `^ 1.2.3` => `^1.2.3`\\n range = range.replace(re[t.CARETTRIM], caretTrimReplace)\\n debug('caret trim', range)\\n\\n // At this point, the range is completely trimmed and\\n // ready to be split into comparators.\\n\\n let rangeList = range\\n .split(' ')\\n .map(comp => parseComparator(comp, this.options))\\n .join(' ')\\n .split(/\\\\s+/)\\n // >=0.0.0 is equivalent to *\\n .map(comp => replaceGTE0(comp, this.options))\\n\\n if (loose) {\\n // in loose mode, throw out any that are not valid comparators\\n rangeList = rangeList.filter(comp => {\\n debug('loose invalid filter', comp, this.options)\\n return !!comp.match(re[t.COMPARATORLOOSE])\\n })\\n }\\n debug('range list', rangeList)\\n\\n // if any comparators are the null set, then replace with JUST null set\\n // if more than one comparator, remove any * comparators\\n // also, don't include the same comparator more than once\\n const rangeMap = new Map()\\n const comparators = rangeList.map(comp => new Comparator(comp, this.options))\\n for (const comp of comparators) {\\n if (isNullSet(comp)) {\\n return [comp]\\n }\\n rangeMap.set(comp.value, comp)\\n }\\n if (rangeMap.size > 1 && rangeMap.has('')) {\\n rangeMap.delete('')\\n }\\n\\n const result = [...rangeMap.values()]\\n cache.set(memoKey, result)\\n return result\\n }\\n\\n intersects (range, options) {\\n if (!(range instanceof Range)) {\\n throw new TypeError('a Range is required')\\n }\\n\\n return this.set.some((thisComparators) => {\\n return (\\n isSatisfiable(thisComparators, options) &&\\n range.set.some((rangeComparators) => {\\n return (\\n isSatisfiable(rangeComparators, options) &&\\n thisComparators.every((thisComparator) => {\\n return rangeComparators.every((rangeComparator) => {\\n return thisComparator.intersects(rangeComparator, options)\\n })\\n })\\n )\\n })\\n )\\n })\\n }\\n\\n // if ANY of the sets match ALL of its comparators, then pass\\n test (version) {\\n if (!version) {\\n return false\\n }\\n\\n if (typeof version === 'string') {\\n try {\\n version = new SemVer(version, this.options)\\n } catch (er) {\\n return false\\n }\\n }\\n\\n for (let i = 0; i < this.set.length; i++) {\\n if (testSet(this.set[i], version, this.options)) {\\n return true\\n }\\n }\\n return false\\n }\\n}\\n\\nmodule.exports = Range\\n\\nconst LRU = require('../internal/lrucache')\\nconst cache = new LRU()\\n\\nconst parseOptions = require('../internal/parse-options')\\nconst Comparator = require('./comparator')\\nconst debug = require('../internal/debug')\\nconst SemVer = require('./semver')\\nconst {\\n safeRe: re,\\n t,\\n comparatorTrimReplace,\\n tildeTrimReplace,\\n caretTrimReplace,\\n} = require('../internal/re')\\nconst { FLAG_INCLUDE_PRERELEASE, FLAG_LOOSE } = require('../internal/constants')\\n\\nconst isNullSet = c => c.value === '<0.0.0-0'\\nconst isAny = c => c.value === ''\\n\\n// take a set of comparators and determine whether there\\n// exists a version which can satisfy it\\nconst isSatisfiable = (comparators, options) => {\\n let result = true\\n const remainingComparators = comparators.slice()\\n let testComparator = remainingComparators.pop()\\n\\n while (result && remainingComparators.length) {\\n result = remainingComparators.every((otherComparator) => {\\n return testComparator.intersects(otherComparator, options)\\n })\\n\\n testComparator = remainingComparators.pop()\\n }\\n\\n return result\\n}\\n\\n// comprised of xranges, tildes, stars, and gtlt's at this point.\\n// already replaced the hyphen ranges\\n// turn into a set of JUST comparators.\\nconst parseComparator = (comp, options) => {\\n comp = comp.replace(re[t.BUILD], '')\\n debug('comp', comp, options)\\n comp = replaceCarets(comp, options)\\n debug('caret', comp)\\n comp = replaceTildes(comp, options)\\n debug('tildes', comp)\\n comp = replaceXRanges(comp, options)\\n debug('xrange', comp)\\n comp = replaceStars(comp, options)\\n debug('stars', comp)\\n return comp\\n}\\n\\nconst isX = id => !id || id.toLowerCase() === 'x' || id === '*'\\n\\n// ~, ~> --> * (any, kinda silly)\\n// ~2, ~2.x, ~2.x.x, ~>2, ~>2.x ~>2.x.x --> >=2.0.0 <3.0.0-0\\n// ~2.0, ~2.0.x, ~>2.0, ~>2.0.x --> >=2.0.0 <2.1.0-0\\n// ~1.2, ~1.2.x, ~>1.2, ~>1.2.x --> >=1.2.0 <1.3.0-0\\n// ~1.2.3, ~>1.2.3 --> >=1.2.3 <1.3.0-0\\n// ~1.2.0, ~>1.2.0 --> >=1.2.0 <1.3.0-0\\n// ~0.0.1 --> >=0.0.1 <0.1.0-0\\nconst replaceTildes = (comp, options) => {\\n return comp\\n .trim()\\n .split(/\\\\s+/)\\n .map((c) => replaceTilde(c, options))\\n .join(' ')\\n}\\n\\nconst replaceTilde = (comp, options) => {\\n const r = options.loose ? re[t.TILDELOOSE] : re[t.TILDE]\\n return comp.replace(r, (_, M, m, p, pr) => {\\n debug('tilde', comp, _, M, m, p, pr)\\n let ret\\n\\n if (isX(M)) {\\n ret = ''\\n } else if (isX(m)) {\\n ret = `>=${M}.0.0 <${+M + 1}.0.0-0`\\n } else if (isX(p)) {\\n // ~1.2 == >=1.2.0 <1.3.0-0\\n ret = `>=${M}.${m}.0 <${M}.${+m + 1}.0-0`\\n } else if (pr) {\\n debug('replaceTilde pr', pr)\\n ret = `>=${M}.${m}.${p}-${pr\\n } <${M}.${+m + 1}.0-0`\\n } else {\\n // ~1.2.3 == >=1.2.3 <1.3.0-0\\n ret = `>=${M}.${m}.${p\\n } <${M}.${+m + 1}.0-0`\\n }\\n\\n debug('tilde return', ret)\\n return ret\\n })\\n}\\n\\n// ^ --> * (any, kinda silly)\\n// ^2, ^2.x, ^2.x.x --> >=2.0.0 <3.0.0-0\\n// ^2.0, ^2.0.x --> >=2.0.0 <3.0.0-0\\n// ^1.2, ^1.2.x --> >=1.2.0 <2.0.0-0\\n// ^1.2.3 --> >=1.2.3 <2.0.0-0\\n// ^1.2.0 --> >=1.2.0 <2.0.0-0\\n// ^0.0.1 --> >=0.0.1 <0.0.2-0\\n// ^0.1.0 --> >=0.1.0 <0.2.0-0\\nconst replaceCarets = (comp, options) => {\\n return comp\\n .trim()\\n .split(/\\\\s+/)\\n .map((c) => replaceCaret(c, options))\\n .join(' ')\\n}\\n\\nconst replaceCaret = (comp, options) => {\\n debug('caret', comp, options)\\n const r = options.loose ? re[t.CARETLOOSE] : re[t.CARET]\\n const z = options.includePrerelease ? '-0' : ''\\n return comp.replace(r, (_, M, m, p, pr) => {\\n debug('caret', comp, _, M, m, p, pr)\\n let ret\\n\\n if (isX(M)) {\\n ret = ''\\n } else if (isX(m)) {\\n ret = `>=${M}.0.0${z} <${+M + 1}.0.0-0`\\n } else if (isX(p)) {\\n if (M === '0') {\\n ret = `>=${M}.${m}.0${z} <${M}.${+m + 1}.0-0`\\n } else {\\n ret = `>=${M}.${m}.0${z} <${+M + 1}.0.0-0`\\n }\\n } else if (pr) {\\n debug('replaceCaret pr', pr)\\n if (M === '0') {\\n if (m === '0') {\\n ret = `>=${M}.${m}.${p}-${pr\\n } <${M}.${m}.${+p + 1}-0`\\n } else {\\n ret = `>=${M}.${m}.${p}-${pr\\n } <${M}.${+m + 1}.0-0`\\n }\\n } else {\\n ret = `>=${M}.${m}.${p}-${pr\\n } <${+M + 1}.0.0-0`\\n }\\n } else {\\n debug('no pr')\\n if (M === '0') {\\n if (m === '0') {\\n ret = `>=${M}.${m}.${p\\n }${z} <${M}.${m}.${+p + 1}-0`\\n } else {\\n ret = `>=${M}.${m}.${p\\n }${z} <${M}.${+m + 1}.0-0`\\n }\\n } else {\\n ret = `>=${M}.${m}.${p\\n } <${+M + 1}.0.0-0`\\n }\\n }\\n\\n debug('caret return', ret)\\n return ret\\n })\\n}\\n\\nconst replaceXRanges = (comp, options) => {\\n debug('replaceXRanges', comp, options)\\n return comp\\n .split(/\\\\s+/)\\n .map((c) => replaceXRange(c, options))\\n .join(' ')\\n}\\n\\nconst replaceXRange = (comp, options) => {\\n comp = comp.trim()\\n const r = options.loose ? re[t.XRANGELOOSE] : re[t.XRANGE]\\n return comp.replace(r, (ret, gtlt, M, m, p, pr) => {\\n debug('xRange', comp, ret, gtlt, M, m, p, pr)\\n const xM = isX(M)\\n const xm = xM || isX(m)\\n const xp = xm || isX(p)\\n const anyX = xp\\n\\n if (gtlt === '=' && anyX) {\\n gtlt = ''\\n }\\n\\n // if we're including prereleases in the match, then we need\\n // to fix this to -0, the lowest possible prerelease value\\n pr = options.includePrerelease ? '-0' : ''\\n\\n if (xM) {\\n if (gtlt === '>' || gtlt === '<') {\\n // nothing is allowed\\n ret = '<0.0.0-0'\\n } else {\\n // nothing is forbidden\\n ret = '*'\\n }\\n } else if (gtlt && anyX) {\\n // we know patch is an x, because we have any x at all.\\n // replace X with 0\\n if (xm) {\\n m = 0\\n }\\n p = 0\\n\\n if (gtlt === '>') {\\n // >1 => >=2.0.0\\n // >1.2 => >=1.3.0\\n gtlt = '>='\\n if (xm) {\\n M = +M + 1\\n m = 0\\n p = 0\\n } else {\\n m = +m + 1\\n p = 0\\n }\\n } else if (gtlt === '<=') {\\n // <=0.7.x is actually <0.8.0, since any 0.7.x should\\n // pass. Similarly, <=7.x is actually <8.0.0, etc.\\n gtlt = '<'\\n if (xm) {\\n M = +M + 1\\n } else {\\n m = +m + 1\\n }\\n }\\n\\n if (gtlt === '<') {\\n pr = '-0'\\n }\\n\\n ret = `${gtlt + M}.${m}.${p}${pr}`\\n } else if (xm) {\\n ret = `>=${M}.0.0${pr} <${+M + 1}.0.0-0`\\n } else if (xp) {\\n ret = `>=${M}.${m}.0${pr\\n } <${M}.${+m + 1}.0-0`\\n }\\n\\n debug('xRange return', ret)\\n\\n return ret\\n })\\n}\\n\\n// Because * is AND-ed with everything else in the comparator,\\n// and '' means \\\"any version\\\", just remove the *s entirely.\\nconst replaceStars = (comp, options) => {\\n debug('replaceStars', comp, options)\\n // Looseness is ignored here. star is always as loose as it gets!\\n return comp\\n .trim()\\n .replace(re[t.STAR], '')\\n}\\n\\nconst replaceGTE0 = (comp, options) => {\\n debug('replaceGTE0', comp, options)\\n return comp\\n .trim()\\n .replace(re[options.includePrerelease ? t.GTE0PRE : t.GTE0], '')\\n}\\n\\n// This function is passed to string.replace(re[t.HYPHENRANGE])\\n// M, m, patch, prerelease, build\\n// 1.2 - 3.4.5 => >=1.2.0 <=3.4.5\\n// 1.2.3 - 3.4 => >=1.2.0 <3.5.0-0 Any 3.4.x will do\\n// 1.2 - 3.4 => >=1.2.0 <3.5.0-0\\n// TODO build?\\nconst hyphenReplace = incPr => ($0,\\n from, fM, fm, fp, fpr, fb,\\n to, tM, tm, tp, tpr) => {\\n if (isX(fM)) {\\n from = ''\\n } else if (isX(fm)) {\\n from = `>=${fM}.0.0${incPr ? '-0' : ''}`\\n } else if (isX(fp)) {\\n from = `>=${fM}.${fm}.0${incPr ? '-0' : ''}`\\n } else if (fpr) {\\n from = `>=${from}`\\n } else {\\n from = `>=${from}${incPr ? '-0' : ''}`\\n }\\n\\n if (isX(tM)) {\\n to = ''\\n } else if (isX(tm)) {\\n to = `<${+tM + 1}.0.0-0`\\n } else if (isX(tp)) {\\n to = `<${tM}.${+tm + 1}.0-0`\\n } else if (tpr) {\\n to = `<=${tM}.${tm}.${tp}-${tpr}`\\n } else if (incPr) {\\n to = `<${tM}.${tm}.${+tp + 1}-0`\\n } else {\\n to = `<=${to}`\\n }\\n\\n return `${from} ${to}`.trim()\\n}\\n\\nconst testSet = (set, version, options) => {\\n for (let i = 0; i < set.length; i++) {\\n if (!set[i].test(version)) {\\n return false\\n }\\n }\\n\\n if (version.prerelease.length && !options.includePrerelease) {\\n // Find the set of versions that are allowed to have prereleases\\n // For example, ^1.2.3-pr.1 desugars to >=1.2.3-pr.1 <2.0.0\\n // That should allow `1.2.3-pr.2` to pass.\\n // However, `1.2.4-alpha.notready` should NOT be allowed,\\n // even though it's within the range set by the comparators.\\n for (let i = 0; i < set.length; i++) {\\n debug(set[i].semver)\\n if (set[i].semver === Comparator.ANY) {\\n continue\\n }\\n\\n if (set[i].semver.prerelease.length > 0) {\\n const allowed = set[i].semver\\n if (allowed.major === version.major &&\\n allowed.minor === version.minor &&\\n allowed.patch === version.patch) {\\n return true\\n }\\n }\\n }\\n\\n // Version has a -pre, but it's not one of the ones we like.\\n return false\\n }\\n\\n return true\\n}\\n\",\"'use strict'\\n\\nconst ANY = Symbol('SemVer ANY')\\n// hoisted class for cyclic dependency\\nclass Comparator {\\n static get ANY () {\\n return ANY\\n }\\n\\n constructor (comp, options) {\\n options = parseOptions(options)\\n\\n if (comp instanceof Comparator) {\\n if (comp.loose === !!options.loose) {\\n return comp\\n } else {\\n comp = comp.value\\n }\\n }\\n\\n comp = comp.trim().split(/\\\\s+/).join(' ')\\n debug('comparator', comp, options)\\n this.options = options\\n this.loose = !!options.loose\\n this.parse(comp)\\n\\n if (this.semver === ANY) {\\n this.value = ''\\n } else {\\n this.value = this.operator + this.semver.version\\n }\\n\\n debug('comp', this)\\n }\\n\\n parse (comp) {\\n const r = this.options.loose ? re[t.COMPARATORLOOSE] : re[t.COMPARATOR]\\n const m = comp.match(r)\\n\\n if (!m) {\\n throw new TypeError(`Invalid comparator: ${comp}`)\\n }\\n\\n this.operator = m[1] !== undefined ? m[1] : ''\\n if (this.operator === '=') {\\n this.operator = ''\\n }\\n\\n // if it literally is just '>' or '' then allow anything.\\n if (!m[2]) {\\n this.semver = ANY\\n } else {\\n this.semver = new SemVer(m[2], this.options.loose)\\n }\\n }\\n\\n toString () {\\n return this.value\\n }\\n\\n test (version) {\\n debug('Comparator.test', version, this.options.loose)\\n\\n if (this.semver === ANY || version === ANY) {\\n return true\\n }\\n\\n if (typeof version === 'string') {\\n try {\\n version = new SemVer(version, this.options)\\n } catch (er) {\\n return false\\n }\\n }\\n\\n return cmp(version, this.operator, this.semver, this.options)\\n }\\n\\n intersects (comp, options) {\\n if (!(comp instanceof Comparator)) {\\n throw new TypeError('a Comparator is required')\\n }\\n\\n if (this.operator === '') {\\n if (this.value === '') {\\n return true\\n }\\n return new Range(comp.value, options).test(this.value)\\n } else if (comp.operator === '') {\\n if (comp.value === '') {\\n return true\\n }\\n return new Range(this.value, options).test(comp.semver)\\n }\\n\\n options = parseOptions(options)\\n\\n // Special cases where nothing can possibly be lower\\n if (options.includePrerelease &&\\n (this.value === '<0.0.0-0' || comp.value === '<0.0.0-0')) {\\n return false\\n }\\n if (!options.includePrerelease &&\\n (this.value.startsWith('<0.0.0') || comp.value.startsWith('<0.0.0'))) {\\n return false\\n }\\n\\n // Same direction increasing (> or >=)\\n if (this.operator.startsWith('>') && comp.operator.startsWith('>')) {\\n return true\\n }\\n // Same direction decreasing (< or <=)\\n if (this.operator.startsWith('<') && comp.operator.startsWith('<')) {\\n return true\\n }\\n // same SemVer and both sides are inclusive (<= or >=)\\n if (\\n (this.semver.version === comp.semver.version) &&\\n this.operator.includes('=') && comp.operator.includes('=')) {\\n return true\\n }\\n // opposite directions less than\\n if (cmp(this.semver, '<', comp.semver, options) &&\\n this.operator.startsWith('>') && comp.operator.startsWith('<')) {\\n return true\\n }\\n // opposite directions greater than\\n if (cmp(this.semver, '>', comp.semver, options) &&\\n this.operator.startsWith('<') && comp.operator.startsWith('>')) {\\n return true\\n }\\n return false\\n }\\n}\\n\\nmodule.exports = Comparator\\n\\nconst parseOptions = require('../internal/parse-options')\\nconst { safeRe: re, t } = require('../internal/re')\\nconst cmp = require('../functions/cmp')\\nconst debug = require('../internal/debug')\\nconst SemVer = require('./semver')\\nconst Range = require('./range')\\n\",\"'use strict'\\n\\nconst Range = require('../classes/range')\\nconst satisfies = (version, range, options) => {\\n try {\\n range = new Range(range, options)\\n } catch (er) {\\n return false\\n }\\n return range.test(version)\\n}\\nmodule.exports = satisfies\\n\",\"'use strict'\\n\\nconst Range = require('../classes/range')\\n\\n// Mostly just for testing and legacy API reasons\\nconst toComparators = (range, options) =>\\n new Range(range, options).set\\n .map(comp => comp.map(c => c.value).join(' ').trim().split(' '))\\n\\nmodule.exports = toComparators\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst Range = require('../classes/range')\\n\\nconst maxSatisfying = (versions, range, options) => {\\n let max = null\\n let maxSV = null\\n let rangeObj = null\\n try {\\n rangeObj = new Range(range, options)\\n } catch (er) {\\n return null\\n }\\n versions.forEach((v) => {\\n if (rangeObj.test(v)) {\\n // satisfies(v, range, options)\\n if (!max || maxSV.compare(v) === -1) {\\n // compare(max, v, true)\\n max = v\\n maxSV = new SemVer(max, options)\\n }\\n }\\n })\\n return max\\n}\\nmodule.exports = maxSatisfying\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst Range = require('../classes/range')\\nconst minSatisfying = (versions, range, options) => {\\n let min = null\\n let minSV = null\\n let rangeObj = null\\n try {\\n rangeObj = new Range(range, options)\\n } catch (er) {\\n return null\\n }\\n versions.forEach((v) => {\\n if (rangeObj.test(v)) {\\n // satisfies(v, range, options)\\n if (!min || minSV.compare(v) === 1) {\\n // compare(min, v, true)\\n min = v\\n minSV = new SemVer(min, options)\\n }\\n }\\n })\\n return min\\n}\\nmodule.exports = minSatisfying\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst Range = require('../classes/range')\\nconst gt = require('../functions/gt')\\n\\nconst minVersion = (range, loose) => {\\n range = new Range(range, loose)\\n\\n let minver = new SemVer('0.0.0')\\n if (range.test(minver)) {\\n return minver\\n }\\n\\n minver = new SemVer('0.0.0-0')\\n if (range.test(minver)) {\\n return minver\\n }\\n\\n minver = null\\n for (let i = 0; i < range.set.length; ++i) {\\n const comparators = range.set[i]\\n\\n let setMin = null\\n comparators.forEach((comparator) => {\\n // Clone to avoid manipulating the comparator's semver object.\\n const compver = new SemVer(comparator.semver.version)\\n switch (comparator.operator) {\\n case '>':\\n if (compver.prerelease.length === 0) {\\n compver.patch++\\n } else {\\n compver.prerelease.push(0)\\n }\\n compver.raw = compver.format()\\n /* fallthrough */\\n case '':\\n case '>=':\\n if (!setMin || gt(compver, setMin)) {\\n setMin = compver\\n }\\n break\\n case '<':\\n case '<=':\\n /* Ignore maximum versions */\\n break\\n /* istanbul ignore next */\\n default:\\n throw new Error(`Unexpected operation: ${comparator.operator}`)\\n }\\n })\\n if (setMin && (!minver || gt(minver, setMin))) {\\n minver = setMin\\n }\\n }\\n\\n if (minver && range.test(minver)) {\\n return minver\\n }\\n\\n return null\\n}\\nmodule.exports = minVersion\\n\",\"'use strict'\\n\\nconst Range = require('../classes/range')\\nconst validRange = (range, options) => {\\n try {\\n // Return '*' instead of '' so that truthiness works.\\n // This will throw if it's invalid anyway\\n return new Range(range, options).range || '*'\\n } catch (er) {\\n return null\\n }\\n}\\nmodule.exports = validRange\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst Comparator = require('../classes/comparator')\\nconst { ANY } = Comparator\\nconst Range = require('../classes/range')\\nconst satisfies = require('../functions/satisfies')\\nconst gt = require('../functions/gt')\\nconst lt = require('../functions/lt')\\nconst lte = require('../functions/lte')\\nconst gte = require('../functions/gte')\\n\\nconst outside = (version, range, hilo, options) => {\\n version = new SemVer(version, options)\\n range = new Range(range, options)\\n\\n let gtfn, ltefn, ltfn, comp, ecomp\\n switch (hilo) {\\n case '>':\\n gtfn = gt\\n ltefn = lte\\n ltfn = lt\\n comp = '>'\\n ecomp = '>='\\n break\\n case '<':\\n gtfn = lt\\n ltefn = gte\\n ltfn = gt\\n comp = '<'\\n ecomp = '<='\\n break\\n default:\\n throw new TypeError('Must provide a hilo val of \\\"<\\\" or \\\">\\\"')\\n }\\n\\n // If it satisfies the range it is not outside\\n if (satisfies(version, range, options)) {\\n return false\\n }\\n\\n // From now on, variable terms are as if we're in \\\"gtr\\\" mode.\\n // but note that everything is flipped for the \\\"ltr\\\" function.\\n\\n for (let i = 0; i < range.set.length; ++i) {\\n const comparators = range.set[i]\\n\\n let high = null\\n let low = null\\n\\n comparators.forEach((comparator) => {\\n if (comparator.semver === ANY) {\\n comparator = new Comparator('>=0.0.0')\\n }\\n high = high || comparator\\n low = low || comparator\\n if (gtfn(comparator.semver, high.semver, options)) {\\n high = comparator\\n } else if (ltfn(comparator.semver, low.semver, options)) {\\n low = comparator\\n }\\n })\\n\\n // If the edge version comparator has a operator then our version\\n // isn't outside it\\n if (high.operator === comp || high.operator === ecomp) {\\n return false\\n }\\n\\n // If the lowest version comparator has an operator and our version\\n // is less than it then it isn't higher than the range\\n if ((!low.operator || low.operator === comp) &&\\n ltefn(version, low.semver)) {\\n return false\\n } else if (low.operator === ecomp && ltfn(version, low.semver)) {\\n return false\\n }\\n }\\n return true\\n}\\n\\nmodule.exports = outside\\n\",\"'use strict'\\n\\n// Determine if version is greater than all the versions possible in the range.\\nconst outside = require('./outside')\\nconst gtr = (version, range, options) => outside(version, range, '>', options)\\nmodule.exports = gtr\\n\",\"'use strict'\\n\\nconst outside = require('./outside')\\n// Determine if version is less than all the versions possible in the range\\nconst ltr = (version, range, options) => outside(version, range, '<', options)\\nmodule.exports = ltr\\n\",\"'use strict'\\n\\nconst Range = require('../classes/range')\\nconst intersects = (r1, r2, options) => {\\n r1 = new Range(r1, options)\\n r2 = new Range(r2, options)\\n return r1.intersects(r2, options)\\n}\\nmodule.exports = intersects\\n\",\"'use strict'\\n\\n// given a set of versions and a range, create a \\\"simplified\\\" range\\n// that includes the same versions that the original range does\\n// If the original range is shorter than the simplified one, return that.\\nconst satisfies = require('../functions/satisfies.js')\\nconst compare = require('../functions/compare.js')\\nmodule.exports = (versions, range, options) => {\\n const set = []\\n let first = null\\n let prev = null\\n const v = versions.sort((a, b) => compare(a, b, options))\\n for (const version of v) {\\n const included = satisfies(version, range, options)\\n if (included) {\\n prev = version\\n if (!first) {\\n first = version\\n }\\n } else {\\n if (prev) {\\n set.push([first, prev])\\n }\\n prev = null\\n first = null\\n }\\n }\\n if (first) {\\n set.push([first, null])\\n }\\n\\n const ranges = []\\n for (const [min, max] of set) {\\n if (min === max) {\\n ranges.push(min)\\n } else if (!max && min === v[0]) {\\n ranges.push('*')\\n } else if (!max) {\\n ranges.push(`>=${min}`)\\n } else if (min === v[0]) {\\n ranges.push(`<=${max}`)\\n } else {\\n ranges.push(`${min} - ${max}`)\\n }\\n }\\n const simplified = ranges.join(' || ')\\n const original = typeof range.raw === 'string' ? range.raw : String(range)\\n return simplified.length < original.length ? simplified : range\\n}\\n\",\"'use strict'\\n\\nconst Range = require('../classes/range.js')\\nconst Comparator = require('../classes/comparator.js')\\nconst { ANY } = Comparator\\nconst satisfies = require('../functions/satisfies.js')\\nconst compare = require('../functions/compare.js')\\n\\n// Complex range `r1 || r2 || ...` is a subset of `R1 || R2 || ...` iff:\\n// - Every simple range `r1, r2, ...` is a null set, OR\\n// - Every simple range `r1, r2, ...` which is not a null set is a subset of\\n// some `R1, R2, ...`\\n//\\n// Simple range `c1 c2 ...` is a subset of simple range `C1 C2 ...` iff:\\n// - If c is only the ANY comparator\\n// - If C is only the ANY comparator, return true\\n// - Else if in prerelease mode, return false\\n// - else replace c with `[>=0.0.0]`\\n// - If C is only the ANY comparator\\n// - if in prerelease mode, return true\\n// - else replace C with `[>=0.0.0]`\\n// - Let EQ be the set of = comparators in c\\n// - If EQ is more than one, return true (null set)\\n// - Let GT be the highest > or >= comparator in c\\n// - Let LT be the lowest < or <= comparator in c\\n// - If GT and LT, and GT.semver > LT.semver, return true (null set)\\n// - If any C is a = range, and GT or LT are set, return false\\n// - If EQ\\n// - If GT, and EQ does not satisfy GT, return true (null set)\\n// - If LT, and EQ does not satisfy LT, return true (null set)\\n// - If EQ satisfies every C, return true\\n// - Else return false\\n// - If GT\\n// - If GT.semver is lower than any > or >= comp in C, return false\\n// - If GT is >=, and GT.semver does not satisfy every C, return false\\n// - If GT.semver has a prerelease, and not in prerelease mode\\n// - If no C has a prerelease and the GT.semver tuple, return false\\n// - If LT\\n// - If LT.semver is greater than any < or <= comp in C, return false\\n// - If LT is <=, and LT.semver does not satisfy every C, return false\\n// - If GT.semver has a prerelease, and not in prerelease mode\\n// - If no C has a prerelease and the LT.semver tuple, return false\\n// - Else return true\\n\\nconst subset = (sub, dom, options = {}) => {\\n if (sub === dom) {\\n return true\\n }\\n\\n sub = new Range(sub, options)\\n dom = new Range(dom, options)\\n let sawNonNull = false\\n\\n OUTER: for (const simpleSub of sub.set) {\\n for (const simpleDom of dom.set) {\\n const isSub = simpleSubset(simpleSub, simpleDom, options)\\n sawNonNull = sawNonNull || isSub !== null\\n if (isSub) {\\n continue OUTER\\n }\\n }\\n // the null set is a subset of everything, but null simple ranges in\\n // a complex range should be ignored. so if we saw a non-null range,\\n // then we know this isn't a subset, but if EVERY simple range was null,\\n // then it is a subset.\\n if (sawNonNull) {\\n return false\\n }\\n }\\n return true\\n}\\n\\nconst minimumVersionWithPreRelease = [new Comparator('>=0.0.0-0')]\\nconst minimumVersion = [new Comparator('>=0.0.0')]\\n\\nconst simpleSubset = (sub, dom, options) => {\\n if (sub === dom) {\\n return true\\n }\\n\\n if (sub.length === 1 && sub[0].semver === ANY) {\\n if (dom.length === 1 && dom[0].semver === ANY) {\\n return true\\n } else if (options.includePrerelease) {\\n sub = minimumVersionWithPreRelease\\n } else {\\n sub = minimumVersion\\n }\\n }\\n\\n if (dom.length === 1 && dom[0].semver === ANY) {\\n if (options.includePrerelease) {\\n return true\\n } else {\\n dom = minimumVersion\\n }\\n }\\n\\n const eqSet = new Set()\\n let gt, lt\\n for (const c of sub) {\\n if (c.operator === '>' || c.operator === '>=') {\\n gt = higherGT(gt, c, options)\\n } else if (c.operator === '<' || c.operator === '<=') {\\n lt = lowerLT(lt, c, options)\\n } else {\\n eqSet.add(c.semver)\\n }\\n }\\n\\n if (eqSet.size > 1) {\\n return null\\n }\\n\\n let gtltComp\\n if (gt && lt) {\\n gtltComp = compare(gt.semver, lt.semver, options)\\n if (gtltComp > 0) {\\n return null\\n } else if (gtltComp === 0 && (gt.operator !== '>=' || lt.operator !== '<=')) {\\n return null\\n }\\n }\\n\\n // will iterate one or zero times\\n for (const eq of eqSet) {\\n if (gt && !satisfies(eq, String(gt), options)) {\\n return null\\n }\\n\\n if (lt && !satisfies(eq, String(lt), options)) {\\n return null\\n }\\n\\n for (const c of dom) {\\n if (!satisfies(eq, String(c), options)) {\\n return false\\n }\\n }\\n\\n return true\\n }\\n\\n let higher, lower\\n let hasDomLT, hasDomGT\\n // if the subset has a prerelease, we need a comparator in the superset\\n // with the same tuple and a prerelease, or it's not a subset\\n let needDomLTPre = lt &&\\n !options.includePrerelease &&\\n lt.semver.prerelease.length ? lt.semver : false\\n let needDomGTPre = gt &&\\n !options.includePrerelease &&\\n gt.semver.prerelease.length ? gt.semver : false\\n // exception: <1.2.3-0 is the same as <1.2.3\\n if (needDomLTPre && needDomLTPre.prerelease.length === 1 &&\\n lt.operator === '<' && needDomLTPre.prerelease[0] === 0) {\\n needDomLTPre = false\\n }\\n\\n for (const c of dom) {\\n hasDomGT = hasDomGT || c.operator === '>' || c.operator === '>='\\n hasDomLT = hasDomLT || c.operator === '<' || c.operator === '<='\\n if (gt) {\\n if (needDomGTPre) {\\n if (c.semver.prerelease && c.semver.prerelease.length &&\\n c.semver.major === needDomGTPre.major &&\\n c.semver.minor === needDomGTPre.minor &&\\n c.semver.patch === needDomGTPre.patch) {\\n needDomGTPre = false\\n }\\n }\\n if (c.operator === '>' || c.operator === '>=') {\\n higher = higherGT(gt, c, options)\\n if (higher === c && higher !== gt) {\\n return false\\n }\\n } else if (gt.operator === '>=' && !satisfies(gt.semver, String(c), options)) {\\n return false\\n }\\n }\\n if (lt) {\\n if (needDomLTPre) {\\n if (c.semver.prerelease && c.semver.prerelease.length &&\\n c.semver.major === needDomLTPre.major &&\\n c.semver.minor === needDomLTPre.minor &&\\n c.semver.patch === needDomLTPre.patch) {\\n needDomLTPre = false\\n }\\n }\\n if (c.operator === '<' || c.operator === '<=') {\\n lower = lowerLT(lt, c, options)\\n if (lower === c && lower !== lt) {\\n return false\\n }\\n } else if (lt.operator === '<=' && !satisfies(lt.semver, String(c), options)) {\\n return false\\n }\\n }\\n if (!c.operator && (lt || gt) && gtltComp !== 0) {\\n return false\\n }\\n }\\n\\n // if there was a < or >, and nothing in the dom, then must be false\\n // UNLESS it was limited by another range in the other direction.\\n // Eg, >1.0.0 <1.0.1 is still a subset of <2.0.0\\n if (gt && hasDomLT && !lt && gtltComp !== 0) {\\n return false\\n }\\n\\n if (lt && hasDomGT && !gt && gtltComp !== 0) {\\n return false\\n }\\n\\n // we needed a prerelease range in a specific tuple, but didn't get one\\n // then this isn't a subset. eg >=1.2.3-pre is not a subset of >=1.0.0,\\n // because it includes prereleases in the 1.2.3 tuple\\n if (needDomGTPre || needDomLTPre) {\\n return false\\n }\\n\\n return true\\n}\\n\\n// >=1.2.3 is lower than >1.2.3\\nconst higherGT = (a, b, options) => {\\n if (!a) {\\n return b\\n }\\n const comp = compare(a.semver, b.semver, options)\\n return comp > 0 ? a\\n : comp < 0 ? b\\n : b.operator === '>' && a.operator === '>=' ? b\\n : a\\n}\\n\\n// <=1.2.3 is higher than <1.2.3\\nconst lowerLT = (a, b, options) => {\\n if (!a) {\\n return b\\n }\\n const comp = compare(a.semver, b.semver, options)\\n return comp < 0 ? a\\n : comp > 0 ? b\\n : b.operator === '<' && a.operator === '<=' ? b\\n : a\\n}\\n\\nmodule.exports = subset\\n\",\"'use strict'\\n\\n// just pre-load all the stuff that index.js lazily exports\\nconst internalRe = require('./internal/re')\\nconst constants = require('./internal/constants')\\nconst SemVer = require('./classes/semver')\\nconst identifiers = require('./internal/identifiers')\\nconst parse = require('./functions/parse')\\nconst valid = require('./functions/valid')\\nconst clean = require('./functions/clean')\\nconst inc = require('./functions/inc')\\nconst diff = require('./functions/diff')\\nconst major = require('./functions/major')\\nconst minor = require('./functions/minor')\\nconst patch = require('./functions/patch')\\nconst prerelease = require('./functions/prerelease')\\nconst compare = require('./functions/compare')\\nconst rcompare = require('./functions/rcompare')\\nconst compareLoose = require('./functions/compare-loose')\\nconst compareBuild = require('./functions/compare-build')\\nconst sort = require('./functions/sort')\\nconst rsort = require('./functions/rsort')\\nconst gt = require('./functions/gt')\\nconst lt = require('./functions/lt')\\nconst eq = require('./functions/eq')\\nconst neq = require('./functions/neq')\\nconst gte = require('./functions/gte')\\nconst lte = require('./functions/lte')\\nconst cmp = require('./functions/cmp')\\nconst coerce = require('./functions/coerce')\\nconst Comparator = require('./classes/comparator')\\nconst Range = require('./classes/range')\\nconst satisfies = require('./functions/satisfies')\\nconst toComparators = require('./ranges/to-comparators')\\nconst maxSatisfying = require('./ranges/max-satisfying')\\nconst minSatisfying = require('./ranges/min-satisfying')\\nconst minVersion = require('./ranges/min-version')\\nconst validRange = require('./ranges/valid')\\nconst outside = require('./ranges/outside')\\nconst gtr = require('./ranges/gtr')\\nconst ltr = require('./ranges/ltr')\\nconst intersects = require('./ranges/intersects')\\nconst simplifyRange = require('./ranges/simplify')\\nconst subset = require('./ranges/subset')\\nmodule.exports = {\\n parse,\\n valid,\\n clean,\\n inc,\\n diff,\\n major,\\n minor,\\n patch,\\n prerelease,\\n compare,\\n rcompare,\\n compareLoose,\\n compareBuild,\\n sort,\\n rsort,\\n gt,\\n lt,\\n eq,\\n neq,\\n gte,\\n lte,\\n cmp,\\n coerce,\\n Comparator,\\n Range,\\n satisfies,\\n toComparators,\\n maxSatisfying,\\n minSatisfying,\\n minVersion,\\n validRange,\\n outside,\\n gtr,\\n ltr,\\n intersects,\\n simplifyRange,\\n subset,\\n SemVer,\\n re: internalRe.re,\\n src: internalRe.src,\\n tokens: internalRe.t,\\n SEMVER_SPEC_VERSION: constants.SEMVER_SPEC_VERSION,\\n RELEASE_TYPES: constants.RELEASE_TYPES,\\n compareIdentifiers: identifiers.compareIdentifiers,\\n rcompareIdentifiers: identifiers.rcompareIdentifiers,\\n}\\n\",\"import { satisfies, valid } from 'semver';\\n\\nconst version = Host.v1.document.get('text/semver-case');\\nconst ranges = ['>=1.2.0 <2.0.0', '^1.2.0', '~1.2.3'];\\n\\nexport default {\\n version,\\n valid: valid(version) !== null,\\n checks: ranges.map((range) => ({ range, ok: satisfies(version, range) })),\\n};\\n\"],\"version\":3}", + "originMeta": { + "originalPath": "node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/comparator.js", + "packageName": "semver", + "packageVersion": "7.7.3", + "integrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562" + } + } + ], + "builderVersion": "deterministic-builder-v1", + "dependencyIntegrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562", + "diagnosticsMeta": { + "entryPath": "/workspace/apps/ecosystem-certifier/fixtures/positive/semver-entry.ts", + "modulePaths": [ + "./semver-entry.js" + ] + }, + "graphHash": "9215dccaba757b484b9b1c608c38ec06a9d4e4c98b0b16ddf6e1d9cf18c0d03f" + } + } + }, + "manifest": { + "abi_id": "Host.v1", + "abi_version": 1, + "functions": [ + { + "fn_id": 1, + "js_path": [ + "document", + "get" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 2, + "js_path": [ + "document", + "getCanonical" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 3, + "js_path": [ + "emit" + ], + "effect": "EMIT", + "arity": 1, + "arg_schema": [ + { + "type": "dv" + } + ], + "return_schema": { + "type": "null" + }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [ + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + } + ] + } + ] + } + }, + { + "id": "green-base64", + "title": "base64-js deterministic roundtrip", + "kind": "ecosystem-green", + "badge": "Green ecosystem fixture", + "description": "Binary roundtrip coverage from the certified green ecosystem corpus.", + "certified": true, + "executionProfile": "compat-binary-v1", + "sourceKind": "module-pack", + "abiId": "Host.v2", + "gasLimit": "5000000", + "sourcePaths": [ + "libs/test-harness/fixtures/library-reuse/binary-base64-entry.ts" + ], + "sourceText": "import { fromByteArray, toByteArray } from 'base64-js';\n\nconst bytes = toByteArray('AQIDBAUGBwg=');\nconst sum = bytes.reduce((acc, value) => acc + value, 0);\n\nexport default {\n length: bytes.length,\n sum,\n first: bytes[0],\n last: bytes[bytes.length - 1],\n reencoded: fromByteArray(bytes),\n};\n", + "hostPreset": "certification", + "hostSummary": { + "label": "Certification host", + "description": "Provides the ecosystem-certifier text and binary documents used for workload certification.", + "documents": [ + "pack/metadata.json", + "pack/metadata.yaml", + "docs/a.md", + "docs/b.md", + "docs/c.md", + "docs/d.md", + "bytes/payload", + "bytes/flagship-extra", + "pack/attachment.deflated" + ] + }, + "docsLinks": [ + { + "label": "Workload certification", + "href": "/docs/workload-certification.md" + }, + { + "label": "Compatibility report", + "href": "/docs/ecosystem-compatibility-report.md" + } + ], + "supportsOogSearch": false, + "program": { + "version": 2, + "abiId": "Host.v2", + "abiVersion": 2, + "abiManifestHash": "ec5c3df99a1b0ab84b692996193707ae6c931382e75c96c7c14b4f8baaae5af2", + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8, + "executionProfile": "compat-binary-v1", + "sourceKind": "module-pack", + "source": { + "modulePack": { + "version": 1, + "entrySpecifier": "./binary-base64-entry.js", + "entryExport": "default", + "modules": [ + { + "specifier": "./binary-base64-entry.js", + "source": "var __create = Object.create;\nvar __defProp = Object.defineProperty;\nvar __getOwnPropDesc = Object.getOwnPropertyDescriptor;\nvar __getOwnPropNames = Object.getOwnPropertyNames;\nvar __getProtoOf = Object.getPrototypeOf;\nvar __hasOwnProp = Object.prototype.hasOwnProperty;\nvar __commonJS = (cb, mod) => function __require() {\n return mod || (0, cb[__getOwnPropNames(cb)[0]])((mod = { exports: {} }).exports, mod), mod.exports;\n};\nvar __copyProps = (to, from, except, desc) => {\n if (from && typeof from === \"object\" || typeof from === \"function\") {\n for (let key of __getOwnPropNames(from))\n if (!__hasOwnProp.call(to, key) && key !== except)\n __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });\n }\n return to;\n};\nvar __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(\n // If the importer is in node compatibility mode or this is not an ESM\n // file that has been converted to a CommonJS file using a Babel-\n // compatible transform (i.e. \"__esModule\" has not been set), then set\n // \"default\" to the CommonJS \"module.exports\" for node compatibility.\n isNodeMode || !mod || !mod.__esModule ? __defProp(target, \"default\", { value: mod, enumerable: true }) : target,\n mod\n));\n\n// node_modules/.pnpm/base64-js@1.5.1/node_modules/base64-js/index.js\nvar require_base64_js = __commonJS({\n \"node_modules/.pnpm/base64-js@1.5.1/node_modules/base64-js/index.js\"(exports) {\n \"use strict\";\n exports.byteLength = byteLength;\n exports.toByteArray = toByteArray2;\n exports.fromByteArray = fromByteArray2;\n var lookup = [];\n var revLookup = [];\n var Arr = typeof Uint8Array !== \"undefined\" ? Uint8Array : Array;\n var code = \"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/\";\n for (i = 0, len = code.length; i < len; ++i) {\n lookup[i] = code[i];\n revLookup[code.charCodeAt(i)] = i;\n }\n var i;\n var len;\n revLookup[\"-\".charCodeAt(0)] = 62;\n revLookup[\"_\".charCodeAt(0)] = 63;\n function getLens(b64) {\n var len2 = b64.length;\n if (len2 % 4 > 0) {\n throw new Error(\"Invalid string. Length must be a multiple of 4\");\n }\n var validLen = b64.indexOf(\"=\");\n if (validLen === -1) validLen = len2;\n var placeHoldersLen = validLen === len2 ? 0 : 4 - validLen % 4;\n return [validLen, placeHoldersLen];\n }\n function byteLength(b64) {\n var lens = getLens(b64);\n var validLen = lens[0];\n var placeHoldersLen = lens[1];\n return (validLen + placeHoldersLen) * 3 / 4 - placeHoldersLen;\n }\n function _byteLength(b64, validLen, placeHoldersLen) {\n return (validLen + placeHoldersLen) * 3 / 4 - placeHoldersLen;\n }\n function toByteArray2(b64) {\n var tmp;\n var lens = getLens(b64);\n var validLen = lens[0];\n var placeHoldersLen = lens[1];\n var arr = new Arr(_byteLength(b64, validLen, placeHoldersLen));\n var curByte = 0;\n var len2 = placeHoldersLen > 0 ? validLen - 4 : validLen;\n var i2;\n for (i2 = 0; i2 < len2; i2 += 4) {\n tmp = revLookup[b64.charCodeAt(i2)] << 18 | revLookup[b64.charCodeAt(i2 + 1)] << 12 | revLookup[b64.charCodeAt(i2 + 2)] << 6 | revLookup[b64.charCodeAt(i2 + 3)];\n arr[curByte++] = tmp >> 16 & 255;\n arr[curByte++] = tmp >> 8 & 255;\n arr[curByte++] = tmp & 255;\n }\n if (placeHoldersLen === 2) {\n tmp = revLookup[b64.charCodeAt(i2)] << 2 | revLookup[b64.charCodeAt(i2 + 1)] >> 4;\n arr[curByte++] = tmp & 255;\n }\n if (placeHoldersLen === 1) {\n tmp = revLookup[b64.charCodeAt(i2)] << 10 | revLookup[b64.charCodeAt(i2 + 1)] << 4 | revLookup[b64.charCodeAt(i2 + 2)] >> 2;\n arr[curByte++] = tmp >> 8 & 255;\n arr[curByte++] = tmp & 255;\n }\n return arr;\n }\n function tripletToBase64(num) {\n return lookup[num >> 18 & 63] + lookup[num >> 12 & 63] + lookup[num >> 6 & 63] + lookup[num & 63];\n }\n function encodeChunk(uint8, start, end) {\n var tmp;\n var output = [];\n for (var i2 = start; i2 < end; i2 += 3) {\n tmp = (uint8[i2] << 16 & 16711680) + (uint8[i2 + 1] << 8 & 65280) + (uint8[i2 + 2] & 255);\n output.push(tripletToBase64(tmp));\n }\n return output.join(\"\");\n }\n function fromByteArray2(uint8) {\n var tmp;\n var len2 = uint8.length;\n var extraBytes = len2 % 3;\n var parts = [];\n var maxChunkLength = 16383;\n for (var i2 = 0, len22 = len2 - extraBytes; i2 < len22; i2 += maxChunkLength) {\n parts.push(encodeChunk(uint8, i2, i2 + maxChunkLength > len22 ? len22 : i2 + maxChunkLength));\n }\n if (extraBytes === 1) {\n tmp = uint8[len2 - 1];\n parts.push(\n lookup[tmp >> 2] + lookup[tmp << 4 & 63] + \"==\"\n );\n } else if (extraBytes === 2) {\n tmp = (uint8[len2 - 2] << 8) + uint8[len2 - 1];\n parts.push(\n lookup[tmp >> 10] + lookup[tmp >> 4 & 63] + lookup[tmp << 2 & 63] + \"=\"\n );\n }\n return parts.join(\"\");\n }\n }\n});\n\n// libs/test-harness/fixtures/library-reuse/binary-base64-entry.ts\nvar import_base64_js = __toESM(require_base64_js(), 1);\nvar bytes = (0, import_base64_js.toByteArray)(\"AQIDBAUGBwg=\");\nvar sum = bytes.reduce((acc, value) => acc + value, 0);\nvar binary_base64_entry_default = {\n length: bytes.length,\n sum,\n first: bytes[0],\n last: bytes[bytes.length - 1],\n reencoded: (0, import_base64_js.fromByteArray)(bytes)\n};\nexport {\n binary_base64_entry_default as default\n};\n", + "sourceMap": "{\"mappings\":\"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\",\"names\":[\"toByteArray\",\"fromByteArray\",\"len\",\"i\",\"len2\"],\"sources\":[\"../node_modules/.pnpm/base64-js@1.5.1/node_modules/base64-js/index.js\",\"../libs/test-harness/fixtures/library-reuse/binary-base64-entry.ts\"],\"sourcesContent\":[\"'use strict'\\n\\nexports.byteLength = byteLength\\nexports.toByteArray = toByteArray\\nexports.fromByteArray = fromByteArray\\n\\nvar lookup = []\\nvar revLookup = []\\nvar Arr = typeof Uint8Array !== 'undefined' ? Uint8Array : Array\\n\\nvar code = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/'\\nfor (var i = 0, len = code.length; i < len; ++i) {\\n lookup[i] = code[i]\\n revLookup[code.charCodeAt(i)] = i\\n}\\n\\n// Support decoding URL-safe base64 strings, as Node.js does.\\n// See: https://en.wikipedia.org/wiki/Base64#URL_applications\\nrevLookup['-'.charCodeAt(0)] = 62\\nrevLookup['_'.charCodeAt(0)] = 63\\n\\nfunction getLens (b64) {\\n var len = b64.length\\n\\n if (len % 4 > 0) {\\n throw new Error('Invalid string. Length must be a multiple of 4')\\n }\\n\\n // Trim off extra bytes after placeholder bytes are found\\n // See: https://github.com/beatgammit/base64-js/issues/42\\n var validLen = b64.indexOf('=')\\n if (validLen === -1) validLen = len\\n\\n var placeHoldersLen = validLen === len\\n ? 0\\n : 4 - (validLen % 4)\\n\\n return [validLen, placeHoldersLen]\\n}\\n\\n// base64 is 4/3 + up to two characters of the original data\\nfunction byteLength (b64) {\\n var lens = getLens(b64)\\n var validLen = lens[0]\\n var placeHoldersLen = lens[1]\\n return ((validLen + placeHoldersLen) * 3 / 4) - placeHoldersLen\\n}\\n\\nfunction _byteLength (b64, validLen, placeHoldersLen) {\\n return ((validLen + placeHoldersLen) * 3 / 4) - placeHoldersLen\\n}\\n\\nfunction toByteArray (b64) {\\n var tmp\\n var lens = getLens(b64)\\n var validLen = lens[0]\\n var placeHoldersLen = lens[1]\\n\\n var arr = new Arr(_byteLength(b64, validLen, placeHoldersLen))\\n\\n var curByte = 0\\n\\n // if there are placeholders, only get up to the last complete 4 chars\\n var len = placeHoldersLen > 0\\n ? validLen - 4\\n : validLen\\n\\n var i\\n for (i = 0; i < len; i += 4) {\\n tmp =\\n (revLookup[b64.charCodeAt(i)] << 18) |\\n (revLookup[b64.charCodeAt(i + 1)] << 12) |\\n (revLookup[b64.charCodeAt(i + 2)] << 6) |\\n revLookup[b64.charCodeAt(i + 3)]\\n arr[curByte++] = (tmp >> 16) & 0xFF\\n arr[curByte++] = (tmp >> 8) & 0xFF\\n arr[curByte++] = tmp & 0xFF\\n }\\n\\n if (placeHoldersLen === 2) {\\n tmp =\\n (revLookup[b64.charCodeAt(i)] << 2) |\\n (revLookup[b64.charCodeAt(i + 1)] >> 4)\\n arr[curByte++] = tmp & 0xFF\\n }\\n\\n if (placeHoldersLen === 1) {\\n tmp =\\n (revLookup[b64.charCodeAt(i)] << 10) |\\n (revLookup[b64.charCodeAt(i + 1)] << 4) |\\n (revLookup[b64.charCodeAt(i + 2)] >> 2)\\n arr[curByte++] = (tmp >> 8) & 0xFF\\n arr[curByte++] = tmp & 0xFF\\n }\\n\\n return arr\\n}\\n\\nfunction tripletToBase64 (num) {\\n return lookup[num >> 18 & 0x3F] +\\n lookup[num >> 12 & 0x3F] +\\n lookup[num >> 6 & 0x3F] +\\n lookup[num & 0x3F]\\n}\\n\\nfunction encodeChunk (uint8, start, end) {\\n var tmp\\n var output = []\\n for (var i = start; i < end; i += 3) {\\n tmp =\\n ((uint8[i] << 16) & 0xFF0000) +\\n ((uint8[i + 1] << 8) & 0xFF00) +\\n (uint8[i + 2] & 0xFF)\\n output.push(tripletToBase64(tmp))\\n }\\n return output.join('')\\n}\\n\\nfunction fromByteArray (uint8) {\\n var tmp\\n var len = uint8.length\\n var extraBytes = len % 3 // if we have 1 byte left, pad 2 bytes\\n var parts = []\\n var maxChunkLength = 16383 // must be multiple of 3\\n\\n // go through the array every three bytes, we'll deal with trailing stuff later\\n for (var i = 0, len2 = len - extraBytes; i < len2; i += maxChunkLength) {\\n parts.push(encodeChunk(uint8, i, (i + maxChunkLength) > len2 ? len2 : (i + maxChunkLength)))\\n }\\n\\n // pad the end with zeros, but make sure to not forget the extra bytes\\n if (extraBytes === 1) {\\n tmp = uint8[len - 1]\\n parts.push(\\n lookup[tmp >> 2] +\\n lookup[(tmp << 4) & 0x3F] +\\n '=='\\n )\\n } else if (extraBytes === 2) {\\n tmp = (uint8[len - 2] << 8) + uint8[len - 1]\\n parts.push(\\n lookup[tmp >> 10] +\\n lookup[(tmp >> 4) & 0x3F] +\\n lookup[(tmp << 2) & 0x3F] +\\n '='\\n )\\n }\\n\\n return parts.join('')\\n}\\n\",\"import { fromByteArray, toByteArray } from 'base64-js';\\n\\nconst bytes = toByteArray('AQIDBAUGBwg=');\\nconst sum = bytes.reduce((acc, value) => acc + value, 0);\\n\\nexport default {\\n length: bytes.length,\\n sum,\\n first: bytes[0],\\n last: bytes[bytes.length - 1],\\n reencoded: fromByteArray(bytes),\\n};\\n\"],\"version\":3}", + "originMeta": { + "originalPath": "node_modules/.pnpm/base64-js@1.5.1/node_modules/base64-js/index.js", + "packageName": "base64-js", + "packageVersion": "1.5.1", + "integrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562" + } + } + ], + "builderVersion": "deterministic-builder-v1", + "dependencyIntegrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562", + "diagnosticsMeta": { + "entryPath": "/workspace/libs/test-harness/fixtures/library-reuse/binary-base64-entry.ts", + "modulePaths": [ + "./binary-base64-entry.js" + ] + }, + "graphHash": "d409281c0ea5deb67a631c31052e39836768a41ecc80e946d071853620684b98" + } + } + }, + "manifest": { + "abi_id": "Host.v2", + "abi_version": 2, + "functions": [ + { + "fn_id": 1, + "js_path": [ + "document", + "get" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 2, + "js_path": [ + "document", + "getCanonical" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 3, + "js_path": [ + "emit" + ], + "effect": "EMIT", + "arity": 1, + "arg_schema": [ + { + "type": "dv" + } + ], + "return_schema": { + "type": "null" + }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [ + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + } + ] + } + ] + } + }, + { + "id": "green-markdown-it", + "title": "markdown-it deterministic tokenization", + "kind": "ecosystem-green", + "badge": "Green ecosystem fixture", + "description": "A larger parser-oriented compatibility fixture running under deterministic constraints.", + "certified": true, + "executionProfile": "compat-binary-v1", + "sourceKind": "module-pack", + "abiId": "Host.v1", + "gasLimit": "1000000", + "sourcePaths": [ + "apps/ecosystem-certifier/fixtures/positive/markdown-it-entry.ts" + ], + "sourceText": "import MarkdownIt from 'markdown-it';\n\nconst md = new MarkdownIt({\n linkify: true,\n});\nconst source = Host.v1.document.get('text/markdown-case');\nconst tokens = md.parse(source, {});\nconst links = md.render(source).match(/ token.type),\n tokenCount: tokens.length,\n linkCount: links,\n};\n", + "hostPreset": "certification", + "hostSummary": { + "label": "Certification host", + "description": "Provides the ecosystem-certifier text and binary documents used for workload certification.", + "documents": [ + "pack/metadata.json", + "pack/metadata.yaml", + "docs/a.md", + "docs/b.md", + "docs/c.md", + "docs/d.md", + "bytes/payload", + "bytes/flagship-extra", + "pack/attachment.deflated" + ] + }, + "docsLinks": [ + { + "label": "Workload certification", + "href": "/docs/workload-certification.md" + }, + { + "label": "Compatibility report", + "href": "/docs/ecosystem-compatibility-report.md" + } + ], + "supportsOogSearch": false, + "program": { + "version": 2, + "abiId": "Host.v1", + "abiVersion": 1, + "abiManifestHash": "e23b0b2ee169900bbde7aff78e6ce20fead1715c60f8a8e3106d9959450a3d34", + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8, + "executionProfile": "compat-binary-v1", + "sourceKind": "module-pack", + "source": { + "modulePack": { + "version": 1, + "entrySpecifier": "./markdown-it-entry.js", + "entryExport": "default", + "modules": [ + { + "specifier": "./markdown-it-entry.js", + "source": "var __defProp = Object.defineProperty;\nvar __export = (target, all) => {\n for (var name in all)\n __defProp(target, name, { get: all[name], enumerable: true });\n};\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/common/utils.mjs\nvar utils_exports = {};\n__export(utils_exports, {\n arrayReplaceAt: () => arrayReplaceAt,\n assign: () => assign,\n escapeHtml: () => escapeHtml,\n escapeRE: () => escapeRE,\n fromCodePoint: () => fromCodePoint2,\n has: () => has,\n isMdAsciiPunct: () => isMdAsciiPunct,\n isPunctChar: () => isPunctChar,\n isSpace: () => isSpace,\n isString: () => isString,\n isValidEntityCode: () => isValidEntityCode,\n isWhiteSpace: () => isWhiteSpace,\n lib: () => lib,\n normalizeReference: () => normalizeReference,\n unescapeAll: () => unescapeAll,\n unescapeMd: () => unescapeMd\n});\n\n// node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/index.mjs\nvar mdurl_exports = {};\n__export(mdurl_exports, {\n decode: () => decode_default,\n encode: () => encode_default,\n format: () => format,\n parse: () => parse_default\n});\n\n// node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/decode.mjs\nvar decodeCache = {};\nfunction getDecodeCache(exclude) {\n let cache = decodeCache[exclude];\n if (cache) {\n return cache;\n }\n cache = decodeCache[exclude] = [];\n for (let i = 0; i < 128; i++) {\n const ch = String.fromCharCode(i);\n cache.push(ch);\n }\n for (let i = 0; i < exclude.length; i++) {\n const ch = exclude.charCodeAt(i);\n cache[ch] = \"%\" + (\"0\" + ch.toString(16).toUpperCase()).slice(-2);\n }\n return cache;\n}\nfunction decode(string, exclude) {\n if (typeof exclude !== \"string\") {\n exclude = decode.defaultChars;\n }\n const cache = getDecodeCache(exclude);\n return string.replace(/(%[a-f0-9]{2})+/gi, function(seq) {\n let result = \"\";\n for (let i = 0, l = seq.length; i < l; i += 3) {\n const b1 = parseInt(seq.slice(i + 1, i + 3), 16);\n if (b1 < 128) {\n result += cache[b1];\n continue;\n }\n if ((b1 & 224) === 192 && i + 3 < l) {\n const b2 = parseInt(seq.slice(i + 4, i + 6), 16);\n if ((b2 & 192) === 128) {\n const chr = b1 << 6 & 1984 | b2 & 63;\n if (chr < 128) {\n result += \"��\";\n } else {\n result += String.fromCharCode(chr);\n }\n i += 3;\n continue;\n }\n }\n if ((b1 & 240) === 224 && i + 6 < l) {\n const b2 = parseInt(seq.slice(i + 4, i + 6), 16);\n const b3 = parseInt(seq.slice(i + 7, i + 9), 16);\n if ((b2 & 192) === 128 && (b3 & 192) === 128) {\n const chr = b1 << 12 & 61440 | b2 << 6 & 4032 | b3 & 63;\n if (chr < 2048 || chr >= 55296 && chr <= 57343) {\n result += \"���\";\n } else {\n result += String.fromCharCode(chr);\n }\n i += 6;\n continue;\n }\n }\n if ((b1 & 248) === 240 && i + 9 < l) {\n const b2 = parseInt(seq.slice(i + 4, i + 6), 16);\n const b3 = parseInt(seq.slice(i + 7, i + 9), 16);\n const b4 = parseInt(seq.slice(i + 10, i + 12), 16);\n if ((b2 & 192) === 128 && (b3 & 192) === 128 && (b4 & 192) === 128) {\n let chr = b1 << 18 & 1835008 | b2 << 12 & 258048 | b3 << 6 & 4032 | b4 & 63;\n if (chr < 65536 || chr > 1114111) {\n result += \"����\";\n } else {\n chr -= 65536;\n result += String.fromCharCode(55296 + (chr >> 10), 56320 + (chr & 1023));\n }\n i += 9;\n continue;\n }\n }\n result += \"�\";\n }\n return result;\n });\n}\ndecode.defaultChars = \";/?:@&=+$,#\";\ndecode.componentChars = \"\";\nvar decode_default = decode;\n\n// node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/encode.mjs\nvar encodeCache = {};\nfunction getEncodeCache(exclude) {\n let cache = encodeCache[exclude];\n if (cache) {\n return cache;\n }\n cache = encodeCache[exclude] = [];\n for (let i = 0; i < 128; i++) {\n const ch = String.fromCharCode(i);\n if (/^[0-9a-z]$/i.test(ch)) {\n cache.push(ch);\n } else {\n cache.push(\"%\" + (\"0\" + i.toString(16).toUpperCase()).slice(-2));\n }\n }\n for (let i = 0; i < exclude.length; i++) {\n cache[exclude.charCodeAt(i)] = exclude[i];\n }\n return cache;\n}\nfunction encode(string, exclude, keepEscaped) {\n if (typeof exclude !== \"string\") {\n keepEscaped = exclude;\n exclude = encode.defaultChars;\n }\n if (typeof keepEscaped === \"undefined\") {\n keepEscaped = true;\n }\n const cache = getEncodeCache(exclude);\n let result = \"\";\n for (let i = 0, l = string.length; i < l; i++) {\n const code2 = string.charCodeAt(i);\n if (keepEscaped && code2 === 37 && i + 2 < l) {\n if (/^[0-9a-f]{2}$/i.test(string.slice(i + 1, i + 3))) {\n result += string.slice(i, i + 3);\n i += 2;\n continue;\n }\n }\n if (code2 < 128) {\n result += cache[code2];\n continue;\n }\n if (code2 >= 55296 && code2 <= 57343) {\n if (code2 >= 55296 && code2 <= 56319 && i + 1 < l) {\n const nextCode = string.charCodeAt(i + 1);\n if (nextCode >= 56320 && nextCode <= 57343) {\n result += encodeURIComponent(string[i] + string[i + 1]);\n i++;\n continue;\n }\n }\n result += \"%EF%BF%BD\";\n continue;\n }\n result += encodeURIComponent(string[i]);\n }\n return result;\n}\nencode.defaultChars = \";/?:@&=+$,-_.!~*'()#\";\nencode.componentChars = \"-_.!~*'()\";\nvar encode_default = encode;\n\n// node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/format.mjs\nfunction format(url) {\n let result = \"\";\n result += url.protocol || \"\";\n result += url.slashes ? \"//\" : \"\";\n result += url.auth ? url.auth + \"@\" : \"\";\n if (url.hostname && url.hostname.indexOf(\":\") !== -1) {\n result += \"[\" + url.hostname + \"]\";\n } else {\n result += url.hostname || \"\";\n }\n result += url.port ? \":\" + url.port : \"\";\n result += url.pathname || \"\";\n result += url.search || \"\";\n result += url.hash || \"\";\n return result;\n}\n\n// node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/parse.mjs\nfunction Url() {\n this.protocol = null;\n this.slashes = null;\n this.auth = null;\n this.port = null;\n this.hostname = null;\n this.hash = null;\n this.search = null;\n this.pathname = null;\n}\nvar protocolPattern = /^([a-z0-9.+-]+:)/i;\nvar portPattern = /:[0-9]*$/;\nvar simplePathPattern = /^(\\/\\/?(?!\\/)[^\\?\\s]*)(\\?[^\\s]*)?$/;\nvar delims = [\"<\", \">\", '\"', \"`\", \" \", \"\\r\", \"\\n\", \"\t\"];\nvar unwise = [\"{\", \"}\", \"|\", \"\\\\\", \"^\", \"`\"].concat(delims);\nvar autoEscape = [\"'\"].concat(unwise);\nvar nonHostChars = [\"%\", \"/\", \"?\", \";\", \"#\"].concat(autoEscape);\nvar hostEndingChars = [\"/\", \"?\", \"#\"];\nvar hostnameMaxLen = 255;\nvar hostnamePartPattern = /^[+a-z0-9A-Z_-]{0,63}$/;\nvar hostnamePartStart = /^([+a-z0-9A-Z_-]{0,63})(.*)$/;\nvar hostlessProtocol = {\n javascript: true,\n \"javascript:\": true\n};\nvar slashedProtocol = {\n http: true,\n https: true,\n ftp: true,\n gopher: true,\n file: true,\n \"http:\": true,\n \"https:\": true,\n \"ftp:\": true,\n \"gopher:\": true,\n \"file:\": true\n};\nfunction urlParse(url, slashesDenoteHost) {\n if (url && url instanceof Url) return url;\n const u = new Url();\n u.parse(url, slashesDenoteHost);\n return u;\n}\nUrl.prototype.parse = function(url, slashesDenoteHost) {\n let lowerProto, hec, slashes;\n let rest = url;\n rest = rest.trim();\n if (!slashesDenoteHost && url.split(\"#\").length === 1) {\n const simplePath = simplePathPattern.exec(rest);\n if (simplePath) {\n this.pathname = simplePath[1];\n if (simplePath[2]) {\n this.search = simplePath[2];\n }\n return this;\n }\n }\n let proto = protocolPattern.exec(rest);\n if (proto) {\n proto = proto[0];\n lowerProto = proto.toLowerCase();\n this.protocol = proto;\n rest = rest.substr(proto.length);\n }\n if (slashesDenoteHost || proto || rest.match(/^\\/\\/[^@\\/]+@[^@\\/]+/)) {\n slashes = rest.substr(0, 2) === \"//\";\n if (slashes && !(proto && hostlessProtocol[proto])) {\n rest = rest.substr(2);\n this.slashes = true;\n }\n }\n if (!hostlessProtocol[proto] && (slashes || proto && !slashedProtocol[proto])) {\n let hostEnd = -1;\n for (let i = 0; i < hostEndingChars.length; i++) {\n hec = rest.indexOf(hostEndingChars[i]);\n if (hec !== -1 && (hostEnd === -1 || hec < hostEnd)) {\n hostEnd = hec;\n }\n }\n let auth, atSign;\n if (hostEnd === -1) {\n atSign = rest.lastIndexOf(\"@\");\n } else {\n atSign = rest.lastIndexOf(\"@\", hostEnd);\n }\n if (atSign !== -1) {\n auth = rest.slice(0, atSign);\n rest = rest.slice(atSign + 1);\n this.auth = auth;\n }\n hostEnd = -1;\n for (let i = 0; i < nonHostChars.length; i++) {\n hec = rest.indexOf(nonHostChars[i]);\n if (hec !== -1 && (hostEnd === -1 || hec < hostEnd)) {\n hostEnd = hec;\n }\n }\n if (hostEnd === -1) {\n hostEnd = rest.length;\n }\n if (rest[hostEnd - 1] === \":\") {\n hostEnd--;\n }\n const host = rest.slice(0, hostEnd);\n rest = rest.slice(hostEnd);\n this.parseHost(host);\n this.hostname = this.hostname || \"\";\n const ipv6Hostname = this.hostname[0] === \"[\" && this.hostname[this.hostname.length - 1] === \"]\";\n if (!ipv6Hostname) {\n const hostparts = this.hostname.split(/\\./);\n for (let i = 0, l = hostparts.length; i < l; i++) {\n const part = hostparts[i];\n if (!part) {\n continue;\n }\n if (!part.match(hostnamePartPattern)) {\n let newpart = \"\";\n for (let j = 0, k = part.length; j < k; j++) {\n if (part.charCodeAt(j) > 127) {\n newpart += \"x\";\n } else {\n newpart += part[j];\n }\n }\n if (!newpart.match(hostnamePartPattern)) {\n const validParts = hostparts.slice(0, i);\n const notHost = hostparts.slice(i + 1);\n const bit = part.match(hostnamePartStart);\n if (bit) {\n validParts.push(bit[1]);\n notHost.unshift(bit[2]);\n }\n if (notHost.length) {\n rest = notHost.join(\".\") + rest;\n }\n this.hostname = validParts.join(\".\");\n break;\n }\n }\n }\n }\n if (this.hostname.length > hostnameMaxLen) {\n this.hostname = \"\";\n }\n if (ipv6Hostname) {\n this.hostname = this.hostname.substr(1, this.hostname.length - 2);\n }\n }\n const hash = rest.indexOf(\"#\");\n if (hash !== -1) {\n this.hash = rest.substr(hash);\n rest = rest.slice(0, hash);\n }\n const qm = rest.indexOf(\"?\");\n if (qm !== -1) {\n this.search = rest.substr(qm);\n rest = rest.slice(0, qm);\n }\n if (rest) {\n this.pathname = rest;\n }\n if (slashedProtocol[lowerProto] && this.hostname && !this.pathname) {\n this.pathname = \"\";\n }\n return this;\n};\nUrl.prototype.parseHost = function(host) {\n let port = portPattern.exec(host);\n if (port) {\n port = port[0];\n if (port !== \":\") {\n this.port = port.substr(1);\n }\n host = host.substr(0, host.length - port.length);\n }\n if (host) {\n this.hostname = host;\n }\n};\nvar parse_default = urlParse;\n\n// node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/index.mjs\nvar uc_exports = {};\n__export(uc_exports, {\n Any: () => regex_default,\n Cc: () => regex_default2,\n Cf: () => regex_default3,\n P: () => regex_default4,\n S: () => regex_default5,\n Z: () => regex_default6\n});\n\n// node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/properties/Any/regex.mjs\nvar regex_default = /[\\0-\\uD7FF\\uE000-\\uFFFF]|[\\uD800-\\uDBFF][\\uDC00-\\uDFFF]|[\\uD800-\\uDBFF](?![\\uDC00-\\uDFFF])|(?:[^\\uD800-\\uDBFF]|^)[\\uDC00-\\uDFFF]/;\n\n// node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/Cc/regex.mjs\nvar regex_default2 = /[\\0-\\x1F\\x7F-\\x9F]/;\n\n// node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/Cf/regex.mjs\nvar regex_default3 = /[\\xAD\\u0600-\\u0605\\u061C\\u06DD\\u070F\\u0890\\u0891\\u08E2\\u180E\\u200B-\\u200F\\u202A-\\u202E\\u2060-\\u2064\\u2066-\\u206F\\uFEFF\\uFFF9-\\uFFFB]|\\uD804[\\uDCBD\\uDCCD]|\\uD80D[\\uDC30-\\uDC3F]|\\uD82F[\\uDCA0-\\uDCA3]|\\uD834[\\uDD73-\\uDD7A]|\\uDB40[\\uDC01\\uDC20-\\uDC7F]/;\n\n// node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/P/regex.mjs\nvar regex_default4 = /[!-#%-\\*,-\\/:;\\?@\\[-\\]_\\{\\}\\xA1\\xA7\\xAB\\xB6\\xB7\\xBB\\xBF\\u037E\\u0387\\u055A-\\u055F\\u0589\\u058A\\u05BE\\u05C0\\u05C3\\u05C6\\u05F3\\u05F4\\u0609\\u060A\\u060C\\u060D\\u061B\\u061D-\\u061F\\u066A-\\u066D\\u06D4\\u0700-\\u070D\\u07F7-\\u07F9\\u0830-\\u083E\\u085E\\u0964\\u0965\\u0970\\u09FD\\u0A76\\u0AF0\\u0C77\\u0C84\\u0DF4\\u0E4F\\u0E5A\\u0E5B\\u0F04-\\u0F12\\u0F14\\u0F3A-\\u0F3D\\u0F85\\u0FD0-\\u0FD4\\u0FD9\\u0FDA\\u104A-\\u104F\\u10FB\\u1360-\\u1368\\u1400\\u166E\\u169B\\u169C\\u16EB-\\u16ED\\u1735\\u1736\\u17D4-\\u17D6\\u17D8-\\u17DA\\u1800-\\u180A\\u1944\\u1945\\u1A1E\\u1A1F\\u1AA0-\\u1AA6\\u1AA8-\\u1AAD\\u1B5A-\\u1B60\\u1B7D\\u1B7E\\u1BFC-\\u1BFF\\u1C3B-\\u1C3F\\u1C7E\\u1C7F\\u1CC0-\\u1CC7\\u1CD3\\u2010-\\u2027\\u2030-\\u2043\\u2045-\\u2051\\u2053-\\u205E\\u207D\\u207E\\u208D\\u208E\\u2308-\\u230B\\u2329\\u232A\\u2768-\\u2775\\u27C5\\u27C6\\u27E6-\\u27EF\\u2983-\\u2998\\u29D8-\\u29DB\\u29FC\\u29FD\\u2CF9-\\u2CFC\\u2CFE\\u2CFF\\u2D70\\u2E00-\\u2E2E\\u2E30-\\u2E4F\\u2E52-\\u2E5D\\u3001-\\u3003\\u3008-\\u3011\\u3014-\\u301F\\u3030\\u303D\\u30A0\\u30FB\\uA4FE\\uA4FF\\uA60D-\\uA60F\\uA673\\uA67E\\uA6F2-\\uA6F7\\uA874-\\uA877\\uA8CE\\uA8CF\\uA8F8-\\uA8FA\\uA8FC\\uA92E\\uA92F\\uA95F\\uA9C1-\\uA9CD\\uA9DE\\uA9DF\\uAA5C-\\uAA5F\\uAADE\\uAADF\\uAAF0\\uAAF1\\uABEB\\uFD3E\\uFD3F\\uFE10-\\uFE19\\uFE30-\\uFE52\\uFE54-\\uFE61\\uFE63\\uFE68\\uFE6A\\uFE6B\\uFF01-\\uFF03\\uFF05-\\uFF0A\\uFF0C-\\uFF0F\\uFF1A\\uFF1B\\uFF1F\\uFF20\\uFF3B-\\uFF3D\\uFF3F\\uFF5B\\uFF5D\\uFF5F-\\uFF65]|\\uD800[\\uDD00-\\uDD02\\uDF9F\\uDFD0]|\\uD801\\uDD6F|\\uD802[\\uDC57\\uDD1F\\uDD3F\\uDE50-\\uDE58\\uDE7F\\uDEF0-\\uDEF6\\uDF39-\\uDF3F\\uDF99-\\uDF9C]|\\uD803[\\uDEAD\\uDF55-\\uDF59\\uDF86-\\uDF89]|\\uD804[\\uDC47-\\uDC4D\\uDCBB\\uDCBC\\uDCBE-\\uDCC1\\uDD40-\\uDD43\\uDD74\\uDD75\\uDDC5-\\uDDC8\\uDDCD\\uDDDB\\uDDDD-\\uDDDF\\uDE38-\\uDE3D\\uDEA9]|\\uD805[\\uDC4B-\\uDC4F\\uDC5A\\uDC5B\\uDC5D\\uDCC6\\uDDC1-\\uDDD7\\uDE41-\\uDE43\\uDE60-\\uDE6C\\uDEB9\\uDF3C-\\uDF3E]|\\uD806[\\uDC3B\\uDD44-\\uDD46\\uDDE2\\uDE3F-\\uDE46\\uDE9A-\\uDE9C\\uDE9E-\\uDEA2\\uDF00-\\uDF09]|\\uD807[\\uDC41-\\uDC45\\uDC70\\uDC71\\uDEF7\\uDEF8\\uDF43-\\uDF4F\\uDFFF]|\\uD809[\\uDC70-\\uDC74]|\\uD80B[\\uDFF1\\uDFF2]|\\uD81A[\\uDE6E\\uDE6F\\uDEF5\\uDF37-\\uDF3B\\uDF44]|\\uD81B[\\uDE97-\\uDE9A\\uDFE2]|\\uD82F\\uDC9F|\\uD836[\\uDE87-\\uDE8B]|\\uD83A[\\uDD5E\\uDD5F]/;\n\n// node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/S/regex.mjs\nvar regex_default5 = /[\\$\\+<->\\^`\\|~\\xA2-\\xA6\\xA8\\xA9\\xAC\\xAE-\\xB1\\xB4\\xB8\\xD7\\xF7\\u02C2-\\u02C5\\u02D2-\\u02DF\\u02E5-\\u02EB\\u02ED\\u02EF-\\u02FF\\u0375\\u0384\\u0385\\u03F6\\u0482\\u058D-\\u058F\\u0606-\\u0608\\u060B\\u060E\\u060F\\u06DE\\u06E9\\u06FD\\u06FE\\u07F6\\u07FE\\u07FF\\u0888\\u09F2\\u09F3\\u09FA\\u09FB\\u0AF1\\u0B70\\u0BF3-\\u0BFA\\u0C7F\\u0D4F\\u0D79\\u0E3F\\u0F01-\\u0F03\\u0F13\\u0F15-\\u0F17\\u0F1A-\\u0F1F\\u0F34\\u0F36\\u0F38\\u0FBE-\\u0FC5\\u0FC7-\\u0FCC\\u0FCE\\u0FCF\\u0FD5-\\u0FD8\\u109E\\u109F\\u1390-\\u1399\\u166D\\u17DB\\u1940\\u19DE-\\u19FF\\u1B61-\\u1B6A\\u1B74-\\u1B7C\\u1FBD\\u1FBF-\\u1FC1\\u1FCD-\\u1FCF\\u1FDD-\\u1FDF\\u1FED-\\u1FEF\\u1FFD\\u1FFE\\u2044\\u2052\\u207A-\\u207C\\u208A-\\u208C\\u20A0-\\u20C0\\u2100\\u2101\\u2103-\\u2106\\u2108\\u2109\\u2114\\u2116-\\u2118\\u211E-\\u2123\\u2125\\u2127\\u2129\\u212E\\u213A\\u213B\\u2140-\\u2144\\u214A-\\u214D\\u214F\\u218A\\u218B\\u2190-\\u2307\\u230C-\\u2328\\u232B-\\u2426\\u2440-\\u244A\\u249C-\\u24E9\\u2500-\\u2767\\u2794-\\u27C4\\u27C7-\\u27E5\\u27F0-\\u2982\\u2999-\\u29D7\\u29DC-\\u29FB\\u29FE-\\u2B73\\u2B76-\\u2B95\\u2B97-\\u2BFF\\u2CE5-\\u2CEA\\u2E50\\u2E51\\u2E80-\\u2E99\\u2E9B-\\u2EF3\\u2F00-\\u2FD5\\u2FF0-\\u2FFF\\u3004\\u3012\\u3013\\u3020\\u3036\\u3037\\u303E\\u303F\\u309B\\u309C\\u3190\\u3191\\u3196-\\u319F\\u31C0-\\u31E3\\u31EF\\u3200-\\u321E\\u322A-\\u3247\\u3250\\u3260-\\u327F\\u328A-\\u32B0\\u32C0-\\u33FF\\u4DC0-\\u4DFF\\uA490-\\uA4C6\\uA700-\\uA716\\uA720\\uA721\\uA789\\uA78A\\uA828-\\uA82B\\uA836-\\uA839\\uAA77-\\uAA79\\uAB5B\\uAB6A\\uAB6B\\uFB29\\uFBB2-\\uFBC2\\uFD40-\\uFD4F\\uFDCF\\uFDFC-\\uFDFF\\uFE62\\uFE64-\\uFE66\\uFE69\\uFF04\\uFF0B\\uFF1C-\\uFF1E\\uFF3E\\uFF40\\uFF5C\\uFF5E\\uFFE0-\\uFFE6\\uFFE8-\\uFFEE\\uFFFC\\uFFFD]|\\uD800[\\uDD37-\\uDD3F\\uDD79-\\uDD89\\uDD8C-\\uDD8E\\uDD90-\\uDD9C\\uDDA0\\uDDD0-\\uDDFC]|\\uD802[\\uDC77\\uDC78\\uDEC8]|\\uD805\\uDF3F|\\uD807[\\uDFD5-\\uDFF1]|\\uD81A[\\uDF3C-\\uDF3F\\uDF45]|\\uD82F\\uDC9C|\\uD833[\\uDF50-\\uDFC3]|\\uD834[\\uDC00-\\uDCF5\\uDD00-\\uDD26\\uDD29-\\uDD64\\uDD6A-\\uDD6C\\uDD83\\uDD84\\uDD8C-\\uDDA9\\uDDAE-\\uDDEA\\uDE00-\\uDE41\\uDE45\\uDF00-\\uDF56]|\\uD835[\\uDEC1\\uDEDB\\uDEFB\\uDF15\\uDF35\\uDF4F\\uDF6F\\uDF89\\uDFA9\\uDFC3]|\\uD836[\\uDC00-\\uDDFF\\uDE37-\\uDE3A\\uDE6D-\\uDE74\\uDE76-\\uDE83\\uDE85\\uDE86]|\\uD838[\\uDD4F\\uDEFF]|\\uD83B[\\uDCAC\\uDCB0\\uDD2E\\uDEF0\\uDEF1]|\\uD83C[\\uDC00-\\uDC2B\\uDC30-\\uDC93\\uDCA0-\\uDCAE\\uDCB1-\\uDCBF\\uDCC1-\\uDCCF\\uDCD1-\\uDCF5\\uDD0D-\\uDDAD\\uDDE6-\\uDE02\\uDE10-\\uDE3B\\uDE40-\\uDE48\\uDE50\\uDE51\\uDE60-\\uDE65\\uDF00-\\uDFFF]|\\uD83D[\\uDC00-\\uDED7\\uDEDC-\\uDEEC\\uDEF0-\\uDEFC\\uDF00-\\uDF76\\uDF7B-\\uDFD9\\uDFE0-\\uDFEB\\uDFF0]|\\uD83E[\\uDC00-\\uDC0B\\uDC10-\\uDC47\\uDC50-\\uDC59\\uDC60-\\uDC87\\uDC90-\\uDCAD\\uDCB0\\uDCB1\\uDD00-\\uDE53\\uDE60-\\uDE6D\\uDE70-\\uDE7C\\uDE80-\\uDE88\\uDE90-\\uDEBD\\uDEBF-\\uDEC5\\uDECE-\\uDEDB\\uDEE0-\\uDEE8\\uDEF0-\\uDEF8\\uDF00-\\uDF92\\uDF94-\\uDFCA]/;\n\n// node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/Z/regex.mjs\nvar regex_default6 = /[ \\xA0\\u1680\\u2000-\\u200A\\u2028\\u2029\\u202F\\u205F\\u3000]/;\n\n// node_modules/.pnpm/entities@4.5.0/node_modules/entities/lib/esm/generated/decode-data-html.js\nvar decode_data_html_default = new Uint16Array(\n // prettier-ignore\n 'ᵁ<Õıʊҝջאٵ۞ޢߖࠏ੊ઑඡ๭༉༦჊ረዡᐕᒝᓃᓟᔥ\\0\\0\\0\\0\\0\\0ᕫᛍᦍᰒᷝ὾⁠↰⊍⏀⏻⑂⠤⤒ⴈ⹈⿎〖㊺㘹㞬㣾㨨㩱㫠㬮ࠀEMabcfglmnoprstu\\\\bfms„‹•˜¦³¹ÈÏlig耻Æ䃆P耻&䀦cute耻Á䃁reve;䄂Āiyx}rc耻Â䃂;䐐r;쀀𝔄rave耻À䃀pha;䎑acr;䄀d;橓Āgp¡on;䄄f;쀀𝔸plyFunction;恡ing耻Å䃅Ācs¾Ãr;쀀𝒜ign;扔ilde耻Ã䃃ml耻Ä䃄ЀaceforsuåûþėĜĢħĪĀcrêòkslash;或Ŷöø;櫧ed;挆y;䐑ƀcrtąċĔause;戵noullis;愬a;䎒r;쀀𝔅pf;쀀𝔹eve;䋘còēmpeq;扎܀HOacdefhilorsuōőŖƀƞƢƵƷƺǜȕɳɸɾcy;䐧PY耻©䂩ƀcpyŝŢźute;䄆Ā;iŧŨ拒talDifferentialD;慅leys;愭ȀaeioƉƎƔƘron;䄌dil耻Ç䃇rc;䄈nint;戰ot;䄊ĀdnƧƭilla;䂸terDot;䂷òſi;䎧rcleȀDMPTLJNjǑǖot;抙inus;抖lus;投imes;抗oĀcsǢǸkwiseContourIntegral;戲eCurlyĀDQȃȏoubleQuote;思uote;怙ȀlnpuȞȨɇɕonĀ;eȥȦ户;橴ƀgitȯȶȺruent;扡nt;戯ourIntegral;戮ĀfrɌɎ;愂oduct;成nterClockwiseContourIntegral;戳oss;樯cr;쀀𝒞pĀ;Cʄʅ拓ap;才րDJSZacefiosʠʬʰʴʸˋ˗ˡ˦̳ҍĀ;oŹʥtrahd;椑cy;䐂cy;䐅cy;䐏ƀgrsʿ˄ˇger;怡r;憡hv;櫤Āayː˕ron;䄎;䐔lĀ;t˝˞戇a;䎔r;쀀𝔇Āaf˫̧Ācm˰̢riticalȀADGT̖̜̀̆cute;䂴oŴ̋̍;䋙bleAcute;䋝rave;䁠ilde;䋜ond;拄ferentialD;慆Ѱ̽\\0\\0\\0͔͂\\0Ѕf;쀀𝔻ƀ;DE͈͉͍䂨ot;惜qual;扐blèCDLRUVͣͲ΂ϏϢϸontourIntegraìȹoɴ͹\\0\\0ͻ»͉nArrow;懓Āeo·ΤftƀARTΐΖΡrrow;懐ightArrow;懔eåˊngĀLRΫτeftĀARγιrrow;柸ightArrow;柺ightArrow;柹ightĀATϘϞrrow;懒ee;抨pɁϩ\\0\\0ϯrrow;懑ownArrow;懕erticalBar;戥ǹABLRTaВЪаўѿͼrrowƀ;BUНОТ憓ar;椓pArrow;懵reve;䌑eft˒к\\0ц\\0ѐightVector;楐eeVector;楞ectorĀ;Bљњ憽ar;楖ightǔѧ\\0ѱeeVector;楟ectorĀ;BѺѻ懁ar;楗eeĀ;A҆҇护rrow;憧ĀctҒҗr;쀀𝒟rok;䄐ࠀNTacdfglmopqstuxҽӀӄӋӞӢӧӮӵԡԯԶՒ՝ՠեG;䅊H耻Ð䃐cute耻É䃉ƀaiyӒӗӜron;䄚rc耻Ê䃊;䐭ot;䄖r;쀀𝔈rave耻È䃈ement;戈ĀapӺӾcr;䄒tyɓԆ\\0\\0ԒmallSquare;旻erySmallSquare;斫ĀgpԦԪon;䄘f;쀀𝔼silon;䎕uĀaiԼՉlĀ;TՂՃ橵ilde;扂librium;懌Āci՗՚r;愰m;橳a;䎗ml耻Ë䃋Āipժկsts;戃onentialE;慇ʀcfiosօֈ֍ֲ׌y;䐤r;쀀𝔉lledɓ֗\\0\\0֣mallSquare;旼erySmallSquare;斪Ͱֺ\\0ֿ\\0\\0ׄf;쀀𝔽All;戀riertrf;愱cò׋؀JTabcdfgorstר׬ׯ׺؀ؒؖ؛؝أ٬ٲcy;䐃耻>䀾mmaĀ;d׷׸䎓;䏜reve;䄞ƀeiy؇،ؐdil;䄢rc;䄜;䐓ot;䄠r;쀀𝔊;拙pf;쀀𝔾eater̀EFGLSTصلَٖٛ٦qualĀ;Lؾؿ扥ess;招ullEqual;执reater;檢ess;扷lantEqual;橾ilde;扳cr;쀀𝒢;扫ЀAacfiosuڅڋږڛڞڪھۊRDcy;䐪Āctڐڔek;䋇;䁞irc;䄤r;愌lbertSpace;愋ǰگ\\0ڲf;愍izontalLine;攀Āctۃۅòکrok;䄦mpńېۘownHumðįqual;扏܀EJOacdfgmnostuۺ۾܃܇܎ܚܞܡܨ݄ݸދޏޕcy;䐕lig;䄲cy;䐁cute耻Í䃍Āiyܓܘrc耻Î䃎;䐘ot;䄰r;愑rave耻Ì䃌ƀ;apܠܯܿĀcgܴܷr;䄪inaryI;慈lieóϝǴ݉\\0ݢĀ;eݍݎ戬Āgrݓݘral;戫section;拂isibleĀCTݬݲomma;恣imes;恢ƀgptݿރވon;䄮f;쀀𝕀a;䎙cr;愐ilde;䄨ǫޚ\\0ޞcy;䐆l耻Ï䃏ʀcfosuެ޷޼߂ߐĀiyޱ޵rc;䄴;䐙r;쀀𝔍pf;쀀𝕁ǣ߇\\0ߌr;쀀𝒥rcy;䐈kcy;䐄΀HJacfosߤߨ߽߬߱ࠂࠈcy;䐥cy;䐌ppa;䎚Āey߶߻dil;䄶;䐚r;쀀𝔎pf;쀀𝕂cr;쀀𝒦րJTaceflmostࠥࠩࠬࡐࡣ঳সে্਷ੇcy;䐉耻<䀼ʀcmnpr࠷࠼ࡁࡄࡍute;䄹bda;䎛g;柪lacetrf;愒r;憞ƀaeyࡗ࡜ࡡron;䄽dil;䄻;䐛Āfsࡨ॰tԀACDFRTUVarࡾࢩࢱࣦ࣠ࣼयज़ΐ४Ānrࢃ࢏gleBracket;柨rowƀ;BR࢙࢚࢞憐ar;懤ightArrow;懆eiling;挈oǵࢷ\\0ࣃbleBracket;柦nǔࣈ\\0࣒eeVector;楡ectorĀ;Bࣛࣜ懃ar;楙loor;挊ightĀAV࣯ࣵrrow;憔ector;楎Āerँगeƀ;AVउऊऐ抣rrow;憤ector;楚iangleƀ;BEतथऩ抲ar;槏qual;抴pƀDTVषूौownVector;楑eeVector;楠ectorĀ;Bॖॗ憿ar;楘ectorĀ;B॥०憼ar;楒ightáΜs̀EFGLSTॾঋকঝঢভqualGreater;拚ullEqual;扦reater;扶ess;檡lantEqual;橽ilde;扲r;쀀𝔏Ā;eঽা拘ftarrow;懚idot;䄿ƀnpw৔ਖਛgȀLRlr৞৷ਂਐeftĀAR০৬rrow;柵ightArrow;柷ightArrow;柶eftĀarγਊightáοightáϊf;쀀𝕃erĀLRਢਬeftArrow;憙ightArrow;憘ƀchtਾੀੂòࡌ;憰rok;䅁;扪Ѐacefiosuਗ਼੝੠੷੼અઋ઎p;椅y;䐜Ādl੥੯iumSpace;恟lintrf;愳r;쀀𝔐nusPlus;戓pf;쀀𝕄cò੶;䎜ҀJacefostuણધભીଔଙඑ඗ඞcy;䐊cute;䅃ƀaey઴હાron;䅇dil;䅅;䐝ƀgswે૰଎ativeƀMTV૓૟૨ediumSpace;怋hiĀcn૦૘ë૙eryThiî૙tedĀGL૸ଆreaterGreateòٳessLesóੈLine;䀊r;쀀𝔑ȀBnptଢନଷ଺reak;恠BreakingSpace;䂠f;愕ڀ;CDEGHLNPRSTV୕ୖ୪୼஡௫ఄ౞಄ದ೘ൡඅ櫬Āou୛୤ngruent;扢pCap;扭oubleVerticalBar;戦ƀlqxஃஊ஛ement;戉ualĀ;Tஒஓ扠ilde;쀀≂̸ists;戄reater΀;EFGLSTஶஷ஽௉௓௘௥扯qual;扱ullEqual;쀀≧̸reater;쀀≫̸ess;批lantEqual;쀀⩾̸ilde;扵umpń௲௽ownHump;쀀≎̸qual;쀀≏̸eĀfsఊధtTriangleƀ;BEచఛడ拪ar;쀀⧏̸qual;括s̀;EGLSTవశ఼ౄోౘ扮qual;扰reater;扸ess;쀀≪̸lantEqual;쀀⩽̸ilde;扴estedĀGL౨౹reaterGreater;쀀⪢̸essLess;쀀⪡̸recedesƀ;ESಒಓಛ技qual;쀀⪯̸lantEqual;拠ĀeiಫಹverseElement;戌ghtTriangleƀ;BEೋೌ೒拫ar;쀀⧐̸qual;拭ĀquೝഌuareSuĀbp೨೹setĀ;E೰ೳ쀀⊏̸qual;拢ersetĀ;Eഃആ쀀⊐̸qual;拣ƀbcpഓതൎsetĀ;Eഛഞ쀀⊂⃒qual;抈ceedsȀ;ESTലള഻െ抁qual;쀀⪰̸lantEqual;拡ilde;쀀≿̸ersetĀ;E൘൛쀀⊃⃒qual;抉ildeȀ;EFT൮൯൵ൿ扁qual;扄ullEqual;扇ilde;扉erticalBar;戤cr;쀀𝒩ilde耻Ñ䃑;䎝܀Eacdfgmoprstuvලෂ෉෕ෛ෠෧෼ขภยา฿ไlig;䅒cute耻Ó䃓Āiy෎ීrc耻Ô䃔;䐞blac;䅐r;쀀𝔒rave耻Ò䃒ƀaei෮ෲ෶cr;䅌ga;䎩cron;䎟pf;쀀𝕆enCurlyĀDQฎบoubleQuote;怜uote;怘;橔Āclวฬr;쀀𝒪ash耻Ø䃘iŬื฼de耻Õ䃕es;樷ml耻Ö䃖erĀBP๋๠Āar๐๓r;怾acĀek๚๜;揞et;掴arenthesis;揜Ҁacfhilors๿ງຊຏຒດຝະ໼rtialD;戂y;䐟r;쀀𝔓i;䎦;䎠usMinus;䂱Āipຢອncareplanåڝf;愙Ȁ;eio຺ູ໠໤檻cedesȀ;EST່້໏໚扺qual;檯lantEqual;扼ilde;找me;怳Ādp໩໮uct;戏ortionĀ;aȥ໹l;戝Āci༁༆r;쀀𝒫;䎨ȀUfos༑༖༛༟OT耻\"䀢r;쀀𝔔pf;愚cr;쀀𝒬؀BEacefhiorsu༾གྷཇའཱིྦྷྪྭ႖ႩႴႾarr;椐G耻®䂮ƀcnrཎནབute;䅔g;柫rĀ;tཛྷཝ憠l;椖ƀaeyཧཬཱron;䅘dil;䅖;䐠Ā;vླྀཹ愜erseĀEUྂྙĀlq྇ྎement;戋uilibrium;懋pEquilibrium;楯r»ཹo;䎡ghtЀACDFTUVa࿁࿫࿳ဢဨၛႇϘĀnr࿆࿒gleBracket;柩rowƀ;BL࿜࿝࿡憒ar;懥eftArrow;懄eiling;按oǵ࿹\\0စbleBracket;柧nǔည\\0နeeVector;楝ectorĀ;Bဝသ懂ar;楕loor;挋Āerိ၃eƀ;AVဵံြ抢rrow;憦ector;楛iangleƀ;BEၐၑၕ抳ar;槐qual;抵pƀDTVၣၮၸownVector;楏eeVector;楜ectorĀ;Bႂႃ憾ar;楔ectorĀ;B႑႒懀ar;楓Āpuႛ႞f;愝ndImplies;楰ightarrow;懛ĀchႹႼr;愛;憱leDelayed;槴ڀHOacfhimoqstuფჱჷჽᄙᄞᅑᅖᅡᅧᆵᆻᆿĀCcჩხHcy;䐩y;䐨FTcy;䐬cute;䅚ʀ;aeiyᄈᄉᄎᄓᄗ檼ron;䅠dil;䅞rc;䅜;䐡r;쀀𝔖ortȀDLRUᄪᄴᄾᅉownArrow»ОeftArrow»࢚ightArrow»࿝pArrow;憑gma;䎣allCircle;战pf;쀀𝕊ɲᅭ\\0\\0ᅰt;戚areȀ;ISUᅻᅼᆉᆯ斡ntersection;抓uĀbpᆏᆞsetĀ;Eᆗᆘ抏qual;抑ersetĀ;Eᆨᆩ抐qual;抒nion;抔cr;쀀𝒮ar;拆ȀbcmpᇈᇛሉላĀ;sᇍᇎ拐etĀ;Eᇍᇕqual;抆ĀchᇠህeedsȀ;ESTᇭᇮᇴᇿ扻qual;檰lantEqual;扽ilde;承Tháྌ;我ƀ;esሒሓሣ拑rsetĀ;Eሜም抃qual;抇et»ሓրHRSacfhiorsሾቄ቉ቕ቞ቱቶኟዂወዑORN耻Þ䃞ADE;愢ĀHc቎ቒcy;䐋y;䐦Ābuቚቜ;䀉;䎤ƀaeyብቪቯron;䅤dil;䅢;䐢r;쀀𝔗Āeiቻ኉Dzኀ\\0ኇefore;戴a;䎘Ācn኎ኘkSpace;쀀  Space;怉ldeȀ;EFTካኬኲኼ戼qual;扃ullEqual;扅ilde;扈pf;쀀𝕋ipleDot;惛Āctዖዛr;쀀𝒯rok;䅦ૡዷጎጚጦ\\0ጬጱ\\0\\0\\0\\0\\0ጸጽ፷ᎅ\\0᏿ᐄᐊᐐĀcrዻጁute耻Ú䃚rĀ;oጇገ憟cir;楉rǣጓ\\0጖y;䐎ve;䅬Āiyጞጣrc耻Û䃛;䐣blac;䅰r;쀀𝔘rave耻Ù䃙acr;䅪Ādiፁ፩erĀBPፈ፝Āarፍፐr;䁟acĀekፗፙ;揟et;掵arenthesis;揝onĀ;P፰፱拃lus;抎Āgp፻፿on;䅲f;쀀𝕌ЀADETadps᎕ᎮᎸᏄϨᏒᏗᏳrrowƀ;BDᅐᎠᎤar;椒ownArrow;懅ownArrow;憕quilibrium;楮eeĀ;AᏋᏌ报rrow;憥ownáϳerĀLRᏞᏨeftArrow;憖ightArrow;憗iĀ;lᏹᏺ䏒on;䎥ing;䅮cr;쀀𝒰ilde;䅨ml耻Ü䃜ҀDbcdefosvᐧᐬᐰᐳᐾᒅᒊᒐᒖash;披ar;櫫y;䐒ashĀ;lᐻᐼ抩;櫦Āerᑃᑅ;拁ƀbtyᑌᑐᑺar;怖Ā;iᑏᑕcalȀBLSTᑡᑥᑪᑴar;戣ine;䁼eparator;杘ilde;所ThinSpace;怊r;쀀𝔙pf;쀀𝕍cr;쀀𝒱dash;抪ʀcefosᒧᒬᒱᒶᒼirc;䅴dge;拀r;쀀𝔚pf;쀀𝕎cr;쀀𝒲Ȁfiosᓋᓐᓒᓘr;쀀𝔛;䎞pf;쀀𝕏cr;쀀𝒳ҀAIUacfosuᓱᓵᓹᓽᔄᔏᔔᔚᔠcy;䐯cy;䐇cy;䐮cute耻Ý䃝Āiyᔉᔍrc;䅶;䐫r;쀀𝔜pf;쀀𝕐cr;쀀𝒴ml;䅸ЀHacdefosᔵᔹᔿᕋᕏᕝᕠᕤcy;䐖cute;䅹Āayᕄᕉron;䅽;䐗ot;䅻Dzᕔ\\0ᕛoWidtè૙a;䎖r;愨pf;愤cr;쀀𝒵௡ᖃᖊᖐ\\0ᖰᖶᖿ\\0\\0\\0\\0ᗆᗛᗫᙟ᙭\\0ᚕ᚛ᚲᚹ\\0ᚾcute耻á䃡reve;䄃̀;Ediuyᖜᖝᖡᖣᖨᖭ戾;쀀∾̳;房rc耻â䃢te肻´̆;䐰lig耻æ䃦Ā;r²ᖺ;쀀𝔞rave耻à䃠ĀepᗊᗖĀfpᗏᗔsym;愵èᗓha;䎱ĀapᗟcĀclᗤᗧr;䄁g;樿ɤᗰ\\0\\0ᘊʀ;adsvᗺᗻᗿᘁᘇ戧nd;橕;橜lope;橘;橚΀;elmrszᘘᘙᘛᘞᘿᙏᙙ戠;榤e»ᘙsdĀ;aᘥᘦ戡ѡᘰᘲᘴᘶᘸᘺᘼᘾ;榨;榩;榪;榫;榬;榭;榮;榯tĀ;vᙅᙆ戟bĀ;dᙌᙍ抾;榝Āptᙔᙗh;戢»¹arr;捼Āgpᙣᙧon;䄅f;쀀𝕒΀;Eaeiop዁ᙻᙽᚂᚄᚇᚊ;橰cir;橯;扊d;手s;䀧roxĀ;e዁ᚒñᚃing耻å䃥ƀctyᚡᚦᚨr;쀀𝒶;䀪mpĀ;e዁ᚯñʈilde耻ã䃣ml耻ä䃤Āciᛂᛈoninôɲnt;樑ࠀNabcdefiklnoprsu᛭ᛱᜰ᜼ᝃᝈ᝸᝽០៦ᠹᡐᜍ᤽᥈ᥰot;櫭Ācrᛶ᜞kȀcepsᜀᜅᜍᜓong;扌psilon;䏶rime;怵imĀ;e᜚᜛戽q;拍Ŷᜢᜦee;抽edĀ;gᜬᜭ挅e»ᜭrkĀ;t፜᜷brk;掶Āoyᜁᝁ;䐱quo;怞ʀcmprtᝓ᝛ᝡᝤᝨausĀ;eĊĉptyv;榰séᜌnoõēƀahwᝯ᝱ᝳ;䎲;愶een;扬r;쀀𝔟g΀costuvwឍឝឳេ៕៛៞ƀaiuបពរðݠrc;旯p»፱ƀdptឤឨឭot;樀lus;樁imes;樂ɱឹ\\0\\0ើcup;樆ar;昅riangleĀdu៍្own;施p;斳plus;樄eåᑄåᒭarow;植ƀako៭ᠦᠵĀcn៲ᠣkƀlst៺֫᠂ozenge;槫riangleȀ;dlr᠒᠓᠘᠝斴own;斾eft;旂ight;斸k;搣Ʊᠫ\\0ᠳƲᠯ\\0ᠱ;斒;斑4;斓ck;斈ĀeoᠾᡍĀ;qᡃᡆ쀀=⃥uiv;쀀≡⃥t;挐Ȁptwxᡙᡞᡧᡬf;쀀𝕓Ā;tᏋᡣom»Ꮜtie;拈؀DHUVbdhmptuvᢅᢖᢪᢻᣗᣛᣬ᣿ᤅᤊᤐᤡȀLRlrᢎᢐᢒᢔ;敗;敔;敖;敓ʀ;DUduᢡᢢᢤᢦᢨ敐;敦;敩;敤;敧ȀLRlrᢳᢵᢷᢹ;敝;敚;敜;教΀;HLRhlrᣊᣋᣍᣏᣑᣓᣕ救;敬;散;敠;敫;敢;敟ox;槉ȀLRlrᣤᣦᣨᣪ;敕;敒;攐;攌ʀ;DUduڽ᣷᣹᣻᣽;敥;敨;攬;攴inus;抟lus;択imes;抠ȀLRlrᤙᤛᤝ᤟;敛;敘;攘;攔΀;HLRhlrᤰᤱᤳᤵᤷ᤻᤹攂;敪;敡;敞;攼;攤;攜Āevģ᥂bar耻¦䂦Ȁceioᥑᥖᥚᥠr;쀀𝒷mi;恏mĀ;e᜚᜜lƀ;bhᥨᥩᥫ䁜;槅sub;柈Ŭᥴ᥾lĀ;e᥹᥺怢t»᥺pƀ;Eeįᦅᦇ;檮Ā;qۜۛೡᦧ\\0᧨ᨑᨕᨲ\\0ᨷᩐ\\0\\0᪴\\0\\0᫁\\0\\0ᬡᬮ᭍᭒\\0᯽\\0ᰌƀcpr᦭ᦲ᧝ute;䄇̀;abcdsᦿᧀᧄ᧊᧕᧙戩nd;橄rcup;橉Āau᧏᧒p;橋p;橇ot;橀;쀀∩︀Āeo᧢᧥t;恁îړȀaeiu᧰᧻ᨁᨅǰ᧵\\0᧸s;橍on;䄍dil耻ç䃧rc;䄉psĀ;sᨌᨍ橌m;橐ot;䄋ƀdmnᨛᨠᨦil肻¸ƭptyv;榲t脀¢;eᨭᨮ䂢räƲr;쀀𝔠ƀceiᨽᩀᩍy;䑇ckĀ;mᩇᩈ朓ark»ᩈ;䏇r΀;Ecefms᩟᩠ᩢᩫ᪤᪪᪮旋;槃ƀ;elᩩᩪᩭ䋆q;扗eɡᩴ\\0\\0᪈rrowĀlr᩼᪁eft;憺ight;憻ʀRSacd᪒᪔᪖᪚᪟»ཇ;擈st;抛irc;抚ash;抝nint;樐id;櫯cir;槂ubsĀ;u᪻᪼晣it»᪼ˬ᫇᫔᫺\\0ᬊonĀ;eᫍᫎ䀺Ā;qÇÆɭ᫙\\0\\0᫢aĀ;t᫞᫟䀬;䁀ƀ;fl᫨᫩᫫戁îᅠeĀmx᫱᫶ent»᫩eóɍǧ᫾\\0ᬇĀ;dኻᬂot;橭nôɆƀfryᬐᬔᬗ;쀀𝕔oäɔ脀©;sŕᬝr;愗Āaoᬥᬩrr;憵ss;朗Ācuᬲᬷr;쀀𝒸Ābpᬼ᭄Ā;eᭁᭂ櫏;櫑Ā;eᭉᭊ櫐;櫒dot;拯΀delprvw᭠᭬᭷ᮂᮬᯔ᯹arrĀlr᭨᭪;椸;椵ɰ᭲\\0\\0᭵r;拞c;拟arrĀ;p᭿ᮀ憶;椽̀;bcdosᮏᮐᮖᮡᮥᮨ截rcap;橈Āauᮛᮞp;橆p;橊ot;抍r;橅;쀀∪︀Ȁalrv᮵ᮿᯞᯣrrĀ;mᮼᮽ憷;椼yƀevwᯇᯔᯘqɰᯎ\\0\\0ᯒreã᭳uã᭵ee;拎edge;拏en耻¤䂤earrowĀlrᯮ᯳eft»ᮀight»ᮽeäᯝĀciᰁᰇoninôǷnt;戱lcty;挭ঀAHabcdefhijlorstuwz᰸᰻᰿ᱝᱩᱵᲊᲞᲬᲷ᳻᳿ᴍᵻᶑᶫᶻ᷆᷍rò΁ar;楥Ȁglrs᱈ᱍ᱒᱔ger;怠eth;愸òᄳhĀ;vᱚᱛ怐»ऊūᱡᱧarow;椏aã̕Āayᱮᱳron;䄏;䐴ƀ;ao̲ᱼᲄĀgrʿᲁr;懊tseq;橷ƀglmᲑᲔᲘ耻°䂰ta;䎴ptyv;榱ĀirᲣᲨsht;楿;쀀𝔡arĀlrᲳᲵ»ࣜ»သʀaegsv᳂͸᳖᳜᳠mƀ;oș᳊᳔ndĀ;ș᳑uit;晦amma;䏝in;拲ƀ;io᳧᳨᳸䃷de脀÷;o᳧ᳰntimes;拇nø᳷cy;䑒cɯᴆ\\0\\0ᴊrn;挞op;挍ʀlptuwᴘᴝᴢᵉᵕlar;䀤f;쀀𝕕ʀ;emps̋ᴭᴷᴽᵂqĀ;d͒ᴳot;扑inus;戸lus;戔quare;抡blebarwedgåúnƀadhᄮᵝᵧownarrowóᲃarpoonĀlrᵲᵶefôᲴighôᲶŢᵿᶅkaro÷གɯᶊ\\0\\0ᶎrn;挟op;挌ƀcotᶘᶣᶦĀryᶝᶡ;쀀𝒹;䑕l;槶rok;䄑Ādrᶰᶴot;拱iĀ;fᶺ᠖斿Āah᷀᷃ròЩaòྦangle;榦Āci᷒ᷕy;䑟grarr;柿ऀDacdefglmnopqrstuxḁḉḙḸոḼṉṡṾấắẽỡἪἷὄ὎὚ĀDoḆᴴoôᲉĀcsḎḔute耻é䃩ter;橮ȀaioyḢḧḱḶron;䄛rĀ;cḭḮ扖耻ê䃪lon;払;䑍ot;䄗ĀDrṁṅot;扒;쀀𝔢ƀ;rsṐṑṗ檚ave耻è䃨Ā;dṜṝ檖ot;檘Ȁ;ilsṪṫṲṴ檙nters;揧;愓Ā;dṹṺ檕ot;檗ƀapsẅẉẗcr;䄓tyƀ;svẒẓẕ戅et»ẓpĀ1;ẝẤijạả;怄;怅怃ĀgsẪẬ;䅋p;怂ĀgpẴẸon;䄙f;쀀𝕖ƀalsỄỎỒrĀ;sỊị拕l;槣us;橱iƀ;lvỚớở䎵on»ớ;䏵ȀcsuvỪỳἋἣĀioữḱrc»Ḯɩỹ\\0\\0ỻíՈantĀglἂἆtr»ṝess»Ṻƀaeiἒ἖Ἒls;䀽st;扟vĀ;DȵἠD;橸parsl;槥ĀDaἯἳot;打rr;楱ƀcdiἾὁỸr;愯oô͒ĀahὉὋ;䎷耻ð䃰Āmrὓὗl耻ë䃫o;悬ƀcipὡὤὧl;䀡sôծĀeoὬὴctatioîՙnentialåչৡᾒ\\0ᾞ\\0ᾡᾧ\\0\\0ῆῌ\\0ΐ\\0ῦῪ \\0 ⁚llingdotseñṄy;䑄male;晀ƀilrᾭᾳ῁lig;耀ffiɩᾹ\\0\\0᾽g;耀ffig;耀ffl;쀀𝔣lig;耀filig;쀀fjƀaltῙ῜ῡt;晭ig;耀flns;斱of;䆒ǰ΅\\0ῳf;쀀𝕗ĀakֿῷĀ;vῼ´拔;櫙artint;樍Āao‌⁕Ācs‑⁒ႉ‸⁅⁈\\0⁐β•‥‧‪‬\\0‮耻½䂽;慓耻¼䂼;慕;慙;慛Ƴ‴\\0‶;慔;慖ʴ‾⁁\\0\\0⁃耻¾䂾;慗;慜5;慘ƶ⁌\\0⁎;慚;慝8;慞l;恄wn;挢cr;쀀𝒻ࢀEabcdefgijlnorstv₂₉₟₥₰₴⃰⃵⃺⃿℃ℒℸ̗ℾ⅒↞Ā;lٍ₇;檌ƀcmpₐₕ₝ute;䇵maĀ;dₜ᳚䎳;檆reve;䄟Āiy₪₮rc;䄝;䐳ot;䄡Ȁ;lqsؾق₽⃉ƀ;qsؾٌ⃄lanô٥Ȁ;cdl٥⃒⃥⃕c;檩otĀ;o⃜⃝檀Ā;l⃢⃣檂;檄Ā;e⃪⃭쀀⋛︀s;檔r;쀀𝔤Ā;gٳ؛mel;愷cy;䑓Ȁ;Eajٚℌℎℐ;檒;檥;檤ȀEaesℛℝ℩ℴ;扩pĀ;p℣ℤ檊rox»ℤĀ;q℮ℯ檈Ā;q℮ℛim;拧pf;쀀𝕘Āci⅃ⅆr;愊mƀ;el٫ⅎ⅐;檎;檐茀>;cdlqr׮ⅠⅪⅮⅳⅹĀciⅥⅧ;檧r;橺ot;拗Par;榕uest;橼ʀadelsↄⅪ←ٖ↛ǰ↉\\0↎proø₞r;楸qĀlqؿ↖lesó₈ií٫Āen↣↭rtneqq;쀀≩︀Å↪ԀAabcefkosy⇄⇇⇱⇵⇺∘∝∯≨≽ròΠȀilmr⇐⇔⇗⇛rsðᒄf»․ilôکĀdr⇠⇤cy;䑊ƀ;cwࣴ⇫⇯ir;楈;憭ar;意irc;䄥ƀalr∁∎∓rtsĀ;u∉∊晥it»∊lip;怦con;抹r;쀀𝔥sĀew∣∩arow;椥arow;椦ʀamopr∺∾≃≞≣rr;懿tht;戻kĀlr≉≓eftarrow;憩ightarrow;憪f;쀀𝕙bar;怕ƀclt≯≴≸r;쀀𝒽asè⇴rok;䄧Ābp⊂⊇ull;恃hen»ᱛૡ⊣\\0⊪\\0⊸⋅⋎\\0⋕⋳\\0\\0⋸⌢⍧⍢⍿\\0⎆⎪⎴cute耻í䃭ƀ;iyݱ⊰⊵rc耻î䃮;䐸Ācx⊼⊿y;䐵cl耻¡䂡ĀfrΟ⋉;쀀𝔦rave耻ì䃬Ȁ;inoܾ⋝⋩⋮Āin⋢⋦nt;樌t;戭fin;槜ta;愩lig;䄳ƀaop⋾⌚⌝ƀcgt⌅⌈⌗r;䄫ƀelpܟ⌏⌓inåގarôܠh;䄱f;抷ed;䆵ʀ;cfotӴ⌬⌱⌽⍁are;愅inĀ;t⌸⌹戞ie;槝doô⌙ʀ;celpݗ⍌⍐⍛⍡al;抺Āgr⍕⍙eróᕣã⍍arhk;樗rod;樼Ȁcgpt⍯⍲⍶⍻y;䑑on;䄯f;쀀𝕚a;䎹uest耻¿䂿Āci⎊⎏r;쀀𝒾nʀ;EdsvӴ⎛⎝⎡ӳ;拹ot;拵Ā;v⎦⎧拴;拳Ā;iݷ⎮lde;䄩ǫ⎸\\0⎼cy;䑖l耻ï䃯̀cfmosu⏌⏗⏜⏡⏧⏵Āiy⏑⏕rc;䄵;䐹r;쀀𝔧ath;䈷pf;쀀𝕛ǣ⏬\\0⏱r;쀀𝒿rcy;䑘kcy;䑔Ѐacfghjos␋␖␢␧␭␱␵␻ppaĀ;v␓␔䎺;䏰Āey␛␠dil;䄷;䐺r;쀀𝔨reen;䄸cy;䑅cy;䑜pf;쀀𝕜cr;쀀𝓀஀ABEHabcdefghjlmnoprstuv⑰⒁⒆⒍⒑┎┽╚▀♎♞♥♹♽⚚⚲⛘❝❨➋⟀⠁⠒ƀart⑷⑺⑼rò৆òΕail;椛arr;椎Ā;gঔ⒋;檋ar;楢ॣ⒥\\0⒪\\0⒱\\0\\0\\0\\0\\0⒵Ⓔ\\0ⓆⓈⓍ\\0⓹ute;䄺mptyv;榴raîࡌbda;䎻gƀ;dlࢎⓁⓃ;榑åࢎ;檅uo耻«䂫rЀ;bfhlpst࢙ⓞⓦⓩ⓫⓮⓱⓵Ā;f࢝ⓣs;椟s;椝ë≒p;憫l;椹im;楳l;憢ƀ;ae⓿─┄檫il;椙Ā;s┉┊檭;쀀⪭︀ƀabr┕┙┝rr;椌rk;杲Āak┢┬cĀek┨┪;䁻;䁛Āes┱┳;榋lĀdu┹┻;榏;榍Ȁaeuy╆╋╖╘ron;䄾Ādi═╔il;䄼ìࢰâ┩;䐻Ȁcqrs╣╦╭╽a;椶uoĀ;rนᝆĀdu╲╷har;楧shar;楋h;憲ʀ;fgqs▋▌উ◳◿扤tʀahlrt▘▤▷◂◨rrowĀ;t࢙□aé⓶arpoonĀdu▯▴own»њp»०eftarrows;懇ightƀahs◍◖◞rrowĀ;sࣴࢧarpoonó྘quigarro÷⇰hreetimes;拋ƀ;qs▋ও◺lanôবʀ;cdgsব☊☍☝☨c;檨otĀ;o☔☕橿Ā;r☚☛檁;檃Ā;e☢☥쀀⋚︀s;檓ʀadegs☳☹☽♉♋pproøⓆot;拖qĀgq♃♅ôউgtò⒌ôছiíলƀilr♕࣡♚sht;楼;쀀𝔩Ā;Eজ♣;檑š♩♶rĀdu▲♮Ā;l॥♳;楪lk;斄cy;䑙ʀ;achtੈ⚈⚋⚑⚖rò◁orneòᴈard;楫ri;旺Āio⚟⚤dot;䅀ustĀ;a⚬⚭掰che»⚭ȀEaes⚻⚽⛉⛔;扨pĀ;p⛃⛄檉rox»⛄Ā;q⛎⛏檇Ā;q⛎⚻im;拦Ѐabnoptwz⛩⛴⛷✚✯❁❇❐Ānr⛮⛱g;柬r;懽rëࣁgƀlmr⛿✍✔eftĀar০✇ightá৲apsto;柼ightá৽parrowĀlr✥✩efô⓭ight;憬ƀafl✶✹✽r;榅;쀀𝕝us;樭imes;樴š❋❏st;戗áፎƀ;ef❗❘᠀旊nge»❘arĀ;l❤❥䀨t;榓ʀachmt❳❶❼➅➇ròࢨorneòᶌarĀ;d྘➃;業;怎ri;抿̀achiqt➘➝ੀ➢➮➻quo;怹r;쀀𝓁mƀ;egল➪➬;檍;檏Ābu┪➳oĀ;rฟ➹;怚rok;䅂萀<;cdhilqrࠫ⟒☹⟜⟠⟥⟪⟰Āci⟗⟙;檦r;橹reå◲mes;拉arr;楶uest;橻ĀPi⟵⟹ar;榖ƀ;ef⠀भ᠛旃rĀdu⠇⠍shar;楊har;楦Āen⠗⠡rtneqq;쀀≨︀Å⠞܀Dacdefhilnopsu⡀⡅⢂⢎⢓⢠⢥⢨⣚⣢⣤ઃ⣳⤂Dot;戺Ȁclpr⡎⡒⡣⡽r耻¯䂯Āet⡗⡙;時Ā;e⡞⡟朠se»⡟Ā;sျ⡨toȀ;dluျ⡳⡷⡻owîҌefôएðᏑker;斮Āoy⢇⢌mma;権;䐼ash;怔asuredangle»ᘦr;쀀𝔪o;愧ƀcdn⢯⢴⣉ro耻µ䂵Ȁ;acdᑤ⢽⣀⣄sôᚧir;櫰ot肻·Ƶusƀ;bd⣒ᤃ⣓戒Ā;uᴼ⣘;横ţ⣞⣡p;櫛ò−ðઁĀdp⣩⣮els;抧f;쀀𝕞Āct⣸⣽r;쀀𝓂pos»ᖝƀ;lm⤉⤊⤍䎼timap;抸ఀGLRVabcdefghijlmoprstuvw⥂⥓⥾⦉⦘⧚⧩⨕⨚⩘⩝⪃⪕⪤⪨⬄⬇⭄⭿⮮ⰴⱧⱼ⳩Āgt⥇⥋;쀀⋙̸Ā;v⥐௏쀀≫⃒ƀelt⥚⥲⥶ftĀar⥡⥧rrow;懍ightarrow;懎;쀀⋘̸Ā;v⥻ే쀀≪⃒ightarrow;懏ĀDd⦎⦓ash;抯ash;抮ʀbcnpt⦣⦧⦬⦱⧌la»˞ute;䅄g;쀀∠⃒ʀ;Eiop඄⦼⧀⧅⧈;쀀⩰̸d;쀀≋̸s;䅉roø඄urĀ;a⧓⧔普lĀ;s⧓ସdz⧟\\0⧣p肻 ଷmpĀ;e௹ఀʀaeouy⧴⧾⨃⨐⨓ǰ⧹\\0⧻;橃on;䅈dil;䅆ngĀ;dൾ⨊ot;쀀⩭̸p;橂;䐽ash;怓΀;Aadqsxஒ⨩⨭⨻⩁⩅⩐rr;懗rĀhr⨳⨶k;椤Ā;oᏲᏰot;쀀≐̸uiöୣĀei⩊⩎ar;椨í஘istĀ;s஠டr;쀀𝔫ȀEest௅⩦⩹⩼ƀ;qs஼⩭௡ƀ;qs஼௅⩴lanô௢ií௪Ā;rஶ⪁»ஷƀAap⪊⪍⪑rò⥱rr;憮ar;櫲ƀ;svྍ⪜ྌĀ;d⪡⪢拼;拺cy;䑚΀AEadest⪷⪺⪾⫂⫅⫶⫹rò⥦;쀀≦̸rr;憚r;急Ȁ;fqs఻⫎⫣⫯tĀar⫔⫙rro÷⫁ightarro÷⪐ƀ;qs఻⪺⫪lanôౕĀ;sౕ⫴»శiíౝĀ;rవ⫾iĀ;eచథiäඐĀpt⬌⬑f;쀀𝕟膀¬;in⬙⬚⬶䂬nȀ;Edvஉ⬤⬨⬮;쀀⋹̸ot;쀀⋵̸ǡஉ⬳⬵;拷;拶iĀ;vಸ⬼ǡಸ⭁⭃;拾;拽ƀaor⭋⭣⭩rȀ;ast୻⭕⭚⭟lleì୻l;쀀⫽⃥;쀀∂̸lint;樔ƀ;ceಒ⭰⭳uåಥĀ;cಘ⭸Ā;eಒ⭽ñಘȀAait⮈⮋⮝⮧rò⦈rrƀ;cw⮔⮕⮙憛;쀀⤳̸;쀀↝̸ghtarrow»⮕riĀ;eೋೖ΀chimpqu⮽⯍⯙⬄୸⯤⯯Ȁ;cerല⯆ഷ⯉uå൅;쀀𝓃ortɭ⬅\\0\\0⯖ará⭖mĀ;e൮⯟Ā;q൴൳suĀbp⯫⯭å೸åഋƀbcp⯶ⰑⰙȀ;Ees⯿ⰀഢⰄ抄;쀀⫅̸etĀ;eഛⰋqĀ;qണⰀcĀ;eലⰗñസȀ;EesⰢⰣൟⰧ抅;쀀⫆̸etĀ;e൘ⰮqĀ;qൠⰣȀgilrⰽⰿⱅⱇìௗlde耻ñ䃱çృiangleĀlrⱒⱜeftĀ;eచⱚñదightĀ;eೋⱥñ೗Ā;mⱬⱭ䎽ƀ;esⱴⱵⱹ䀣ro;愖p;怇ҀDHadgilrsⲏⲔⲙⲞⲣⲰⲶⳓⳣash;抭arr;椄p;쀀≍⃒ash;抬ĀetⲨⲬ;쀀≥⃒;쀀>⃒nfin;槞ƀAetⲽⳁⳅrr;椂;쀀≤⃒Ā;rⳊⳍ쀀<⃒ie;쀀⊴⃒ĀAtⳘⳜrr;椃rie;쀀⊵⃒im;쀀∼⃒ƀAan⳰⳴ⴂrr;懖rĀhr⳺⳽k;椣Ā;oᏧᏥear;椧ቓ᪕\\0\\0\\0\\0\\0\\0\\0\\0\\0\\0\\0\\0\\0ⴭ\\0ⴸⵈⵠⵥ⵲ⶄᬇ\\0\\0ⶍⶫ\\0ⷈⷎ\\0ⷜ⸙⸫⸾⹃Ācsⴱ᪗ute耻ó䃳ĀiyⴼⵅrĀ;c᪞ⵂ耻ô䃴;䐾ʀabios᪠ⵒⵗLjⵚlac;䅑v;樸old;榼lig;䅓Ācr⵩⵭ir;榿;쀀𝔬ͯ⵹\\0\\0⵼\\0ⶂn;䋛ave耻ò䃲;槁Ābmⶈ෴ar;榵Ȁacitⶕ⶘ⶥⶨrò᪀Āir⶝ⶠr;榾oss;榻nå๒;槀ƀaeiⶱⶵⶹcr;䅍ga;䏉ƀcdnⷀⷅǍron;䎿;榶pf;쀀𝕠ƀaelⷔ⷗ǒr;榷rp;榹΀;adiosvⷪⷫⷮ⸈⸍⸐⸖戨rò᪆Ȁ;efmⷷⷸ⸂⸅橝rĀ;oⷾⷿ愴f»ⷿ耻ª䂪耻º䂺gof;抶r;橖lope;橗;橛ƀclo⸟⸡⸧ò⸁ash耻ø䃸l;折iŬⸯ⸴de耻õ䃵esĀ;aǛ⸺s;樶ml耻ö䃶bar;挽ૡ⹞\\0⹽\\0⺀⺝\\0⺢⺹\\0\\0⻋ຜ\\0⼓\\0\\0⼫⾼\\0⿈rȀ;astЃ⹧⹲຅脀¶;l⹭⹮䂶leìЃɩ⹸\\0\\0⹻m;櫳;櫽y;䐿rʀcimpt⺋⺏⺓ᡥ⺗nt;䀥od;䀮il;怰enk;怱r;쀀𝔭ƀimo⺨⺰⺴Ā;v⺭⺮䏆;䏕maô੶ne;明ƀ;tv⺿⻀⻈䏀chfork»´;䏖Āau⻏⻟nĀck⻕⻝kĀ;h⇴⻛;愎ö⇴sҀ;abcdemst⻳⻴ᤈ⻹⻽⼄⼆⼊⼎䀫cir;樣ir;樢Āouᵀ⼂;樥;橲n肻±ຝim;樦wo;樧ƀipu⼙⼠⼥ntint;樕f;쀀𝕡nd耻£䂣Ԁ;Eaceinosu່⼿⽁⽄⽇⾁⾉⾒⽾⾶;檳p;檷uå໙Ā;c໎⽌̀;acens່⽙⽟⽦⽨⽾pproø⽃urlyeñ໙ñ໎ƀaes⽯⽶⽺pprox;檹qq;檵im;拨iíໟmeĀ;s⾈ຮ怲ƀEas⽸⾐⽺ð⽵ƀdfp໬⾙⾯ƀals⾠⾥⾪lar;挮ine;挒urf;挓Ā;t໻⾴ï໻rel;抰Āci⿀⿅r;쀀𝓅;䏈ncsp;怈̀fiopsu⿚⋢⿟⿥⿫⿱r;쀀𝔮pf;쀀𝕢rime;恗cr;쀀𝓆ƀaeo⿸〉〓tĀei⿾々rnionóڰnt;樖stĀ;e【】䀿ñἙô༔઀ABHabcdefhilmnoprstux぀けさすムㄎㄫㅇㅢㅲㆎ㈆㈕㈤㈩㉘㉮㉲㊐㊰㊷ƀartぇおがròႳòϝail;検aròᱥar;楤΀cdenqrtとふへみわゔヌĀeuねぱ;쀀∽̱te;䅕iãᅮmptyv;榳gȀ;del࿑らるろ;榒;榥å࿑uo耻»䂻rր;abcfhlpstw࿜ガクシスゼゾダッデナp;極Ā;f࿠ゴs;椠;椳s;椞ë≝ð✮l;楅im;楴l;憣;憝Āaiパフil;椚oĀ;nホボ戶aló༞ƀabrョリヮrò៥rk;杳ĀakンヽcĀekヹ・;䁽;䁝Āes㄂㄄;榌lĀduㄊㄌ;榎;榐Ȁaeuyㄗㄜㄧㄩron;䅙Ādiㄡㄥil;䅗ì࿲âヺ;䑀Ȁclqsㄴㄷㄽㅄa;椷dhar;楩uoĀ;rȎȍh;憳ƀacgㅎㅟངlȀ;ipsླྀㅘㅛႜnåႻarôྩt;断ƀilrㅩဣㅮsht;楽;쀀𝔯ĀaoㅷㆆrĀduㅽㅿ»ѻĀ;l႑ㆄ;楬Ā;vㆋㆌ䏁;䏱ƀgns㆕ㇹㇼht̀ahlrstㆤㆰ㇂㇘㇤㇮rrowĀ;t࿜ㆭaéトarpoonĀduㆻㆿowîㅾp»႒eftĀah㇊㇐rrowó࿪arpoonóՑightarrows;應quigarro÷ニhreetimes;拌g;䋚ingdotseñἲƀahm㈍㈐㈓rò࿪aòՑ;怏oustĀ;a㈞㈟掱che»㈟mid;櫮Ȁabpt㈲㈽㉀㉒Ānr㈷㈺g;柭r;懾rëဃƀafl㉇㉊㉎r;榆;쀀𝕣us;樮imes;樵Āap㉝㉧rĀ;g㉣㉤䀩t;榔olint;樒arò㇣Ȁachq㉻㊀Ⴜ㊅quo;怺r;쀀𝓇Ābu・㊊oĀ;rȔȓƀhir㊗㊛㊠reåㇸmes;拊iȀ;efl㊪ၙᠡ㊫方tri;槎luhar;楨;愞ൡ㋕㋛㋟㌬㌸㍱\\0㍺㎤\\0\\0㏬㏰\\0㐨㑈㑚㒭㒱㓊㓱\\0㘖\\0\\0㘳cute;䅛quï➺Ԁ;Eaceinpsyᇭ㋳㋵㋿㌂㌋㌏㌟㌦㌩;檴ǰ㋺\\0㋼;檸on;䅡uåᇾĀ;dᇳ㌇il;䅟rc;䅝ƀEas㌖㌘㌛;檶p;檺im;择olint;樓iíሄ;䑁otƀ;be㌴ᵇ㌵担;橦΀Aacmstx㍆㍊㍗㍛㍞㍣㍭rr;懘rĀhr㍐㍒ë∨Ā;oਸ਼਴t耻§䂧i;䀻war;椩mĀin㍩ðnuóñt;朶rĀ;o㍶⁕쀀𝔰Ȁacoy㎂㎆㎑㎠rp;景Āhy㎋㎏cy;䑉;䑈rtɭ㎙\\0\\0㎜iäᑤaraì⹯耻­䂭Āgm㎨㎴maƀ;fv㎱㎲㎲䏃;䏂Ѐ;deglnprካ㏅㏉㏎㏖㏞㏡㏦ot;橪Ā;q኱ኰĀ;E㏓㏔檞;檠Ā;E㏛㏜檝;檟e;扆lus;樤arr;楲aròᄽȀaeit㏸㐈㐏㐗Āls㏽㐄lsetmé㍪hp;樳parsl;槤Ādlᑣ㐔e;挣Ā;e㐜㐝檪Ā;s㐢㐣檬;쀀⪬︀ƀflp㐮㐳㑂tcy;䑌Ā;b㐸㐹䀯Ā;a㐾㐿槄r;挿f;쀀𝕤aĀdr㑍ЂesĀ;u㑔㑕晠it»㑕ƀcsu㑠㑹㒟Āau㑥㑯pĀ;sᆈ㑫;쀀⊓︀pĀ;sᆴ㑵;쀀⊔︀uĀbp㑿㒏ƀ;esᆗᆜ㒆etĀ;eᆗ㒍ñᆝƀ;esᆨᆭ㒖etĀ;eᆨ㒝ñᆮƀ;afᅻ㒦ְrť㒫ֱ»ᅼaròᅈȀcemt㒹㒾㓂㓅r;쀀𝓈tmîñiì㐕aræᆾĀar㓎㓕rĀ;f㓔ឿ昆Āan㓚㓭ightĀep㓣㓪psiloîỠhé⺯s»⡒ʀbcmnp㓻㕞ሉ㖋㖎Ҁ;Edemnprs㔎㔏㔑㔕㔞㔣㔬㔱㔶抂;櫅ot;檽Ā;dᇚ㔚ot;櫃ult;櫁ĀEe㔨㔪;櫋;把lus;檿arr;楹ƀeiu㔽㕒㕕tƀ;en㔎㕅㕋qĀ;qᇚ㔏eqĀ;q㔫㔨m;櫇Ābp㕚㕜;櫕;櫓c̀;acensᇭ㕬㕲㕹㕻㌦pproø㋺urlyeñᇾñᇳƀaes㖂㖈㌛pproø㌚qñ㌗g;晪ڀ123;Edehlmnps㖩㖬㖯ሜ㖲㖴㗀㗉㗕㗚㗟㗨㗭耻¹䂹耻²䂲耻³䂳;櫆Āos㖹㖼t;檾ub;櫘Ā;dሢ㗅ot;櫄sĀou㗏㗒l;柉b;櫗arr;楻ult;櫂ĀEe㗤㗦;櫌;抋lus;櫀ƀeiu㗴㘉㘌tƀ;enሜ㗼㘂qĀ;qሢ㖲eqĀ;q㗧㗤m;櫈Ābp㘑㘓;櫔;櫖ƀAan㘜㘠㘭rr;懙rĀhr㘦㘨ë∮Ā;oਫ਩war;椪lig耻ß䃟௡㙑㙝㙠ዎ㙳㙹\\0㙾㛂\\0\\0\\0\\0\\0㛛㜃\\0㜉㝬\\0\\0\\0㞇ɲ㙖\\0\\0㙛get;挖;䏄rë๟ƀaey㙦㙫㙰ron;䅥dil;䅣;䑂lrec;挕r;쀀𝔱Ȁeiko㚆㚝㚵㚼Dz㚋\\0㚑eĀ4fኄኁaƀ;sv㚘㚙㚛䎸ym;䏑Ācn㚢㚲kĀas㚨㚮pproø዁im»ኬsðኞĀas㚺㚮ð዁rn耻þ䃾Ǭ̟㛆⋧es膀×;bd㛏㛐㛘䃗Ā;aᤏ㛕r;樱;樰ƀeps㛡㛣㜀á⩍Ȁ;bcf҆㛬㛰㛴ot;挶ir;櫱Ā;o㛹㛼쀀𝕥rk;櫚á㍢rime;怴ƀaip㜏㜒㝤dåቈ΀adempst㜡㝍㝀㝑㝗㝜㝟ngleʀ;dlqr㜰㜱㜶㝀㝂斵own»ᶻeftĀ;e⠀㜾ñम;扜ightĀ;e㊪㝋ñၚot;旬inus;樺lus;樹b;槍ime;樻ezium;揢ƀcht㝲㝽㞁Āry㝷㝻;쀀𝓉;䑆cy;䑛rok;䅧Āio㞋㞎xô᝷headĀlr㞗㞠eftarro÷ࡏightarrow»ཝऀAHabcdfghlmoprstuw㟐㟓㟗㟤㟰㟼㠎㠜㠣㠴㡑㡝㡫㢩㣌㣒㣪㣶ròϭar;楣Ācr㟜㟢ute耻ú䃺òᅐrǣ㟪\\0㟭y;䑞ve;䅭Āiy㟵㟺rc耻û䃻;䑃ƀabh㠃㠆㠋ròᎭlac;䅱aòᏃĀir㠓㠘sht;楾;쀀𝔲rave耻ù䃹š㠧㠱rĀlr㠬㠮»ॗ»ႃlk;斀Āct㠹㡍ɯ㠿\\0\\0㡊rnĀ;e㡅㡆挜r»㡆op;挏ri;旸Āal㡖㡚cr;䅫肻¨͉Āgp㡢㡦on;䅳f;쀀𝕦̀adhlsuᅋ㡸㡽፲㢑㢠ownáᎳarpoonĀlr㢈㢌efô㠭ighô㠯iƀ;hl㢙㢚㢜䏅»ᏺon»㢚parrows;懈ƀcit㢰㣄㣈ɯ㢶\\0\\0㣁rnĀ;e㢼㢽挝r»㢽op;挎ng;䅯ri;旹cr;쀀𝓊ƀdir㣙㣝㣢ot;拰lde;䅩iĀ;f㜰㣨»᠓Āam㣯㣲rò㢨l耻ü䃼angle;榧ހABDacdeflnoprsz㤜㤟㤩㤭㦵㦸㦽㧟㧤㧨㧳㧹㧽㨁㨠ròϷarĀ;v㤦㤧櫨;櫩asèϡĀnr㤲㤷grt;榜΀eknprst㓣㥆㥋㥒㥝㥤㦖appá␕othinçẖƀhir㓫⻈㥙opô⾵Ā;hᎷ㥢ïㆍĀiu㥩㥭gmá㎳Ābp㥲㦄setneqĀ;q㥽㦀쀀⊊︀;쀀⫋︀setneqĀ;q㦏㦒쀀⊋︀;쀀⫌︀Āhr㦛㦟etá㚜iangleĀlr㦪㦯eft»थight»ၑy;䐲ash»ံƀelr㧄㧒㧗ƀ;beⷪ㧋㧏ar;抻q;扚lip;拮Ābt㧜ᑨaòᑩr;쀀𝔳tré㦮suĀbp㧯㧱»ജ»൙pf;쀀𝕧roð໻tré㦴Ācu㨆㨋r;쀀𝓋Ābp㨐㨘nĀEe㦀㨖»㥾nĀEe㦒㨞»㦐igzag;榚΀cefoprs㨶㨻㩖㩛㩔㩡㩪irc;䅵Ādi㩀㩑Ābg㩅㩉ar;機eĀ;qᗺ㩏;扙erp;愘r;쀀𝔴pf;쀀𝕨Ā;eᑹ㩦atèᑹcr;쀀𝓌ૣណ㪇\\0㪋\\0㪐㪛\\0\\0㪝㪨㪫㪯\\0\\0㫃㫎\\0㫘ៜ៟tré៑r;쀀𝔵ĀAa㪔㪗ròσrò৶;䎾ĀAa㪡㪤ròθrò৫að✓is;拻ƀdptឤ㪵㪾Āfl㪺ឩ;쀀𝕩imåឲĀAa㫇㫊ròώròਁĀcq㫒ីr;쀀𝓍Āpt៖㫜ré។Ѐacefiosu㫰㫽㬈㬌㬑㬕㬛㬡cĀuy㫶㫻te耻ý䃽;䑏Āiy㬂㬆rc;䅷;䑋n耻¥䂥r;쀀𝔶cy;䑗pf;쀀𝕪cr;쀀𝓎Ācm㬦㬩y;䑎l耻ÿ䃿Ԁacdefhiosw㭂㭈㭔㭘㭤㭩㭭㭴㭺㮀cute;䅺Āay㭍㭒ron;䅾;䐷ot;䅼Āet㭝㭡træᕟa;䎶r;쀀𝔷cy;䐶grarr;懝pf;쀀𝕫cr;쀀𝓏Ājn㮅㮇;怍j;怌'.split(\"\").map((c) => c.charCodeAt(0))\n);\n\n// node_modules/.pnpm/entities@4.5.0/node_modules/entities/lib/esm/generated/decode-data-xml.js\nvar decode_data_xml_default = new Uint16Array(\n // prettier-ignore\n \"Ȁaglq\t\u0015\u0018\\x1Bɭ\u000f\\0\\0\u0012p;䀦os;䀧t;䀾t;䀼uot;䀢\".split(\"\").map((c) => c.charCodeAt(0))\n);\n\n// node_modules/.pnpm/entities@4.5.0/node_modules/entities/lib/esm/decode_codepoint.js\nvar _a;\nvar decodeMap = /* @__PURE__ */ new Map([\n [0, 65533],\n // C1 Unicode control character reference replacements\n [128, 8364],\n [130, 8218],\n [131, 402],\n [132, 8222],\n [133, 8230],\n [134, 8224],\n [135, 8225],\n [136, 710],\n [137, 8240],\n [138, 352],\n [139, 8249],\n [140, 338],\n [142, 381],\n [145, 8216],\n [146, 8217],\n [147, 8220],\n [148, 8221],\n [149, 8226],\n [150, 8211],\n [151, 8212],\n [152, 732],\n [153, 8482],\n [154, 353],\n [155, 8250],\n [156, 339],\n [158, 382],\n [159, 376]\n]);\nvar fromCodePoint = (\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition, node/no-unsupported-features/es-builtins\n (_a = String.fromCodePoint) !== null && _a !== void 0 ? _a : function(codePoint) {\n let output = \"\";\n if (codePoint > 65535) {\n codePoint -= 65536;\n output += String.fromCharCode(codePoint >>> 10 & 1023 | 55296);\n codePoint = 56320 | codePoint & 1023;\n }\n output += String.fromCharCode(codePoint);\n return output;\n }\n);\nfunction replaceCodePoint(codePoint) {\n var _a2;\n if (codePoint >= 55296 && codePoint <= 57343 || codePoint > 1114111) {\n return 65533;\n }\n return (_a2 = decodeMap.get(codePoint)) !== null && _a2 !== void 0 ? _a2 : codePoint;\n}\n\n// node_modules/.pnpm/entities@4.5.0/node_modules/entities/lib/esm/decode.js\nvar CharCodes;\n(function(CharCodes2) {\n CharCodes2[CharCodes2[\"NUM\"] = 35] = \"NUM\";\n CharCodes2[CharCodes2[\"SEMI\"] = 59] = \"SEMI\";\n CharCodes2[CharCodes2[\"EQUALS\"] = 61] = \"EQUALS\";\n CharCodes2[CharCodes2[\"ZERO\"] = 48] = \"ZERO\";\n CharCodes2[CharCodes2[\"NINE\"] = 57] = \"NINE\";\n CharCodes2[CharCodes2[\"LOWER_A\"] = 97] = \"LOWER_A\";\n CharCodes2[CharCodes2[\"LOWER_F\"] = 102] = \"LOWER_F\";\n CharCodes2[CharCodes2[\"LOWER_X\"] = 120] = \"LOWER_X\";\n CharCodes2[CharCodes2[\"LOWER_Z\"] = 122] = \"LOWER_Z\";\n CharCodes2[CharCodes2[\"UPPER_A\"] = 65] = \"UPPER_A\";\n CharCodes2[CharCodes2[\"UPPER_F\"] = 70] = \"UPPER_F\";\n CharCodes2[CharCodes2[\"UPPER_Z\"] = 90] = \"UPPER_Z\";\n})(CharCodes || (CharCodes = {}));\nvar TO_LOWER_BIT = 32;\nvar BinTrieFlags;\n(function(BinTrieFlags2) {\n BinTrieFlags2[BinTrieFlags2[\"VALUE_LENGTH\"] = 49152] = \"VALUE_LENGTH\";\n BinTrieFlags2[BinTrieFlags2[\"BRANCH_LENGTH\"] = 16256] = \"BRANCH_LENGTH\";\n BinTrieFlags2[BinTrieFlags2[\"JUMP_TABLE\"] = 127] = \"JUMP_TABLE\";\n})(BinTrieFlags || (BinTrieFlags = {}));\nfunction isNumber(code2) {\n return code2 >= CharCodes.ZERO && code2 <= CharCodes.NINE;\n}\nfunction isHexadecimalCharacter(code2) {\n return code2 >= CharCodes.UPPER_A && code2 <= CharCodes.UPPER_F || code2 >= CharCodes.LOWER_A && code2 <= CharCodes.LOWER_F;\n}\nfunction isAsciiAlphaNumeric(code2) {\n return code2 >= CharCodes.UPPER_A && code2 <= CharCodes.UPPER_Z || code2 >= CharCodes.LOWER_A && code2 <= CharCodes.LOWER_Z || isNumber(code2);\n}\nfunction isEntityInAttributeInvalidEnd(code2) {\n return code2 === CharCodes.EQUALS || isAsciiAlphaNumeric(code2);\n}\nvar EntityDecoderState;\n(function(EntityDecoderState2) {\n EntityDecoderState2[EntityDecoderState2[\"EntityStart\"] = 0] = \"EntityStart\";\n EntityDecoderState2[EntityDecoderState2[\"NumericStart\"] = 1] = \"NumericStart\";\n EntityDecoderState2[EntityDecoderState2[\"NumericDecimal\"] = 2] = \"NumericDecimal\";\n EntityDecoderState2[EntityDecoderState2[\"NumericHex\"] = 3] = \"NumericHex\";\n EntityDecoderState2[EntityDecoderState2[\"NamedEntity\"] = 4] = \"NamedEntity\";\n})(EntityDecoderState || (EntityDecoderState = {}));\nvar DecodingMode;\n(function(DecodingMode2) {\n DecodingMode2[DecodingMode2[\"Legacy\"] = 0] = \"Legacy\";\n DecodingMode2[DecodingMode2[\"Strict\"] = 1] = \"Strict\";\n DecodingMode2[DecodingMode2[\"Attribute\"] = 2] = \"Attribute\";\n})(DecodingMode || (DecodingMode = {}));\nvar EntityDecoder = class {\n constructor(decodeTree, emitCodePoint, errors2) {\n this.decodeTree = decodeTree;\n this.emitCodePoint = emitCodePoint;\n this.errors = errors2;\n this.state = EntityDecoderState.EntityStart;\n this.consumed = 1;\n this.result = 0;\n this.treeIndex = 0;\n this.excess = 1;\n this.decodeMode = DecodingMode.Strict;\n }\n /** Resets the instance to make it reusable. */\n startEntity(decodeMode) {\n this.decodeMode = decodeMode;\n this.state = EntityDecoderState.EntityStart;\n this.result = 0;\n this.treeIndex = 0;\n this.excess = 1;\n this.consumed = 1;\n }\n /**\n * Write an entity to the decoder. This can be called multiple times with partial entities.\n * If the entity is incomplete, the decoder will return -1.\n *\n * Mirrors the implementation of `getDecoder`, but with the ability to stop decoding if the\n * entity is incomplete, and resume when the next string is written.\n *\n * @param string The string containing the entity (or a continuation of the entity).\n * @param offset The offset at which the entity begins. Should be 0 if this is not the first call.\n * @returns The number of characters that were consumed, or -1 if the entity is incomplete.\n */\n write(str, offset) {\n switch (this.state) {\n case EntityDecoderState.EntityStart: {\n if (str.charCodeAt(offset) === CharCodes.NUM) {\n this.state = EntityDecoderState.NumericStart;\n this.consumed += 1;\n return this.stateNumericStart(str, offset + 1);\n }\n this.state = EntityDecoderState.NamedEntity;\n return this.stateNamedEntity(str, offset);\n }\n case EntityDecoderState.NumericStart: {\n return this.stateNumericStart(str, offset);\n }\n case EntityDecoderState.NumericDecimal: {\n return this.stateNumericDecimal(str, offset);\n }\n case EntityDecoderState.NumericHex: {\n return this.stateNumericHex(str, offset);\n }\n case EntityDecoderState.NamedEntity: {\n return this.stateNamedEntity(str, offset);\n }\n }\n }\n /**\n * Switches between the numeric decimal and hexadecimal states.\n *\n * Equivalent to the `Numeric character reference state` in the HTML spec.\n *\n * @param str The string containing the entity (or a continuation of the entity).\n * @param offset The current offset.\n * @returns The number of characters that were consumed, or -1 if the entity is incomplete.\n */\n stateNumericStart(str, offset) {\n if (offset >= str.length) {\n return -1;\n }\n if ((str.charCodeAt(offset) | TO_LOWER_BIT) === CharCodes.LOWER_X) {\n this.state = EntityDecoderState.NumericHex;\n this.consumed += 1;\n return this.stateNumericHex(str, offset + 1);\n }\n this.state = EntityDecoderState.NumericDecimal;\n return this.stateNumericDecimal(str, offset);\n }\n addToNumericResult(str, start, end, base2) {\n if (start !== end) {\n const digitCount = end - start;\n this.result = this.result * Math.pow(base2, digitCount) + parseInt(str.substr(start, digitCount), base2);\n this.consumed += digitCount;\n }\n }\n /**\n * Parses a hexadecimal numeric entity.\n *\n * Equivalent to the `Hexademical character reference state` in the HTML spec.\n *\n * @param str The string containing the entity (or a continuation of the entity).\n * @param offset The current offset.\n * @returns The number of characters that were consumed, or -1 if the entity is incomplete.\n */\n stateNumericHex(str, offset) {\n const startIdx = offset;\n while (offset < str.length) {\n const char = str.charCodeAt(offset);\n if (isNumber(char) || isHexadecimalCharacter(char)) {\n offset += 1;\n } else {\n this.addToNumericResult(str, startIdx, offset, 16);\n return this.emitNumericEntity(char, 3);\n }\n }\n this.addToNumericResult(str, startIdx, offset, 16);\n return -1;\n }\n /**\n * Parses a decimal numeric entity.\n *\n * Equivalent to the `Decimal character reference state` in the HTML spec.\n *\n * @param str The string containing the entity (or a continuation of the entity).\n * @param offset The current offset.\n * @returns The number of characters that were consumed, or -1 if the entity is incomplete.\n */\n stateNumericDecimal(str, offset) {\n const startIdx = offset;\n while (offset < str.length) {\n const char = str.charCodeAt(offset);\n if (isNumber(char)) {\n offset += 1;\n } else {\n this.addToNumericResult(str, startIdx, offset, 10);\n return this.emitNumericEntity(char, 2);\n }\n }\n this.addToNumericResult(str, startIdx, offset, 10);\n return -1;\n }\n /**\n * Validate and emit a numeric entity.\n *\n * Implements the logic from the `Hexademical character reference start\n * state` and `Numeric character reference end state` in the HTML spec.\n *\n * @param lastCp The last code point of the entity. Used to see if the\n * entity was terminated with a semicolon.\n * @param expectedLength The minimum number of characters that should be\n * consumed. Used to validate that at least one digit\n * was consumed.\n * @returns The number of characters that were consumed.\n */\n emitNumericEntity(lastCp, expectedLength) {\n var _a2;\n if (this.consumed <= expectedLength) {\n (_a2 = this.errors) === null || _a2 === void 0 ? void 0 : _a2.absenceOfDigitsInNumericCharacterReference(this.consumed);\n return 0;\n }\n if (lastCp === CharCodes.SEMI) {\n this.consumed += 1;\n } else if (this.decodeMode === DecodingMode.Strict) {\n return 0;\n }\n this.emitCodePoint(replaceCodePoint(this.result), this.consumed);\n if (this.errors) {\n if (lastCp !== CharCodes.SEMI) {\n this.errors.missingSemicolonAfterCharacterReference();\n }\n this.errors.validateNumericCharacterReference(this.result);\n }\n return this.consumed;\n }\n /**\n * Parses a named entity.\n *\n * Equivalent to the `Named character reference state` in the HTML spec.\n *\n * @param str The string containing the entity (or a continuation of the entity).\n * @param offset The current offset.\n * @returns The number of characters that were consumed, or -1 if the entity is incomplete.\n */\n stateNamedEntity(str, offset) {\n const { decodeTree } = this;\n let current = decodeTree[this.treeIndex];\n let valueLength = (current & BinTrieFlags.VALUE_LENGTH) >> 14;\n for (; offset < str.length; offset++, this.excess++) {\n const char = str.charCodeAt(offset);\n this.treeIndex = determineBranch(decodeTree, current, this.treeIndex + Math.max(1, valueLength), char);\n if (this.treeIndex < 0) {\n return this.result === 0 || // If we are parsing an attribute\n this.decodeMode === DecodingMode.Attribute && // We shouldn't have consumed any characters after the entity,\n (valueLength === 0 || // And there should be no invalid characters.\n isEntityInAttributeInvalidEnd(char)) ? 0 : this.emitNotTerminatedNamedEntity();\n }\n current = decodeTree[this.treeIndex];\n valueLength = (current & BinTrieFlags.VALUE_LENGTH) >> 14;\n if (valueLength !== 0) {\n if (char === CharCodes.SEMI) {\n return this.emitNamedEntityData(this.treeIndex, valueLength, this.consumed + this.excess);\n }\n if (this.decodeMode !== DecodingMode.Strict) {\n this.result = this.treeIndex;\n this.consumed += this.excess;\n this.excess = 0;\n }\n }\n }\n return -1;\n }\n /**\n * Emit a named entity that was not terminated with a semicolon.\n *\n * @returns The number of characters consumed.\n */\n emitNotTerminatedNamedEntity() {\n var _a2;\n const { result, decodeTree } = this;\n const valueLength = (decodeTree[result] & BinTrieFlags.VALUE_LENGTH) >> 14;\n this.emitNamedEntityData(result, valueLength, this.consumed);\n (_a2 = this.errors) === null || _a2 === void 0 ? void 0 : _a2.missingSemicolonAfterCharacterReference();\n return this.consumed;\n }\n /**\n * Emit a named entity.\n *\n * @param result The index of the entity in the decode tree.\n * @param valueLength The number of bytes in the entity.\n * @param consumed The number of characters consumed.\n *\n * @returns The number of characters consumed.\n */\n emitNamedEntityData(result, valueLength, consumed) {\n const { decodeTree } = this;\n this.emitCodePoint(valueLength === 1 ? decodeTree[result] & ~BinTrieFlags.VALUE_LENGTH : decodeTree[result + 1], consumed);\n if (valueLength === 3) {\n this.emitCodePoint(decodeTree[result + 2], consumed);\n }\n return consumed;\n }\n /**\n * Signal to the parser that the end of the input was reached.\n *\n * Remaining data will be emitted and relevant errors will be produced.\n *\n * @returns The number of characters consumed.\n */\n end() {\n var _a2;\n switch (this.state) {\n case EntityDecoderState.NamedEntity: {\n return this.result !== 0 && (this.decodeMode !== DecodingMode.Attribute || this.result === this.treeIndex) ? this.emitNotTerminatedNamedEntity() : 0;\n }\n // Otherwise, emit a numeric entity if we have one.\n case EntityDecoderState.NumericDecimal: {\n return this.emitNumericEntity(0, 2);\n }\n case EntityDecoderState.NumericHex: {\n return this.emitNumericEntity(0, 3);\n }\n case EntityDecoderState.NumericStart: {\n (_a2 = this.errors) === null || _a2 === void 0 ? void 0 : _a2.absenceOfDigitsInNumericCharacterReference(this.consumed);\n return 0;\n }\n case EntityDecoderState.EntityStart: {\n return 0;\n }\n }\n }\n};\nfunction getDecoder(decodeTree) {\n let ret = \"\";\n const decoder = new EntityDecoder(decodeTree, (str) => ret += fromCodePoint(str));\n return function decodeWithTrie(str, decodeMode) {\n let lastIndex = 0;\n let offset = 0;\n while ((offset = str.indexOf(\"&\", offset)) >= 0) {\n ret += str.slice(lastIndex, offset);\n decoder.startEntity(decodeMode);\n const len = decoder.write(\n str,\n // Skip the \"&\"\n offset + 1\n );\n if (len < 0) {\n lastIndex = offset + decoder.end();\n break;\n }\n lastIndex = offset + len;\n offset = len === 0 ? lastIndex + 1 : lastIndex;\n }\n const result = ret + str.slice(lastIndex);\n ret = \"\";\n return result;\n };\n}\nfunction determineBranch(decodeTree, current, nodeIdx, char) {\n const branchCount = (current & BinTrieFlags.BRANCH_LENGTH) >> 7;\n const jumpOffset = current & BinTrieFlags.JUMP_TABLE;\n if (branchCount === 0) {\n return jumpOffset !== 0 && char === jumpOffset ? nodeIdx : -1;\n }\n if (jumpOffset) {\n const value = char - jumpOffset;\n return value < 0 || value >= branchCount ? -1 : decodeTree[nodeIdx + value] - 1;\n }\n let lo = nodeIdx;\n let hi = lo + branchCount - 1;\n while (lo <= hi) {\n const mid = lo + hi >>> 1;\n const midVal = decodeTree[mid];\n if (midVal < char) {\n lo = mid + 1;\n } else if (midVal > char) {\n hi = mid - 1;\n } else {\n return decodeTree[mid + branchCount];\n }\n }\n return -1;\n}\nvar htmlDecoder = getDecoder(decode_data_html_default);\nvar xmlDecoder = getDecoder(decode_data_xml_default);\nfunction decodeHTML(str, mode = DecodingMode.Legacy) {\n return htmlDecoder(str, mode);\n}\n\n// node_modules/.pnpm/entities@4.5.0/node_modules/entities/lib/esm/generated/encode-html.js\nfunction restoreDiff(arr) {\n for (let i = 1; i < arr.length; i++) {\n arr[i][0] += arr[i - 1][0] + 1;\n }\n return arr;\n}\nvar encode_html_default = new Map(/* @__PURE__ */ restoreDiff([[9, \" \"], [0, \" \"], [22, \"!\"], [0, \""\"], [0, \"#\"], [0, \"$\"], [0, \"%\"], [0, \"&\"], [0, \"'\"], [0, \"(\"], [0, \")\"], [0, \"*\"], [0, \"+\"], [0, \",\"], [1, \".\"], [0, \"/\"], [10, \":\"], [0, \";\"], [0, { v: \"<\", n: 8402, o: \"<⃒\" }], [0, { v: \"=\", n: 8421, o: \"=⃥\" }], [0, { v: \">\", n: 8402, o: \">⃒\" }], [0, \"?\"], [0, \"@\"], [26, \"[\"], [0, \"\\"], [0, \"]\"], [0, \"^\"], [0, \"_\"], [0, \"`\"], [5, { n: 106, o: \"fj\" }], [20, \"{\"], [0, \"|\"], [0, \"}\"], [34, \" \"], [0, \"¡\"], [0, \"¢\"], [0, \"£\"], [0, \"¤\"], [0, \"¥\"], [0, \"¦\"], [0, \"§\"], [0, \"¨\"], [0, \"©\"], [0, \"ª\"], [0, \"«\"], [0, \"¬\"], [0, \"­\"], [0, \"®\"], [0, \"¯\"], [0, \"°\"], [0, \"±\"], [0, \"²\"], [0, \"³\"], [0, \"´\"], [0, \"µ\"], [0, \"¶\"], [0, \"·\"], [0, \"¸\"], [0, \"¹\"], [0, \"º\"], [0, \"»\"], [0, \"¼\"], [0, \"½\"], [0, \"¾\"], [0, \"¿\"], [0, \"À\"], [0, \"Á\"], [0, \"Â\"], [0, \"Ã\"], [0, \"Ä\"], [0, \"Å\"], [0, \"Æ\"], [0, \"Ç\"], [0, \"È\"], [0, \"É\"], [0, \"Ê\"], [0, \"Ë\"], [0, \"Ì\"], [0, \"Í\"], [0, \"Î\"], [0, \"Ï\"], [0, \"Ð\"], [0, \"Ñ\"], [0, \"Ò\"], [0, \"Ó\"], [0, \"Ô\"], [0, \"Õ\"], [0, \"Ö\"], [0, \"×\"], [0, \"Ø\"], [0, \"Ù\"], [0, \"Ú\"], [0, \"Û\"], [0, \"Ü\"], [0, \"Ý\"], [0, \"Þ\"], [0, \"ß\"], [0, \"à\"], [0, \"á\"], [0, \"â\"], [0, \"ã\"], [0, \"ä\"], [0, \"å\"], [0, \"æ\"], [0, \"ç\"], [0, \"è\"], [0, \"é\"], [0, \"ê\"], [0, \"ë\"], [0, \"ì\"], [0, \"í\"], [0, \"î\"], [0, \"ï\"], [0, \"ð\"], [0, \"ñ\"], [0, \"ò\"], [0, \"ó\"], [0, \"ô\"], [0, \"õ\"], [0, \"ö\"], [0, \"÷\"], [0, \"ø\"], [0, \"ù\"], [0, \"ú\"], [0, \"û\"], [0, \"ü\"], [0, \"ý\"], [0, \"þ\"], [0, \"ÿ\"], [0, \"Ā\"], [0, \"ā\"], [0, \"Ă\"], [0, \"ă\"], [0, \"Ą\"], [0, \"ą\"], [0, \"Ć\"], [0, \"ć\"], [0, \"Ĉ\"], [0, \"ĉ\"], [0, \"Ċ\"], [0, \"ċ\"], [0, \"Č\"], [0, \"č\"], [0, \"Ď\"], [0, \"ď\"], [0, \"Đ\"], [0, \"đ\"], [0, \"Ē\"], [0, \"ē\"], [2, \"Ė\"], [0, \"ė\"], [0, \"Ę\"], [0, \"ę\"], [0, \"Ě\"], [0, \"ě\"], [0, \"Ĝ\"], [0, \"ĝ\"], [0, \"Ğ\"], [0, \"ğ\"], [0, \"Ġ\"], [0, \"ġ\"], [0, \"Ģ\"], [1, \"Ĥ\"], [0, \"ĥ\"], [0, \"Ħ\"], [0, \"ħ\"], [0, \"Ĩ\"], [0, \"ĩ\"], [0, \"Ī\"], [0, \"ī\"], [2, \"Į\"], [0, \"į\"], [0, \"İ\"], [0, \"ı\"], [0, \"IJ\"], [0, \"ij\"], [0, \"Ĵ\"], [0, \"ĵ\"], [0, \"Ķ\"], [0, \"ķ\"], [0, \"ĸ\"], [0, \"Ĺ\"], [0, \"ĺ\"], [0, \"Ļ\"], [0, \"ļ\"], [0, \"Ľ\"], [0, \"ľ\"], [0, \"Ŀ\"], [0, \"ŀ\"], [0, \"Ł\"], [0, \"ł\"], [0, \"Ń\"], [0, \"ń\"], [0, \"Ņ\"], [0, \"ņ\"], [0, \"Ň\"], [0, \"ň\"], [0, \"ʼn\"], [0, \"Ŋ\"], [0, \"ŋ\"], [0, \"Ō\"], [0, \"ō\"], [2, \"Ő\"], [0, \"ő\"], [0, \"Œ\"], [0, \"œ\"], [0, \"Ŕ\"], [0, \"ŕ\"], [0, \"Ŗ\"], [0, \"ŗ\"], [0, \"Ř\"], [0, \"ř\"], [0, \"Ś\"], [0, \"ś\"], [0, \"Ŝ\"], [0, \"ŝ\"], [0, \"Ş\"], [0, \"ş\"], [0, \"Š\"], [0, \"š\"], [0, \"Ţ\"], [0, \"ţ\"], [0, \"Ť\"], [0, \"ť\"], [0, \"Ŧ\"], [0, \"ŧ\"], [0, \"Ũ\"], [0, \"ũ\"], [0, \"Ū\"], [0, \"ū\"], [0, \"Ŭ\"], [0, \"ŭ\"], [0, \"Ů\"], [0, \"ů\"], [0, \"Ű\"], [0, \"ű\"], [0, \"Ų\"], [0, \"ų\"], [0, \"Ŵ\"], [0, \"ŵ\"], [0, \"Ŷ\"], [0, \"ŷ\"], [0, \"Ÿ\"], [0, \"Ź\"], [0, \"ź\"], [0, \"Ż\"], [0, \"ż\"], [0, \"Ž\"], [0, \"ž\"], [19, \"ƒ\"], [34, \"Ƶ\"], [63, \"ǵ\"], [65, \"ȷ\"], [142, \"ˆ\"], [0, \"ˇ\"], [16, \"˘\"], [0, \"˙\"], [0, \"˚\"], [0, \"˛\"], [0, \"˜\"], [0, \"˝\"], [51, \"̑\"], [127, \"Α\"], [0, \"Β\"], [0, \"Γ\"], [0, \"Δ\"], [0, \"Ε\"], [0, \"Ζ\"], [0, \"Η\"], [0, \"Θ\"], [0, \"Ι\"], [0, \"Κ\"], [0, \"Λ\"], [0, \"Μ\"], [0, \"Ν\"], [0, \"Ξ\"], [0, \"Ο\"], [0, \"Π\"], [0, \"Ρ\"], [1, \"Σ\"], [0, \"Τ\"], [0, \"Υ\"], [0, \"Φ\"], [0, \"Χ\"], [0, \"Ψ\"], [0, \"Ω\"], [7, \"α\"], [0, \"β\"], [0, \"γ\"], [0, \"δ\"], [0, \"ε\"], [0, \"ζ\"], [0, \"η\"], [0, \"θ\"], [0, \"ι\"], [0, \"κ\"], [0, \"λ\"], [0, \"μ\"], [0, \"ν\"], [0, \"ξ\"], [0, \"ο\"], [0, \"π\"], [0, \"ρ\"], [0, \"ς\"], [0, \"σ\"], [0, \"τ\"], [0, \"υ\"], [0, \"φ\"], [0, \"χ\"], [0, \"ψ\"], [0, \"ω\"], [7, \"ϑ\"], [0, \"ϒ\"], [2, \"ϕ\"], [0, \"ϖ\"], [5, \"Ϝ\"], [0, \"ϝ\"], [18, \"ϰ\"], [0, \"ϱ\"], [3, \"ϵ\"], [0, \"϶\"], [10, \"Ё\"], [0, \"Ђ\"], [0, \"Ѓ\"], [0, \"Є\"], [0, \"Ѕ\"], [0, \"І\"], [0, \"Ї\"], [0, \"Ј\"], [0, \"Љ\"], [0, \"Њ\"], [0, \"Ћ\"], [0, \"Ќ\"], [1, \"Ў\"], [0, \"Џ\"], [0, \"А\"], [0, \"Б\"], [0, \"В\"], [0, \"Г\"], [0, \"Д\"], [0, \"Е\"], [0, \"Ж\"], [0, \"З\"], [0, \"И\"], [0, \"Й\"], [0, \"К\"], [0, \"Л\"], [0, \"М\"], [0, \"Н\"], [0, \"О\"], [0, \"П\"], [0, \"Р\"], [0, \"С\"], [0, \"Т\"], [0, \"У\"], [0, \"Ф\"], [0, \"Х\"], [0, \"Ц\"], [0, \"Ч\"], [0, \"Ш\"], [0, \"Щ\"], [0, \"Ъ\"], [0, \"Ы\"], [0, \"Ь\"], [0, \"Э\"], [0, \"Ю\"], [0, \"Я\"], [0, \"а\"], [0, \"б\"], [0, \"в\"], [0, \"г\"], [0, \"д\"], [0, \"е\"], [0, \"ж\"], [0, \"з\"], [0, \"и\"], [0, \"й\"], [0, \"к\"], [0, \"л\"], [0, \"м\"], [0, \"н\"], [0, \"о\"], [0, \"п\"], [0, \"р\"], [0, \"с\"], [0, \"т\"], [0, \"у\"], [0, \"ф\"], [0, \"х\"], [0, \"ц\"], [0, \"ч\"], [0, \"ш\"], [0, \"щ\"], [0, \"ъ\"], [0, \"ы\"], [0, \"ь\"], [0, \"э\"], [0, \"ю\"], [0, \"я\"], [1, \"ё\"], [0, \"ђ\"], [0, \"ѓ\"], [0, \"є\"], [0, \"ѕ\"], [0, \"і\"], [0, \"ї\"], [0, \"ј\"], [0, \"љ\"], [0, \"њ\"], [0, \"ћ\"], [0, \"ќ\"], [1, \"ў\"], [0, \"џ\"], [7074, \" \"], [0, \" \"], [0, \" \"], [0, \" \"], [1, \" \"], [0, \" \"], [0, \" \"], [0, \" \"], [0, \"​\"], [0, \"‌\"], [0, \"‍\"], [0, \"‎\"], [0, \"‏\"], [0, \"‐\"], [2, \"–\"], [0, \"—\"], [0, \"―\"], [0, \"‖\"], [1, \"‘\"], [0, \"’\"], [0, \"‚\"], [1, \"“\"], [0, \"”\"], [0, \"„\"], [1, \"†\"], [0, \"‡\"], [0, \"•\"], [2, \"‥\"], [0, \"…\"], [9, \"‰\"], [0, \"‱\"], [0, \"′\"], [0, \"″\"], [0, \"‴\"], [0, \"‵\"], [3, \"‹\"], [0, \"›\"], [3, \"‾\"], [2, \"⁁\"], [1, \"⁃\"], [0, \"⁄\"], [10, \"⁏\"], [7, \"⁗\"], [7, { v: \" \", n: 8202, o: \"  \" }], [0, \"⁠\"], [0, \"⁡\"], [0, \"⁢\"], [0, \"⁣\"], [72, \"€\"], [46, \"⃛\"], [0, \"⃜\"], [37, \"ℂ\"], [2, \"℅\"], [4, \"ℊ\"], [0, \"ℋ\"], [0, \"ℌ\"], [0, \"ℍ\"], [0, \"ℎ\"], [0, \"ℏ\"], [0, \"ℐ\"], [0, \"ℑ\"], [0, \"ℒ\"], [0, \"ℓ\"], [1, \"ℕ\"], [0, \"№\"], [0, \"℗\"], [0, \"℘\"], [0, \"ℙ\"], [0, \"ℚ\"], [0, \"ℛ\"], [0, \"ℜ\"], [0, \"ℝ\"], [0, \"℞\"], [3, \"™\"], [1, \"ℤ\"], [2, \"℧\"], [0, \"ℨ\"], [0, \"℩\"], [2, \"ℬ\"], [0, \"ℭ\"], [1, \"ℯ\"], [0, \"ℰ\"], [0, \"ℱ\"], [1, \"ℳ\"], [0, \"ℴ\"], [0, \"ℵ\"], [0, \"ℶ\"], [0, \"ℷ\"], [0, \"ℸ\"], [12, \"ⅅ\"], [0, \"ⅆ\"], [0, \"ⅇ\"], [0, \"ⅈ\"], [10, \"⅓\"], [0, \"⅔\"], [0, \"⅕\"], [0, \"⅖\"], [0, \"⅗\"], [0, \"⅘\"], [0, \"⅙\"], [0, \"⅚\"], [0, \"⅛\"], [0, \"⅜\"], [0, \"⅝\"], [0, \"⅞\"], [49, \"←\"], [0, \"↑\"], [0, \"→\"], [0, \"↓\"], [0, \"↔\"], [0, \"↕\"], [0, \"↖\"], [0, \"↗\"], [0, \"↘\"], [0, \"↙\"], [0, \"↚\"], [0, \"↛\"], [1, { v: \"↝\", n: 824, o: \"↝̸\" }], [0, \"↞\"], [0, \"↟\"], [0, \"↠\"], [0, \"↡\"], [0, \"↢\"], [0, \"↣\"], [0, \"↤\"], [0, \"↥\"], [0, \"↦\"], [0, \"↧\"], [1, \"↩\"], [0, \"↪\"], [0, \"↫\"], [0, \"↬\"], [0, \"↭\"], [0, \"↮\"], [1, \"↰\"], [0, \"↱\"], [0, \"↲\"], [0, \"↳\"], [1, \"↵\"], [0, \"↶\"], [0, \"↷\"], [2, \"↺\"], [0, \"↻\"], [0, \"↼\"], [0, \"↽\"], [0, \"↾\"], [0, \"↿\"], [0, \"⇀\"], [0, \"⇁\"], [0, \"⇂\"], [0, \"⇃\"], [0, \"⇄\"], [0, \"⇅\"], [0, \"⇆\"], [0, \"⇇\"], [0, \"⇈\"], [0, \"⇉\"], [0, \"⇊\"], [0, \"⇋\"], [0, \"⇌\"], [0, \"⇍\"], [0, \"⇎\"], [0, \"⇏\"], [0, \"⇐\"], [0, \"⇑\"], [0, \"⇒\"], [0, \"⇓\"], [0, \"⇔\"], [0, \"⇕\"], [0, \"⇖\"], [0, \"⇗\"], [0, \"⇘\"], [0, \"⇙\"], [0, \"⇚\"], [0, \"⇛\"], [1, \"⇝\"], [6, \"⇤\"], [0, \"⇥\"], [15, \"⇵\"], [7, \"⇽\"], [0, \"⇾\"], [0, \"⇿\"], [0, \"∀\"], [0, \"∁\"], [0, { v: \"∂\", n: 824, o: \"∂̸\" }], [0, \"∃\"], [0, \"∄\"], [0, \"∅\"], [1, \"∇\"], [0, \"∈\"], [0, \"∉\"], [1, \"∋\"], [0, \"∌\"], [2, \"∏\"], [0, \"∐\"], [0, \"∑\"], [0, \"−\"], [0, \"∓\"], [0, \"∔\"], [1, \"∖\"], [0, \"∗\"], [0, \"∘\"], [1, \"√\"], [2, \"∝\"], [0, \"∞\"], [0, \"∟\"], [0, { v: \"∠\", n: 8402, o: \"∠⃒\" }], [0, \"∡\"], [0, \"∢\"], [0, \"∣\"], [0, \"∤\"], [0, \"∥\"], [0, \"∦\"], [0, \"∧\"], [0, \"∨\"], [0, { v: \"∩\", n: 65024, o: \"∩︀\" }], [0, { v: \"∪\", n: 65024, o: \"∪︀\" }], [0, \"∫\"], [0, \"∬\"], [0, \"∭\"], [0, \"∮\"], [0, \"∯\"], [0, \"∰\"], [0, \"∱\"], [0, \"∲\"], [0, \"∳\"], [0, \"∴\"], [0, \"∵\"], [0, \"∶\"], [0, \"∷\"], [0, \"∸\"], [1, \"∺\"], [0, \"∻\"], [0, { v: \"∼\", n: 8402, o: \"∼⃒\" }], [0, { v: \"∽\", n: 817, o: \"∽̱\" }], [0, { v: \"∾\", n: 819, o: \"∾̳\" }], [0, \"∿\"], [0, \"≀\"], [0, \"≁\"], [0, { v: \"≂\", n: 824, o: \"≂̸\" }], [0, \"≃\"], [0, \"≄\"], [0, \"≅\"], [0, \"≆\"], [0, \"≇\"], [0, \"≈\"], [0, \"≉\"], [0, \"≊\"], [0, { v: \"≋\", n: 824, o: \"≋̸\" }], [0, \"≌\"], [0, { v: \"≍\", n: 8402, o: \"≍⃒\" }], [0, { v: \"≎\", n: 824, o: \"≎̸\" }], [0, { v: \"≏\", n: 824, o: \"≏̸\" }], [0, { v: \"≐\", n: 824, o: \"≐̸\" }], [0, \"≑\"], [0, \"≒\"], [0, \"≓\"], [0, \"≔\"], [0, \"≕\"], [0, \"≖\"], [0, \"≗\"], [1, \"≙\"], [0, \"≚\"], [1, \"≜\"], [2, \"≟\"], [0, \"≠\"], [0, { v: \"≡\", n: 8421, o: \"≡⃥\" }], [0, \"≢\"], [1, { v: \"≤\", n: 8402, o: \"≤⃒\" }], [0, { v: \"≥\", n: 8402, o: \"≥⃒\" }], [0, { v: \"≦\", n: 824, o: \"≦̸\" }], [0, { v: \"≧\", n: 824, o: \"≧̸\" }], [0, { v: \"≨\", n: 65024, o: \"≨︀\" }], [0, { v: \"≩\", n: 65024, o: \"≩︀\" }], [0, { v: \"≪\", n: new Map(/* @__PURE__ */ restoreDiff([[824, \"≪̸\"], [7577, \"≪⃒\"]])) }], [0, { v: \"≫\", n: new Map(/* @__PURE__ */ restoreDiff([[824, \"≫̸\"], [7577, \"≫⃒\"]])) }], [0, \"≬\"], [0, \"≭\"], [0, \"≮\"], [0, \"≯\"], [0, \"≰\"], [0, \"≱\"], [0, \"≲\"], [0, \"≳\"], [0, \"≴\"], [0, \"≵\"], [0, \"≶\"], [0, \"≷\"], [0, \"≸\"], [0, \"≹\"], [0, \"≺\"], [0, \"≻\"], [0, \"≼\"], [0, \"≽\"], [0, \"≾\"], [0, { v: \"≿\", n: 824, o: \"≿̸\" }], [0, \"⊀\"], [0, \"⊁\"], [0, { v: \"⊂\", n: 8402, o: \"⊂⃒\" }], [0, { v: \"⊃\", n: 8402, o: \"⊃⃒\" }], [0, \"⊄\"], [0, \"⊅\"], [0, \"⊆\"], [0, \"⊇\"], [0, \"⊈\"], [0, \"⊉\"], [0, { v: \"⊊\", n: 65024, o: \"⊊︀\" }], [0, { v: \"⊋\", n: 65024, o: \"⊋︀\" }], [1, \"⊍\"], [0, \"⊎\"], [0, { v: \"⊏\", n: 824, o: \"⊏̸\" }], [0, { v: \"⊐\", n: 824, o: \"⊐̸\" }], [0, \"⊑\"], [0, \"⊒\"], [0, { v: \"⊓\", n: 65024, o: \"⊓︀\" }], [0, { v: \"⊔\", n: 65024, o: \"⊔︀\" }], [0, \"⊕\"], [0, \"⊖\"], [0, \"⊗\"], [0, \"⊘\"], [0, \"⊙\"], [0, \"⊚\"], [0, \"⊛\"], [1, \"⊝\"], [0, \"⊞\"], [0, \"⊟\"], [0, \"⊠\"], [0, \"⊡\"], [0, \"⊢\"], [0, \"⊣\"], [0, \"⊤\"], [0, \"⊥\"], [1, \"⊧\"], [0, \"⊨\"], [0, \"⊩\"], [0, \"⊪\"], [0, \"⊫\"], [0, \"⊬\"], [0, \"⊭\"], [0, \"⊮\"], [0, \"⊯\"], [0, \"⊰\"], [1, \"⊲\"], [0, \"⊳\"], [0, { v: \"⊴\", n: 8402, o: \"⊴⃒\" }], [0, { v: \"⊵\", n: 8402, o: \"⊵⃒\" }], [0, \"⊶\"], [0, \"⊷\"], [0, \"⊸\"], [0, \"⊹\"], [0, \"⊺\"], [0, \"⊻\"], [1, \"⊽\"], [0, \"⊾\"], [0, \"⊿\"], [0, \"⋀\"], [0, \"⋁\"], [0, \"⋂\"], [0, \"⋃\"], [0, \"⋄\"], [0, \"⋅\"], [0, \"⋆\"], [0, \"⋇\"], [0, \"⋈\"], [0, \"⋉\"], [0, \"⋊\"], [0, \"⋋\"], [0, \"⋌\"], [0, \"⋍\"], [0, \"⋎\"], [0, \"⋏\"], [0, \"⋐\"], [0, \"⋑\"], [0, \"⋒\"], [0, \"⋓\"], [0, \"⋔\"], [0, \"⋕\"], [0, \"⋖\"], [0, \"⋗\"], [0, { v: \"⋘\", n: 824, o: \"⋘̸\" }], [0, { v: \"⋙\", n: 824, o: \"⋙̸\" }], [0, { v: \"⋚\", n: 65024, o: \"⋚︀\" }], [0, { v: \"⋛\", n: 65024, o: \"⋛︀\" }], [2, \"⋞\"], [0, \"⋟\"], [0, \"⋠\"], [0, \"⋡\"], [0, \"⋢\"], [0, \"⋣\"], [2, \"⋦\"], [0, \"⋧\"], [0, \"⋨\"], [0, \"⋩\"], [0, \"⋪\"], [0, \"⋫\"], [0, \"⋬\"], [0, \"⋭\"], [0, \"⋮\"], [0, \"⋯\"], [0, \"⋰\"], [0, \"⋱\"], [0, \"⋲\"], [0, \"⋳\"], [0, \"⋴\"], [0, { v: \"⋵\", n: 824, o: \"⋵̸\" }], [0, \"⋶\"], [0, \"⋷\"], [1, { v: \"⋹\", n: 824, o: \"⋹̸\" }], [0, \"⋺\"], [0, \"⋻\"], [0, \"⋼\"], [0, \"⋽\"], [0, \"⋾\"], [6, \"⌅\"], [0, \"⌆\"], [1, \"⌈\"], [0, \"⌉\"], [0, \"⌊\"], [0, \"⌋\"], [0, \"⌌\"], [0, \"⌍\"], [0, \"⌎\"], [0, \"⌏\"], [0, \"⌐\"], [1, \"⌒\"], [0, \"⌓\"], [1, \"⌕\"], [0, \"⌖\"], [5, \"⌜\"], [0, \"⌝\"], [0, \"⌞\"], [0, \"⌟\"], [2, \"⌢\"], [0, \"⌣\"], [9, \"⌭\"], [0, \"⌮\"], [7, \"⌶\"], [6, \"⌽\"], [1, \"⌿\"], [60, \"⍼\"], [51, \"⎰\"], [0, \"⎱\"], [2, \"⎴\"], [0, \"⎵\"], [0, \"⎶\"], [37, \"⏜\"], [0, \"⏝\"], [0, \"⏞\"], [0, \"⏟\"], [2, \"⏢\"], [4, \"⏧\"], [59, \"␣\"], [164, \"Ⓢ\"], [55, \"─\"], [1, \"│\"], [9, \"┌\"], [3, \"┐\"], [3, \"└\"], [3, \"┘\"], [3, \"├\"], [7, \"┤\"], [7, \"┬\"], [7, \"┴\"], [7, \"┼\"], [19, \"═\"], [0, \"║\"], [0, \"╒\"], [0, \"╓\"], [0, \"╔\"], [0, \"╕\"], [0, \"╖\"], [0, \"╗\"], [0, \"╘\"], [0, \"╙\"], [0, \"╚\"], [0, \"╛\"], [0, \"╜\"], [0, \"╝\"], [0, \"╞\"], [0, \"╟\"], [0, \"╠\"], [0, \"╡\"], [0, \"╢\"], [0, \"╣\"], [0, \"╤\"], [0, \"╥\"], [0, \"╦\"], [0, \"╧\"], [0, \"╨\"], [0, \"╩\"], [0, \"╪\"], [0, \"╫\"], [0, \"╬\"], [19, \"▀\"], [3, \"▄\"], [3, \"█\"], [8, \"░\"], [0, \"▒\"], [0, \"▓\"], [13, \"□\"], [8, \"▪\"], [0, \"▫\"], [1, \"▭\"], [0, \"▮\"], [2, \"▱\"], [1, \"△\"], [0, \"▴\"], [0, \"▵\"], [2, \"▸\"], [0, \"▹\"], [3, \"▽\"], [0, \"▾\"], [0, \"▿\"], [2, \"◂\"], [0, \"◃\"], [6, \"◊\"], [0, \"○\"], [32, \"◬\"], [2, \"◯\"], [8, \"◸\"], [0, \"◹\"], [0, \"◺\"], [0, \"◻\"], [0, \"◼\"], [8, \"★\"], [0, \"☆\"], [7, \"☎\"], [49, \"♀\"], [1, \"♂\"], [29, \"♠\"], [2, \"♣\"], [1, \"♥\"], [0, \"♦\"], [3, \"♪\"], [2, \"♭\"], [0, \"♮\"], [0, \"♯\"], [163, \"✓\"], [3, \"✗\"], [8, \"✠\"], [21, \"✶\"], [33, \"❘\"], [25, \"❲\"], [0, \"❳\"], [84, \"⟈\"], [0, \"⟉\"], [28, \"⟦\"], [0, \"⟧\"], [0, \"⟨\"], [0, \"⟩\"], [0, \"⟪\"], [0, \"⟫\"], [0, \"⟬\"], [0, \"⟭\"], [7, \"⟵\"], [0, \"⟶\"], [0, \"⟷\"], [0, \"⟸\"], [0, \"⟹\"], [0, \"⟺\"], [1, \"⟼\"], [2, \"⟿\"], [258, \"⤂\"], [0, \"⤃\"], [0, \"⤄\"], [0, \"⤅\"], [6, \"⤌\"], [0, \"⤍\"], [0, \"⤎\"], [0, \"⤏\"], [0, \"⤐\"], [0, \"⤑\"], [0, \"⤒\"], [0, \"⤓\"], [2, \"⤖\"], [2, \"⤙\"], [0, \"⤚\"], [0, \"⤛\"], [0, \"⤜\"], [0, \"⤝\"], [0, \"⤞\"], [0, \"⤟\"], [0, \"⤠\"], [2, \"⤣\"], [0, \"⤤\"], [0, \"⤥\"], [0, \"⤦\"], [0, \"⤧\"], [0, \"⤨\"], [0, \"⤩\"], [0, \"⤪\"], [8, { v: \"⤳\", n: 824, o: \"⤳̸\" }], [1, \"⤵\"], [0, \"⤶\"], [0, \"⤷\"], [0, \"⤸\"], [0, \"⤹\"], [2, \"⤼\"], [0, \"⤽\"], [7, \"⥅\"], [2, \"⥈\"], [0, \"⥉\"], [0, \"⥊\"], [0, \"⥋\"], [2, \"⥎\"], [0, \"⥏\"], [0, \"⥐\"], [0, \"⥑\"], [0, \"⥒\"], [0, \"⥓\"], [0, \"⥔\"], [0, \"⥕\"], [0, \"⥖\"], [0, \"⥗\"], [0, \"⥘\"], [0, \"⥙\"], [0, \"⥚\"], [0, \"⥛\"], [0, \"⥜\"], [0, \"⥝\"], [0, \"⥞\"], [0, \"⥟\"], [0, \"⥠\"], [0, \"⥡\"], [0, \"⥢\"], [0, \"⥣\"], [0, \"⥤\"], [0, \"⥥\"], [0, \"⥦\"], [0, \"⥧\"], [0, \"⥨\"], [0, \"⥩\"], [0, \"⥪\"], [0, \"⥫\"], [0, \"⥬\"], [0, \"⥭\"], [0, \"⥮\"], [0, \"⥯\"], [0, \"⥰\"], [0, \"⥱\"], [0, \"⥲\"], [0, \"⥳\"], [0, \"⥴\"], [0, \"⥵\"], [0, \"⥶\"], [1, \"⥸\"], [0, \"⥹\"], [1, \"⥻\"], [0, \"⥼\"], [0, \"⥽\"], [0, \"⥾\"], [0, \"⥿\"], [5, \"⦅\"], [0, \"⦆\"], [4, \"⦋\"], [0, \"⦌\"], [0, \"⦍\"], [0, \"⦎\"], [0, \"⦏\"], [0, \"⦐\"], [0, \"⦑\"], [0, \"⦒\"], [0, \"⦓\"], [0, \"⦔\"], [0, \"⦕\"], [0, \"⦖\"], [3, \"⦚\"], [1, \"⦜\"], [0, \"⦝\"], [6, \"⦤\"], [0, \"⦥\"], [0, \"⦦\"], [0, \"⦧\"], [0, \"⦨\"], [0, \"⦩\"], [0, \"⦪\"], [0, \"⦫\"], [0, \"⦬\"], [0, \"⦭\"], [0, \"⦮\"], [0, \"⦯\"], [0, \"⦰\"], [0, \"⦱\"], [0, \"⦲\"], [0, \"⦳\"], [0, \"⦴\"], [0, \"⦵\"], [0, \"⦶\"], [0, \"⦷\"], [1, \"⦹\"], [1, \"⦻\"], [0, \"⦼\"], [1, \"⦾\"], [0, \"⦿\"], [0, \"⧀\"], [0, \"⧁\"], [0, \"⧂\"], [0, \"⧃\"], [0, \"⧄\"], [0, \"⧅\"], [3, \"⧉\"], [3, \"⧍\"], [0, \"⧎\"], [0, { v: \"⧏\", n: 824, o: \"⧏̸\" }], [0, { v: \"⧐\", n: 824, o: \"⧐̸\" }], [11, \"⧜\"], [0, \"⧝\"], [0, \"⧞\"], [4, \"⧣\"], [0, \"⧤\"], [0, \"⧥\"], [5, \"⧫\"], [8, \"⧴\"], [1, \"⧶\"], [9, \"⨀\"], [0, \"⨁\"], [0, \"⨂\"], [1, \"⨄\"], [1, \"⨆\"], [5, \"⨌\"], [0, \"⨍\"], [2, \"⨐\"], [0, \"⨑\"], [0, \"⨒\"], [0, \"⨓\"], [0, \"⨔\"], [0, \"⨕\"], [0, \"⨖\"], [0, \"⨗\"], [10, \"⨢\"], [0, \"⨣\"], [0, \"⨤\"], [0, \"⨥\"], [0, \"⨦\"], [0, \"⨧\"], [1, \"⨩\"], [0, \"⨪\"], [2, \"⨭\"], [0, \"⨮\"], [0, \"⨯\"], [0, \"⨰\"], [0, \"⨱\"], [1, \"⨳\"], [0, \"⨴\"], [0, \"⨵\"], [0, \"⨶\"], [0, \"⨷\"], [0, \"⨸\"], [0, \"⨹\"], [0, \"⨺\"], [0, \"⨻\"], [0, \"⨼\"], [2, \"⨿\"], [0, \"⩀\"], [1, \"⩂\"], [0, \"⩃\"], [0, \"⩄\"], [0, \"⩅\"], [0, \"⩆\"], [0, \"⩇\"], [0, \"⩈\"], [0, \"⩉\"], [0, \"⩊\"], [0, \"⩋\"], [0, \"⩌\"], [0, \"⩍\"], [2, \"⩐\"], [2, \"⩓\"], [0, \"⩔\"], [0, \"⩕\"], [0, \"⩖\"], [0, \"⩗\"], [0, \"⩘\"], [1, \"⩚\"], [0, \"⩛\"], [0, \"⩜\"], [0, \"⩝\"], [1, \"⩟\"], [6, \"⩦\"], [3, \"⩪\"], [2, { v: \"⩭\", n: 824, o: \"⩭̸\" }], [0, \"⩮\"], [0, \"⩯\"], [0, { v: \"⩰\", n: 824, o: \"⩰̸\" }], [0, \"⩱\"], [0, \"⩲\"], [0, \"⩳\"], [0, \"⩴\"], [0, \"⩵\"], [1, \"⩷\"], [0, \"⩸\"], [0, \"⩹\"], [0, \"⩺\"], [0, \"⩻\"], [0, \"⩼\"], [0, { v: \"⩽\", n: 824, o: \"⩽̸\" }], [0, { v: \"⩾\", n: 824, o: \"⩾̸\" }], [0, \"⩿\"], [0, \"⪀\"], [0, \"⪁\"], [0, \"⪂\"], [0, \"⪃\"], [0, \"⪄\"], [0, \"⪅\"], [0, \"⪆\"], [0, \"⪇\"], [0, \"⪈\"], [0, \"⪉\"], [0, \"⪊\"], [0, \"⪋\"], [0, \"⪌\"], [0, \"⪍\"], [0, \"⪎\"], [0, \"⪏\"], [0, \"⪐\"], [0, \"⪑\"], [0, \"⪒\"], [0, \"⪓\"], [0, \"⪔\"], [0, \"⪕\"], [0, \"⪖\"], [0, \"⪗\"], [0, \"⪘\"], [0, \"⪙\"], [0, \"⪚\"], [2, \"⪝\"], [0, \"⪞\"], [0, \"⪟\"], [0, \"⪠\"], [0, { v: \"⪡\", n: 824, o: \"⪡̸\" }], [0, { v: \"⪢\", n: 824, o: \"⪢̸\" }], [1, \"⪤\"], [0, \"⪥\"], [0, \"⪦\"], [0, \"⪧\"], [0, \"⪨\"], [0, \"⪩\"], [0, \"⪪\"], [0, \"⪫\"], [0, { v: \"⪬\", n: 65024, o: \"⪬︀\" }], [0, { v: \"⪭\", n: 65024, o: \"⪭︀\" }], [0, \"⪮\"], [0, { v: \"⪯\", n: 824, o: \"⪯̸\" }], [0, { v: \"⪰\", n: 824, o: \"⪰̸\" }], [2, \"⪳\"], [0, \"⪴\"], [0, \"⪵\"], [0, \"⪶\"], [0, \"⪷\"], [0, \"⪸\"], [0, \"⪹\"], [0, \"⪺\"], [0, \"⪻\"], [0, \"⪼\"], [0, \"⪽\"], [0, \"⪾\"], [0, \"⪿\"], [0, \"⫀\"], [0, \"⫁\"], [0, \"⫂\"], [0, \"⫃\"], [0, \"⫄\"], [0, { v: \"⫅\", n: 824, o: \"⫅̸\" }], [0, { v: \"⫆\", n: 824, o: \"⫆̸\" }], [0, \"⫇\"], [0, \"⫈\"], [2, { v: \"⫋\", n: 65024, o: \"⫋︀\" }], [0, { v: \"⫌\", n: 65024, o: \"⫌︀\" }], [2, \"⫏\"], [0, \"⫐\"], [0, \"⫑\"], [0, \"⫒\"], [0, \"⫓\"], [0, \"⫔\"], [0, \"⫕\"], [0, \"⫖\"], [0, \"⫗\"], [0, \"⫘\"], [0, \"⫙\"], [0, \"⫚\"], [0, \"⫛\"], [8, \"⫤\"], [1, \"⫦\"], [0, \"⫧\"], [0, \"⫨\"], [0, \"⫩\"], [1, \"⫫\"], [0, \"⫬\"], [0, \"⫭\"], [0, \"⫮\"], [0, \"⫯\"], [0, \"⫰\"], [0, \"⫱\"], [0, \"⫲\"], [0, \"⫳\"], [9, { v: \"⫽\", n: 8421, o: \"⫽⃥\" }], [44343, { n: new Map(/* @__PURE__ */ restoreDiff([[56476, \"𝒜\"], [1, \"𝒞\"], [0, \"𝒟\"], [2, \"𝒢\"], [2, \"𝒥\"], [0, \"𝒦\"], [2, \"𝒩\"], [0, \"𝒪\"], [0, \"𝒫\"], [0, \"𝒬\"], [1, \"𝒮\"], [0, \"𝒯\"], [0, \"𝒰\"], [0, \"𝒱\"], [0, \"𝒲\"], [0, \"𝒳\"], [0, \"𝒴\"], [0, \"𝒵\"], [0, \"𝒶\"], [0, \"𝒷\"], [0, \"𝒸\"], [0, \"𝒹\"], [1, \"𝒻\"], [1, \"𝒽\"], [0, \"𝒾\"], [0, \"𝒿\"], [0, \"𝓀\"], [0, \"𝓁\"], [0, \"𝓂\"], [0, \"𝓃\"], [1, \"𝓅\"], [0, \"𝓆\"], [0, \"𝓇\"], [0, \"𝓈\"], [0, \"𝓉\"], [0, \"𝓊\"], [0, \"𝓋\"], [0, \"𝓌\"], [0, \"𝓍\"], [0, \"𝓎\"], [0, \"𝓏\"], [52, \"𝔄\"], [0, \"𝔅\"], [1, \"𝔇\"], [0, \"𝔈\"], [0, \"𝔉\"], [0, \"𝔊\"], [2, \"𝔍\"], [0, \"𝔎\"], [0, \"𝔏\"], [0, \"𝔐\"], [0, \"𝔑\"], [0, \"𝔒\"], [0, \"𝔓\"], [0, \"𝔔\"], [1, \"𝔖\"], [0, \"𝔗\"], [0, \"𝔘\"], [0, \"𝔙\"], [0, \"𝔚\"], [0, \"𝔛\"], [0, \"𝔜\"], [1, \"𝔞\"], [0, \"𝔟\"], [0, \"𝔠\"], [0, \"𝔡\"], [0, \"𝔢\"], [0, \"𝔣\"], [0, \"𝔤\"], [0, \"𝔥\"], [0, \"𝔦\"], [0, \"𝔧\"], [0, \"𝔨\"], [0, \"𝔩\"], [0, \"𝔪\"], [0, \"𝔫\"], [0, \"𝔬\"], [0, \"𝔭\"], [0, \"𝔮\"], [0, \"𝔯\"], [0, \"𝔰\"], [0, \"𝔱\"], [0, \"𝔲\"], [0, \"𝔳\"], [0, \"𝔴\"], [0, \"𝔵\"], [0, \"𝔶\"], [0, \"𝔷\"], [0, \"𝔸\"], [0, \"𝔹\"], [1, \"𝔻\"], [0, \"𝔼\"], [0, \"𝔽\"], [0, \"𝔾\"], [1, \"𝕀\"], [0, \"𝕁\"], [0, \"𝕂\"], [0, \"𝕃\"], [0, \"𝕄\"], [1, \"𝕆\"], [3, \"𝕊\"], [0, \"𝕋\"], [0, \"𝕌\"], [0, \"𝕍\"], [0, \"𝕎\"], [0, \"𝕏\"], [0, \"𝕐\"], [1, \"𝕒\"], [0, \"𝕓\"], [0, \"𝕔\"], [0, \"𝕕\"], [0, \"𝕖\"], [0, \"𝕗\"], [0, \"𝕘\"], [0, \"𝕙\"], [0, \"𝕚\"], [0, \"𝕛\"], [0, \"𝕜\"], [0, \"𝕝\"], [0, \"𝕞\"], [0, \"𝕟\"], [0, \"𝕠\"], [0, \"𝕡\"], [0, \"𝕢\"], [0, \"𝕣\"], [0, \"𝕤\"], [0, \"𝕥\"], [0, \"𝕦\"], [0, \"𝕧\"], [0, \"𝕨\"], [0, \"𝕩\"], [0, \"𝕪\"], [0, \"𝕫\"]])) }], [8906, \"ff\"], [0, \"fi\"], [0, \"fl\"], [0, \"ffi\"], [0, \"ffl\"]]));\n\n// node_modules/.pnpm/entities@4.5.0/node_modules/entities/lib/esm/escape.js\nvar xmlCodeMap = /* @__PURE__ */ new Map([\n [34, \""\"],\n [38, \"&\"],\n [39, \"'\"],\n [60, \"<\"],\n [62, \">\"]\n]);\nvar getCodePoint = (\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n String.prototype.codePointAt != null ? (str, index) => str.codePointAt(index) : (\n // http://mathiasbynens.be/notes/javascript-encoding#surrogate-formulae\n (c, index) => (c.charCodeAt(index) & 64512) === 55296 ? (c.charCodeAt(index) - 55296) * 1024 + c.charCodeAt(index + 1) - 56320 + 65536 : c.charCodeAt(index)\n )\n);\nfunction getEscaper(regex, map2) {\n return function escape3(data) {\n let match2;\n let lastIdx = 0;\n let result = \"\";\n while (match2 = regex.exec(data)) {\n if (lastIdx !== match2.index) {\n result += data.substring(lastIdx, match2.index);\n }\n result += map2.get(match2[0].charCodeAt(0));\n lastIdx = match2.index + 1;\n }\n return result + data.substring(lastIdx);\n };\n}\nvar escapeUTF8 = getEscaper(/[&<>'\"]/g, xmlCodeMap);\nvar escapeAttribute = getEscaper(/[\"&\\u00A0]/g, /* @__PURE__ */ new Map([\n [34, \""\"],\n [38, \"&\"],\n [160, \" \"]\n]));\nvar escapeText = getEscaper(/[&<>\\u00A0]/g, /* @__PURE__ */ new Map([\n [38, \"&\"],\n [60, \"<\"],\n [62, \">\"],\n [160, \" \"]\n]));\n\n// node_modules/.pnpm/entities@4.5.0/node_modules/entities/lib/esm/index.js\nvar EntityLevel;\n(function(EntityLevel2) {\n EntityLevel2[EntityLevel2[\"XML\"] = 0] = \"XML\";\n EntityLevel2[EntityLevel2[\"HTML\"] = 1] = \"HTML\";\n})(EntityLevel || (EntityLevel = {}));\nvar EncodingMode;\n(function(EncodingMode2) {\n EncodingMode2[EncodingMode2[\"UTF8\"] = 0] = \"UTF8\";\n EncodingMode2[EncodingMode2[\"ASCII\"] = 1] = \"ASCII\";\n EncodingMode2[EncodingMode2[\"Extensive\"] = 2] = \"Extensive\";\n EncodingMode2[EncodingMode2[\"Attribute\"] = 3] = \"Attribute\";\n EncodingMode2[EncodingMode2[\"Text\"] = 4] = \"Text\";\n})(EncodingMode || (EncodingMode = {}));\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/common/utils.mjs\nfunction _class(obj) {\n return Object.prototype.toString.call(obj);\n}\nfunction isString(obj) {\n return _class(obj) === \"[object String]\";\n}\nvar _hasOwnProperty = Object.prototype.hasOwnProperty;\nfunction has(object, key) {\n return _hasOwnProperty.call(object, key);\n}\nfunction assign(obj) {\n const sources = Array.prototype.slice.call(arguments, 1);\n sources.forEach(function(source2) {\n if (!source2) {\n return;\n }\n if (typeof source2 !== \"object\") {\n throw new TypeError(source2 + \"must be object\");\n }\n Object.keys(source2).forEach(function(key) {\n obj[key] = source2[key];\n });\n });\n return obj;\n}\nfunction arrayReplaceAt(src, pos, newElements) {\n return [].concat(src.slice(0, pos), newElements, src.slice(pos + 1));\n}\nfunction isValidEntityCode(c) {\n if (c >= 55296 && c <= 57343) {\n return false;\n }\n if (c >= 64976 && c <= 65007) {\n return false;\n }\n if ((c & 65535) === 65535 || (c & 65535) === 65534) {\n return false;\n }\n if (c >= 0 && c <= 8) {\n return false;\n }\n if (c === 11) {\n return false;\n }\n if (c >= 14 && c <= 31) {\n return false;\n }\n if (c >= 127 && c <= 159) {\n return false;\n }\n if (c > 1114111) {\n return false;\n }\n return true;\n}\nfunction fromCodePoint2(c) {\n if (c > 65535) {\n c -= 65536;\n const surrogate1 = 55296 + (c >> 10);\n const surrogate2 = 56320 + (c & 1023);\n return String.fromCharCode(surrogate1, surrogate2);\n }\n return String.fromCharCode(c);\n}\nvar UNESCAPE_MD_RE = /\\\\([!\"#$%&'()*+,\\-./:;<=>?@[\\\\\\]^_`{|}~])/g;\nvar ENTITY_RE = /&([a-z#][a-z0-9]{1,31});/gi;\nvar UNESCAPE_ALL_RE = new RegExp(UNESCAPE_MD_RE.source + \"|\" + ENTITY_RE.source, \"gi\");\nvar DIGITAL_ENTITY_TEST_RE = /^#((?:x[a-f0-9]{1,8}|[0-9]{1,8}))$/i;\nfunction replaceEntityPattern(match2, name) {\n if (name.charCodeAt(0) === 35 && DIGITAL_ENTITY_TEST_RE.test(name)) {\n const code2 = name[1].toLowerCase() === \"x\" ? parseInt(name.slice(2), 16) : parseInt(name.slice(1), 10);\n if (isValidEntityCode(code2)) {\n return fromCodePoint2(code2);\n }\n return match2;\n }\n const decoded = decodeHTML(match2);\n if (decoded !== match2) {\n return decoded;\n }\n return match2;\n}\nfunction unescapeMd(str) {\n if (str.indexOf(\"\\\\\") < 0) {\n return str;\n }\n return str.replace(UNESCAPE_MD_RE, \"$1\");\n}\nfunction unescapeAll(str) {\n if (str.indexOf(\"\\\\\") < 0 && str.indexOf(\"&\") < 0) {\n return str;\n }\n return str.replace(UNESCAPE_ALL_RE, function(match2, escaped, entity2) {\n if (escaped) {\n return escaped;\n }\n return replaceEntityPattern(match2, entity2);\n });\n}\nvar HTML_ESCAPE_TEST_RE = /[&<>\"]/;\nvar HTML_ESCAPE_REPLACE_RE = /[&<>\"]/g;\nvar HTML_REPLACEMENTS = {\n \"&\": \"&\",\n \"<\": \"<\",\n \">\": \">\",\n '\"': \""\"\n};\nfunction replaceUnsafeChar(ch) {\n return HTML_REPLACEMENTS[ch];\n}\nfunction escapeHtml(str) {\n if (HTML_ESCAPE_TEST_RE.test(str)) {\n return str.replace(HTML_ESCAPE_REPLACE_RE, replaceUnsafeChar);\n }\n return str;\n}\nvar REGEXP_ESCAPE_RE = /[.?*+^$[\\]\\\\(){}|-]/g;\nfunction escapeRE(str) {\n return str.replace(REGEXP_ESCAPE_RE, \"\\\\$&\");\n}\nfunction isSpace(code2) {\n switch (code2) {\n case 9:\n case 32:\n return true;\n }\n return false;\n}\nfunction isWhiteSpace(code2) {\n if (code2 >= 8192 && code2 <= 8202) {\n return true;\n }\n switch (code2) {\n case 9:\n // \\t\n case 10:\n // \\n\n case 11:\n // \\v\n case 12:\n // \\f\n case 13:\n // \\r\n case 32:\n case 160:\n case 5760:\n case 8239:\n case 8287:\n case 12288:\n return true;\n }\n return false;\n}\nfunction isPunctChar(ch) {\n return regex_default4.test(ch) || regex_default5.test(ch);\n}\nfunction isMdAsciiPunct(ch) {\n switch (ch) {\n case 33:\n case 34:\n case 35:\n case 36:\n case 37:\n case 38:\n case 39:\n case 40:\n case 41:\n case 42:\n case 43:\n case 44:\n case 45:\n case 46:\n case 47:\n case 58:\n case 59:\n case 60:\n case 61:\n case 62:\n case 63:\n case 64:\n case 91:\n case 92:\n case 93:\n case 94:\n case 95:\n case 96:\n case 123:\n case 124:\n case 125:\n case 126:\n return true;\n default:\n return false;\n }\n}\nfunction normalizeReference(str) {\n str = str.trim().replace(/\\s+/g, \" \");\n if (\"ẞ\".toLowerCase() === \"Ṿ\") {\n str = str.replace(/ẞ/g, \"ß\");\n }\n return str.toLowerCase().toUpperCase();\n}\nvar lib = { mdurl: mdurl_exports, ucmicro: uc_exports };\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/index.mjs\nvar helpers_exports = {};\n__export(helpers_exports, {\n parseLinkDestination: () => parseLinkDestination,\n parseLinkLabel: () => parseLinkLabel,\n parseLinkTitle: () => parseLinkTitle\n});\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/parse_link_label.mjs\nfunction parseLinkLabel(state, start, disableNested) {\n let level, found, marker, prevPos;\n const max = state.posMax;\n const oldPos = state.pos;\n state.pos = start + 1;\n level = 1;\n while (state.pos < max) {\n marker = state.src.charCodeAt(state.pos);\n if (marker === 93) {\n level--;\n if (level === 0) {\n found = true;\n break;\n }\n }\n prevPos = state.pos;\n state.md.inline.skipToken(state);\n if (marker === 91) {\n if (prevPos === state.pos - 1) {\n level++;\n } else if (disableNested) {\n state.pos = oldPos;\n return -1;\n }\n }\n }\n let labelEnd = -1;\n if (found) {\n labelEnd = state.pos;\n }\n state.pos = oldPos;\n return labelEnd;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/parse_link_destination.mjs\nfunction parseLinkDestination(str, start, max) {\n let code2;\n let pos = start;\n const result = {\n ok: false,\n pos: 0,\n str: \"\"\n };\n if (str.charCodeAt(pos) === 60) {\n pos++;\n while (pos < max) {\n code2 = str.charCodeAt(pos);\n if (code2 === 10) {\n return result;\n }\n if (code2 === 60) {\n return result;\n }\n if (code2 === 62) {\n result.pos = pos + 1;\n result.str = unescapeAll(str.slice(start + 1, pos));\n result.ok = true;\n return result;\n }\n if (code2 === 92 && pos + 1 < max) {\n pos += 2;\n continue;\n }\n pos++;\n }\n return result;\n }\n let level = 0;\n while (pos < max) {\n code2 = str.charCodeAt(pos);\n if (code2 === 32) {\n break;\n }\n if (code2 < 32 || code2 === 127) {\n break;\n }\n if (code2 === 92 && pos + 1 < max) {\n if (str.charCodeAt(pos + 1) === 32) {\n break;\n }\n pos += 2;\n continue;\n }\n if (code2 === 40) {\n level++;\n if (level > 32) {\n return result;\n }\n }\n if (code2 === 41) {\n if (level === 0) {\n break;\n }\n level--;\n }\n pos++;\n }\n if (start === pos) {\n return result;\n }\n if (level !== 0) {\n return result;\n }\n result.str = unescapeAll(str.slice(start, pos));\n result.pos = pos;\n result.ok = true;\n return result;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/parse_link_title.mjs\nfunction parseLinkTitle(str, start, max, prev_state) {\n let code2;\n let pos = start;\n const state = {\n // if `true`, this is a valid link title\n ok: false,\n // if `true`, this link can be continued on the next line\n can_continue: false,\n // if `ok`, it's the position of the first character after the closing marker\n pos: 0,\n // if `ok`, it's the unescaped title\n str: \"\",\n // expected closing marker character code\n marker: 0\n };\n if (prev_state) {\n state.str = prev_state.str;\n state.marker = prev_state.marker;\n } else {\n if (pos >= max) {\n return state;\n }\n let marker = str.charCodeAt(pos);\n if (marker !== 34 && marker !== 39 && marker !== 40) {\n return state;\n }\n start++;\n pos++;\n if (marker === 40) {\n marker = 41;\n }\n state.marker = marker;\n }\n while (pos < max) {\n code2 = str.charCodeAt(pos);\n if (code2 === state.marker) {\n state.pos = pos + 1;\n state.str += unescapeAll(str.slice(start, pos));\n state.ok = true;\n return state;\n } else if (code2 === 40 && state.marker === 41) {\n return state;\n } else if (code2 === 92 && pos + 1 < max) {\n pos++;\n }\n pos++;\n }\n state.can_continue = true;\n state.str += unescapeAll(str.slice(start, pos));\n return state;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/renderer.mjs\nvar default_rules = {};\ndefault_rules.code_inline = function(tokens2, idx, options, env, slf) {\n const token = tokens2[idx];\n return \"\" + escapeHtml(token.content) + \"\";\n};\ndefault_rules.code_block = function(tokens2, idx, options, env, slf) {\n const token = tokens2[idx];\n return \"\" + escapeHtml(tokens2[idx].content) + \"\\n\";\n};\ndefault_rules.fence = function(tokens2, idx, options, env, slf) {\n const token = tokens2[idx];\n const info = token.info ? unescapeAll(token.info).trim() : \"\";\n let langName = \"\";\n let langAttrs = \"\";\n if (info) {\n const arr = info.split(/(\\s+)/g);\n langName = arr[0];\n langAttrs = arr.slice(2).join(\"\");\n }\n let highlighted;\n if (options.highlight) {\n highlighted = options.highlight(token.content, langName, langAttrs) || escapeHtml(token.content);\n } else {\n highlighted = escapeHtml(token.content);\n }\n if (highlighted.indexOf(\"${highlighted}\n`;\n }\n return `
${highlighted}
\n`;\n};\ndefault_rules.image = function(tokens2, idx, options, env, slf) {\n const token = tokens2[idx];\n token.attrs[token.attrIndex(\"alt\")][1] = slf.renderInlineAsText(token.children, options, env);\n return slf.renderToken(tokens2, idx, options);\n};\ndefault_rules.hardbreak = function(tokens2, idx, options) {\n return options.xhtmlOut ? \"
\\n\" : \"
\\n\";\n};\ndefault_rules.softbreak = function(tokens2, idx, options) {\n return options.breaks ? options.xhtmlOut ? \"
\\n\" : \"
\\n\" : \"\\n\";\n};\ndefault_rules.text = function(tokens2, idx) {\n return escapeHtml(tokens2[idx].content);\n};\ndefault_rules.html_block = function(tokens2, idx) {\n return tokens2[idx].content;\n};\ndefault_rules.html_inline = function(tokens2, idx) {\n return tokens2[idx].content;\n};\nfunction Renderer() {\n this.rules = assign({}, default_rules);\n}\nRenderer.prototype.renderAttrs = function renderAttrs(token) {\n let i, l, result;\n if (!token.attrs) {\n return \"\";\n }\n result = \"\";\n for (i = 0, l = token.attrs.length; i < l; i++) {\n result += \" \" + escapeHtml(token.attrs[i][0]) + '=\"' + escapeHtml(token.attrs[i][1]) + '\"';\n }\n return result;\n};\nRenderer.prototype.renderToken = function renderToken(tokens2, idx, options) {\n const token = tokens2[idx];\n let result = \"\";\n if (token.hidden) {\n return \"\";\n }\n if (token.block && token.nesting !== -1 && idx && tokens2[idx - 1].hidden) {\n result += \"\\n\";\n }\n result += (token.nesting === -1 ? \"\\n\" : \">\";\n return result;\n};\nRenderer.prototype.renderInline = function(tokens2, options, env) {\n let result = \"\";\n const rules = this.rules;\n for (let i = 0, len = tokens2.length; i < len; i++) {\n const type = tokens2[i].type;\n if (typeof rules[type] !== \"undefined\") {\n result += rules[type](tokens2, i, options, env, this);\n } else {\n result += this.renderToken(tokens2, i, options);\n }\n }\n return result;\n};\nRenderer.prototype.renderInlineAsText = function(tokens2, options, env) {\n let result = \"\";\n for (let i = 0, len = tokens2.length; i < len; i++) {\n switch (tokens2[i].type) {\n case \"text\":\n result += tokens2[i].content;\n break;\n case \"image\":\n result += this.renderInlineAsText(tokens2[i].children, options, env);\n break;\n case \"html_inline\":\n case \"html_block\":\n result += tokens2[i].content;\n break;\n case \"softbreak\":\n case \"hardbreak\":\n result += \"\\n\";\n break;\n default:\n }\n }\n return result;\n};\nRenderer.prototype.render = function(tokens2, options, env) {\n let result = \"\";\n const rules = this.rules;\n for (let i = 0, len = tokens2.length; i < len; i++) {\n const type = tokens2[i].type;\n if (type === \"inline\") {\n result += this.renderInline(tokens2[i].children, options, env);\n } else if (typeof rules[type] !== \"undefined\") {\n result += rules[type](tokens2, i, options, env, this);\n } else {\n result += this.renderToken(tokens2, i, options, env);\n }\n }\n return result;\n};\nvar renderer_default = Renderer;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/ruler.mjs\nfunction Ruler() {\n this.__rules__ = [];\n this.__cache__ = null;\n}\nRuler.prototype.__find__ = function(name) {\n for (let i = 0; i < this.__rules__.length; i++) {\n if (this.__rules__[i].name === name) {\n return i;\n }\n }\n return -1;\n};\nRuler.prototype.__compile__ = function() {\n const self = this;\n const chains = [\"\"];\n self.__rules__.forEach(function(rule) {\n if (!rule.enabled) {\n return;\n }\n rule.alt.forEach(function(altName) {\n if (chains.indexOf(altName) < 0) {\n chains.push(altName);\n }\n });\n });\n self.__cache__ = {};\n chains.forEach(function(chain) {\n self.__cache__[chain] = [];\n self.__rules__.forEach(function(rule) {\n if (!rule.enabled) {\n return;\n }\n if (chain && rule.alt.indexOf(chain) < 0) {\n return;\n }\n self.__cache__[chain].push(rule.fn);\n });\n });\n};\nRuler.prototype.at = function(name, fn, options) {\n const index = this.__find__(name);\n const opt = options || {};\n if (index === -1) {\n throw new Error(\"Parser rule not found: \" + name);\n }\n this.__rules__[index].fn = fn;\n this.__rules__[index].alt = opt.alt || [];\n this.__cache__ = null;\n};\nRuler.prototype.before = function(beforeName, ruleName, fn, options) {\n const index = this.__find__(beforeName);\n const opt = options || {};\n if (index === -1) {\n throw new Error(\"Parser rule not found: \" + beforeName);\n }\n this.__rules__.splice(index, 0, {\n name: ruleName,\n enabled: true,\n fn,\n alt: opt.alt || []\n });\n this.__cache__ = null;\n};\nRuler.prototype.after = function(afterName, ruleName, fn, options) {\n const index = this.__find__(afterName);\n const opt = options || {};\n if (index === -1) {\n throw new Error(\"Parser rule not found: \" + afterName);\n }\n this.__rules__.splice(index + 1, 0, {\n name: ruleName,\n enabled: true,\n fn,\n alt: opt.alt || []\n });\n this.__cache__ = null;\n};\nRuler.prototype.push = function(ruleName, fn, options) {\n const opt = options || {};\n this.__rules__.push({\n name: ruleName,\n enabled: true,\n fn,\n alt: opt.alt || []\n });\n this.__cache__ = null;\n};\nRuler.prototype.enable = function(list2, ignoreInvalid) {\n if (!Array.isArray(list2)) {\n list2 = [list2];\n }\n const result = [];\n list2.forEach(function(name) {\n const idx = this.__find__(name);\n if (idx < 0) {\n if (ignoreInvalid) {\n return;\n }\n throw new Error(\"Rules manager: invalid rule name \" + name);\n }\n this.__rules__[idx].enabled = true;\n result.push(name);\n }, this);\n this.__cache__ = null;\n return result;\n};\nRuler.prototype.enableOnly = function(list2, ignoreInvalid) {\n if (!Array.isArray(list2)) {\n list2 = [list2];\n }\n this.__rules__.forEach(function(rule) {\n rule.enabled = false;\n });\n this.enable(list2, ignoreInvalid);\n};\nRuler.prototype.disable = function(list2, ignoreInvalid) {\n if (!Array.isArray(list2)) {\n list2 = [list2];\n }\n const result = [];\n list2.forEach(function(name) {\n const idx = this.__find__(name);\n if (idx < 0) {\n if (ignoreInvalid) {\n return;\n }\n throw new Error(\"Rules manager: invalid rule name \" + name);\n }\n this.__rules__[idx].enabled = false;\n result.push(name);\n }, this);\n this.__cache__ = null;\n return result;\n};\nRuler.prototype.getRules = function(chainName) {\n if (this.__cache__ === null) {\n this.__compile__();\n }\n return this.__cache__[chainName] || [];\n};\nvar ruler_default = Ruler;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/token.mjs\nfunction Token(type, tag, nesting) {\n this.type = type;\n this.tag = tag;\n this.attrs = null;\n this.map = null;\n this.nesting = nesting;\n this.level = 0;\n this.children = null;\n this.content = \"\";\n this.markup = \"\";\n this.info = \"\";\n this.meta = null;\n this.block = false;\n this.hidden = false;\n}\nToken.prototype.attrIndex = function attrIndex(name) {\n if (!this.attrs) {\n return -1;\n }\n const attrs = this.attrs;\n for (let i = 0, len = attrs.length; i < len; i++) {\n if (attrs[i][0] === name) {\n return i;\n }\n }\n return -1;\n};\nToken.prototype.attrPush = function attrPush(attrData) {\n if (this.attrs) {\n this.attrs.push(attrData);\n } else {\n this.attrs = [attrData];\n }\n};\nToken.prototype.attrSet = function attrSet(name, value) {\n const idx = this.attrIndex(name);\n const attrData = [name, value];\n if (idx < 0) {\n this.attrPush(attrData);\n } else {\n this.attrs[idx] = attrData;\n }\n};\nToken.prototype.attrGet = function attrGet(name) {\n const idx = this.attrIndex(name);\n let value = null;\n if (idx >= 0) {\n value = this.attrs[idx][1];\n }\n return value;\n};\nToken.prototype.attrJoin = function attrJoin(name, value) {\n const idx = this.attrIndex(name);\n if (idx < 0) {\n this.attrPush([name, value]);\n } else {\n this.attrs[idx][1] = this.attrs[idx][1] + \" \" + value;\n }\n};\nvar token_default = Token;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/state_core.mjs\nfunction StateCore(src, md2, env) {\n this.src = src;\n this.env = env;\n this.tokens = [];\n this.inlineMode = false;\n this.md = md2;\n}\nStateCore.prototype.Token = token_default;\nvar state_core_default = StateCore;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/normalize.mjs\nvar NEWLINES_RE = /\\r\\n?|\\n/g;\nvar NULL_RE = /\\0/g;\nfunction normalize(state) {\n let str;\n str = state.src.replace(NEWLINES_RE, \"\\n\");\n str = str.replace(NULL_RE, \"�\");\n state.src = str;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/block.mjs\nfunction block(state) {\n let token;\n if (state.inlineMode) {\n token = new state.Token(\"inline\", \"\", 0);\n token.content = state.src;\n token.map = [0, 1];\n token.children = [];\n state.tokens.push(token);\n } else {\n state.md.block.parse(state.src, state.md, state.env, state.tokens);\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/inline.mjs\nfunction inline(state) {\n const tokens2 = state.tokens;\n for (let i = 0, l = tokens2.length; i < l; i++) {\n const tok = tokens2[i];\n if (tok.type === \"inline\") {\n state.md.inline.parse(tok.content, state.md, state.env, tok.children);\n }\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/linkify.mjs\nfunction isLinkOpen(str) {\n return /^\\s]/i.test(str);\n}\nfunction isLinkClose(str) {\n return /^<\\/a\\s*>/i.test(str);\n}\nfunction linkify(state) {\n const blockTokens = state.tokens;\n if (!state.md.options.linkify) {\n return;\n }\n for (let j = 0, l = blockTokens.length; j < l; j++) {\n if (blockTokens[j].type !== \"inline\" || !state.md.linkify.pretest(blockTokens[j].content)) {\n continue;\n }\n let tokens2 = blockTokens[j].children;\n let htmlLinkLevel = 0;\n for (let i = tokens2.length - 1; i >= 0; i--) {\n const currentToken = tokens2[i];\n if (currentToken.type === \"link_close\") {\n i--;\n while (tokens2[i].level !== currentToken.level && tokens2[i].type !== \"link_open\") {\n i--;\n }\n continue;\n }\n if (currentToken.type === \"html_inline\") {\n if (isLinkOpen(currentToken.content) && htmlLinkLevel > 0) {\n htmlLinkLevel--;\n }\n if (isLinkClose(currentToken.content)) {\n htmlLinkLevel++;\n }\n }\n if (htmlLinkLevel > 0) {\n continue;\n }\n if (currentToken.type === \"text\" && state.md.linkify.test(currentToken.content)) {\n const text2 = currentToken.content;\n let links2 = state.md.linkify.match(text2);\n const nodes = [];\n let level = currentToken.level;\n let lastPos = 0;\n if (links2.length > 0 && links2[0].index === 0 && i > 0 && tokens2[i - 1].type === \"text_special\") {\n links2 = links2.slice(1);\n }\n for (let ln = 0; ln < links2.length; ln++) {\n const url = links2[ln].url;\n const fullUrl = state.md.normalizeLink(url);\n if (!state.md.validateLink(fullUrl)) {\n continue;\n }\n let urlText = links2[ln].text;\n if (!links2[ln].schema) {\n urlText = state.md.normalizeLinkText(\"http://\" + urlText).replace(/^http:\\/\\//, \"\");\n } else if (links2[ln].schema === \"mailto:\" && !/^mailto:/i.test(urlText)) {\n urlText = state.md.normalizeLinkText(\"mailto:\" + urlText).replace(/^mailto:/, \"\");\n } else {\n urlText = state.md.normalizeLinkText(urlText);\n }\n const pos = links2[ln].index;\n if (pos > lastPos) {\n const token = new state.Token(\"text\", \"\", 0);\n token.content = text2.slice(lastPos, pos);\n token.level = level;\n nodes.push(token);\n }\n const token_o = new state.Token(\"link_open\", \"a\", 1);\n token_o.attrs = [[\"href\", fullUrl]];\n token_o.level = level++;\n token_o.markup = \"linkify\";\n token_o.info = \"auto\";\n nodes.push(token_o);\n const token_t = new state.Token(\"text\", \"\", 0);\n token_t.content = urlText;\n token_t.level = level;\n nodes.push(token_t);\n const token_c = new state.Token(\"link_close\", \"a\", -1);\n token_c.level = --level;\n token_c.markup = \"linkify\";\n token_c.info = \"auto\";\n nodes.push(token_c);\n lastPos = links2[ln].lastIndex;\n }\n if (lastPos < text2.length) {\n const token = new state.Token(\"text\", \"\", 0);\n token.content = text2.slice(lastPos);\n token.level = level;\n nodes.push(token);\n }\n blockTokens[j].children = tokens2 = arrayReplaceAt(tokens2, i, nodes);\n }\n }\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/replacements.mjs\nvar RARE_RE = /\\+-|\\.\\.|\\?\\?\\?\\?|!!!!|,,|--/;\nvar SCOPED_ABBR_TEST_RE = /\\((c|tm|r)\\)/i;\nvar SCOPED_ABBR_RE = /\\((c|tm|r)\\)/ig;\nvar SCOPED_ABBR = {\n c: \"©\",\n r: \"®\",\n tm: \"™\"\n};\nfunction replaceFn(match2, name) {\n return SCOPED_ABBR[name.toLowerCase()];\n}\nfunction replace_scoped(inlineTokens) {\n let inside_autolink = 0;\n for (let i = inlineTokens.length - 1; i >= 0; i--) {\n const token = inlineTokens[i];\n if (token.type === \"text\" && !inside_autolink) {\n token.content = token.content.replace(SCOPED_ABBR_RE, replaceFn);\n }\n if (token.type === \"link_open\" && token.info === \"auto\") {\n inside_autolink--;\n }\n if (token.type === \"link_close\" && token.info === \"auto\") {\n inside_autolink++;\n }\n }\n}\nfunction replace_rare(inlineTokens) {\n let inside_autolink = 0;\n for (let i = inlineTokens.length - 1; i >= 0; i--) {\n const token = inlineTokens[i];\n if (token.type === \"text\" && !inside_autolink) {\n if (RARE_RE.test(token.content)) {\n token.content = token.content.replace(/\\+-/g, \"±\").replace(/\\.{2,}/g, \"…\").replace(/([?!])…/g, \"$1..\").replace(/([?!]){4,}/g, \"$1$1$1\").replace(/,{2,}/g, \",\").replace(/(^|[^-])---(?=[^-]|$)/mg, \"$1—\").replace(/(^|\\s)--(?=\\s|$)/mg, \"$1–\").replace(/(^|[^-\\s])--(?=[^-\\s]|$)/mg, \"$1–\");\n }\n }\n if (token.type === \"link_open\" && token.info === \"auto\") {\n inside_autolink--;\n }\n if (token.type === \"link_close\" && token.info === \"auto\") {\n inside_autolink++;\n }\n }\n}\nfunction replace(state) {\n let blkIdx;\n if (!state.md.options.typographer) {\n return;\n }\n for (blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) {\n if (state.tokens[blkIdx].type !== \"inline\") {\n continue;\n }\n if (SCOPED_ABBR_TEST_RE.test(state.tokens[blkIdx].content)) {\n replace_scoped(state.tokens[blkIdx].children);\n }\n if (RARE_RE.test(state.tokens[blkIdx].content)) {\n replace_rare(state.tokens[blkIdx].children);\n }\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/smartquotes.mjs\nvar QUOTE_TEST_RE = /['\"]/;\nvar QUOTE_RE = /['\"]/g;\nvar APOSTROPHE = \"’\";\nfunction replaceAt(str, index, ch) {\n return str.slice(0, index) + ch + str.slice(index + 1);\n}\nfunction process_inlines(tokens2, state) {\n let j;\n const stack = [];\n for (let i = 0; i < tokens2.length; i++) {\n const token = tokens2[i];\n const thisLevel = tokens2[i].level;\n for (j = stack.length - 1; j >= 0; j--) {\n if (stack[j].level <= thisLevel) {\n break;\n }\n }\n stack.length = j + 1;\n if (token.type !== \"text\") {\n continue;\n }\n let text2 = token.content;\n let pos = 0;\n let max = text2.length;\n OUTER:\n while (pos < max) {\n QUOTE_RE.lastIndex = pos;\n const t = QUOTE_RE.exec(text2);\n if (!t) {\n break;\n }\n let canOpen = true;\n let canClose = true;\n pos = t.index + 1;\n const isSingle = t[0] === \"'\";\n let lastChar = 32;\n if (t.index - 1 >= 0) {\n lastChar = text2.charCodeAt(t.index - 1);\n } else {\n for (j = i - 1; j >= 0; j--) {\n if (tokens2[j].type === \"softbreak\" || tokens2[j].type === \"hardbreak\") break;\n if (!tokens2[j].content) continue;\n lastChar = tokens2[j].content.charCodeAt(tokens2[j].content.length - 1);\n break;\n }\n }\n let nextChar = 32;\n if (pos < max) {\n nextChar = text2.charCodeAt(pos);\n } else {\n for (j = i + 1; j < tokens2.length; j++) {\n if (tokens2[j].type === \"softbreak\" || tokens2[j].type === \"hardbreak\") break;\n if (!tokens2[j].content) continue;\n nextChar = tokens2[j].content.charCodeAt(0);\n break;\n }\n }\n const isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar));\n const isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar));\n const isLastWhiteSpace = isWhiteSpace(lastChar);\n const isNextWhiteSpace = isWhiteSpace(nextChar);\n if (isNextWhiteSpace) {\n canOpen = false;\n } else if (isNextPunctChar) {\n if (!(isLastWhiteSpace || isLastPunctChar)) {\n canOpen = false;\n }\n }\n if (isLastWhiteSpace) {\n canClose = false;\n } else if (isLastPunctChar) {\n if (!(isNextWhiteSpace || isNextPunctChar)) {\n canClose = false;\n }\n }\n if (nextChar === 34 && t[0] === '\"') {\n if (lastChar >= 48 && lastChar <= 57) {\n canClose = canOpen = false;\n }\n }\n if (canOpen && canClose) {\n canOpen = isLastPunctChar;\n canClose = isNextPunctChar;\n }\n if (!canOpen && !canClose) {\n if (isSingle) {\n token.content = replaceAt(token.content, t.index, APOSTROPHE);\n }\n continue;\n }\n if (canClose) {\n for (j = stack.length - 1; j >= 0; j--) {\n let item = stack[j];\n if (stack[j].level < thisLevel) {\n break;\n }\n if (item.single === isSingle && stack[j].level === thisLevel) {\n item = stack[j];\n let openQuote;\n let closeQuote;\n if (isSingle) {\n openQuote = state.md.options.quotes[2];\n closeQuote = state.md.options.quotes[3];\n } else {\n openQuote = state.md.options.quotes[0];\n closeQuote = state.md.options.quotes[1];\n }\n token.content = replaceAt(token.content, t.index, closeQuote);\n tokens2[item.token].content = replaceAt(\n tokens2[item.token].content,\n item.pos,\n openQuote\n );\n pos += closeQuote.length - 1;\n if (item.token === i) {\n pos += openQuote.length - 1;\n }\n text2 = token.content;\n max = text2.length;\n stack.length = j;\n continue OUTER;\n }\n }\n }\n if (canOpen) {\n stack.push({\n token: i,\n pos: t.index,\n single: isSingle,\n level: thisLevel\n });\n } else if (canClose && isSingle) {\n token.content = replaceAt(token.content, t.index, APOSTROPHE);\n }\n }\n }\n}\nfunction smartquotes(state) {\n if (!state.md.options.typographer) {\n return;\n }\n for (let blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) {\n if (state.tokens[blkIdx].type !== \"inline\" || !QUOTE_TEST_RE.test(state.tokens[blkIdx].content)) {\n continue;\n }\n process_inlines(state.tokens[blkIdx].children, state);\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/text_join.mjs\nfunction text_join(state) {\n let curr, last;\n const blockTokens = state.tokens;\n const l = blockTokens.length;\n for (let j = 0; j < l; j++) {\n if (blockTokens[j].type !== \"inline\") continue;\n const tokens2 = blockTokens[j].children;\n const max = tokens2.length;\n for (curr = 0; curr < max; curr++) {\n if (tokens2[curr].type === \"text_special\") {\n tokens2[curr].type = \"text\";\n }\n }\n for (curr = last = 0; curr < max; curr++) {\n if (tokens2[curr].type === \"text\" && curr + 1 < max && tokens2[curr + 1].type === \"text\") {\n tokens2[curr + 1].content = tokens2[curr].content + tokens2[curr + 1].content;\n } else {\n if (curr !== last) {\n tokens2[last] = tokens2[curr];\n }\n last++;\n }\n }\n if (curr !== last) {\n tokens2.length = last;\n }\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/parser_core.mjs\nvar _rules = [\n [\"normalize\", normalize],\n [\"block\", block],\n [\"inline\", inline],\n [\"linkify\", linkify],\n [\"replacements\", replace],\n [\"smartquotes\", smartquotes],\n // `text_join` finds `text_special` tokens (for escape sequences)\n // and joins them with the rest of the text\n [\"text_join\", text_join]\n];\nfunction Core() {\n this.ruler = new ruler_default();\n for (let i = 0; i < _rules.length; i++) {\n this.ruler.push(_rules[i][0], _rules[i][1]);\n }\n}\nCore.prototype.process = function(state) {\n const rules = this.ruler.getRules(\"\");\n for (let i = 0, l = rules.length; i < l; i++) {\n rules[i](state);\n }\n};\nCore.prototype.State = state_core_default;\nvar parser_core_default = Core;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/state_block.mjs\nfunction StateBlock(src, md2, env, tokens2) {\n this.src = src;\n this.md = md2;\n this.env = env;\n this.tokens = tokens2;\n this.bMarks = [];\n this.eMarks = [];\n this.tShift = [];\n this.sCount = [];\n this.bsCount = [];\n this.blkIndent = 0;\n this.line = 0;\n this.lineMax = 0;\n this.tight = false;\n this.ddIndent = -1;\n this.listIndent = -1;\n this.parentType = \"root\";\n this.level = 0;\n const s = this.src;\n for (let start = 0, pos = 0, indent = 0, offset = 0, len = s.length, indent_found = false; pos < len; pos++) {\n const ch = s.charCodeAt(pos);\n if (!indent_found) {\n if (isSpace(ch)) {\n indent++;\n if (ch === 9) {\n offset += 4 - offset % 4;\n } else {\n offset++;\n }\n continue;\n } else {\n indent_found = true;\n }\n }\n if (ch === 10 || pos === len - 1) {\n if (ch !== 10) {\n pos++;\n }\n this.bMarks.push(start);\n this.eMarks.push(pos);\n this.tShift.push(indent);\n this.sCount.push(offset);\n this.bsCount.push(0);\n indent_found = false;\n indent = 0;\n offset = 0;\n start = pos + 1;\n }\n }\n this.bMarks.push(s.length);\n this.eMarks.push(s.length);\n this.tShift.push(0);\n this.sCount.push(0);\n this.bsCount.push(0);\n this.lineMax = this.bMarks.length - 1;\n}\nStateBlock.prototype.push = function(type, tag, nesting) {\n const token = new token_default(type, tag, nesting);\n token.block = true;\n if (nesting < 0) this.level--;\n token.level = this.level;\n if (nesting > 0) this.level++;\n this.tokens.push(token);\n return token;\n};\nStateBlock.prototype.isEmpty = function isEmpty(line) {\n return this.bMarks[line] + this.tShift[line] >= this.eMarks[line];\n};\nStateBlock.prototype.skipEmptyLines = function skipEmptyLines(from) {\n for (let max = this.lineMax; from < max; from++) {\n if (this.bMarks[from] + this.tShift[from] < this.eMarks[from]) {\n break;\n }\n }\n return from;\n};\nStateBlock.prototype.skipSpaces = function skipSpaces(pos) {\n for (let max = this.src.length; pos < max; pos++) {\n const ch = this.src.charCodeAt(pos);\n if (!isSpace(ch)) {\n break;\n }\n }\n return pos;\n};\nStateBlock.prototype.skipSpacesBack = function skipSpacesBack(pos, min) {\n if (pos <= min) {\n return pos;\n }\n while (pos > min) {\n if (!isSpace(this.src.charCodeAt(--pos))) {\n return pos + 1;\n }\n }\n return pos;\n};\nStateBlock.prototype.skipChars = function skipChars(pos, code2) {\n for (let max = this.src.length; pos < max; pos++) {\n if (this.src.charCodeAt(pos) !== code2) {\n break;\n }\n }\n return pos;\n};\nStateBlock.prototype.skipCharsBack = function skipCharsBack(pos, code2, min) {\n if (pos <= min) {\n return pos;\n }\n while (pos > min) {\n if (code2 !== this.src.charCodeAt(--pos)) {\n return pos + 1;\n }\n }\n return pos;\n};\nStateBlock.prototype.getLines = function getLines(begin, end, indent, keepLastLF) {\n if (begin >= end) {\n return \"\";\n }\n const queue = new Array(end - begin);\n for (let i = 0, line = begin; line < end; line++, i++) {\n let lineIndent = 0;\n const lineStart = this.bMarks[line];\n let first = lineStart;\n let last;\n if (line + 1 < end || keepLastLF) {\n last = this.eMarks[line] + 1;\n } else {\n last = this.eMarks[line];\n }\n while (first < last && lineIndent < indent) {\n const ch = this.src.charCodeAt(first);\n if (isSpace(ch)) {\n if (ch === 9) {\n lineIndent += 4 - (lineIndent + this.bsCount[line]) % 4;\n } else {\n lineIndent++;\n }\n } else if (first - lineStart < this.tShift[line]) {\n lineIndent++;\n } else {\n break;\n }\n first++;\n }\n if (lineIndent > indent) {\n queue[i] = new Array(lineIndent - indent + 1).join(\" \") + this.src.slice(first, last);\n } else {\n queue[i] = this.src.slice(first, last);\n }\n }\n return queue.join(\"\");\n};\nStateBlock.prototype.Token = token_default;\nvar state_block_default = StateBlock;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/table.mjs\nvar MAX_AUTOCOMPLETED_CELLS = 65536;\nfunction getLine(state, line) {\n const pos = state.bMarks[line] + state.tShift[line];\n const max = state.eMarks[line];\n return state.src.slice(pos, max);\n}\nfunction escapedSplit(str) {\n const result = [];\n const max = str.length;\n let pos = 0;\n let ch = str.charCodeAt(pos);\n let isEscaped = false;\n let lastPos = 0;\n let current = \"\";\n while (pos < max) {\n if (ch === 124) {\n if (!isEscaped) {\n result.push(current + str.substring(lastPos, pos));\n current = \"\";\n lastPos = pos + 1;\n } else {\n current += str.substring(lastPos, pos - 1);\n lastPos = pos;\n }\n }\n isEscaped = ch === 92;\n pos++;\n ch = str.charCodeAt(pos);\n }\n result.push(current + str.substring(lastPos));\n return result;\n}\nfunction table(state, startLine, endLine, silent) {\n if (startLine + 2 > endLine) {\n return false;\n }\n let nextLine = startLine + 1;\n if (state.sCount[nextLine] < state.blkIndent) {\n return false;\n }\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\n return false;\n }\n let pos = state.bMarks[nextLine] + state.tShift[nextLine];\n if (pos >= state.eMarks[nextLine]) {\n return false;\n }\n const firstCh = state.src.charCodeAt(pos++);\n if (firstCh !== 124 && firstCh !== 45 && firstCh !== 58) {\n return false;\n }\n if (pos >= state.eMarks[nextLine]) {\n return false;\n }\n const secondCh = state.src.charCodeAt(pos++);\n if (secondCh !== 124 && secondCh !== 45 && secondCh !== 58 && !isSpace(secondCh)) {\n return false;\n }\n if (firstCh === 45 && isSpace(secondCh)) {\n return false;\n }\n while (pos < state.eMarks[nextLine]) {\n const ch = state.src.charCodeAt(pos);\n if (ch !== 124 && ch !== 45 && ch !== 58 && !isSpace(ch)) {\n return false;\n }\n pos++;\n }\n let lineText = getLine(state, startLine + 1);\n let columns = lineText.split(\"|\");\n const aligns = [];\n for (let i = 0; i < columns.length; i++) {\n const t = columns[i].trim();\n if (!t) {\n if (i === 0 || i === columns.length - 1) {\n continue;\n } else {\n return false;\n }\n }\n if (!/^:?-+:?$/.test(t)) {\n return false;\n }\n if (t.charCodeAt(t.length - 1) === 58) {\n aligns.push(t.charCodeAt(0) === 58 ? \"center\" : \"right\");\n } else if (t.charCodeAt(0) === 58) {\n aligns.push(\"left\");\n } else {\n aligns.push(\"\");\n }\n }\n lineText = getLine(state, startLine).trim();\n if (lineText.indexOf(\"|\") === -1) {\n return false;\n }\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n columns = escapedSplit(lineText);\n if (columns.length && columns[0] === \"\") columns.shift();\n if (columns.length && columns[columns.length - 1] === \"\") columns.pop();\n const columnCount = columns.length;\n if (columnCount === 0 || columnCount !== aligns.length) {\n return false;\n }\n if (silent) {\n return true;\n }\n const oldParentType = state.parentType;\n state.parentType = \"table\";\n const terminatorRules = state.md.block.ruler.getRules(\"blockquote\");\n const token_to = state.push(\"table_open\", \"table\", 1);\n const tableLines = [startLine, 0];\n token_to.map = tableLines;\n const token_tho = state.push(\"thead_open\", \"thead\", 1);\n token_tho.map = [startLine, startLine + 1];\n const token_htro = state.push(\"tr_open\", \"tr\", 1);\n token_htro.map = [startLine, startLine + 1];\n for (let i = 0; i < columns.length; i++) {\n const token_ho = state.push(\"th_open\", \"th\", 1);\n if (aligns[i]) {\n token_ho.attrs = [[\"style\", \"text-align:\" + aligns[i]]];\n }\n const token_il = state.push(\"inline\", \"\", 0);\n token_il.content = columns[i].trim();\n token_il.children = [];\n state.push(\"th_close\", \"th\", -1);\n }\n state.push(\"tr_close\", \"tr\", -1);\n state.push(\"thead_close\", \"thead\", -1);\n let tbodyLines;\n let autocompletedCells = 0;\n for (nextLine = startLine + 2; nextLine < endLine; nextLine++) {\n if (state.sCount[nextLine] < state.blkIndent) {\n break;\n }\n let terminate = false;\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\n if (terminatorRules[i](state, nextLine, endLine, true)) {\n terminate = true;\n break;\n }\n }\n if (terminate) {\n break;\n }\n lineText = getLine(state, nextLine).trim();\n if (!lineText) {\n break;\n }\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\n break;\n }\n columns = escapedSplit(lineText);\n if (columns.length && columns[0] === \"\") columns.shift();\n if (columns.length && columns[columns.length - 1] === \"\") columns.pop();\n autocompletedCells += columnCount - columns.length;\n if (autocompletedCells > MAX_AUTOCOMPLETED_CELLS) {\n break;\n }\n if (nextLine === startLine + 2) {\n const token_tbo = state.push(\"tbody_open\", \"tbody\", 1);\n token_tbo.map = tbodyLines = [startLine + 2, 0];\n }\n const token_tro = state.push(\"tr_open\", \"tr\", 1);\n token_tro.map = [nextLine, nextLine + 1];\n for (let i = 0; i < columnCount; i++) {\n const token_tdo = state.push(\"td_open\", \"td\", 1);\n if (aligns[i]) {\n token_tdo.attrs = [[\"style\", \"text-align:\" + aligns[i]]];\n }\n const token_il = state.push(\"inline\", \"\", 0);\n token_il.content = columns[i] ? columns[i].trim() : \"\";\n token_il.children = [];\n state.push(\"td_close\", \"td\", -1);\n }\n state.push(\"tr_close\", \"tr\", -1);\n }\n if (tbodyLines) {\n state.push(\"tbody_close\", \"tbody\", -1);\n tbodyLines[1] = nextLine;\n }\n state.push(\"table_close\", \"table\", -1);\n tableLines[1] = nextLine;\n state.parentType = oldParentType;\n state.line = nextLine;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/code.mjs\nfunction code(state, startLine, endLine) {\n if (state.sCount[startLine] - state.blkIndent < 4) {\n return false;\n }\n let nextLine = startLine + 1;\n let last = nextLine;\n while (nextLine < endLine) {\n if (state.isEmpty(nextLine)) {\n nextLine++;\n continue;\n }\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\n nextLine++;\n last = nextLine;\n continue;\n }\n break;\n }\n state.line = last;\n const token = state.push(\"code_block\", \"code\", 0);\n token.content = state.getLines(startLine, last, 4 + state.blkIndent, false) + \"\\n\";\n token.map = [startLine, state.line];\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/fence.mjs\nfunction fence(state, startLine, endLine, silent) {\n let pos = state.bMarks[startLine] + state.tShift[startLine];\n let max = state.eMarks[startLine];\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n if (pos + 3 > max) {\n return false;\n }\n const marker = state.src.charCodeAt(pos);\n if (marker !== 126 && marker !== 96) {\n return false;\n }\n let mem = pos;\n pos = state.skipChars(pos, marker);\n let len = pos - mem;\n if (len < 3) {\n return false;\n }\n const markup = state.src.slice(mem, pos);\n const params = state.src.slice(pos, max);\n if (marker === 96) {\n if (params.indexOf(String.fromCharCode(marker)) >= 0) {\n return false;\n }\n }\n if (silent) {\n return true;\n }\n let nextLine = startLine;\n let haveEndMarker = false;\n for (; ; ) {\n nextLine++;\n if (nextLine >= endLine) {\n break;\n }\n pos = mem = state.bMarks[nextLine] + state.tShift[nextLine];\n max = state.eMarks[nextLine];\n if (pos < max && state.sCount[nextLine] < state.blkIndent) {\n break;\n }\n if (state.src.charCodeAt(pos) !== marker) {\n continue;\n }\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\n continue;\n }\n pos = state.skipChars(pos, marker);\n if (pos - mem < len) {\n continue;\n }\n pos = state.skipSpaces(pos);\n if (pos < max) {\n continue;\n }\n haveEndMarker = true;\n break;\n }\n len = state.sCount[startLine];\n state.line = nextLine + (haveEndMarker ? 1 : 0);\n const token = state.push(\"fence\", \"code\", 0);\n token.info = params;\n token.content = state.getLines(startLine + 1, nextLine, len, true);\n token.markup = markup;\n token.map = [startLine, state.line];\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/blockquote.mjs\nfunction blockquote(state, startLine, endLine, silent) {\n let pos = state.bMarks[startLine] + state.tShift[startLine];\n let max = state.eMarks[startLine];\n const oldLineMax = state.lineMax;\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n if (state.src.charCodeAt(pos) !== 62) {\n return false;\n }\n if (silent) {\n return true;\n }\n const oldBMarks = [];\n const oldBSCount = [];\n const oldSCount = [];\n const oldTShift = [];\n const terminatorRules = state.md.block.ruler.getRules(\"blockquote\");\n const oldParentType = state.parentType;\n state.parentType = \"blockquote\";\n let lastLineEmpty = false;\n let nextLine;\n for (nextLine = startLine; nextLine < endLine; nextLine++) {\n const isOutdented = state.sCount[nextLine] < state.blkIndent;\n pos = state.bMarks[nextLine] + state.tShift[nextLine];\n max = state.eMarks[nextLine];\n if (pos >= max) {\n break;\n }\n if (state.src.charCodeAt(pos++) === 62 && !isOutdented) {\n let initial = state.sCount[nextLine] + 1;\n let spaceAfterMarker;\n let adjustTab;\n if (state.src.charCodeAt(pos) === 32) {\n pos++;\n initial++;\n adjustTab = false;\n spaceAfterMarker = true;\n } else if (state.src.charCodeAt(pos) === 9) {\n spaceAfterMarker = true;\n if ((state.bsCount[nextLine] + initial) % 4 === 3) {\n pos++;\n initial++;\n adjustTab = false;\n } else {\n adjustTab = true;\n }\n } else {\n spaceAfterMarker = false;\n }\n let offset = initial;\n oldBMarks.push(state.bMarks[nextLine]);\n state.bMarks[nextLine] = pos;\n while (pos < max) {\n const ch = state.src.charCodeAt(pos);\n if (isSpace(ch)) {\n if (ch === 9) {\n offset += 4 - (offset + state.bsCount[nextLine] + (adjustTab ? 1 : 0)) % 4;\n } else {\n offset++;\n }\n } else {\n break;\n }\n pos++;\n }\n lastLineEmpty = pos >= max;\n oldBSCount.push(state.bsCount[nextLine]);\n state.bsCount[nextLine] = state.sCount[nextLine] + 1 + (spaceAfterMarker ? 1 : 0);\n oldSCount.push(state.sCount[nextLine]);\n state.sCount[nextLine] = offset - initial;\n oldTShift.push(state.tShift[nextLine]);\n state.tShift[nextLine] = pos - state.bMarks[nextLine];\n continue;\n }\n if (lastLineEmpty) {\n break;\n }\n let terminate = false;\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\n if (terminatorRules[i](state, nextLine, endLine, true)) {\n terminate = true;\n break;\n }\n }\n if (terminate) {\n state.lineMax = nextLine;\n if (state.blkIndent !== 0) {\n oldBMarks.push(state.bMarks[nextLine]);\n oldBSCount.push(state.bsCount[nextLine]);\n oldTShift.push(state.tShift[nextLine]);\n oldSCount.push(state.sCount[nextLine]);\n state.sCount[nextLine] -= state.blkIndent;\n }\n break;\n }\n oldBMarks.push(state.bMarks[nextLine]);\n oldBSCount.push(state.bsCount[nextLine]);\n oldTShift.push(state.tShift[nextLine]);\n oldSCount.push(state.sCount[nextLine]);\n state.sCount[nextLine] = -1;\n }\n const oldIndent = state.blkIndent;\n state.blkIndent = 0;\n const token_o = state.push(\"blockquote_open\", \"blockquote\", 1);\n token_o.markup = \">\";\n const lines = [startLine, 0];\n token_o.map = lines;\n state.md.block.tokenize(state, startLine, nextLine);\n const token_c = state.push(\"blockquote_close\", \"blockquote\", -1);\n token_c.markup = \">\";\n state.lineMax = oldLineMax;\n state.parentType = oldParentType;\n lines[1] = state.line;\n for (let i = 0; i < oldTShift.length; i++) {\n state.bMarks[i + startLine] = oldBMarks[i];\n state.tShift[i + startLine] = oldTShift[i];\n state.sCount[i + startLine] = oldSCount[i];\n state.bsCount[i + startLine] = oldBSCount[i];\n }\n state.blkIndent = oldIndent;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/hr.mjs\nfunction hr(state, startLine, endLine, silent) {\n const max = state.eMarks[startLine];\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n let pos = state.bMarks[startLine] + state.tShift[startLine];\n const marker = state.src.charCodeAt(pos++);\n if (marker !== 42 && marker !== 45 && marker !== 95) {\n return false;\n }\n let cnt = 1;\n while (pos < max) {\n const ch = state.src.charCodeAt(pos++);\n if (ch !== marker && !isSpace(ch)) {\n return false;\n }\n if (ch === marker) {\n cnt++;\n }\n }\n if (cnt < 3) {\n return false;\n }\n if (silent) {\n return true;\n }\n state.line = startLine + 1;\n const token = state.push(\"hr\", \"hr\", 0);\n token.map = [startLine, state.line];\n token.markup = Array(cnt + 1).join(String.fromCharCode(marker));\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/list.mjs\nfunction skipBulletListMarker(state, startLine) {\n const max = state.eMarks[startLine];\n let pos = state.bMarks[startLine] + state.tShift[startLine];\n const marker = state.src.charCodeAt(pos++);\n if (marker !== 42 && marker !== 45 && marker !== 43) {\n return -1;\n }\n if (pos < max) {\n const ch = state.src.charCodeAt(pos);\n if (!isSpace(ch)) {\n return -1;\n }\n }\n return pos;\n}\nfunction skipOrderedListMarker(state, startLine) {\n const start = state.bMarks[startLine] + state.tShift[startLine];\n const max = state.eMarks[startLine];\n let pos = start;\n if (pos + 1 >= max) {\n return -1;\n }\n let ch = state.src.charCodeAt(pos++);\n if (ch < 48 || ch > 57) {\n return -1;\n }\n for (; ; ) {\n if (pos >= max) {\n return -1;\n }\n ch = state.src.charCodeAt(pos++);\n if (ch >= 48 && ch <= 57) {\n if (pos - start >= 10) {\n return -1;\n }\n continue;\n }\n if (ch === 41 || ch === 46) {\n break;\n }\n return -1;\n }\n if (pos < max) {\n ch = state.src.charCodeAt(pos);\n if (!isSpace(ch)) {\n return -1;\n }\n }\n return pos;\n}\nfunction markTightParagraphs(state, idx) {\n const level = state.level + 2;\n for (let i = idx + 2, l = state.tokens.length - 2; i < l; i++) {\n if (state.tokens[i].level === level && state.tokens[i].type === \"paragraph_open\") {\n state.tokens[i + 2].hidden = true;\n state.tokens[i].hidden = true;\n i += 2;\n }\n }\n}\nfunction list(state, startLine, endLine, silent) {\n let max, pos, start, token;\n let nextLine = startLine;\n let tight = true;\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\n return false;\n }\n if (state.listIndent >= 0 && state.sCount[nextLine] - state.listIndent >= 4 && state.sCount[nextLine] < state.blkIndent) {\n return false;\n }\n let isTerminatingParagraph = false;\n if (silent && state.parentType === \"paragraph\") {\n if (state.sCount[nextLine] >= state.blkIndent) {\n isTerminatingParagraph = true;\n }\n }\n let isOrdered;\n let markerValue;\n let posAfterMarker;\n if ((posAfterMarker = skipOrderedListMarker(state, nextLine)) >= 0) {\n isOrdered = true;\n start = state.bMarks[nextLine] + state.tShift[nextLine];\n markerValue = Number(state.src.slice(start, posAfterMarker - 1));\n if (isTerminatingParagraph && markerValue !== 1) return false;\n } else if ((posAfterMarker = skipBulletListMarker(state, nextLine)) >= 0) {\n isOrdered = false;\n } else {\n return false;\n }\n if (isTerminatingParagraph) {\n if (state.skipSpaces(posAfterMarker) >= state.eMarks[nextLine]) return false;\n }\n if (silent) {\n return true;\n }\n const markerCharCode = state.src.charCodeAt(posAfterMarker - 1);\n const listTokIdx = state.tokens.length;\n if (isOrdered) {\n token = state.push(\"ordered_list_open\", \"ol\", 1);\n if (markerValue !== 1) {\n token.attrs = [[\"start\", markerValue]];\n }\n } else {\n token = state.push(\"bullet_list_open\", \"ul\", 1);\n }\n const listLines = [nextLine, 0];\n token.map = listLines;\n token.markup = String.fromCharCode(markerCharCode);\n let prevEmptyEnd = false;\n const terminatorRules = state.md.block.ruler.getRules(\"list\");\n const oldParentType = state.parentType;\n state.parentType = \"list\";\n while (nextLine < endLine) {\n pos = posAfterMarker;\n max = state.eMarks[nextLine];\n const initial = state.sCount[nextLine] + posAfterMarker - (state.bMarks[nextLine] + state.tShift[nextLine]);\n let offset = initial;\n while (pos < max) {\n const ch = state.src.charCodeAt(pos);\n if (ch === 9) {\n offset += 4 - (offset + state.bsCount[nextLine]) % 4;\n } else if (ch === 32) {\n offset++;\n } else {\n break;\n }\n pos++;\n }\n const contentStart = pos;\n let indentAfterMarker;\n if (contentStart >= max) {\n indentAfterMarker = 1;\n } else {\n indentAfterMarker = offset - initial;\n }\n if (indentAfterMarker > 4) {\n indentAfterMarker = 1;\n }\n const indent = initial + indentAfterMarker;\n token = state.push(\"list_item_open\", \"li\", 1);\n token.markup = String.fromCharCode(markerCharCode);\n const itemLines = [nextLine, 0];\n token.map = itemLines;\n if (isOrdered) {\n token.info = state.src.slice(start, posAfterMarker - 1);\n }\n const oldTight = state.tight;\n const oldTShift = state.tShift[nextLine];\n const oldSCount = state.sCount[nextLine];\n const oldListIndent = state.listIndent;\n state.listIndent = state.blkIndent;\n state.blkIndent = indent;\n state.tight = true;\n state.tShift[nextLine] = contentStart - state.bMarks[nextLine];\n state.sCount[nextLine] = offset;\n if (contentStart >= max && state.isEmpty(nextLine + 1)) {\n state.line = Math.min(state.line + 2, endLine);\n } else {\n state.md.block.tokenize(state, nextLine, endLine, true);\n }\n if (!state.tight || prevEmptyEnd) {\n tight = false;\n }\n prevEmptyEnd = state.line - nextLine > 1 && state.isEmpty(state.line - 1);\n state.blkIndent = state.listIndent;\n state.listIndent = oldListIndent;\n state.tShift[nextLine] = oldTShift;\n state.sCount[nextLine] = oldSCount;\n state.tight = oldTight;\n token = state.push(\"list_item_close\", \"li\", -1);\n token.markup = String.fromCharCode(markerCharCode);\n nextLine = state.line;\n itemLines[1] = nextLine;\n if (nextLine >= endLine) {\n break;\n }\n if (state.sCount[nextLine] < state.blkIndent) {\n break;\n }\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\n break;\n }\n let terminate = false;\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\n if (terminatorRules[i](state, nextLine, endLine, true)) {\n terminate = true;\n break;\n }\n }\n if (terminate) {\n break;\n }\n if (isOrdered) {\n posAfterMarker = skipOrderedListMarker(state, nextLine);\n if (posAfterMarker < 0) {\n break;\n }\n start = state.bMarks[nextLine] + state.tShift[nextLine];\n } else {\n posAfterMarker = skipBulletListMarker(state, nextLine);\n if (posAfterMarker < 0) {\n break;\n }\n }\n if (markerCharCode !== state.src.charCodeAt(posAfterMarker - 1)) {\n break;\n }\n }\n if (isOrdered) {\n token = state.push(\"ordered_list_close\", \"ol\", -1);\n } else {\n token = state.push(\"bullet_list_close\", \"ul\", -1);\n }\n token.markup = String.fromCharCode(markerCharCode);\n listLines[1] = nextLine;\n state.line = nextLine;\n state.parentType = oldParentType;\n if (tight) {\n markTightParagraphs(state, listTokIdx);\n }\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/reference.mjs\nfunction reference(state, startLine, _endLine, silent) {\n let pos = state.bMarks[startLine] + state.tShift[startLine];\n let max = state.eMarks[startLine];\n let nextLine = startLine + 1;\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n if (state.src.charCodeAt(pos) !== 91) {\n return false;\n }\n function getNextLine(nextLine2) {\n const endLine = state.lineMax;\n if (nextLine2 >= endLine || state.isEmpty(nextLine2)) {\n return null;\n }\n let isContinuation = false;\n if (state.sCount[nextLine2] - state.blkIndent > 3) {\n isContinuation = true;\n }\n if (state.sCount[nextLine2] < 0) {\n isContinuation = true;\n }\n if (!isContinuation) {\n const terminatorRules = state.md.block.ruler.getRules(\"reference\");\n const oldParentType = state.parentType;\n state.parentType = \"reference\";\n let terminate = false;\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\n if (terminatorRules[i](state, nextLine2, endLine, true)) {\n terminate = true;\n break;\n }\n }\n state.parentType = oldParentType;\n if (terminate) {\n return null;\n }\n }\n const pos2 = state.bMarks[nextLine2] + state.tShift[nextLine2];\n const max2 = state.eMarks[nextLine2];\n return state.src.slice(pos2, max2 + 1);\n }\n let str = state.src.slice(pos, max + 1);\n max = str.length;\n let labelEnd = -1;\n for (pos = 1; pos < max; pos++) {\n const ch = str.charCodeAt(pos);\n if (ch === 91) {\n return false;\n } else if (ch === 93) {\n labelEnd = pos;\n break;\n } else if (ch === 10) {\n const lineContent = getNextLine(nextLine);\n if (lineContent !== null) {\n str += lineContent;\n max = str.length;\n nextLine++;\n }\n } else if (ch === 92) {\n pos++;\n if (pos < max && str.charCodeAt(pos) === 10) {\n const lineContent = getNextLine(nextLine);\n if (lineContent !== null) {\n str += lineContent;\n max = str.length;\n nextLine++;\n }\n }\n }\n }\n if (labelEnd < 0 || str.charCodeAt(labelEnd + 1) !== 58) {\n return false;\n }\n for (pos = labelEnd + 2; pos < max; pos++) {\n const ch = str.charCodeAt(pos);\n if (ch === 10) {\n const lineContent = getNextLine(nextLine);\n if (lineContent !== null) {\n str += lineContent;\n max = str.length;\n nextLine++;\n }\n } else if (isSpace(ch)) {\n } else {\n break;\n }\n }\n const destRes = state.md.helpers.parseLinkDestination(str, pos, max);\n if (!destRes.ok) {\n return false;\n }\n const href = state.md.normalizeLink(destRes.str);\n if (!state.md.validateLink(href)) {\n return false;\n }\n pos = destRes.pos;\n const destEndPos = pos;\n const destEndLineNo = nextLine;\n const start = pos;\n for (; pos < max; pos++) {\n const ch = str.charCodeAt(pos);\n if (ch === 10) {\n const lineContent = getNextLine(nextLine);\n if (lineContent !== null) {\n str += lineContent;\n max = str.length;\n nextLine++;\n }\n } else if (isSpace(ch)) {\n } else {\n break;\n }\n }\n let titleRes = state.md.helpers.parseLinkTitle(str, pos, max);\n while (titleRes.can_continue) {\n const lineContent = getNextLine(nextLine);\n if (lineContent === null) break;\n str += lineContent;\n pos = max;\n max = str.length;\n nextLine++;\n titleRes = state.md.helpers.parseLinkTitle(str, pos, max, titleRes);\n }\n let title;\n if (pos < max && start !== pos && titleRes.ok) {\n title = titleRes.str;\n pos = titleRes.pos;\n } else {\n title = \"\";\n pos = destEndPos;\n nextLine = destEndLineNo;\n }\n while (pos < max) {\n const ch = str.charCodeAt(pos);\n if (!isSpace(ch)) {\n break;\n }\n pos++;\n }\n if (pos < max && str.charCodeAt(pos) !== 10) {\n if (title) {\n title = \"\";\n pos = destEndPos;\n nextLine = destEndLineNo;\n while (pos < max) {\n const ch = str.charCodeAt(pos);\n if (!isSpace(ch)) {\n break;\n }\n pos++;\n }\n }\n }\n if (pos < max && str.charCodeAt(pos) !== 10) {\n return false;\n }\n const label = normalizeReference(str.slice(1, labelEnd));\n if (!label) {\n return false;\n }\n if (silent) {\n return true;\n }\n if (typeof state.env.references === \"undefined\") {\n state.env.references = {};\n }\n if (typeof state.env.references[label] === \"undefined\") {\n state.env.references[label] = { title, href };\n }\n state.line = nextLine;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/common/html_blocks.mjs\nvar html_blocks_default = [\n \"address\",\n \"article\",\n \"aside\",\n \"base\",\n \"basefont\",\n \"blockquote\",\n \"body\",\n \"caption\",\n \"center\",\n \"col\",\n \"colgroup\",\n \"dd\",\n \"details\",\n \"dialog\",\n \"dir\",\n \"div\",\n \"dl\",\n \"dt\",\n \"fieldset\",\n \"figcaption\",\n \"figure\",\n \"footer\",\n \"form\",\n \"frame\",\n \"frameset\",\n \"h1\",\n \"h2\",\n \"h3\",\n \"h4\",\n \"h5\",\n \"h6\",\n \"head\",\n \"header\",\n \"hr\",\n \"html\",\n \"iframe\",\n \"legend\",\n \"li\",\n \"link\",\n \"main\",\n \"menu\",\n \"menuitem\",\n \"nav\",\n \"noframes\",\n \"ol\",\n \"optgroup\",\n \"option\",\n \"p\",\n \"param\",\n \"search\",\n \"section\",\n \"summary\",\n \"table\",\n \"tbody\",\n \"td\",\n \"tfoot\",\n \"th\",\n \"thead\",\n \"title\",\n \"tr\",\n \"track\",\n \"ul\"\n];\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/common/html_re.mjs\nvar attr_name = \"[a-zA-Z_:][a-zA-Z0-9:._-]*\";\nvar unquoted = \"[^\\\"'=<>`\\\\x00-\\\\x20]+\";\nvar single_quoted = \"'[^']*'\";\nvar double_quoted = '\"[^\"]*\"';\nvar attr_value = \"(?:\" + unquoted + \"|\" + single_quoted + \"|\" + double_quoted + \")\";\nvar attribute = \"(?:\\\\s+\" + attr_name + \"(?:\\\\s*=\\\\s*\" + attr_value + \")?)\";\nvar open_tag = \"<[A-Za-z][A-Za-z0-9\\\\-]*\" + attribute + \"*\\\\s*\\\\/?>\";\nvar close_tag = \"<\\\\/[A-Za-z][A-Za-z0-9\\\\-]*\\\\s*>\";\nvar comment = \"\";\nvar processing = \"<[?][\\\\s\\\\S]*?[?]>\";\nvar declaration = \"]*>\";\nvar cdata = \"\";\nvar HTML_TAG_RE = new RegExp(\"^(?:\" + open_tag + \"|\" + close_tag + \"|\" + comment + \"|\" + processing + \"|\" + declaration + \"|\" + cdata + \")\");\nvar HTML_OPEN_CLOSE_TAG_RE = new RegExp(\"^(?:\" + open_tag + \"|\" + close_tag + \")\");\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/html_block.mjs\nvar HTML_SEQUENCES = [\n [/^<(script|pre|style|textarea)(?=(\\s|>|$))/i, /<\\/(script|pre|style|textarea)>/i, true],\n [/^/, true],\n [/^<\\?/, /\\?>/, true],\n [/^/, true],\n [/^/, true],\n [new RegExp(\"^|$))\", \"i\"), /^$/, true],\n [new RegExp(HTML_OPEN_CLOSE_TAG_RE.source + \"\\\\s*$\"), /^$/, false]\n];\nfunction html_block(state, startLine, endLine, silent) {\n let pos = state.bMarks[startLine] + state.tShift[startLine];\n let max = state.eMarks[startLine];\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n if (!state.md.options.html) {\n return false;\n }\n if (state.src.charCodeAt(pos) !== 60) {\n return false;\n }\n let lineText = state.src.slice(pos, max);\n let i = 0;\n for (; i < HTML_SEQUENCES.length; i++) {\n if (HTML_SEQUENCES[i][0].test(lineText)) {\n break;\n }\n }\n if (i === HTML_SEQUENCES.length) {\n return false;\n }\n if (silent) {\n return HTML_SEQUENCES[i][2];\n }\n let nextLine = startLine + 1;\n if (!HTML_SEQUENCES[i][1].test(lineText)) {\n for (; nextLine < endLine; nextLine++) {\n if (state.sCount[nextLine] < state.blkIndent) {\n break;\n }\n pos = state.bMarks[nextLine] + state.tShift[nextLine];\n max = state.eMarks[nextLine];\n lineText = state.src.slice(pos, max);\n if (HTML_SEQUENCES[i][1].test(lineText)) {\n if (lineText.length !== 0) {\n nextLine++;\n }\n break;\n }\n }\n }\n state.line = nextLine;\n const token = state.push(\"html_block\", \"\", 0);\n token.map = [startLine, nextLine];\n token.content = state.getLines(startLine, nextLine, state.blkIndent, true);\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/heading.mjs\nfunction heading(state, startLine, endLine, silent) {\n let pos = state.bMarks[startLine] + state.tShift[startLine];\n let max = state.eMarks[startLine];\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n let ch = state.src.charCodeAt(pos);\n if (ch !== 35 || pos >= max) {\n return false;\n }\n let level = 1;\n ch = state.src.charCodeAt(++pos);\n while (ch === 35 && pos < max && level <= 6) {\n level++;\n ch = state.src.charCodeAt(++pos);\n }\n if (level > 6 || pos < max && !isSpace(ch)) {\n return false;\n }\n if (silent) {\n return true;\n }\n max = state.skipSpacesBack(max, pos);\n const tmp = state.skipCharsBack(max, 35, pos);\n if (tmp > pos && isSpace(state.src.charCodeAt(tmp - 1))) {\n max = tmp;\n }\n state.line = startLine + 1;\n const token_o = state.push(\"heading_open\", \"h\" + String(level), 1);\n token_o.markup = \"########\".slice(0, level);\n token_o.map = [startLine, state.line];\n const token_i = state.push(\"inline\", \"\", 0);\n token_i.content = state.src.slice(pos, max).trim();\n token_i.map = [startLine, state.line];\n token_i.children = [];\n const token_c = state.push(\"heading_close\", \"h\" + String(level), -1);\n token_c.markup = \"########\".slice(0, level);\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/lheading.mjs\nfunction lheading(state, startLine, endLine) {\n const terminatorRules = state.md.block.ruler.getRules(\"paragraph\");\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n const oldParentType = state.parentType;\n state.parentType = \"paragraph\";\n let level = 0;\n let marker;\n let nextLine = startLine + 1;\n for (; nextLine < endLine && !state.isEmpty(nextLine); nextLine++) {\n if (state.sCount[nextLine] - state.blkIndent > 3) {\n continue;\n }\n if (state.sCount[nextLine] >= state.blkIndent) {\n let pos = state.bMarks[nextLine] + state.tShift[nextLine];\n const max = state.eMarks[nextLine];\n if (pos < max) {\n marker = state.src.charCodeAt(pos);\n if (marker === 45 || marker === 61) {\n pos = state.skipChars(pos, marker);\n pos = state.skipSpaces(pos);\n if (pos >= max) {\n level = marker === 61 ? 1 : 2;\n break;\n }\n }\n }\n }\n if (state.sCount[nextLine] < 0) {\n continue;\n }\n let terminate = false;\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\n if (terminatorRules[i](state, nextLine, endLine, true)) {\n terminate = true;\n break;\n }\n }\n if (terminate) {\n break;\n }\n }\n if (!level) {\n return false;\n }\n const content = state.getLines(startLine, nextLine, state.blkIndent, false).trim();\n state.line = nextLine + 1;\n const token_o = state.push(\"heading_open\", \"h\" + String(level), 1);\n token_o.markup = String.fromCharCode(marker);\n token_o.map = [startLine, state.line];\n const token_i = state.push(\"inline\", \"\", 0);\n token_i.content = content;\n token_i.map = [startLine, state.line - 1];\n token_i.children = [];\n const token_c = state.push(\"heading_close\", \"h\" + String(level), -1);\n token_c.markup = String.fromCharCode(marker);\n state.parentType = oldParentType;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/paragraph.mjs\nfunction paragraph(state, startLine, endLine) {\n const terminatorRules = state.md.block.ruler.getRules(\"paragraph\");\n const oldParentType = state.parentType;\n let nextLine = startLine + 1;\n state.parentType = \"paragraph\";\n for (; nextLine < endLine && !state.isEmpty(nextLine); nextLine++) {\n if (state.sCount[nextLine] - state.blkIndent > 3) {\n continue;\n }\n if (state.sCount[nextLine] < 0) {\n continue;\n }\n let terminate = false;\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\n if (terminatorRules[i](state, nextLine, endLine, true)) {\n terminate = true;\n break;\n }\n }\n if (terminate) {\n break;\n }\n }\n const content = state.getLines(startLine, nextLine, state.blkIndent, false).trim();\n state.line = nextLine;\n const token_o = state.push(\"paragraph_open\", \"p\", 1);\n token_o.map = [startLine, state.line];\n const token_i = state.push(\"inline\", \"\", 0);\n token_i.content = content;\n token_i.map = [startLine, state.line];\n token_i.children = [];\n state.push(\"paragraph_close\", \"p\", -1);\n state.parentType = oldParentType;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/parser_block.mjs\nvar _rules2 = [\n // First 2 params - rule name & source. Secondary array - list of rules,\n // which can be terminated by this one.\n [\"table\", table, [\"paragraph\", \"reference\"]],\n [\"code\", code],\n [\"fence\", fence, [\"paragraph\", \"reference\", \"blockquote\", \"list\"]],\n [\"blockquote\", blockquote, [\"paragraph\", \"reference\", \"blockquote\", \"list\"]],\n [\"hr\", hr, [\"paragraph\", \"reference\", \"blockquote\", \"list\"]],\n [\"list\", list, [\"paragraph\", \"reference\", \"blockquote\"]],\n [\"reference\", reference],\n [\"html_block\", html_block, [\"paragraph\", \"reference\", \"blockquote\"]],\n [\"heading\", heading, [\"paragraph\", \"reference\", \"blockquote\"]],\n [\"lheading\", lheading],\n [\"paragraph\", paragraph]\n];\nfunction ParserBlock() {\n this.ruler = new ruler_default();\n for (let i = 0; i < _rules2.length; i++) {\n this.ruler.push(_rules2[i][0], _rules2[i][1], { alt: (_rules2[i][2] || []).slice() });\n }\n}\nParserBlock.prototype.tokenize = function(state, startLine, endLine) {\n const rules = this.ruler.getRules(\"\");\n const len = rules.length;\n const maxNesting = state.md.options.maxNesting;\n let line = startLine;\n let hasEmptyLines = false;\n while (line < endLine) {\n state.line = line = state.skipEmptyLines(line);\n if (line >= endLine) {\n break;\n }\n if (state.sCount[line] < state.blkIndent) {\n break;\n }\n if (state.level >= maxNesting) {\n state.line = endLine;\n break;\n }\n const prevLine = state.line;\n let ok = false;\n for (let i = 0; i < len; i++) {\n ok = rules[i](state, line, endLine, false);\n if (ok) {\n if (prevLine >= state.line) {\n throw new Error(\"block rule didn't increment state.line\");\n }\n break;\n }\n }\n if (!ok) throw new Error(\"none of the block rules matched\");\n state.tight = !hasEmptyLines;\n if (state.isEmpty(state.line - 1)) {\n hasEmptyLines = true;\n }\n line = state.line;\n if (line < endLine && state.isEmpty(line)) {\n hasEmptyLines = true;\n line++;\n state.line = line;\n }\n }\n};\nParserBlock.prototype.parse = function(src, md2, env, outTokens) {\n if (!src) {\n return;\n }\n const state = new this.State(src, md2, env, outTokens);\n this.tokenize(state, state.line, state.lineMax);\n};\nParserBlock.prototype.State = state_block_default;\nvar parser_block_default = ParserBlock;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/state_inline.mjs\nfunction StateInline(src, md2, env, outTokens) {\n this.src = src;\n this.env = env;\n this.md = md2;\n this.tokens = outTokens;\n this.tokens_meta = Array(outTokens.length);\n this.pos = 0;\n this.posMax = this.src.length;\n this.level = 0;\n this.pending = \"\";\n this.pendingLevel = 0;\n this.cache = {};\n this.delimiters = [];\n this._prev_delimiters = [];\n this.backticks = {};\n this.backticksScanned = false;\n this.linkLevel = 0;\n}\nStateInline.prototype.pushPending = function() {\n const token = new token_default(\"text\", \"\", 0);\n token.content = this.pending;\n token.level = this.pendingLevel;\n this.tokens.push(token);\n this.pending = \"\";\n return token;\n};\nStateInline.prototype.push = function(type, tag, nesting) {\n if (this.pending) {\n this.pushPending();\n }\n const token = new token_default(type, tag, nesting);\n let token_meta = null;\n if (nesting < 0) {\n this.level--;\n this.delimiters = this._prev_delimiters.pop();\n }\n token.level = this.level;\n if (nesting > 0) {\n this.level++;\n this._prev_delimiters.push(this.delimiters);\n this.delimiters = [];\n token_meta = { delimiters: this.delimiters };\n }\n this.pendingLevel = this.level;\n this.tokens.push(token);\n this.tokens_meta.push(token_meta);\n return token;\n};\nStateInline.prototype.scanDelims = function(start, canSplitWord) {\n const max = this.posMax;\n const marker = this.src.charCodeAt(start);\n const lastChar = start > 0 ? this.src.charCodeAt(start - 1) : 32;\n let pos = start;\n while (pos < max && this.src.charCodeAt(pos) === marker) {\n pos++;\n }\n const count = pos - start;\n const nextChar = pos < max ? this.src.charCodeAt(pos) : 32;\n const isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar));\n const isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar));\n const isLastWhiteSpace = isWhiteSpace(lastChar);\n const isNextWhiteSpace = isWhiteSpace(nextChar);\n const left_flanking = !isNextWhiteSpace && (!isNextPunctChar || isLastWhiteSpace || isLastPunctChar);\n const right_flanking = !isLastWhiteSpace && (!isLastPunctChar || isNextWhiteSpace || isNextPunctChar);\n const can_open = left_flanking && (canSplitWord || !right_flanking || isLastPunctChar);\n const can_close = right_flanking && (canSplitWord || !left_flanking || isNextPunctChar);\n return { can_open, can_close, length: count };\n};\nStateInline.prototype.Token = token_default;\nvar state_inline_default = StateInline;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/text.mjs\nfunction isTerminatorChar(ch) {\n switch (ch) {\n case 10:\n case 33:\n case 35:\n case 36:\n case 37:\n case 38:\n case 42:\n case 43:\n case 45:\n case 58:\n case 60:\n case 61:\n case 62:\n case 64:\n case 91:\n case 92:\n case 93:\n case 94:\n case 95:\n case 96:\n case 123:\n case 125:\n case 126:\n return true;\n default:\n return false;\n }\n}\nfunction text(state, silent) {\n let pos = state.pos;\n while (pos < state.posMax && !isTerminatorChar(state.src.charCodeAt(pos))) {\n pos++;\n }\n if (pos === state.pos) {\n return false;\n }\n if (!silent) {\n state.pending += state.src.slice(state.pos, pos);\n }\n state.pos = pos;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/linkify.mjs\nvar SCHEME_RE = /(?:^|[^a-z0-9.+-])([a-z][a-z0-9.+-]*)$/i;\nfunction linkify2(state, silent) {\n if (!state.md.options.linkify) return false;\n if (state.linkLevel > 0) return false;\n const pos = state.pos;\n const max = state.posMax;\n if (pos + 3 > max) return false;\n if (state.src.charCodeAt(pos) !== 58) return false;\n if (state.src.charCodeAt(pos + 1) !== 47) return false;\n if (state.src.charCodeAt(pos + 2) !== 47) return false;\n const match2 = state.pending.match(SCHEME_RE);\n if (!match2) return false;\n const proto = match2[1];\n const link2 = state.md.linkify.matchAtStart(state.src.slice(pos - proto.length));\n if (!link2) return false;\n let url = link2.url;\n if (url.length <= proto.length) return false;\n let urlEnd = url.length;\n while (urlEnd > 0 && url.charCodeAt(urlEnd - 1) === 42) {\n urlEnd--;\n }\n if (urlEnd !== url.length) {\n url = url.slice(0, urlEnd);\n }\n const fullUrl = state.md.normalizeLink(url);\n if (!state.md.validateLink(fullUrl)) return false;\n if (!silent) {\n state.pending = state.pending.slice(0, -proto.length);\n const token_o = state.push(\"link_open\", \"a\", 1);\n token_o.attrs = [[\"href\", fullUrl]];\n token_o.markup = \"linkify\";\n token_o.info = \"auto\";\n const token_t = state.push(\"text\", \"\", 0);\n token_t.content = state.md.normalizeLinkText(url);\n const token_c = state.push(\"link_close\", \"a\", -1);\n token_c.markup = \"linkify\";\n token_c.info = \"auto\";\n }\n state.pos += url.length - proto.length;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/newline.mjs\nfunction newline(state, silent) {\n let pos = state.pos;\n if (state.src.charCodeAt(pos) !== 10) {\n return false;\n }\n const pmax = state.pending.length - 1;\n const max = state.posMax;\n if (!silent) {\n if (pmax >= 0 && state.pending.charCodeAt(pmax) === 32) {\n if (pmax >= 1 && state.pending.charCodeAt(pmax - 1) === 32) {\n let ws = pmax - 1;\n while (ws >= 1 && state.pending.charCodeAt(ws - 1) === 32) ws--;\n state.pending = state.pending.slice(0, ws);\n state.push(\"hardbreak\", \"br\", 0);\n } else {\n state.pending = state.pending.slice(0, -1);\n state.push(\"softbreak\", \"br\", 0);\n }\n } else {\n state.push(\"softbreak\", \"br\", 0);\n }\n }\n pos++;\n while (pos < max && isSpace(state.src.charCodeAt(pos))) {\n pos++;\n }\n state.pos = pos;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/escape.mjs\nvar ESCAPED = [];\nfor (let i = 0; i < 256; i++) {\n ESCAPED.push(0);\n}\n\"\\\\!\\\"#$%&'()*+,./:;<=>?@[]^_`{|}~-\".split(\"\").forEach(function(ch) {\n ESCAPED[ch.charCodeAt(0)] = 1;\n});\nfunction escape2(state, silent) {\n let pos = state.pos;\n const max = state.posMax;\n if (state.src.charCodeAt(pos) !== 92) return false;\n pos++;\n if (pos >= max) return false;\n let ch1 = state.src.charCodeAt(pos);\n if (ch1 === 10) {\n if (!silent) {\n state.push(\"hardbreak\", \"br\", 0);\n }\n pos++;\n while (pos < max) {\n ch1 = state.src.charCodeAt(pos);\n if (!isSpace(ch1)) break;\n pos++;\n }\n state.pos = pos;\n return true;\n }\n let escapedStr = state.src[pos];\n if (ch1 >= 55296 && ch1 <= 56319 && pos + 1 < max) {\n const ch2 = state.src.charCodeAt(pos + 1);\n if (ch2 >= 56320 && ch2 <= 57343) {\n escapedStr += state.src[pos + 1];\n pos++;\n }\n }\n const origStr = \"\\\\\" + escapedStr;\n if (!silent) {\n const token = state.push(\"text_special\", \"\", 0);\n if (ch1 < 256 && ESCAPED[ch1] !== 0) {\n token.content = escapedStr;\n } else {\n token.content = origStr;\n }\n token.markup = origStr;\n token.info = \"escape\";\n }\n state.pos = pos + 1;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/backticks.mjs\nfunction backtick(state, silent) {\n let pos = state.pos;\n const ch = state.src.charCodeAt(pos);\n if (ch !== 96) {\n return false;\n }\n const start = pos;\n pos++;\n const max = state.posMax;\n while (pos < max && state.src.charCodeAt(pos) === 96) {\n pos++;\n }\n const marker = state.src.slice(start, pos);\n const openerLength = marker.length;\n if (state.backticksScanned && (state.backticks[openerLength] || 0) <= start) {\n if (!silent) state.pending += marker;\n state.pos += openerLength;\n return true;\n }\n let matchEnd = pos;\n let matchStart;\n while ((matchStart = state.src.indexOf(\"`\", matchEnd)) !== -1) {\n matchEnd = matchStart + 1;\n while (matchEnd < max && state.src.charCodeAt(matchEnd) === 96) {\n matchEnd++;\n }\n const closerLength = matchEnd - matchStart;\n if (closerLength === openerLength) {\n if (!silent) {\n const token = state.push(\"code_inline\", \"code\", 0);\n token.markup = marker;\n token.content = state.src.slice(pos, matchStart).replace(/\\n/g, \" \").replace(/^ (.+) $/, \"$1\");\n }\n state.pos = matchEnd;\n return true;\n }\n state.backticks[closerLength] = matchStart;\n }\n state.backticksScanned = true;\n if (!silent) state.pending += marker;\n state.pos += openerLength;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/strikethrough.mjs\nfunction strikethrough_tokenize(state, silent) {\n const start = state.pos;\n const marker = state.src.charCodeAt(start);\n if (silent) {\n return false;\n }\n if (marker !== 126) {\n return false;\n }\n const scanned = state.scanDelims(state.pos, true);\n let len = scanned.length;\n const ch = String.fromCharCode(marker);\n if (len < 2) {\n return false;\n }\n let token;\n if (len % 2) {\n token = state.push(\"text\", \"\", 0);\n token.content = ch;\n len--;\n }\n for (let i = 0; i < len; i += 2) {\n token = state.push(\"text\", \"\", 0);\n token.content = ch + ch;\n state.delimiters.push({\n marker,\n length: 0,\n // disable \"rule of 3\" length checks meant for emphasis\n token: state.tokens.length - 1,\n end: -1,\n open: scanned.can_open,\n close: scanned.can_close\n });\n }\n state.pos += scanned.length;\n return true;\n}\nfunction postProcess(state, delimiters) {\n let token;\n const loneMarkers = [];\n const max = delimiters.length;\n for (let i = 0; i < max; i++) {\n const startDelim = delimiters[i];\n if (startDelim.marker !== 126) {\n continue;\n }\n if (startDelim.end === -1) {\n continue;\n }\n const endDelim = delimiters[startDelim.end];\n token = state.tokens[startDelim.token];\n token.type = \"s_open\";\n token.tag = \"s\";\n token.nesting = 1;\n token.markup = \"~~\";\n token.content = \"\";\n token = state.tokens[endDelim.token];\n token.type = \"s_close\";\n token.tag = \"s\";\n token.nesting = -1;\n token.markup = \"~~\";\n token.content = \"\";\n if (state.tokens[endDelim.token - 1].type === \"text\" && state.tokens[endDelim.token - 1].content === \"~\") {\n loneMarkers.push(endDelim.token - 1);\n }\n }\n while (loneMarkers.length) {\n const i = loneMarkers.pop();\n let j = i + 1;\n while (j < state.tokens.length && state.tokens[j].type === \"s_close\") {\n j++;\n }\n j--;\n if (i !== j) {\n token = state.tokens[j];\n state.tokens[j] = state.tokens[i];\n state.tokens[i] = token;\n }\n }\n}\nfunction strikethrough_postProcess(state) {\n const tokens_meta = state.tokens_meta;\n const max = state.tokens_meta.length;\n postProcess(state, state.delimiters);\n for (let curr = 0; curr < max; curr++) {\n if (tokens_meta[curr] && tokens_meta[curr].delimiters) {\n postProcess(state, tokens_meta[curr].delimiters);\n }\n }\n}\nvar strikethrough_default = {\n tokenize: strikethrough_tokenize,\n postProcess: strikethrough_postProcess\n};\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/emphasis.mjs\nfunction emphasis_tokenize(state, silent) {\n const start = state.pos;\n const marker = state.src.charCodeAt(start);\n if (silent) {\n return false;\n }\n if (marker !== 95 && marker !== 42) {\n return false;\n }\n const scanned = state.scanDelims(state.pos, marker === 42);\n for (let i = 0; i < scanned.length; i++) {\n const token = state.push(\"text\", \"\", 0);\n token.content = String.fromCharCode(marker);\n state.delimiters.push({\n // Char code of the starting marker (number).\n //\n marker,\n // Total length of these series of delimiters.\n //\n length: scanned.length,\n // A position of the token this delimiter corresponds to.\n //\n token: state.tokens.length - 1,\n // If this delimiter is matched as a valid opener, `end` will be\n // equal to its position, otherwise it's `-1`.\n //\n end: -1,\n // Boolean flags that determine if this delimiter could open or close\n // an emphasis.\n //\n open: scanned.can_open,\n close: scanned.can_close\n });\n }\n state.pos += scanned.length;\n return true;\n}\nfunction postProcess2(state, delimiters) {\n const max = delimiters.length;\n for (let i = max - 1; i >= 0; i--) {\n const startDelim = delimiters[i];\n if (startDelim.marker !== 95 && startDelim.marker !== 42) {\n continue;\n }\n if (startDelim.end === -1) {\n continue;\n }\n const endDelim = delimiters[startDelim.end];\n const isStrong = i > 0 && delimiters[i - 1].end === startDelim.end + 1 && // check that first two markers match and adjacent\n delimiters[i - 1].marker === startDelim.marker && delimiters[i - 1].token === startDelim.token - 1 && // check that last two markers are adjacent (we can safely assume they match)\n delimiters[startDelim.end + 1].token === endDelim.token + 1;\n const ch = String.fromCharCode(startDelim.marker);\n const token_o = state.tokens[startDelim.token];\n token_o.type = isStrong ? \"strong_open\" : \"em_open\";\n token_o.tag = isStrong ? \"strong\" : \"em\";\n token_o.nesting = 1;\n token_o.markup = isStrong ? ch + ch : ch;\n token_o.content = \"\";\n const token_c = state.tokens[endDelim.token];\n token_c.type = isStrong ? \"strong_close\" : \"em_close\";\n token_c.tag = isStrong ? \"strong\" : \"em\";\n token_c.nesting = -1;\n token_c.markup = isStrong ? ch + ch : ch;\n token_c.content = \"\";\n if (isStrong) {\n state.tokens[delimiters[i - 1].token].content = \"\";\n state.tokens[delimiters[startDelim.end + 1].token].content = \"\";\n i--;\n }\n }\n}\nfunction emphasis_post_process(state) {\n const tokens_meta = state.tokens_meta;\n const max = state.tokens_meta.length;\n postProcess2(state, state.delimiters);\n for (let curr = 0; curr < max; curr++) {\n if (tokens_meta[curr] && tokens_meta[curr].delimiters) {\n postProcess2(state, tokens_meta[curr].delimiters);\n }\n }\n}\nvar emphasis_default = {\n tokenize: emphasis_tokenize,\n postProcess: emphasis_post_process\n};\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/link.mjs\nfunction link(state, silent) {\n let code2, label, res, ref;\n let href = \"\";\n let title = \"\";\n let start = state.pos;\n let parseReference = true;\n if (state.src.charCodeAt(state.pos) !== 91) {\n return false;\n }\n const oldPos = state.pos;\n const max = state.posMax;\n const labelStart = state.pos + 1;\n const labelEnd = state.md.helpers.parseLinkLabel(state, state.pos, true);\n if (labelEnd < 0) {\n return false;\n }\n let pos = labelEnd + 1;\n if (pos < max && state.src.charCodeAt(pos) === 40) {\n parseReference = false;\n pos++;\n for (; pos < max; pos++) {\n code2 = state.src.charCodeAt(pos);\n if (!isSpace(code2) && code2 !== 10) {\n break;\n }\n }\n if (pos >= max) {\n return false;\n }\n start = pos;\n res = state.md.helpers.parseLinkDestination(state.src, pos, state.posMax);\n if (res.ok) {\n href = state.md.normalizeLink(res.str);\n if (state.md.validateLink(href)) {\n pos = res.pos;\n } else {\n href = \"\";\n }\n start = pos;\n for (; pos < max; pos++) {\n code2 = state.src.charCodeAt(pos);\n if (!isSpace(code2) && code2 !== 10) {\n break;\n }\n }\n res = state.md.helpers.parseLinkTitle(state.src, pos, state.posMax);\n if (pos < max && start !== pos && res.ok) {\n title = res.str;\n pos = res.pos;\n for (; pos < max; pos++) {\n code2 = state.src.charCodeAt(pos);\n if (!isSpace(code2) && code2 !== 10) {\n break;\n }\n }\n }\n }\n if (pos >= max || state.src.charCodeAt(pos) !== 41) {\n parseReference = true;\n }\n pos++;\n }\n if (parseReference) {\n if (typeof state.env.references === \"undefined\") {\n return false;\n }\n if (pos < max && state.src.charCodeAt(pos) === 91) {\n start = pos + 1;\n pos = state.md.helpers.parseLinkLabel(state, pos);\n if (pos >= 0) {\n label = state.src.slice(start, pos++);\n } else {\n pos = labelEnd + 1;\n }\n } else {\n pos = labelEnd + 1;\n }\n if (!label) {\n label = state.src.slice(labelStart, labelEnd);\n }\n ref = state.env.references[normalizeReference(label)];\n if (!ref) {\n state.pos = oldPos;\n return false;\n }\n href = ref.href;\n title = ref.title;\n }\n if (!silent) {\n state.pos = labelStart;\n state.posMax = labelEnd;\n const token_o = state.push(\"link_open\", \"a\", 1);\n const attrs = [[\"href\", href]];\n token_o.attrs = attrs;\n if (title) {\n attrs.push([\"title\", title]);\n }\n state.linkLevel++;\n state.md.inline.tokenize(state);\n state.linkLevel--;\n state.push(\"link_close\", \"a\", -1);\n }\n state.pos = pos;\n state.posMax = max;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/image.mjs\nfunction image(state, silent) {\n let code2, content, label, pos, ref, res, title, start;\n let href = \"\";\n const oldPos = state.pos;\n const max = state.posMax;\n if (state.src.charCodeAt(state.pos) !== 33) {\n return false;\n }\n if (state.src.charCodeAt(state.pos + 1) !== 91) {\n return false;\n }\n const labelStart = state.pos + 2;\n const labelEnd = state.md.helpers.parseLinkLabel(state, state.pos + 1, false);\n if (labelEnd < 0) {\n return false;\n }\n pos = labelEnd + 1;\n if (pos < max && state.src.charCodeAt(pos) === 40) {\n pos++;\n for (; pos < max; pos++) {\n code2 = state.src.charCodeAt(pos);\n if (!isSpace(code2) && code2 !== 10) {\n break;\n }\n }\n if (pos >= max) {\n return false;\n }\n start = pos;\n res = state.md.helpers.parseLinkDestination(state.src, pos, state.posMax);\n if (res.ok) {\n href = state.md.normalizeLink(res.str);\n if (state.md.validateLink(href)) {\n pos = res.pos;\n } else {\n href = \"\";\n }\n }\n start = pos;\n for (; pos < max; pos++) {\n code2 = state.src.charCodeAt(pos);\n if (!isSpace(code2) && code2 !== 10) {\n break;\n }\n }\n res = state.md.helpers.parseLinkTitle(state.src, pos, state.posMax);\n if (pos < max && start !== pos && res.ok) {\n title = res.str;\n pos = res.pos;\n for (; pos < max; pos++) {\n code2 = state.src.charCodeAt(pos);\n if (!isSpace(code2) && code2 !== 10) {\n break;\n }\n }\n } else {\n title = \"\";\n }\n if (pos >= max || state.src.charCodeAt(pos) !== 41) {\n state.pos = oldPos;\n return false;\n }\n pos++;\n } else {\n if (typeof state.env.references === \"undefined\") {\n return false;\n }\n if (pos < max && state.src.charCodeAt(pos) === 91) {\n start = pos + 1;\n pos = state.md.helpers.parseLinkLabel(state, pos);\n if (pos >= 0) {\n label = state.src.slice(start, pos++);\n } else {\n pos = labelEnd + 1;\n }\n } else {\n pos = labelEnd + 1;\n }\n if (!label) {\n label = state.src.slice(labelStart, labelEnd);\n }\n ref = state.env.references[normalizeReference(label)];\n if (!ref) {\n state.pos = oldPos;\n return false;\n }\n href = ref.href;\n title = ref.title;\n }\n if (!silent) {\n content = state.src.slice(labelStart, labelEnd);\n const tokens2 = [];\n state.md.inline.parse(\n content,\n state.md,\n state.env,\n tokens2\n );\n const token = state.push(\"image\", \"img\", 0);\n const attrs = [[\"src\", href], [\"alt\", \"\"]];\n token.attrs = attrs;\n token.children = tokens2;\n token.content = content;\n if (title) {\n attrs.push([\"title\", title]);\n }\n }\n state.pos = pos;\n state.posMax = max;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/autolink.mjs\nvar EMAIL_RE = /^([a-zA-Z0-9.!#$%&'*+/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*)$/;\nvar AUTOLINK_RE = /^([a-zA-Z][a-zA-Z0-9+.-]{1,31}):([^<>\\x00-\\x20]*)$/;\nfunction autolink(state, silent) {\n let pos = state.pos;\n if (state.src.charCodeAt(pos) !== 60) {\n return false;\n }\n const start = state.pos;\n const max = state.posMax;\n for (; ; ) {\n if (++pos >= max) return false;\n const ch = state.src.charCodeAt(pos);\n if (ch === 60) return false;\n if (ch === 62) break;\n }\n const url = state.src.slice(start + 1, pos);\n if (AUTOLINK_RE.test(url)) {\n const fullUrl = state.md.normalizeLink(url);\n if (!state.md.validateLink(fullUrl)) {\n return false;\n }\n if (!silent) {\n const token_o = state.push(\"link_open\", \"a\", 1);\n token_o.attrs = [[\"href\", fullUrl]];\n token_o.markup = \"autolink\";\n token_o.info = \"auto\";\n const token_t = state.push(\"text\", \"\", 0);\n token_t.content = state.md.normalizeLinkText(url);\n const token_c = state.push(\"link_close\", \"a\", -1);\n token_c.markup = \"autolink\";\n token_c.info = \"auto\";\n }\n state.pos += url.length + 2;\n return true;\n }\n if (EMAIL_RE.test(url)) {\n const fullUrl = state.md.normalizeLink(\"mailto:\" + url);\n if (!state.md.validateLink(fullUrl)) {\n return false;\n }\n if (!silent) {\n const token_o = state.push(\"link_open\", \"a\", 1);\n token_o.attrs = [[\"href\", fullUrl]];\n token_o.markup = \"autolink\";\n token_o.info = \"auto\";\n const token_t = state.push(\"text\", \"\", 0);\n token_t.content = state.md.normalizeLinkText(url);\n const token_c = state.push(\"link_close\", \"a\", -1);\n token_c.markup = \"autolink\";\n token_c.info = \"auto\";\n }\n state.pos += url.length + 2;\n return true;\n }\n return false;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/html_inline.mjs\nfunction isLinkOpen2(str) {\n return /^\\s]/i.test(str);\n}\nfunction isLinkClose2(str) {\n return /^<\\/a\\s*>/i.test(str);\n}\nfunction isLetter(ch) {\n const lc = ch | 32;\n return lc >= 97 && lc <= 122;\n}\nfunction html_inline(state, silent) {\n if (!state.md.options.html) {\n return false;\n }\n const max = state.posMax;\n const pos = state.pos;\n if (state.src.charCodeAt(pos) !== 60 || pos + 2 >= max) {\n return false;\n }\n const ch = state.src.charCodeAt(pos + 1);\n if (ch !== 33 && ch !== 63 && ch !== 47 && !isLetter(ch)) {\n return false;\n }\n const match2 = state.src.slice(pos).match(HTML_TAG_RE);\n if (!match2) {\n return false;\n }\n if (!silent) {\n const token = state.push(\"html_inline\", \"\", 0);\n token.content = match2[0];\n if (isLinkOpen2(token.content)) state.linkLevel++;\n if (isLinkClose2(token.content)) state.linkLevel--;\n }\n state.pos += match2[0].length;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/entity.mjs\nvar DIGITAL_RE = /^&#((?:x[a-f0-9]{1,6}|[0-9]{1,7}));/i;\nvar NAMED_RE = /^&([a-z][a-z0-9]{1,31});/i;\nfunction entity(state, silent) {\n const pos = state.pos;\n const max = state.posMax;\n if (state.src.charCodeAt(pos) !== 38) return false;\n if (pos + 1 >= max) return false;\n const ch = state.src.charCodeAt(pos + 1);\n if (ch === 35) {\n const match2 = state.src.slice(pos).match(DIGITAL_RE);\n if (match2) {\n if (!silent) {\n const code2 = match2[1][0].toLowerCase() === \"x\" ? parseInt(match2[1].slice(1), 16) : parseInt(match2[1], 10);\n const token = state.push(\"text_special\", \"\", 0);\n token.content = isValidEntityCode(code2) ? fromCodePoint2(code2) : fromCodePoint2(65533);\n token.markup = match2[0];\n token.info = \"entity\";\n }\n state.pos += match2[0].length;\n return true;\n }\n } else {\n const match2 = state.src.slice(pos).match(NAMED_RE);\n if (match2) {\n const decoded = decodeHTML(match2[0]);\n if (decoded !== match2[0]) {\n if (!silent) {\n const token = state.push(\"text_special\", \"\", 0);\n token.content = decoded;\n token.markup = match2[0];\n token.info = \"entity\";\n }\n state.pos += match2[0].length;\n return true;\n }\n }\n }\n return false;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/balance_pairs.mjs\nfunction processDelimiters(delimiters) {\n const openersBottom = {};\n const max = delimiters.length;\n if (!max) return;\n let headerIdx = 0;\n let lastTokenIdx = -2;\n const jumps = [];\n for (let closerIdx = 0; closerIdx < max; closerIdx++) {\n const closer = delimiters[closerIdx];\n jumps.push(0);\n if (delimiters[headerIdx].marker !== closer.marker || lastTokenIdx !== closer.token - 1) {\n headerIdx = closerIdx;\n }\n lastTokenIdx = closer.token;\n closer.length = closer.length || 0;\n if (!closer.close) continue;\n if (!openersBottom.hasOwnProperty(closer.marker)) {\n openersBottom[closer.marker] = [-1, -1, -1, -1, -1, -1];\n }\n const minOpenerIdx = openersBottom[closer.marker][(closer.open ? 3 : 0) + closer.length % 3];\n let openerIdx = headerIdx - jumps[headerIdx] - 1;\n let newMinOpenerIdx = openerIdx;\n for (; openerIdx > minOpenerIdx; openerIdx -= jumps[openerIdx] + 1) {\n const opener = delimiters[openerIdx];\n if (opener.marker !== closer.marker) continue;\n if (opener.open && opener.end < 0) {\n let isOddMatch = false;\n if (opener.close || closer.open) {\n if ((opener.length + closer.length) % 3 === 0) {\n if (opener.length % 3 !== 0 || closer.length % 3 !== 0) {\n isOddMatch = true;\n }\n }\n }\n if (!isOddMatch) {\n const lastJump = openerIdx > 0 && !delimiters[openerIdx - 1].open ? jumps[openerIdx - 1] + 1 : 0;\n jumps[closerIdx] = closerIdx - openerIdx + lastJump;\n jumps[openerIdx] = lastJump;\n closer.open = false;\n opener.end = closerIdx;\n opener.close = false;\n newMinOpenerIdx = -1;\n lastTokenIdx = -2;\n break;\n }\n }\n }\n if (newMinOpenerIdx !== -1) {\n openersBottom[closer.marker][(closer.open ? 3 : 0) + (closer.length || 0) % 3] = newMinOpenerIdx;\n }\n }\n}\nfunction link_pairs(state) {\n const tokens_meta = state.tokens_meta;\n const max = state.tokens_meta.length;\n processDelimiters(state.delimiters);\n for (let curr = 0; curr < max; curr++) {\n if (tokens_meta[curr] && tokens_meta[curr].delimiters) {\n processDelimiters(tokens_meta[curr].delimiters);\n }\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/fragments_join.mjs\nfunction fragments_join(state) {\n let curr, last;\n let level = 0;\n const tokens2 = state.tokens;\n const max = state.tokens.length;\n for (curr = last = 0; curr < max; curr++) {\n if (tokens2[curr].nesting < 0) level--;\n tokens2[curr].level = level;\n if (tokens2[curr].nesting > 0) level++;\n if (tokens2[curr].type === \"text\" && curr + 1 < max && tokens2[curr + 1].type === \"text\") {\n tokens2[curr + 1].content = tokens2[curr].content + tokens2[curr + 1].content;\n } else {\n if (curr !== last) {\n tokens2[last] = tokens2[curr];\n }\n last++;\n }\n }\n if (curr !== last) {\n tokens2.length = last;\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/parser_inline.mjs\nvar _rules3 = [\n [\"text\", text],\n [\"linkify\", linkify2],\n [\"newline\", newline],\n [\"escape\", escape2],\n [\"backticks\", backtick],\n [\"strikethrough\", strikethrough_default.tokenize],\n [\"emphasis\", emphasis_default.tokenize],\n [\"link\", link],\n [\"image\", image],\n [\"autolink\", autolink],\n [\"html_inline\", html_inline],\n [\"entity\", entity]\n];\nvar _rules22 = [\n [\"balance_pairs\", link_pairs],\n [\"strikethrough\", strikethrough_default.postProcess],\n [\"emphasis\", emphasis_default.postProcess],\n // rules for pairs separate '**' into its own text tokens, which may be left unused,\n // rule below merges unused segments back with the rest of the text\n [\"fragments_join\", fragments_join]\n];\nfunction ParserInline() {\n this.ruler = new ruler_default();\n for (let i = 0; i < _rules3.length; i++) {\n this.ruler.push(_rules3[i][0], _rules3[i][1]);\n }\n this.ruler2 = new ruler_default();\n for (let i = 0; i < _rules22.length; i++) {\n this.ruler2.push(_rules22[i][0], _rules22[i][1]);\n }\n}\nParserInline.prototype.skipToken = function(state) {\n const pos = state.pos;\n const rules = this.ruler.getRules(\"\");\n const len = rules.length;\n const maxNesting = state.md.options.maxNesting;\n const cache = state.cache;\n if (typeof cache[pos] !== \"undefined\") {\n state.pos = cache[pos];\n return;\n }\n let ok = false;\n if (state.level < maxNesting) {\n for (let i = 0; i < len; i++) {\n state.level++;\n ok = rules[i](state, true);\n state.level--;\n if (ok) {\n if (pos >= state.pos) {\n throw new Error(\"inline rule didn't increment state.pos\");\n }\n break;\n }\n }\n } else {\n state.pos = state.posMax;\n }\n if (!ok) {\n state.pos++;\n }\n cache[pos] = state.pos;\n};\nParserInline.prototype.tokenize = function(state) {\n const rules = this.ruler.getRules(\"\");\n const len = rules.length;\n const end = state.posMax;\n const maxNesting = state.md.options.maxNesting;\n while (state.pos < end) {\n const prevPos = state.pos;\n let ok = false;\n if (state.level < maxNesting) {\n for (let i = 0; i < len; i++) {\n ok = rules[i](state, false);\n if (ok) {\n if (prevPos >= state.pos) {\n throw new Error(\"inline rule didn't increment state.pos\");\n }\n break;\n }\n }\n }\n if (ok) {\n if (state.pos >= end) {\n break;\n }\n continue;\n }\n state.pending += state.src[state.pos++];\n }\n if (state.pending) {\n state.pushPending();\n }\n};\nParserInline.prototype.parse = function(str, md2, env, outTokens) {\n const state = new this.State(str, md2, env, outTokens);\n this.tokenize(state);\n const rules = this.ruler2.getRules(\"\");\n const len = rules.length;\n for (let i = 0; i < len; i++) {\n rules[i](state);\n }\n};\nParserInline.prototype.State = state_inline_default;\nvar parser_inline_default = ParserInline;\n\n// node_modules/.pnpm/linkify-it@5.0.0/node_modules/linkify-it/lib/re.mjs\nfunction re_default(opts) {\n const re = {};\n opts = opts || {};\n re.src_Any = regex_default.source;\n re.src_Cc = regex_default2.source;\n re.src_Z = regex_default6.source;\n re.src_P = regex_default4.source;\n re.src_ZPCc = [re.src_Z, re.src_P, re.src_Cc].join(\"|\");\n re.src_ZCc = [re.src_Z, re.src_Cc].join(\"|\");\n const text_separators = \"[><|]\";\n re.src_pseudo_letter = \"(?:(?!\" + text_separators + \"|\" + re.src_ZPCc + \")\" + re.src_Any + \")\";\n re.src_ip4 = \"(?:(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\";\n re.src_auth = \"(?:(?:(?!\" + re.src_ZCc + \"|[@/\\\\[\\\\]()]).)+@)?\";\n re.src_port = \"(?::(?:6(?:[0-4]\\\\d{3}|5(?:[0-4]\\\\d{2}|5(?:[0-2]\\\\d|3[0-5])))|[1-5]?\\\\d{1,4}))?\";\n re.src_host_terminator = \"(?=$|\" + text_separators + \"|\" + re.src_ZPCc + \")(?!\" + (opts[\"---\"] ? \"-(?!--)|\" : \"-|\") + \"_|:\\\\d|\\\\.-|\\\\.(?!$|\" + re.src_ZPCc + \"))\";\n re.src_path = \"(?:[/?#](?:(?!\" + re.src_ZCc + \"|\" + text_separators + `|[()[\\\\]{}.,\"'?!\\\\-;]).|\\\\[(?:(?!` + re.src_ZCc + \"|\\\\]).)*\\\\]|\\\\((?:(?!\" + re.src_ZCc + \"|[)]).)*\\\\)|\\\\{(?:(?!\" + re.src_ZCc + '|[}]).)*\\\\}|\\\\\"(?:(?!' + re.src_ZCc + `|[\"]).)+\\\\\"|\\\\'(?:(?!` + re.src_ZCc + \"|[']).)+\\\\'|\\\\'(?=\" + re.src_pseudo_letter + \"|[-])|\\\\.{2,}[a-zA-Z0-9%/&]|\\\\.(?!\" + re.src_ZCc + \"|[.]|$)|\" + (opts[\"---\"] ? \"\\\\-(?!--(?:[^-]|$))(?:-*)|\" : \"\\\\-+|\") + // allow `,,,` in paths\n \",(?!\" + re.src_ZCc + \"|$)|;(?!\" + re.src_ZCc + \"|$)|\\\\!+(?!\" + re.src_ZCc + \"|[!]|$)|\\\\?(?!\" + re.src_ZCc + \"|[?]|$))+|\\\\/)?\";\n re.src_email_name = '[\\\\-;:&=\\\\+\\\\$,\\\\.a-zA-Z0-9_][\\\\-;:&=\\\\+\\\\$,\\\\\"\\\\.a-zA-Z0-9_]*';\n re.src_xn = \"xn--[a-z0-9\\\\-]{1,59}\";\n re.src_domain_root = // Allow letters & digits (http://test1)\n \"(?:\" + re.src_xn + \"|\" + re.src_pseudo_letter + \"{1,63})\";\n re.src_domain = \"(?:\" + re.src_xn + \"|(?:\" + re.src_pseudo_letter + \")|(?:\" + re.src_pseudo_letter + \"(?:-|\" + re.src_pseudo_letter + \"){0,61}\" + re.src_pseudo_letter + \"))\";\n re.src_host = \"(?:(?:(?:(?:\" + re.src_domain + \")\\\\.)*\" + re.src_domain + \"))\";\n re.tpl_host_fuzzy = \"(?:\" + re.src_ip4 + \"|(?:(?:(?:\" + re.src_domain + \")\\\\.)+(?:%TLDS%)))\";\n re.tpl_host_no_ip_fuzzy = \"(?:(?:(?:\" + re.src_domain + \")\\\\.)+(?:%TLDS%))\";\n re.src_host_strict = re.src_host + re.src_host_terminator;\n re.tpl_host_fuzzy_strict = re.tpl_host_fuzzy + re.src_host_terminator;\n re.src_host_port_strict = re.src_host + re.src_port + re.src_host_terminator;\n re.tpl_host_port_fuzzy_strict = re.tpl_host_fuzzy + re.src_port + re.src_host_terminator;\n re.tpl_host_port_no_ip_fuzzy_strict = re.tpl_host_no_ip_fuzzy + re.src_port + re.src_host_terminator;\n re.tpl_host_fuzzy_test = \"localhost|www\\\\.|\\\\.\\\\d{1,3}\\\\.|(?:\\\\.(?:%TLDS%)(?:\" + re.src_ZPCc + \"|>|$))\";\n re.tpl_email_fuzzy = \"(^|\" + text_separators + '|\"|\\\\(|' + re.src_ZCc + \")(\" + re.src_email_name + \"@\" + re.tpl_host_fuzzy_strict + \")\";\n re.tpl_link_fuzzy = // Fuzzy link can't be prepended with .:/\\- and non punctuation.\n // but can start with > (markdown blockquote)\n \"(^|(?![.:/\\\\-_@])(?:[$+<=>^`||]|\" + re.src_ZPCc + \"))((?![$+<=>^`||])\" + re.tpl_host_port_fuzzy_strict + re.src_path + \")\";\n re.tpl_link_no_ip_fuzzy = // Fuzzy link can't be prepended with .:/\\- and non punctuation.\n // but can start with > (markdown blockquote)\n \"(^|(?![.:/\\\\-_@])(?:[$+<=>^`||]|\" + re.src_ZPCc + \"))((?![$+<=>^`||])\" + re.tpl_host_port_no_ip_fuzzy_strict + re.src_path + \")\";\n return re;\n}\n\n// node_modules/.pnpm/linkify-it@5.0.0/node_modules/linkify-it/index.mjs\nfunction assign2(obj) {\n const sources = Array.prototype.slice.call(arguments, 1);\n sources.forEach(function(source2) {\n if (!source2) {\n return;\n }\n Object.keys(source2).forEach(function(key) {\n obj[key] = source2[key];\n });\n });\n return obj;\n}\nfunction _class2(obj) {\n return Object.prototype.toString.call(obj);\n}\nfunction isString2(obj) {\n return _class2(obj) === \"[object String]\";\n}\nfunction isObject(obj) {\n return _class2(obj) === \"[object Object]\";\n}\nfunction isRegExp(obj) {\n return _class2(obj) === \"[object RegExp]\";\n}\nfunction isFunction(obj) {\n return _class2(obj) === \"[object Function]\";\n}\nfunction escapeRE2(str) {\n return str.replace(/[.?*+^$[\\]\\\\(){}|-]/g, \"\\\\$&\");\n}\nvar defaultOptions = {\n fuzzyLink: true,\n fuzzyEmail: true,\n fuzzyIP: false\n};\nfunction isOptionsObj(obj) {\n return Object.keys(obj || {}).reduce(function(acc, k) {\n return acc || defaultOptions.hasOwnProperty(k);\n }, false);\n}\nvar defaultSchemas = {\n \"http:\": {\n validate: function(text2, pos, self) {\n const tail = text2.slice(pos);\n if (!self.re.http) {\n self.re.http = new RegExp(\n \"^\\\\/\\\\/\" + self.re.src_auth + self.re.src_host_port_strict + self.re.src_path,\n \"i\"\n );\n }\n if (self.re.http.test(tail)) {\n return tail.match(self.re.http)[0].length;\n }\n return 0;\n }\n },\n \"https:\": \"http:\",\n \"ftp:\": \"http:\",\n \"//\": {\n validate: function(text2, pos, self) {\n const tail = text2.slice(pos);\n if (!self.re.no_http) {\n self.re.no_http = new RegExp(\n \"^\" + self.re.src_auth + // Don't allow single-level domains, because of false positives like '//test'\n // with code comments\n \"(?:localhost|(?:(?:\" + self.re.src_domain + \")\\\\.)+\" + self.re.src_domain_root + \")\" + self.re.src_port + self.re.src_host_terminator + self.re.src_path,\n \"i\"\n );\n }\n if (self.re.no_http.test(tail)) {\n if (pos >= 3 && text2[pos - 3] === \":\") {\n return 0;\n }\n if (pos >= 3 && text2[pos - 3] === \"/\") {\n return 0;\n }\n return tail.match(self.re.no_http)[0].length;\n }\n return 0;\n }\n },\n \"mailto:\": {\n validate: function(text2, pos, self) {\n const tail = text2.slice(pos);\n if (!self.re.mailto) {\n self.re.mailto = new RegExp(\n \"^\" + self.re.src_email_name + \"@\" + self.re.src_host_strict,\n \"i\"\n );\n }\n if (self.re.mailto.test(tail)) {\n return tail.match(self.re.mailto)[0].length;\n }\n return 0;\n }\n }\n};\nvar tlds_2ch_src_re = \"a[cdefgilmnoqrstuwxz]|b[abdefghijmnorstvwyz]|c[acdfghiklmnoruvwxyz]|d[ejkmoz]|e[cegrstu]|f[ijkmor]|g[abdefghilmnpqrstuwy]|h[kmnrtu]|i[delmnoqrst]|j[emop]|k[eghimnprwyz]|l[abcikrstuvy]|m[acdeghklmnopqrstuvwxyz]|n[acefgilopruz]|om|p[aefghklmnrstwy]|qa|r[eosuw]|s[abcdeghijklmnortuvxyz]|t[cdfghjklmnortvwz]|u[agksyz]|v[aceginu]|w[fs]|y[et]|z[amw]\";\nvar tlds_default = \"biz|com|edu|gov|net|org|pro|web|xxx|aero|asia|coop|info|museum|name|shop|рф\".split(\"|\");\nfunction resetScanCache(self) {\n self.__index__ = -1;\n self.__text_cache__ = \"\";\n}\nfunction createValidator(re) {\n return function(text2, pos) {\n const tail = text2.slice(pos);\n if (re.test(tail)) {\n return tail.match(re)[0].length;\n }\n return 0;\n };\n}\nfunction createNormalizer() {\n return function(match2, self) {\n self.normalize(match2);\n };\n}\nfunction compile(self) {\n const re = self.re = re_default(self.__opts__);\n const tlds2 = self.__tlds__.slice();\n self.onCompile();\n if (!self.__tlds_replaced__) {\n tlds2.push(tlds_2ch_src_re);\n }\n tlds2.push(re.src_xn);\n re.src_tlds = tlds2.join(\"|\");\n function untpl(tpl) {\n return tpl.replace(\"%TLDS%\", re.src_tlds);\n }\n re.email_fuzzy = RegExp(untpl(re.tpl_email_fuzzy), \"i\");\n re.link_fuzzy = RegExp(untpl(re.tpl_link_fuzzy), \"i\");\n re.link_no_ip_fuzzy = RegExp(untpl(re.tpl_link_no_ip_fuzzy), \"i\");\n re.host_fuzzy_test = RegExp(untpl(re.tpl_host_fuzzy_test), \"i\");\n const aliases = [];\n self.__compiled__ = {};\n function schemaError(name, val) {\n throw new Error('(LinkifyIt) Invalid schema \"' + name + '\": ' + val);\n }\n Object.keys(self.__schemas__).forEach(function(name) {\n const val = self.__schemas__[name];\n if (val === null) {\n return;\n }\n const compiled = { validate: null, link: null };\n self.__compiled__[name] = compiled;\n if (isObject(val)) {\n if (isRegExp(val.validate)) {\n compiled.validate = createValidator(val.validate);\n } else if (isFunction(val.validate)) {\n compiled.validate = val.validate;\n } else {\n schemaError(name, val);\n }\n if (isFunction(val.normalize)) {\n compiled.normalize = val.normalize;\n } else if (!val.normalize) {\n compiled.normalize = createNormalizer();\n } else {\n schemaError(name, val);\n }\n return;\n }\n if (isString2(val)) {\n aliases.push(name);\n return;\n }\n schemaError(name, val);\n });\n aliases.forEach(function(alias) {\n if (!self.__compiled__[self.__schemas__[alias]]) {\n return;\n }\n self.__compiled__[alias].validate = self.__compiled__[self.__schemas__[alias]].validate;\n self.__compiled__[alias].normalize = self.__compiled__[self.__schemas__[alias]].normalize;\n });\n self.__compiled__[\"\"] = { validate: null, normalize: createNormalizer() };\n const slist = Object.keys(self.__compiled__).filter(function(name) {\n return name.length > 0 && self.__compiled__[name];\n }).map(escapeRE2).join(\"|\");\n self.re.schema_test = RegExp(\"(^|(?!_)(?:[><|]|\" + re.src_ZPCc + \"))(\" + slist + \")\", \"i\");\n self.re.schema_search = RegExp(\"(^|(?!_)(?:[><|]|\" + re.src_ZPCc + \"))(\" + slist + \")\", \"ig\");\n self.re.schema_at_start = RegExp(\"^\" + self.re.schema_search.source, \"i\");\n self.re.pretest = RegExp(\n \"(\" + self.re.schema_test.source + \")|(\" + self.re.host_fuzzy_test.source + \")|@\",\n \"i\"\n );\n resetScanCache(self);\n}\nfunction Match(self, shift) {\n const start = self.__index__;\n const end = self.__last_index__;\n const text2 = self.__text_cache__.slice(start, end);\n this.schema = self.__schema__.toLowerCase();\n this.index = start + shift;\n this.lastIndex = end + shift;\n this.raw = text2;\n this.text = text2;\n this.url = text2;\n}\nfunction createMatch(self, shift) {\n const match2 = new Match(self, shift);\n self.__compiled__[match2.schema].normalize(match2, self);\n return match2;\n}\nfunction LinkifyIt(schemas, options) {\n if (!(this instanceof LinkifyIt)) {\n return new LinkifyIt(schemas, options);\n }\n if (!options) {\n if (isOptionsObj(schemas)) {\n options = schemas;\n schemas = {};\n }\n }\n this.__opts__ = assign2({}, defaultOptions, options);\n this.__index__ = -1;\n this.__last_index__ = -1;\n this.__schema__ = \"\";\n this.__text_cache__ = \"\";\n this.__schemas__ = assign2({}, defaultSchemas, schemas);\n this.__compiled__ = {};\n this.__tlds__ = tlds_default;\n this.__tlds_replaced__ = false;\n this.re = {};\n compile(this);\n}\nLinkifyIt.prototype.add = function add(schema, definition) {\n this.__schemas__[schema] = definition;\n compile(this);\n return this;\n};\nLinkifyIt.prototype.set = function set(options) {\n this.__opts__ = assign2(this.__opts__, options);\n return this;\n};\nLinkifyIt.prototype.test = function test(text2) {\n this.__text_cache__ = text2;\n this.__index__ = -1;\n if (!text2.length) {\n return false;\n }\n let m, ml, me, len, shift, next, re, tld_pos, at_pos;\n if (this.re.schema_test.test(text2)) {\n re = this.re.schema_search;\n re.lastIndex = 0;\n while ((m = re.exec(text2)) !== null) {\n len = this.testSchemaAt(text2, m[2], re.lastIndex);\n if (len) {\n this.__schema__ = m[2];\n this.__index__ = m.index + m[1].length;\n this.__last_index__ = m.index + m[0].length + len;\n break;\n }\n }\n }\n if (this.__opts__.fuzzyLink && this.__compiled__[\"http:\"]) {\n tld_pos = text2.search(this.re.host_fuzzy_test);\n if (tld_pos >= 0) {\n if (this.__index__ < 0 || tld_pos < this.__index__) {\n if ((ml = text2.match(this.__opts__.fuzzyIP ? this.re.link_fuzzy : this.re.link_no_ip_fuzzy)) !== null) {\n shift = ml.index + ml[1].length;\n if (this.__index__ < 0 || shift < this.__index__) {\n this.__schema__ = \"\";\n this.__index__ = shift;\n this.__last_index__ = ml.index + ml[0].length;\n }\n }\n }\n }\n }\n if (this.__opts__.fuzzyEmail && this.__compiled__[\"mailto:\"]) {\n at_pos = text2.indexOf(\"@\");\n if (at_pos >= 0) {\n if ((me = text2.match(this.re.email_fuzzy)) !== null) {\n shift = me.index + me[1].length;\n next = me.index + me[0].length;\n if (this.__index__ < 0 || shift < this.__index__ || shift === this.__index__ && next > this.__last_index__) {\n this.__schema__ = \"mailto:\";\n this.__index__ = shift;\n this.__last_index__ = next;\n }\n }\n }\n }\n return this.__index__ >= 0;\n};\nLinkifyIt.prototype.pretest = function pretest(text2) {\n return this.re.pretest.test(text2);\n};\nLinkifyIt.prototype.testSchemaAt = function testSchemaAt(text2, schema, pos) {\n if (!this.__compiled__[schema.toLowerCase()]) {\n return 0;\n }\n return this.__compiled__[schema.toLowerCase()].validate(text2, pos, this);\n};\nLinkifyIt.prototype.match = function match(text2) {\n const result = [];\n let shift = 0;\n if (this.__index__ >= 0 && this.__text_cache__ === text2) {\n result.push(createMatch(this, shift));\n shift = this.__last_index__;\n }\n let tail = shift ? text2.slice(shift) : text2;\n while (this.test(tail)) {\n result.push(createMatch(this, shift));\n tail = tail.slice(this.__last_index__);\n shift += this.__last_index__;\n }\n if (result.length) {\n return result;\n }\n return null;\n};\nLinkifyIt.prototype.matchAtStart = function matchAtStart(text2) {\n this.__text_cache__ = text2;\n this.__index__ = -1;\n if (!text2.length) return null;\n const m = this.re.schema_at_start.exec(text2);\n if (!m) return null;\n const len = this.testSchemaAt(text2, m[2], m[0].length);\n if (!len) return null;\n this.__schema__ = m[2];\n this.__index__ = m.index + m[1].length;\n this.__last_index__ = m.index + m[0].length + len;\n return createMatch(this, 0);\n};\nLinkifyIt.prototype.tlds = function tlds(list2, keepOld) {\n list2 = Array.isArray(list2) ? list2 : [list2];\n if (!keepOld) {\n this.__tlds__ = list2.slice();\n this.__tlds_replaced__ = true;\n compile(this);\n return this;\n }\n this.__tlds__ = this.__tlds__.concat(list2).sort().filter(function(el, idx, arr) {\n return el !== arr[idx - 1];\n }).reverse();\n compile(this);\n return this;\n};\nLinkifyIt.prototype.normalize = function normalize2(match2) {\n if (!match2.schema) {\n match2.url = \"http://\" + match2.url;\n }\n if (match2.schema === \"mailto:\" && !/^mailto:/i.test(match2.url)) {\n match2.url = \"mailto:\" + match2.url;\n }\n};\nLinkifyIt.prototype.onCompile = function onCompile() {\n};\nvar linkify_it_default = LinkifyIt;\n\n// node_modules/.pnpm/punycode.js@2.3.1/node_modules/punycode.js/punycode.es6.js\nvar maxInt = 2147483647;\nvar base = 36;\nvar tMin = 1;\nvar tMax = 26;\nvar skew = 38;\nvar damp = 700;\nvar initialBias = 72;\nvar initialN = 128;\nvar delimiter = \"-\";\nvar regexPunycode = /^xn--/;\nvar regexNonASCII = /[^\\0-\\x7F]/;\nvar regexSeparators = /[\\x2E\\u3002\\uFF0E\\uFF61]/g;\nvar errors = {\n \"overflow\": \"Overflow: input needs wider integers to process\",\n \"not-basic\": \"Illegal input >= 0x80 (not a basic code point)\",\n \"invalid-input\": \"Invalid input\"\n};\nvar baseMinusTMin = base - tMin;\nvar floor = Math.floor;\nvar stringFromCharCode = String.fromCharCode;\nfunction error(type) {\n throw new RangeError(errors[type]);\n}\nfunction map(array, callback) {\n const result = [];\n let length = array.length;\n while (length--) {\n result[length] = callback(array[length]);\n }\n return result;\n}\nfunction mapDomain(domain, callback) {\n const parts = domain.split(\"@\");\n let result = \"\";\n if (parts.length > 1) {\n result = parts[0] + \"@\";\n domain = parts[1];\n }\n domain = domain.replace(regexSeparators, \".\");\n const labels = domain.split(\".\");\n const encoded = map(labels, callback).join(\".\");\n return result + encoded;\n}\nfunction ucs2decode(string) {\n const output = [];\n let counter = 0;\n const length = string.length;\n while (counter < length) {\n const value = string.charCodeAt(counter++);\n if (value >= 55296 && value <= 56319 && counter < length) {\n const extra = string.charCodeAt(counter++);\n if ((extra & 64512) == 56320) {\n output.push(((value & 1023) << 10) + (extra & 1023) + 65536);\n } else {\n output.push(value);\n counter--;\n }\n } else {\n output.push(value);\n }\n }\n return output;\n}\nvar ucs2encode = (codePoints) => String.fromCodePoint(...codePoints);\nvar basicToDigit = function(codePoint) {\n if (codePoint >= 48 && codePoint < 58) {\n return 26 + (codePoint - 48);\n }\n if (codePoint >= 65 && codePoint < 91) {\n return codePoint - 65;\n }\n if (codePoint >= 97 && codePoint < 123) {\n return codePoint - 97;\n }\n return base;\n};\nvar digitToBasic = function(digit, flag) {\n return digit + 22 + 75 * (digit < 26) - ((flag != 0) << 5);\n};\nvar adapt = function(delta, numPoints, firstTime) {\n let k = 0;\n delta = firstTime ? floor(delta / damp) : delta >> 1;\n delta += floor(delta / numPoints);\n for (; delta > baseMinusTMin * tMax >> 1; k += base) {\n delta = floor(delta / baseMinusTMin);\n }\n return floor(k + (baseMinusTMin + 1) * delta / (delta + skew));\n};\nvar decode2 = function(input) {\n const output = [];\n const inputLength = input.length;\n let i = 0;\n let n = initialN;\n let bias = initialBias;\n let basic = input.lastIndexOf(delimiter);\n if (basic < 0) {\n basic = 0;\n }\n for (let j = 0; j < basic; ++j) {\n if (input.charCodeAt(j) >= 128) {\n error(\"not-basic\");\n }\n output.push(input.charCodeAt(j));\n }\n for (let index = basic > 0 ? basic + 1 : 0; index < inputLength; ) {\n const oldi = i;\n for (let w = 1, k = base; ; k += base) {\n if (index >= inputLength) {\n error(\"invalid-input\");\n }\n const digit = basicToDigit(input.charCodeAt(index++));\n if (digit >= base) {\n error(\"invalid-input\");\n }\n if (digit > floor((maxInt - i) / w)) {\n error(\"overflow\");\n }\n i += digit * w;\n const t = k <= bias ? tMin : k >= bias + tMax ? tMax : k - bias;\n if (digit < t) {\n break;\n }\n const baseMinusT = base - t;\n if (w > floor(maxInt / baseMinusT)) {\n error(\"overflow\");\n }\n w *= baseMinusT;\n }\n const out = output.length + 1;\n bias = adapt(i - oldi, out, oldi == 0);\n if (floor(i / out) > maxInt - n) {\n error(\"overflow\");\n }\n n += floor(i / out);\n i %= out;\n output.splice(i++, 0, n);\n }\n return String.fromCodePoint(...output);\n};\nvar encode2 = function(input) {\n const output = [];\n input = ucs2decode(input);\n const inputLength = input.length;\n let n = initialN;\n let delta = 0;\n let bias = initialBias;\n for (const currentValue of input) {\n if (currentValue < 128) {\n output.push(stringFromCharCode(currentValue));\n }\n }\n const basicLength = output.length;\n let handledCPCount = basicLength;\n if (basicLength) {\n output.push(delimiter);\n }\n while (handledCPCount < inputLength) {\n let m = maxInt;\n for (const currentValue of input) {\n if (currentValue >= n && currentValue < m) {\n m = currentValue;\n }\n }\n const handledCPCountPlusOne = handledCPCount + 1;\n if (m - n > floor((maxInt - delta) / handledCPCountPlusOne)) {\n error(\"overflow\");\n }\n delta += (m - n) * handledCPCountPlusOne;\n n = m;\n for (const currentValue of input) {\n if (currentValue < n && ++delta > maxInt) {\n error(\"overflow\");\n }\n if (currentValue === n) {\n let q = delta;\n for (let k = base; ; k += base) {\n const t = k <= bias ? tMin : k >= bias + tMax ? tMax : k - bias;\n if (q < t) {\n break;\n }\n const qMinusT = q - t;\n const baseMinusT = base - t;\n output.push(\n stringFromCharCode(digitToBasic(t + qMinusT % baseMinusT, 0))\n );\n q = floor(qMinusT / baseMinusT);\n }\n output.push(stringFromCharCode(digitToBasic(q, 0)));\n bias = adapt(delta, handledCPCountPlusOne, handledCPCount === basicLength);\n delta = 0;\n ++handledCPCount;\n }\n }\n ++delta;\n ++n;\n }\n return output.join(\"\");\n};\nvar toUnicode = function(input) {\n return mapDomain(input, function(string) {\n return regexPunycode.test(string) ? decode2(string.slice(4).toLowerCase()) : string;\n });\n};\nvar toASCII = function(input) {\n return mapDomain(input, function(string) {\n return regexNonASCII.test(string) ? \"xn--\" + encode2(string) : string;\n });\n};\nvar punycode = {\n /**\n * A string representing the current Punycode.js version number.\n * @memberOf punycode\n * @type String\n */\n \"version\": \"2.3.1\",\n /**\n * An object of methods to convert from JavaScript's internal character\n * representation (UCS-2) to Unicode code points, and back.\n * @see \n * @memberOf punycode\n * @type Object\n */\n \"ucs2\": {\n \"decode\": ucs2decode,\n \"encode\": ucs2encode\n },\n \"decode\": decode2,\n \"encode\": encode2,\n \"toASCII\": toASCII,\n \"toUnicode\": toUnicode\n};\nvar punycode_es6_default = punycode;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/presets/default.mjs\nvar default_default = {\n options: {\n // Enable HTML tags in source\n html: false,\n // Use '/' to close single tags (
)\n xhtmlOut: false,\n // Convert '\\n' in paragraphs into
\n breaks: false,\n // CSS language prefix for fenced blocks\n langPrefix: \"language-\",\n // autoconvert URL-like texts to links\n linkify: false,\n // Enable some language-neutral replacements + quotes beautification\n typographer: false,\n // Double + single quotes replacement pairs, when typographer enabled,\n // and smartquotes on. Could be either a String or an Array.\n //\n // For example, you can use '«»„“' for Russian, '„“‚‘' for German,\n // and ['«\\xA0', '\\xA0»', '‹\\xA0', '\\xA0›'] for French (including nbsp).\n quotes: \"“”‘’\",\n /* “”‘’ */\n // Highlighter function. Should return escaped HTML,\n // or '' if the source string is not changed and should be escaped externaly.\n // If result starts with )\n xhtmlOut: false,\n // Convert '\\n' in paragraphs into
\n breaks: false,\n // CSS language prefix for fenced blocks\n langPrefix: \"language-\",\n // autoconvert URL-like texts to links\n linkify: false,\n // Enable some language-neutral replacements + quotes beautification\n typographer: false,\n // Double + single quotes replacement pairs, when typographer enabled,\n // and smartquotes on. Could be either a String or an Array.\n //\n // For example, you can use '«»„“' for Russian, '„“‚‘' for German,\n // and ['«\\xA0', '\\xA0»', '‹\\xA0', '\\xA0›'] for French (including nbsp).\n quotes: \"“”‘’\",\n /* “”‘’ */\n // Highlighter function. Should return escaped HTML,\n // or '' if the source string is not changed and should be escaped externaly.\n // If result starts with )\n xhtmlOut: true,\n // Convert '\\n' in paragraphs into
\n breaks: false,\n // CSS language prefix for fenced blocks\n langPrefix: \"language-\",\n // autoconvert URL-like texts to links\n linkify: false,\n // Enable some language-neutral replacements + quotes beautification\n typographer: false,\n // Double + single quotes replacement pairs, when typographer enabled,\n // and smartquotes on. Could be either a String or an Array.\n //\n // For example, you can use '«»„“' for Russian, '„“‚‘' for German,\n // and ['«\\xA0', '\\xA0»', '‹\\xA0', '\\xA0›'] for French (including nbsp).\n quotes: \"“”‘’\",\n /* “”‘’ */\n // Highlighter function. Should return escaped HTML,\n // or '' if the source string is not changed and should be escaped externaly.\n // If result starts with = 0) {\n try {\n parsed.hostname = punycode_es6_default.toASCII(parsed.hostname);\n } catch (er) {\n }\n }\n }\n return encode_default(format(parsed));\n}\nfunction normalizeLinkText(url) {\n const parsed = parse_default(url, true);\n if (parsed.hostname) {\n if (!parsed.protocol || RECODE_HOSTNAME_FOR.indexOf(parsed.protocol) >= 0) {\n try {\n parsed.hostname = punycode_es6_default.toUnicode(parsed.hostname);\n } catch (er) {\n }\n }\n }\n return decode_default(format(parsed), decode_default.defaultChars + \"%\");\n}\nfunction MarkdownIt(presetName, options) {\n if (!(this instanceof MarkdownIt)) {\n return new MarkdownIt(presetName, options);\n }\n if (!options) {\n if (!isString(presetName)) {\n options = presetName || {};\n presetName = \"default\";\n }\n }\n this.inline = new parser_inline_default();\n this.block = new parser_block_default();\n this.core = new parser_core_default();\n this.renderer = new renderer_default();\n this.linkify = new linkify_it_default();\n this.validateLink = validateLink;\n this.normalizeLink = normalizeLink;\n this.normalizeLinkText = normalizeLinkText;\n this.utils = utils_exports;\n this.helpers = assign({}, helpers_exports);\n this.options = {};\n this.configure(presetName);\n if (options) {\n this.set(options);\n }\n}\nMarkdownIt.prototype.set = function(options) {\n assign(this.options, options);\n return this;\n};\nMarkdownIt.prototype.configure = function(presets) {\n const self = this;\n if (isString(presets)) {\n const presetName = presets;\n presets = config[presetName];\n if (!presets) {\n throw new Error('Wrong `markdown-it` preset \"' + presetName + '\", check name');\n }\n }\n if (!presets) {\n throw new Error(\"Wrong `markdown-it` preset, can't be empty\");\n }\n if (presets.options) {\n self.set(presets.options);\n }\n if (presets.components) {\n Object.keys(presets.components).forEach(function(name) {\n if (presets.components[name].rules) {\n self[name].ruler.enableOnly(presets.components[name].rules);\n }\n if (presets.components[name].rules2) {\n self[name].ruler2.enableOnly(presets.components[name].rules2);\n }\n });\n }\n return this;\n};\nMarkdownIt.prototype.enable = function(list2, ignoreInvalid) {\n let result = [];\n if (!Array.isArray(list2)) {\n list2 = [list2];\n }\n [\"core\", \"block\", \"inline\"].forEach(function(chain) {\n result = result.concat(this[chain].ruler.enable(list2, true));\n }, this);\n result = result.concat(this.inline.ruler2.enable(list2, true));\n const missed = list2.filter(function(name) {\n return result.indexOf(name) < 0;\n });\n if (missed.length && !ignoreInvalid) {\n throw new Error(\"MarkdownIt. Failed to enable unknown rule(s): \" + missed);\n }\n return this;\n};\nMarkdownIt.prototype.disable = function(list2, ignoreInvalid) {\n let result = [];\n if (!Array.isArray(list2)) {\n list2 = [list2];\n }\n [\"core\", \"block\", \"inline\"].forEach(function(chain) {\n result = result.concat(this[chain].ruler.disable(list2, true));\n }, this);\n result = result.concat(this.inline.ruler2.disable(list2, true));\n const missed = list2.filter(function(name) {\n return result.indexOf(name) < 0;\n });\n if (missed.length && !ignoreInvalid) {\n throw new Error(\"MarkdownIt. Failed to disable unknown rule(s): \" + missed);\n }\n return this;\n};\nMarkdownIt.prototype.use = function(plugin) {\n const args = [this].concat(Array.prototype.slice.call(arguments, 1));\n plugin.apply(plugin, args);\n return this;\n};\nMarkdownIt.prototype.parse = function(src, env) {\n if (typeof src !== \"string\") {\n throw new Error(\"Input data should be a String\");\n }\n const state = new this.core.State(src, this, env);\n this.core.process(state);\n return state.tokens;\n};\nMarkdownIt.prototype.render = function(src, env) {\n env = env || {};\n return this.renderer.render(this.parse(src, env), this.options, env);\n};\nMarkdownIt.prototype.parseInline = function(src, env) {\n const state = new this.core.State(src, this, env);\n state.inlineMode = true;\n this.core.process(state);\n return state.tokens;\n};\nMarkdownIt.prototype.renderInline = function(src, env) {\n env = env || {};\n return this.renderer.render(this.parseInline(src, env), this.options, env);\n};\nvar lib_default = MarkdownIt;\n\n// apps/ecosystem-certifier/fixtures/positive/markdown-it-entry.ts\nvar md = new lib_default({\n linkify: true\n});\nvar source = Host.v1.document.get(\"text/markdown-case\");\nvar tokens = md.parse(source, {});\nvar links = md.render(source).match(/
token.type),\n tokenCount: tokens.length,\n linkCount: links\n};\nexport {\n markdown_it_entry_default as default\n};\n", + "sourceMap": "{\"mappings\":\"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AQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UA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E,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,MAAK,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,uBAAuB,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,mBAAmB,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,yBAAyB,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,IAAG,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,EAAC,GAAE,iBAAgB,GAAE,MAAK,GAAE,eAAc,CAAC,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,kBAAkB,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,IAAG,QAAQ,GAAE,CAAC,IAAG,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,IAAG,aAAa,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,cAAc,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,IAAG,wBAAwB,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,IAAG,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,IAAG,QAAQ,GAAE,CAAC,GAAE,gBAAgB,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,eAAe,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,mBAAmB,GAAE,CAAC,GAAE,kBAAkB,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,KAAI,GAAE,WAAU,CAAC,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,gBAAgB,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,gBAAgB,GAAE,CAAC,GAAE,iBAAiB,GAAE,CAAC,GAAE,kBAAkB,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,kBAAkB,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,mBAAmB,GAAE,CAAC,GAAE,oBAAoB,GAAE,CAAC,GAAE,iBAAiB,GAAE,CAAC,GAAE,kBAAkB,GAAE,CAAC,GAAE,iBAAiB,GAAE,CAAC,GAAE,gBAAgB,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,mBAAmB,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,uBAAuB,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,uBAAuB,GAAE,CAAC,GAAE,kBAAkB,GAAE,CAAC,GAAE,cAAc,GAAE,CAAC,GAAE,oBAAoB,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,qBAAqB,GAAE,CAAC,GAAE,eAAe,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,mBAAmB,GAAE,CAAC,GAAE,iBAAiB,GAAE,CAAC,GAAE,oBAAoB,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,wBAAwB,GAAE,CAAC,GAAE,qBAAqB,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,IAAG,oBAAoB,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,EAAC,GAAE,UAAS,GAAE,KAAI,GAAE,UAAS,CAAC,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,cAAc,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,EAAC,GAAE,SAAQ,GAAE,MAAK,GAAE,SAAQ,CAAC,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,qBAAqB,GAAE,CAAC,GAAE,wBAAwB,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,EAAC,GAAE,SAAQ,GAAE,OAAM,GAAE,SAAQ,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,SAAQ,GAAE,OAAM,GAAE,SAAQ,CAAC,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,4BAA4B,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,EAAC,GAAE,SAAQ,GAAE,MAAK,GAAE,UAAS,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,aAAY,GAAE,KAAI,GAAE,SAAQ,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,QAAO,GAAE,KAAI,GAAE,QAAO,CAAC,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,iBAAiB,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,KAAI,GAAE,UAAS,CAAC,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,iBAAiB,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,EAAC,GAAE,UAAS,GAAE,KAAI,GAAE,UAAS,CAAC,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,EAAC,GAAE,aAAY,GAAE,MAAK,GAAE,SAAQ,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,UAAS,GAAE,KAAI,GAAE,UAAS,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,KAAI,GAAE,WAAU,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,KAAI,GAAE,UAAS,CAAC,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,EAAC,GAAE,eAAc,GAAE,MAAK,GAAE,YAAW,CAAC,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,EAAC,GAAE,QAAO,GAAE,MAAK,GAAE,SAAQ,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,QAAO,GAAE,MAAK,GAAE,SAAQ,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,QAAO,GAAE,KAAI,GAAE,QAAO,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,QAAO,GAAE,KAAI,GAAE,QAAO,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,SAAQ,GAAE,OAAM,GAAE,cAAa,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,SAAQ,GAAE,OAAM,GAAE,cAAa,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,QAAO,GAAE,IAAI,IAAkC,4BAAY,CAAC,CAAC,KAAI,QAAQ,GAAE,CAAC,MAAK,OAAO,CAAC,CAAC,CAAC,EAAC,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,QAAO,GAAE,IAAI,IAAkC,4BAAY,CAAC,CAAC,KAAI,QAAQ,GAAE,CAAC,MAAK,OAAO,CAAC,CAAC,CAAC,EAAC,CAAC,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,gBAAgB,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,eAAe,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,kBAAkB,GAAE,CAAC,GAAE,kBAAkB,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,iBAAiB,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,KAAI,GAAE,qBAAoB,CAAC,GAAE,CAAC,GAAE,eAAe,GAAE,CAAC,GAAE,eAAe,GAAE,CAAC,GAAE,EAAC,GAAE,SAAQ,GAAE,MAAK,GAAE,cAAa,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,SAAQ,GAAE,MAAK,GAAE,gBAAe,CAAC,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,kBAAkB,GAAE,CAAC,GAAE,oBAAoB,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,OAAM,GAAE,iBAAgB,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,OAAM,GAAE,iBAAgB,CAAC,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,KAAI,GAAE,oBAAmB,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,KAAI,GAAE,sBAAqB,CAAC,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,OAAM,GAAE,WAAU,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,OAAM,GAAE,WAAU,CAAC,GAAE,CAAC,GAAE,cAAc,GAAE,CAAC,GAAE,eAAe,GAAE,CAAC,GAAE,eAAe,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,eAAe,GAAE,CAAC,GAAE,cAAc,GAAE,CAAC,GAAE,eAAe,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,kBAAkB,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,gBAAgB,GAAE,CAAC,GAAE,iBAAiB,GAAE,CAAC,GAAE,EAAC,GAAE,uBAAsB,GAAE,MAAK,GAAE,YAAW,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,wBAAuB,GAAE,MAAK,GAAE,YAAW,CAAC,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,iBAAiB,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,kBAAkB,GAAE,CAAC,GAAE,mBAAmB,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,cAAc,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,EAAC,GAAE,QAAO,GAAE,KAAI,GAAE,QAAO,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,QAAO,GAAE,KAAI,GAAE,QAAO,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,SAAQ,GAAE,OAAM,GAAE,SAAQ,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,SAAQ,GAAE,OAAM,GAAE,SAAQ,CAAC,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,yBAAyB,GAAE,CAAC,GAAE,yBAAyB,GAAE,CAAC,GAAE,wBAAwB,GAAE,CAAC,GAAE,0BAA0B,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,oBAAoB,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,yBAAyB,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,EAAC,GAAE,aAAY,GAAE,KAAI,GAAE,aAAY,CAAC,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,KAAI,GAAE,WAAU,CAAC,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,IAAG,WAAW,GAAE,CAAC,IAAG,cAAc,GAAE,CAAC,GAAE,cAAc,GAAE,CAAC,GAAE,eAAe,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,IAAG,mBAAmB,GAAE,CAAC,GAAE,oBAAoB,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,cAAc,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,IAAG,SAAS,GAAE,CAAC,KAAI,YAAY,GAAE,CAAC,IAAG,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,IAAG,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,IAAG,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,IAAG,UAAU,GAAE,CAAC,GAAE,eAAe,GAAE,CAAC,GAAE,wBAAwB,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,iBAAiB,GAAE,CAAC,GAAE,iBAAiB,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,sBAAsB,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,mBAAmB,GAAE,CAAC,GAAE,qBAAqB,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,qBAAqB,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,IAAG,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,oBAAoB,GAAE,CAAC,GAAE,qBAAqB,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,IAAG,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,IAAG,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,eAAe,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,KAAI,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,IAAG,QAAQ,GAAE,CAAC,IAAG,qBAAqB,GAAE,CAAC,IAAG,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,IAAG,YAAY,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,IAAG,qBAAqB,GAAE,CAAC,GAAE,sBAAsB,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,iBAAiB,GAAE,CAAC,GAAE,kBAAkB,GAAE,CAAC,GAAE,sBAAsB,GAAE,CAAC,GAAE,uBAAuB,GAAE,CAAC,GAAE,wBAAwB,GAAE,CAAC,GAAE,4BAA4B,GAAE,CAAC,GAAE,cAAc,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,KAAI,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,cAAc,GAAE,CAAC,GAAE,gBAAgB,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,KAAI,GAAE,WAAU,CAAC,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,mBAAmB,GAAE,CAAC,GAAE,qBAAqB,GAAE,CAAC,GAAE,uBAAuB,GAAE,CAAC,GAAE,oBAAoB,GAAE,CAAC,GAAE,iBAAiB,GAAE,CAAC,GAAE,kBAAkB,GAAE,CAAC,GAAE,oBAAoB,GAAE,CAAC,GAAE,sBAAsB,GAAE,CAAC,GAAE,qBAAqB,GAAE,CAAC,GAAE,sBAAsB,GAAE,CAAC,GAAE,mBAAmB,GAAE,CAAC,GAAE,qBAAqB,GAAE,CAAC,GAAE,iBAAiB,GAAE,CAAC,GAAE,kBAAkB,GAAE,CAAC,GAAE,oBAAoB,GAAE,CAAC,GAAE,sBAAsB,GAAE,CAAC,GAAE,qBAAqB,GAAE,CAAC,GAAE,sBAAsB,GAAE,CAAC,GAAE,mBAAmB,GAAE,CAAC,GAAE,qBAAqB,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,gBAAgB,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,EAAC,GAAE,qBAAoB,GAAE,KAAI,GAAE,uBAAsB,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,sBAAqB,GAAE,KAAI,GAAE,wBAAuB,CAAC,GAAE,CAAC,IAAG,UAAU,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,gBAAgB,GAAE,CAAC,GAAE,eAAe,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,IAAG,WAAW,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,EAAC,GAAE,aAAY,GAAE,KAAI,GAAE,aAAY,CAAC,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,EAAC,GAAE,SAAQ,GAAE,KAAI,GAAE,SAAQ,CAAC,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,EAAC,GAAE,cAAa,GAAE,KAAI,GAAE,cAAa,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,cAAa,GAAE,KAAI,GAAE,cAAa,CAAC,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,EAAC,GAAE,cAAa,GAAE,KAAI,GAAE,sBAAqB,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,oBAAmB,GAAE,KAAI,GAAE,4BAA2B,CAAC,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,EAAC,GAAE,UAAS,GAAE,OAAM,GAAE,UAAS,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,UAAS,GAAE,OAAM,GAAE,UAAS,CAAC,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,EAAC,GAAE,mBAAkB,GAAE,KAAI,GAAE,qBAAoB,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,SAAQ,GAAE,KAAI,GAAE,qBAAoB,CAAC,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,eAAe,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,MAAM,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,EAAC,GAAE,UAAS,GAAE,KAAI,GAAE,UAAS,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,UAAS,GAAE,KAAI,GAAE,UAAS,CAAC,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,OAAM,GAAE,kBAAiB,CAAC,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,OAAM,GAAE,kBAAiB,CAAC,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,WAAW,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,EAAC,GAAE,WAAU,GAAE,MAAK,GAAE,WAAU,CAAC,GAAE,CAAC,OAAM,EAAC,GAAE,IAAI,IAAkC,4BAAY,CAAC,CAAC,OAAM,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,IAAG,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CA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\",\"names\":[\"fromCodePoint\",\"code\",\"regex_default\",\"regex_default\",\"regex_default\",\"regex_default\",\"regex_default\",\"regex_default\",\"_a\",\"CharCodes\",\"BinTrieFlags\",\"code\",\"EntityDecoderState\",\"DecodingMode\",\"errors\",\"base\",\"_a\",\"map\",\"escape\",\"match\",\"EntityLevel\",\"EncodingMode\",\"source\",\"fromCodePoint\",\"match\",\"code\",\"entity\",\"regex_default\",\"code\",\"code\",\"tokens\",\"list\",\"md\",\"tokens\",\"tokens\",\"text\",\"links\",\"match\",\"tokens\",\"text\",\"tokens\",\"md\",\"tokens\",\"code\",\"nextLine\",\"pos\",\"max\",\"_rules\",\"md\",\"md\",\"linkify\",\"match\",\"link\",\"escape\",\"postProcess\",\"code\",\"code\",\"tokens\",\"isLinkOpen\",\"isLinkClose\",\"match\",\"match\",\"code\",\"fromCodePoint\",\"tokens\",\"_rules\",\"linkify\",\"escape\",\"_rules2\",\"md\",\"regex_default\",\"assign\",\"source\",\"_class\",\"isString\",\"escapeRE\",\"text\",\"match\",\"tlds\",\"list\",\"normalize\",\"decode\",\"encode\",\"list\"],\"sources\":[\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/common/utils.mjs\",\"../node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/index.mjs\",\"../node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/decode.mjs\",\"../node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/encode.mjs\",\"../node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/format.mjs\",\"../node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/parse.mjs\",\"../node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/index.mjs\",\"../node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/properties/Any/regex.mjs\",\"../node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/Cc/regex.mjs\",\"../node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/Cf/regex.mjs\",\"../node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/P/regex.mjs\",\"../node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/S/regex.mjs\",\"../node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/Z/regex.mjs\",\"https://raw.githubusercontent.com/fb55/entities/61afd4701eaa736978b13c7351cd3de9a96b04bc/src/generated/decode-data-html.ts\",\"https://raw.githubusercontent.com/fb55/entities/61afd4701eaa736978b13c7351cd3de9a96b04bc/src/generated/decode-data-xml.ts\",\"https://raw.githubusercontent.com/fb55/entities/61afd4701eaa736978b13c7351cd3de9a96b04bc/src/decode_codepoint.ts\",\"https://raw.githubusercontent.com/fb55/entities/61afd4701eaa736978b13c7351cd3de9a96b04bc/src/decode.ts\",\"https://raw.githubusercontent.com/fb55/entities/61afd4701eaa736978b13c7351cd3de9a96b04bc/src/generated/encode-html.ts\",\"https://raw.githubusercontent.com/fb55/entities/61afd4701eaa736978b13c7351cd3de9a96b04bc/src/escape.ts\",\"https://raw.githubusercontent.com/fb55/entities/61afd4701eaa736978b13c7351cd3de9a96b04bc/src/index.ts\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/index.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/parse_link_label.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/parse_link_destination.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/parse_link_title.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/renderer.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/ruler.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/token.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/state_core.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/normalize.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/block.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/inline.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/linkify.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/replacements.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/smartquotes.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/text_join.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/parser_core.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/state_block.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/table.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/code.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/fence.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/blockquote.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/hr.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/list.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/reference.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/common/html_blocks.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/common/html_re.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/html_block.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/heading.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/lheading.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/paragraph.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/parser_block.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/state_inline.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/text.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/linkify.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/newline.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/escape.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/backticks.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/strikethrough.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/emphasis.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/link.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/image.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/autolink.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/html_inline.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/entity.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/balance_pairs.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/fragments_join.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/parser_inline.mjs\",\"../node_modules/.pnpm/linkify-it@5.0.0/node_modules/linkify-it/lib/re.mjs\",\"../node_modules/.pnpm/linkify-it@5.0.0/node_modules/linkify-it/index.mjs\",\"../node_modules/.pnpm/punycode.js@2.3.1/node_modules/punycode.js/punycode.es6.js\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/presets/default.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/presets/zero.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/presets/commonmark.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/index.mjs\",\"../apps/ecosystem-certifier/fixtures/positive/markdown-it-entry.ts\"],\"sourcesContent\":[\"// Utilities\\n//\\n\\nimport * as mdurl from 'mdurl'\\nimport * as ucmicro from 'uc.micro'\\nimport { decodeHTML } from 'entities'\\n\\nfunction _class (obj) { return Object.prototype.toString.call(obj) }\\n\\nfunction isString (obj) { return _class(obj) === '[object String]' }\\n\\nconst _hasOwnProperty = Object.prototype.hasOwnProperty\\n\\nfunction has (object, key) {\\n return _hasOwnProperty.call(object, key)\\n}\\n\\n// Merge objects\\n//\\nfunction assign (obj /* from1, from2, from3, ... */) {\\n const sources = Array.prototype.slice.call(arguments, 1)\\n\\n sources.forEach(function (source) {\\n if (!source) { return }\\n\\n if (typeof source !== 'object') {\\n throw new TypeError(source + 'must be object')\\n }\\n\\n Object.keys(source).forEach(function (key) {\\n obj[key] = source[key]\\n })\\n })\\n\\n return obj\\n}\\n\\n// Remove element from array and put another array at those position.\\n// Useful for some operations with tokens\\nfunction arrayReplaceAt (src, pos, newElements) {\\n return [].concat(src.slice(0, pos), newElements, src.slice(pos + 1))\\n}\\n\\nfunction isValidEntityCode (c) {\\n /* eslint no-bitwise:0 */\\n // broken sequence\\n if (c >= 0xD800 && c <= 0xDFFF) { return false }\\n // never used\\n if (c >= 0xFDD0 && c <= 0xFDEF) { return false }\\n if ((c & 0xFFFF) === 0xFFFF || (c & 0xFFFF) === 0xFFFE) { return false }\\n // control codes\\n if (c >= 0x00 && c <= 0x08) { return false }\\n if (c === 0x0B) { return false }\\n if (c >= 0x0E && c <= 0x1F) { return false }\\n if (c >= 0x7F && c <= 0x9F) { return false }\\n // out of range\\n if (c > 0x10FFFF) { return false }\\n return true\\n}\\n\\nfunction fromCodePoint (c) {\\n /* eslint no-bitwise:0 */\\n if (c > 0xffff) {\\n c -= 0x10000\\n const surrogate1 = 0xd800 + (c >> 10)\\n const surrogate2 = 0xdc00 + (c & 0x3ff)\\n\\n return String.fromCharCode(surrogate1, surrogate2)\\n }\\n return String.fromCharCode(c)\\n}\\n\\nconst UNESCAPE_MD_RE = /\\\\\\\\([!\\\"#$%&'()*+,\\\\-./:;<=>?@[\\\\\\\\\\\\]^_`{|}~])/g\\nconst ENTITY_RE = /&([a-z#][a-z0-9]{1,31});/gi\\nconst UNESCAPE_ALL_RE = new RegExp(UNESCAPE_MD_RE.source + '|' + ENTITY_RE.source, 'gi')\\n\\nconst DIGITAL_ENTITY_TEST_RE = /^#((?:x[a-f0-9]{1,8}|[0-9]{1,8}))$/i\\n\\nfunction replaceEntityPattern (match, name) {\\n if (name.charCodeAt(0) === 0x23/* # */ && DIGITAL_ENTITY_TEST_RE.test(name)) {\\n const code = name[1].toLowerCase() === 'x'\\n ? parseInt(name.slice(2), 16)\\n : parseInt(name.slice(1), 10)\\n\\n if (isValidEntityCode(code)) {\\n return fromCodePoint(code)\\n }\\n\\n return match\\n }\\n\\n const decoded = decodeHTML(match)\\n if (decoded !== match) {\\n return decoded\\n }\\n\\n return match\\n}\\n\\n/* function replaceEntities(str) {\\n if (str.indexOf('&') < 0) { return str; }\\n\\n return str.replace(ENTITY_RE, replaceEntityPattern);\\n} */\\n\\nfunction unescapeMd (str) {\\n if (str.indexOf('\\\\\\\\') < 0) { return str }\\n return str.replace(UNESCAPE_MD_RE, '$1')\\n}\\n\\nfunction unescapeAll (str) {\\n if (str.indexOf('\\\\\\\\') < 0 && str.indexOf('&') < 0) { return str }\\n\\n return str.replace(UNESCAPE_ALL_RE, function (match, escaped, entity) {\\n if (escaped) { return escaped }\\n return replaceEntityPattern(match, entity)\\n })\\n}\\n\\nconst HTML_ESCAPE_TEST_RE = /[&<>\\\"]/\\nconst HTML_ESCAPE_REPLACE_RE = /[&<>\\\"]/g\\nconst HTML_REPLACEMENTS = {\\n '&': '&',\\n '<': '<',\\n '>': '>',\\n '\\\"': '"'\\n}\\n\\nfunction replaceUnsafeChar (ch) {\\n return HTML_REPLACEMENTS[ch]\\n}\\n\\nfunction escapeHtml (str) {\\n if (HTML_ESCAPE_TEST_RE.test(str)) {\\n return str.replace(HTML_ESCAPE_REPLACE_RE, replaceUnsafeChar)\\n }\\n return str\\n}\\n\\nconst REGEXP_ESCAPE_RE = /[.?*+^$[\\\\]\\\\\\\\(){}|-]/g\\n\\nfunction escapeRE (str) {\\n return str.replace(REGEXP_ESCAPE_RE, '\\\\\\\\$&')\\n}\\n\\nfunction isSpace (code) {\\n switch (code) {\\n case 0x09:\\n case 0x20:\\n return true\\n }\\n return false\\n}\\n\\n// Zs (unicode class) || [\\\\t\\\\f\\\\v\\\\r\\\\n]\\nfunction isWhiteSpace (code) {\\n if (code >= 0x2000 && code <= 0x200A) { return true }\\n switch (code) {\\n case 0x09: // \\\\t\\n case 0x0A: // \\\\n\\n case 0x0B: // \\\\v\\n case 0x0C: // \\\\f\\n case 0x0D: // \\\\r\\n case 0x20:\\n case 0xA0:\\n case 0x1680:\\n case 0x202F:\\n case 0x205F:\\n case 0x3000:\\n return true\\n }\\n return false\\n}\\n\\n/* eslint-disable max-len */\\n\\n// Currently without astral characters support.\\nfunction isPunctChar (ch) {\\n return ucmicro.P.test(ch) || ucmicro.S.test(ch)\\n}\\n\\n// Markdown ASCII punctuation characters.\\n//\\n// !, \\\", #, $, %, &, ', (, ), *, +, ,, -, ., /, :, ;, <, =, >, ?, @, [, \\\\, ], ^, _, `, {, |, }, or ~\\n// http://spec.commonmark.org/0.15/#ascii-punctuation-character\\n//\\n// Don't confuse with unicode punctuation !!! It lacks some chars in ascii range.\\n//\\nfunction isMdAsciiPunct (ch) {\\n switch (ch) {\\n case 0x21/* ! */:\\n case 0x22/* \\\" */:\\n case 0x23/* # */:\\n case 0x24/* $ */:\\n case 0x25/* % */:\\n case 0x26/* & */:\\n case 0x27/* ' */:\\n case 0x28/* ( */:\\n case 0x29/* ) */:\\n case 0x2A/* * */:\\n case 0x2B/* + */:\\n case 0x2C/* , */:\\n case 0x2D/* - */:\\n case 0x2E/* . */:\\n case 0x2F/* / */:\\n case 0x3A/* : */:\\n case 0x3B/* ; */:\\n case 0x3C/* < */:\\n case 0x3D/* = */:\\n case 0x3E/* > */:\\n case 0x3F/* ? */:\\n case 0x40/* @ */:\\n case 0x5B/* [ */:\\n case 0x5C/* \\\\ */:\\n case 0x5D/* ] */:\\n case 0x5E/* ^ */:\\n case 0x5F/* _ */:\\n case 0x60/* ` */:\\n case 0x7B/* { */:\\n case 0x7C/* | */:\\n case 0x7D/* } */:\\n case 0x7E/* ~ */:\\n return true\\n default:\\n return false\\n }\\n}\\n\\n// Hepler to unify [reference labels].\\n//\\nfunction normalizeReference (str) {\\n // Trim and collapse whitespace\\n //\\n str = str.trim().replace(/\\\\s+/g, ' ')\\n\\n // In node v10 'ẞ'.toLowerCase() === 'Ṿ', which is presumed to be a bug\\n // fixed in v12 (couldn't find any details).\\n //\\n // So treat this one as a special case\\n // (remove this when node v10 is no longer supported).\\n //\\n if ('ẞ'.toLowerCase() === 'Ṿ') {\\n str = str.replace(/ẞ/g, 'ß')\\n }\\n\\n // .toLowerCase().toUpperCase() should get rid of all differences\\n // between letter variants.\\n //\\n // Simple .toLowerCase() doesn't normalize 125 code points correctly,\\n // and .toUpperCase doesn't normalize 6 of them (list of exceptions:\\n // İ, ϴ, ẞ, Ω, K, Å - those are already uppercased, but have differently\\n // uppercased versions).\\n //\\n // Here's an example showing how it happens. Lets take greek letter omega:\\n // uppercase U+0398 (Θ), U+03f4 (ϴ) and lowercase U+03b8 (θ), U+03d1 (ϑ)\\n //\\n // Unicode entries:\\n // 0398;GREEK CAPITAL LETTER THETA;Lu;0;L;;;;;N;;;;03B8;\\n // 03B8;GREEK SMALL LETTER THETA;Ll;0;L;;;;;N;;;0398;;0398\\n // 03D1;GREEK THETA SYMBOL;Ll;0;L; 03B8;;;;N;GREEK SMALL LETTER SCRIPT THETA;;0398;;0398\\n // 03F4;GREEK CAPITAL THETA SYMBOL;Lu;0;L; 0398;;;;N;;;;03B8;\\n //\\n // Case-insensitive comparison should treat all of them as equivalent.\\n //\\n // But .toLowerCase() doesn't change ϑ (it's already lowercase),\\n // and .toUpperCase() doesn't change ϴ (already uppercase).\\n //\\n // Applying first lower then upper case normalizes any character:\\n // '\\\\u0398\\\\u03f4\\\\u03b8\\\\u03d1'.toLowerCase().toUpperCase() === '\\\\u0398\\\\u0398\\\\u0398\\\\u0398'\\n //\\n // Note: this is equivalent to unicode case folding; unicode normalization\\n // is a different step that is not required here.\\n //\\n // Final result should be uppercased, because it's later stored in an object\\n // (this avoid a conflict with Object.prototype members,\\n // most notably, `__proto__`)\\n //\\n return str.toLowerCase().toUpperCase()\\n}\\n\\n// Re-export libraries commonly used in both markdown-it and its plugins,\\n// so plugins won't have to depend on them explicitly, which reduces their\\n// bundled size (e.g. a browser build).\\n//\\nconst lib = { mdurl, ucmicro }\\n\\nexport {\\n lib,\\n assign,\\n isString,\\n has,\\n unescapeMd,\\n unescapeAll,\\n isValidEntityCode,\\n fromCodePoint,\\n escapeHtml,\\n arrayReplaceAt,\\n isSpace,\\n isWhiteSpace,\\n isMdAsciiPunct,\\n isPunctChar,\\n escapeRE,\\n normalizeReference\\n}\\n\",\"import decode from './lib/decode.mjs'\\nimport encode from './lib/encode.mjs'\\nimport format from './lib/format.mjs'\\nimport parse from './lib/parse.mjs'\\n\\nexport {\\n decode,\\n encode,\\n format,\\n parse\\n}\\n\",\"/* eslint-disable no-bitwise */\\n\\nconst decodeCache = {}\\n\\nfunction getDecodeCache (exclude) {\\n let cache = decodeCache[exclude]\\n if (cache) { return cache }\\n\\n cache = decodeCache[exclude] = []\\n\\n for (let i = 0; i < 128; i++) {\\n const ch = String.fromCharCode(i)\\n cache.push(ch)\\n }\\n\\n for (let i = 0; i < exclude.length; i++) {\\n const ch = exclude.charCodeAt(i)\\n cache[ch] = '%' + ('0' + ch.toString(16).toUpperCase()).slice(-2)\\n }\\n\\n return cache\\n}\\n\\n// Decode percent-encoded string.\\n//\\nfunction decode (string, exclude) {\\n if (typeof exclude !== 'string') {\\n exclude = decode.defaultChars\\n }\\n\\n const cache = getDecodeCache(exclude)\\n\\n return string.replace(/(%[a-f0-9]{2})+/gi, function (seq) {\\n let result = ''\\n\\n for (let i = 0, l = seq.length; i < l; i += 3) {\\n const b1 = parseInt(seq.slice(i + 1, i + 3), 16)\\n\\n if (b1 < 0x80) {\\n result += cache[b1]\\n continue\\n }\\n\\n if ((b1 & 0xE0) === 0xC0 && (i + 3 < l)) {\\n // 110xxxxx 10xxxxxx\\n const b2 = parseInt(seq.slice(i + 4, i + 6), 16)\\n\\n if ((b2 & 0xC0) === 0x80) {\\n const chr = ((b1 << 6) & 0x7C0) | (b2 & 0x3F)\\n\\n if (chr < 0x80) {\\n result += '\\\\ufffd\\\\ufffd'\\n } else {\\n result += String.fromCharCode(chr)\\n }\\n\\n i += 3\\n continue\\n }\\n }\\n\\n if ((b1 & 0xF0) === 0xE0 && (i + 6 < l)) {\\n // 1110xxxx 10xxxxxx 10xxxxxx\\n const b2 = parseInt(seq.slice(i + 4, i + 6), 16)\\n const b3 = parseInt(seq.slice(i + 7, i + 9), 16)\\n\\n if ((b2 & 0xC0) === 0x80 && (b3 & 0xC0) === 0x80) {\\n const chr = ((b1 << 12) & 0xF000) | ((b2 << 6) & 0xFC0) | (b3 & 0x3F)\\n\\n if (chr < 0x800 || (chr >= 0xD800 && chr <= 0xDFFF)) {\\n result += '\\\\ufffd\\\\ufffd\\\\ufffd'\\n } else {\\n result += String.fromCharCode(chr)\\n }\\n\\n i += 6\\n continue\\n }\\n }\\n\\n if ((b1 & 0xF8) === 0xF0 && (i + 9 < l)) {\\n // 111110xx 10xxxxxx 10xxxxxx 10xxxxxx\\n const b2 = parseInt(seq.slice(i + 4, i + 6), 16)\\n const b3 = parseInt(seq.slice(i + 7, i + 9), 16)\\n const b4 = parseInt(seq.slice(i + 10, i + 12), 16)\\n\\n if ((b2 & 0xC0) === 0x80 && (b3 & 0xC0) === 0x80 && (b4 & 0xC0) === 0x80) {\\n let chr = ((b1 << 18) & 0x1C0000) | ((b2 << 12) & 0x3F000) | ((b3 << 6) & 0xFC0) | (b4 & 0x3F)\\n\\n if (chr < 0x10000 || chr > 0x10FFFF) {\\n result += '\\\\ufffd\\\\ufffd\\\\ufffd\\\\ufffd'\\n } else {\\n chr -= 0x10000\\n result += String.fromCharCode(0xD800 + (chr >> 10), 0xDC00 + (chr & 0x3FF))\\n }\\n\\n i += 9\\n continue\\n }\\n }\\n\\n result += '\\\\ufffd'\\n }\\n\\n return result\\n })\\n}\\n\\ndecode.defaultChars = ';/?:@&=+$,#'\\ndecode.componentChars = ''\\n\\nexport default decode\\n\",\"const encodeCache = {}\\n\\n// Create a lookup array where anything but characters in `chars` string\\n// and alphanumeric chars is percent-encoded.\\n//\\nfunction getEncodeCache (exclude) {\\n let cache = encodeCache[exclude]\\n if (cache) { return cache }\\n\\n cache = encodeCache[exclude] = []\\n\\n for (let i = 0; i < 128; i++) {\\n const ch = String.fromCharCode(i)\\n\\n if (/^[0-9a-z]$/i.test(ch)) {\\n // always allow unencoded alphanumeric characters\\n cache.push(ch)\\n } else {\\n cache.push('%' + ('0' + i.toString(16).toUpperCase()).slice(-2))\\n }\\n }\\n\\n for (let i = 0; i < exclude.length; i++) {\\n cache[exclude.charCodeAt(i)] = exclude[i]\\n }\\n\\n return cache\\n}\\n\\n// Encode unsafe characters with percent-encoding, skipping already\\n// encoded sequences.\\n//\\n// - string - string to encode\\n// - exclude - list of characters to ignore (in addition to a-zA-Z0-9)\\n// - keepEscaped - don't encode '%' in a correct escape sequence (default: true)\\n//\\nfunction encode (string, exclude, keepEscaped) {\\n if (typeof exclude !== 'string') {\\n // encode(string, keepEscaped)\\n keepEscaped = exclude\\n exclude = encode.defaultChars\\n }\\n\\n if (typeof keepEscaped === 'undefined') {\\n keepEscaped = true\\n }\\n\\n const cache = getEncodeCache(exclude)\\n let result = ''\\n\\n for (let i = 0, l = string.length; i < l; i++) {\\n const code = string.charCodeAt(i)\\n\\n if (keepEscaped && code === 0x25 /* % */ && i + 2 < l) {\\n if (/^[0-9a-f]{2}$/i.test(string.slice(i + 1, i + 3))) {\\n result += string.slice(i, i + 3)\\n i += 2\\n continue\\n }\\n }\\n\\n if (code < 128) {\\n result += cache[code]\\n continue\\n }\\n\\n if (code >= 0xD800 && code <= 0xDFFF) {\\n if (code >= 0xD800 && code <= 0xDBFF && i + 1 < l) {\\n const nextCode = string.charCodeAt(i + 1)\\n if (nextCode >= 0xDC00 && nextCode <= 0xDFFF) {\\n result += encodeURIComponent(string[i] + string[i + 1])\\n i++\\n continue\\n }\\n }\\n result += '%EF%BF%BD'\\n continue\\n }\\n\\n result += encodeURIComponent(string[i])\\n }\\n\\n return result\\n}\\n\\nencode.defaultChars = \\\";/?:@&=+$,-_.!~*'()#\\\"\\nencode.componentChars = \\\"-_.!~*'()\\\"\\n\\nexport default encode\\n\",\"export default function format (url) {\\n let result = ''\\n\\n result += url.protocol || ''\\n result += url.slashes ? '//' : ''\\n result += url.auth ? url.auth + '@' : ''\\n\\n if (url.hostname && url.hostname.indexOf(':') !== -1) {\\n // ipv6 address\\n result += '[' + url.hostname + ']'\\n } else {\\n result += url.hostname || ''\\n }\\n\\n result += url.port ? ':' + url.port : ''\\n result += url.pathname || ''\\n result += url.search || ''\\n result += url.hash || ''\\n\\n return result\\n};\\n\",\"// Copyright Joyent, Inc. and other Node contributors.\\n//\\n// Permission is hereby granted, free of charge, to any person obtaining a\\n// copy of this software and associated documentation files (the\\n// \\\"Software\\\"), to deal in the Software without restriction, including\\n// without limitation the rights to use, copy, modify, merge, publish,\\n// distribute, sublicense, and/or sell copies of the Software, and to permit\\n// persons to whom the Software is furnished to do so, subject to the\\n// following conditions:\\n//\\n// The above copyright notice and this permission notice shall be included\\n// in all copies or substantial portions of the Software.\\n//\\n// THE SOFTWARE IS PROVIDED \\\"AS IS\\\", WITHOUT WARRANTY OF ANY KIND, EXPRESS\\n// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\\n// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN\\n// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,\\n// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR\\n// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE\\n// USE OR OTHER DEALINGS IN THE SOFTWARE.\\n\\n//\\n// Changes from joyent/node:\\n//\\n// 1. No leading slash in paths,\\n// e.g. in `url.parse('http://foo?bar')` pathname is ``, not `/`\\n//\\n// 2. Backslashes are not replaced with slashes,\\n// so `http:\\\\\\\\example.org\\\\` is treated like a relative path\\n//\\n// 3. Trailing colon is treated like a part of the path,\\n// i.e. in `http://example.org:foo` pathname is `:foo`\\n//\\n// 4. Nothing is URL-encoded in the resulting object,\\n// (in joyent/node some chars in auth and paths are encoded)\\n//\\n// 5. `url.parse()` does not have `parseQueryString` argument\\n//\\n// 6. Removed extraneous result properties: `host`, `path`, `query`, etc.,\\n// which can be constructed using other parts of the url.\\n//\\n\\nfunction Url () {\\n this.protocol = null\\n this.slashes = null\\n this.auth = null\\n this.port = null\\n this.hostname = null\\n this.hash = null\\n this.search = null\\n this.pathname = null\\n}\\n\\n// Reference: RFC 3986, RFC 1808, RFC 2396\\n\\n// define these here so at least they only have to be\\n// compiled once on the first module load.\\nconst protocolPattern = /^([a-z0-9.+-]+:)/i\\nconst portPattern = /:[0-9]*$/\\n\\n// Special case for a simple path URL\\n/* eslint-disable-next-line no-useless-escape */\\nconst simplePathPattern = /^(\\\\/\\\\/?(?!\\\\/)[^\\\\?\\\\s]*)(\\\\?[^\\\\s]*)?$/\\n\\n// RFC 2396: characters reserved for delimiting URLs.\\n// We actually just auto-escape these.\\nconst delims = ['<', '>', '\\\"', '`', ' ', '\\\\r', '\\\\n', '\\\\t']\\n\\n// RFC 2396: characters not allowed for various reasons.\\nconst unwise = ['{', '}', '|', '\\\\\\\\', '^', '`'].concat(delims)\\n\\n// Allowed by RFCs, but cause of XSS attacks. Always escape these.\\nconst autoEscape = ['\\\\''].concat(unwise)\\n// Characters that are never ever allowed in a hostname.\\n// Note that any invalid chars are also handled, but these\\n// are the ones that are *expected* to be seen, so we fast-path\\n// them.\\nconst nonHostChars = ['%', '/', '?', ';', '#'].concat(autoEscape)\\nconst hostEndingChars = ['/', '?', '#']\\nconst hostnameMaxLen = 255\\nconst hostnamePartPattern = /^[+a-z0-9A-Z_-]{0,63}$/\\nconst hostnamePartStart = /^([+a-z0-9A-Z_-]{0,63})(.*)$/\\n// protocols that can allow \\\"unsafe\\\" and \\\"unwise\\\" chars.\\n// protocols that never have a hostname.\\nconst hostlessProtocol = {\\n javascript: true,\\n 'javascript:': true\\n}\\n// protocols that always contain a // bit.\\nconst slashedProtocol = {\\n http: true,\\n https: true,\\n ftp: true,\\n gopher: true,\\n file: true,\\n 'http:': true,\\n 'https:': true,\\n 'ftp:': true,\\n 'gopher:': true,\\n 'file:': true\\n}\\n\\nfunction urlParse (url, slashesDenoteHost) {\\n if (url && url instanceof Url) return url\\n\\n const u = new Url()\\n u.parse(url, slashesDenoteHost)\\n return u\\n}\\n\\nUrl.prototype.parse = function (url, slashesDenoteHost) {\\n let lowerProto, hec, slashes\\n let rest = url\\n\\n // trim before proceeding.\\n // This is to support parse stuff like \\\" http://foo.com \\\\n\\\"\\n rest = rest.trim()\\n\\n if (!slashesDenoteHost && url.split('#').length === 1) {\\n // Try fast path regexp\\n const simplePath = simplePathPattern.exec(rest)\\n if (simplePath) {\\n this.pathname = simplePath[1]\\n if (simplePath[2]) {\\n this.search = simplePath[2]\\n }\\n return this\\n }\\n }\\n\\n let proto = protocolPattern.exec(rest)\\n if (proto) {\\n proto = proto[0]\\n lowerProto = proto.toLowerCase()\\n this.protocol = proto\\n rest = rest.substr(proto.length)\\n }\\n\\n // figure out if it's got a host\\n // user@server is *always* interpreted as a hostname, and url\\n // resolution will treat //foo/bar as host=foo,path=bar because that's\\n // how the browser resolves relative URLs.\\n /* eslint-disable-next-line no-useless-escape */\\n if (slashesDenoteHost || proto || rest.match(/^\\\\/\\\\/[^@\\\\/]+@[^@\\\\/]+/)) {\\n slashes = rest.substr(0, 2) === '//'\\n if (slashes && !(proto && hostlessProtocol[proto])) {\\n rest = rest.substr(2)\\n this.slashes = true\\n }\\n }\\n\\n if (!hostlessProtocol[proto] &&\\n (slashes || (proto && !slashedProtocol[proto]))) {\\n // there's a hostname.\\n // the first instance of /, ?, ;, or # ends the host.\\n //\\n // If there is an @ in the hostname, then non-host chars *are* allowed\\n // to the left of the last @ sign, unless some host-ending character\\n // comes *before* the @-sign.\\n // URLs are obnoxious.\\n //\\n // ex:\\n // http://a@b@c/ => user:a@b host:c\\n // http://a@b?@c => user:a host:c path:/?@c\\n\\n // v0.12 TODO(isaacs): This is not quite how Chrome does things.\\n // Review our test case against browsers more comprehensively.\\n\\n // find the first instance of any hostEndingChars\\n let hostEnd = -1\\n for (let i = 0; i < hostEndingChars.length; i++) {\\n hec = rest.indexOf(hostEndingChars[i])\\n if (hec !== -1 && (hostEnd === -1 || hec < hostEnd)) {\\n hostEnd = hec\\n }\\n }\\n\\n // at this point, either we have an explicit point where the\\n // auth portion cannot go past, or the last @ char is the decider.\\n let auth, atSign\\n if (hostEnd === -1) {\\n // atSign can be anywhere.\\n atSign = rest.lastIndexOf('@')\\n } else {\\n // atSign must be in auth portion.\\n // http://a@b/c@d => host:b auth:a path:/c@d\\n atSign = rest.lastIndexOf('@', hostEnd)\\n }\\n\\n // Now we have a portion which is definitely the auth.\\n // Pull that off.\\n if (atSign !== -1) {\\n auth = rest.slice(0, atSign)\\n rest = rest.slice(atSign + 1)\\n this.auth = auth\\n }\\n\\n // the host is the remaining to the left of the first non-host char\\n hostEnd = -1\\n for (let i = 0; i < nonHostChars.length; i++) {\\n hec = rest.indexOf(nonHostChars[i])\\n if (hec !== -1 && (hostEnd === -1 || hec < hostEnd)) {\\n hostEnd = hec\\n }\\n }\\n // if we still have not hit it, then the entire thing is a host.\\n if (hostEnd === -1) {\\n hostEnd = rest.length\\n }\\n\\n if (rest[hostEnd - 1] === ':') { hostEnd-- }\\n const host = rest.slice(0, hostEnd)\\n rest = rest.slice(hostEnd)\\n\\n // pull out port.\\n this.parseHost(host)\\n\\n // we've indicated that there is a hostname,\\n // so even if it's empty, it has to be present.\\n this.hostname = this.hostname || ''\\n\\n // if hostname begins with [ and ends with ]\\n // assume that it's an IPv6 address.\\n const ipv6Hostname = this.hostname[0] === '[' &&\\n this.hostname[this.hostname.length - 1] === ']'\\n\\n // validate a little.\\n if (!ipv6Hostname) {\\n const hostparts = this.hostname.split(/\\\\./)\\n for (let i = 0, l = hostparts.length; i < l; i++) {\\n const part = hostparts[i]\\n if (!part) { continue }\\n if (!part.match(hostnamePartPattern)) {\\n let newpart = ''\\n for (let j = 0, k = part.length; j < k; j++) {\\n if (part.charCodeAt(j) > 127) {\\n // we replace non-ASCII char with a temporary placeholder\\n // we need this to make sure size of hostname is not\\n // broken by replacing non-ASCII by nothing\\n newpart += 'x'\\n } else {\\n newpart += part[j]\\n }\\n }\\n // we test again with ASCII char only\\n if (!newpart.match(hostnamePartPattern)) {\\n const validParts = hostparts.slice(0, i)\\n const notHost = hostparts.slice(i + 1)\\n const bit = part.match(hostnamePartStart)\\n if (bit) {\\n validParts.push(bit[1])\\n notHost.unshift(bit[2])\\n }\\n if (notHost.length) {\\n rest = notHost.join('.') + rest\\n }\\n this.hostname = validParts.join('.')\\n break\\n }\\n }\\n }\\n }\\n\\n if (this.hostname.length > hostnameMaxLen) {\\n this.hostname = ''\\n }\\n\\n // strip [ and ] from the hostname\\n // the host field still retains them, though\\n if (ipv6Hostname) {\\n this.hostname = this.hostname.substr(1, this.hostname.length - 2)\\n }\\n }\\n\\n // chop off from the tail first.\\n const hash = rest.indexOf('#')\\n if (hash !== -1) {\\n // got a fragment string.\\n this.hash = rest.substr(hash)\\n rest = rest.slice(0, hash)\\n }\\n const qm = rest.indexOf('?')\\n if (qm !== -1) {\\n this.search = rest.substr(qm)\\n rest = rest.slice(0, qm)\\n }\\n if (rest) { this.pathname = rest }\\n if (slashedProtocol[lowerProto] &&\\n this.hostname && !this.pathname) {\\n this.pathname = ''\\n }\\n\\n return this\\n}\\n\\nUrl.prototype.parseHost = function (host) {\\n let port = portPattern.exec(host)\\n if (port) {\\n port = port[0]\\n if (port !== ':') {\\n this.port = port.substr(1)\\n }\\n host = host.substr(0, host.length - port.length)\\n }\\n if (host) { this.hostname = host }\\n}\\n\\nexport default urlParse\\n\",\"import Any from './properties/Any/regex.mjs';\\nimport Cc from './categories/Cc/regex.mjs';\\nimport Cf from './categories/Cf/regex.mjs';\\nimport P from './categories/P/regex.mjs';\\nimport S from './categories/S/regex.mjs';\\nimport Z from './categories/Z/regex.mjs';\\n\\nexport { Any, Cc, Cf, P, S, Z };\\n\",\"export default /[\\\\0-\\\\uD7FF\\\\uE000-\\\\uFFFF]|[\\\\uD800-\\\\uDBFF][\\\\uDC00-\\\\uDFFF]|[\\\\uD800-\\\\uDBFF](?![\\\\uDC00-\\\\uDFFF])|(?:[^\\\\uD800-\\\\uDBFF]|^)[\\\\uDC00-\\\\uDFFF]/\",\"export default /[\\\\0-\\\\x1F\\\\x7F-\\\\x9F]/\",\"export default /[\\\\xAD\\\\u0600-\\\\u0605\\\\u061C\\\\u06DD\\\\u070F\\\\u0890\\\\u0891\\\\u08E2\\\\u180E\\\\u200B-\\\\u200F\\\\u202A-\\\\u202E\\\\u2060-\\\\u2064\\\\u2066-\\\\u206F\\\\uFEFF\\\\uFFF9-\\\\uFFFB]|\\\\uD804[\\\\uDCBD\\\\uDCCD]|\\\\uD80D[\\\\uDC30-\\\\uDC3F]|\\\\uD82F[\\\\uDCA0-\\\\uDCA3]|\\\\uD834[\\\\uDD73-\\\\uDD7A]|\\\\uDB40[\\\\uDC01\\\\uDC20-\\\\uDC7F]/\",\"export default /[!-#%-\\\\*,-\\\\/:;\\\\?@\\\\[-\\\\]_\\\\{\\\\}\\\\xA1\\\\xA7\\\\xAB\\\\xB6\\\\xB7\\\\xBB\\\\xBF\\\\u037E\\\\u0387\\\\u055A-\\\\u055F\\\\u0589\\\\u058A\\\\u05BE\\\\u05C0\\\\u05C3\\\\u05C6\\\\u05F3\\\\u05F4\\\\u0609\\\\u060A\\\\u060C\\\\u060D\\\\u061B\\\\u061D-\\\\u061F\\\\u066A-\\\\u066D\\\\u06D4\\\\u0700-\\\\u070D\\\\u07F7-\\\\u07F9\\\\u0830-\\\\u083E\\\\u085E\\\\u0964\\\\u0965\\\\u0970\\\\u09FD\\\\u0A76\\\\u0AF0\\\\u0C77\\\\u0C84\\\\u0DF4\\\\u0E4F\\\\u0E5A\\\\u0E5B\\\\u0F04-\\\\u0F12\\\\u0F14\\\\u0F3A-\\\\u0F3D\\\\u0F85\\\\u0FD0-\\\\u0FD4\\\\u0FD9\\\\u0FDA\\\\u104A-\\\\u104F\\\\u10FB\\\\u1360-\\\\u1368\\\\u1400\\\\u166E\\\\u169B\\\\u169C\\\\u16EB-\\\\u16ED\\\\u1735\\\\u1736\\\\u17D4-\\\\u17D6\\\\u17D8-\\\\u17DA\\\\u1800-\\\\u180A\\\\u1944\\\\u1945\\\\u1A1E\\\\u1A1F\\\\u1AA0-\\\\u1AA6\\\\u1AA8-\\\\u1AAD\\\\u1B5A-\\\\u1B60\\\\u1B7D\\\\u1B7E\\\\u1BFC-\\\\u1BFF\\\\u1C3B-\\\\u1C3F\\\\u1C7E\\\\u1C7F\\\\u1CC0-\\\\u1CC7\\\\u1CD3\\\\u2010-\\\\u2027\\\\u2030-\\\\u2043\\\\u2045-\\\\u2051\\\\u2053-\\\\u205E\\\\u207D\\\\u207E\\\\u208D\\\\u208E\\\\u2308-\\\\u230B\\\\u2329\\\\u232A\\\\u2768-\\\\u2775\\\\u27C5\\\\u27C6\\\\u27E6-\\\\u27EF\\\\u2983-\\\\u2998\\\\u29D8-\\\\u29DB\\\\u29FC\\\\u29FD\\\\u2CF9-\\\\u2CFC\\\\u2CFE\\\\u2CFF\\\\u2D70\\\\u2E00-\\\\u2E2E\\\\u2E30-\\\\u2E4F\\\\u2E52-\\\\u2E5D\\\\u3001-\\\\u3003\\\\u3008-\\\\u3011\\\\u3014-\\\\u301F\\\\u3030\\\\u303D\\\\u30A0\\\\u30FB\\\\uA4FE\\\\uA4FF\\\\uA60D-\\\\uA60F\\\\uA673\\\\uA67E\\\\uA6F2-\\\\uA6F7\\\\uA874-\\\\uA877\\\\uA8CE\\\\uA8CF\\\\uA8F8-\\\\uA8FA\\\\uA8FC\\\\uA92E\\\\uA92F\\\\uA95F\\\\uA9C1-\\\\uA9CD\\\\uA9DE\\\\uA9DF\\\\uAA5C-\\\\uAA5F\\\\uAADE\\\\uAADF\\\\uAAF0\\\\uAAF1\\\\uABEB\\\\uFD3E\\\\uFD3F\\\\uFE10-\\\\uFE19\\\\uFE30-\\\\uFE52\\\\uFE54-\\\\uFE61\\\\uFE63\\\\uFE68\\\\uFE6A\\\\uFE6B\\\\uFF01-\\\\uFF03\\\\uFF05-\\\\uFF0A\\\\uFF0C-\\\\uFF0F\\\\uFF1A\\\\uFF1B\\\\uFF1F\\\\uFF20\\\\uFF3B-\\\\uFF3D\\\\uFF3F\\\\uFF5B\\\\uFF5D\\\\uFF5F-\\\\uFF65]|\\\\uD800[\\\\uDD00-\\\\uDD02\\\\uDF9F\\\\uDFD0]|\\\\uD801\\\\uDD6F|\\\\uD802[\\\\uDC57\\\\uDD1F\\\\uDD3F\\\\uDE50-\\\\uDE58\\\\uDE7F\\\\uDEF0-\\\\uDEF6\\\\uDF39-\\\\uDF3F\\\\uDF99-\\\\uDF9C]|\\\\uD803[\\\\uDEAD\\\\uDF55-\\\\uDF59\\\\uDF86-\\\\uDF89]|\\\\uD804[\\\\uDC47-\\\\uDC4D\\\\uDCBB\\\\uDCBC\\\\uDCBE-\\\\uDCC1\\\\uDD40-\\\\uDD43\\\\uDD74\\\\uDD75\\\\uDDC5-\\\\uDDC8\\\\uDDCD\\\\uDDDB\\\\uDDDD-\\\\uDDDF\\\\uDE38-\\\\uDE3D\\\\uDEA9]|\\\\uD805[\\\\uDC4B-\\\\uDC4F\\\\uDC5A\\\\uDC5B\\\\uDC5D\\\\uDCC6\\\\uDDC1-\\\\uDDD7\\\\uDE41-\\\\uDE43\\\\uDE60-\\\\uDE6C\\\\uDEB9\\\\uDF3C-\\\\uDF3E]|\\\\uD806[\\\\uDC3B\\\\uDD44-\\\\uDD46\\\\uDDE2\\\\uDE3F-\\\\uDE46\\\\uDE9A-\\\\uDE9C\\\\uDE9E-\\\\uDEA2\\\\uDF00-\\\\uDF09]|\\\\uD807[\\\\uDC41-\\\\uDC45\\\\uDC70\\\\uDC71\\\\uDEF7\\\\uDEF8\\\\uDF43-\\\\uDF4F\\\\uDFFF]|\\\\uD809[\\\\uDC70-\\\\uDC74]|\\\\uD80B[\\\\uDFF1\\\\uDFF2]|\\\\uD81A[\\\\uDE6E\\\\uDE6F\\\\uDEF5\\\\uDF37-\\\\uDF3B\\\\uDF44]|\\\\uD81B[\\\\uDE97-\\\\uDE9A\\\\uDFE2]|\\\\uD82F\\\\uDC9F|\\\\uD836[\\\\uDE87-\\\\uDE8B]|\\\\uD83A[\\\\uDD5E\\\\uDD5F]/\",\"export default /[\\\\$\\\\+<->\\\\^`\\\\|~\\\\xA2-\\\\xA6\\\\xA8\\\\xA9\\\\xAC\\\\xAE-\\\\xB1\\\\xB4\\\\xB8\\\\xD7\\\\xF7\\\\u02C2-\\\\u02C5\\\\u02D2-\\\\u02DF\\\\u02E5-\\\\u02EB\\\\u02ED\\\\u02EF-\\\\u02FF\\\\u0375\\\\u0384\\\\u0385\\\\u03F6\\\\u0482\\\\u058D-\\\\u058F\\\\u0606-\\\\u0608\\\\u060B\\\\u060E\\\\u060F\\\\u06DE\\\\u06E9\\\\u06FD\\\\u06FE\\\\u07F6\\\\u07FE\\\\u07FF\\\\u0888\\\\u09F2\\\\u09F3\\\\u09FA\\\\u09FB\\\\u0AF1\\\\u0B70\\\\u0BF3-\\\\u0BFA\\\\u0C7F\\\\u0D4F\\\\u0D79\\\\u0E3F\\\\u0F01-\\\\u0F03\\\\u0F13\\\\u0F15-\\\\u0F17\\\\u0F1A-\\\\u0F1F\\\\u0F34\\\\u0F36\\\\u0F38\\\\u0FBE-\\\\u0FC5\\\\u0FC7-\\\\u0FCC\\\\u0FCE\\\\u0FCF\\\\u0FD5-\\\\u0FD8\\\\u109E\\\\u109F\\\\u1390-\\\\u1399\\\\u166D\\\\u17DB\\\\u1940\\\\u19DE-\\\\u19FF\\\\u1B61-\\\\u1B6A\\\\u1B74-\\\\u1B7C\\\\u1FBD\\\\u1FBF-\\\\u1FC1\\\\u1FCD-\\\\u1FCF\\\\u1FDD-\\\\u1FDF\\\\u1FED-\\\\u1FEF\\\\u1FFD\\\\u1FFE\\\\u2044\\\\u2052\\\\u207A-\\\\u207C\\\\u208A-\\\\u208C\\\\u20A0-\\\\u20C0\\\\u2100\\\\u2101\\\\u2103-\\\\u2106\\\\u2108\\\\u2109\\\\u2114\\\\u2116-\\\\u2118\\\\u211E-\\\\u2123\\\\u2125\\\\u2127\\\\u2129\\\\u212E\\\\u213A\\\\u213B\\\\u2140-\\\\u2144\\\\u214A-\\\\u214D\\\\u214F\\\\u218A\\\\u218B\\\\u2190-\\\\u2307\\\\u230C-\\\\u2328\\\\u232B-\\\\u2426\\\\u2440-\\\\u244A\\\\u249C-\\\\u24E9\\\\u2500-\\\\u2767\\\\u2794-\\\\u27C4\\\\u27C7-\\\\u27E5\\\\u27F0-\\\\u2982\\\\u2999-\\\\u29D7\\\\u29DC-\\\\u29FB\\\\u29FE-\\\\u2B73\\\\u2B76-\\\\u2B95\\\\u2B97-\\\\u2BFF\\\\u2CE5-\\\\u2CEA\\\\u2E50\\\\u2E51\\\\u2E80-\\\\u2E99\\\\u2E9B-\\\\u2EF3\\\\u2F00-\\\\u2FD5\\\\u2FF0-\\\\u2FFF\\\\u3004\\\\u3012\\\\u3013\\\\u3020\\\\u3036\\\\u3037\\\\u303E\\\\u303F\\\\u309B\\\\u309C\\\\u3190\\\\u3191\\\\u3196-\\\\u319F\\\\u31C0-\\\\u31E3\\\\u31EF\\\\u3200-\\\\u321E\\\\u322A-\\\\u3247\\\\u3250\\\\u3260-\\\\u327F\\\\u328A-\\\\u32B0\\\\u32C0-\\\\u33FF\\\\u4DC0-\\\\u4DFF\\\\uA490-\\\\uA4C6\\\\uA700-\\\\uA716\\\\uA720\\\\uA721\\\\uA789\\\\uA78A\\\\uA828-\\\\uA82B\\\\uA836-\\\\uA839\\\\uAA77-\\\\uAA79\\\\uAB5B\\\\uAB6A\\\\uAB6B\\\\uFB29\\\\uFBB2-\\\\uFBC2\\\\uFD40-\\\\uFD4F\\\\uFDCF\\\\uFDFC-\\\\uFDFF\\\\uFE62\\\\uFE64-\\\\uFE66\\\\uFE69\\\\uFF04\\\\uFF0B\\\\uFF1C-\\\\uFF1E\\\\uFF3E\\\\uFF40\\\\uFF5C\\\\uFF5E\\\\uFFE0-\\\\uFFE6\\\\uFFE8-\\\\uFFEE\\\\uFFFC\\\\uFFFD]|\\\\uD800[\\\\uDD37-\\\\uDD3F\\\\uDD79-\\\\uDD89\\\\uDD8C-\\\\uDD8E\\\\uDD90-\\\\uDD9C\\\\uDDA0\\\\uDDD0-\\\\uDDFC]|\\\\uD802[\\\\uDC77\\\\uDC78\\\\uDEC8]|\\\\uD805\\\\uDF3F|\\\\uD807[\\\\uDFD5-\\\\uDFF1]|\\\\uD81A[\\\\uDF3C-\\\\uDF3F\\\\uDF45]|\\\\uD82F\\\\uDC9C|\\\\uD833[\\\\uDF50-\\\\uDFC3]|\\\\uD834[\\\\uDC00-\\\\uDCF5\\\\uDD00-\\\\uDD26\\\\uDD29-\\\\uDD64\\\\uDD6A-\\\\uDD6C\\\\uDD83\\\\uDD84\\\\uDD8C-\\\\uDDA9\\\\uDDAE-\\\\uDDEA\\\\uDE00-\\\\uDE41\\\\uDE45\\\\uDF00-\\\\uDF56]|\\\\uD835[\\\\uDEC1\\\\uDEDB\\\\uDEFB\\\\uDF15\\\\uDF35\\\\uDF4F\\\\uDF6F\\\\uDF89\\\\uDFA9\\\\uDFC3]|\\\\uD836[\\\\uDC00-\\\\uDDFF\\\\uDE37-\\\\uDE3A\\\\uDE6D-\\\\uDE74\\\\uDE76-\\\\uDE83\\\\uDE85\\\\uDE86]|\\\\uD838[\\\\uDD4F\\\\uDEFF]|\\\\uD83B[\\\\uDCAC\\\\uDCB0\\\\uDD2E\\\\uDEF0\\\\uDEF1]|\\\\uD83C[\\\\uDC00-\\\\uDC2B\\\\uDC30-\\\\uDC93\\\\uDCA0-\\\\uDCAE\\\\uDCB1-\\\\uDCBF\\\\uDCC1-\\\\uDCCF\\\\uDCD1-\\\\uDCF5\\\\uDD0D-\\\\uDDAD\\\\uDDE6-\\\\uDE02\\\\uDE10-\\\\uDE3B\\\\uDE40-\\\\uDE48\\\\uDE50\\\\uDE51\\\\uDE60-\\\\uDE65\\\\uDF00-\\\\uDFFF]|\\\\uD83D[\\\\uDC00-\\\\uDED7\\\\uDEDC-\\\\uDEEC\\\\uDEF0-\\\\uDEFC\\\\uDF00-\\\\uDF76\\\\uDF7B-\\\\uDFD9\\\\uDFE0-\\\\uDFEB\\\\uDFF0]|\\\\uD83E[\\\\uDC00-\\\\uDC0B\\\\uDC10-\\\\uDC47\\\\uDC50-\\\\uDC59\\\\uDC60-\\\\uDC87\\\\uDC90-\\\\uDCAD\\\\uDCB0\\\\uDCB1\\\\uDD00-\\\\uDE53\\\\uDE60-\\\\uDE6D\\\\uDE70-\\\\uDE7C\\\\uDE80-\\\\uDE88\\\\uDE90-\\\\uDEBD\\\\uDEBF-\\\\uDEC5\\\\uDECE-\\\\uDEDB\\\\uDEE0-\\\\uDEE8\\\\uDEF0-\\\\uDEF8\\\\uDF00-\\\\uDF92\\\\uDF94-\\\\uDFCA]/\",\"export default /[ \\\\xA0\\\\u1680\\\\u2000-\\\\u200A\\\\u2028\\\\u2029\\\\u202F\\\\u205F\\\\u3000]/\",null,null,null,null,null,null,null,\"// Just a shortcut for bulk export\\n\\nimport parseLinkLabel from './parse_link_label.mjs'\\nimport parseLinkDestination from './parse_link_destination.mjs'\\nimport parseLinkTitle from './parse_link_title.mjs'\\n\\nexport {\\n parseLinkLabel,\\n parseLinkDestination,\\n parseLinkTitle\\n}\\n\",\"// Parse link label\\n//\\n// this function assumes that first character (\\\"[\\\") already matches;\\n// returns the end of the label\\n//\\n\\nexport default function parseLinkLabel (state, start, disableNested) {\\n let level, found, marker, prevPos\\n\\n const max = state.posMax\\n const oldPos = state.pos\\n\\n state.pos = start + 1\\n level = 1\\n\\n while (state.pos < max) {\\n marker = state.src.charCodeAt(state.pos)\\n if (marker === 0x5D /* ] */) {\\n level--\\n if (level === 0) {\\n found = true\\n break\\n }\\n }\\n\\n prevPos = state.pos\\n state.md.inline.skipToken(state)\\n if (marker === 0x5B /* [ */) {\\n if (prevPos === state.pos - 1) {\\n // increase level if we find text `[`, which is not a part of any token\\n level++\\n } else if (disableNested) {\\n state.pos = oldPos\\n return -1\\n }\\n }\\n }\\n\\n let labelEnd = -1\\n\\n if (found) {\\n labelEnd = state.pos\\n }\\n\\n // restore old state\\n state.pos = oldPos\\n\\n return labelEnd\\n}\\n\",\"// Parse link destination\\n//\\n\\nimport { unescapeAll } from '../common/utils.mjs'\\n\\nexport default function parseLinkDestination (str, start, max) {\\n let code\\n let pos = start\\n\\n const result = {\\n ok: false,\\n pos: 0,\\n str: ''\\n }\\n\\n if (str.charCodeAt(pos) === 0x3C /* < */) {\\n pos++\\n while (pos < max) {\\n code = str.charCodeAt(pos)\\n if (code === 0x0A /* \\\\n */) { return result }\\n if (code === 0x3C /* < */) { return result }\\n if (code === 0x3E /* > */) {\\n result.pos = pos + 1\\n result.str = unescapeAll(str.slice(start + 1, pos))\\n result.ok = true\\n return result\\n }\\n if (code === 0x5C /* \\\\ */ && pos + 1 < max) {\\n pos += 2\\n continue\\n }\\n\\n pos++\\n }\\n\\n // no closing '>'\\n return result\\n }\\n\\n // this should be ... } else { ... branch\\n\\n let level = 0\\n while (pos < max) {\\n code = str.charCodeAt(pos)\\n\\n if (code === 0x20) { break }\\n\\n // ascii control characters\\n if (code < 0x20 || code === 0x7F) { break }\\n\\n if (code === 0x5C /* \\\\ */ && pos + 1 < max) {\\n if (str.charCodeAt(pos + 1) === 0x20) { break }\\n pos += 2\\n continue\\n }\\n\\n if (code === 0x28 /* ( */) {\\n level++\\n if (level > 32) { return result }\\n }\\n\\n if (code === 0x29 /* ) */) {\\n if (level === 0) { break }\\n level--\\n }\\n\\n pos++\\n }\\n\\n if (start === pos) { return result }\\n if (level !== 0) { return result }\\n\\n result.str = unescapeAll(str.slice(start, pos))\\n result.pos = pos\\n result.ok = true\\n return result\\n}\\n\",\"// Parse link title\\n//\\n\\nimport { unescapeAll } from '../common/utils.mjs'\\n\\n// Parse link title within `str` in [start, max] range,\\n// or continue previous parsing if `prev_state` is defined (equal to result of last execution).\\n//\\nexport default function parseLinkTitle (str, start, max, prev_state) {\\n let code\\n let pos = start\\n\\n const state = {\\n // if `true`, this is a valid link title\\n ok: false,\\n // if `true`, this link can be continued on the next line\\n can_continue: false,\\n // if `ok`, it's the position of the first character after the closing marker\\n pos: 0,\\n // if `ok`, it's the unescaped title\\n str: '',\\n // expected closing marker character code\\n marker: 0\\n }\\n\\n if (prev_state) {\\n // this is a continuation of a previous parseLinkTitle call on the next line,\\n // used in reference links only\\n state.str = prev_state.str\\n state.marker = prev_state.marker\\n } else {\\n if (pos >= max) { return state }\\n\\n let marker = str.charCodeAt(pos)\\n if (marker !== 0x22 /* \\\" */ && marker !== 0x27 /* ' */ && marker !== 0x28 /* ( */) { return state }\\n\\n start++\\n pos++\\n\\n // if opening marker is \\\"(\\\", switch it to closing marker \\\")\\\"\\n if (marker === 0x28) { marker = 0x29 }\\n\\n state.marker = marker\\n }\\n\\n while (pos < max) {\\n code = str.charCodeAt(pos)\\n if (code === state.marker) {\\n state.pos = pos + 1\\n state.str += unescapeAll(str.slice(start, pos))\\n state.ok = true\\n return state\\n } else if (code === 0x28 /* ( */ && state.marker === 0x29 /* ) */) {\\n return state\\n } else if (code === 0x5C /* \\\\ */ && pos + 1 < max) {\\n pos++\\n }\\n\\n pos++\\n }\\n\\n // no closing marker found, but this link title may continue on the next line (for references)\\n state.can_continue = true\\n state.str += unescapeAll(str.slice(start, pos))\\n return state\\n}\\n\",\"/**\\n * class Renderer\\n *\\n * Generates HTML from parsed token stream. Each instance has independent\\n * copy of rules. Those can be rewritten with ease. Also, you can add new\\n * rules if you create plugin and adds new token types.\\n **/\\n\\nimport { assign, unescapeAll, escapeHtml } from './common/utils.mjs'\\n\\nconst default_rules = {}\\n\\ndefault_rules.code_inline = function (tokens, idx, options, env, slf) {\\n const token = tokens[idx]\\n\\n return '' +\\n escapeHtml(token.content) +\\n ''\\n}\\n\\ndefault_rules.code_block = function (tokens, idx, options, env, slf) {\\n const token = tokens[idx]\\n\\n return '' +\\n escapeHtml(tokens[idx].content) +\\n '\\\\n'\\n}\\n\\ndefault_rules.fence = function (tokens, idx, options, env, slf) {\\n const token = tokens[idx]\\n const info = token.info ? unescapeAll(token.info).trim() : ''\\n let langName = ''\\n let langAttrs = ''\\n\\n if (info) {\\n const arr = info.split(/(\\\\s+)/g)\\n langName = arr[0]\\n langAttrs = arr.slice(2).join('')\\n }\\n\\n let highlighted\\n if (options.highlight) {\\n highlighted = options.highlight(token.content, langName, langAttrs) || escapeHtml(token.content)\\n } else {\\n highlighted = escapeHtml(token.content)\\n }\\n\\n if (highlighted.indexOf('${highlighted}\\\\n`\\n }\\n\\n return `
${highlighted}
\\\\n`\\n}\\n\\ndefault_rules.image = function (tokens, idx, options, env, slf) {\\n const token = tokens[idx]\\n\\n // \\\"alt\\\" attr MUST be set, even if empty. Because it's mandatory and\\n // should be placed on proper position for tests.\\n //\\n // Replace content with actual value\\n\\n token.attrs[token.attrIndex('alt')][1] =\\n slf.renderInlineAsText(token.children, options, env)\\n\\n return slf.renderToken(tokens, idx, options)\\n}\\n\\ndefault_rules.hardbreak = function (tokens, idx, options /*, env */) {\\n return options.xhtmlOut ? '
\\\\n' : '
\\\\n'\\n}\\ndefault_rules.softbreak = function (tokens, idx, options /*, env */) {\\n return options.breaks ? (options.xhtmlOut ? '
\\\\n' : '
\\\\n') : '\\\\n'\\n}\\n\\ndefault_rules.text = function (tokens, idx /*, options, env */) {\\n return escapeHtml(tokens[idx].content)\\n}\\n\\ndefault_rules.html_block = function (tokens, idx /*, options, env */) {\\n return tokens[idx].content\\n}\\ndefault_rules.html_inline = function (tokens, idx /*, options, env */) {\\n return tokens[idx].content\\n}\\n\\n/**\\n * new Renderer()\\n *\\n * Creates new [[Renderer]] instance and fill [[Renderer#rules]] with defaults.\\n **/\\nfunction Renderer () {\\n /**\\n * Renderer#rules -> Object\\n *\\n * Contains render rules for tokens. Can be updated and extended.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n *\\n * md.renderer.rules.strong_open = function () { return ''; };\\n * md.renderer.rules.strong_close = function () { return ''; };\\n *\\n * var result = md.renderInline(...);\\n * ```\\n *\\n * Each rule is called as independent static function with fixed signature:\\n *\\n * ```javascript\\n * function my_token_render(tokens, idx, options, env, renderer) {\\n * // ...\\n * return renderedHTML;\\n * }\\n * ```\\n *\\n * See [source code](https://github.com/markdown-it/markdown-it/blob/master/lib/renderer.mjs)\\n * for more details and examples.\\n **/\\n this.rules = assign({}, default_rules)\\n}\\n\\n/**\\n * Renderer.renderAttrs(token) -> String\\n *\\n * Render token attributes to string.\\n **/\\nRenderer.prototype.renderAttrs = function renderAttrs (token) {\\n let i, l, result\\n\\n if (!token.attrs) { return '' }\\n\\n result = ''\\n\\n for (i = 0, l = token.attrs.length; i < l; i++) {\\n result += ' ' + escapeHtml(token.attrs[i][0]) + '=\\\"' + escapeHtml(token.attrs[i][1]) + '\\\"'\\n }\\n\\n return result\\n}\\n\\n/**\\n * Renderer.renderToken(tokens, idx, options) -> String\\n * - tokens (Array): list of tokens\\n * - idx (Numbed): token index to render\\n * - options (Object): params of parser instance\\n *\\n * Default token renderer. Can be overriden by custom function\\n * in [[Renderer#rules]].\\n **/\\nRenderer.prototype.renderToken = function renderToken (tokens, idx, options) {\\n const token = tokens[idx]\\n let result = ''\\n\\n // Tight list paragraphs\\n if (token.hidden) {\\n return ''\\n }\\n\\n // Insert a newline between hidden paragraph and subsequent opening\\n // block-level tag.\\n //\\n // For example, here we should insert a newline before blockquote:\\n // - a\\n // >\\n //\\n if (token.block && token.nesting !== -1 && idx && tokens[idx - 1].hidden) {\\n result += '\\\\n'\\n }\\n\\n // Add token name, e.g. ``.\\n //\\n needLf = false\\n }\\n }\\n }\\n }\\n\\n result += needLf ? '>\\\\n' : '>'\\n\\n return result\\n}\\n\\n/**\\n * Renderer.renderInline(tokens, options, env) -> String\\n * - tokens (Array): list on block tokens to render\\n * - options (Object): params of parser instance\\n * - env (Object): additional data from parsed input (references, for example)\\n *\\n * The same as [[Renderer.render]], but for single token of `inline` type.\\n **/\\nRenderer.prototype.renderInline = function (tokens, options, env) {\\n let result = ''\\n const rules = this.rules\\n\\n for (let i = 0, len = tokens.length; i < len; i++) {\\n const type = tokens[i].type\\n\\n if (typeof rules[type] !== 'undefined') {\\n result += rules[type](tokens, i, options, env, this)\\n } else {\\n result += this.renderToken(tokens, i, options)\\n }\\n }\\n\\n return result\\n}\\n\\n/** internal\\n * Renderer.renderInlineAsText(tokens, options, env) -> String\\n * - tokens (Array): list on block tokens to render\\n * - options (Object): params of parser instance\\n * - env (Object): additional data from parsed input (references, for example)\\n *\\n * Special kludge for image `alt` attributes to conform CommonMark spec.\\n * Don't try to use it! Spec requires to show `alt` content with stripped markup,\\n * instead of simple escaping.\\n **/\\nRenderer.prototype.renderInlineAsText = function (tokens, options, env) {\\n let result = ''\\n\\n for (let i = 0, len = tokens.length; i < len; i++) {\\n switch (tokens[i].type) {\\n case 'text':\\n result += tokens[i].content\\n break\\n case 'image':\\n result += this.renderInlineAsText(tokens[i].children, options, env)\\n break\\n case 'html_inline':\\n case 'html_block':\\n result += tokens[i].content\\n break\\n case 'softbreak':\\n case 'hardbreak':\\n result += '\\\\n'\\n break\\n default:\\n // all other tokens are skipped\\n }\\n }\\n\\n return result\\n}\\n\\n/**\\n * Renderer.render(tokens, options, env) -> String\\n * - tokens (Array): list on block tokens to render\\n * - options (Object): params of parser instance\\n * - env (Object): additional data from parsed input (references, for example)\\n *\\n * Takes token stream and generates HTML. Probably, you will never need to call\\n * this method directly.\\n **/\\nRenderer.prototype.render = function (tokens, options, env) {\\n let result = ''\\n const rules = this.rules\\n\\n for (let i = 0, len = tokens.length; i < len; i++) {\\n const type = tokens[i].type\\n\\n if (type === 'inline') {\\n result += this.renderInline(tokens[i].children, options, env)\\n } else if (typeof rules[type] !== 'undefined') {\\n result += rules[type](tokens, i, options, env, this)\\n } else {\\n result += this.renderToken(tokens, i, options, env)\\n }\\n }\\n\\n return result\\n}\\n\\nexport default Renderer\\n\",\"/**\\n * class Ruler\\n *\\n * Helper class, used by [[MarkdownIt#core]], [[MarkdownIt#block]] and\\n * [[MarkdownIt#inline]] to manage sequences of functions (rules):\\n *\\n * - keep rules in defined order\\n * - assign the name to each rule\\n * - enable/disable rules\\n * - add/replace rules\\n * - allow assign rules to additional named chains (in the same)\\n * - cacheing lists of active rules\\n *\\n * You will not need use this class directly until write plugins. For simple\\n * rules control use [[MarkdownIt.disable]], [[MarkdownIt.enable]] and\\n * [[MarkdownIt.use]].\\n **/\\n\\n/**\\n * new Ruler()\\n **/\\nfunction Ruler () {\\n // List of added rules. Each element is:\\n //\\n // {\\n // name: XXX,\\n // enabled: Boolean,\\n // fn: Function(),\\n // alt: [ name2, name3 ]\\n // }\\n //\\n this.__rules__ = []\\n\\n // Cached rule chains.\\n //\\n // First level - chain name, '' for default.\\n // Second level - diginal anchor for fast filtering by charcodes.\\n //\\n this.__cache__ = null\\n}\\n\\n// Helper methods, should not be used directly\\n\\n// Find rule index by name\\n//\\nRuler.prototype.__find__ = function (name) {\\n for (let i = 0; i < this.__rules__.length; i++) {\\n if (this.__rules__[i].name === name) {\\n return i\\n }\\n }\\n return -1\\n}\\n\\n// Build rules lookup cache\\n//\\nRuler.prototype.__compile__ = function () {\\n const self = this\\n const chains = ['']\\n\\n // collect unique names\\n self.__rules__.forEach(function (rule) {\\n if (!rule.enabled) { return }\\n\\n rule.alt.forEach(function (altName) {\\n if (chains.indexOf(altName) < 0) {\\n chains.push(altName)\\n }\\n })\\n })\\n\\n self.__cache__ = {}\\n\\n chains.forEach(function (chain) {\\n self.__cache__[chain] = []\\n self.__rules__.forEach(function (rule) {\\n if (!rule.enabled) { return }\\n\\n if (chain && rule.alt.indexOf(chain) < 0) { return }\\n\\n self.__cache__[chain].push(rule.fn)\\n })\\n })\\n}\\n\\n/**\\n * Ruler.at(name, fn [, options])\\n * - name (String): rule name to replace.\\n * - fn (Function): new rule function.\\n * - options (Object): new rule options (not mandatory).\\n *\\n * Replace rule by name with new function & options. Throws error if name not\\n * found.\\n *\\n * ##### Options:\\n *\\n * - __alt__ - array with names of \\\"alternate\\\" chains.\\n *\\n * ##### Example\\n *\\n * Replace existing typographer replacement rule with new one:\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n *\\n * md.core.ruler.at('replacements', function replace(state) {\\n * //...\\n * });\\n * ```\\n **/\\nRuler.prototype.at = function (name, fn, options) {\\n const index = this.__find__(name)\\n const opt = options || {}\\n\\n if (index === -1) { throw new Error('Parser rule not found: ' + name) }\\n\\n this.__rules__[index].fn = fn\\n this.__rules__[index].alt = opt.alt || []\\n this.__cache__ = null\\n}\\n\\n/**\\n * Ruler.before(beforeName, ruleName, fn [, options])\\n * - beforeName (String): new rule will be added before this one.\\n * - ruleName (String): name of added rule.\\n * - fn (Function): rule function.\\n * - options (Object): rule options (not mandatory).\\n *\\n * Add new rule to chain before one with given name. See also\\n * [[Ruler.after]], [[Ruler.push]].\\n *\\n * ##### Options:\\n *\\n * - __alt__ - array with names of \\\"alternate\\\" chains.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n *\\n * md.block.ruler.before('paragraph', 'my_rule', function replace(state) {\\n * //...\\n * });\\n * ```\\n **/\\nRuler.prototype.before = function (beforeName, ruleName, fn, options) {\\n const index = this.__find__(beforeName)\\n const opt = options || {}\\n\\n if (index === -1) { throw new Error('Parser rule not found: ' + beforeName) }\\n\\n this.__rules__.splice(index, 0, {\\n name: ruleName,\\n enabled: true,\\n fn,\\n alt: opt.alt || []\\n })\\n\\n this.__cache__ = null\\n}\\n\\n/**\\n * Ruler.after(afterName, ruleName, fn [, options])\\n * - afterName (String): new rule will be added after this one.\\n * - ruleName (String): name of added rule.\\n * - fn (Function): rule function.\\n * - options (Object): rule options (not mandatory).\\n *\\n * Add new rule to chain after one with given name. See also\\n * [[Ruler.before]], [[Ruler.push]].\\n *\\n * ##### Options:\\n *\\n * - __alt__ - array with names of \\\"alternate\\\" chains.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n *\\n * md.inline.ruler.after('text', 'my_rule', function replace(state) {\\n * //...\\n * });\\n * ```\\n **/\\nRuler.prototype.after = function (afterName, ruleName, fn, options) {\\n const index = this.__find__(afterName)\\n const opt = options || {}\\n\\n if (index === -1) { throw new Error('Parser rule not found: ' + afterName) }\\n\\n this.__rules__.splice(index + 1, 0, {\\n name: ruleName,\\n enabled: true,\\n fn,\\n alt: opt.alt || []\\n })\\n\\n this.__cache__ = null\\n}\\n\\n/**\\n * Ruler.push(ruleName, fn [, options])\\n * - ruleName (String): name of added rule.\\n * - fn (Function): rule function.\\n * - options (Object): rule options (not mandatory).\\n *\\n * Push new rule to the end of chain. See also\\n * [[Ruler.before]], [[Ruler.after]].\\n *\\n * ##### Options:\\n *\\n * - __alt__ - array with names of \\\"alternate\\\" chains.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n *\\n * md.core.ruler.push('my_rule', function replace(state) {\\n * //...\\n * });\\n * ```\\n **/\\nRuler.prototype.push = function (ruleName, fn, options) {\\n const opt = options || {}\\n\\n this.__rules__.push({\\n name: ruleName,\\n enabled: true,\\n fn,\\n alt: opt.alt || []\\n })\\n\\n this.__cache__ = null\\n}\\n\\n/**\\n * Ruler.enable(list [, ignoreInvalid]) -> Array\\n * - list (String|Array): list of rule names to enable.\\n * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found.\\n *\\n * Enable rules with given names. If any rule name not found - throw Error.\\n * Errors can be disabled by second param.\\n *\\n * Returns list of found rule names (if no exception happened).\\n *\\n * See also [[Ruler.disable]], [[Ruler.enableOnly]].\\n **/\\nRuler.prototype.enable = function (list, ignoreInvalid) {\\n if (!Array.isArray(list)) { list = [list] }\\n\\n const result = []\\n\\n // Search by name and enable\\n list.forEach(function (name) {\\n const idx = this.__find__(name)\\n\\n if (idx < 0) {\\n if (ignoreInvalid) { return }\\n throw new Error('Rules manager: invalid rule name ' + name)\\n }\\n this.__rules__[idx].enabled = true\\n result.push(name)\\n }, this)\\n\\n this.__cache__ = null\\n return result\\n}\\n\\n/**\\n * Ruler.enableOnly(list [, ignoreInvalid])\\n * - list (String|Array): list of rule names to enable (whitelist).\\n * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found.\\n *\\n * Enable rules with given names, and disable everything else. If any rule name\\n * not found - throw Error. Errors can be disabled by second param.\\n *\\n * See also [[Ruler.disable]], [[Ruler.enable]].\\n **/\\nRuler.prototype.enableOnly = function (list, ignoreInvalid) {\\n if (!Array.isArray(list)) { list = [list] }\\n\\n this.__rules__.forEach(function (rule) { rule.enabled = false })\\n\\n this.enable(list, ignoreInvalid)\\n}\\n\\n/**\\n * Ruler.disable(list [, ignoreInvalid]) -> Array\\n * - list (String|Array): list of rule names to disable.\\n * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found.\\n *\\n * Disable rules with given names. If any rule name not found - throw Error.\\n * Errors can be disabled by second param.\\n *\\n * Returns list of found rule names (if no exception happened).\\n *\\n * See also [[Ruler.enable]], [[Ruler.enableOnly]].\\n **/\\nRuler.prototype.disable = function (list, ignoreInvalid) {\\n if (!Array.isArray(list)) { list = [list] }\\n\\n const result = []\\n\\n // Search by name and disable\\n list.forEach(function (name) {\\n const idx = this.__find__(name)\\n\\n if (idx < 0) {\\n if (ignoreInvalid) { return }\\n throw new Error('Rules manager: invalid rule name ' + name)\\n }\\n this.__rules__[idx].enabled = false\\n result.push(name)\\n }, this)\\n\\n this.__cache__ = null\\n return result\\n}\\n\\n/**\\n * Ruler.getRules(chainName) -> Array\\n *\\n * Return array of active functions (rules) for given chain name. It analyzes\\n * rules configuration, compiles caches if not exists and returns result.\\n *\\n * Default chain name is `''` (empty string). It can't be skipped. That's\\n * done intentionally, to keep signature monomorphic for high speed.\\n **/\\nRuler.prototype.getRules = function (chainName) {\\n if (this.__cache__ === null) {\\n this.__compile__()\\n }\\n\\n // Chain can be empty, if rules disabled. But we still have to return Array.\\n return this.__cache__[chainName] || []\\n}\\n\\nexport default Ruler\\n\",\"// Token class\\n\\n/**\\n * class Token\\n **/\\n\\n/**\\n * new Token(type, tag, nesting)\\n *\\n * Create new token and fill passed properties.\\n **/\\nfunction Token (type, tag, nesting) {\\n /**\\n * Token#type -> String\\n *\\n * Type of the token (string, e.g. \\\"paragraph_open\\\")\\n **/\\n this.type = type\\n\\n /**\\n * Token#tag -> String\\n *\\n * html tag name, e.g. \\\"p\\\"\\n **/\\n this.tag = tag\\n\\n /**\\n * Token#attrs -> Array\\n *\\n * Html attributes. Format: `[ [ name1, value1 ], [ name2, value2 ] ]`\\n **/\\n this.attrs = null\\n\\n /**\\n * Token#map -> Array\\n *\\n * Source map info. Format: `[ line_begin, line_end ]`\\n **/\\n this.map = null\\n\\n /**\\n * Token#nesting -> Number\\n *\\n * Level change (number in {-1, 0, 1} set), where:\\n *\\n * - `1` means the tag is opening\\n * - `0` means the tag is self-closing\\n * - `-1` means the tag is closing\\n **/\\n this.nesting = nesting\\n\\n /**\\n * Token#level -> Number\\n *\\n * nesting level, the same as `state.level`\\n **/\\n this.level = 0\\n\\n /**\\n * Token#children -> Array\\n *\\n * An array of child nodes (inline and img tokens)\\n **/\\n this.children = null\\n\\n /**\\n * Token#content -> String\\n *\\n * In a case of self-closing tag (code, html, fence, etc.),\\n * it has contents of this tag.\\n **/\\n this.content = ''\\n\\n /**\\n * Token#markup -> String\\n *\\n * '*' or '_' for emphasis, fence string for fence, etc.\\n **/\\n this.markup = ''\\n\\n /**\\n * Token#info -> String\\n *\\n * Additional information:\\n *\\n * - Info string for \\\"fence\\\" tokens\\n * - The value \\\"auto\\\" for autolink \\\"link_open\\\" and \\\"link_close\\\" tokens\\n * - The string value of the item marker for ordered-list \\\"list_item_open\\\" tokens\\n **/\\n this.info = ''\\n\\n /**\\n * Token#meta -> Object\\n *\\n * A place for plugins to store an arbitrary data\\n **/\\n this.meta = null\\n\\n /**\\n * Token#block -> Boolean\\n *\\n * True for block-level tokens, false for inline tokens.\\n * Used in renderer to calculate line breaks\\n **/\\n this.block = false\\n\\n /**\\n * Token#hidden -> Boolean\\n *\\n * If it's true, ignore this element when rendering. Used for tight lists\\n * to hide paragraphs.\\n **/\\n this.hidden = false\\n}\\n\\n/**\\n * Token.attrIndex(name) -> Number\\n *\\n * Search attribute index by name.\\n **/\\nToken.prototype.attrIndex = function attrIndex (name) {\\n if (!this.attrs) { return -1 }\\n\\n const attrs = this.attrs\\n\\n for (let i = 0, len = attrs.length; i < len; i++) {\\n if (attrs[i][0] === name) { return i }\\n }\\n return -1\\n}\\n\\n/**\\n * Token.attrPush(attrData)\\n *\\n * Add `[ name, value ]` attribute to list. Init attrs if necessary\\n **/\\nToken.prototype.attrPush = function attrPush (attrData) {\\n if (this.attrs) {\\n this.attrs.push(attrData)\\n } else {\\n this.attrs = [attrData]\\n }\\n}\\n\\n/**\\n * Token.attrSet(name, value)\\n *\\n * Set `name` attribute to `value`. Override old value if exists.\\n **/\\nToken.prototype.attrSet = function attrSet (name, value) {\\n const idx = this.attrIndex(name)\\n const attrData = [name, value]\\n\\n if (idx < 0) {\\n this.attrPush(attrData)\\n } else {\\n this.attrs[idx] = attrData\\n }\\n}\\n\\n/**\\n * Token.attrGet(name)\\n *\\n * Get the value of attribute `name`, or null if it does not exist.\\n **/\\nToken.prototype.attrGet = function attrGet (name) {\\n const idx = this.attrIndex(name)\\n let value = null\\n if (idx >= 0) {\\n value = this.attrs[idx][1]\\n }\\n return value\\n}\\n\\n/**\\n * Token.attrJoin(name, value)\\n *\\n * Join value to existing attribute via space. Or create new attribute if not\\n * exists. Useful to operate with token classes.\\n **/\\nToken.prototype.attrJoin = function attrJoin (name, value) {\\n const idx = this.attrIndex(name)\\n\\n if (idx < 0) {\\n this.attrPush([name, value])\\n } else {\\n this.attrs[idx][1] = this.attrs[idx][1] + ' ' + value\\n }\\n}\\n\\nexport default Token\\n\",\"// Core state object\\n//\\n\\nimport Token from '../token.mjs'\\n\\nfunction StateCore (src, md, env) {\\n this.src = src\\n this.env = env\\n this.tokens = []\\n this.inlineMode = false\\n this.md = md // link to parser instance\\n}\\n\\n// re-export Token class to use in core rules\\nStateCore.prototype.Token = Token\\n\\nexport default StateCore\\n\",\"// Normalize input string\\n\\n// https://spec.commonmark.org/0.29/#line-ending\\nconst NEWLINES_RE = /\\\\r\\\\n?|\\\\n/g\\nconst NULL_RE = /\\\\0/g\\n\\nexport default function normalize (state) {\\n let str\\n\\n // Normalize newlines\\n str = state.src.replace(NEWLINES_RE, '\\\\n')\\n\\n // Replace NULL characters\\n str = str.replace(NULL_RE, '\\\\uFFFD')\\n\\n state.src = str\\n}\\n\",\"export default function block (state) {\\n let token\\n\\n if (state.inlineMode) {\\n token = new state.Token('inline', '', 0)\\n token.content = state.src\\n token.map = [0, 1]\\n token.children = []\\n state.tokens.push(token)\\n } else {\\n state.md.block.parse(state.src, state.md, state.env, state.tokens)\\n }\\n}\\n\",\"export default function inline (state) {\\n const tokens = state.tokens\\n\\n // Parse inlines\\n for (let i = 0, l = tokens.length; i < l; i++) {\\n const tok = tokens[i]\\n if (tok.type === 'inline') {\\n state.md.inline.parse(tok.content, state.md, state.env, tok.children)\\n }\\n }\\n}\\n\",\"// Replace link-like texts with link nodes.\\n//\\n// Currently restricted by `md.validateLink()` to http/https/ftp\\n//\\n\\nimport { arrayReplaceAt } from '../common/utils.mjs'\\n\\nfunction isLinkOpen (str) {\\n return /^\\\\s]/i.test(str)\\n}\\nfunction isLinkClose (str) {\\n return /^<\\\\/a\\\\s*>/i.test(str)\\n}\\n\\nexport default function linkify (state) {\\n const blockTokens = state.tokens\\n\\n if (!state.md.options.linkify) { return }\\n\\n for (let j = 0, l = blockTokens.length; j < l; j++) {\\n if (blockTokens[j].type !== 'inline' ||\\n !state.md.linkify.pretest(blockTokens[j].content)) {\\n continue\\n }\\n\\n let tokens = blockTokens[j].children\\n\\n let htmlLinkLevel = 0\\n\\n // We scan from the end, to keep position when new tags added.\\n // Use reversed logic in links start/end match\\n for (let i = tokens.length - 1; i >= 0; i--) {\\n const currentToken = tokens[i]\\n\\n // Skip content of markdown links\\n if (currentToken.type === 'link_close') {\\n i--\\n while (tokens[i].level !== currentToken.level && tokens[i].type !== 'link_open') {\\n i--\\n }\\n continue\\n }\\n\\n // Skip content of html tag links\\n if (currentToken.type === 'html_inline') {\\n if (isLinkOpen(currentToken.content) && htmlLinkLevel > 0) {\\n htmlLinkLevel--\\n }\\n if (isLinkClose(currentToken.content)) {\\n htmlLinkLevel++\\n }\\n }\\n if (htmlLinkLevel > 0) { continue }\\n\\n if (currentToken.type === 'text' && state.md.linkify.test(currentToken.content)) {\\n const text = currentToken.content\\n let links = state.md.linkify.match(text)\\n\\n // Now split string to nodes\\n const nodes = []\\n let level = currentToken.level\\n let lastPos = 0\\n\\n // forbid escape sequence at the start of the string,\\n // this avoids http\\\\://example.com/ from being linkified as\\n // http:
//example.com/\\n if (links.length > 0 &&\\n links[0].index === 0 &&\\n i > 0 &&\\n tokens[i - 1].type === 'text_special') {\\n links = links.slice(1)\\n }\\n\\n for (let ln = 0; ln < links.length; ln++) {\\n const url = links[ln].url\\n const fullUrl = state.md.normalizeLink(url)\\n if (!state.md.validateLink(fullUrl)) { continue }\\n\\n let urlText = links[ln].text\\n\\n // Linkifier might send raw hostnames like \\\"example.com\\\", where url\\n // starts with domain name. So we prepend http:// in those cases,\\n // and remove it afterwards.\\n //\\n if (!links[ln].schema) {\\n urlText = state.md.normalizeLinkText('http://' + urlText).replace(/^http:\\\\/\\\\//, '')\\n } else if (links[ln].schema === 'mailto:' && !/^mailto:/i.test(urlText)) {\\n urlText = state.md.normalizeLinkText('mailto:' + urlText).replace(/^mailto:/, '')\\n } else {\\n urlText = state.md.normalizeLinkText(urlText)\\n }\\n\\n const pos = links[ln].index\\n\\n if (pos > lastPos) {\\n const token = new state.Token('text', '', 0)\\n token.content = text.slice(lastPos, pos)\\n token.level = level\\n nodes.push(token)\\n }\\n\\n const token_o = new state.Token('link_open', 'a', 1)\\n token_o.attrs = [['href', fullUrl]]\\n token_o.level = level++\\n token_o.markup = 'linkify'\\n token_o.info = 'auto'\\n nodes.push(token_o)\\n\\n const token_t = new state.Token('text', '', 0)\\n token_t.content = urlText\\n token_t.level = level\\n nodes.push(token_t)\\n\\n const token_c = new state.Token('link_close', 'a', -1)\\n token_c.level = --level\\n token_c.markup = 'linkify'\\n token_c.info = 'auto'\\n nodes.push(token_c)\\n\\n lastPos = links[ln].lastIndex\\n }\\n if (lastPos < text.length) {\\n const token = new state.Token('text', '', 0)\\n token.content = text.slice(lastPos)\\n token.level = level\\n nodes.push(token)\\n }\\n\\n // replace current node\\n blockTokens[j].children = tokens = arrayReplaceAt(tokens, i, nodes)\\n }\\n }\\n }\\n}\\n\",\"// Simple typographic replacements\\n//\\n// (c) (C) → ©\\n// (tm) (TM) → ™\\n// (r) (R) → ®\\n// +- → ±\\n// ... → … (also ?.... → ?.., !.... → !..)\\n// ???????? → ???, !!!!! → !!!, `,,` → `,`\\n// -- → –, --- → —\\n//\\n\\n// TODO:\\n// - fractionals 1/2, 1/4, 3/4 -> ½, ¼, ¾\\n// - multiplications 2 x 4 -> 2 × 4\\n\\nconst RARE_RE = /\\\\+-|\\\\.\\\\.|\\\\?\\\\?\\\\?\\\\?|!!!!|,,|--/\\n\\n// Workaround for phantomjs - need regex without /g flag,\\n// or root check will fail every second time\\nconst SCOPED_ABBR_TEST_RE = /\\\\((c|tm|r)\\\\)/i\\n\\nconst SCOPED_ABBR_RE = /\\\\((c|tm|r)\\\\)/ig\\nconst SCOPED_ABBR = {\\n c: '©',\\n r: '®',\\n tm: '™'\\n}\\n\\nfunction replaceFn (match, name) {\\n return SCOPED_ABBR[name.toLowerCase()]\\n}\\n\\nfunction replace_scoped (inlineTokens) {\\n let inside_autolink = 0\\n\\n for (let i = inlineTokens.length - 1; i >= 0; i--) {\\n const token = inlineTokens[i]\\n\\n if (token.type === 'text' && !inside_autolink) {\\n token.content = token.content.replace(SCOPED_ABBR_RE, replaceFn)\\n }\\n\\n if (token.type === 'link_open' && token.info === 'auto') {\\n inside_autolink--\\n }\\n\\n if (token.type === 'link_close' && token.info === 'auto') {\\n inside_autolink++\\n }\\n }\\n}\\n\\nfunction replace_rare (inlineTokens) {\\n let inside_autolink = 0\\n\\n for (let i = inlineTokens.length - 1; i >= 0; i--) {\\n const token = inlineTokens[i]\\n\\n if (token.type === 'text' && !inside_autolink) {\\n if (RARE_RE.test(token.content)) {\\n token.content = token.content\\n .replace(/\\\\+-/g, '±')\\n // .., ..., ....... -> …\\n // but ?..... & !..... -> ?.. & !..\\n .replace(/\\\\.{2,}/g, '…').replace(/([?!])…/g, '$1..')\\n .replace(/([?!]){4,}/g, '$1$1$1').replace(/,{2,}/g, ',')\\n // em-dash\\n .replace(/(^|[^-])---(?=[^-]|$)/mg, '$1\\\\u2014')\\n // en-dash\\n .replace(/(^|\\\\s)--(?=\\\\s|$)/mg, '$1\\\\u2013')\\n .replace(/(^|[^-\\\\s])--(?=[^-\\\\s]|$)/mg, '$1\\\\u2013')\\n }\\n }\\n\\n if (token.type === 'link_open' && token.info === 'auto') {\\n inside_autolink--\\n }\\n\\n if (token.type === 'link_close' && token.info === 'auto') {\\n inside_autolink++\\n }\\n }\\n}\\n\\nexport default function replace (state) {\\n let blkIdx\\n\\n if (!state.md.options.typographer) { return }\\n\\n for (blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) {\\n if (state.tokens[blkIdx].type !== 'inline') { continue }\\n\\n if (SCOPED_ABBR_TEST_RE.test(state.tokens[blkIdx].content)) {\\n replace_scoped(state.tokens[blkIdx].children)\\n }\\n\\n if (RARE_RE.test(state.tokens[blkIdx].content)) {\\n replace_rare(state.tokens[blkIdx].children)\\n }\\n }\\n}\\n\",\"// Convert straight quotation marks to typographic ones\\n//\\n\\nimport { isWhiteSpace, isPunctChar, isMdAsciiPunct } from '../common/utils.mjs'\\n\\nconst QUOTE_TEST_RE = /['\\\"]/\\nconst QUOTE_RE = /['\\\"]/g\\nconst APOSTROPHE = '\\\\u2019' /* ’ */\\n\\nfunction replaceAt (str, index, ch) {\\n return str.slice(0, index) + ch + str.slice(index + 1)\\n}\\n\\nfunction process_inlines (tokens, state) {\\n let j\\n\\n const stack = []\\n\\n for (let i = 0; i < tokens.length; i++) {\\n const token = tokens[i]\\n\\n const thisLevel = tokens[i].level\\n\\n for (j = stack.length - 1; j >= 0; j--) {\\n if (stack[j].level <= thisLevel) { break }\\n }\\n stack.length = j + 1\\n\\n if (token.type !== 'text') { continue }\\n\\n let text = token.content\\n let pos = 0\\n let max = text.length\\n\\n /* eslint no-labels:0,block-scoped-var:0 */\\n OUTER:\\n while (pos < max) {\\n QUOTE_RE.lastIndex = pos\\n const t = QUOTE_RE.exec(text)\\n if (!t) { break }\\n\\n let canOpen = true\\n let canClose = true\\n pos = t.index + 1\\n const isSingle = (t[0] === \\\"'\\\")\\n\\n // Find previous character,\\n // default to space if it's the beginning of the line\\n //\\n let lastChar = 0x20\\n\\n if (t.index - 1 >= 0) {\\n lastChar = text.charCodeAt(t.index - 1)\\n } else {\\n for (j = i - 1; j >= 0; j--) {\\n if (tokens[j].type === 'softbreak' || tokens[j].type === 'hardbreak') break // lastChar defaults to 0x20\\n if (!tokens[j].content) continue // should skip all tokens except 'text', 'html_inline' or 'code_inline'\\n\\n lastChar = tokens[j].content.charCodeAt(tokens[j].content.length - 1)\\n break\\n }\\n }\\n\\n // Find next character,\\n // default to space if it's the end of the line\\n //\\n let nextChar = 0x20\\n\\n if (pos < max) {\\n nextChar = text.charCodeAt(pos)\\n } else {\\n for (j = i + 1; j < tokens.length; j++) {\\n if (tokens[j].type === 'softbreak' || tokens[j].type === 'hardbreak') break // nextChar defaults to 0x20\\n if (!tokens[j].content) continue // should skip all tokens except 'text', 'html_inline' or 'code_inline'\\n\\n nextChar = tokens[j].content.charCodeAt(0)\\n break\\n }\\n }\\n\\n const isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar))\\n const isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar))\\n\\n const isLastWhiteSpace = isWhiteSpace(lastChar)\\n const isNextWhiteSpace = isWhiteSpace(nextChar)\\n\\n if (isNextWhiteSpace) {\\n canOpen = false\\n } else if (isNextPunctChar) {\\n if (!(isLastWhiteSpace || isLastPunctChar)) {\\n canOpen = false\\n }\\n }\\n\\n if (isLastWhiteSpace) {\\n canClose = false\\n } else if (isLastPunctChar) {\\n if (!(isNextWhiteSpace || isNextPunctChar)) {\\n canClose = false\\n }\\n }\\n\\n if (nextChar === 0x22 /* \\\" */ && t[0] === '\\\"') {\\n if (lastChar >= 0x30 /* 0 */ && lastChar <= 0x39 /* 9 */) {\\n // special case: 1\\\"\\\" - count first quote as an inch\\n canClose = canOpen = false\\n }\\n }\\n\\n if (canOpen && canClose) {\\n // Replace quotes in the middle of punctuation sequence, but not\\n // in the middle of the words, i.e.:\\n //\\n // 1. foo \\\" bar \\\" baz - not replaced\\n // 2. foo-\\\"-bar-\\\"-baz - replaced\\n // 3. foo\\\"bar\\\"baz - not replaced\\n //\\n canOpen = isLastPunctChar\\n canClose = isNextPunctChar\\n }\\n\\n if (!canOpen && !canClose) {\\n // middle of word\\n if (isSingle) {\\n token.content = replaceAt(token.content, t.index, APOSTROPHE)\\n }\\n continue\\n }\\n\\n if (canClose) {\\n // this could be a closing quote, rewind the stack to get a match\\n for (j = stack.length - 1; j >= 0; j--) {\\n let item = stack[j]\\n if (stack[j].level < thisLevel) { break }\\n if (item.single === isSingle && stack[j].level === thisLevel) {\\n item = stack[j]\\n\\n let openQuote\\n let closeQuote\\n if (isSingle) {\\n openQuote = state.md.options.quotes[2]\\n closeQuote = state.md.options.quotes[3]\\n } else {\\n openQuote = state.md.options.quotes[0]\\n closeQuote = state.md.options.quotes[1]\\n }\\n\\n // replace token.content *before* tokens[item.token].content,\\n // because, if they are pointing at the same token, replaceAt\\n // could mess up indices when quote length != 1\\n token.content = replaceAt(token.content, t.index, closeQuote)\\n tokens[item.token].content = replaceAt(\\n tokens[item.token].content, item.pos, openQuote)\\n\\n pos += closeQuote.length - 1\\n if (item.token === i) { pos += openQuote.length - 1 }\\n\\n text = token.content\\n max = text.length\\n\\n stack.length = j\\n continue OUTER\\n }\\n }\\n }\\n\\n if (canOpen) {\\n stack.push({\\n token: i,\\n pos: t.index,\\n single: isSingle,\\n level: thisLevel\\n })\\n } else if (canClose && isSingle) {\\n token.content = replaceAt(token.content, t.index, APOSTROPHE)\\n }\\n }\\n }\\n}\\n\\nexport default function smartquotes (state) {\\n /* eslint max-depth:0 */\\n if (!state.md.options.typographer) { return }\\n\\n for (let blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) {\\n if (state.tokens[blkIdx].type !== 'inline' ||\\n !QUOTE_TEST_RE.test(state.tokens[blkIdx].content)) {\\n continue\\n }\\n\\n process_inlines(state.tokens[blkIdx].children, state)\\n }\\n}\\n\",\"// Join raw text tokens with the rest of the text\\n//\\n// This is set as a separate rule to provide an opportunity for plugins\\n// to run text replacements after text join, but before escape join.\\n//\\n// For example, `\\\\:)` shouldn't be replaced with an emoji.\\n//\\n\\nexport default function text_join (state) {\\n let curr, last\\n const blockTokens = state.tokens\\n const l = blockTokens.length\\n\\n for (let j = 0; j < l; j++) {\\n if (blockTokens[j].type !== 'inline') continue\\n\\n const tokens = blockTokens[j].children\\n const max = tokens.length\\n\\n for (curr = 0; curr < max; curr++) {\\n if (tokens[curr].type === 'text_special') {\\n tokens[curr].type = 'text'\\n }\\n }\\n\\n for (curr = last = 0; curr < max; curr++) {\\n if (tokens[curr].type === 'text' &&\\n curr + 1 < max &&\\n tokens[curr + 1].type === 'text') {\\n // collapse two adjacent text nodes\\n tokens[curr + 1].content = tokens[curr].content + tokens[curr + 1].content\\n } else {\\n if (curr !== last) { tokens[last] = tokens[curr] }\\n\\n last++\\n }\\n }\\n\\n if (curr !== last) {\\n tokens.length = last\\n }\\n }\\n}\\n\",\"/** internal\\n * class Core\\n *\\n * Top-level rules executor. Glues block/inline parsers and does intermediate\\n * transformations.\\n **/\\n\\nimport Ruler from './ruler.mjs'\\nimport StateCore from './rules_core/state_core.mjs'\\n\\nimport r_normalize from './rules_core/normalize.mjs'\\nimport r_block from './rules_core/block.mjs'\\nimport r_inline from './rules_core/inline.mjs'\\nimport r_linkify from './rules_core/linkify.mjs'\\nimport r_replacements from './rules_core/replacements.mjs'\\nimport r_smartquotes from './rules_core/smartquotes.mjs'\\nimport r_text_join from './rules_core/text_join.mjs'\\n\\nconst _rules = [\\n ['normalize', r_normalize],\\n ['block', r_block],\\n ['inline', r_inline],\\n ['linkify', r_linkify],\\n ['replacements', r_replacements],\\n ['smartquotes', r_smartquotes],\\n // `text_join` finds `text_special` tokens (for escape sequences)\\n // and joins them with the rest of the text\\n ['text_join', r_text_join]\\n]\\n\\n/**\\n * new Core()\\n **/\\nfunction Core () {\\n /**\\n * Core#ruler -> Ruler\\n *\\n * [[Ruler]] instance. Keep configuration of core rules.\\n **/\\n this.ruler = new Ruler()\\n\\n for (let i = 0; i < _rules.length; i++) {\\n this.ruler.push(_rules[i][0], _rules[i][1])\\n }\\n}\\n\\n/**\\n * Core.process(state)\\n *\\n * Executes core chain rules.\\n **/\\nCore.prototype.process = function (state) {\\n const rules = this.ruler.getRules('')\\n\\n for (let i = 0, l = rules.length; i < l; i++) {\\n rules[i](state)\\n }\\n}\\n\\nCore.prototype.State = StateCore\\n\\nexport default Core\\n\",\"// Parser state class\\n\\nimport Token from '../token.mjs'\\nimport { isSpace } from '../common/utils.mjs'\\n\\nfunction StateBlock (src, md, env, tokens) {\\n this.src = src\\n\\n // link to parser instance\\n this.md = md\\n\\n this.env = env\\n\\n //\\n // Internal state vartiables\\n //\\n\\n this.tokens = tokens\\n\\n this.bMarks = [] // line begin offsets for fast jumps\\n this.eMarks = [] // line end offsets for fast jumps\\n this.tShift = [] // offsets of the first non-space characters (tabs not expanded)\\n this.sCount = [] // indents for each line (tabs expanded)\\n\\n // An amount of virtual spaces (tabs expanded) between beginning\\n // of each line (bMarks) and real beginning of that line.\\n //\\n // It exists only as a hack because blockquotes override bMarks\\n // losing information in the process.\\n //\\n // It's used only when expanding tabs, you can think about it as\\n // an initial tab length, e.g. bsCount=21 applied to string `\\\\t123`\\n // means first tab should be expanded to 4-21%4 === 3 spaces.\\n //\\n this.bsCount = []\\n\\n // block parser variables\\n\\n // required block content indent (for example, if we are\\n // inside a list, it would be positioned after list marker)\\n this.blkIndent = 0\\n this.line = 0 // line index in src\\n this.lineMax = 0 // lines count\\n this.tight = false // loose/tight mode for lists\\n this.ddIndent = -1 // indent of the current dd block (-1 if there isn't any)\\n this.listIndent = -1 // indent of the current list block (-1 if there isn't any)\\n\\n // can be 'blockquote', 'list', 'root', 'paragraph' or 'reference'\\n // used in lists to determine if they interrupt a paragraph\\n this.parentType = 'root'\\n\\n this.level = 0\\n\\n // Create caches\\n // Generate markers.\\n const s = this.src\\n\\n for (let start = 0, pos = 0, indent = 0, offset = 0, len = s.length, indent_found = false; pos < len; pos++) {\\n const ch = s.charCodeAt(pos)\\n\\n if (!indent_found) {\\n if (isSpace(ch)) {\\n indent++\\n\\n if (ch === 0x09) {\\n offset += 4 - offset % 4\\n } else {\\n offset++\\n }\\n continue\\n } else {\\n indent_found = true\\n }\\n }\\n\\n if (ch === 0x0A || pos === len - 1) {\\n if (ch !== 0x0A) { pos++ }\\n this.bMarks.push(start)\\n this.eMarks.push(pos)\\n this.tShift.push(indent)\\n this.sCount.push(offset)\\n this.bsCount.push(0)\\n\\n indent_found = false\\n indent = 0\\n offset = 0\\n start = pos + 1\\n }\\n }\\n\\n // Push fake entry to simplify cache bounds checks\\n this.bMarks.push(s.length)\\n this.eMarks.push(s.length)\\n this.tShift.push(0)\\n this.sCount.push(0)\\n this.bsCount.push(0)\\n\\n this.lineMax = this.bMarks.length - 1 // don't count last fake line\\n}\\n\\n// Push new token to \\\"stream\\\".\\n//\\nStateBlock.prototype.push = function (type, tag, nesting) {\\n const token = new Token(type, tag, nesting)\\n token.block = true\\n\\n if (nesting < 0) this.level-- // closing tag\\n token.level = this.level\\n if (nesting > 0) this.level++ // opening tag\\n\\n this.tokens.push(token)\\n return token\\n}\\n\\nStateBlock.prototype.isEmpty = function isEmpty (line) {\\n return this.bMarks[line] + this.tShift[line] >= this.eMarks[line]\\n}\\n\\nStateBlock.prototype.skipEmptyLines = function skipEmptyLines (from) {\\n for (let max = this.lineMax; from < max; from++) {\\n if (this.bMarks[from] + this.tShift[from] < this.eMarks[from]) {\\n break\\n }\\n }\\n return from\\n}\\n\\n// Skip spaces from given position.\\nStateBlock.prototype.skipSpaces = function skipSpaces (pos) {\\n for (let max = this.src.length; pos < max; pos++) {\\n const ch = this.src.charCodeAt(pos)\\n if (!isSpace(ch)) { break }\\n }\\n return pos\\n}\\n\\n// Skip spaces from given position in reverse.\\nStateBlock.prototype.skipSpacesBack = function skipSpacesBack (pos, min) {\\n if (pos <= min) { return pos }\\n\\n while (pos > min) {\\n if (!isSpace(this.src.charCodeAt(--pos))) { return pos + 1 }\\n }\\n return pos\\n}\\n\\n// Skip char codes from given position\\nStateBlock.prototype.skipChars = function skipChars (pos, code) {\\n for (let max = this.src.length; pos < max; pos++) {\\n if (this.src.charCodeAt(pos) !== code) { break }\\n }\\n return pos\\n}\\n\\n// Skip char codes reverse from given position - 1\\nStateBlock.prototype.skipCharsBack = function skipCharsBack (pos, code, min) {\\n if (pos <= min) { return pos }\\n\\n while (pos > min) {\\n if (code !== this.src.charCodeAt(--pos)) { return pos + 1 }\\n }\\n return pos\\n}\\n\\n// cut lines range from source.\\nStateBlock.prototype.getLines = function getLines (begin, end, indent, keepLastLF) {\\n if (begin >= end) {\\n return ''\\n }\\n\\n const queue = new Array(end - begin)\\n\\n for (let i = 0, line = begin; line < end; line++, i++) {\\n let lineIndent = 0\\n const lineStart = this.bMarks[line]\\n let first = lineStart\\n let last\\n\\n if (line + 1 < end || keepLastLF) {\\n // No need for bounds check because we have fake entry on tail.\\n last = this.eMarks[line] + 1\\n } else {\\n last = this.eMarks[line]\\n }\\n\\n while (first < last && lineIndent < indent) {\\n const ch = this.src.charCodeAt(first)\\n\\n if (isSpace(ch)) {\\n if (ch === 0x09) {\\n lineIndent += 4 - (lineIndent + this.bsCount[line]) % 4\\n } else {\\n lineIndent++\\n }\\n } else if (first - lineStart < this.tShift[line]) {\\n // patched tShift masked characters to look like spaces (blockquotes, list markers)\\n lineIndent++\\n } else {\\n break\\n }\\n\\n first++\\n }\\n\\n if (lineIndent > indent) {\\n // partially expanding tabs in code blocks, e.g '\\\\t\\\\tfoobar'\\n // with indent=2 becomes ' \\\\tfoobar'\\n queue[i] = new Array(lineIndent - indent + 1).join(' ') + this.src.slice(first, last)\\n } else {\\n queue[i] = this.src.slice(first, last)\\n }\\n }\\n\\n return queue.join('')\\n}\\n\\n// re-export Token class to use in block rules\\nStateBlock.prototype.Token = Token\\n\\nexport default StateBlock\\n\",\"// GFM table, https://github.github.com/gfm/#tables-extension-\\n\\nimport { isSpace } from '../common/utils.mjs'\\n\\n// Limit the amount of empty autocompleted cells in a table,\\n// see https://github.com/markdown-it/markdown-it/issues/1000,\\n//\\n// Both pulldown-cmark and commonmark-hs limit the number of cells this way to ~200k.\\n// We set it to 65k, which can expand user input by a factor of x370\\n// (256x256 square is 1.8kB expanded into 650kB).\\nconst MAX_AUTOCOMPLETED_CELLS = 0x10000\\n\\nfunction getLine (state, line) {\\n const pos = state.bMarks[line] + state.tShift[line]\\n const max = state.eMarks[line]\\n\\n return state.src.slice(pos, max)\\n}\\n\\nfunction escapedSplit (str) {\\n const result = []\\n const max = str.length\\n\\n let pos = 0\\n let ch = str.charCodeAt(pos)\\n let isEscaped = false\\n let lastPos = 0\\n let current = ''\\n\\n while (pos < max) {\\n if (ch === 0x7c/* | */) {\\n if (!isEscaped) {\\n // pipe separating cells, '|'\\n result.push(current + str.substring(lastPos, pos))\\n current = ''\\n lastPos = pos + 1\\n } else {\\n // escaped pipe, '\\\\|'\\n current += str.substring(lastPos, pos - 1)\\n lastPos = pos\\n }\\n }\\n\\n isEscaped = (ch === 0x5c/* \\\\ */)\\n pos++\\n\\n ch = str.charCodeAt(pos)\\n }\\n\\n result.push(current + str.substring(lastPos))\\n\\n return result\\n}\\n\\nexport default function table (state, startLine, endLine, silent) {\\n // should have at least two lines\\n if (startLine + 2 > endLine) { return false }\\n\\n let nextLine = startLine + 1\\n\\n if (state.sCount[nextLine] < state.blkIndent) { return false }\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[nextLine] - state.blkIndent >= 4) { return false }\\n\\n // first character of the second line should be '|', '-', ':',\\n // and no other characters are allowed but spaces;\\n // basically, this is the equivalent of /^[-:|][-:|\\\\s]*$/ regexp\\n\\n let pos = state.bMarks[nextLine] + state.tShift[nextLine]\\n if (pos >= state.eMarks[nextLine]) { return false }\\n\\n const firstCh = state.src.charCodeAt(pos++)\\n if (firstCh !== 0x7C/* | */ && firstCh !== 0x2D/* - */ && firstCh !== 0x3A/* : */) { return false }\\n\\n if (pos >= state.eMarks[nextLine]) { return false }\\n\\n const secondCh = state.src.charCodeAt(pos++)\\n if (secondCh !== 0x7C/* | */ && secondCh !== 0x2D/* - */ && secondCh !== 0x3A/* : */ && !isSpace(secondCh)) {\\n return false\\n }\\n\\n // if first character is '-', then second character must not be a space\\n // (due to parsing ambiguity with list)\\n if (firstCh === 0x2D/* - */ && isSpace(secondCh)) { return false }\\n\\n while (pos < state.eMarks[nextLine]) {\\n const ch = state.src.charCodeAt(pos)\\n\\n if (ch !== 0x7C/* | */ && ch !== 0x2D/* - */ && ch !== 0x3A/* : */ && !isSpace(ch)) { return false }\\n\\n pos++\\n }\\n\\n let lineText = getLine(state, startLine + 1)\\n let columns = lineText.split('|')\\n const aligns = []\\n for (let i = 0; i < columns.length; i++) {\\n const t = columns[i].trim()\\n if (!t) {\\n // allow empty columns before and after table, but not in between columns;\\n // e.g. allow ` |---| `, disallow ` ---||--- `\\n if (i === 0 || i === columns.length - 1) {\\n continue\\n } else {\\n return false\\n }\\n }\\n\\n if (!/^:?-+:?$/.test(t)) { return false }\\n if (t.charCodeAt(t.length - 1) === 0x3A/* : */) {\\n aligns.push(t.charCodeAt(0) === 0x3A/* : */ ? 'center' : 'right')\\n } else if (t.charCodeAt(0) === 0x3A/* : */) {\\n aligns.push('left')\\n } else {\\n aligns.push('')\\n }\\n }\\n\\n lineText = getLine(state, startLine).trim()\\n if (lineText.indexOf('|') === -1) { return false }\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n columns = escapedSplit(lineText)\\n if (columns.length && columns[0] === '') columns.shift()\\n if (columns.length && columns[columns.length - 1] === '') columns.pop()\\n\\n // header row will define an amount of columns in the entire table,\\n // and align row should be exactly the same (the rest of the rows can differ)\\n const columnCount = columns.length\\n if (columnCount === 0 || columnCount !== aligns.length) { return false }\\n\\n if (silent) { return true }\\n\\n const oldParentType = state.parentType\\n state.parentType = 'table'\\n\\n // use 'blockquote' lists for termination because it's\\n // the most similar to tables\\n const terminatorRules = state.md.block.ruler.getRules('blockquote')\\n\\n const token_to = state.push('table_open', 'table', 1)\\n const tableLines = [startLine, 0]\\n token_to.map = tableLines\\n\\n const token_tho = state.push('thead_open', 'thead', 1)\\n token_tho.map = [startLine, startLine + 1]\\n\\n const token_htro = state.push('tr_open', 'tr', 1)\\n token_htro.map = [startLine, startLine + 1]\\n\\n for (let i = 0; i < columns.length; i++) {\\n const token_ho = state.push('th_open', 'th', 1)\\n if (aligns[i]) {\\n token_ho.attrs = [['style', 'text-align:' + aligns[i]]]\\n }\\n\\n const token_il = state.push('inline', '', 0)\\n token_il.content = columns[i].trim()\\n token_il.children = []\\n\\n state.push('th_close', 'th', -1)\\n }\\n\\n state.push('tr_close', 'tr', -1)\\n state.push('thead_close', 'thead', -1)\\n\\n let tbodyLines\\n let autocompletedCells = 0\\n\\n for (nextLine = startLine + 2; nextLine < endLine; nextLine++) {\\n if (state.sCount[nextLine] < state.blkIndent) { break }\\n\\n let terminate = false\\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\\n if (terminatorRules[i](state, nextLine, endLine, true)) {\\n terminate = true\\n break\\n }\\n }\\n\\n if (terminate) { break }\\n lineText = getLine(state, nextLine).trim()\\n if (!lineText) { break }\\n if (state.sCount[nextLine] - state.blkIndent >= 4) { break }\\n columns = escapedSplit(lineText)\\n if (columns.length && columns[0] === '') columns.shift()\\n if (columns.length && columns[columns.length - 1] === '') columns.pop()\\n\\n // note: autocomplete count can be negative if user specifies more columns than header,\\n // but that does not affect intended use (which is limiting expansion)\\n autocompletedCells += columnCount - columns.length\\n if (autocompletedCells > MAX_AUTOCOMPLETED_CELLS) { break }\\n\\n if (nextLine === startLine + 2) {\\n const token_tbo = state.push('tbody_open', 'tbody', 1)\\n token_tbo.map = tbodyLines = [startLine + 2, 0]\\n }\\n\\n const token_tro = state.push('tr_open', 'tr', 1)\\n token_tro.map = [nextLine, nextLine + 1]\\n\\n for (let i = 0; i < columnCount; i++) {\\n const token_tdo = state.push('td_open', 'td', 1)\\n if (aligns[i]) {\\n token_tdo.attrs = [['style', 'text-align:' + aligns[i]]]\\n }\\n\\n const token_il = state.push('inline', '', 0)\\n token_il.content = columns[i] ? columns[i].trim() : ''\\n token_il.children = []\\n\\n state.push('td_close', 'td', -1)\\n }\\n state.push('tr_close', 'tr', -1)\\n }\\n\\n if (tbodyLines) {\\n state.push('tbody_close', 'tbody', -1)\\n tbodyLines[1] = nextLine\\n }\\n\\n state.push('table_close', 'table', -1)\\n tableLines[1] = nextLine\\n\\n state.parentType = oldParentType\\n state.line = nextLine\\n return true\\n}\\n\",\"// Code block (4 spaces padded)\\n\\nexport default function code (state, startLine, endLine/*, silent */) {\\n if (state.sCount[startLine] - state.blkIndent < 4) { return false }\\n\\n let nextLine = startLine + 1\\n let last = nextLine\\n\\n while (nextLine < endLine) {\\n if (state.isEmpty(nextLine)) {\\n nextLine++\\n continue\\n }\\n\\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\\n nextLine++\\n last = nextLine\\n continue\\n }\\n break\\n }\\n\\n state.line = last\\n\\n const token = state.push('code_block', 'code', 0)\\n token.content = state.getLines(startLine, last, 4 + state.blkIndent, false) + '\\\\n'\\n token.map = [startLine, state.line]\\n\\n return true\\n}\\n\",\"// fences (``` lang, ~~~ lang)\\n\\nexport default function fence (state, startLine, endLine, silent) {\\n let pos = state.bMarks[startLine] + state.tShift[startLine]\\n let max = state.eMarks[startLine]\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n\\n if (pos + 3 > max) { return false }\\n\\n const marker = state.src.charCodeAt(pos)\\n\\n if (marker !== 0x7E/* ~ */ && marker !== 0x60 /* ` */) {\\n return false\\n }\\n\\n // scan marker length\\n let mem = pos\\n pos = state.skipChars(pos, marker)\\n\\n let len = pos - mem\\n\\n if (len < 3) { return false }\\n\\n const markup = state.src.slice(mem, pos)\\n const params = state.src.slice(pos, max)\\n\\n if (marker === 0x60 /* ` */) {\\n if (params.indexOf(String.fromCharCode(marker)) >= 0) {\\n return false\\n }\\n }\\n\\n // Since start is found, we can report success here in validation mode\\n if (silent) { return true }\\n\\n // search end of block\\n let nextLine = startLine\\n let haveEndMarker = false\\n\\n for (;;) {\\n nextLine++\\n if (nextLine >= endLine) {\\n // unclosed block should be autoclosed by end of document.\\n // also block seems to be autoclosed by end of parent\\n break\\n }\\n\\n pos = mem = state.bMarks[nextLine] + state.tShift[nextLine]\\n max = state.eMarks[nextLine]\\n\\n if (pos < max && state.sCount[nextLine] < state.blkIndent) {\\n // non-empty line with negative indent should stop the list:\\n // - ```\\n // test\\n break\\n }\\n\\n if (state.src.charCodeAt(pos) !== marker) { continue }\\n\\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\\n // closing fence should be indented less than 4 spaces\\n continue\\n }\\n\\n pos = state.skipChars(pos, marker)\\n\\n // closing code fence must be at least as long as the opening one\\n if (pos - mem < len) { continue }\\n\\n // make sure tail has spaces only\\n pos = state.skipSpaces(pos)\\n\\n if (pos < max) { continue }\\n\\n haveEndMarker = true\\n // found!\\n break\\n }\\n\\n // If a fence has heading spaces, they should be removed from its inner block\\n len = state.sCount[startLine]\\n\\n state.line = nextLine + (haveEndMarker ? 1 : 0)\\n\\n const token = state.push('fence', 'code', 0)\\n token.info = params\\n token.content = state.getLines(startLine + 1, nextLine, len, true)\\n token.markup = markup\\n token.map = [startLine, state.line]\\n\\n return true\\n}\\n\",\"// Block quotes\\n\\nimport { isSpace } from '../common/utils.mjs'\\n\\nexport default function blockquote (state, startLine, endLine, silent) {\\n let pos = state.bMarks[startLine] + state.tShift[startLine]\\n let max = state.eMarks[startLine]\\n\\n const oldLineMax = state.lineMax\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n\\n // check the block quote marker\\n if (state.src.charCodeAt(pos) !== 0x3E/* > */) { return false }\\n\\n // we know that it's going to be a valid blockquote,\\n // so no point trying to find the end of it in silent mode\\n if (silent) { return true }\\n\\n const oldBMarks = []\\n const oldBSCount = []\\n const oldSCount = []\\n const oldTShift = []\\n\\n const terminatorRules = state.md.block.ruler.getRules('blockquote')\\n\\n const oldParentType = state.parentType\\n state.parentType = 'blockquote'\\n let lastLineEmpty = false\\n let nextLine\\n\\n // Search the end of the block\\n //\\n // Block ends with either:\\n // 1. an empty line outside:\\n // ```\\n // > test\\n //\\n // ```\\n // 2. an empty line inside:\\n // ```\\n // >\\n // test\\n // ```\\n // 3. another tag:\\n // ```\\n // > test\\n // - - -\\n // ```\\n for (nextLine = startLine; nextLine < endLine; nextLine++) {\\n // check if it's outdented, i.e. it's inside list item and indented\\n // less than said list item:\\n //\\n // ```\\n // 1. anything\\n // > current blockquote\\n // 2. checking this line\\n // ```\\n const isOutdented = state.sCount[nextLine] < state.blkIndent\\n\\n pos = state.bMarks[nextLine] + state.tShift[nextLine]\\n max = state.eMarks[nextLine]\\n\\n if (pos >= max) {\\n // Case 1: line is not inside the blockquote, and this line is empty.\\n break\\n }\\n\\n if (state.src.charCodeAt(pos++) === 0x3E/* > */ && !isOutdented) {\\n // This line is inside the blockquote.\\n\\n // set offset past spaces and \\\">\\\"\\n let initial = state.sCount[nextLine] + 1\\n let spaceAfterMarker\\n let adjustTab\\n\\n // skip one optional space after '>'\\n if (state.src.charCodeAt(pos) === 0x20 /* space */) {\\n // ' > test '\\n // ^ -- position start of line here:\\n pos++\\n initial++\\n adjustTab = false\\n spaceAfterMarker = true\\n } else if (state.src.charCodeAt(pos) === 0x09 /* tab */) {\\n spaceAfterMarker = true\\n\\n if ((state.bsCount[nextLine] + initial) % 4 === 3) {\\n // ' >\\\\t test '\\n // ^ -- position start of line here (tab has width===1)\\n pos++\\n initial++\\n adjustTab = false\\n } else {\\n // ' >\\\\t test '\\n // ^ -- position start of line here + shift bsCount slightly\\n // to make extra space appear\\n adjustTab = true\\n }\\n } else {\\n spaceAfterMarker = false\\n }\\n\\n let offset = initial\\n oldBMarks.push(state.bMarks[nextLine])\\n state.bMarks[nextLine] = pos\\n\\n while (pos < max) {\\n const ch = state.src.charCodeAt(pos)\\n\\n if (isSpace(ch)) {\\n if (ch === 0x09) {\\n offset += 4 - (offset + state.bsCount[nextLine] + (adjustTab ? 1 : 0)) % 4\\n } else {\\n offset++\\n }\\n } else {\\n break\\n }\\n\\n pos++\\n }\\n\\n lastLineEmpty = pos >= max\\n\\n oldBSCount.push(state.bsCount[nextLine])\\n state.bsCount[nextLine] = state.sCount[nextLine] + 1 + (spaceAfterMarker ? 1 : 0)\\n\\n oldSCount.push(state.sCount[nextLine])\\n state.sCount[nextLine] = offset - initial\\n\\n oldTShift.push(state.tShift[nextLine])\\n state.tShift[nextLine] = pos - state.bMarks[nextLine]\\n continue\\n }\\n\\n // Case 2: line is not inside the blockquote, and the last line was empty.\\n if (lastLineEmpty) { break }\\n\\n // Case 3: another tag found.\\n let terminate = false\\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\\n if (terminatorRules[i](state, nextLine, endLine, true)) {\\n terminate = true\\n break\\n }\\n }\\n\\n if (terminate) {\\n // Quirk to enforce \\\"hard termination mode\\\" for paragraphs;\\n // normally if you call `tokenize(state, startLine, nextLine)`,\\n // paragraphs will look below nextLine for paragraph continuation,\\n // but if blockquote is terminated by another tag, they shouldn't\\n state.lineMax = nextLine\\n\\n if (state.blkIndent !== 0) {\\n // state.blkIndent was non-zero, we now set it to zero,\\n // so we need to re-calculate all offsets to appear as\\n // if indent wasn't changed\\n oldBMarks.push(state.bMarks[nextLine])\\n oldBSCount.push(state.bsCount[nextLine])\\n oldTShift.push(state.tShift[nextLine])\\n oldSCount.push(state.sCount[nextLine])\\n state.sCount[nextLine] -= state.blkIndent\\n }\\n\\n break\\n }\\n\\n oldBMarks.push(state.bMarks[nextLine])\\n oldBSCount.push(state.bsCount[nextLine])\\n oldTShift.push(state.tShift[nextLine])\\n oldSCount.push(state.sCount[nextLine])\\n\\n // A negative indentation means that this is a paragraph continuation\\n //\\n state.sCount[nextLine] = -1\\n }\\n\\n const oldIndent = state.blkIndent\\n state.blkIndent = 0\\n\\n const token_o = state.push('blockquote_open', 'blockquote', 1)\\n token_o.markup = '>'\\n const lines = [startLine, 0]\\n token_o.map = lines\\n\\n state.md.block.tokenize(state, startLine, nextLine)\\n\\n const token_c = state.push('blockquote_close', 'blockquote', -1)\\n token_c.markup = '>'\\n\\n state.lineMax = oldLineMax\\n state.parentType = oldParentType\\n lines[1] = state.line\\n\\n // Restore original tShift; this might not be necessary since the parser\\n // has already been here, but just to make sure we can do that.\\n for (let i = 0; i < oldTShift.length; i++) {\\n state.bMarks[i + startLine] = oldBMarks[i]\\n state.tShift[i + startLine] = oldTShift[i]\\n state.sCount[i + startLine] = oldSCount[i]\\n state.bsCount[i + startLine] = oldBSCount[i]\\n }\\n state.blkIndent = oldIndent\\n\\n return true\\n}\\n\",\"// Horizontal rule\\n\\nimport { isSpace } from '../common/utils.mjs'\\n\\nexport default function hr (state, startLine, endLine, silent) {\\n const max = state.eMarks[startLine]\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n\\n let pos = state.bMarks[startLine] + state.tShift[startLine]\\n const marker = state.src.charCodeAt(pos++)\\n\\n // Check hr marker\\n if (marker !== 0x2A/* * */ &&\\n marker !== 0x2D/* - */ &&\\n marker !== 0x5F/* _ */) {\\n return false\\n }\\n\\n // markers can be mixed with spaces, but there should be at least 3 of them\\n\\n let cnt = 1\\n while (pos < max) {\\n const ch = state.src.charCodeAt(pos++)\\n if (ch !== marker && !isSpace(ch)) { return false }\\n if (ch === marker) { cnt++ }\\n }\\n\\n if (cnt < 3) { return false }\\n\\n if (silent) { return true }\\n\\n state.line = startLine + 1\\n\\n const token = state.push('hr', 'hr', 0)\\n token.map = [startLine, state.line]\\n token.markup = Array(cnt + 1).join(String.fromCharCode(marker))\\n\\n return true\\n}\\n\",\"// Lists\\n\\nimport { isSpace } from '../common/utils.mjs'\\n\\n// Search `[-+*][\\\\n ]`, returns next pos after marker on success\\n// or -1 on fail.\\nfunction skipBulletListMarker (state, startLine) {\\n const max = state.eMarks[startLine]\\n let pos = state.bMarks[startLine] + state.tShift[startLine]\\n\\n const marker = state.src.charCodeAt(pos++)\\n // Check bullet\\n if (marker !== 0x2A/* * */ &&\\n marker !== 0x2D/* - */ &&\\n marker !== 0x2B/* + */) {\\n return -1\\n }\\n\\n if (pos < max) {\\n const ch = state.src.charCodeAt(pos)\\n\\n if (!isSpace(ch)) {\\n // \\\" -test \\\" - is not a list item\\n return -1\\n }\\n }\\n\\n return pos\\n}\\n\\n// Search `\\\\d+[.)][\\\\n ]`, returns next pos after marker on success\\n// or -1 on fail.\\nfunction skipOrderedListMarker (state, startLine) {\\n const start = state.bMarks[startLine] + state.tShift[startLine]\\n const max = state.eMarks[startLine]\\n let pos = start\\n\\n // List marker should have at least 2 chars (digit + dot)\\n if (pos + 1 >= max) { return -1 }\\n\\n let ch = state.src.charCodeAt(pos++)\\n\\n if (ch < 0x30/* 0 */ || ch > 0x39/* 9 */) { return -1 }\\n\\n for (;;) {\\n // EOL -> fail\\n if (pos >= max) { return -1 }\\n\\n ch = state.src.charCodeAt(pos++)\\n\\n if (ch >= 0x30/* 0 */ && ch <= 0x39/* 9 */) {\\n // List marker should have no more than 9 digits\\n // (prevents integer overflow in browsers)\\n if (pos - start >= 10) { return -1 }\\n\\n continue\\n }\\n\\n // found valid marker\\n if (ch === 0x29/* ) */ || ch === 0x2e/* . */) {\\n break\\n }\\n\\n return -1\\n }\\n\\n if (pos < max) {\\n ch = state.src.charCodeAt(pos)\\n\\n if (!isSpace(ch)) {\\n // \\\" 1.test \\\" - is not a list item\\n return -1\\n }\\n }\\n return pos\\n}\\n\\nfunction markTightParagraphs (state, idx) {\\n const level = state.level + 2\\n\\n for (let i = idx + 2, l = state.tokens.length - 2; i < l; i++) {\\n if (state.tokens[i].level === level && state.tokens[i].type === 'paragraph_open') {\\n state.tokens[i + 2].hidden = true\\n state.tokens[i].hidden = true\\n i += 2\\n }\\n }\\n}\\n\\nexport default function list (state, startLine, endLine, silent) {\\n let max, pos, start, token\\n let nextLine = startLine\\n let tight = true\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[nextLine] - state.blkIndent >= 4) { return false }\\n\\n // Special case:\\n // - item 1\\n // - item 2\\n // - item 3\\n // - item 4\\n // - this one is a paragraph continuation\\n if (state.listIndent >= 0 &&\\n state.sCount[nextLine] - state.listIndent >= 4 &&\\n state.sCount[nextLine] < state.blkIndent) {\\n return false\\n }\\n\\n let isTerminatingParagraph = false\\n\\n // limit conditions when list can interrupt\\n // a paragraph (validation mode only)\\n if (silent && state.parentType === 'paragraph') {\\n // Next list item should still terminate previous list item;\\n //\\n // This code can fail if plugins use blkIndent as well as lists,\\n // but I hope the spec gets fixed long before that happens.\\n //\\n if (state.sCount[nextLine] >= state.blkIndent) {\\n isTerminatingParagraph = true\\n }\\n }\\n\\n // Detect list type and position after marker\\n let isOrdered\\n let markerValue\\n let posAfterMarker\\n if ((posAfterMarker = skipOrderedListMarker(state, nextLine)) >= 0) {\\n isOrdered = true\\n start = state.bMarks[nextLine] + state.tShift[nextLine]\\n markerValue = Number(state.src.slice(start, posAfterMarker - 1))\\n\\n // If we're starting a new ordered list right after\\n // a paragraph, it should start with 1.\\n if (isTerminatingParagraph && markerValue !== 1) return false\\n } else if ((posAfterMarker = skipBulletListMarker(state, nextLine)) >= 0) {\\n isOrdered = false\\n } else {\\n return false\\n }\\n\\n // If we're starting a new unordered list right after\\n // a paragraph, first line should not be empty.\\n if (isTerminatingParagraph) {\\n if (state.skipSpaces(posAfterMarker) >= state.eMarks[nextLine]) return false\\n }\\n\\n // For validation mode we can terminate immediately\\n if (silent) { return true }\\n\\n // We should terminate list on style change. Remember first one to compare.\\n const markerCharCode = state.src.charCodeAt(posAfterMarker - 1)\\n\\n // Start list\\n const listTokIdx = state.tokens.length\\n\\n if (isOrdered) {\\n token = state.push('ordered_list_open', 'ol', 1)\\n if (markerValue !== 1) {\\n token.attrs = [['start', markerValue]]\\n }\\n } else {\\n token = state.push('bullet_list_open', 'ul', 1)\\n }\\n\\n const listLines = [nextLine, 0]\\n token.map = listLines\\n token.markup = String.fromCharCode(markerCharCode)\\n\\n //\\n // Iterate list items\\n //\\n\\n let prevEmptyEnd = false\\n const terminatorRules = state.md.block.ruler.getRules('list')\\n\\n const oldParentType = state.parentType\\n state.parentType = 'list'\\n\\n while (nextLine < endLine) {\\n pos = posAfterMarker\\n max = state.eMarks[nextLine]\\n\\n const initial = state.sCount[nextLine] + posAfterMarker - (state.bMarks[nextLine] + state.tShift[nextLine])\\n let offset = initial\\n\\n while (pos < max) {\\n const ch = state.src.charCodeAt(pos)\\n\\n if (ch === 0x09) {\\n offset += 4 - (offset + state.bsCount[nextLine]) % 4\\n } else if (ch === 0x20) {\\n offset++\\n } else {\\n break\\n }\\n\\n pos++\\n }\\n\\n const contentStart = pos\\n let indentAfterMarker\\n\\n if (contentStart >= max) {\\n // trimming space in \\\"- \\\\n 3\\\" case, indent is 1 here\\n indentAfterMarker = 1\\n } else {\\n indentAfterMarker = offset - initial\\n }\\n\\n // If we have more than 4 spaces, the indent is 1\\n // (the rest is just indented code block)\\n if (indentAfterMarker > 4) { indentAfterMarker = 1 }\\n\\n // \\\" - test\\\"\\n // ^^^^^ - calculating total length of this thing\\n const indent = initial + indentAfterMarker\\n\\n // Run subparser & write tokens\\n token = state.push('list_item_open', 'li', 1)\\n token.markup = String.fromCharCode(markerCharCode)\\n const itemLines = [nextLine, 0]\\n token.map = itemLines\\n if (isOrdered) {\\n token.info = state.src.slice(start, posAfterMarker - 1)\\n }\\n\\n // change current state, then restore it after parser subcall\\n const oldTight = state.tight\\n const oldTShift = state.tShift[nextLine]\\n const oldSCount = state.sCount[nextLine]\\n\\n // - example list\\n // ^ listIndent position will be here\\n // ^ blkIndent position will be here\\n //\\n const oldListIndent = state.listIndent\\n state.listIndent = state.blkIndent\\n state.blkIndent = indent\\n\\n state.tight = true\\n state.tShift[nextLine] = contentStart - state.bMarks[nextLine]\\n state.sCount[nextLine] = offset\\n\\n if (contentStart >= max && state.isEmpty(nextLine + 1)) {\\n // workaround for this case\\n // (list item is empty, list terminates before \\\"foo\\\"):\\n // ~~~~~~~~\\n // -\\n //\\n // foo\\n // ~~~~~~~~\\n state.line = Math.min(state.line + 2, endLine)\\n } else {\\n state.md.block.tokenize(state, nextLine, endLine, true)\\n }\\n\\n // If any of list item is tight, mark list as tight\\n if (!state.tight || prevEmptyEnd) {\\n tight = false\\n }\\n // Item become loose if finish with empty line,\\n // but we should filter last element, because it means list finish\\n prevEmptyEnd = (state.line - nextLine) > 1 && state.isEmpty(state.line - 1)\\n\\n state.blkIndent = state.listIndent\\n state.listIndent = oldListIndent\\n state.tShift[nextLine] = oldTShift\\n state.sCount[nextLine] = oldSCount\\n state.tight = oldTight\\n\\n token = state.push('list_item_close', 'li', -1)\\n token.markup = String.fromCharCode(markerCharCode)\\n\\n nextLine = state.line\\n itemLines[1] = nextLine\\n\\n if (nextLine >= endLine) { break }\\n\\n //\\n // Try to check if list is terminated or continued.\\n //\\n if (state.sCount[nextLine] < state.blkIndent) { break }\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[nextLine] - state.blkIndent >= 4) { break }\\n\\n // fail if terminating block found\\n let terminate = false\\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\\n if (terminatorRules[i](state, nextLine, endLine, true)) {\\n terminate = true\\n break\\n }\\n }\\n if (terminate) { break }\\n\\n // fail if list has another type\\n if (isOrdered) {\\n posAfterMarker = skipOrderedListMarker(state, nextLine)\\n if (posAfterMarker < 0) { break }\\n start = state.bMarks[nextLine] + state.tShift[nextLine]\\n } else {\\n posAfterMarker = skipBulletListMarker(state, nextLine)\\n if (posAfterMarker < 0) { break }\\n }\\n\\n if (markerCharCode !== state.src.charCodeAt(posAfterMarker - 1)) { break }\\n }\\n\\n // Finalize list\\n if (isOrdered) {\\n token = state.push('ordered_list_close', 'ol', -1)\\n } else {\\n token = state.push('bullet_list_close', 'ul', -1)\\n }\\n token.markup = String.fromCharCode(markerCharCode)\\n\\n listLines[1] = nextLine\\n state.line = nextLine\\n\\n state.parentType = oldParentType\\n\\n // mark paragraphs tight if needed\\n if (tight) {\\n markTightParagraphs(state, listTokIdx)\\n }\\n\\n return true\\n}\\n\",\"import { isSpace, normalizeReference } from '../common/utils.mjs'\\n\\nexport default function reference (state, startLine, _endLine, silent) {\\n let pos = state.bMarks[startLine] + state.tShift[startLine]\\n let max = state.eMarks[startLine]\\n let nextLine = startLine + 1\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n\\n if (state.src.charCodeAt(pos) !== 0x5B/* [ */) { return false }\\n\\n function getNextLine (nextLine) {\\n const endLine = state.lineMax\\n\\n if (nextLine >= endLine || state.isEmpty(nextLine)) {\\n // empty line or end of input\\n return null\\n }\\n\\n let isContinuation = false\\n\\n // this would be a code block normally, but after paragraph\\n // it's considered a lazy continuation regardless of what's there\\n if (state.sCount[nextLine] - state.blkIndent > 3) { isContinuation = true }\\n\\n // quirk for blockquotes, this line should already be checked by that rule\\n if (state.sCount[nextLine] < 0) { isContinuation = true }\\n\\n if (!isContinuation) {\\n const terminatorRules = state.md.block.ruler.getRules('reference')\\n const oldParentType = state.parentType\\n state.parentType = 'reference'\\n\\n // Some tags can terminate paragraph without empty line.\\n let terminate = false\\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\\n if (terminatorRules[i](state, nextLine, endLine, true)) {\\n terminate = true\\n break\\n }\\n }\\n\\n state.parentType = oldParentType\\n if (terminate) {\\n // terminated by another block\\n return null\\n }\\n }\\n\\n const pos = state.bMarks[nextLine] + state.tShift[nextLine]\\n const max = state.eMarks[nextLine]\\n\\n // max + 1 explicitly includes the newline\\n return state.src.slice(pos, max + 1)\\n }\\n\\n let str = state.src.slice(pos, max + 1)\\n\\n max = str.length\\n let labelEnd = -1\\n\\n for (pos = 1; pos < max; pos++) {\\n const ch = str.charCodeAt(pos)\\n if (ch === 0x5B /* [ */) {\\n return false\\n } else if (ch === 0x5D /* ] */) {\\n labelEnd = pos\\n break\\n } else if (ch === 0x0A /* \\\\n */) {\\n const lineContent = getNextLine(nextLine)\\n if (lineContent !== null) {\\n str += lineContent\\n max = str.length\\n nextLine++\\n }\\n } else if (ch === 0x5C /* \\\\ */) {\\n pos++\\n if (pos < max && str.charCodeAt(pos) === 0x0A) {\\n const lineContent = getNextLine(nextLine)\\n if (lineContent !== null) {\\n str += lineContent\\n max = str.length\\n nextLine++\\n }\\n }\\n }\\n }\\n\\n if (labelEnd < 0 || str.charCodeAt(labelEnd + 1) !== 0x3A/* : */) { return false }\\n\\n // [label]: destination 'title'\\n // ^^^ skip optional whitespace here\\n for (pos = labelEnd + 2; pos < max; pos++) {\\n const ch = str.charCodeAt(pos)\\n if (ch === 0x0A) {\\n const lineContent = getNextLine(nextLine)\\n if (lineContent !== null) {\\n str += lineContent\\n max = str.length\\n nextLine++\\n }\\n } else if (isSpace(ch)) {\\n /* eslint no-empty:0 */\\n } else {\\n break\\n }\\n }\\n\\n // [label]: destination 'title'\\n // ^^^^^^^^^^^ parse this\\n const destRes = state.md.helpers.parseLinkDestination(str, pos, max)\\n if (!destRes.ok) { return false }\\n\\n const href = state.md.normalizeLink(destRes.str)\\n if (!state.md.validateLink(href)) { return false }\\n\\n pos = destRes.pos\\n\\n // save cursor state, we could require to rollback later\\n const destEndPos = pos\\n const destEndLineNo = nextLine\\n\\n // [label]: destination 'title'\\n // ^^^ skipping those spaces\\n const start = pos\\n for (; pos < max; pos++) {\\n const ch = str.charCodeAt(pos)\\n if (ch === 0x0A) {\\n const lineContent = getNextLine(nextLine)\\n if (lineContent !== null) {\\n str += lineContent\\n max = str.length\\n nextLine++\\n }\\n } else if (isSpace(ch)) {\\n /* eslint no-empty:0 */\\n } else {\\n break\\n }\\n }\\n\\n // [label]: destination 'title'\\n // ^^^^^^^ parse this\\n let titleRes = state.md.helpers.parseLinkTitle(str, pos, max)\\n while (titleRes.can_continue) {\\n const lineContent = getNextLine(nextLine)\\n if (lineContent === null) break\\n str += lineContent\\n pos = max\\n max = str.length\\n nextLine++\\n titleRes = state.md.helpers.parseLinkTitle(str, pos, max, titleRes)\\n }\\n let title\\n\\n if (pos < max && start !== pos && titleRes.ok) {\\n title = titleRes.str\\n pos = titleRes.pos\\n } else {\\n title = ''\\n pos = destEndPos\\n nextLine = destEndLineNo\\n }\\n\\n // skip trailing spaces until the rest of the line\\n while (pos < max) {\\n const ch = str.charCodeAt(pos)\\n if (!isSpace(ch)) { break }\\n pos++\\n }\\n\\n if (pos < max && str.charCodeAt(pos) !== 0x0A) {\\n if (title) {\\n // garbage at the end of the line after title,\\n // but it could still be a valid reference if we roll back\\n title = ''\\n pos = destEndPos\\n nextLine = destEndLineNo\\n while (pos < max) {\\n const ch = str.charCodeAt(pos)\\n if (!isSpace(ch)) { break }\\n pos++\\n }\\n }\\n }\\n\\n if (pos < max && str.charCodeAt(pos) !== 0x0A) {\\n // garbage at the end of the line\\n return false\\n }\\n\\n const label = normalizeReference(str.slice(1, labelEnd))\\n if (!label) {\\n // CommonMark 0.20 disallows empty labels\\n return false\\n }\\n\\n // Reference can not terminate anything. This check is for safety only.\\n /* istanbul ignore if */\\n if (silent) { return true }\\n\\n if (typeof state.env.references === 'undefined') {\\n state.env.references = {}\\n }\\n if (typeof state.env.references[label] === 'undefined') {\\n state.env.references[label] = { title, href }\\n }\\n\\n state.line = nextLine\\n return true\\n}\\n\",\"// List of valid html blocks names, according to commonmark spec\\n// https://spec.commonmark.org/0.30/#html-blocks\\n\\nexport default [\\n 'address',\\n 'article',\\n 'aside',\\n 'base',\\n 'basefont',\\n 'blockquote',\\n 'body',\\n 'caption',\\n 'center',\\n 'col',\\n 'colgroup',\\n 'dd',\\n 'details',\\n 'dialog',\\n 'dir',\\n 'div',\\n 'dl',\\n 'dt',\\n 'fieldset',\\n 'figcaption',\\n 'figure',\\n 'footer',\\n 'form',\\n 'frame',\\n 'frameset',\\n 'h1',\\n 'h2',\\n 'h3',\\n 'h4',\\n 'h5',\\n 'h6',\\n 'head',\\n 'header',\\n 'hr',\\n 'html',\\n 'iframe',\\n 'legend',\\n 'li',\\n 'link',\\n 'main',\\n 'menu',\\n 'menuitem',\\n 'nav',\\n 'noframes',\\n 'ol',\\n 'optgroup',\\n 'option',\\n 'p',\\n 'param',\\n 'search',\\n 'section',\\n 'summary',\\n 'table',\\n 'tbody',\\n 'td',\\n 'tfoot',\\n 'th',\\n 'thead',\\n 'title',\\n 'tr',\\n 'track',\\n 'ul'\\n]\\n\",\"// Regexps to match html elements\\n\\nconst attr_name = '[a-zA-Z_:][a-zA-Z0-9:._-]*'\\n\\nconst unquoted = '[^\\\"\\\\'=<>`\\\\\\\\x00-\\\\\\\\x20]+'\\nconst single_quoted = \\\"'[^']*'\\\"\\nconst double_quoted = '\\\"[^\\\"]*\\\"'\\n\\nconst attr_value = '(?:' + unquoted + '|' + single_quoted + '|' + double_quoted + ')'\\n\\nconst attribute = '(?:\\\\\\\\s+' + attr_name + '(?:\\\\\\\\s*=\\\\\\\\s*' + attr_value + ')?)'\\n\\nconst open_tag = '<[A-Za-z][A-Za-z0-9\\\\\\\\-]*' + attribute + '*\\\\\\\\s*\\\\\\\\/?>'\\n\\nconst close_tag = '<\\\\\\\\/[A-Za-z][A-Za-z0-9\\\\\\\\-]*\\\\\\\\s*>'\\nconst comment = ''\\nconst processing = '<[?][\\\\\\\\s\\\\\\\\S]*?[?]>'\\nconst declaration = ']*>'\\nconst cdata = ''\\n\\nconst HTML_TAG_RE = new RegExp('^(?:' + open_tag + '|' + close_tag + '|' + comment +\\n '|' + processing + '|' + declaration + '|' + cdata + ')')\\nconst HTML_OPEN_CLOSE_TAG_RE = new RegExp('^(?:' + open_tag + '|' + close_tag + ')')\\n\\nexport { HTML_TAG_RE, HTML_OPEN_CLOSE_TAG_RE }\\n\",\"// HTML block\\n\\nimport block_names from '../common/html_blocks.mjs'\\nimport { HTML_OPEN_CLOSE_TAG_RE } from '../common/html_re.mjs'\\n\\n// An array of opening and corresponding closing sequences for html tags,\\n// last argument defines whether it can terminate a paragraph or not\\n//\\nconst HTML_SEQUENCES = [\\n [/^<(script|pre|style|textarea)(?=(\\\\s|>|$))/i, /<\\\\/(script|pre|style|textarea)>/i, true],\\n [/^/, true],\\n [/^<\\\\?/, /\\\\?>/, true],\\n [/^/, true],\\n [/^/, true],\\n [new RegExp('^|$))', 'i'), /^$/, true],\\n [new RegExp(HTML_OPEN_CLOSE_TAG_RE.source + '\\\\\\\\s*$'), /^$/, false]\\n]\\n\\nexport default function html_block (state, startLine, endLine, silent) {\\n let pos = state.bMarks[startLine] + state.tShift[startLine]\\n let max = state.eMarks[startLine]\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n\\n if (!state.md.options.html) { return false }\\n\\n if (state.src.charCodeAt(pos) !== 0x3C/* < */) { return false }\\n\\n let lineText = state.src.slice(pos, max)\\n\\n let i = 0\\n for (; i < HTML_SEQUENCES.length; i++) {\\n if (HTML_SEQUENCES[i][0].test(lineText)) { break }\\n }\\n if (i === HTML_SEQUENCES.length) { return false }\\n\\n if (silent) {\\n // true if this sequence can be a terminator, false otherwise\\n return HTML_SEQUENCES[i][2]\\n }\\n\\n let nextLine = startLine + 1\\n\\n // If we are here - we detected HTML block.\\n // Let's roll down till block end.\\n if (!HTML_SEQUENCES[i][1].test(lineText)) {\\n for (; nextLine < endLine; nextLine++) {\\n if (state.sCount[nextLine] < state.blkIndent) { break }\\n\\n pos = state.bMarks[nextLine] + state.tShift[nextLine]\\n max = state.eMarks[nextLine]\\n lineText = state.src.slice(pos, max)\\n\\n if (HTML_SEQUENCES[i][1].test(lineText)) {\\n if (lineText.length !== 0) { nextLine++ }\\n break\\n }\\n }\\n }\\n\\n state.line = nextLine\\n\\n const token = state.push('html_block', '', 0)\\n token.map = [startLine, nextLine]\\n token.content = state.getLines(startLine, nextLine, state.blkIndent, true)\\n\\n return true\\n}\\n\",\"// heading (#, ##, ...)\\n\\nimport { isSpace } from '../common/utils.mjs'\\n\\nexport default function heading (state, startLine, endLine, silent) {\\n let pos = state.bMarks[startLine] + state.tShift[startLine]\\n let max = state.eMarks[startLine]\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n\\n let ch = state.src.charCodeAt(pos)\\n\\n if (ch !== 0x23/* # */ || pos >= max) { return false }\\n\\n // count heading level\\n let level = 1\\n ch = state.src.charCodeAt(++pos)\\n while (ch === 0x23/* # */ && pos < max && level <= 6) {\\n level++\\n ch = state.src.charCodeAt(++pos)\\n }\\n\\n if (level > 6 || (pos < max && !isSpace(ch))) { return false }\\n\\n if (silent) { return true }\\n\\n // Let's cut tails like ' ### ' from the end of string\\n\\n max = state.skipSpacesBack(max, pos)\\n const tmp = state.skipCharsBack(max, 0x23, pos) // #\\n if (tmp > pos && isSpace(state.src.charCodeAt(tmp - 1))) {\\n max = tmp\\n }\\n\\n state.line = startLine + 1\\n\\n const token_o = state.push('heading_open', 'h' + String(level), 1)\\n token_o.markup = '########'.slice(0, level)\\n token_o.map = [startLine, state.line]\\n\\n const token_i = state.push('inline', '', 0)\\n token_i.content = state.src.slice(pos, max).trim()\\n token_i.map = [startLine, state.line]\\n token_i.children = []\\n\\n const token_c = state.push('heading_close', 'h' + String(level), -1)\\n token_c.markup = '########'.slice(0, level)\\n\\n return true\\n}\\n\",\"// lheading (---, ===)\\n\\nexport default function lheading (state, startLine, endLine/*, silent */) {\\n const terminatorRules = state.md.block.ruler.getRules('paragraph')\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n\\n const oldParentType = state.parentType\\n state.parentType = 'paragraph' // use paragraph to match terminatorRules\\n\\n // jump line-by-line until empty one or EOF\\n let level = 0\\n let marker\\n let nextLine = startLine + 1\\n\\n for (; nextLine < endLine && !state.isEmpty(nextLine); nextLine++) {\\n // this would be a code block normally, but after paragraph\\n // it's considered a lazy continuation regardless of what's there\\n if (state.sCount[nextLine] - state.blkIndent > 3) { continue }\\n\\n //\\n // Check for underline in setext header\\n //\\n if (state.sCount[nextLine] >= state.blkIndent) {\\n let pos = state.bMarks[nextLine] + state.tShift[nextLine]\\n const max = state.eMarks[nextLine]\\n\\n if (pos < max) {\\n marker = state.src.charCodeAt(pos)\\n\\n if (marker === 0x2D/* - */ || marker === 0x3D/* = */) {\\n pos = state.skipChars(pos, marker)\\n pos = state.skipSpaces(pos)\\n\\n if (pos >= max) {\\n level = (marker === 0x3D/* = */ ? 1 : 2)\\n break\\n }\\n }\\n }\\n }\\n\\n // quirk for blockquotes, this line should already be checked by that rule\\n if (state.sCount[nextLine] < 0) { continue }\\n\\n // Some tags can terminate paragraph without empty line.\\n let terminate = false\\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\\n if (terminatorRules[i](state, nextLine, endLine, true)) {\\n terminate = true\\n break\\n }\\n }\\n if (terminate) { break }\\n }\\n\\n if (!level) {\\n // Didn't find valid underline\\n return false\\n }\\n\\n const content = state.getLines(startLine, nextLine, state.blkIndent, false).trim()\\n\\n state.line = nextLine + 1\\n\\n const token_o = state.push('heading_open', 'h' + String(level), 1)\\n token_o.markup = String.fromCharCode(marker)\\n token_o.map = [startLine, state.line]\\n\\n const token_i = state.push('inline', '', 0)\\n token_i.content = content\\n token_i.map = [startLine, state.line - 1]\\n token_i.children = []\\n\\n const token_c = state.push('heading_close', 'h' + String(level), -1)\\n token_c.markup = String.fromCharCode(marker)\\n\\n state.parentType = oldParentType\\n\\n return true\\n}\\n\",\"// Paragraph\\n\\nexport default function paragraph (state, startLine, endLine) {\\n const terminatorRules = state.md.block.ruler.getRules('paragraph')\\n const oldParentType = state.parentType\\n let nextLine = startLine + 1\\n state.parentType = 'paragraph'\\n\\n // jump line-by-line until empty one or EOF\\n for (; nextLine < endLine && !state.isEmpty(nextLine); nextLine++) {\\n // this would be a code block normally, but after paragraph\\n // it's considered a lazy continuation regardless of what's there\\n if (state.sCount[nextLine] - state.blkIndent > 3) { continue }\\n\\n // quirk for blockquotes, this line should already be checked by that rule\\n if (state.sCount[nextLine] < 0) { continue }\\n\\n // Some tags can terminate paragraph without empty line.\\n let terminate = false\\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\\n if (terminatorRules[i](state, nextLine, endLine, true)) {\\n terminate = true\\n break\\n }\\n }\\n if (terminate) { break }\\n }\\n\\n const content = state.getLines(startLine, nextLine, state.blkIndent, false).trim()\\n\\n state.line = nextLine\\n\\n const token_o = state.push('paragraph_open', 'p', 1)\\n token_o.map = [startLine, state.line]\\n\\n const token_i = state.push('inline', '', 0)\\n token_i.content = content\\n token_i.map = [startLine, state.line]\\n token_i.children = []\\n\\n state.push('paragraph_close', 'p', -1)\\n\\n state.parentType = oldParentType\\n\\n return true\\n}\\n\",\"/** internal\\n * class ParserBlock\\n *\\n * Block-level tokenizer.\\n **/\\n\\nimport Ruler from './ruler.mjs'\\nimport StateBlock from './rules_block/state_block.mjs'\\n\\nimport r_table from './rules_block/table.mjs'\\nimport r_code from './rules_block/code.mjs'\\nimport r_fence from './rules_block/fence.mjs'\\nimport r_blockquote from './rules_block/blockquote.mjs'\\nimport r_hr from './rules_block/hr.mjs'\\nimport r_list from './rules_block/list.mjs'\\nimport r_reference from './rules_block/reference.mjs'\\nimport r_html_block from './rules_block/html_block.mjs'\\nimport r_heading from './rules_block/heading.mjs'\\nimport r_lheading from './rules_block/lheading.mjs'\\nimport r_paragraph from './rules_block/paragraph.mjs'\\n\\nconst _rules = [\\n // First 2 params - rule name & source. Secondary array - list of rules,\\n // which can be terminated by this one.\\n ['table', r_table, ['paragraph', 'reference']],\\n ['code', r_code],\\n ['fence', r_fence, ['paragraph', 'reference', 'blockquote', 'list']],\\n ['blockquote', r_blockquote, ['paragraph', 'reference', 'blockquote', 'list']],\\n ['hr', r_hr, ['paragraph', 'reference', 'blockquote', 'list']],\\n ['list', r_list, ['paragraph', 'reference', 'blockquote']],\\n ['reference', r_reference],\\n ['html_block', r_html_block, ['paragraph', 'reference', 'blockquote']],\\n ['heading', r_heading, ['paragraph', 'reference', 'blockquote']],\\n ['lheading', r_lheading],\\n ['paragraph', r_paragraph]\\n]\\n\\n/**\\n * new ParserBlock()\\n **/\\nfunction ParserBlock () {\\n /**\\n * ParserBlock#ruler -> Ruler\\n *\\n * [[Ruler]] instance. Keep configuration of block rules.\\n **/\\n this.ruler = new Ruler()\\n\\n for (let i = 0; i < _rules.length; i++) {\\n this.ruler.push(_rules[i][0], _rules[i][1], { alt: (_rules[i][2] || []).slice() })\\n }\\n}\\n\\n// Generate tokens for input range\\n//\\nParserBlock.prototype.tokenize = function (state, startLine, endLine) {\\n const rules = this.ruler.getRules('')\\n const len = rules.length\\n const maxNesting = state.md.options.maxNesting\\n let line = startLine\\n let hasEmptyLines = false\\n\\n while (line < endLine) {\\n state.line = line = state.skipEmptyLines(line)\\n if (line >= endLine) { break }\\n\\n // Termination condition for nested calls.\\n // Nested calls currently used for blockquotes & lists\\n if (state.sCount[line] < state.blkIndent) { break }\\n\\n // If nesting level exceeded - skip tail to the end. That's not ordinary\\n // situation and we should not care about content.\\n if (state.level >= maxNesting) {\\n state.line = endLine\\n break\\n }\\n\\n // Try all possible rules.\\n // On success, rule should:\\n //\\n // - update `state.line`\\n // - update `state.tokens`\\n // - return true\\n const prevLine = state.line\\n let ok = false\\n\\n for (let i = 0; i < len; i++) {\\n ok = rules[i](state, line, endLine, false)\\n if (ok) {\\n if (prevLine >= state.line) {\\n throw new Error(\\\"block rule didn't increment state.line\\\")\\n }\\n break\\n }\\n }\\n\\n // this can only happen if user disables paragraph rule\\n if (!ok) throw new Error('none of the block rules matched')\\n\\n // set state.tight if we had an empty line before current tag\\n // i.e. latest empty line should not count\\n state.tight = !hasEmptyLines\\n\\n // paragraph might \\\"eat\\\" one newline after it in nested lists\\n if (state.isEmpty(state.line - 1)) {\\n hasEmptyLines = true\\n }\\n\\n line = state.line\\n\\n if (line < endLine && state.isEmpty(line)) {\\n hasEmptyLines = true\\n line++\\n state.line = line\\n }\\n }\\n}\\n\\n/**\\n * ParserBlock.parse(str, md, env, outTokens)\\n *\\n * Process input string and push block tokens into `outTokens`\\n **/\\nParserBlock.prototype.parse = function (src, md, env, outTokens) {\\n if (!src) { return }\\n\\n const state = new this.State(src, md, env, outTokens)\\n\\n this.tokenize(state, state.line, state.lineMax)\\n}\\n\\nParserBlock.prototype.State = StateBlock\\n\\nexport default ParserBlock\\n\",\"// Inline parser state\\n\\nimport Token from '../token.mjs'\\nimport { isWhiteSpace, isPunctChar, isMdAsciiPunct } from '../common/utils.mjs'\\n\\nfunction StateInline (src, md, env, outTokens) {\\n this.src = src\\n this.env = env\\n this.md = md\\n this.tokens = outTokens\\n this.tokens_meta = Array(outTokens.length)\\n\\n this.pos = 0\\n this.posMax = this.src.length\\n this.level = 0\\n this.pending = ''\\n this.pendingLevel = 0\\n\\n // Stores { start: end } pairs. Useful for backtrack\\n // optimization of pairs parse (emphasis, strikes).\\n this.cache = {}\\n\\n // List of emphasis-like delimiters for current tag\\n this.delimiters = []\\n\\n // Stack of delimiter lists for upper level tags\\n this._prev_delimiters = []\\n\\n // backtick length => last seen position\\n this.backticks = {}\\n this.backticksScanned = false\\n\\n // Counter used to disable inline linkify-it execution\\n // inside and markdown links\\n this.linkLevel = 0\\n}\\n\\n// Flush pending text\\n//\\nStateInline.prototype.pushPending = function () {\\n const token = new Token('text', '', 0)\\n token.content = this.pending\\n token.level = this.pendingLevel\\n this.tokens.push(token)\\n this.pending = ''\\n return token\\n}\\n\\n// Push new token to \\\"stream\\\".\\n// If pending text exists - flush it as text token\\n//\\nStateInline.prototype.push = function (type, tag, nesting) {\\n if (this.pending) {\\n this.pushPending()\\n }\\n\\n const token = new Token(type, tag, nesting)\\n let token_meta = null\\n\\n if (nesting < 0) {\\n // closing tag\\n this.level--\\n this.delimiters = this._prev_delimiters.pop()\\n }\\n\\n token.level = this.level\\n\\n if (nesting > 0) {\\n // opening tag\\n this.level++\\n this._prev_delimiters.push(this.delimiters)\\n this.delimiters = []\\n token_meta = { delimiters: this.delimiters }\\n }\\n\\n this.pendingLevel = this.level\\n this.tokens.push(token)\\n this.tokens_meta.push(token_meta)\\n return token\\n}\\n\\n// Scan a sequence of emphasis-like markers, and determine whether\\n// it can start an emphasis sequence or end an emphasis sequence.\\n//\\n// - start - position to scan from (it should point at a valid marker);\\n// - canSplitWord - determine if these markers can be found inside a word\\n//\\nStateInline.prototype.scanDelims = function (start, canSplitWord) {\\n const max = this.posMax\\n const marker = this.src.charCodeAt(start)\\n\\n // treat beginning of the line as a whitespace\\n const lastChar = start > 0 ? this.src.charCodeAt(start - 1) : 0x20\\n\\n let pos = start\\n while (pos < max && this.src.charCodeAt(pos) === marker) { pos++ }\\n\\n const count = pos - start\\n\\n // treat end of the line as a whitespace\\n const nextChar = pos < max ? this.src.charCodeAt(pos) : 0x20\\n\\n const isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar))\\n const isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar))\\n\\n const isLastWhiteSpace = isWhiteSpace(lastChar)\\n const isNextWhiteSpace = isWhiteSpace(nextChar)\\n\\n const left_flanking =\\n !isNextWhiteSpace && (!isNextPunctChar || isLastWhiteSpace || isLastPunctChar)\\n const right_flanking =\\n !isLastWhiteSpace && (!isLastPunctChar || isNextWhiteSpace || isNextPunctChar)\\n\\n const can_open = left_flanking && (canSplitWord || !right_flanking || isLastPunctChar)\\n const can_close = right_flanking && (canSplitWord || !left_flanking || isNextPunctChar)\\n\\n return { can_open, can_close, length: count }\\n}\\n\\n// re-export Token class to use in block rules\\nStateInline.prototype.Token = Token\\n\\nexport default StateInline\\n\",\"// Skip text characters for text token, place those to pending buffer\\n// and increment current pos\\n\\n// Rule to skip pure text\\n// '{}$%@~+=:' reserved for extentions\\n\\n// !, \\\", #, $, %, &, ', (, ), *, +, ,, -, ., /, :, ;, <, =, >, ?, @, [, \\\\, ], ^, _, `, {, |, }, or ~\\n\\n// !!!! Don't confuse with \\\"Markdown ASCII Punctuation\\\" chars\\n// http://spec.commonmark.org/0.15/#ascii-punctuation-character\\nfunction isTerminatorChar (ch) {\\n switch (ch) {\\n case 0x0A/* \\\\n */:\\n case 0x21/* ! */:\\n case 0x23/* # */:\\n case 0x24/* $ */:\\n case 0x25/* % */:\\n case 0x26/* & */:\\n case 0x2A/* * */:\\n case 0x2B/* + */:\\n case 0x2D/* - */:\\n case 0x3A/* : */:\\n case 0x3C/* < */:\\n case 0x3D/* = */:\\n case 0x3E/* > */:\\n case 0x40/* @ */:\\n case 0x5B/* [ */:\\n case 0x5C/* \\\\ */:\\n case 0x5D/* ] */:\\n case 0x5E/* ^ */:\\n case 0x5F/* _ */:\\n case 0x60/* ` */:\\n case 0x7B/* { */:\\n case 0x7D/* } */:\\n case 0x7E/* ~ */:\\n return true\\n default:\\n return false\\n }\\n}\\n\\nexport default function text (state, silent) {\\n let pos = state.pos\\n\\n while (pos < state.posMax && !isTerminatorChar(state.src.charCodeAt(pos))) {\\n pos++\\n }\\n\\n if (pos === state.pos) { return false }\\n\\n if (!silent) { state.pending += state.src.slice(state.pos, pos) }\\n\\n state.pos = pos\\n\\n return true\\n}\\n\\n// Alternative implementation, for memory.\\n//\\n// It costs 10% of performance, but allows extend terminators list, if place it\\n// to `ParserInline` property. Probably, will switch to it sometime, such\\n// flexibility required.\\n\\n/*\\nvar TERMINATOR_RE = /[\\\\n!#$%&*+\\\\-:<=>@[\\\\\\\\\\\\]^_`{}~]/;\\n\\nmodule.exports = function text(state, silent) {\\n var pos = state.pos,\\n idx = state.src.slice(pos).search(TERMINATOR_RE);\\n\\n // first char is terminator -> empty text\\n if (idx === 0) { return false; }\\n\\n // no terminator -> text till end of string\\n if (idx < 0) {\\n if (!silent) { state.pending += state.src.slice(pos); }\\n state.pos = state.src.length;\\n return true;\\n }\\n\\n if (!silent) { state.pending += state.src.slice(pos, pos + idx); }\\n\\n state.pos += idx;\\n\\n return true;\\n}; */\\n\",\"// Process links like https://example.org/\\n\\n// RFC3986: scheme = ALPHA *( ALPHA / DIGIT / \\\"+\\\" / \\\"-\\\" / \\\".\\\" )\\nconst SCHEME_RE = /(?:^|[^a-z0-9.+-])([a-z][a-z0-9.+-]*)$/i\\n\\nexport default function linkify (state, silent) {\\n if (!state.md.options.linkify) return false\\n if (state.linkLevel > 0) return false\\n\\n const pos = state.pos\\n const max = state.posMax\\n\\n if (pos + 3 > max) return false\\n if (state.src.charCodeAt(pos) !== 0x3A/* : */) return false\\n if (state.src.charCodeAt(pos + 1) !== 0x2F/* / */) return false\\n if (state.src.charCodeAt(pos + 2) !== 0x2F/* / */) return false\\n\\n const match = state.pending.match(SCHEME_RE)\\n if (!match) return false\\n\\n const proto = match[1]\\n\\n const link = state.md.linkify.matchAtStart(state.src.slice(pos - proto.length))\\n if (!link) return false\\n\\n let url = link.url\\n\\n // invalid link, but still detected by linkify somehow;\\n // need to check to prevent infinite loop below\\n if (url.length <= proto.length) return false\\n\\n // disallow '*' at the end of the link (conflicts with emphasis)\\n // do manual backsearch to avoid perf issues with regex /\\\\*+$/ on \\\"****...****a\\\".\\n let urlEnd = url.length\\n while (urlEnd > 0 && url.charCodeAt(urlEnd - 1) === 0x2A/* * */) {\\n urlEnd--\\n }\\n if (urlEnd !== url.length) {\\n url = url.slice(0, urlEnd)\\n }\\n\\n const fullUrl = state.md.normalizeLink(url)\\n if (!state.md.validateLink(fullUrl)) return false\\n\\n if (!silent) {\\n state.pending = state.pending.slice(0, -proto.length)\\n\\n const token_o = state.push('link_open', 'a', 1)\\n token_o.attrs = [['href', fullUrl]]\\n token_o.markup = 'linkify'\\n token_o.info = 'auto'\\n\\n const token_t = state.push('text', '', 0)\\n token_t.content = state.md.normalizeLinkText(url)\\n\\n const token_c = state.push('link_close', 'a', -1)\\n token_c.markup = 'linkify'\\n token_c.info = 'auto'\\n }\\n\\n state.pos += url.length - proto.length\\n return true\\n}\\n\",\"// Proceess '\\\\n'\\n\\nimport { isSpace } from '../common/utils.mjs'\\n\\nexport default function newline (state, silent) {\\n let pos = state.pos\\n\\n if (state.src.charCodeAt(pos) !== 0x0A/* \\\\n */) { return false }\\n\\n const pmax = state.pending.length - 1\\n const max = state.posMax\\n\\n // ' \\\\n' -> hardbreak\\n // Lookup in pending chars is bad practice! Don't copy to other rules!\\n // Pending string is stored in concat mode, indexed lookups will cause\\n // convertion to flat mode.\\n if (!silent) {\\n if (pmax >= 0 && state.pending.charCodeAt(pmax) === 0x20) {\\n if (pmax >= 1 && state.pending.charCodeAt(pmax - 1) === 0x20) {\\n // Find whitespaces tail of pending chars.\\n let ws = pmax - 1\\n while (ws >= 1 && state.pending.charCodeAt(ws - 1) === 0x20) ws--\\n\\n state.pending = state.pending.slice(0, ws)\\n state.push('hardbreak', 'br', 0)\\n } else {\\n state.pending = state.pending.slice(0, -1)\\n state.push('softbreak', 'br', 0)\\n }\\n } else {\\n state.push('softbreak', 'br', 0)\\n }\\n }\\n\\n pos++\\n\\n // skip heading spaces for next line\\n while (pos < max && isSpace(state.src.charCodeAt(pos))) { pos++ }\\n\\n state.pos = pos\\n return true\\n}\\n\",\"// Process escaped chars and hardbreaks\\n\\nimport { isSpace } from '../common/utils.mjs'\\n\\nconst ESCAPED = []\\n\\nfor (let i = 0; i < 256; i++) { ESCAPED.push(0) }\\n\\n'\\\\\\\\!\\\"#$%&\\\\'()*+,./:;<=>?@[]^_`{|}~-'\\n .split('').forEach(function (ch) { ESCAPED[ch.charCodeAt(0)] = 1 })\\n\\nexport default function escape (state, silent) {\\n let pos = state.pos\\n const max = state.posMax\\n\\n if (state.src.charCodeAt(pos) !== 0x5C/* \\\\ */) return false\\n pos++\\n\\n // '\\\\' at the end of the inline block\\n if (pos >= max) return false\\n\\n let ch1 = state.src.charCodeAt(pos)\\n\\n if (ch1 === 0x0A) {\\n if (!silent) {\\n state.push('hardbreak', 'br', 0)\\n }\\n\\n pos++\\n // skip leading whitespaces from next line\\n while (pos < max) {\\n ch1 = state.src.charCodeAt(pos)\\n if (!isSpace(ch1)) break\\n pos++\\n }\\n\\n state.pos = pos\\n return true\\n }\\n\\n let escapedStr = state.src[pos]\\n\\n if (ch1 >= 0xD800 && ch1 <= 0xDBFF && pos + 1 < max) {\\n const ch2 = state.src.charCodeAt(pos + 1)\\n\\n if (ch2 >= 0xDC00 && ch2 <= 0xDFFF) {\\n escapedStr += state.src[pos + 1]\\n pos++\\n }\\n }\\n\\n const origStr = '\\\\\\\\' + escapedStr\\n\\n if (!silent) {\\n const token = state.push('text_special', '', 0)\\n\\n if (ch1 < 256 && ESCAPED[ch1] !== 0) {\\n token.content = escapedStr\\n } else {\\n token.content = origStr\\n }\\n\\n token.markup = origStr\\n token.info = 'escape'\\n }\\n\\n state.pos = pos + 1\\n return true\\n}\\n\",\"// Parse backticks\\n\\nexport default function backtick (state, silent) {\\n let pos = state.pos\\n const ch = state.src.charCodeAt(pos)\\n\\n if (ch !== 0x60/* ` */) { return false }\\n\\n const start = pos\\n pos++\\n const max = state.posMax\\n\\n // scan marker length\\n while (pos < max && state.src.charCodeAt(pos) === 0x60/* ` */) { pos++ }\\n\\n const marker = state.src.slice(start, pos)\\n const openerLength = marker.length\\n\\n if (state.backticksScanned && (state.backticks[openerLength] || 0) <= start) {\\n if (!silent) state.pending += marker\\n state.pos += openerLength\\n return true\\n }\\n\\n let matchEnd = pos\\n let matchStart\\n\\n // Nothing found in the cache, scan until the end of the line (or until marker is found)\\n while ((matchStart = state.src.indexOf('`', matchEnd)) !== -1) {\\n matchEnd = matchStart + 1\\n\\n // scan marker length\\n while (matchEnd < max && state.src.charCodeAt(matchEnd) === 0x60/* ` */) { matchEnd++ }\\n\\n const closerLength = matchEnd - matchStart\\n\\n if (closerLength === openerLength) {\\n // Found matching closer length.\\n if (!silent) {\\n const token = state.push('code_inline', 'code', 0)\\n token.markup = marker\\n token.content = state.src.slice(pos, matchStart)\\n .replace(/\\\\n/g, ' ')\\n .replace(/^ (.+) $/, '$1')\\n }\\n state.pos = matchEnd\\n return true\\n }\\n\\n // Some different length found, put it in cache as upper limit of where closer can be found\\n state.backticks[closerLength] = matchStart\\n }\\n\\n // Scanned through the end, didn't find anything\\n state.backticksScanned = true\\n\\n if (!silent) state.pending += marker\\n state.pos += openerLength\\n return true\\n}\\n\",\"// ~~strike through~~\\n//\\n\\n// Insert each marker as a separate text token, and add it to delimiter list\\n//\\nfunction strikethrough_tokenize (state, silent) {\\n const start = state.pos\\n const marker = state.src.charCodeAt(start)\\n\\n if (silent) { return false }\\n\\n if (marker !== 0x7E/* ~ */) { return false }\\n\\n const scanned = state.scanDelims(state.pos, true)\\n let len = scanned.length\\n const ch = String.fromCharCode(marker)\\n\\n if (len < 2) { return false }\\n\\n let token\\n\\n if (len % 2) {\\n token = state.push('text', '', 0)\\n token.content = ch\\n len--\\n }\\n\\n for (let i = 0; i < len; i += 2) {\\n token = state.push('text', '', 0)\\n token.content = ch + ch\\n\\n state.delimiters.push({\\n marker,\\n length: 0, // disable \\\"rule of 3\\\" length checks meant for emphasis\\n token: state.tokens.length - 1,\\n end: -1,\\n open: scanned.can_open,\\n close: scanned.can_close\\n })\\n }\\n\\n state.pos += scanned.length\\n\\n return true\\n}\\n\\nfunction postProcess (state, delimiters) {\\n let token\\n const loneMarkers = []\\n const max = delimiters.length\\n\\n for (let i = 0; i < max; i++) {\\n const startDelim = delimiters[i]\\n\\n if (startDelim.marker !== 0x7E/* ~ */) {\\n continue\\n }\\n\\n if (startDelim.end === -1) {\\n continue\\n }\\n\\n const endDelim = delimiters[startDelim.end]\\n\\n token = state.tokens[startDelim.token]\\n token.type = 's_open'\\n token.tag = 's'\\n token.nesting = 1\\n token.markup = '~~'\\n token.content = ''\\n\\n token = state.tokens[endDelim.token]\\n token.type = 's_close'\\n token.tag = 's'\\n token.nesting = -1\\n token.markup = '~~'\\n token.content = ''\\n\\n if (state.tokens[endDelim.token - 1].type === 'text' &&\\n state.tokens[endDelim.token - 1].content === '~') {\\n loneMarkers.push(endDelim.token - 1)\\n }\\n }\\n\\n // If a marker sequence has an odd number of characters, it's splitted\\n // like this: `~~~~~` -> `~` + `~~` + `~~`, leaving one marker at the\\n // start of the sequence.\\n //\\n // So, we have to move all those markers after subsequent s_close tags.\\n //\\n while (loneMarkers.length) {\\n const i = loneMarkers.pop()\\n let j = i + 1\\n\\n while (j < state.tokens.length && state.tokens[j].type === 's_close') {\\n j++\\n }\\n\\n j--\\n\\n if (i !== j) {\\n token = state.tokens[j]\\n state.tokens[j] = state.tokens[i]\\n state.tokens[i] = token\\n }\\n }\\n}\\n\\n// Walk through delimiter list and replace text tokens with tags\\n//\\nfunction strikethrough_postProcess (state) {\\n const tokens_meta = state.tokens_meta\\n const max = state.tokens_meta.length\\n\\n postProcess(state, state.delimiters)\\n\\n for (let curr = 0; curr < max; curr++) {\\n if (tokens_meta[curr] && tokens_meta[curr].delimiters) {\\n postProcess(state, tokens_meta[curr].delimiters)\\n }\\n }\\n}\\n\\nexport default {\\n tokenize: strikethrough_tokenize,\\n postProcess: strikethrough_postProcess\\n}\\n\",\"// Process *this* and _that_\\n//\\n\\n// Insert each marker as a separate text token, and add it to delimiter list\\n//\\nfunction emphasis_tokenize (state, silent) {\\n const start = state.pos\\n const marker = state.src.charCodeAt(start)\\n\\n if (silent) { return false }\\n\\n if (marker !== 0x5F /* _ */ && marker !== 0x2A /* * */) { return false }\\n\\n const scanned = state.scanDelims(state.pos, marker === 0x2A)\\n\\n for (let i = 0; i < scanned.length; i++) {\\n const token = state.push('text', '', 0)\\n token.content = String.fromCharCode(marker)\\n\\n state.delimiters.push({\\n // Char code of the starting marker (number).\\n //\\n marker,\\n\\n // Total length of these series of delimiters.\\n //\\n length: scanned.length,\\n\\n // A position of the token this delimiter corresponds to.\\n //\\n token: state.tokens.length - 1,\\n\\n // If this delimiter is matched as a valid opener, `end` will be\\n // equal to its position, otherwise it's `-1`.\\n //\\n end: -1,\\n\\n // Boolean flags that determine if this delimiter could open or close\\n // an emphasis.\\n //\\n open: scanned.can_open,\\n close: scanned.can_close\\n })\\n }\\n\\n state.pos += scanned.length\\n\\n return true\\n}\\n\\nfunction postProcess (state, delimiters) {\\n const max = delimiters.length\\n\\n for (let i = max - 1; i >= 0; i--) {\\n const startDelim = delimiters[i]\\n\\n if (startDelim.marker !== 0x5F/* _ */ && startDelim.marker !== 0x2A/* * */) {\\n continue\\n }\\n\\n // Process only opening markers\\n if (startDelim.end === -1) {\\n continue\\n }\\n\\n const endDelim = delimiters[startDelim.end]\\n\\n // If the previous delimiter has the same marker and is adjacent to this one,\\n // merge those into one strong delimiter.\\n //\\n // `whatever` -> `whatever`\\n //\\n const isStrong = i > 0 &&\\n delimiters[i - 1].end === startDelim.end + 1 &&\\n // check that first two markers match and adjacent\\n delimiters[i - 1].marker === startDelim.marker &&\\n delimiters[i - 1].token === startDelim.token - 1 &&\\n // check that last two markers are adjacent (we can safely assume they match)\\n delimiters[startDelim.end + 1].token === endDelim.token + 1\\n\\n const ch = String.fromCharCode(startDelim.marker)\\n\\n const token_o = state.tokens[startDelim.token]\\n token_o.type = isStrong ? 'strong_open' : 'em_open'\\n token_o.tag = isStrong ? 'strong' : 'em'\\n token_o.nesting = 1\\n token_o.markup = isStrong ? ch + ch : ch\\n token_o.content = ''\\n\\n const token_c = state.tokens[endDelim.token]\\n token_c.type = isStrong ? 'strong_close' : 'em_close'\\n token_c.tag = isStrong ? 'strong' : 'em'\\n token_c.nesting = -1\\n token_c.markup = isStrong ? ch + ch : ch\\n token_c.content = ''\\n\\n if (isStrong) {\\n state.tokens[delimiters[i - 1].token].content = ''\\n state.tokens[delimiters[startDelim.end + 1].token].content = ''\\n i--\\n }\\n }\\n}\\n\\n// Walk through delimiter list and replace text tokens with tags\\n//\\nfunction emphasis_post_process (state) {\\n const tokens_meta = state.tokens_meta\\n const max = state.tokens_meta.length\\n\\n postProcess(state, state.delimiters)\\n\\n for (let curr = 0; curr < max; curr++) {\\n if (tokens_meta[curr] && tokens_meta[curr].delimiters) {\\n postProcess(state, tokens_meta[curr].delimiters)\\n }\\n }\\n}\\n\\nexport default {\\n tokenize: emphasis_tokenize,\\n postProcess: emphasis_post_process\\n}\\n\",\"// Process [link]( \\\"stuff\\\")\\n\\nimport { normalizeReference, isSpace } from '../common/utils.mjs'\\n\\nexport default function link (state, silent) {\\n let code, label, res, ref\\n let href = ''\\n let title = ''\\n let start = state.pos\\n let parseReference = true\\n\\n if (state.src.charCodeAt(state.pos) !== 0x5B/* [ */) { return false }\\n\\n const oldPos = state.pos\\n const max = state.posMax\\n const labelStart = state.pos + 1\\n const labelEnd = state.md.helpers.parseLinkLabel(state, state.pos, true)\\n\\n // parser failed to find ']', so it's not a valid link\\n if (labelEnd < 0) { return false }\\n\\n let pos = labelEnd + 1\\n if (pos < max && state.src.charCodeAt(pos) === 0x28/* ( */) {\\n //\\n // Inline link\\n //\\n\\n // might have found a valid shortcut link, disable reference parsing\\n parseReference = false\\n\\n // [link]( \\\"title\\\" )\\n // ^^ skipping these spaces\\n pos++\\n for (; pos < max; pos++) {\\n code = state.src.charCodeAt(pos)\\n if (!isSpace(code) && code !== 0x0A) { break }\\n }\\n if (pos >= max) { return false }\\n\\n // [link]( \\\"title\\\" )\\n // ^^^^^^ parsing link destination\\n start = pos\\n res = state.md.helpers.parseLinkDestination(state.src, pos, state.posMax)\\n if (res.ok) {\\n href = state.md.normalizeLink(res.str)\\n if (state.md.validateLink(href)) {\\n pos = res.pos\\n } else {\\n href = ''\\n }\\n\\n // [link]( \\\"title\\\" )\\n // ^^ skipping these spaces\\n start = pos\\n for (; pos < max; pos++) {\\n code = state.src.charCodeAt(pos)\\n if (!isSpace(code) && code !== 0x0A) { break }\\n }\\n\\n // [link]( \\\"title\\\" )\\n // ^^^^^^^ parsing link title\\n res = state.md.helpers.parseLinkTitle(state.src, pos, state.posMax)\\n if (pos < max && start !== pos && res.ok) {\\n title = res.str\\n pos = res.pos\\n\\n // [link]( \\\"title\\\" )\\n // ^^ skipping these spaces\\n for (; pos < max; pos++) {\\n code = state.src.charCodeAt(pos)\\n if (!isSpace(code) && code !== 0x0A) { break }\\n }\\n }\\n }\\n\\n if (pos >= max || state.src.charCodeAt(pos) !== 0x29/* ) */) {\\n // parsing a valid shortcut link failed, fallback to reference\\n parseReference = true\\n }\\n pos++\\n }\\n\\n if (parseReference) {\\n //\\n // Link reference\\n //\\n if (typeof state.env.references === 'undefined') { return false }\\n\\n if (pos < max && state.src.charCodeAt(pos) === 0x5B/* [ */) {\\n start = pos + 1\\n pos = state.md.helpers.parseLinkLabel(state, pos)\\n if (pos >= 0) {\\n label = state.src.slice(start, pos++)\\n } else {\\n pos = labelEnd + 1\\n }\\n } else {\\n pos = labelEnd + 1\\n }\\n\\n // covers label === '' and label === undefined\\n // (collapsed reference link and shortcut reference link respectively)\\n if (!label) { label = state.src.slice(labelStart, labelEnd) }\\n\\n ref = state.env.references[normalizeReference(label)]\\n if (!ref) {\\n state.pos = oldPos\\n return false\\n }\\n href = ref.href\\n title = ref.title\\n }\\n\\n //\\n // We found the end of the link, and know for a fact it's a valid link;\\n // so all that's left to do is to call tokenizer.\\n //\\n if (!silent) {\\n state.pos = labelStart\\n state.posMax = labelEnd\\n\\n const token_o = state.push('link_open', 'a', 1)\\n const attrs = [['href', href]]\\n token_o.attrs = attrs\\n if (title) {\\n attrs.push(['title', title])\\n }\\n\\n state.linkLevel++\\n state.md.inline.tokenize(state)\\n state.linkLevel--\\n\\n state.push('link_close', 'a', -1)\\n }\\n\\n state.pos = pos\\n state.posMax = max\\n return true\\n}\\n\",\"// Process ![image]( \\\"title\\\")\\n\\nimport { normalizeReference, isSpace } from '../common/utils.mjs'\\n\\nexport default function image (state, silent) {\\n let code, content, label, pos, ref, res, title, start\\n let href = ''\\n const oldPos = state.pos\\n const max = state.posMax\\n\\n if (state.src.charCodeAt(state.pos) !== 0x21/* ! */) { return false }\\n if (state.src.charCodeAt(state.pos + 1) !== 0x5B/* [ */) { return false }\\n\\n const labelStart = state.pos + 2\\n const labelEnd = state.md.helpers.parseLinkLabel(state, state.pos + 1, false)\\n\\n // parser failed to find ']', so it's not a valid link\\n if (labelEnd < 0) { return false }\\n\\n pos = labelEnd + 1\\n if (pos < max && state.src.charCodeAt(pos) === 0x28/* ( */) {\\n //\\n // Inline link\\n //\\n\\n // [link]( \\\"title\\\" )\\n // ^^ skipping these spaces\\n pos++\\n for (; pos < max; pos++) {\\n code = state.src.charCodeAt(pos)\\n if (!isSpace(code) && code !== 0x0A) { break }\\n }\\n if (pos >= max) { return false }\\n\\n // [link]( \\\"title\\\" )\\n // ^^^^^^ parsing link destination\\n start = pos\\n res = state.md.helpers.parseLinkDestination(state.src, pos, state.posMax)\\n if (res.ok) {\\n href = state.md.normalizeLink(res.str)\\n if (state.md.validateLink(href)) {\\n pos = res.pos\\n } else {\\n href = ''\\n }\\n }\\n\\n // [link]( \\\"title\\\" )\\n // ^^ skipping these spaces\\n start = pos\\n for (; pos < max; pos++) {\\n code = state.src.charCodeAt(pos)\\n if (!isSpace(code) && code !== 0x0A) { break }\\n }\\n\\n // [link]( \\\"title\\\" )\\n // ^^^^^^^ parsing link title\\n res = state.md.helpers.parseLinkTitle(state.src, pos, state.posMax)\\n if (pos < max && start !== pos && res.ok) {\\n title = res.str\\n pos = res.pos\\n\\n // [link]( \\\"title\\\" )\\n // ^^ skipping these spaces\\n for (; pos < max; pos++) {\\n code = state.src.charCodeAt(pos)\\n if (!isSpace(code) && code !== 0x0A) { break }\\n }\\n } else {\\n title = ''\\n }\\n\\n if (pos >= max || state.src.charCodeAt(pos) !== 0x29/* ) */) {\\n state.pos = oldPos\\n return false\\n }\\n pos++\\n } else {\\n //\\n // Link reference\\n //\\n if (typeof state.env.references === 'undefined') { return false }\\n\\n if (pos < max && state.src.charCodeAt(pos) === 0x5B/* [ */) {\\n start = pos + 1\\n pos = state.md.helpers.parseLinkLabel(state, pos)\\n if (pos >= 0) {\\n label = state.src.slice(start, pos++)\\n } else {\\n pos = labelEnd + 1\\n }\\n } else {\\n pos = labelEnd + 1\\n }\\n\\n // covers label === '' and label === undefined\\n // (collapsed reference link and shortcut reference link respectively)\\n if (!label) { label = state.src.slice(labelStart, labelEnd) }\\n\\n ref = state.env.references[normalizeReference(label)]\\n if (!ref) {\\n state.pos = oldPos\\n return false\\n }\\n href = ref.href\\n title = ref.title\\n }\\n\\n //\\n // We found the end of the link, and know for a fact it's a valid link;\\n // so all that's left to do is to call tokenizer.\\n //\\n if (!silent) {\\n content = state.src.slice(labelStart, labelEnd)\\n\\n const tokens = []\\n state.md.inline.parse(\\n content,\\n state.md,\\n state.env,\\n tokens\\n )\\n\\n const token = state.push('image', 'img', 0)\\n const attrs = [['src', href], ['alt', '']]\\n token.attrs = attrs\\n token.children = tokens\\n token.content = content\\n\\n if (title) {\\n attrs.push(['title', title])\\n }\\n }\\n\\n state.pos = pos\\n state.posMax = max\\n return true\\n}\\n\",\"// Process autolinks ''\\n\\n/* eslint max-len:0 */\\nconst EMAIL_RE = /^([a-zA-Z0-9.!#$%&'*+/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\\\\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*)$/\\n/* eslint-disable-next-line no-control-regex */\\nconst AUTOLINK_RE = /^([a-zA-Z][a-zA-Z0-9+.-]{1,31}):([^<>\\\\x00-\\\\x20]*)$/\\n\\nexport default function autolink (state, silent) {\\n let pos = state.pos\\n\\n if (state.src.charCodeAt(pos) !== 0x3C/* < */) { return false }\\n\\n const start = state.pos\\n const max = state.posMax\\n\\n for (;;) {\\n if (++pos >= max) return false\\n\\n const ch = state.src.charCodeAt(pos)\\n\\n if (ch === 0x3C /* < */) return false\\n if (ch === 0x3E /* > */) break\\n }\\n\\n const url = state.src.slice(start + 1, pos)\\n\\n if (AUTOLINK_RE.test(url)) {\\n const fullUrl = state.md.normalizeLink(url)\\n if (!state.md.validateLink(fullUrl)) { return false }\\n\\n if (!silent) {\\n const token_o = state.push('link_open', 'a', 1)\\n token_o.attrs = [['href', fullUrl]]\\n token_o.markup = 'autolink'\\n token_o.info = 'auto'\\n\\n const token_t = state.push('text', '', 0)\\n token_t.content = state.md.normalizeLinkText(url)\\n\\n const token_c = state.push('link_close', 'a', -1)\\n token_c.markup = 'autolink'\\n token_c.info = 'auto'\\n }\\n\\n state.pos += url.length + 2\\n return true\\n }\\n\\n if (EMAIL_RE.test(url)) {\\n const fullUrl = state.md.normalizeLink('mailto:' + url)\\n if (!state.md.validateLink(fullUrl)) { return false }\\n\\n if (!silent) {\\n const token_o = state.push('link_open', 'a', 1)\\n token_o.attrs = [['href', fullUrl]]\\n token_o.markup = 'autolink'\\n token_o.info = 'auto'\\n\\n const token_t = state.push('text', '', 0)\\n token_t.content = state.md.normalizeLinkText(url)\\n\\n const token_c = state.push('link_close', 'a', -1)\\n token_c.markup = 'autolink'\\n token_c.info = 'auto'\\n }\\n\\n state.pos += url.length + 2\\n return true\\n }\\n\\n return false\\n}\\n\",\"// Process html tags\\n\\nimport { HTML_TAG_RE } from '../common/html_re.mjs'\\n\\nfunction isLinkOpen (str) {\\n return /^\\\\s]/i.test(str)\\n}\\nfunction isLinkClose (str) {\\n return /^<\\\\/a\\\\s*>/i.test(str)\\n}\\n\\nfunction isLetter (ch) {\\n /* eslint no-bitwise:0 */\\n const lc = ch | 0x20 // to lower case\\n return (lc >= 0x61/* a */) && (lc <= 0x7a/* z */)\\n}\\n\\nexport default function html_inline (state, silent) {\\n if (!state.md.options.html) { return false }\\n\\n // Check start\\n const max = state.posMax\\n const pos = state.pos\\n if (state.src.charCodeAt(pos) !== 0x3C/* < */ ||\\n pos + 2 >= max) {\\n return false\\n }\\n\\n // Quick fail on second char\\n const ch = state.src.charCodeAt(pos + 1)\\n if (ch !== 0x21/* ! */ &&\\n ch !== 0x3F/* ? */ &&\\n ch !== 0x2F/* / */ &&\\n !isLetter(ch)) {\\n return false\\n }\\n\\n const match = state.src.slice(pos).match(HTML_TAG_RE)\\n if (!match) { return false }\\n\\n if (!silent) {\\n const token = state.push('html_inline', '', 0)\\n token.content = match[0]\\n\\n if (isLinkOpen(token.content)) state.linkLevel++\\n if (isLinkClose(token.content)) state.linkLevel--\\n }\\n state.pos += match[0].length\\n return true\\n}\\n\",\"// Process html entity - {, ¯, ", ...\\n\\nimport { decodeHTML } from 'entities'\\nimport { isValidEntityCode, fromCodePoint } from '../common/utils.mjs'\\n\\nconst DIGITAL_RE = /^&#((?:x[a-f0-9]{1,6}|[0-9]{1,7}));/i\\nconst NAMED_RE = /^&([a-z][a-z0-9]{1,31});/i\\n\\nexport default function entity (state, silent) {\\n const pos = state.pos\\n const max = state.posMax\\n\\n if (state.src.charCodeAt(pos) !== 0x26/* & */) return false\\n\\n if (pos + 1 >= max) return false\\n\\n const ch = state.src.charCodeAt(pos + 1)\\n\\n if (ch === 0x23 /* # */) {\\n const match = state.src.slice(pos).match(DIGITAL_RE)\\n if (match) {\\n if (!silent) {\\n const code = match[1][0].toLowerCase() === 'x' ? parseInt(match[1].slice(1), 16) : parseInt(match[1], 10)\\n\\n const token = state.push('text_special', '', 0)\\n token.content = isValidEntityCode(code) ? fromCodePoint(code) : fromCodePoint(0xFFFD)\\n token.markup = match[0]\\n token.info = 'entity'\\n }\\n state.pos += match[0].length\\n return true\\n }\\n } else {\\n const match = state.src.slice(pos).match(NAMED_RE)\\n if (match) {\\n const decoded = decodeHTML(match[0])\\n if (decoded !== match[0]) {\\n if (!silent) {\\n const token = state.push('text_special', '', 0)\\n token.content = decoded\\n token.markup = match[0]\\n token.info = 'entity'\\n }\\n state.pos += match[0].length\\n return true\\n }\\n }\\n }\\n\\n return false\\n}\\n\",\"// For each opening emphasis-like marker find a matching closing one\\n//\\n\\nfunction processDelimiters (delimiters) {\\n const openersBottom = {}\\n const max = delimiters.length\\n\\n if (!max) return\\n\\n // headerIdx is the first delimiter of the current (where closer is) delimiter run\\n let headerIdx = 0\\n let lastTokenIdx = -2 // needs any value lower than -1\\n const jumps = []\\n\\n for (let closerIdx = 0; closerIdx < max; closerIdx++) {\\n const closer = delimiters[closerIdx]\\n\\n jumps.push(0)\\n\\n // markers belong to same delimiter run if:\\n // - they have adjacent tokens\\n // - AND markers are the same\\n //\\n if (delimiters[headerIdx].marker !== closer.marker || lastTokenIdx !== closer.token - 1) {\\n headerIdx = closerIdx\\n }\\n\\n lastTokenIdx = closer.token\\n\\n // Length is only used for emphasis-specific \\\"rule of 3\\\",\\n // if it's not defined (in strikethrough or 3rd party plugins),\\n // we can default it to 0 to disable those checks.\\n //\\n closer.length = closer.length || 0\\n\\n if (!closer.close) continue\\n\\n // Previously calculated lower bounds (previous fails)\\n // for each marker, each delimiter length modulo 3,\\n // and for whether this closer can be an opener;\\n // https://github.com/commonmark/cmark/commit/34250e12ccebdc6372b8b49c44fab57c72443460\\n /* eslint-disable-next-line no-prototype-builtins */\\n if (!openersBottom.hasOwnProperty(closer.marker)) {\\n openersBottom[closer.marker] = [-1, -1, -1, -1, -1, -1]\\n }\\n\\n const minOpenerIdx = openersBottom[closer.marker][(closer.open ? 3 : 0) + (closer.length % 3)]\\n\\n let openerIdx = headerIdx - jumps[headerIdx] - 1\\n\\n let newMinOpenerIdx = openerIdx\\n\\n for (; openerIdx > minOpenerIdx; openerIdx -= jumps[openerIdx] + 1) {\\n const opener = delimiters[openerIdx]\\n\\n if (opener.marker !== closer.marker) continue\\n\\n if (opener.open && opener.end < 0) {\\n let isOddMatch = false\\n\\n // from spec:\\n //\\n // If one of the delimiters can both open and close emphasis, then the\\n // sum of the lengths of the delimiter runs containing the opening and\\n // closing delimiters must not be a multiple of 3 unless both lengths\\n // are multiples of 3.\\n //\\n if (opener.close || closer.open) {\\n if ((opener.length + closer.length) % 3 === 0) {\\n if (opener.length % 3 !== 0 || closer.length % 3 !== 0) {\\n isOddMatch = true\\n }\\n }\\n }\\n\\n if (!isOddMatch) {\\n // If previous delimiter cannot be an opener, we can safely skip\\n // the entire sequence in future checks. This is required to make\\n // sure algorithm has linear complexity (see *_*_*_*_*_... case).\\n //\\n const lastJump = openerIdx > 0 && !delimiters[openerIdx - 1].open\\n ? jumps[openerIdx - 1] + 1\\n : 0\\n\\n jumps[closerIdx] = closerIdx - openerIdx + lastJump\\n jumps[openerIdx] = lastJump\\n\\n closer.open = false\\n opener.end = closerIdx\\n opener.close = false\\n newMinOpenerIdx = -1\\n // treat next token as start of run,\\n // it optimizes skips in **<...>**a**<...>** pathological case\\n lastTokenIdx = -2\\n break\\n }\\n }\\n }\\n\\n if (newMinOpenerIdx !== -1) {\\n // If match for this delimiter run failed, we want to set lower bound for\\n // future lookups. This is required to make sure algorithm has linear\\n // complexity.\\n //\\n // See details here:\\n // https://github.com/commonmark/cmark/issues/178#issuecomment-270417442\\n //\\n openersBottom[closer.marker][(closer.open ? 3 : 0) + ((closer.length || 0) % 3)] = newMinOpenerIdx\\n }\\n }\\n}\\n\\nexport default function link_pairs (state) {\\n const tokens_meta = state.tokens_meta\\n const max = state.tokens_meta.length\\n\\n processDelimiters(state.delimiters)\\n\\n for (let curr = 0; curr < max; curr++) {\\n if (tokens_meta[curr] && tokens_meta[curr].delimiters) {\\n processDelimiters(tokens_meta[curr].delimiters)\\n }\\n }\\n}\\n\",\"// Clean up tokens after emphasis and strikethrough postprocessing:\\n// merge adjacent text nodes into one and re-calculate all token levels\\n//\\n// This is necessary because initially emphasis delimiter markers (*, _, ~)\\n// are treated as their own separate text tokens. Then emphasis rule either\\n// leaves them as text (needed to merge with adjacent text) or turns them\\n// into opening/closing tags (which messes up levels inside).\\n//\\n\\nexport default function fragments_join (state) {\\n let curr, last\\n let level = 0\\n const tokens = state.tokens\\n const max = state.tokens.length\\n\\n for (curr = last = 0; curr < max; curr++) {\\n // re-calculate levels after emphasis/strikethrough turns some text nodes\\n // into opening/closing tags\\n if (tokens[curr].nesting < 0) level-- // closing tag\\n tokens[curr].level = level\\n if (tokens[curr].nesting > 0) level++ // opening tag\\n\\n if (tokens[curr].type === 'text' &&\\n curr + 1 < max &&\\n tokens[curr + 1].type === 'text') {\\n // collapse two adjacent text nodes\\n tokens[curr + 1].content = tokens[curr].content + tokens[curr + 1].content\\n } else {\\n if (curr !== last) { tokens[last] = tokens[curr] }\\n\\n last++\\n }\\n }\\n\\n if (curr !== last) {\\n tokens.length = last\\n }\\n}\\n\",\"/** internal\\n * class ParserInline\\n *\\n * Tokenizes paragraph content.\\n **/\\n\\nimport Ruler from './ruler.mjs'\\nimport StateInline from './rules_inline/state_inline.mjs'\\n\\nimport r_text from './rules_inline/text.mjs'\\nimport r_linkify from './rules_inline/linkify.mjs'\\nimport r_newline from './rules_inline/newline.mjs'\\nimport r_escape from './rules_inline/escape.mjs'\\nimport r_backticks from './rules_inline/backticks.mjs'\\nimport r_strikethrough from './rules_inline/strikethrough.mjs'\\nimport r_emphasis from './rules_inline/emphasis.mjs'\\nimport r_link from './rules_inline/link.mjs'\\nimport r_image from './rules_inline/image.mjs'\\nimport r_autolink from './rules_inline/autolink.mjs'\\nimport r_html_inline from './rules_inline/html_inline.mjs'\\nimport r_entity from './rules_inline/entity.mjs'\\n\\nimport r_balance_pairs from './rules_inline/balance_pairs.mjs'\\nimport r_fragments_join from './rules_inline/fragments_join.mjs'\\n\\n// Parser rules\\n\\nconst _rules = [\\n ['text', r_text],\\n ['linkify', r_linkify],\\n ['newline', r_newline],\\n ['escape', r_escape],\\n ['backticks', r_backticks],\\n ['strikethrough', r_strikethrough.tokenize],\\n ['emphasis', r_emphasis.tokenize],\\n ['link', r_link],\\n ['image', r_image],\\n ['autolink', r_autolink],\\n ['html_inline', r_html_inline],\\n ['entity', r_entity]\\n]\\n\\n// `rule2` ruleset was created specifically for emphasis/strikethrough\\n// post-processing and may be changed in the future.\\n//\\n// Don't use this for anything except pairs (plugins working with `balance_pairs`).\\n//\\nconst _rules2 = [\\n ['balance_pairs', r_balance_pairs],\\n ['strikethrough', r_strikethrough.postProcess],\\n ['emphasis', r_emphasis.postProcess],\\n // rules for pairs separate '**' into its own text tokens, which may be left unused,\\n // rule below merges unused segments back with the rest of the text\\n ['fragments_join', r_fragments_join]\\n]\\n\\n/**\\n * new ParserInline()\\n **/\\nfunction ParserInline () {\\n /**\\n * ParserInline#ruler -> Ruler\\n *\\n * [[Ruler]] instance. Keep configuration of inline rules.\\n **/\\n this.ruler = new Ruler()\\n\\n for (let i = 0; i < _rules.length; i++) {\\n this.ruler.push(_rules[i][0], _rules[i][1])\\n }\\n\\n /**\\n * ParserInline#ruler2 -> Ruler\\n *\\n * [[Ruler]] instance. Second ruler used for post-processing\\n * (e.g. in emphasis-like rules).\\n **/\\n this.ruler2 = new Ruler()\\n\\n for (let i = 0; i < _rules2.length; i++) {\\n this.ruler2.push(_rules2[i][0], _rules2[i][1])\\n }\\n}\\n\\n// Skip single token by running all rules in validation mode;\\n// returns `true` if any rule reported success\\n//\\nParserInline.prototype.skipToken = function (state) {\\n const pos = state.pos\\n const rules = this.ruler.getRules('')\\n const len = rules.length\\n const maxNesting = state.md.options.maxNesting\\n const cache = state.cache\\n\\n if (typeof cache[pos] !== 'undefined') {\\n state.pos = cache[pos]\\n return\\n }\\n\\n let ok = false\\n\\n if (state.level < maxNesting) {\\n for (let i = 0; i < len; i++) {\\n // Increment state.level and decrement it later to limit recursion.\\n // It's harmless to do here, because no tokens are created. But ideally,\\n // we'd need a separate private state variable for this purpose.\\n //\\n state.level++\\n ok = rules[i](state, true)\\n state.level--\\n\\n if (ok) {\\n if (pos >= state.pos) { throw new Error(\\\"inline rule didn't increment state.pos\\\") }\\n break\\n }\\n }\\n } else {\\n // Too much nesting, just skip until the end of the paragraph.\\n //\\n // NOTE: this will cause links to behave incorrectly in the following case,\\n // when an amount of `[` is exactly equal to `maxNesting + 1`:\\n //\\n // [[[[[[[[[[[[[[[[[[[[[foo]()\\n //\\n // TODO: remove this workaround when CM standard will allow nested links\\n // (we can replace it by preventing links from being parsed in\\n // validation mode)\\n //\\n state.pos = state.posMax\\n }\\n\\n if (!ok) { state.pos++ }\\n cache[pos] = state.pos\\n}\\n\\n// Generate tokens for input range\\n//\\nParserInline.prototype.tokenize = function (state) {\\n const rules = this.ruler.getRules('')\\n const len = rules.length\\n const end = state.posMax\\n const maxNesting = state.md.options.maxNesting\\n\\n while (state.pos < end) {\\n // Try all possible rules.\\n // On success, rule should:\\n //\\n // - update `state.pos`\\n // - update `state.tokens`\\n // - return true\\n const prevPos = state.pos\\n let ok = false\\n\\n if (state.level < maxNesting) {\\n for (let i = 0; i < len; i++) {\\n ok = rules[i](state, false)\\n if (ok) {\\n if (prevPos >= state.pos) { throw new Error(\\\"inline rule didn't increment state.pos\\\") }\\n break\\n }\\n }\\n }\\n\\n if (ok) {\\n if (state.pos >= end) { break }\\n continue\\n }\\n\\n state.pending += state.src[state.pos++]\\n }\\n\\n if (state.pending) {\\n state.pushPending()\\n }\\n}\\n\\n/**\\n * ParserInline.parse(str, md, env, outTokens)\\n *\\n * Process input string and push inline tokens into `outTokens`\\n **/\\nParserInline.prototype.parse = function (str, md, env, outTokens) {\\n const state = new this.State(str, md, env, outTokens)\\n\\n this.tokenize(state)\\n\\n const rules = this.ruler2.getRules('')\\n const len = rules.length\\n\\n for (let i = 0; i < len; i++) {\\n rules[i](state)\\n }\\n}\\n\\nParserInline.prototype.State = StateInline\\n\\nexport default ParserInline\\n\",\"import { Any, Cc, Z, P } from 'uc.micro'\\n\\nexport default function (opts) {\\n const re = {}\\n opts = opts || {}\\n\\n re.src_Any = Any.source\\n re.src_Cc = Cc.source\\n re.src_Z = Z.source\\n re.src_P = P.source\\n\\n // \\\\p{\\\\Z\\\\P\\\\Cc\\\\CF} (white spaces + control + format + punctuation)\\n re.src_ZPCc = [re.src_Z, re.src_P, re.src_Cc].join('|')\\n\\n // \\\\p{\\\\Z\\\\Cc} (white spaces + control)\\n re.src_ZCc = [re.src_Z, re.src_Cc].join('|')\\n\\n // Experimental. List of chars, completely prohibited in links\\n // because can separate it from other part of text\\n const text_separators = '[><\\\\uff5c]'\\n\\n // All possible word characters (everything without punctuation, spaces & controls)\\n // Defined via punctuation & spaces to save space\\n // Should be something like \\\\p{\\\\L\\\\N\\\\S\\\\M} (\\\\w but without `_`)\\n re.src_pseudo_letter = '(?:(?!' + text_separators + '|' + re.src_ZPCc + ')' + re.src_Any + ')'\\n // The same as abothe but without [0-9]\\n // var src_pseudo_letter_non_d = '(?:(?![0-9]|' + src_ZPCc + ')' + src_Any + ')';\\n\\n re.src_ip4 =\\n\\n '(?:(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\\\\\\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)'\\n\\n // Prohibit any of \\\"@/[]()\\\" in user/pass to avoid wrong domain fetch.\\n re.src_auth = '(?:(?:(?!' + re.src_ZCc + '|[@/\\\\\\\\[\\\\\\\\]()]).)+@)?'\\n\\n re.src_port =\\n\\n '(?::(?:6(?:[0-4]\\\\\\\\d{3}|5(?:[0-4]\\\\\\\\d{2}|5(?:[0-2]\\\\\\\\d|3[0-5])))|[1-5]?\\\\\\\\d{1,4}))?'\\n\\n re.src_host_terminator =\\n\\n '(?=$|' + text_separators + '|' + re.src_ZPCc + ')' +\\n '(?!' + (opts['---'] ? '-(?!--)|' : '-|') + '_|:\\\\\\\\d|\\\\\\\\.-|\\\\\\\\.(?!$|' + re.src_ZPCc + '))'\\n\\n re.src_path =\\n\\n '(?:' +\\n '[/?#]' +\\n '(?:' +\\n '(?!' + re.src_ZCc + '|' + text_separators + '|[()[\\\\\\\\]{}.,\\\"\\\\'?!\\\\\\\\-;]).|' +\\n '\\\\\\\\[(?:(?!' + re.src_ZCc + '|\\\\\\\\]).)*\\\\\\\\]|' +\\n '\\\\\\\\((?:(?!' + re.src_ZCc + '|[)]).)*\\\\\\\\)|' +\\n '\\\\\\\\{(?:(?!' + re.src_ZCc + '|[}]).)*\\\\\\\\}|' +\\n '\\\\\\\\\\\"(?:(?!' + re.src_ZCc + '|[\\\"]).)+\\\\\\\\\\\"|' +\\n \\\"\\\\\\\\'(?:(?!\\\" + re.src_ZCc + \\\"|[']).)+\\\\\\\\'|\\\" +\\n\\n // allow `I'm_king` if no pair found\\n \\\"\\\\\\\\'(?=\\\" + re.src_pseudo_letter + '|[-])|' +\\n\\n // google has many dots in \\\"google search\\\" links (#66, #81).\\n // github has ... in commit range links,\\n // Restrict to\\n // - english\\n // - percent-encoded\\n // - parts of file path\\n // - params separator\\n // until more examples found.\\n '\\\\\\\\.{2,}[a-zA-Z0-9%/&]|' +\\n\\n '\\\\\\\\.(?!' + re.src_ZCc + '|[.]|$)|' +\\n (opts['---']\\n ? '\\\\\\\\-(?!--(?:[^-]|$))(?:-*)|' // `---` => long dash, terminate\\n : '\\\\\\\\-+|'\\n ) +\\n // allow `,,,` in paths\\n ',(?!' + re.src_ZCc + '|$)|' +\\n\\n // allow `;` if not followed by space-like char\\n ';(?!' + re.src_ZCc + '|$)|' +\\n\\n // allow `!!!` in paths, but not at the end\\n '\\\\\\\\!+(?!' + re.src_ZCc + '|[!]|$)|' +\\n\\n '\\\\\\\\?(?!' + re.src_ZCc + '|[?]|$)' +\\n ')+' +\\n '|\\\\\\\\/' +\\n ')?'\\n\\n // Allow anything in markdown spec, forbid quote (\\\") at the first position\\n // because emails enclosed in quotes are far more common\\n re.src_email_name =\\n\\n '[\\\\\\\\-;:&=\\\\\\\\+\\\\\\\\$,\\\\\\\\.a-zA-Z0-9_][\\\\\\\\-;:&=\\\\\\\\+\\\\\\\\$,\\\\\\\\\\\"\\\\\\\\.a-zA-Z0-9_]*'\\n\\n re.src_xn =\\n\\n 'xn--[a-z0-9\\\\\\\\-]{1,59}'\\n\\n // More to read about domain names\\n // http://serverfault.com/questions/638260/\\n\\n re.src_domain_root =\\n\\n // Allow letters & digits (http://test1)\\n '(?:' +\\n re.src_xn +\\n '|' +\\n re.src_pseudo_letter + '{1,63}' +\\n ')'\\n\\n re.src_domain =\\n\\n '(?:' +\\n re.src_xn +\\n '|' +\\n '(?:' + re.src_pseudo_letter + ')' +\\n '|' +\\n '(?:' + re.src_pseudo_letter + '(?:-|' + re.src_pseudo_letter + '){0,61}' + re.src_pseudo_letter + ')' +\\n ')'\\n\\n re.src_host =\\n\\n '(?:' +\\n // Don't need IP check, because digits are already allowed in normal domain names\\n // src_ip4 +\\n // '|' +\\n '(?:(?:(?:' + re.src_domain + ')\\\\\\\\.)*' + re.src_domain/* _root */ + ')' +\\n ')'\\n\\n re.tpl_host_fuzzy =\\n\\n '(?:' +\\n re.src_ip4 +\\n '|' +\\n '(?:(?:(?:' + re.src_domain + ')\\\\\\\\.)+(?:%TLDS%))' +\\n ')'\\n\\n re.tpl_host_no_ip_fuzzy =\\n\\n '(?:(?:(?:' + re.src_domain + ')\\\\\\\\.)+(?:%TLDS%))'\\n\\n re.src_host_strict =\\n\\n re.src_host + re.src_host_terminator\\n\\n re.tpl_host_fuzzy_strict =\\n\\n re.tpl_host_fuzzy + re.src_host_terminator\\n\\n re.src_host_port_strict =\\n\\n re.src_host + re.src_port + re.src_host_terminator\\n\\n re.tpl_host_port_fuzzy_strict =\\n\\n re.tpl_host_fuzzy + re.src_port + re.src_host_terminator\\n\\n re.tpl_host_port_no_ip_fuzzy_strict =\\n\\n re.tpl_host_no_ip_fuzzy + re.src_port + re.src_host_terminator\\n\\n //\\n // Main rules\\n //\\n\\n // Rude test fuzzy links by host, for quick deny\\n re.tpl_host_fuzzy_test =\\n\\n 'localhost|www\\\\\\\\.|\\\\\\\\.\\\\\\\\d{1,3}\\\\\\\\.|(?:\\\\\\\\.(?:%TLDS%)(?:' + re.src_ZPCc + '|>|$))'\\n\\n re.tpl_email_fuzzy =\\n\\n '(^|' + text_separators + '|\\\"|\\\\\\\\(|' + re.src_ZCc + ')' +\\n '(' + re.src_email_name + '@' + re.tpl_host_fuzzy_strict + ')'\\n\\n re.tpl_link_fuzzy =\\n // Fuzzy link can't be prepended with .:/\\\\- and non punctuation.\\n // but can start with > (markdown blockquote)\\n '(^|(?![.:/\\\\\\\\-_@])(?:[$+<=>^`|\\\\uff5c]|' + re.src_ZPCc + '))' +\\n '((?![$+<=>^`|\\\\uff5c])' + re.tpl_host_port_fuzzy_strict + re.src_path + ')'\\n\\n re.tpl_link_no_ip_fuzzy =\\n // Fuzzy link can't be prepended with .:/\\\\- and non punctuation.\\n // but can start with > (markdown blockquote)\\n '(^|(?![.:/\\\\\\\\-_@])(?:[$+<=>^`|\\\\uff5c]|' + re.src_ZPCc + '))' +\\n '((?![$+<=>^`|\\\\uff5c])' + re.tpl_host_port_no_ip_fuzzy_strict + re.src_path + ')'\\n\\n return re\\n}\\n\",\"import reFactory from './lib/re.mjs'\\n\\n//\\n// Helpers\\n//\\n\\n// Merge objects\\n//\\nfunction assign (obj /* from1, from2, from3, ... */) {\\n const sources = Array.prototype.slice.call(arguments, 1)\\n\\n sources.forEach(function (source) {\\n if (!source) { return }\\n\\n Object.keys(source).forEach(function (key) {\\n obj[key] = source[key]\\n })\\n })\\n\\n return obj\\n}\\n\\nfunction _class (obj) { return Object.prototype.toString.call(obj) }\\nfunction isString (obj) { return _class(obj) === '[object String]' }\\nfunction isObject (obj) { return _class(obj) === '[object Object]' }\\nfunction isRegExp (obj) { return _class(obj) === '[object RegExp]' }\\nfunction isFunction (obj) { return _class(obj) === '[object Function]' }\\n\\nfunction escapeRE (str) { return str.replace(/[.?*+^$[\\\\]\\\\\\\\(){}|-]/g, '\\\\\\\\$&') }\\n\\n//\\n\\nconst defaultOptions = {\\n fuzzyLink: true,\\n fuzzyEmail: true,\\n fuzzyIP: false\\n}\\n\\nfunction isOptionsObj (obj) {\\n return Object.keys(obj || {}).reduce(function (acc, k) {\\n /* eslint-disable-next-line no-prototype-builtins */\\n return acc || defaultOptions.hasOwnProperty(k)\\n }, false)\\n}\\n\\nconst defaultSchemas = {\\n 'http:': {\\n validate: function (text, pos, self) {\\n const tail = text.slice(pos)\\n\\n if (!self.re.http) {\\n // compile lazily, because \\\"host\\\"-containing variables can change on tlds update.\\n self.re.http = new RegExp(\\n '^\\\\\\\\/\\\\\\\\/' + self.re.src_auth + self.re.src_host_port_strict + self.re.src_path, 'i'\\n )\\n }\\n if (self.re.http.test(tail)) {\\n return tail.match(self.re.http)[0].length\\n }\\n return 0\\n }\\n },\\n 'https:': 'http:',\\n 'ftp:': 'http:',\\n '//': {\\n validate: function (text, pos, self) {\\n const tail = text.slice(pos)\\n\\n if (!self.re.no_http) {\\n // compile lazily, because \\\"host\\\"-containing variables can change on tlds update.\\n self.re.no_http = new RegExp(\\n '^' +\\n self.re.src_auth +\\n // Don't allow single-level domains, because of false positives like '//test'\\n // with code comments\\n '(?:localhost|(?:(?:' + self.re.src_domain + ')\\\\\\\\.)+' + self.re.src_domain_root + ')' +\\n self.re.src_port +\\n self.re.src_host_terminator +\\n self.re.src_path,\\n\\n 'i'\\n )\\n }\\n\\n if (self.re.no_http.test(tail)) {\\n // should not be `://` & `///`, that protects from errors in protocol name\\n if (pos >= 3 && text[pos - 3] === ':') { return 0 }\\n if (pos >= 3 && text[pos - 3] === '/') { return 0 }\\n return tail.match(self.re.no_http)[0].length\\n }\\n return 0\\n }\\n },\\n 'mailto:': {\\n validate: function (text, pos, self) {\\n const tail = text.slice(pos)\\n\\n if (!self.re.mailto) {\\n self.re.mailto = new RegExp(\\n '^' + self.re.src_email_name + '@' + self.re.src_host_strict, 'i'\\n )\\n }\\n if (self.re.mailto.test(tail)) {\\n return tail.match(self.re.mailto)[0].length\\n }\\n return 0\\n }\\n }\\n}\\n\\n// RE pattern for 2-character tlds (autogenerated by ./support/tlds_2char_gen.js)\\n/* eslint-disable-next-line max-len */\\nconst tlds_2ch_src_re = 'a[cdefgilmnoqrstuwxz]|b[abdefghijmnorstvwyz]|c[acdfghiklmnoruvwxyz]|d[ejkmoz]|e[cegrstu]|f[ijkmor]|g[abdefghilmnpqrstuwy]|h[kmnrtu]|i[delmnoqrst]|j[emop]|k[eghimnprwyz]|l[abcikrstuvy]|m[acdeghklmnopqrstuvwxyz]|n[acefgilopruz]|om|p[aefghklmnrstwy]|qa|r[eosuw]|s[abcdeghijklmnortuvxyz]|t[cdfghjklmnortvwz]|u[agksyz]|v[aceginu]|w[fs]|y[et]|z[amw]'\\n\\n// DON'T try to make PRs with changes. Extend TLDs with LinkifyIt.tlds() instead\\nconst tlds_default = 'biz|com|edu|gov|net|org|pro|web|xxx|aero|asia|coop|info|museum|name|shop|рф'.split('|')\\n\\nfunction resetScanCache (self) {\\n self.__index__ = -1\\n self.__text_cache__ = ''\\n}\\n\\nfunction createValidator (re) {\\n return function (text, pos) {\\n const tail = text.slice(pos)\\n\\n if (re.test(tail)) {\\n return tail.match(re)[0].length\\n }\\n return 0\\n }\\n}\\n\\nfunction createNormalizer () {\\n return function (match, self) {\\n self.normalize(match)\\n }\\n}\\n\\n// Schemas compiler. Build regexps.\\n//\\nfunction compile (self) {\\n // Load & clone RE patterns.\\n const re = self.re = reFactory(self.__opts__)\\n\\n // Define dynamic patterns\\n const tlds = self.__tlds__.slice()\\n\\n self.onCompile()\\n\\n if (!self.__tlds_replaced__) {\\n tlds.push(tlds_2ch_src_re)\\n }\\n tlds.push(re.src_xn)\\n\\n re.src_tlds = tlds.join('|')\\n\\n function untpl (tpl) { return tpl.replace('%TLDS%', re.src_tlds) }\\n\\n re.email_fuzzy = RegExp(untpl(re.tpl_email_fuzzy), 'i')\\n re.link_fuzzy = RegExp(untpl(re.tpl_link_fuzzy), 'i')\\n re.link_no_ip_fuzzy = RegExp(untpl(re.tpl_link_no_ip_fuzzy), 'i')\\n re.host_fuzzy_test = RegExp(untpl(re.tpl_host_fuzzy_test), 'i')\\n\\n //\\n // Compile each schema\\n //\\n\\n const aliases = []\\n\\n self.__compiled__ = {} // Reset compiled data\\n\\n function schemaError (name, val) {\\n throw new Error('(LinkifyIt) Invalid schema \\\"' + name + '\\\": ' + val)\\n }\\n\\n Object.keys(self.__schemas__).forEach(function (name) {\\n const val = self.__schemas__[name]\\n\\n // skip disabled methods\\n if (val === null) { return }\\n\\n const compiled = { validate: null, link: null }\\n\\n self.__compiled__[name] = compiled\\n\\n if (isObject(val)) {\\n if (isRegExp(val.validate)) {\\n compiled.validate = createValidator(val.validate)\\n } else if (isFunction(val.validate)) {\\n compiled.validate = val.validate\\n } else {\\n schemaError(name, val)\\n }\\n\\n if (isFunction(val.normalize)) {\\n compiled.normalize = val.normalize\\n } else if (!val.normalize) {\\n compiled.normalize = createNormalizer()\\n } else {\\n schemaError(name, val)\\n }\\n\\n return\\n }\\n\\n if (isString(val)) {\\n aliases.push(name)\\n return\\n }\\n\\n schemaError(name, val)\\n })\\n\\n //\\n // Compile postponed aliases\\n //\\n\\n aliases.forEach(function (alias) {\\n if (!self.__compiled__[self.__schemas__[alias]]) {\\n // Silently fail on missed schemas to avoid errons on disable.\\n // schemaError(alias, self.__schemas__[alias]);\\n return\\n }\\n\\n self.__compiled__[alias].validate =\\n self.__compiled__[self.__schemas__[alias]].validate\\n self.__compiled__[alias].normalize =\\n self.__compiled__[self.__schemas__[alias]].normalize\\n })\\n\\n //\\n // Fake record for guessed links\\n //\\n self.__compiled__[''] = { validate: null, normalize: createNormalizer() }\\n\\n //\\n // Build schema condition\\n //\\n const slist = Object.keys(self.__compiled__)\\n .filter(function (name) {\\n // Filter disabled & fake schemas\\n return name.length > 0 && self.__compiled__[name]\\n })\\n .map(escapeRE)\\n .join('|')\\n // (?!_) cause 1.5x slowdown\\n self.re.schema_test = RegExp('(^|(?!_)(?:[><\\\\uff5c]|' + re.src_ZPCc + '))(' + slist + ')', 'i')\\n self.re.schema_search = RegExp('(^|(?!_)(?:[><\\\\uff5c]|' + re.src_ZPCc + '))(' + slist + ')', 'ig')\\n self.re.schema_at_start = RegExp('^' + self.re.schema_search.source, 'i')\\n\\n self.re.pretest = RegExp(\\n '(' + self.re.schema_test.source + ')|(' + self.re.host_fuzzy_test.source + ')|@',\\n 'i'\\n )\\n\\n //\\n // Cleanup\\n //\\n\\n resetScanCache(self)\\n}\\n\\n/**\\n * class Match\\n *\\n * Match result. Single element of array, returned by [[LinkifyIt#match]]\\n **/\\nfunction Match (self, shift) {\\n const start = self.__index__\\n const end = self.__last_index__\\n const text = self.__text_cache__.slice(start, end)\\n\\n /**\\n * Match#schema -> String\\n *\\n * Prefix (protocol) for matched string.\\n **/\\n this.schema = self.__schema__.toLowerCase()\\n /**\\n * Match#index -> Number\\n *\\n * First position of matched string.\\n **/\\n this.index = start + shift\\n /**\\n * Match#lastIndex -> Number\\n *\\n * Next position after matched string.\\n **/\\n this.lastIndex = end + shift\\n /**\\n * Match#raw -> String\\n *\\n * Matched string.\\n **/\\n this.raw = text\\n /**\\n * Match#text -> String\\n *\\n * Notmalized text of matched string.\\n **/\\n this.text = text\\n /**\\n * Match#url -> String\\n *\\n * Normalized url of matched string.\\n **/\\n this.url = text\\n}\\n\\nfunction createMatch (self, shift) {\\n const match = new Match(self, shift)\\n\\n self.__compiled__[match.schema].normalize(match, self)\\n\\n return match\\n}\\n\\n/**\\n * class LinkifyIt\\n **/\\n\\n/**\\n * new LinkifyIt(schemas, options)\\n * - schemas (Object): Optional. Additional schemas to validate (prefix/validator)\\n * - options (Object): { fuzzyLink|fuzzyEmail|fuzzyIP: true|false }\\n *\\n * Creates new linkifier instance with optional additional schemas.\\n * Can be called without `new` keyword for convenience.\\n *\\n * By default understands:\\n *\\n * - `http(s)://...` , `ftp://...`, `mailto:...` & `//...` links\\n * - \\\"fuzzy\\\" links and emails (example.com, foo@bar.com).\\n *\\n * `schemas` is an object, where each key/value describes protocol/rule:\\n *\\n * - __key__ - link prefix (usually, protocol name with `:` at the end, `skype:`\\n * for example). `linkify-it` makes shure that prefix is not preceeded with\\n * alphanumeric char and symbols. Only whitespaces and punctuation allowed.\\n * - __value__ - rule to check tail after link prefix\\n * - _String_ - just alias to existing rule\\n * - _Object_\\n * - _validate_ - validator function (should return matched length on success),\\n * or `RegExp`.\\n * - _normalize_ - optional function to normalize text & url of matched result\\n * (for example, for @twitter mentions).\\n *\\n * `options`:\\n *\\n * - __fuzzyLink__ - recognige URL-s without `http(s):` prefix. Default `true`.\\n * - __fuzzyIP__ - allow IPs in fuzzy links above. Can conflict with some texts\\n * like version numbers. Default `false`.\\n * - __fuzzyEmail__ - recognize emails without `mailto:` prefix.\\n *\\n **/\\nfunction LinkifyIt (schemas, options) {\\n if (!(this instanceof LinkifyIt)) {\\n return new LinkifyIt(schemas, options)\\n }\\n\\n if (!options) {\\n if (isOptionsObj(schemas)) {\\n options = schemas\\n schemas = {}\\n }\\n }\\n\\n this.__opts__ = assign({}, defaultOptions, options)\\n\\n // Cache last tested result. Used to skip repeating steps on next `match` call.\\n this.__index__ = -1\\n this.__last_index__ = -1 // Next scan position\\n this.__schema__ = ''\\n this.__text_cache__ = ''\\n\\n this.__schemas__ = assign({}, defaultSchemas, schemas)\\n this.__compiled__ = {}\\n\\n this.__tlds__ = tlds_default\\n this.__tlds_replaced__ = false\\n\\n this.re = {}\\n\\n compile(this)\\n}\\n\\n/** chainable\\n * LinkifyIt#add(schema, definition)\\n * - schema (String): rule name (fixed pattern prefix)\\n * - definition (String|RegExp|Object): schema definition\\n *\\n * Add new rule definition. See constructor description for details.\\n **/\\nLinkifyIt.prototype.add = function add (schema, definition) {\\n this.__schemas__[schema] = definition\\n compile(this)\\n return this\\n}\\n\\n/** chainable\\n * LinkifyIt#set(options)\\n * - options (Object): { fuzzyLink|fuzzyEmail|fuzzyIP: true|false }\\n *\\n * Set recognition options for links without schema.\\n **/\\nLinkifyIt.prototype.set = function set (options) {\\n this.__opts__ = assign(this.__opts__, options)\\n return this\\n}\\n\\n/**\\n * LinkifyIt#test(text) -> Boolean\\n *\\n * Searches linkifiable pattern and returns `true` on success or `false` on fail.\\n **/\\nLinkifyIt.prototype.test = function test (text) {\\n // Reset scan cache\\n this.__text_cache__ = text\\n this.__index__ = -1\\n\\n if (!text.length) { return false }\\n\\n let m, ml, me, len, shift, next, re, tld_pos, at_pos\\n\\n // try to scan for link with schema - that's the most simple rule\\n if (this.re.schema_test.test(text)) {\\n re = this.re.schema_search\\n re.lastIndex = 0\\n while ((m = re.exec(text)) !== null) {\\n len = this.testSchemaAt(text, m[2], re.lastIndex)\\n if (len) {\\n this.__schema__ = m[2]\\n this.__index__ = m.index + m[1].length\\n this.__last_index__ = m.index + m[0].length + len\\n break\\n }\\n }\\n }\\n\\n if (this.__opts__.fuzzyLink && this.__compiled__['http:']) {\\n // guess schemaless links\\n tld_pos = text.search(this.re.host_fuzzy_test)\\n if (tld_pos >= 0) {\\n // if tld is located after found link - no need to check fuzzy pattern\\n if (this.__index__ < 0 || tld_pos < this.__index__) {\\n if ((ml = text.match(this.__opts__.fuzzyIP ? this.re.link_fuzzy : this.re.link_no_ip_fuzzy)) !== null) {\\n shift = ml.index + ml[1].length\\n\\n if (this.__index__ < 0 || shift < this.__index__) {\\n this.__schema__ = ''\\n this.__index__ = shift\\n this.__last_index__ = ml.index + ml[0].length\\n }\\n }\\n }\\n }\\n }\\n\\n if (this.__opts__.fuzzyEmail && this.__compiled__['mailto:']) {\\n // guess schemaless emails\\n at_pos = text.indexOf('@')\\n if (at_pos >= 0) {\\n // We can't skip this check, because this cases are possible:\\n // 192.168.1.1@gmail.com, my.in@example.com\\n if ((me = text.match(this.re.email_fuzzy)) !== null) {\\n shift = me.index + me[1].length\\n next = me.index + me[0].length\\n\\n if (this.__index__ < 0 || shift < this.__index__ ||\\n (shift === this.__index__ && next > this.__last_index__)) {\\n this.__schema__ = 'mailto:'\\n this.__index__ = shift\\n this.__last_index__ = next\\n }\\n }\\n }\\n }\\n\\n return this.__index__ >= 0\\n}\\n\\n/**\\n * LinkifyIt#pretest(text) -> Boolean\\n *\\n * Very quick check, that can give false positives. Returns true if link MAY BE\\n * can exists. Can be used for speed optimization, when you need to check that\\n * link NOT exists.\\n **/\\nLinkifyIt.prototype.pretest = function pretest (text) {\\n return this.re.pretest.test(text)\\n}\\n\\n/**\\n * LinkifyIt#testSchemaAt(text, name, position) -> Number\\n * - text (String): text to scan\\n * - name (String): rule (schema) name\\n * - position (Number): text offset to check from\\n *\\n * Similar to [[LinkifyIt#test]] but checks only specific protocol tail exactly\\n * at given position. Returns length of found pattern (0 on fail).\\n **/\\nLinkifyIt.prototype.testSchemaAt = function testSchemaAt (text, schema, pos) {\\n // If not supported schema check requested - terminate\\n if (!this.__compiled__[schema.toLowerCase()]) {\\n return 0\\n }\\n return this.__compiled__[schema.toLowerCase()].validate(text, pos, this)\\n}\\n\\n/**\\n * LinkifyIt#match(text) -> Array|null\\n *\\n * Returns array of found link descriptions or `null` on fail. We strongly\\n * recommend to use [[LinkifyIt#test]] first, for best speed.\\n *\\n * ##### Result match description\\n *\\n * - __schema__ - link schema, can be empty for fuzzy links, or `//` for\\n * protocol-neutral links.\\n * - __index__ - offset of matched text\\n * - __lastIndex__ - index of next char after mathch end\\n * - __raw__ - matched text\\n * - __text__ - normalized text\\n * - __url__ - link, generated from matched text\\n **/\\nLinkifyIt.prototype.match = function match (text) {\\n const result = []\\n let shift = 0\\n\\n // Try to take previous element from cache, if .test() called before\\n if (this.__index__ >= 0 && this.__text_cache__ === text) {\\n result.push(createMatch(this, shift))\\n shift = this.__last_index__\\n }\\n\\n // Cut head if cache was used\\n let tail = shift ? text.slice(shift) : text\\n\\n // Scan string until end reached\\n while (this.test(tail)) {\\n result.push(createMatch(this, shift))\\n\\n tail = tail.slice(this.__last_index__)\\n shift += this.__last_index__\\n }\\n\\n if (result.length) {\\n return result\\n }\\n\\n return null\\n}\\n\\n/**\\n * LinkifyIt#matchAtStart(text) -> Match|null\\n *\\n * Returns fully-formed (not fuzzy) link if it starts at the beginning\\n * of the string, and null otherwise.\\n **/\\nLinkifyIt.prototype.matchAtStart = function matchAtStart (text) {\\n // Reset scan cache\\n this.__text_cache__ = text\\n this.__index__ = -1\\n\\n if (!text.length) return null\\n\\n const m = this.re.schema_at_start.exec(text)\\n if (!m) return null\\n\\n const len = this.testSchemaAt(text, m[2], m[0].length)\\n if (!len) return null\\n\\n this.__schema__ = m[2]\\n this.__index__ = m.index + m[1].length\\n this.__last_index__ = m.index + m[0].length + len\\n\\n return createMatch(this, 0)\\n}\\n\\n/** chainable\\n * LinkifyIt#tlds(list [, keepOld]) -> this\\n * - list (Array): list of tlds\\n * - keepOld (Boolean): merge with current list if `true` (`false` by default)\\n *\\n * Load (or merge) new tlds list. Those are user for fuzzy links (without prefix)\\n * to avoid false positives. By default this algorythm used:\\n *\\n * - hostname with any 2-letter root zones are ok.\\n * - biz|com|edu|gov|net|org|pro|web|xxx|aero|asia|coop|info|museum|name|shop|рф\\n * are ok.\\n * - encoded (`xn--...`) root zones are ok.\\n *\\n * If list is replaced, then exact match for 2-chars root zones will be checked.\\n **/\\nLinkifyIt.prototype.tlds = function tlds (list, keepOld) {\\n list = Array.isArray(list) ? list : [list]\\n\\n if (!keepOld) {\\n this.__tlds__ = list.slice()\\n this.__tlds_replaced__ = true\\n compile(this)\\n return this\\n }\\n\\n this.__tlds__ = this.__tlds__.concat(list)\\n .sort()\\n .filter(function (el, idx, arr) {\\n return el !== arr[idx - 1]\\n })\\n .reverse()\\n\\n compile(this)\\n return this\\n}\\n\\n/**\\n * LinkifyIt#normalize(match)\\n *\\n * Default normalizer (if schema does not define it's own).\\n **/\\nLinkifyIt.prototype.normalize = function normalize (match) {\\n // Do minimal possible changes by default. Need to collect feedback prior\\n // to move forward https://github.com/markdown-it/linkify-it/issues/1\\n\\n if (!match.schema) { match.url = 'http://' + match.url }\\n\\n if (match.schema === 'mailto:' && !/^mailto:/i.test(match.url)) {\\n match.url = 'mailto:' + match.url\\n }\\n}\\n\\n/**\\n * LinkifyIt#onCompile()\\n *\\n * Override to modify basic RegExp-s.\\n **/\\nLinkifyIt.prototype.onCompile = function onCompile () {\\n}\\n\\nexport default LinkifyIt\\n\",\"'use strict';\\n\\n/** Highest positive signed 32-bit float value */\\nconst maxInt = 2147483647; // aka. 0x7FFFFFFF or 2^31-1\\n\\n/** Bootstring parameters */\\nconst base = 36;\\nconst tMin = 1;\\nconst tMax = 26;\\nconst skew = 38;\\nconst damp = 700;\\nconst initialBias = 72;\\nconst initialN = 128; // 0x80\\nconst delimiter = '-'; // '\\\\x2D'\\n\\n/** Regular expressions */\\nconst regexPunycode = /^xn--/;\\nconst regexNonASCII = /[^\\\\0-\\\\x7F]/; // Note: U+007F DEL is excluded too.\\nconst regexSeparators = /[\\\\x2E\\\\u3002\\\\uFF0E\\\\uFF61]/g; // RFC 3490 separators\\n\\n/** Error messages */\\nconst errors = {\\n\\t'overflow': 'Overflow: input needs wider integers to process',\\n\\t'not-basic': 'Illegal input >= 0x80 (not a basic code point)',\\n\\t'invalid-input': 'Invalid input'\\n};\\n\\n/** Convenience shortcuts */\\nconst baseMinusTMin = base - tMin;\\nconst floor = Math.floor;\\nconst stringFromCharCode = String.fromCharCode;\\n\\n/*--------------------------------------------------------------------------*/\\n\\n/**\\n * A generic error utility function.\\n * @private\\n * @param {String} type The error type.\\n * @returns {Error} Throws a `RangeError` with the applicable error message.\\n */\\nfunction error(type) {\\n\\tthrow new RangeError(errors[type]);\\n}\\n\\n/**\\n * A generic `Array#map` utility function.\\n * @private\\n * @param {Array} array The array to iterate over.\\n * @param {Function} callback The function that gets called for every array\\n * item.\\n * @returns {Array} A new array of values returned by the callback function.\\n */\\nfunction map(array, callback) {\\n\\tconst result = [];\\n\\tlet length = array.length;\\n\\twhile (length--) {\\n\\t\\tresult[length] = callback(array[length]);\\n\\t}\\n\\treturn result;\\n}\\n\\n/**\\n * A simple `Array#map`-like wrapper to work with domain name strings or email\\n * addresses.\\n * @private\\n * @param {String} domain The domain name or email address.\\n * @param {Function} callback The function that gets called for every\\n * character.\\n * @returns {String} A new string of characters returned by the callback\\n * function.\\n */\\nfunction mapDomain(domain, callback) {\\n\\tconst parts = domain.split('@');\\n\\tlet result = '';\\n\\tif (parts.length > 1) {\\n\\t\\t// In email addresses, only the domain name should be punycoded. Leave\\n\\t\\t// the local part (i.e. everything up to `@`) intact.\\n\\t\\tresult = parts[0] + '@';\\n\\t\\tdomain = parts[1];\\n\\t}\\n\\t// Avoid `split(regex)` for IE8 compatibility. See #17.\\n\\tdomain = domain.replace(regexSeparators, '\\\\x2E');\\n\\tconst labels = domain.split('.');\\n\\tconst encoded = map(labels, callback).join('.');\\n\\treturn result + encoded;\\n}\\n\\n/**\\n * Creates an array containing the numeric code points of each Unicode\\n * character in the string. While JavaScript uses UCS-2 internally,\\n * this function will convert a pair of surrogate halves (each of which\\n * UCS-2 exposes as separate characters) into a single code point,\\n * matching UTF-16.\\n * @see `punycode.ucs2.encode`\\n * @see \\n * @memberOf punycode.ucs2\\n * @name decode\\n * @param {String} string The Unicode input string (UCS-2).\\n * @returns {Array} The new array of code points.\\n */\\nfunction ucs2decode(string) {\\n\\tconst output = [];\\n\\tlet counter = 0;\\n\\tconst length = string.length;\\n\\twhile (counter < length) {\\n\\t\\tconst value = string.charCodeAt(counter++);\\n\\t\\tif (value >= 0xD800 && value <= 0xDBFF && counter < length) {\\n\\t\\t\\t// It's a high surrogate, and there is a next character.\\n\\t\\t\\tconst extra = string.charCodeAt(counter++);\\n\\t\\t\\tif ((extra & 0xFC00) == 0xDC00) { // Low surrogate.\\n\\t\\t\\t\\toutput.push(((value & 0x3FF) << 10) + (extra & 0x3FF) + 0x10000);\\n\\t\\t\\t} else {\\n\\t\\t\\t\\t// It's an unmatched surrogate; only append this code unit, in case the\\n\\t\\t\\t\\t// next code unit is the high surrogate of a surrogate pair.\\n\\t\\t\\t\\toutput.push(value);\\n\\t\\t\\t\\tcounter--;\\n\\t\\t\\t}\\n\\t\\t} else {\\n\\t\\t\\toutput.push(value);\\n\\t\\t}\\n\\t}\\n\\treturn output;\\n}\\n\\n/**\\n * Creates a string based on an array of numeric code points.\\n * @see `punycode.ucs2.decode`\\n * @memberOf punycode.ucs2\\n * @name encode\\n * @param {Array} codePoints The array of numeric code points.\\n * @returns {String} The new Unicode string (UCS-2).\\n */\\nconst ucs2encode = codePoints => String.fromCodePoint(...codePoints);\\n\\n/**\\n * Converts a basic code point into a digit/integer.\\n * @see `digitToBasic()`\\n * @private\\n * @param {Number} codePoint The basic numeric code point value.\\n * @returns {Number} The numeric value of a basic code point (for use in\\n * representing integers) in the range `0` to `base - 1`, or `base` if\\n * the code point does not represent a value.\\n */\\nconst basicToDigit = function(codePoint) {\\n\\tif (codePoint >= 0x30 && codePoint < 0x3A) {\\n\\t\\treturn 26 + (codePoint - 0x30);\\n\\t}\\n\\tif (codePoint >= 0x41 && codePoint < 0x5B) {\\n\\t\\treturn codePoint - 0x41;\\n\\t}\\n\\tif (codePoint >= 0x61 && codePoint < 0x7B) {\\n\\t\\treturn codePoint - 0x61;\\n\\t}\\n\\treturn base;\\n};\\n\\n/**\\n * Converts a digit/integer into a basic code point.\\n * @see `basicToDigit()`\\n * @private\\n * @param {Number} digit The numeric value of a basic code point.\\n * @returns {Number} The basic code point whose value (when used for\\n * representing integers) is `digit`, which needs to be in the range\\n * `0` to `base - 1`. If `flag` is non-zero, the uppercase form is\\n * used; else, the lowercase form is used. The behavior is undefined\\n * if `flag` is non-zero and `digit` has no uppercase form.\\n */\\nconst digitToBasic = function(digit, flag) {\\n\\t// 0..25 map to ASCII a..z or A..Z\\n\\t// 26..35 map to ASCII 0..9\\n\\treturn digit + 22 + 75 * (digit < 26) - ((flag != 0) << 5);\\n};\\n\\n/**\\n * Bias adaptation function as per section 3.4 of RFC 3492.\\n * https://tools.ietf.org/html/rfc3492#section-3.4\\n * @private\\n */\\nconst adapt = function(delta, numPoints, firstTime) {\\n\\tlet k = 0;\\n\\tdelta = firstTime ? floor(delta / damp) : delta >> 1;\\n\\tdelta += floor(delta / numPoints);\\n\\tfor (/* no initialization */; delta > baseMinusTMin * tMax >> 1; k += base) {\\n\\t\\tdelta = floor(delta / baseMinusTMin);\\n\\t}\\n\\treturn floor(k + (baseMinusTMin + 1) * delta / (delta + skew));\\n};\\n\\n/**\\n * Converts a Punycode string of ASCII-only symbols to a string of Unicode\\n * symbols.\\n * @memberOf punycode\\n * @param {String} input The Punycode string of ASCII-only symbols.\\n * @returns {String} The resulting string of Unicode symbols.\\n */\\nconst decode = function(input) {\\n\\t// Don't use UCS-2.\\n\\tconst output = [];\\n\\tconst inputLength = input.length;\\n\\tlet i = 0;\\n\\tlet n = initialN;\\n\\tlet bias = initialBias;\\n\\n\\t// Handle the basic code points: let `basic` be the number of input code\\n\\t// points before the last delimiter, or `0` if there is none, then copy\\n\\t// the first basic code points to the output.\\n\\n\\tlet basic = input.lastIndexOf(delimiter);\\n\\tif (basic < 0) {\\n\\t\\tbasic = 0;\\n\\t}\\n\\n\\tfor (let j = 0; j < basic; ++j) {\\n\\t\\t// if it's not a basic code point\\n\\t\\tif (input.charCodeAt(j) >= 0x80) {\\n\\t\\t\\terror('not-basic');\\n\\t\\t}\\n\\t\\toutput.push(input.charCodeAt(j));\\n\\t}\\n\\n\\t// Main decoding loop: start just after the last delimiter if any basic code\\n\\t// points were copied; start at the beginning otherwise.\\n\\n\\tfor (let index = basic > 0 ? basic + 1 : 0; index < inputLength; /* no final expression */) {\\n\\n\\t\\t// `index` is the index of the next character to be consumed.\\n\\t\\t// Decode a generalized variable-length integer into `delta`,\\n\\t\\t// which gets added to `i`. The overflow checking is easier\\n\\t\\t// if we increase `i` as we go, then subtract off its starting\\n\\t\\t// value at the end to obtain `delta`.\\n\\t\\tconst oldi = i;\\n\\t\\tfor (let w = 1, k = base; /* no condition */; k += base) {\\n\\n\\t\\t\\tif (index >= inputLength) {\\n\\t\\t\\t\\terror('invalid-input');\\n\\t\\t\\t}\\n\\n\\t\\t\\tconst digit = basicToDigit(input.charCodeAt(index++));\\n\\n\\t\\t\\tif (digit >= base) {\\n\\t\\t\\t\\terror('invalid-input');\\n\\t\\t\\t}\\n\\t\\t\\tif (digit > floor((maxInt - i) / w)) {\\n\\t\\t\\t\\terror('overflow');\\n\\t\\t\\t}\\n\\n\\t\\t\\ti += digit * w;\\n\\t\\t\\tconst t = k <= bias ? tMin : (k >= bias + tMax ? tMax : k - bias);\\n\\n\\t\\t\\tif (digit < t) {\\n\\t\\t\\t\\tbreak;\\n\\t\\t\\t}\\n\\n\\t\\t\\tconst baseMinusT = base - t;\\n\\t\\t\\tif (w > floor(maxInt / baseMinusT)) {\\n\\t\\t\\t\\terror('overflow');\\n\\t\\t\\t}\\n\\n\\t\\t\\tw *= baseMinusT;\\n\\n\\t\\t}\\n\\n\\t\\tconst out = output.length + 1;\\n\\t\\tbias = adapt(i - oldi, out, oldi == 0);\\n\\n\\t\\t// `i` was supposed to wrap around from `out` to `0`,\\n\\t\\t// incrementing `n` each time, so we'll fix that now:\\n\\t\\tif (floor(i / out) > maxInt - n) {\\n\\t\\t\\terror('overflow');\\n\\t\\t}\\n\\n\\t\\tn += floor(i / out);\\n\\t\\ti %= out;\\n\\n\\t\\t// Insert `n` at position `i` of the output.\\n\\t\\toutput.splice(i++, 0, n);\\n\\n\\t}\\n\\n\\treturn String.fromCodePoint(...output);\\n};\\n\\n/**\\n * Converts a string of Unicode symbols (e.g. a domain name label) to a\\n * Punycode string of ASCII-only symbols.\\n * @memberOf punycode\\n * @param {String} input The string of Unicode symbols.\\n * @returns {String} The resulting Punycode string of ASCII-only symbols.\\n */\\nconst encode = function(input) {\\n\\tconst output = [];\\n\\n\\t// Convert the input in UCS-2 to an array of Unicode code points.\\n\\tinput = ucs2decode(input);\\n\\n\\t// Cache the length.\\n\\tconst inputLength = input.length;\\n\\n\\t// Initialize the state.\\n\\tlet n = initialN;\\n\\tlet delta = 0;\\n\\tlet bias = initialBias;\\n\\n\\t// Handle the basic code points.\\n\\tfor (const currentValue of input) {\\n\\t\\tif (currentValue < 0x80) {\\n\\t\\t\\toutput.push(stringFromCharCode(currentValue));\\n\\t\\t}\\n\\t}\\n\\n\\tconst basicLength = output.length;\\n\\tlet handledCPCount = basicLength;\\n\\n\\t// `handledCPCount` is the number of code points that have been handled;\\n\\t// `basicLength` is the number of basic code points.\\n\\n\\t// Finish the basic string with a delimiter unless it's empty.\\n\\tif (basicLength) {\\n\\t\\toutput.push(delimiter);\\n\\t}\\n\\n\\t// Main encoding loop:\\n\\twhile (handledCPCount < inputLength) {\\n\\n\\t\\t// All non-basic code points < n have been handled already. Find the next\\n\\t\\t// larger one:\\n\\t\\tlet m = maxInt;\\n\\t\\tfor (const currentValue of input) {\\n\\t\\t\\tif (currentValue >= n && currentValue < m) {\\n\\t\\t\\t\\tm = currentValue;\\n\\t\\t\\t}\\n\\t\\t}\\n\\n\\t\\t// Increase `delta` enough to advance the decoder's state to ,\\n\\t\\t// but guard against overflow.\\n\\t\\tconst handledCPCountPlusOne = handledCPCount + 1;\\n\\t\\tif (m - n > floor((maxInt - delta) / handledCPCountPlusOne)) {\\n\\t\\t\\terror('overflow');\\n\\t\\t}\\n\\n\\t\\tdelta += (m - n) * handledCPCountPlusOne;\\n\\t\\tn = m;\\n\\n\\t\\tfor (const currentValue of input) {\\n\\t\\t\\tif (currentValue < n && ++delta > maxInt) {\\n\\t\\t\\t\\terror('overflow');\\n\\t\\t\\t}\\n\\t\\t\\tif (currentValue === n) {\\n\\t\\t\\t\\t// Represent delta as a generalized variable-length integer.\\n\\t\\t\\t\\tlet q = delta;\\n\\t\\t\\t\\tfor (let k = base; /* no condition */; k += base) {\\n\\t\\t\\t\\t\\tconst t = k <= bias ? tMin : (k >= bias + tMax ? tMax : k - bias);\\n\\t\\t\\t\\t\\tif (q < t) {\\n\\t\\t\\t\\t\\t\\tbreak;\\n\\t\\t\\t\\t\\t}\\n\\t\\t\\t\\t\\tconst qMinusT = q - t;\\n\\t\\t\\t\\t\\tconst baseMinusT = base - t;\\n\\t\\t\\t\\t\\toutput.push(\\n\\t\\t\\t\\t\\t\\tstringFromCharCode(digitToBasic(t + qMinusT % baseMinusT, 0))\\n\\t\\t\\t\\t\\t);\\n\\t\\t\\t\\t\\tq = floor(qMinusT / baseMinusT);\\n\\t\\t\\t\\t}\\n\\n\\t\\t\\t\\toutput.push(stringFromCharCode(digitToBasic(q, 0)));\\n\\t\\t\\t\\tbias = adapt(delta, handledCPCountPlusOne, handledCPCount === basicLength);\\n\\t\\t\\t\\tdelta = 0;\\n\\t\\t\\t\\t++handledCPCount;\\n\\t\\t\\t}\\n\\t\\t}\\n\\n\\t\\t++delta;\\n\\t\\t++n;\\n\\n\\t}\\n\\treturn output.join('');\\n};\\n\\n/**\\n * Converts a Punycode string representing a domain name or an email address\\n * to Unicode. Only the Punycoded parts of the input will be converted, i.e.\\n * it doesn't matter if you call it on a string that has already been\\n * converted to Unicode.\\n * @memberOf punycode\\n * @param {String} input The Punycoded domain name or email address to\\n * convert to Unicode.\\n * @returns {String} The Unicode representation of the given Punycode\\n * string.\\n */\\nconst toUnicode = function(input) {\\n\\treturn mapDomain(input, function(string) {\\n\\t\\treturn regexPunycode.test(string)\\n\\t\\t\\t? decode(string.slice(4).toLowerCase())\\n\\t\\t\\t: string;\\n\\t});\\n};\\n\\n/**\\n * Converts a Unicode string representing a domain name or an email address to\\n * Punycode. Only the non-ASCII parts of the domain name will be converted,\\n * i.e. it doesn't matter if you call it with a domain that's already in\\n * ASCII.\\n * @memberOf punycode\\n * @param {String} input The domain name or email address to convert, as a\\n * Unicode string.\\n * @returns {String} The Punycode representation of the given domain name or\\n * email address.\\n */\\nconst toASCII = function(input) {\\n\\treturn mapDomain(input, function(string) {\\n\\t\\treturn regexNonASCII.test(string)\\n\\t\\t\\t? 'xn--' + encode(string)\\n\\t\\t\\t: string;\\n\\t});\\n};\\n\\n/*--------------------------------------------------------------------------*/\\n\\n/** Define the public API */\\nconst punycode = {\\n\\t/**\\n\\t * A string representing the current Punycode.js version number.\\n\\t * @memberOf punycode\\n\\t * @type String\\n\\t */\\n\\t'version': '2.3.1',\\n\\t/**\\n\\t * An object of methods to convert from JavaScript's internal character\\n\\t * representation (UCS-2) to Unicode code points, and back.\\n\\t * @see \\n\\t * @memberOf punycode\\n\\t * @type Object\\n\\t */\\n\\t'ucs2': {\\n\\t\\t'decode': ucs2decode,\\n\\t\\t'encode': ucs2encode\\n\\t},\\n\\t'decode': decode,\\n\\t'encode': encode,\\n\\t'toASCII': toASCII,\\n\\t'toUnicode': toUnicode\\n};\\n\\nexport { ucs2decode, ucs2encode, decode, encode, toASCII, toUnicode };\\nexport default punycode;\\n\",\"// markdown-it default options\\n\\nexport default {\\n options: {\\n // Enable HTML tags in source\\n html: false,\\n\\n // Use '/' to close single tags (
)\\n xhtmlOut: false,\\n\\n // Convert '\\\\n' in paragraphs into
\\n breaks: false,\\n\\n // CSS language prefix for fenced blocks\\n langPrefix: 'language-',\\n\\n // autoconvert URL-like texts to links\\n linkify: false,\\n\\n // Enable some language-neutral replacements + quotes beautification\\n typographer: false,\\n\\n // Double + single quotes replacement pairs, when typographer enabled,\\n // and smartquotes on. Could be either a String or an Array.\\n //\\n // For example, you can use '«»„“' for Russian, '„“‚‘' for German,\\n // and ['«\\\\xA0', '\\\\xA0»', '‹\\\\xA0', '\\\\xA0›'] for French (including nbsp).\\n quotes: '\\\\u201c\\\\u201d\\\\u2018\\\\u2019', /* “”‘’ */\\n\\n // Highlighter function. Should return escaped HTML,\\n // or '' if the source string is not changed and should be escaped externaly.\\n // If result starts with )\\n xhtmlOut: false,\\n\\n // Convert '\\\\n' in paragraphs into
\\n breaks: false,\\n\\n // CSS language prefix for fenced blocks\\n langPrefix: 'language-',\\n\\n // autoconvert URL-like texts to links\\n linkify: false,\\n\\n // Enable some language-neutral replacements + quotes beautification\\n typographer: false,\\n\\n // Double + single quotes replacement pairs, when typographer enabled,\\n // and smartquotes on. Could be either a String or an Array.\\n //\\n // For example, you can use '«»„“' for Russian, '„“‚‘' for German,\\n // and ['«\\\\xA0', '\\\\xA0»', '‹\\\\xA0', '\\\\xA0›'] for French (including nbsp).\\n quotes: '\\\\u201c\\\\u201d\\\\u2018\\\\u2019', /* “”‘’ */\\n\\n // Highlighter function. Should return escaped HTML,\\n // or '' if the source string is not changed and should be escaped externaly.\\n // If result starts with )\\n xhtmlOut: true,\\n\\n // Convert '\\\\n' in paragraphs into
\\n breaks: false,\\n\\n // CSS language prefix for fenced blocks\\n langPrefix: 'language-',\\n\\n // autoconvert URL-like texts to links\\n linkify: false,\\n\\n // Enable some language-neutral replacements + quotes beautification\\n typographer: false,\\n\\n // Double + single quotes replacement pairs, when typographer enabled,\\n // and smartquotes on. Could be either a String or an Array.\\n //\\n // For example, you can use '«»„“' for Russian, '„“‚‘' for German,\\n // and ['«\\\\xA0', '\\\\xA0»', '‹\\\\xA0', '\\\\xA0›'] for French (including nbsp).\\n quotes: '\\\\u201c\\\\u201d\\\\u2018\\\\u2019', /* “”‘’ */\\n\\n // Highlighter function. Should return escaped HTML,\\n // or '' if the source string is not changed and should be escaped externaly.\\n // If result starts with = 0) {\\n try {\\n parsed.hostname = punycode.toASCII(parsed.hostname)\\n } catch (er) { /**/ }\\n }\\n }\\n\\n return mdurl.encode(mdurl.format(parsed))\\n}\\n\\nfunction normalizeLinkText (url) {\\n const parsed = mdurl.parse(url, true)\\n\\n if (parsed.hostname) {\\n // Encode hostnames in urls like:\\n // `http://host/`, `https://host/`, `mailto:user@host`, `//host/`\\n //\\n // We don't encode unknown schemas, because it's likely that we encode\\n // something we shouldn't (e.g. `skype:name` treated as `skype:host`)\\n //\\n if (!parsed.protocol || RECODE_HOSTNAME_FOR.indexOf(parsed.protocol) >= 0) {\\n try {\\n parsed.hostname = punycode.toUnicode(parsed.hostname)\\n } catch (er) { /**/ }\\n }\\n }\\n\\n // add '%' to exclude list because of https://github.com/markdown-it/markdown-it/issues/720\\n return mdurl.decode(mdurl.format(parsed), mdurl.decode.defaultChars + '%')\\n}\\n\\n/**\\n * class MarkdownIt\\n *\\n * Main parser/renderer class.\\n *\\n * ##### Usage\\n *\\n * ```javascript\\n * // node.js, \\\"classic\\\" way:\\n * var MarkdownIt = require('markdown-it'),\\n * md = new MarkdownIt();\\n * var result = md.render('# markdown-it rulezz!');\\n *\\n * // node.js, the same, but with sugar:\\n * var md = require('markdown-it')();\\n * var result = md.render('# markdown-it rulezz!');\\n *\\n * // browser without AMD, added to \\\"window\\\" on script load\\n * // Note, there are no dash.\\n * var md = window.markdownit();\\n * var result = md.render('# markdown-it rulezz!');\\n * ```\\n *\\n * Single line rendering, without paragraph wrap:\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n * var result = md.renderInline('__markdown-it__ rulezz!');\\n * ```\\n **/\\n\\n/**\\n * new MarkdownIt([presetName, options])\\n * - presetName (String): optional, `commonmark` / `zero`\\n * - options (Object)\\n *\\n * Creates parser instanse with given config. Can be called without `new`.\\n *\\n * ##### presetName\\n *\\n * MarkdownIt provides named presets as a convenience to quickly\\n * enable/disable active syntax rules and options for common use cases.\\n *\\n * - [\\\"commonmark\\\"](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/commonmark.mjs) -\\n * configures parser to strict [CommonMark](http://commonmark.org/) mode.\\n * - [default](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/default.mjs) -\\n * similar to GFM, used when no preset name given. Enables all available rules,\\n * but still without html, typographer & autolinker.\\n * - [\\\"zero\\\"](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/zero.mjs) -\\n * all rules disabled. Useful to quickly setup your config via `.enable()`.\\n * For example, when you need only `bold` and `italic` markup and nothing else.\\n *\\n * ##### options:\\n *\\n * - __html__ - `false`. Set `true` to enable HTML tags in source. Be careful!\\n * That's not safe! You may need external sanitizer to protect output from XSS.\\n * It's better to extend features via plugins, instead of enabling HTML.\\n * - __xhtmlOut__ - `false`. Set `true` to add '/' when closing single tags\\n * (`
`). This is needed only for full CommonMark compatibility. In real\\n * world you will need HTML output.\\n * - __breaks__ - `false`. Set `true` to convert `\\\\n` in paragraphs into `
`.\\n * - __langPrefix__ - `language-`. CSS language class prefix for fenced blocks.\\n * Can be useful for external highlighters.\\n * - __linkify__ - `false`. Set `true` to autoconvert URL-like text to links.\\n * - __typographer__ - `false`. Set `true` to enable [some language-neutral\\n * replacement](https://github.com/markdown-it/markdown-it/blob/master/lib/rules_core/replacements.mjs) +\\n * quotes beautification (smartquotes).\\n * - __quotes__ - `“”‘’`, String or Array. Double + single quotes replacement\\n * pairs, when typographer enabled and smartquotes on. For example, you can\\n * use `'«»„“'` for Russian, `'„“‚‘'` for German, and\\n * `['«\\\\xA0', '\\\\xA0»', '‹\\\\xA0', '\\\\xA0›']` for French (including nbsp).\\n * - __highlight__ - `null`. Highlighter function for fenced code blocks.\\n * Highlighter `function (str, lang)` should return escaped HTML. It can also\\n * return empty string if the source was not changed and should be escaped\\n * externaly. If result starts with ` or ``):\\n *\\n * ```javascript\\n * var hljs = require('highlight.js') // https://highlightjs.org/\\n *\\n * // Actual default values\\n * var md = require('markdown-it')({\\n * highlight: function (str, lang) {\\n * if (lang && hljs.getLanguage(lang)) {\\n * try {\\n * return '
' +\\n *                hljs.highlight(str, { language: lang, ignoreIllegals: true }).value +\\n *                '
';\\n * } catch (__) {}\\n * }\\n *\\n * return '
' + md.utils.escapeHtml(str) + '
';\\n * }\\n * });\\n * ```\\n *\\n **/\\nfunction MarkdownIt (presetName, options) {\\n if (!(this instanceof MarkdownIt)) {\\n return new MarkdownIt(presetName, options)\\n }\\n\\n if (!options) {\\n if (!utils.isString(presetName)) {\\n options = presetName || {}\\n presetName = 'default'\\n }\\n }\\n\\n /**\\n * MarkdownIt#inline -> ParserInline\\n *\\n * Instance of [[ParserInline]]. You may need it to add new rules when\\n * writing plugins. For simple rules control use [[MarkdownIt.disable]] and\\n * [[MarkdownIt.enable]].\\n **/\\n this.inline = new ParserInline()\\n\\n /**\\n * MarkdownIt#block -> ParserBlock\\n *\\n * Instance of [[ParserBlock]]. You may need it to add new rules when\\n * writing plugins. For simple rules control use [[MarkdownIt.disable]] and\\n * [[MarkdownIt.enable]].\\n **/\\n this.block = new ParserBlock()\\n\\n /**\\n * MarkdownIt#core -> Core\\n *\\n * Instance of [[Core]] chain executor. You may need it to add new rules when\\n * writing plugins. For simple rules control use [[MarkdownIt.disable]] and\\n * [[MarkdownIt.enable]].\\n **/\\n this.core = new ParserCore()\\n\\n /**\\n * MarkdownIt#renderer -> Renderer\\n *\\n * Instance of [[Renderer]]. Use it to modify output look. Or to add rendering\\n * rules for new token types, generated by plugins.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n *\\n * function myToken(tokens, idx, options, env, self) {\\n * //...\\n * return result;\\n * };\\n *\\n * md.renderer.rules['my_token'] = myToken\\n * ```\\n *\\n * See [[Renderer]] docs and [source code](https://github.com/markdown-it/markdown-it/blob/master/lib/renderer.mjs).\\n **/\\n this.renderer = new Renderer()\\n\\n /**\\n * MarkdownIt#linkify -> LinkifyIt\\n *\\n * [linkify-it](https://github.com/markdown-it/linkify-it) instance.\\n * Used by [linkify](https://github.com/markdown-it/markdown-it/blob/master/lib/rules_core/linkify.mjs)\\n * rule.\\n **/\\n this.linkify = new LinkifyIt()\\n\\n /**\\n * MarkdownIt#validateLink(url) -> Boolean\\n *\\n * Link validation function. CommonMark allows too much in links. By default\\n * we disable `javascript:`, `vbscript:`, `file:` schemas, and almost all `data:...` schemas\\n * except some embedded image types.\\n *\\n * You can change this behaviour:\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n * // enable everything\\n * md.validateLink = function () { return true; }\\n * ```\\n **/\\n this.validateLink = validateLink\\n\\n /**\\n * MarkdownIt#normalizeLink(url) -> String\\n *\\n * Function used to encode link url to a machine-readable format,\\n * which includes url-encoding, punycode, etc.\\n **/\\n this.normalizeLink = normalizeLink\\n\\n /**\\n * MarkdownIt#normalizeLinkText(url) -> String\\n *\\n * Function used to decode link url to a human-readable format`\\n **/\\n this.normalizeLinkText = normalizeLinkText\\n\\n // Expose utils & helpers for easy acces from plugins\\n\\n /**\\n * MarkdownIt#utils -> utils\\n *\\n * Assorted utility functions, useful to write plugins. See details\\n * [here](https://github.com/markdown-it/markdown-it/blob/master/lib/common/utils.mjs).\\n **/\\n this.utils = utils\\n\\n /**\\n * MarkdownIt#helpers -> helpers\\n *\\n * Link components parser functions, useful to write plugins. See details\\n * [here](https://github.com/markdown-it/markdown-it/blob/master/lib/helpers).\\n **/\\n this.helpers = utils.assign({}, helpers)\\n\\n this.options = {}\\n this.configure(presetName)\\n\\n if (options) { this.set(options) }\\n}\\n\\n/** chainable\\n * MarkdownIt.set(options)\\n *\\n * Set parser options (in the same format as in constructor). Probably, you\\n * will never need it, but you can change options after constructor call.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var md = require('markdown-it')()\\n * .set({ html: true, breaks: true })\\n * .set({ typographer, true });\\n * ```\\n *\\n * __Note:__ To achieve the best possible performance, don't modify a\\n * `markdown-it` instance options on the fly. If you need multiple configurations\\n * it's best to create multiple instances and initialize each with separate\\n * config.\\n **/\\nMarkdownIt.prototype.set = function (options) {\\n utils.assign(this.options, options)\\n return this\\n}\\n\\n/** chainable, internal\\n * MarkdownIt.configure(presets)\\n *\\n * Batch load of all options and compenent settings. This is internal method,\\n * and you probably will not need it. But if you will - see available presets\\n * and data structure [here](https://github.com/markdown-it/markdown-it/tree/master/lib/presets)\\n *\\n * We strongly recommend to use presets instead of direct config loads. That\\n * will give better compatibility with next versions.\\n **/\\nMarkdownIt.prototype.configure = function (presets) {\\n const self = this\\n\\n if (utils.isString(presets)) {\\n const presetName = presets\\n presets = config[presetName]\\n if (!presets) { throw new Error('Wrong `markdown-it` preset \\\"' + presetName + '\\\", check name') }\\n }\\n\\n if (!presets) { throw new Error('Wrong `markdown-it` preset, can\\\\'t be empty') }\\n\\n if (presets.options) { self.set(presets.options) }\\n\\n if (presets.components) {\\n Object.keys(presets.components).forEach(function (name) {\\n if (presets.components[name].rules) {\\n self[name].ruler.enableOnly(presets.components[name].rules)\\n }\\n if (presets.components[name].rules2) {\\n self[name].ruler2.enableOnly(presets.components[name].rules2)\\n }\\n })\\n }\\n return this\\n}\\n\\n/** chainable\\n * MarkdownIt.enable(list, ignoreInvalid)\\n * - list (String|Array): rule name or list of rule names to enable\\n * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found.\\n *\\n * Enable list or rules. It will automatically find appropriate components,\\n * containing rules with given names. If rule not found, and `ignoreInvalid`\\n * not set - throws exception.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var md = require('markdown-it')()\\n * .enable(['sub', 'sup'])\\n * .disable('smartquotes');\\n * ```\\n **/\\nMarkdownIt.prototype.enable = function (list, ignoreInvalid) {\\n let result = []\\n\\n if (!Array.isArray(list)) { list = [list] }\\n\\n ['core', 'block', 'inline'].forEach(function (chain) {\\n result = result.concat(this[chain].ruler.enable(list, true))\\n }, this)\\n\\n result = result.concat(this.inline.ruler2.enable(list, true))\\n\\n const missed = list.filter(function (name) { return result.indexOf(name) < 0 })\\n\\n if (missed.length && !ignoreInvalid) {\\n throw new Error('MarkdownIt. Failed to enable unknown rule(s): ' + missed)\\n }\\n\\n return this\\n}\\n\\n/** chainable\\n * MarkdownIt.disable(list, ignoreInvalid)\\n * - list (String|Array): rule name or list of rule names to disable.\\n * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found.\\n *\\n * The same as [[MarkdownIt.enable]], but turn specified rules off.\\n **/\\nMarkdownIt.prototype.disable = function (list, ignoreInvalid) {\\n let result = []\\n\\n if (!Array.isArray(list)) { list = [list] }\\n\\n ['core', 'block', 'inline'].forEach(function (chain) {\\n result = result.concat(this[chain].ruler.disable(list, true))\\n }, this)\\n\\n result = result.concat(this.inline.ruler2.disable(list, true))\\n\\n const missed = list.filter(function (name) { return result.indexOf(name) < 0 })\\n\\n if (missed.length && !ignoreInvalid) {\\n throw new Error('MarkdownIt. Failed to disable unknown rule(s): ' + missed)\\n }\\n return this\\n}\\n\\n/** chainable\\n * MarkdownIt.use(plugin, params)\\n *\\n * Load specified plugin with given params into current parser instance.\\n * It's just a sugar to call `plugin(md, params)` with curring.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var iterator = require('markdown-it-for-inline');\\n * var md = require('markdown-it')()\\n * .use(iterator, 'foo_replace', 'text', function (tokens, idx) {\\n * tokens[idx].content = tokens[idx].content.replace(/foo/g, 'bar');\\n * });\\n * ```\\n **/\\nMarkdownIt.prototype.use = function (plugin /*, params, ... */) {\\n const args = [this].concat(Array.prototype.slice.call(arguments, 1))\\n plugin.apply(plugin, args)\\n return this\\n}\\n\\n/** internal\\n * MarkdownIt.parse(src, env) -> Array\\n * - src (String): source string\\n * - env (Object): environment sandbox\\n *\\n * Parse input string and return list of block tokens (special token type\\n * \\\"inline\\\" will contain list of inline tokens). You should not call this\\n * method directly, until you write custom renderer (for example, to produce\\n * AST).\\n *\\n * `env` is used to pass data between \\\"distributed\\\" rules and return additional\\n * metadata like reference info, needed for the renderer. It also can be used to\\n * inject data in specific cases. Usually, you will be ok to pass `{}`,\\n * and then pass updated object to renderer.\\n **/\\nMarkdownIt.prototype.parse = function (src, env) {\\n if (typeof src !== 'string') {\\n throw new Error('Input data should be a String')\\n }\\n\\n const state = new this.core.State(src, this, env)\\n\\n this.core.process(state)\\n\\n return state.tokens\\n}\\n\\n/**\\n * MarkdownIt.render(src [, env]) -> String\\n * - src (String): source string\\n * - env (Object): environment sandbox\\n *\\n * Render markdown string into html. It does all magic for you :).\\n *\\n * `env` can be used to inject additional metadata (`{}` by default).\\n * But you will not need it with high probability. See also comment\\n * in [[MarkdownIt.parse]].\\n **/\\nMarkdownIt.prototype.render = function (src, env) {\\n env = env || {}\\n\\n return this.renderer.render(this.parse(src, env), this.options, env)\\n}\\n\\n/** internal\\n * MarkdownIt.parseInline(src, env) -> Array\\n * - src (String): source string\\n * - env (Object): environment sandbox\\n *\\n * The same as [[MarkdownIt.parse]] but skip all block rules. It returns the\\n * block tokens list with the single `inline` element, containing parsed inline\\n * tokens in `children` property. Also updates `env` object.\\n **/\\nMarkdownIt.prototype.parseInline = function (src, env) {\\n const state = new this.core.State(src, this, env)\\n\\n state.inlineMode = true\\n this.core.process(state)\\n\\n return state.tokens\\n}\\n\\n/**\\n * MarkdownIt.renderInline(src [, env]) -> String\\n * - src (String): source string\\n * - env (Object): environment sandbox\\n *\\n * Similar to [[MarkdownIt.render]] but for single paragraph content. Result\\n * will NOT be wrapped into `

` tags.\\n **/\\nMarkdownIt.prototype.renderInline = function (src, env) {\\n env = env || {}\\n\\n return this.renderer.render(this.parseInline(src, env), this.options, env)\\n}\\n\\nexport default MarkdownIt\\n\",\"import MarkdownIt from 'markdown-it';\\n\\nconst md = new MarkdownIt({\\n linkify: true,\\n});\\nconst source = Host.v1.document.get('text/markdown-case');\\nconst tokens = md.parse(source, {});\\nconst links = md.render(source).match(/ token.type),\\n tokenCount: tokens.length,\\n linkCount: links,\\n};\\n\"],\"version\":3}", + "originMeta": { + "originalPath": "node_modules/.pnpm/entities@4.5.0/node_modules/entities/lib/esm/decode.js", + "packageName": "entities", + "packageVersion": "4.5.0", + "integrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562" + } + } + ], + "builderVersion": "deterministic-builder-v1", + "dependencyIntegrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562", + "diagnosticsMeta": { + "entryPath": "/workspace/apps/ecosystem-certifier/fixtures/positive/markdown-it-entry.ts", + "modulePaths": [ + "./markdown-it-entry.js" + ] + }, + "graphHash": "6715cbd20f57956012dee5439799c99cde5890a813559ad2f7440e37c71896f8" + } + } + }, + "manifest": { + "abi_id": "Host.v1", + "abi_version": 1, + "functions": [ + { + "fn_id": 1, + "js_path": [ + "document", + "get" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 2, + "js_path": [ + "document", + "getCanonical" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 3, + "js_path": [ + "emit" + ], + "effect": "EMIT", + "arity": 1, + "arg_schema": [ + { + "type": "dv" + } + ], + "return_schema": { + "type": "null" + }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [ + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + } + ] + } + ] + } + }, + { + "id": "green-noble-sha", + "title": "@noble/hashes deterministic digest", + "kind": "ecosystem-green", + "badge": "Green ecosystem fixture", + "description": "A binary-heavy crypto-style fixture showing deterministic digest behavior.", + "certified": true, + "executionProfile": "compat-binary-v1", + "sourceKind": "module-pack", + "abiId": "Host.v2", + "gasLimit": "5000000", + "sourcePaths": [ + "libs/test-harness/fixtures/library-reuse/binary-sha256-entry.ts" + ], + "sourceText": "import { sha256 } from '@noble/hashes/sha256';\nimport { bytesToHex } from '@noble/hashes/utils';\n\nconst digest = sha256(\n Uint8Array.from([\n 98, 108, 117, 101, 45, 113, 117, 105, 99, 107, 106, 115, 45, 98, 105, 110,\n 97, 114, 121, 45, 102, 105, 120, 116, 117, 114, 101,\n ]),\n);\n\nexport default {\n hex: bytesToHex(digest),\n length: digest.length,\n first: digest[0],\n last: digest[digest.length - 1],\n};\n", + "hostPreset": "certification", + "hostSummary": { + "label": "Certification host", + "description": "Provides the ecosystem-certifier text and binary documents used for workload certification.", + "documents": [ + "pack/metadata.json", + "pack/metadata.yaml", + "docs/a.md", + "docs/b.md", + "docs/c.md", + "docs/d.md", + "bytes/payload", + "bytes/flagship-extra", + "pack/attachment.deflated" + ] + }, + "docsLinks": [ + { + "label": "Workload certification", + "href": "/docs/workload-certification.md" + }, + { + "label": "Compatibility report", + "href": "/docs/ecosystem-compatibility-report.md" + } + ], + "supportsOogSearch": false, + "program": { + "version": 2, + "abiId": "Host.v2", + "abiVersion": 2, + "abiManifestHash": "ec5c3df99a1b0ab84b692996193707ae6c931382e75c96c7c14b4f8baaae5af2", + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8, + "executionProfile": "compat-binary-v1", + "sourceKind": "module-pack", + "source": { + "modulePack": { + "version": 1, + "entrySpecifier": "./binary-sha256-entry.js", + "entryExport": "default", + "modules": [ + { + "specifier": "./binary-sha256-entry.js", + "source": "// node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/utils.js\nfunction isBytes(a) {\n return a instanceof Uint8Array || ArrayBuffer.isView(a) && a.constructor.name === \"Uint8Array\";\n}\nfunction abytes(b, ...lengths) {\n if (!isBytes(b))\n throw new Error(\"Uint8Array expected\");\n if (lengths.length > 0 && !lengths.includes(b.length))\n throw new Error(\"Uint8Array expected of length \" + lengths + \", got length=\" + b.length);\n}\nfunction aexists(instance, checkFinished = true) {\n if (instance.destroyed)\n throw new Error(\"Hash instance has been destroyed\");\n if (checkFinished && instance.finished)\n throw new Error(\"Hash#digest() has already been called\");\n}\nfunction aoutput(out, instance) {\n abytes(out);\n const min = instance.outputLen;\n if (out.length < min) {\n throw new Error(\"digestInto() expects output buffer of length at least \" + min);\n }\n}\nfunction clean(...arrays) {\n for (let i = 0; i < arrays.length; i++) {\n arrays[i].fill(0);\n }\n}\nfunction createView(arr) {\n return new DataView(arr.buffer, arr.byteOffset, arr.byteLength);\n}\nfunction rotr(word, shift) {\n return word << 32 - shift | word >>> shift;\n}\nvar hasHexBuiltin = /* @__PURE__ */ (() => (\n // @ts-ignore\n typeof Uint8Array.from([]).toHex === \"function\" && typeof Uint8Array.fromHex === \"function\"\n))();\nvar hexes = /* @__PURE__ */ Array.from({ length: 256 }, (_, i) => i.toString(16).padStart(2, \"0\"));\nfunction bytesToHex(bytes) {\n abytes(bytes);\n if (hasHexBuiltin)\n return bytes.toHex();\n let hex = \"\";\n for (let i = 0; i < bytes.length; i++) {\n hex += hexes[bytes[i]];\n }\n return hex;\n}\nfunction utf8ToBytes(str) {\n if (typeof str !== \"string\")\n throw new Error(\"string expected\");\n return new Uint8Array(new TextEncoder().encode(str));\n}\nfunction toBytes(data) {\n if (typeof data === \"string\")\n data = utf8ToBytes(data);\n abytes(data);\n return data;\n}\nvar Hash = class {\n};\nfunction createHasher(hashCons) {\n const hashC = (msg) => hashCons().update(toBytes(msg)).digest();\n const tmp = hashCons();\n hashC.outputLen = tmp.outputLen;\n hashC.blockLen = tmp.blockLen;\n hashC.create = () => hashCons();\n return hashC;\n}\n\n// node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/_md.js\nfunction setBigUint64(view, byteOffset, value, isLE) {\n if (typeof view.setBigUint64 === \"function\")\n return view.setBigUint64(byteOffset, value, isLE);\n const _32n = BigInt(32);\n const _u32_max = BigInt(4294967295);\n const wh = Number(value >> _32n & _u32_max);\n const wl = Number(value & _u32_max);\n const h = isLE ? 4 : 0;\n const l = isLE ? 0 : 4;\n view.setUint32(byteOffset + h, wh, isLE);\n view.setUint32(byteOffset + l, wl, isLE);\n}\nfunction Chi(a, b, c) {\n return a & b ^ ~a & c;\n}\nfunction Maj(a, b, c) {\n return a & b ^ a & c ^ b & c;\n}\nvar HashMD = class extends Hash {\n constructor(blockLen, outputLen, padOffset, isLE) {\n super();\n this.finished = false;\n this.length = 0;\n this.pos = 0;\n this.destroyed = false;\n this.blockLen = blockLen;\n this.outputLen = outputLen;\n this.padOffset = padOffset;\n this.isLE = isLE;\n this.buffer = new Uint8Array(blockLen);\n this.view = createView(this.buffer);\n }\n update(data) {\n aexists(this);\n data = toBytes(data);\n abytes(data);\n const { view, buffer, blockLen } = this;\n const len = data.length;\n for (let pos = 0; pos < len; ) {\n const take = Math.min(blockLen - this.pos, len - pos);\n if (take === blockLen) {\n const dataView = createView(data);\n for (; blockLen <= len - pos; pos += blockLen)\n this.process(dataView, pos);\n continue;\n }\n buffer.set(data.subarray(pos, pos + take), this.pos);\n this.pos += take;\n pos += take;\n if (this.pos === blockLen) {\n this.process(view, 0);\n this.pos = 0;\n }\n }\n this.length += data.length;\n this.roundClean();\n return this;\n }\n digestInto(out) {\n aexists(this);\n aoutput(out, this);\n this.finished = true;\n const { buffer, view, blockLen, isLE } = this;\n let { pos } = this;\n buffer[pos++] = 128;\n clean(this.buffer.subarray(pos));\n if (this.padOffset > blockLen - pos) {\n this.process(view, 0);\n pos = 0;\n }\n for (let i = pos; i < blockLen; i++)\n buffer[i] = 0;\n setBigUint64(view, blockLen - 8, BigInt(this.length * 8), isLE);\n this.process(view, 0);\n const oview = createView(out);\n const len = this.outputLen;\n if (len % 4)\n throw new Error(\"_sha2: outputLen should be aligned to 32bit\");\n const outLen = len / 4;\n const state = this.get();\n if (outLen > state.length)\n throw new Error(\"_sha2: outputLen bigger than state\");\n for (let i = 0; i < outLen; i++)\n oview.setUint32(4 * i, state[i], isLE);\n }\n digest() {\n const { buffer, outputLen } = this;\n this.digestInto(buffer);\n const res = buffer.slice(0, outputLen);\n this.destroy();\n return res;\n }\n _cloneInto(to) {\n to || (to = new this.constructor());\n to.set(...this.get());\n const { blockLen, buffer, length, finished, destroyed, pos } = this;\n to.destroyed = destroyed;\n to.finished = finished;\n to.length = length;\n to.pos = pos;\n if (length % blockLen)\n to.buffer.set(buffer);\n return to;\n }\n clone() {\n return this._cloneInto();\n }\n};\nvar SHA256_IV = /* @__PURE__ */ Uint32Array.from([\n 1779033703,\n 3144134277,\n 1013904242,\n 2773480762,\n 1359893119,\n 2600822924,\n 528734635,\n 1541459225\n]);\n\n// node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/sha2.js\nvar SHA256_K = /* @__PURE__ */ Uint32Array.from([\n 1116352408,\n 1899447441,\n 3049323471,\n 3921009573,\n 961987163,\n 1508970993,\n 2453635748,\n 2870763221,\n 3624381080,\n 310598401,\n 607225278,\n 1426881987,\n 1925078388,\n 2162078206,\n 2614888103,\n 3248222580,\n 3835390401,\n 4022224774,\n 264347078,\n 604807628,\n 770255983,\n 1249150122,\n 1555081692,\n 1996064986,\n 2554220882,\n 2821834349,\n 2952996808,\n 3210313671,\n 3336571891,\n 3584528711,\n 113926993,\n 338241895,\n 666307205,\n 773529912,\n 1294757372,\n 1396182291,\n 1695183700,\n 1986661051,\n 2177026350,\n 2456956037,\n 2730485921,\n 2820302411,\n 3259730800,\n 3345764771,\n 3516065817,\n 3600352804,\n 4094571909,\n 275423344,\n 430227734,\n 506948616,\n 659060556,\n 883997877,\n 958139571,\n 1322822218,\n 1537002063,\n 1747873779,\n 1955562222,\n 2024104815,\n 2227730452,\n 2361852424,\n 2428436474,\n 2756734187,\n 3204031479,\n 3329325298\n]);\nvar SHA256_W = /* @__PURE__ */ new Uint32Array(64);\nvar SHA256 = class extends HashMD {\n constructor(outputLen = 32) {\n super(64, outputLen, 8, false);\n this.A = SHA256_IV[0] | 0;\n this.B = SHA256_IV[1] | 0;\n this.C = SHA256_IV[2] | 0;\n this.D = SHA256_IV[3] | 0;\n this.E = SHA256_IV[4] | 0;\n this.F = SHA256_IV[5] | 0;\n this.G = SHA256_IV[6] | 0;\n this.H = SHA256_IV[7] | 0;\n }\n get() {\n const { A, B, C, D, E, F, G, H } = this;\n return [A, B, C, D, E, F, G, H];\n }\n // prettier-ignore\n set(A, B, C, D, E, F, G, H) {\n this.A = A | 0;\n this.B = B | 0;\n this.C = C | 0;\n this.D = D | 0;\n this.E = E | 0;\n this.F = F | 0;\n this.G = G | 0;\n this.H = H | 0;\n }\n process(view, offset) {\n for (let i = 0; i < 16; i++, offset += 4)\n SHA256_W[i] = view.getUint32(offset, false);\n for (let i = 16; i < 64; i++) {\n const W15 = SHA256_W[i - 15];\n const W2 = SHA256_W[i - 2];\n const s0 = rotr(W15, 7) ^ rotr(W15, 18) ^ W15 >>> 3;\n const s1 = rotr(W2, 17) ^ rotr(W2, 19) ^ W2 >>> 10;\n SHA256_W[i] = s1 + SHA256_W[i - 7] + s0 + SHA256_W[i - 16] | 0;\n }\n let { A, B, C, D, E, F, G, H } = this;\n for (let i = 0; i < 64; i++) {\n const sigma1 = rotr(E, 6) ^ rotr(E, 11) ^ rotr(E, 25);\n const T1 = H + sigma1 + Chi(E, F, G) + SHA256_K[i] + SHA256_W[i] | 0;\n const sigma0 = rotr(A, 2) ^ rotr(A, 13) ^ rotr(A, 22);\n const T2 = sigma0 + Maj(A, B, C) | 0;\n H = G;\n G = F;\n F = E;\n E = D + T1 | 0;\n D = C;\n C = B;\n B = A;\n A = T1 + T2 | 0;\n }\n A = A + this.A | 0;\n B = B + this.B | 0;\n C = C + this.C | 0;\n D = D + this.D | 0;\n E = E + this.E | 0;\n F = F + this.F | 0;\n G = G + this.G | 0;\n H = H + this.H | 0;\n this.set(A, B, C, D, E, F, G, H);\n }\n roundClean() {\n clean(SHA256_W);\n }\n destroy() {\n this.set(0, 0, 0, 0, 0, 0, 0, 0);\n clean(this.buffer);\n }\n};\nvar sha256 = /* @__PURE__ */ createHasher(() => new SHA256());\n\n// node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/sha256.js\nvar sha2562 = sha256;\n\n// libs/test-harness/fixtures/library-reuse/binary-sha256-entry.ts\nvar digest = sha2562(\n Uint8Array.from([\n 98,\n 108,\n 117,\n 101,\n 45,\n 113,\n 117,\n 105,\n 99,\n 107,\n 106,\n 115,\n 45,\n 98,\n 105,\n 110,\n 97,\n 114,\n 121,\n 45,\n 102,\n 105,\n 120,\n 116,\n 117,\n 114,\n 101\n ])\n);\nvar binary_sha256_entry_default = {\n hex: bytesToHex(digest),\n length: digest.length,\n first: digest[0],\n last: digest[digest.length - 1]\n};\nexport {\n binary_sha256_entry_default as default\n};\n", + "sourceMap": "{\"mappings\":\"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\",\"names\":[\"sha256\",\"sha256\"],\"sources\":[\"../node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/src/utils.ts\",\"../node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/src/_md.ts\",\"../node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/src/sha2.ts\",\"../node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/src/sha256.ts\",\"../libs/test-harness/fixtures/library-reuse/binary-sha256-entry.ts\"],\"sourcesContent\":[\"/**\\n * Utilities for hex, bytes, CSPRNG.\\n * @module\\n */\\n/*! noble-hashes - MIT License (c) 2022 Paul Miller (paulmillr.com) */\\n\\n// We use WebCrypto aka globalThis.crypto, which exists in browsers and node.js 16+.\\n// node.js versions earlier than v19 don't declare it in global scope.\\n// For node.js, package.json#exports field mapping rewrites import\\n// from `crypto` to `cryptoNode`, which imports native module.\\n// Makes the utils un-importable in browsers without a bundler.\\n// Once node.js 18 is deprecated (2025-04-30), we can just drop the import.\\nimport { crypto } from '@noble/hashes/crypto';\\n\\n/** Checks if something is Uint8Array. Be careful: nodejs Buffer will return true. */\\nexport function isBytes(a: unknown): a is Uint8Array {\\n return a instanceof Uint8Array || (ArrayBuffer.isView(a) && a.constructor.name === 'Uint8Array');\\n}\\n\\n/** Asserts something is positive integer. */\\nexport function anumber(n: number): void {\\n if (!Number.isSafeInteger(n) || n < 0) throw new Error('positive integer expected, got ' + n);\\n}\\n\\n/** Asserts something is Uint8Array. */\\nexport function abytes(b: Uint8Array | undefined, ...lengths: number[]): void {\\n if (!isBytes(b)) throw new Error('Uint8Array expected');\\n if (lengths.length > 0 && !lengths.includes(b.length))\\n throw new Error('Uint8Array expected of length ' + lengths + ', got length=' + b.length);\\n}\\n\\n/** Asserts something is hash */\\nexport function ahash(h: IHash): void {\\n if (typeof h !== 'function' || typeof h.create !== 'function')\\n throw new Error('Hash should be wrapped by utils.createHasher');\\n anumber(h.outputLen);\\n anumber(h.blockLen);\\n}\\n\\n/** Asserts a hash instance has not been destroyed / finished */\\nexport function aexists(instance: any, checkFinished = true): void {\\n if (instance.destroyed) throw new Error('Hash instance has been destroyed');\\n if (checkFinished && instance.finished) throw new Error('Hash#digest() has already been called');\\n}\\n\\n/** Asserts output is properly-sized byte array */\\nexport function aoutput(out: any, instance: any): void {\\n abytes(out);\\n const min = instance.outputLen;\\n if (out.length < min) {\\n throw new Error('digestInto() expects output buffer of length at least ' + min);\\n }\\n}\\n\\n/** Generic type encompassing 8/16/32-byte arrays - but not 64-byte. */\\n// prettier-ignore\\nexport type TypedArray = Int8Array | Uint8ClampedArray | Uint8Array |\\n Uint16Array | Int16Array | Uint32Array | Int32Array;\\n\\n/** Cast u8 / u16 / u32 to u8. */\\nexport function u8(arr: TypedArray): Uint8Array {\\n return new Uint8Array(arr.buffer, arr.byteOffset, arr.byteLength);\\n}\\n\\n/** Cast u8 / u16 / u32 to u32. */\\nexport function u32(arr: TypedArray): Uint32Array {\\n return new Uint32Array(arr.buffer, arr.byteOffset, Math.floor(arr.byteLength / 4));\\n}\\n\\n/** Zeroize a byte array. Warning: JS provides no guarantees. */\\nexport function clean(...arrays: TypedArray[]): void {\\n for (let i = 0; i < arrays.length; i++) {\\n arrays[i].fill(0);\\n }\\n}\\n\\n/** Create DataView of an array for easy byte-level manipulation. */\\nexport function createView(arr: TypedArray): DataView {\\n return new DataView(arr.buffer, arr.byteOffset, arr.byteLength);\\n}\\n\\n/** The rotate right (circular right shift) operation for uint32 */\\nexport function rotr(word: number, shift: number): number {\\n return (word << (32 - shift)) | (word >>> shift);\\n}\\n\\n/** The rotate left (circular left shift) operation for uint32 */\\nexport function rotl(word: number, shift: number): number {\\n return (word << shift) | ((word >>> (32 - shift)) >>> 0);\\n}\\n\\n/** Is current platform little-endian? Most are. Big-Endian platform: IBM */\\nexport const isLE: boolean = /* @__PURE__ */ (() =>\\n new Uint8Array(new Uint32Array([0x11223344]).buffer)[0] === 0x44)();\\n\\n/** The byte swap operation for uint32 */\\nexport function byteSwap(word: number): number {\\n return (\\n ((word << 24) & 0xff000000) |\\n ((word << 8) & 0xff0000) |\\n ((word >>> 8) & 0xff00) |\\n ((word >>> 24) & 0xff)\\n );\\n}\\n/** Conditionally byte swap if on a big-endian platform */\\nexport const swap8IfBE: (n: number) => number = isLE\\n ? (n: number) => n\\n : (n: number) => byteSwap(n);\\n\\n/** @deprecated */\\nexport const byteSwapIfBE: typeof swap8IfBE = swap8IfBE;\\n/** In place byte swap for Uint32Array */\\nexport function byteSwap32(arr: Uint32Array): Uint32Array {\\n for (let i = 0; i < arr.length; i++) {\\n arr[i] = byteSwap(arr[i]);\\n }\\n return arr;\\n}\\n\\nexport const swap32IfBE: (u: Uint32Array) => Uint32Array = isLE\\n ? (u: Uint32Array) => u\\n : byteSwap32;\\n\\n// Built-in hex conversion https://caniuse.com/mdn-javascript_builtins_uint8array_fromhex\\nconst hasHexBuiltin: boolean = /* @__PURE__ */ (() =>\\n // @ts-ignore\\n typeof Uint8Array.from([]).toHex === 'function' && typeof Uint8Array.fromHex === 'function')();\\n\\n// Array where index 0xf0 (240) is mapped to string 'f0'\\nconst hexes = /* @__PURE__ */ Array.from({ length: 256 }, (_, i) =>\\n i.toString(16).padStart(2, '0')\\n);\\n\\n/**\\n * Convert byte array to hex string. Uses built-in function, when available.\\n * @example bytesToHex(Uint8Array.from([0xca, 0xfe, 0x01, 0x23])) // 'cafe0123'\\n */\\nexport function bytesToHex(bytes: Uint8Array): string {\\n abytes(bytes);\\n // @ts-ignore\\n if (hasHexBuiltin) return bytes.toHex();\\n // pre-caching improves the speed 6x\\n let hex = '';\\n for (let i = 0; i < bytes.length; i++) {\\n hex += hexes[bytes[i]];\\n }\\n return hex;\\n}\\n\\n// We use optimized technique to convert hex string to byte array\\nconst asciis = { _0: 48, _9: 57, A: 65, F: 70, a: 97, f: 102 } as const;\\nfunction asciiToBase16(ch: number): number | undefined {\\n if (ch >= asciis._0 && ch <= asciis._9) return ch - asciis._0; // '2' => 50-48\\n if (ch >= asciis.A && ch <= asciis.F) return ch - (asciis.A - 10); // 'B' => 66-(65-10)\\n if (ch >= asciis.a && ch <= asciis.f) return ch - (asciis.a - 10); // 'b' => 98-(97-10)\\n return;\\n}\\n\\n/**\\n * Convert hex string to byte array. Uses built-in function, when available.\\n * @example hexToBytes('cafe0123') // Uint8Array.from([0xca, 0xfe, 0x01, 0x23])\\n */\\nexport function hexToBytes(hex: string): Uint8Array {\\n if (typeof hex !== 'string') throw new Error('hex string expected, got ' + typeof hex);\\n // @ts-ignore\\n if (hasHexBuiltin) return Uint8Array.fromHex(hex);\\n const hl = hex.length;\\n const al = hl / 2;\\n if (hl % 2) throw new Error('hex string expected, got unpadded hex of length ' + hl);\\n const array = new Uint8Array(al);\\n for (let ai = 0, hi = 0; ai < al; ai++, hi += 2) {\\n const n1 = asciiToBase16(hex.charCodeAt(hi));\\n const n2 = asciiToBase16(hex.charCodeAt(hi + 1));\\n if (n1 === undefined || n2 === undefined) {\\n const char = hex[hi] + hex[hi + 1];\\n throw new Error('hex string expected, got non-hex character \\\"' + char + '\\\" at index ' + hi);\\n }\\n array[ai] = n1 * 16 + n2; // multiply first octet, e.g. 'a3' => 10*16+3 => 160 + 3 => 163\\n }\\n return array;\\n}\\n\\n/**\\n * There is no setImmediate in browser and setTimeout is slow.\\n * Call of async fn will return Promise, which will be fullfiled only on\\n * next scheduler queue processing step and this is exactly what we need.\\n */\\nexport const nextTick = async (): Promise => {};\\n\\n/** Returns control to thread each 'tick' ms to avoid blocking. */\\nexport async function asyncLoop(\\n iters: number,\\n tick: number,\\n cb: (i: number) => void\\n): Promise {\\n let ts = Date.now();\\n for (let i = 0; i < iters; i++) {\\n cb(i);\\n // Date.now() is not monotonic, so in case if clock goes backwards we return return control too\\n const diff = Date.now() - ts;\\n if (diff >= 0 && diff < tick) continue;\\n await nextTick();\\n ts += diff;\\n }\\n}\\n\\n// Global symbols, but ts doesn't see them: https://github.com/microsoft/TypeScript/issues/31535\\ndeclare const TextEncoder: any;\\ndeclare const TextDecoder: any;\\n\\n/**\\n * Converts string to bytes using UTF8 encoding.\\n * @example utf8ToBytes('abc') // Uint8Array.from([97, 98, 99])\\n */\\nexport function utf8ToBytes(str: string): Uint8Array {\\n if (typeof str !== 'string') throw new Error('string expected');\\n return new Uint8Array(new TextEncoder().encode(str)); // https://bugzil.la/1681809\\n}\\n\\n/**\\n * Converts bytes to string using UTF8 encoding.\\n * @example bytesToUtf8(Uint8Array.from([97, 98, 99])) // 'abc'\\n */\\nexport function bytesToUtf8(bytes: Uint8Array): string {\\n return new TextDecoder().decode(bytes);\\n}\\n\\n/** Accepted input of hash functions. Strings are converted to byte arrays. */\\nexport type Input = string | Uint8Array;\\n/**\\n * Normalizes (non-hex) string or Uint8Array to Uint8Array.\\n * Warning: when Uint8Array is passed, it would NOT get copied.\\n * Keep in mind for future mutable operations.\\n */\\nexport function toBytes(data: Input): Uint8Array {\\n if (typeof data === 'string') data = utf8ToBytes(data);\\n abytes(data);\\n return data;\\n}\\n\\n/** KDFs can accept string or Uint8Array for user convenience. */\\nexport type KDFInput = string | Uint8Array;\\n/**\\n * Helper for KDFs: consumes uint8array or string.\\n * When string is passed, does utf8 decoding, using TextDecoder.\\n */\\nexport function kdfInputToBytes(data: KDFInput): Uint8Array {\\n if (typeof data === 'string') data = utf8ToBytes(data);\\n abytes(data);\\n return data;\\n}\\n\\n/** Copies several Uint8Arrays into one. */\\nexport function concatBytes(...arrays: Uint8Array[]): Uint8Array {\\n let sum = 0;\\n for (let i = 0; i < arrays.length; i++) {\\n const a = arrays[i];\\n abytes(a);\\n sum += a.length;\\n }\\n const res = new Uint8Array(sum);\\n for (let i = 0, pad = 0; i < arrays.length; i++) {\\n const a = arrays[i];\\n res.set(a, pad);\\n pad += a.length;\\n }\\n return res;\\n}\\n\\ntype EmptyObj = {};\\nexport function checkOpts(\\n defaults: T1,\\n opts?: T2\\n): T1 & T2 {\\n if (opts !== undefined && {}.toString.call(opts) !== '[object Object]')\\n throw new Error('options should be object or undefined');\\n const merged = Object.assign(defaults, opts);\\n return merged as T1 & T2;\\n}\\n\\n/** Hash interface. */\\nexport type IHash = {\\n (data: Uint8Array): Uint8Array;\\n blockLen: number;\\n outputLen: number;\\n create: any;\\n};\\n\\n/** For runtime check if class implements interface */\\nexport abstract class Hash> {\\n abstract blockLen: number; // Bytes per block\\n abstract outputLen: number; // Bytes in output\\n abstract update(buf: Input): this;\\n // Writes digest into buf\\n abstract digestInto(buf: Uint8Array): void;\\n abstract digest(): Uint8Array;\\n /**\\n * Resets internal state. Makes Hash instance unusable.\\n * Reset is impossible for keyed hashes if key is consumed into state. If digest is not consumed\\n * by user, they will need to manually call `destroy()` when zeroing is necessary.\\n */\\n abstract destroy(): void;\\n /**\\n * Clones hash instance. Unsafe: doesn't check whether `to` is valid. Can be used as `clone()`\\n * when no options are passed.\\n * Reasons to use `_cloneInto` instead of clone: 1) performance 2) reuse instance => all internal\\n * buffers are overwritten => causes buffer overwrite which is used for digest in some cases.\\n * There are no guarantees for clean-up because it's impossible in JS.\\n */\\n abstract _cloneInto(to?: T): T;\\n // Safe version that clones internal state\\n abstract clone(): T;\\n}\\n\\n/**\\n * XOF: streaming API to read digest in chunks.\\n * Same as 'squeeze' in keccak/k12 and 'seek' in blake3, but more generic name.\\n * When hash used in XOF mode it is up to user to call '.destroy' afterwards, since we cannot\\n * destroy state, next call can require more bytes.\\n */\\nexport type HashXOF> = Hash & {\\n xof(bytes: number): Uint8Array; // Read 'bytes' bytes from digest stream\\n xofInto(buf: Uint8Array): Uint8Array; // read buf.length bytes from digest stream into buf\\n};\\n\\n/** Hash function */\\nexport type CHash = ReturnType;\\n/** Hash function with output */\\nexport type CHashO = ReturnType;\\n/** XOF with output */\\nexport type CHashXO = ReturnType;\\n\\n/** Wraps hash function, creating an interface on top of it */\\nexport function createHasher>(\\n hashCons: () => Hash\\n): {\\n (msg: Input): Uint8Array;\\n outputLen: number;\\n blockLen: number;\\n create(): Hash;\\n} {\\n const hashC = (msg: Input): Uint8Array => hashCons().update(toBytes(msg)).digest();\\n const tmp = hashCons();\\n hashC.outputLen = tmp.outputLen;\\n hashC.blockLen = tmp.blockLen;\\n hashC.create = () => hashCons();\\n return hashC;\\n}\\n\\nexport function createOptHasher, T extends Object>(\\n hashCons: (opts?: T) => Hash\\n): {\\n (msg: Input, opts?: T): Uint8Array;\\n outputLen: number;\\n blockLen: number;\\n create(opts?: T): Hash;\\n} {\\n const hashC = (msg: Input, opts?: T): Uint8Array => hashCons(opts).update(toBytes(msg)).digest();\\n const tmp = hashCons({} as T);\\n hashC.outputLen = tmp.outputLen;\\n hashC.blockLen = tmp.blockLen;\\n hashC.create = (opts?: T) => hashCons(opts);\\n return hashC;\\n}\\n\\nexport function createXOFer, T extends Object>(\\n hashCons: (opts?: T) => HashXOF\\n): {\\n (msg: Input, opts?: T): Uint8Array;\\n outputLen: number;\\n blockLen: number;\\n create(opts?: T): HashXOF;\\n} {\\n const hashC = (msg: Input, opts?: T): Uint8Array => hashCons(opts).update(toBytes(msg)).digest();\\n const tmp = hashCons({} as T);\\n hashC.outputLen = tmp.outputLen;\\n hashC.blockLen = tmp.blockLen;\\n hashC.create = (opts?: T) => hashCons(opts);\\n return hashC;\\n}\\nexport const wrapConstructor: typeof createHasher = createHasher;\\nexport const wrapConstructorWithOpts: typeof createOptHasher = createOptHasher;\\nexport const wrapXOFConstructorWithOpts: typeof createXOFer = createXOFer;\\n\\n/** Cryptographically secure PRNG. Uses internal OS-level `crypto.getRandomValues`. */\\nexport function randomBytes(bytesLength = 32): Uint8Array {\\n if (crypto && typeof crypto.getRandomValues === 'function') {\\n return crypto.getRandomValues(new Uint8Array(bytesLength));\\n }\\n // Legacy Node.js compatibility\\n if (crypto && typeof crypto.randomBytes === 'function') {\\n return Uint8Array.from(crypto.randomBytes(bytesLength));\\n }\\n throw new Error('crypto.getRandomValues must be defined');\\n}\\n\",\"/**\\n * Internal Merkle-Damgard hash utils.\\n * @module\\n */\\nimport { type Input, Hash, abytes, aexists, aoutput, clean, createView, toBytes } from './utils.ts';\\n\\n/** Polyfill for Safari 14. https://caniuse.com/mdn-javascript_builtins_dataview_setbiguint64 */\\nexport function setBigUint64(\\n view: DataView,\\n byteOffset: number,\\n value: bigint,\\n isLE: boolean\\n): void {\\n if (typeof view.setBigUint64 === 'function') return view.setBigUint64(byteOffset, value, isLE);\\n const _32n = BigInt(32);\\n const _u32_max = BigInt(0xffffffff);\\n const wh = Number((value >> _32n) & _u32_max);\\n const wl = Number(value & _u32_max);\\n const h = isLE ? 4 : 0;\\n const l = isLE ? 0 : 4;\\n view.setUint32(byteOffset + h, wh, isLE);\\n view.setUint32(byteOffset + l, wl, isLE);\\n}\\n\\n/** Choice: a ? b : c */\\nexport function Chi(a: number, b: number, c: number): number {\\n return (a & b) ^ (~a & c);\\n}\\n\\n/** Majority function, true if any two inputs is true. */\\nexport function Maj(a: number, b: number, c: number): number {\\n return (a & b) ^ (a & c) ^ (b & c);\\n}\\n\\n/**\\n * Merkle-Damgard hash construction base class.\\n * Could be used to create MD5, RIPEMD, SHA1, SHA2.\\n */\\nexport abstract class HashMD> extends Hash {\\n protected abstract process(buf: DataView, offset: number): void;\\n protected abstract get(): number[];\\n protected abstract set(...args: number[]): void;\\n abstract destroy(): void;\\n protected abstract roundClean(): void;\\n\\n readonly blockLen: number;\\n readonly outputLen: number;\\n readonly padOffset: number;\\n readonly isLE: boolean;\\n\\n // For partial updates less than block size\\n protected buffer: Uint8Array;\\n protected view: DataView;\\n protected finished = false;\\n protected length = 0;\\n protected pos = 0;\\n protected destroyed = false;\\n\\n constructor(blockLen: number, outputLen: number, padOffset: number, isLE: boolean) {\\n super();\\n this.blockLen = blockLen;\\n this.outputLen = outputLen;\\n this.padOffset = padOffset;\\n this.isLE = isLE;\\n this.buffer = new Uint8Array(blockLen);\\n this.view = createView(this.buffer);\\n }\\n update(data: Input): this {\\n aexists(this);\\n data = toBytes(data);\\n abytes(data);\\n const { view, buffer, blockLen } = this;\\n const len = data.length;\\n for (let pos = 0; pos < len; ) {\\n const take = Math.min(blockLen - this.pos, len - pos);\\n // Fast path: we have at least one block in input, cast it to view and process\\n if (take === blockLen) {\\n const dataView = createView(data);\\n for (; blockLen <= len - pos; pos += blockLen) this.process(dataView, pos);\\n continue;\\n }\\n buffer.set(data.subarray(pos, pos + take), this.pos);\\n this.pos += take;\\n pos += take;\\n if (this.pos === blockLen) {\\n this.process(view, 0);\\n this.pos = 0;\\n }\\n }\\n this.length += data.length;\\n this.roundClean();\\n return this;\\n }\\n digestInto(out: Uint8Array): void {\\n aexists(this);\\n aoutput(out, this);\\n this.finished = true;\\n // Padding\\n // We can avoid allocation of buffer for padding completely if it\\n // was previously not allocated here. But it won't change performance.\\n const { buffer, view, blockLen, isLE } = this;\\n let { pos } = this;\\n // append the bit '1' to the message\\n buffer[pos++] = 0b10000000;\\n clean(this.buffer.subarray(pos));\\n // we have less than padOffset left in buffer, so we cannot put length in\\n // current block, need process it and pad again\\n if (this.padOffset > blockLen - pos) {\\n this.process(view, 0);\\n pos = 0;\\n }\\n // Pad until full block byte with zeros\\n for (let i = pos; i < blockLen; i++) buffer[i] = 0;\\n // Note: sha512 requires length to be 128bit integer, but length in JS will overflow before that\\n // You need to write around 2 exabytes (u64_max / 8 / (1024**6)) for this to happen.\\n // So we just write lowest 64 bits of that value.\\n setBigUint64(view, blockLen - 8, BigInt(this.length * 8), isLE);\\n this.process(view, 0);\\n const oview = createView(out);\\n const len = this.outputLen;\\n // NOTE: we do division by 4 later, which should be fused in single op with modulo by JIT\\n if (len % 4) throw new Error('_sha2: outputLen should be aligned to 32bit');\\n const outLen = len / 4;\\n const state = this.get();\\n if (outLen > state.length) throw new Error('_sha2: outputLen bigger than state');\\n for (let i = 0; i < outLen; i++) oview.setUint32(4 * i, state[i], isLE);\\n }\\n digest(): Uint8Array {\\n const { buffer, outputLen } = this;\\n this.digestInto(buffer);\\n const res = buffer.slice(0, outputLen);\\n this.destroy();\\n return res;\\n }\\n _cloneInto(to?: T): T {\\n to ||= new (this.constructor as any)() as T;\\n to.set(...this.get());\\n const { blockLen, buffer, length, finished, destroyed, pos } = this;\\n to.destroyed = destroyed;\\n to.finished = finished;\\n to.length = length;\\n to.pos = pos;\\n if (length % blockLen) to.buffer.set(buffer);\\n return to;\\n }\\n clone(): T {\\n return this._cloneInto();\\n }\\n}\\n\\n/**\\n * Initial SHA-2 state: fractional parts of square roots of first 16 primes 2..53.\\n * Check out `test/misc/sha2-gen-iv.js` for recomputation guide.\\n */\\n\\n/** Initial SHA256 state. Bits 0..32 of frac part of sqrt of primes 2..19 */\\nexport const SHA256_IV: Uint32Array = /* @__PURE__ */ Uint32Array.from([\\n 0x6a09e667, 0xbb67ae85, 0x3c6ef372, 0xa54ff53a, 0x510e527f, 0x9b05688c, 0x1f83d9ab, 0x5be0cd19,\\n]);\\n\\n/** Initial SHA224 state. Bits 32..64 of frac part of sqrt of primes 23..53 */\\nexport const SHA224_IV: Uint32Array = /* @__PURE__ */ Uint32Array.from([\\n 0xc1059ed8, 0x367cd507, 0x3070dd17, 0xf70e5939, 0xffc00b31, 0x68581511, 0x64f98fa7, 0xbefa4fa4,\\n]);\\n\\n/** Initial SHA384 state. Bits 0..64 of frac part of sqrt of primes 23..53 */\\nexport const SHA384_IV: Uint32Array = /* @__PURE__ */ Uint32Array.from([\\n 0xcbbb9d5d, 0xc1059ed8, 0x629a292a, 0x367cd507, 0x9159015a, 0x3070dd17, 0x152fecd8, 0xf70e5939,\\n 0x67332667, 0xffc00b31, 0x8eb44a87, 0x68581511, 0xdb0c2e0d, 0x64f98fa7, 0x47b5481d, 0xbefa4fa4,\\n]);\\n\\n/** Initial SHA512 state. Bits 0..64 of frac part of sqrt of primes 2..19 */\\nexport const SHA512_IV: Uint32Array = /* @__PURE__ */ Uint32Array.from([\\n 0x6a09e667, 0xf3bcc908, 0xbb67ae85, 0x84caa73b, 0x3c6ef372, 0xfe94f82b, 0xa54ff53a, 0x5f1d36f1,\\n 0x510e527f, 0xade682d1, 0x9b05688c, 0x2b3e6c1f, 0x1f83d9ab, 0xfb41bd6b, 0x5be0cd19, 0x137e2179,\\n]);\\n\",\"/**\\n * SHA2 hash function. A.k.a. sha256, sha384, sha512, sha512_224, sha512_256.\\n * SHA256 is the fastest hash implementable in JS, even faster than Blake3.\\n * Check out [RFC 4634](https://datatracker.ietf.org/doc/html/rfc4634) and\\n * [FIPS 180-4](https://nvlpubs.nist.gov/nistpubs/FIPS/NIST.FIPS.180-4.pdf).\\n * @module\\n */\\nimport { Chi, HashMD, Maj, SHA224_IV, SHA256_IV, SHA384_IV, SHA512_IV } from './_md.ts';\\nimport * as u64 from './_u64.ts';\\nimport { type CHash, clean, createHasher, rotr } from './utils.ts';\\n\\n/**\\n * Round constants:\\n * First 32 bits of fractional parts of the cube roots of the first 64 primes 2..311)\\n */\\n// prettier-ignore\\nconst SHA256_K = /* @__PURE__ */ Uint32Array.from([\\n 0x428a2f98, 0x71374491, 0xb5c0fbcf, 0xe9b5dba5, 0x3956c25b, 0x59f111f1, 0x923f82a4, 0xab1c5ed5,\\n 0xd807aa98, 0x12835b01, 0x243185be, 0x550c7dc3, 0x72be5d74, 0x80deb1fe, 0x9bdc06a7, 0xc19bf174,\\n 0xe49b69c1, 0xefbe4786, 0x0fc19dc6, 0x240ca1cc, 0x2de92c6f, 0x4a7484aa, 0x5cb0a9dc, 0x76f988da,\\n 0x983e5152, 0xa831c66d, 0xb00327c8, 0xbf597fc7, 0xc6e00bf3, 0xd5a79147, 0x06ca6351, 0x14292967,\\n 0x27b70a85, 0x2e1b2138, 0x4d2c6dfc, 0x53380d13, 0x650a7354, 0x766a0abb, 0x81c2c92e, 0x92722c85,\\n 0xa2bfe8a1, 0xa81a664b, 0xc24b8b70, 0xc76c51a3, 0xd192e819, 0xd6990624, 0xf40e3585, 0x106aa070,\\n 0x19a4c116, 0x1e376c08, 0x2748774c, 0x34b0bcb5, 0x391c0cb3, 0x4ed8aa4a, 0x5b9cca4f, 0x682e6ff3,\\n 0x748f82ee, 0x78a5636f, 0x84c87814, 0x8cc70208, 0x90befffa, 0xa4506ceb, 0xbef9a3f7, 0xc67178f2\\n]);\\n\\n/** Reusable temporary buffer. \\\"W\\\" comes straight from spec. */\\nconst SHA256_W = /* @__PURE__ */ new Uint32Array(64);\\nexport class SHA256 extends HashMD {\\n // We cannot use array here since array allows indexing by variable\\n // which means optimizer/compiler cannot use registers.\\n protected A: number = SHA256_IV[0] | 0;\\n protected B: number = SHA256_IV[1] | 0;\\n protected C: number = SHA256_IV[2] | 0;\\n protected D: number = SHA256_IV[3] | 0;\\n protected E: number = SHA256_IV[4] | 0;\\n protected F: number = SHA256_IV[5] | 0;\\n protected G: number = SHA256_IV[6] | 0;\\n protected H: number = SHA256_IV[7] | 0;\\n\\n constructor(outputLen: number = 32) {\\n super(64, outputLen, 8, false);\\n }\\n protected get(): [number, number, number, number, number, number, number, number] {\\n const { A, B, C, D, E, F, G, H } = this;\\n return [A, B, C, D, E, F, G, H];\\n }\\n // prettier-ignore\\n protected set(\\n A: number, B: number, C: number, D: number, E: number, F: number, G: number, H: number\\n ): void {\\n this.A = A | 0;\\n this.B = B | 0;\\n this.C = C | 0;\\n this.D = D | 0;\\n this.E = E | 0;\\n this.F = F | 0;\\n this.G = G | 0;\\n this.H = H | 0;\\n }\\n protected process(view: DataView, offset: number): void {\\n // Extend the first 16 words into the remaining 48 words w[16..63] of the message schedule array\\n for (let i = 0; i < 16; i++, offset += 4) SHA256_W[i] = view.getUint32(offset, false);\\n for (let i = 16; i < 64; i++) {\\n const W15 = SHA256_W[i - 15];\\n const W2 = SHA256_W[i - 2];\\n const s0 = rotr(W15, 7) ^ rotr(W15, 18) ^ (W15 >>> 3);\\n const s1 = rotr(W2, 17) ^ rotr(W2, 19) ^ (W2 >>> 10);\\n SHA256_W[i] = (s1 + SHA256_W[i - 7] + s0 + SHA256_W[i - 16]) | 0;\\n }\\n // Compression function main loop, 64 rounds\\n let { A, B, C, D, E, F, G, H } = this;\\n for (let i = 0; i < 64; i++) {\\n const sigma1 = rotr(E, 6) ^ rotr(E, 11) ^ rotr(E, 25);\\n const T1 = (H + sigma1 + Chi(E, F, G) + SHA256_K[i] + SHA256_W[i]) | 0;\\n const sigma0 = rotr(A, 2) ^ rotr(A, 13) ^ rotr(A, 22);\\n const T2 = (sigma0 + Maj(A, B, C)) | 0;\\n H = G;\\n G = F;\\n F = E;\\n E = (D + T1) | 0;\\n D = C;\\n C = B;\\n B = A;\\n A = (T1 + T2) | 0;\\n }\\n // Add the compressed chunk to the current hash value\\n A = (A + this.A) | 0;\\n B = (B + this.B) | 0;\\n C = (C + this.C) | 0;\\n D = (D + this.D) | 0;\\n E = (E + this.E) | 0;\\n F = (F + this.F) | 0;\\n G = (G + this.G) | 0;\\n H = (H + this.H) | 0;\\n this.set(A, B, C, D, E, F, G, H);\\n }\\n protected roundClean(): void {\\n clean(SHA256_W);\\n }\\n destroy(): void {\\n this.set(0, 0, 0, 0, 0, 0, 0, 0);\\n clean(this.buffer);\\n }\\n}\\n\\nexport class SHA224 extends SHA256 {\\n protected A: number = SHA224_IV[0] | 0;\\n protected B: number = SHA224_IV[1] | 0;\\n protected C: number = SHA224_IV[2] | 0;\\n protected D: number = SHA224_IV[3] | 0;\\n protected E: number = SHA224_IV[4] | 0;\\n protected F: number = SHA224_IV[5] | 0;\\n protected G: number = SHA224_IV[6] | 0;\\n protected H: number = SHA224_IV[7] | 0;\\n constructor() {\\n super(28);\\n }\\n}\\n\\n// SHA2-512 is slower than sha256 in js because u64 operations are slow.\\n\\n// Round contants\\n// First 32 bits of the fractional parts of the cube roots of the first 80 primes 2..409\\n// prettier-ignore\\nconst K512 = /* @__PURE__ */ (() => u64.split([\\n '0x428a2f98d728ae22', '0x7137449123ef65cd', '0xb5c0fbcfec4d3b2f', '0xe9b5dba58189dbbc',\\n '0x3956c25bf348b538', '0x59f111f1b605d019', '0x923f82a4af194f9b', '0xab1c5ed5da6d8118',\\n '0xd807aa98a3030242', '0x12835b0145706fbe', '0x243185be4ee4b28c', '0x550c7dc3d5ffb4e2',\\n '0x72be5d74f27b896f', '0x80deb1fe3b1696b1', '0x9bdc06a725c71235', '0xc19bf174cf692694',\\n '0xe49b69c19ef14ad2', '0xefbe4786384f25e3', '0x0fc19dc68b8cd5b5', '0x240ca1cc77ac9c65',\\n '0x2de92c6f592b0275', '0x4a7484aa6ea6e483', '0x5cb0a9dcbd41fbd4', '0x76f988da831153b5',\\n '0x983e5152ee66dfab', '0xa831c66d2db43210', '0xb00327c898fb213f', '0xbf597fc7beef0ee4',\\n '0xc6e00bf33da88fc2', '0xd5a79147930aa725', '0x06ca6351e003826f', '0x142929670a0e6e70',\\n '0x27b70a8546d22ffc', '0x2e1b21385c26c926', '0x4d2c6dfc5ac42aed', '0x53380d139d95b3df',\\n '0x650a73548baf63de', '0x766a0abb3c77b2a8', '0x81c2c92e47edaee6', '0x92722c851482353b',\\n '0xa2bfe8a14cf10364', '0xa81a664bbc423001', '0xc24b8b70d0f89791', '0xc76c51a30654be30',\\n '0xd192e819d6ef5218', '0xd69906245565a910', '0xf40e35855771202a', '0x106aa07032bbd1b8',\\n '0x19a4c116b8d2d0c8', '0x1e376c085141ab53', '0x2748774cdf8eeb99', '0x34b0bcb5e19b48a8',\\n '0x391c0cb3c5c95a63', '0x4ed8aa4ae3418acb', '0x5b9cca4f7763e373', '0x682e6ff3d6b2b8a3',\\n '0x748f82ee5defb2fc', '0x78a5636f43172f60', '0x84c87814a1f0ab72', '0x8cc702081a6439ec',\\n '0x90befffa23631e28', '0xa4506cebde82bde9', '0xbef9a3f7b2c67915', '0xc67178f2e372532b',\\n '0xca273eceea26619c', '0xd186b8c721c0c207', '0xeada7dd6cde0eb1e', '0xf57d4f7fee6ed178',\\n '0x06f067aa72176fba', '0x0a637dc5a2c898a6', '0x113f9804bef90dae', '0x1b710b35131c471b',\\n '0x28db77f523047d84', '0x32caab7b40c72493', '0x3c9ebe0a15c9bebc', '0x431d67c49c100d4c',\\n '0x4cc5d4becb3e42b6', '0x597f299cfc657e2a', '0x5fcb6fab3ad6faec', '0x6c44198c4a475817'\\n].map(n => BigInt(n))))();\\nconst SHA512_Kh = /* @__PURE__ */ (() => K512[0])();\\nconst SHA512_Kl = /* @__PURE__ */ (() => K512[1])();\\n\\n// Reusable temporary buffers\\nconst SHA512_W_H = /* @__PURE__ */ new Uint32Array(80);\\nconst SHA512_W_L = /* @__PURE__ */ new Uint32Array(80);\\n\\nexport class SHA512 extends HashMD {\\n // We cannot use array here since array allows indexing by variable\\n // which means optimizer/compiler cannot use registers.\\n // h -- high 32 bits, l -- low 32 bits\\n protected Ah: number = SHA512_IV[0] | 0;\\n protected Al: number = SHA512_IV[1] | 0;\\n protected Bh: number = SHA512_IV[2] | 0;\\n protected Bl: number = SHA512_IV[3] | 0;\\n protected Ch: number = SHA512_IV[4] | 0;\\n protected Cl: number = SHA512_IV[5] | 0;\\n protected Dh: number = SHA512_IV[6] | 0;\\n protected Dl: number = SHA512_IV[7] | 0;\\n protected Eh: number = SHA512_IV[8] | 0;\\n protected El: number = SHA512_IV[9] | 0;\\n protected Fh: number = SHA512_IV[10] | 0;\\n protected Fl: number = SHA512_IV[11] | 0;\\n protected Gh: number = SHA512_IV[12] | 0;\\n protected Gl: number = SHA512_IV[13] | 0;\\n protected Hh: number = SHA512_IV[14] | 0;\\n protected Hl: number = SHA512_IV[15] | 0;\\n\\n constructor(outputLen: number = 64) {\\n super(128, outputLen, 16, false);\\n }\\n // prettier-ignore\\n protected get(): [\\n number, number, number, number, number, number, number, number,\\n number, number, number, number, number, number, number, number\\n ] {\\n const { Ah, Al, Bh, Bl, Ch, Cl, Dh, Dl, Eh, El, Fh, Fl, Gh, Gl, Hh, Hl } = this;\\n return [Ah, Al, Bh, Bl, Ch, Cl, Dh, Dl, Eh, El, Fh, Fl, Gh, Gl, Hh, Hl];\\n }\\n // prettier-ignore\\n protected set(\\n Ah: number, Al: number, Bh: number, Bl: number, Ch: number, Cl: number, Dh: number, Dl: number,\\n Eh: number, El: number, Fh: number, Fl: number, Gh: number, Gl: number, Hh: number, Hl: number\\n ): void {\\n this.Ah = Ah | 0;\\n this.Al = Al | 0;\\n this.Bh = Bh | 0;\\n this.Bl = Bl | 0;\\n this.Ch = Ch | 0;\\n this.Cl = Cl | 0;\\n this.Dh = Dh | 0;\\n this.Dl = Dl | 0;\\n this.Eh = Eh | 0;\\n this.El = El | 0;\\n this.Fh = Fh | 0;\\n this.Fl = Fl | 0;\\n this.Gh = Gh | 0;\\n this.Gl = Gl | 0;\\n this.Hh = Hh | 0;\\n this.Hl = Hl | 0;\\n }\\n protected process(view: DataView, offset: number): void {\\n // Extend the first 16 words into the remaining 64 words w[16..79] of the message schedule array\\n for (let i = 0; i < 16; i++, offset += 4) {\\n SHA512_W_H[i] = view.getUint32(offset);\\n SHA512_W_L[i] = view.getUint32((offset += 4));\\n }\\n for (let i = 16; i < 80; i++) {\\n // s0 := (w[i-15] rightrotate 1) xor (w[i-15] rightrotate 8) xor (w[i-15] rightshift 7)\\n const W15h = SHA512_W_H[i - 15] | 0;\\n const W15l = SHA512_W_L[i - 15] | 0;\\n const s0h = u64.rotrSH(W15h, W15l, 1) ^ u64.rotrSH(W15h, W15l, 8) ^ u64.shrSH(W15h, W15l, 7);\\n const s0l = u64.rotrSL(W15h, W15l, 1) ^ u64.rotrSL(W15h, W15l, 8) ^ u64.shrSL(W15h, W15l, 7);\\n // s1 := (w[i-2] rightrotate 19) xor (w[i-2] rightrotate 61) xor (w[i-2] rightshift 6)\\n const W2h = SHA512_W_H[i - 2] | 0;\\n const W2l = SHA512_W_L[i - 2] | 0;\\n const s1h = u64.rotrSH(W2h, W2l, 19) ^ u64.rotrBH(W2h, W2l, 61) ^ u64.shrSH(W2h, W2l, 6);\\n const s1l = u64.rotrSL(W2h, W2l, 19) ^ u64.rotrBL(W2h, W2l, 61) ^ u64.shrSL(W2h, W2l, 6);\\n // SHA256_W[i] = s0 + s1 + SHA256_W[i - 7] + SHA256_W[i - 16];\\n const SUMl = u64.add4L(s0l, s1l, SHA512_W_L[i - 7], SHA512_W_L[i - 16]);\\n const SUMh = u64.add4H(SUMl, s0h, s1h, SHA512_W_H[i - 7], SHA512_W_H[i - 16]);\\n SHA512_W_H[i] = SUMh | 0;\\n SHA512_W_L[i] = SUMl | 0;\\n }\\n let { Ah, Al, Bh, Bl, Ch, Cl, Dh, Dl, Eh, El, Fh, Fl, Gh, Gl, Hh, Hl } = this;\\n // Compression function main loop, 80 rounds\\n for (let i = 0; i < 80; i++) {\\n // S1 := (e rightrotate 14) xor (e rightrotate 18) xor (e rightrotate 41)\\n const sigma1h = u64.rotrSH(Eh, El, 14) ^ u64.rotrSH(Eh, El, 18) ^ u64.rotrBH(Eh, El, 41);\\n const sigma1l = u64.rotrSL(Eh, El, 14) ^ u64.rotrSL(Eh, El, 18) ^ u64.rotrBL(Eh, El, 41);\\n //const T1 = (H + sigma1 + Chi(E, F, G) + SHA256_K[i] + SHA256_W[i]) | 0;\\n const CHIh = (Eh & Fh) ^ (~Eh & Gh);\\n const CHIl = (El & Fl) ^ (~El & Gl);\\n // T1 = H + sigma1 + Chi(E, F, G) + SHA512_K[i] + SHA512_W[i]\\n // prettier-ignore\\n const T1ll = u64.add5L(Hl, sigma1l, CHIl, SHA512_Kl[i], SHA512_W_L[i]);\\n const T1h = u64.add5H(T1ll, Hh, sigma1h, CHIh, SHA512_Kh[i], SHA512_W_H[i]);\\n const T1l = T1ll | 0;\\n // S0 := (a rightrotate 28) xor (a rightrotate 34) xor (a rightrotate 39)\\n const sigma0h = u64.rotrSH(Ah, Al, 28) ^ u64.rotrBH(Ah, Al, 34) ^ u64.rotrBH(Ah, Al, 39);\\n const sigma0l = u64.rotrSL(Ah, Al, 28) ^ u64.rotrBL(Ah, Al, 34) ^ u64.rotrBL(Ah, Al, 39);\\n const MAJh = (Ah & Bh) ^ (Ah & Ch) ^ (Bh & Ch);\\n const MAJl = (Al & Bl) ^ (Al & Cl) ^ (Bl & Cl);\\n Hh = Gh | 0;\\n Hl = Gl | 0;\\n Gh = Fh | 0;\\n Gl = Fl | 0;\\n Fh = Eh | 0;\\n Fl = El | 0;\\n ({ h: Eh, l: El } = u64.add(Dh | 0, Dl | 0, T1h | 0, T1l | 0));\\n Dh = Ch | 0;\\n Dl = Cl | 0;\\n Ch = Bh | 0;\\n Cl = Bl | 0;\\n Bh = Ah | 0;\\n Bl = Al | 0;\\n const All = u64.add3L(T1l, sigma0l, MAJl);\\n Ah = u64.add3H(All, T1h, sigma0h, MAJh);\\n Al = All | 0;\\n }\\n // Add the compressed chunk to the current hash value\\n ({ h: Ah, l: Al } = u64.add(this.Ah | 0, this.Al | 0, Ah | 0, Al | 0));\\n ({ h: Bh, l: Bl } = u64.add(this.Bh | 0, this.Bl | 0, Bh | 0, Bl | 0));\\n ({ h: Ch, l: Cl } = u64.add(this.Ch | 0, this.Cl | 0, Ch | 0, Cl | 0));\\n ({ h: Dh, l: Dl } = u64.add(this.Dh | 0, this.Dl | 0, Dh | 0, Dl | 0));\\n ({ h: Eh, l: El } = u64.add(this.Eh | 0, this.El | 0, Eh | 0, El | 0));\\n ({ h: Fh, l: Fl } = u64.add(this.Fh | 0, this.Fl | 0, Fh | 0, Fl | 0));\\n ({ h: Gh, l: Gl } = u64.add(this.Gh | 0, this.Gl | 0, Gh | 0, Gl | 0));\\n ({ h: Hh, l: Hl } = u64.add(this.Hh | 0, this.Hl | 0, Hh | 0, Hl | 0));\\n this.set(Ah, Al, Bh, Bl, Ch, Cl, Dh, Dl, Eh, El, Fh, Fl, Gh, Gl, Hh, Hl);\\n }\\n protected roundClean(): void {\\n clean(SHA512_W_H, SHA512_W_L);\\n }\\n destroy(): void {\\n clean(this.buffer);\\n this.set(0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);\\n }\\n}\\n\\nexport class SHA384 extends SHA512 {\\n protected Ah: number = SHA384_IV[0] | 0;\\n protected Al: number = SHA384_IV[1] | 0;\\n protected Bh: number = SHA384_IV[2] | 0;\\n protected Bl: number = SHA384_IV[3] | 0;\\n protected Ch: number = SHA384_IV[4] | 0;\\n protected Cl: number = SHA384_IV[5] | 0;\\n protected Dh: number = SHA384_IV[6] | 0;\\n protected Dl: number = SHA384_IV[7] | 0;\\n protected Eh: number = SHA384_IV[8] | 0;\\n protected El: number = SHA384_IV[9] | 0;\\n protected Fh: number = SHA384_IV[10] | 0;\\n protected Fl: number = SHA384_IV[11] | 0;\\n protected Gh: number = SHA384_IV[12] | 0;\\n protected Gl: number = SHA384_IV[13] | 0;\\n protected Hh: number = SHA384_IV[14] | 0;\\n protected Hl: number = SHA384_IV[15] | 0;\\n\\n constructor() {\\n super(48);\\n }\\n}\\n\\n/**\\n * Truncated SHA512/256 and SHA512/224.\\n * SHA512_IV is XORed with 0xa5a5a5a5a5a5a5a5, then used as \\\"intermediary\\\" IV of SHA512/t.\\n * Then t hashes string to produce result IV.\\n * See `test/misc/sha2-gen-iv.js`.\\n */\\n\\n/** SHA512/224 IV */\\nconst T224_IV = /* @__PURE__ */ Uint32Array.from([\\n 0x8c3d37c8, 0x19544da2, 0x73e19966, 0x89dcd4d6, 0x1dfab7ae, 0x32ff9c82, 0x679dd514, 0x582f9fcf,\\n 0x0f6d2b69, 0x7bd44da8, 0x77e36f73, 0x04c48942, 0x3f9d85a8, 0x6a1d36c8, 0x1112e6ad, 0x91d692a1,\\n]);\\n\\n/** SHA512/256 IV */\\nconst T256_IV = /* @__PURE__ */ Uint32Array.from([\\n 0x22312194, 0xfc2bf72c, 0x9f555fa3, 0xc84c64c2, 0x2393b86b, 0x6f53b151, 0x96387719, 0x5940eabd,\\n 0x96283ee2, 0xa88effe3, 0xbe5e1e25, 0x53863992, 0x2b0199fc, 0x2c85b8aa, 0x0eb72ddc, 0x81c52ca2,\\n]);\\n\\nexport class SHA512_224 extends SHA512 {\\n protected Ah: number = T224_IV[0] | 0;\\n protected Al: number = T224_IV[1] | 0;\\n protected Bh: number = T224_IV[2] | 0;\\n protected Bl: number = T224_IV[3] | 0;\\n protected Ch: number = T224_IV[4] | 0;\\n protected Cl: number = T224_IV[5] | 0;\\n protected Dh: number = T224_IV[6] | 0;\\n protected Dl: number = T224_IV[7] | 0;\\n protected Eh: number = T224_IV[8] | 0;\\n protected El: number = T224_IV[9] | 0;\\n protected Fh: number = T224_IV[10] | 0;\\n protected Fl: number = T224_IV[11] | 0;\\n protected Gh: number = T224_IV[12] | 0;\\n protected Gl: number = T224_IV[13] | 0;\\n protected Hh: number = T224_IV[14] | 0;\\n protected Hl: number = T224_IV[15] | 0;\\n\\n constructor() {\\n super(28);\\n }\\n}\\n\\nexport class SHA512_256 extends SHA512 {\\n protected Ah: number = T256_IV[0] | 0;\\n protected Al: number = T256_IV[1] | 0;\\n protected Bh: number = T256_IV[2] | 0;\\n protected Bl: number = T256_IV[3] | 0;\\n protected Ch: number = T256_IV[4] | 0;\\n protected Cl: number = T256_IV[5] | 0;\\n protected Dh: number = T256_IV[6] | 0;\\n protected Dl: number = T256_IV[7] | 0;\\n protected Eh: number = T256_IV[8] | 0;\\n protected El: number = T256_IV[9] | 0;\\n protected Fh: number = T256_IV[10] | 0;\\n protected Fl: number = T256_IV[11] | 0;\\n protected Gh: number = T256_IV[12] | 0;\\n protected Gl: number = T256_IV[13] | 0;\\n protected Hh: number = T256_IV[14] | 0;\\n protected Hl: number = T256_IV[15] | 0;\\n\\n constructor() {\\n super(32);\\n }\\n}\\n\\n/**\\n * SHA2-256 hash function from RFC 4634.\\n *\\n * It is the fastest JS hash, even faster than Blake3.\\n * To break sha256 using birthday attack, attackers need to try 2^128 hashes.\\n * BTC network is doing 2^70 hashes/sec (2^95 hashes/year) as per 2025.\\n */\\nexport const sha256: CHash = /* @__PURE__ */ createHasher(() => new SHA256());\\n/** SHA2-224 hash function from RFC 4634 */\\nexport const sha224: CHash = /* @__PURE__ */ createHasher(() => new SHA224());\\n\\n/** SHA2-512 hash function from RFC 4634. */\\nexport const sha512: CHash = /* @__PURE__ */ createHasher(() => new SHA512());\\n/** SHA2-384 hash function from RFC 4634. */\\nexport const sha384: CHash = /* @__PURE__ */ createHasher(() => new SHA384());\\n\\n/**\\n * SHA2-512/256 \\\"truncated\\\" hash function, with improved resistance to length extension attacks.\\n * See the paper on [truncated SHA512](https://eprint.iacr.org/2010/548.pdf).\\n */\\nexport const sha512_256: CHash = /* @__PURE__ */ createHasher(() => new SHA512_256());\\n/**\\n * SHA2-512/224 \\\"truncated\\\" hash function, with improved resistance to length extension attacks.\\n * See the paper on [truncated SHA512](https://eprint.iacr.org/2010/548.pdf).\\n */\\nexport const sha512_224: CHash = /* @__PURE__ */ createHasher(() => new SHA512_224());\\n\",\"/**\\n * SHA2-256 a.k.a. sha256. In JS, it is the fastest hash, even faster than Blake3.\\n *\\n * To break sha256 using birthday attack, attackers need to try 2^128 hashes.\\n * BTC network is doing 2^70 hashes/sec (2^95 hashes/year) as per 2025.\\n *\\n * Check out [FIPS 180-4](https://nvlpubs.nist.gov/nistpubs/FIPS/NIST.FIPS.180-4.pdf).\\n * @module\\n * @deprecated\\n */\\nimport {\\n SHA224 as SHA224n,\\n sha224 as sha224n,\\n SHA256 as SHA256n,\\n sha256 as sha256n,\\n} from './sha2.ts';\\n/** @deprecated Use import from `noble/hashes/sha2` module */\\nexport const SHA256: typeof SHA256n = SHA256n;\\n/** @deprecated Use import from `noble/hashes/sha2` module */\\nexport const sha256: typeof sha256n = sha256n;\\n/** @deprecated Use import from `noble/hashes/sha2` module */\\nexport const SHA224: typeof SHA224n = SHA224n;\\n/** @deprecated Use import from `noble/hashes/sha2` module */\\nexport const sha224: typeof sha224n = sha224n;\\n\",\"import { sha256 } from '@noble/hashes/sha256';\\nimport { bytesToHex } from '@noble/hashes/utils';\\n\\nconst digest = sha256(\\n Uint8Array.from([\\n 98, 108, 117, 101, 45, 113, 117, 105, 99, 107, 106, 115, 45, 98, 105, 110,\\n 97, 114, 121, 45, 102, 105, 120, 116, 117, 114, 101,\\n ]),\\n);\\n\\nexport default {\\n hex: bytesToHex(digest),\\n length: digest.length,\\n first: digest[0],\\n last: digest[digest.length - 1],\\n};\\n\"],\"version\":3}", + "originMeta": { + "originalPath": "node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/_md.js", + "packageName": "@noble/hashes", + "packageVersion": "1.8.0", + "integrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562" + } + } + ], + "builderVersion": "deterministic-builder-v1", + "dependencyIntegrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562", + "diagnosticsMeta": { + "entryPath": "/workspace/libs/test-harness/fixtures/library-reuse/binary-sha256-entry.ts", + "modulePaths": [ + "./binary-sha256-entry.js" + ] + }, + "graphHash": "ffab4b727f608149e30ca86a1fb421eb9b44ef62b3136b5aca6057fbd034af12" + } + } + }, + "manifest": { + "abi_id": "Host.v2", + "abi_version": 2, + "functions": [ + { + "fn_id": 1, + "js_path": [ + "document", + "get" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 2, + "js_path": [ + "document", + "getCanonical" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 3, + "js_path": [ + "emit" + ], + "effect": "EMIT", + "arity": 1, + "arg_schema": [ + { + "type": "dv" + } + ], + "return_schema": { + "type": "null" + }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [ + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + } + ] + } + ] + } + }, + { + "id": "flagship-knowledge-pack", + "title": "Flagship knowledge/compliance pack processor", + "kind": "flagship", + "badge": "Flagship workload", + "description": "A browsable flagship deterministic workload that mixes static imports, Promise jobs, text and binary host data, and certification-ready evidence.", + "certified": true, + "executionProfile": "compat-binary-v1", + "sourceKind": "module-pack", + "abiId": "Host.v2", + "gasLimit": "8000000", + "sourcePaths": [ + "apps/ecosystem-certifier/fixtures/flagship/knowledge-pack-entry.ts" + ], + "sourceText": "import { toByteArray, fromByteArray } from 'base64-js';\nimport { inflateSync } from 'fflate';\nimport deepEqual from 'fast-deep-equal';\nimport stableStringify from 'fast-json-stable-stringify';\nimport he from 'he';\nimport jsonLogic from 'json-logic-js';\nimport LinkifyIt from 'linkify-it';\nimport MarkdownIt from 'markdown-it';\nimport { sha256 } from '@noble/hashes/sha256';\nimport { bytesToHex } from '@noble/hashes/utils';\nimport { match as pathMatch } from 'path-to-regexp';\nimport semver from 'semver';\nimport TinyQueue from 'tinyqueue';\nimport CRC32 from 'crc-32';\n\nlet summary;\ntry {\n const metadataText = Host.v2.document.get('pack/metadata.json');\n const ruleText = Host.v2.document.get('rules/findings.json');\n const compressedAttachment = Host.v2.document.get('pack/attachment.deflated');\n const payload = Host.v2.document.get('bytes/payload');\n const extraPayload = Host.v2.document.get('bytes/flagship-extra');\n\n const metadata = JSON.parse(metadataText);\n const docPaths = metadata.links ?? ['docs/a.md', 'docs/b.md'];\n const docs = docPaths.map((docPath) => ({\n docPath,\n text: Host.v2.document.get(docPath),\n }));\n const markdown = new MarkdownIt({ linkify: true });\n const linkify = new LinkifyIt();\n const markdownSource = docs.map((doc) => doc.text).join('\\n');\n const markdownTokens = markdown.parse(markdownSource, {});\n const linkMatches = docs\n .flatMap((doc) => linkify.match(doc.text) ?? [])\n .map((item) => item.url);\n\n const releaseChecks = (metadata.requires ?? []).map((range) =>\n semver.satisfies(metadata.release, range),\n );\n const rules = JSON.parse(ruleText);\n const findingInput = {\n linkCount: linkMatches.length,\n releaseOk: releaseChecks.every(Boolean),\n };\n const ruleInputStable = deepEqual(\n findingInput,\n JSON.parse(stableStringify(findingInput)),\n );\n const rulePasses = Boolean(jsonLogic.apply(rules, findingInput));\n\n const queue = new TinyQueue([], (left, right) => left.priority - right.priority);\n for (const link of linkMatches) {\n queue.push({ link, priority: link.length });\n }\n const orderedLinks = [];\n while (queue.length > 0) {\n orderedLinks.push(queue.pop().link);\n }\n\n const decompressed = inflateSync(compressedAttachment);\n const attachmentRoundTrip = toByteArray(fromByteArray(decompressed));\n const mergedBinary = new Uint8Array(\n attachmentRoundTrip.length + payload.length + extraPayload.length,\n );\n mergedBinary.set(attachmentRoundTrip, 0);\n mergedBinary.set(payload, attachmentRoundTrip.length);\n mergedBinary.set(extraPayload, attachmentRoundTrip.length + payload.length);\n const digestHex = bytesToHex(sha256(mergedBinary));\n const crc32 = (CRC32.buf(mergedBinary) >>> 0)\n .toString(16)\n .padStart(8, '0');\n\n const decodedEntities = he.decode('<b>safe</b>');\n const versionCapture = pathMatch('/document/:id/version/:version')(\n '/document/42/version/1.2.3',\n );\n const orderedFindings = [\n { id: 'links', value: linkMatches.length },\n { id: 'rules', value: Number(rulePasses) },\n { id: 'tokens', value: markdownTokens.length },\n ].sort((left, right) => left.id.localeCompare(right.id));\n\n Promise.resolve('scheduled').then(() => undefined);\n queueMicrotask(() => undefined);\n\n for (const doc of docs) {\n Host.v2.emit({\n type: 'knowledge-pack-doc',\n docPath: doc.docPath,\n length: doc.text.length,\n });\n }\n\n summary = {\n status: 'ok',\n packId: metadata.packId,\n release: metadata.release,\n checks: releaseChecks,\n docTokenCount: markdownTokens.length,\n linkCount: linkMatches.length,\n uniqueLinks: [...new Set(orderedLinks)],\n binary: {\n byteLength: mergedBinary.length,\n digestHex,\n crc32,\n },\n decodedEntities,\n versionCapture,\n findings: orderedFindings,\n ruleInputStable,\n rulePasses,\n };\n} catch (error) {\n summary = {\n status: 'error',\n message: String(error instanceof Error ? error.message : error),\n };\n}\n\nHost.v2.emit({\n type: 'knowledge-pack-summary',\n summaryHash: bytesToHex(\n sha256(\n toByteArray(\n fromByteArray(\n new Uint8Array([\n ...Host.v2.document.get('bytes/payload'),\n ...Host.v2.document.get('bytes/flagship-extra'),\n ]),\n ),\n ),\n ),\n ),\n status: summary.status,\n});\n\nexport default summary;\n", + "hostPreset": "certification", + "hostSummary": { + "label": "Certification host", + "description": "Provides the ecosystem-certifier text and binary documents used for workload certification.", + "documents": [ + "pack/metadata.json", + "pack/metadata.yaml", + "docs/a.md", + "docs/b.md", + "docs/c.md", + "docs/d.md", + "bytes/payload", + "bytes/flagship-extra", + "pack/attachment.deflated" + ] + }, + "docsLinks": [ + { + "label": "Workload certification", + "href": "/docs/workload-certification.md" + }, + { + "label": "Compatibility report", + "href": "/docs/ecosystem-compatibility-report.md" + }, + { + "label": "Architecture overview", + "href": "/docs/architecture-overview.md" + } + ], + "supportsOogSearch": false, + "program": { + "version": 2, + "abiId": "Host.v2", + "abiVersion": 2, + "abiManifestHash": "ec5c3df99a1b0ab84b692996193707ae6c931382e75c96c7c14b4f8baaae5af2", + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8, + "executionProfile": "compat-binary-v1", + "sourceKind": "module-pack", + "source": { + "modulePack": { + "version": 1, + "entrySpecifier": "./knowledge-pack-entry.js", + "entryExport": "default", + "modules": [ + { + "specifier": "./knowledge-pack-entry.js", + "source": "var __create = Object.create;\nvar __defProp = Object.defineProperty;\nvar __getOwnPropDesc = Object.getOwnPropertyDescriptor;\nvar __getOwnPropNames = Object.getOwnPropertyNames;\nvar __getProtoOf = Object.getPrototypeOf;\nvar __hasOwnProp = Object.prototype.hasOwnProperty;\nvar __commonJS = (cb, mod) => function __require() {\n return mod || (0, cb[__getOwnPropNames(cb)[0]])((mod = { exports: {} }).exports, mod), mod.exports;\n};\nvar __export = (target, all) => {\n for (var name in all)\n __defProp(target, name, { get: all[name], enumerable: true });\n};\nvar __copyProps = (to, from, except, desc) => {\n if (from && typeof from === \"object\" || typeof from === \"function\") {\n for (let key of __getOwnPropNames(from))\n if (!__hasOwnProp.call(to, key) && key !== except)\n __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });\n }\n return to;\n};\nvar __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(\n // If the importer is in node compatibility mode or this is not an ESM\n // file that has been converted to a CommonJS file using a Babel-\n // compatible transform (i.e. \"__esModule\" has not been set), then set\n // \"default\" to the CommonJS \"module.exports\" for node compatibility.\n isNodeMode || !mod || !mod.__esModule ? __defProp(target, \"default\", { value: mod, enumerable: true }) : target,\n mod\n));\n\n// node_modules/.pnpm/base64-js@1.5.1/node_modules/base64-js/index.js\nvar require_base64_js = __commonJS({\n \"node_modules/.pnpm/base64-js@1.5.1/node_modules/base64-js/index.js\"(exports) {\n \"use strict\";\n exports.byteLength = byteLength;\n exports.toByteArray = toByteArray2;\n exports.fromByteArray = fromByteArray2;\n var lookup = [];\n var revLookup = [];\n var Arr = typeof Uint8Array !== \"undefined\" ? Uint8Array : Array;\n var code2 = \"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/\";\n for (i = 0, len = code2.length; i < len; ++i) {\n lookup[i] = code2[i];\n revLookup[code2.charCodeAt(i)] = i;\n }\n var i;\n var len;\n revLookup[\"-\".charCodeAt(0)] = 62;\n revLookup[\"_\".charCodeAt(0)] = 63;\n function getLens(b64) {\n var len2 = b64.length;\n if (len2 % 4 > 0) {\n throw new Error(\"Invalid string. Length must be a multiple of 4\");\n }\n var validLen = b64.indexOf(\"=\");\n if (validLen === -1) validLen = len2;\n var placeHoldersLen = validLen === len2 ? 0 : 4 - validLen % 4;\n return [validLen, placeHoldersLen];\n }\n function byteLength(b64) {\n var lens = getLens(b64);\n var validLen = lens[0];\n var placeHoldersLen = lens[1];\n return (validLen + placeHoldersLen) * 3 / 4 - placeHoldersLen;\n }\n function _byteLength(b64, validLen, placeHoldersLen) {\n return (validLen + placeHoldersLen) * 3 / 4 - placeHoldersLen;\n }\n function toByteArray2(b64) {\n var tmp;\n var lens = getLens(b64);\n var validLen = lens[0];\n var placeHoldersLen = lens[1];\n var arr = new Arr(_byteLength(b64, validLen, placeHoldersLen));\n var curByte = 0;\n var len2 = placeHoldersLen > 0 ? validLen - 4 : validLen;\n var i2;\n for (i2 = 0; i2 < len2; i2 += 4) {\n tmp = revLookup[b64.charCodeAt(i2)] << 18 | revLookup[b64.charCodeAt(i2 + 1)] << 12 | revLookup[b64.charCodeAt(i2 + 2)] << 6 | revLookup[b64.charCodeAt(i2 + 3)];\n arr[curByte++] = tmp >> 16 & 255;\n arr[curByte++] = tmp >> 8 & 255;\n arr[curByte++] = tmp & 255;\n }\n if (placeHoldersLen === 2) {\n tmp = revLookup[b64.charCodeAt(i2)] << 2 | revLookup[b64.charCodeAt(i2 + 1)] >> 4;\n arr[curByte++] = tmp & 255;\n }\n if (placeHoldersLen === 1) {\n tmp = revLookup[b64.charCodeAt(i2)] << 10 | revLookup[b64.charCodeAt(i2 + 1)] << 4 | revLookup[b64.charCodeAt(i2 + 2)] >> 2;\n arr[curByte++] = tmp >> 8 & 255;\n arr[curByte++] = tmp & 255;\n }\n return arr;\n }\n function tripletToBase64(num) {\n return lookup[num >> 18 & 63] + lookup[num >> 12 & 63] + lookup[num >> 6 & 63] + lookup[num & 63];\n }\n function encodeChunk(uint8, start, end) {\n var tmp;\n var output = [];\n for (var i2 = start; i2 < end; i2 += 3) {\n tmp = (uint8[i2] << 16 & 16711680) + (uint8[i2 + 1] << 8 & 65280) + (uint8[i2 + 2] & 255);\n output.push(tripletToBase64(tmp));\n }\n return output.join(\"\");\n }\n function fromByteArray2(uint8) {\n var tmp;\n var len2 = uint8.length;\n var extraBytes = len2 % 3;\n var parts = [];\n var maxChunkLength = 16383;\n for (var i2 = 0, len22 = len2 - extraBytes; i2 < len22; i2 += maxChunkLength) {\n parts.push(encodeChunk(uint8, i2, i2 + maxChunkLength > len22 ? len22 : i2 + maxChunkLength));\n }\n if (extraBytes === 1) {\n tmp = uint8[len2 - 1];\n parts.push(\n lookup[tmp >> 2] + lookup[tmp << 4 & 63] + \"==\"\n );\n } else if (extraBytes === 2) {\n tmp = (uint8[len2 - 2] << 8) + uint8[len2 - 1];\n parts.push(\n lookup[tmp >> 10] + lookup[tmp >> 4 & 63] + lookup[tmp << 2 & 63] + \"=\"\n );\n }\n return parts.join(\"\");\n }\n }\n});\n\n// node_modules/.pnpm/fast-deep-equal@3.1.3/node_modules/fast-deep-equal/index.js\nvar require_fast_deep_equal = __commonJS({\n \"node_modules/.pnpm/fast-deep-equal@3.1.3/node_modules/fast-deep-equal/index.js\"(exports, module) {\n \"use strict\";\n module.exports = function equal(a, b) {\n if (a === b) return true;\n if (a && b && typeof a == \"object\" && typeof b == \"object\") {\n if (a.constructor !== b.constructor) return false;\n var length, i, keys;\n if (Array.isArray(a)) {\n length = a.length;\n if (length != b.length) return false;\n for (i = length; i-- !== 0; )\n if (!equal(a[i], b[i])) return false;\n return true;\n }\n if (a.constructor === RegExp) return a.source === b.source && a.flags === b.flags;\n if (a.valueOf !== Object.prototype.valueOf) return a.valueOf() === b.valueOf();\n if (a.toString !== Object.prototype.toString) return a.toString() === b.toString();\n keys = Object.keys(a);\n length = keys.length;\n if (length !== Object.keys(b).length) return false;\n for (i = length; i-- !== 0; )\n if (!Object.prototype.hasOwnProperty.call(b, keys[i])) return false;\n for (i = length; i-- !== 0; ) {\n var key = keys[i];\n if (!equal(a[key], b[key])) return false;\n }\n return true;\n }\n return a !== a && b !== b;\n };\n }\n});\n\n// node_modules/.pnpm/fast-json-stable-stringify@2.1.0/node_modules/fast-json-stable-stringify/index.js\nvar require_fast_json_stable_stringify = __commonJS({\n \"node_modules/.pnpm/fast-json-stable-stringify@2.1.0/node_modules/fast-json-stable-stringify/index.js\"(exports, module) {\n \"use strict\";\n module.exports = function(data, opts) {\n if (!opts) opts = {};\n if (typeof opts === \"function\") opts = { cmp: opts };\n var cycles = typeof opts.cycles === \"boolean\" ? opts.cycles : false;\n var cmp = opts.cmp && /* @__PURE__ */ (function(f) {\n return function(node) {\n return function(a, b) {\n var aobj = { key: a, value: node[a] };\n var bobj = { key: b, value: node[b] };\n return f(aobj, bobj);\n };\n };\n })(opts.cmp);\n var seen = [];\n return (function stringify(node) {\n if (node && node.toJSON && typeof node.toJSON === \"function\") {\n node = node.toJSON();\n }\n if (node === void 0) return;\n if (typeof node == \"number\") return isFinite(node) ? \"\" + node : \"null\";\n if (typeof node !== \"object\") return JSON.stringify(node);\n var i, out;\n if (Array.isArray(node)) {\n out = \"[\";\n for (i = 0; i < node.length; i++) {\n if (i) out += \",\";\n out += stringify(node[i]) || \"null\";\n }\n return out + \"]\";\n }\n if (node === null) return \"null\";\n if (seen.indexOf(node) !== -1) {\n if (cycles) return JSON.stringify(\"__cycle__\");\n throw new TypeError(\"Converting circular structure to JSON\");\n }\n var seenIndex = seen.push(node) - 1;\n var keys = Object.keys(node).sort(cmp && cmp(node));\n out = \"\";\n for (i = 0; i < keys.length; i++) {\n var key = keys[i];\n var value = stringify(node[key]);\n if (!value) continue;\n if (out) out += \",\";\n out += JSON.stringify(key) + \":\" + value;\n }\n seen.splice(seenIndex, 1);\n return \"{\" + out + \"}\";\n })(data);\n };\n }\n});\n\n// node_modules/.pnpm/he@1.2.0/node_modules/he/he.js\nvar require_he = __commonJS({\n \"node_modules/.pnpm/he@1.2.0/node_modules/he/he.js\"(exports, module) {\n (function(root) {\n var freeExports = typeof exports == \"object\" && exports;\n var freeModule = typeof module == \"object\" && module && module.exports == freeExports && module;\n var freeGlobal = typeof global == \"object\" && global;\n if (freeGlobal.global === freeGlobal || freeGlobal.window === freeGlobal) {\n root = freeGlobal;\n }\n var regexAstralSymbols = /[\\uD800-\\uDBFF][\\uDC00-\\uDFFF]/g;\n var regexAsciiWhitelist = /[\\x01-\\x7F]/g;\n var regexBmpWhitelist = /[\\x01-\\t\\x0B\\f\\x0E-\\x1F\\x7F\\x81\\x8D\\x8F\\x90\\x9D\\xA0-\\uFFFF]/g;\n var regexEncodeNonAscii = /<\\u20D2|=\\u20E5|>\\u20D2|\\u205F\\u200A|\\u219D\\u0338|\\u2202\\u0338|\\u2220\\u20D2|\\u2229\\uFE00|\\u222A\\uFE00|\\u223C\\u20D2|\\u223D\\u0331|\\u223E\\u0333|\\u2242\\u0338|\\u224B\\u0338|\\u224D\\u20D2|\\u224E\\u0338|\\u224F\\u0338|\\u2250\\u0338|\\u2261\\u20E5|\\u2264\\u20D2|\\u2265\\u20D2|\\u2266\\u0338|\\u2267\\u0338|\\u2268\\uFE00|\\u2269\\uFE00|\\u226A\\u0338|\\u226A\\u20D2|\\u226B\\u0338|\\u226B\\u20D2|\\u227F\\u0338|\\u2282\\u20D2|\\u2283\\u20D2|\\u228A\\uFE00|\\u228B\\uFE00|\\u228F\\u0338|\\u2290\\u0338|\\u2293\\uFE00|\\u2294\\uFE00|\\u22B4\\u20D2|\\u22B5\\u20D2|\\u22D8\\u0338|\\u22D9\\u0338|\\u22DA\\uFE00|\\u22DB\\uFE00|\\u22F5\\u0338|\\u22F9\\u0338|\\u2933\\u0338|\\u29CF\\u0338|\\u29D0\\u0338|\\u2A6D\\u0338|\\u2A70\\u0338|\\u2A7D\\u0338|\\u2A7E\\u0338|\\u2AA1\\u0338|\\u2AA2\\u0338|\\u2AAC\\uFE00|\\u2AAD\\uFE00|\\u2AAF\\u0338|\\u2AB0\\u0338|\\u2AC5\\u0338|\\u2AC6\\u0338|\\u2ACB\\uFE00|\\u2ACC\\uFE00|\\u2AFD\\u20E5|[\\xA0-\\u0113\\u0116-\\u0122\\u0124-\\u012B\\u012E-\\u014D\\u0150-\\u017E\\u0192\\u01B5\\u01F5\\u0237\\u02C6\\u02C7\\u02D8-\\u02DD\\u0311\\u0391-\\u03A1\\u03A3-\\u03A9\\u03B1-\\u03C9\\u03D1\\u03D2\\u03D5\\u03D6\\u03DC\\u03DD\\u03F0\\u03F1\\u03F5\\u03F6\\u0401-\\u040C\\u040E-\\u044F\\u0451-\\u045C\\u045E\\u045F\\u2002-\\u2005\\u2007-\\u2010\\u2013-\\u2016\\u2018-\\u201A\\u201C-\\u201E\\u2020-\\u2022\\u2025\\u2026\\u2030-\\u2035\\u2039\\u203A\\u203E\\u2041\\u2043\\u2044\\u204F\\u2057\\u205F-\\u2063\\u20AC\\u20DB\\u20DC\\u2102\\u2105\\u210A-\\u2113\\u2115-\\u211E\\u2122\\u2124\\u2127-\\u2129\\u212C\\u212D\\u212F-\\u2131\\u2133-\\u2138\\u2145-\\u2148\\u2153-\\u215E\\u2190-\\u219B\\u219D-\\u21A7\\u21A9-\\u21AE\\u21B0-\\u21B3\\u21B5-\\u21B7\\u21BA-\\u21DB\\u21DD\\u21E4\\u21E5\\u21F5\\u21FD-\\u2205\\u2207-\\u2209\\u220B\\u220C\\u220F-\\u2214\\u2216-\\u2218\\u221A\\u221D-\\u2238\\u223A-\\u2257\\u2259\\u225A\\u225C\\u225F-\\u2262\\u2264-\\u228B\\u228D-\\u229B\\u229D-\\u22A5\\u22A7-\\u22B0\\u22B2-\\u22BB\\u22BD-\\u22DB\\u22DE-\\u22E3\\u22E6-\\u22F7\\u22F9-\\u22FE\\u2305\\u2306\\u2308-\\u2310\\u2312\\u2313\\u2315\\u2316\\u231C-\\u231F\\u2322\\u2323\\u232D\\u232E\\u2336\\u233D\\u233F\\u237C\\u23B0\\u23B1\\u23B4-\\u23B6\\u23DC-\\u23DF\\u23E2\\u23E7\\u2423\\u24C8\\u2500\\u2502\\u250C\\u2510\\u2514\\u2518\\u251C\\u2524\\u252C\\u2534\\u253C\\u2550-\\u256C\\u2580\\u2584\\u2588\\u2591-\\u2593\\u25A1\\u25AA\\u25AB\\u25AD\\u25AE\\u25B1\\u25B3-\\u25B5\\u25B8\\u25B9\\u25BD-\\u25BF\\u25C2\\u25C3\\u25CA\\u25CB\\u25EC\\u25EF\\u25F8-\\u25FC\\u2605\\u2606\\u260E\\u2640\\u2642\\u2660\\u2663\\u2665\\u2666\\u266A\\u266D-\\u266F\\u2713\\u2717\\u2720\\u2736\\u2758\\u2772\\u2773\\u27C8\\u27C9\\u27E6-\\u27ED\\u27F5-\\u27FA\\u27FC\\u27FF\\u2902-\\u2905\\u290C-\\u2913\\u2916\\u2919-\\u2920\\u2923-\\u292A\\u2933\\u2935-\\u2939\\u293C\\u293D\\u2945\\u2948-\\u294B\\u294E-\\u2976\\u2978\\u2979\\u297B-\\u297F\\u2985\\u2986\\u298B-\\u2996\\u299A\\u299C\\u299D\\u29A4-\\u29B7\\u29B9\\u29BB\\u29BC\\u29BE-\\u29C5\\u29C9\\u29CD-\\u29D0\\u29DC-\\u29DE\\u29E3-\\u29E5\\u29EB\\u29F4\\u29F6\\u2A00-\\u2A02\\u2A04\\u2A06\\u2A0C\\u2A0D\\u2A10-\\u2A17\\u2A22-\\u2A27\\u2A29\\u2A2A\\u2A2D-\\u2A31\\u2A33-\\u2A3C\\u2A3F\\u2A40\\u2A42-\\u2A4D\\u2A50\\u2A53-\\u2A58\\u2A5A-\\u2A5D\\u2A5F\\u2A66\\u2A6A\\u2A6D-\\u2A75\\u2A77-\\u2A9A\\u2A9D-\\u2AA2\\u2AA4-\\u2AB0\\u2AB3-\\u2AC8\\u2ACB\\u2ACC\\u2ACF-\\u2ADB\\u2AE4\\u2AE6-\\u2AE9\\u2AEB-\\u2AF3\\u2AFD\\uFB00-\\uFB04]|\\uD835[\\uDC9C\\uDC9E\\uDC9F\\uDCA2\\uDCA5\\uDCA6\\uDCA9-\\uDCAC\\uDCAE-\\uDCB9\\uDCBB\\uDCBD-\\uDCC3\\uDCC5-\\uDCCF\\uDD04\\uDD05\\uDD07-\\uDD0A\\uDD0D-\\uDD14\\uDD16-\\uDD1C\\uDD1E-\\uDD39\\uDD3B-\\uDD3E\\uDD40-\\uDD44\\uDD46\\uDD4A-\\uDD50\\uDD52-\\uDD6B]/g;\n var encodeMap = { \"­\": \"shy\", \"‌\": \"zwnj\", \"‍\": \"zwj\", \"‎\": \"lrm\", \"⁣\": \"ic\", \"⁢\": \"it\", \"⁡\": \"af\", \"‏\": \"rlm\", \"​\": \"ZeroWidthSpace\", \"⁠\": \"NoBreak\", \"̑\": \"DownBreve\", \"⃛\": \"tdot\", \"⃜\": \"DotDot\", \"\t\": \"Tab\", \"\\n\": \"NewLine\", \" \": \"puncsp\", \" \": \"MediumSpace\", \" \": \"thinsp\", \" \": \"hairsp\", \" \": \"emsp13\", \" \": \"ensp\", \" \": \"emsp14\", \" \": \"emsp\", \" \": \"numsp\", \" \": \"nbsp\", \"  \": \"ThickSpace\", \"‾\": \"oline\", \"_\": \"lowbar\", \"‐\": \"dash\", \"–\": \"ndash\", \"—\": \"mdash\", \"―\": \"horbar\", \",\": \"comma\", \";\": \"semi\", \"⁏\": \"bsemi\", \":\": \"colon\", \"⩴\": \"Colone\", \"!\": \"excl\", \"¡\": \"iexcl\", \"?\": \"quest\", \"¿\": \"iquest\", \".\": \"period\", \"‥\": \"nldr\", \"…\": \"mldr\", \"·\": \"middot\", \"'\": \"apos\", \"‘\": \"lsquo\", \"’\": \"rsquo\", \"‚\": \"sbquo\", \"‹\": \"lsaquo\", \"›\": \"rsaquo\", '\"': \"quot\", \"“\": \"ldquo\", \"”\": \"rdquo\", \"„\": \"bdquo\", \"«\": \"laquo\", \"»\": \"raquo\", \"(\": \"lpar\", \")\": \"rpar\", \"[\": \"lsqb\", \"]\": \"rsqb\", \"{\": \"lcub\", \"}\": \"rcub\", \"⌈\": \"lceil\", \"⌉\": \"rceil\", \"⌊\": \"lfloor\", \"⌋\": \"rfloor\", \"⦅\": \"lopar\", \"⦆\": \"ropar\", \"⦋\": \"lbrke\", \"⦌\": \"rbrke\", \"⦍\": \"lbrkslu\", \"⦎\": \"rbrksld\", \"⦏\": \"lbrksld\", \"⦐\": \"rbrkslu\", \"⦑\": \"langd\", \"⦒\": \"rangd\", \"⦓\": \"lparlt\", \"⦔\": \"rpargt\", \"⦕\": \"gtlPar\", \"⦖\": \"ltrPar\", \"⟦\": \"lobrk\", \"⟧\": \"robrk\", \"⟨\": \"lang\", \"⟩\": \"rang\", \"⟪\": \"Lang\", \"⟫\": \"Rang\", \"⟬\": \"loang\", \"⟭\": \"roang\", \"❲\": \"lbbrk\", \"❳\": \"rbbrk\", \"‖\": \"Vert\", \"§\": \"sect\", \"¶\": \"para\", \"@\": \"commat\", \"*\": \"ast\", \"/\": \"sol\", \"undefined\": null, \"&\": \"amp\", \"#\": \"num\", \"%\": \"percnt\", \"‰\": \"permil\", \"‱\": \"pertenk\", \"†\": \"dagger\", \"‡\": \"Dagger\", \"•\": \"bull\", \"⁃\": \"hybull\", \"′\": \"prime\", \"″\": \"Prime\", \"‴\": \"tprime\", \"⁗\": \"qprime\", \"‵\": \"bprime\", \"⁁\": \"caret\", \"`\": \"grave\", \"´\": \"acute\", \"˜\": \"tilde\", \"^\": \"Hat\", \"¯\": \"macr\", \"˘\": \"breve\", \"˙\": \"dot\", \"¨\": \"die\", \"˚\": \"ring\", \"˝\": \"dblac\", \"¸\": \"cedil\", \"˛\": \"ogon\", \"ˆ\": \"circ\", \"ˇ\": \"caron\", \"°\": \"deg\", \"©\": \"copy\", \"®\": \"reg\", \"℗\": \"copysr\", \"℘\": \"wp\", \"℞\": \"rx\", \"℧\": \"mho\", \"℩\": \"iiota\", \"←\": \"larr\", \"↚\": \"nlarr\", \"→\": \"rarr\", \"↛\": \"nrarr\", \"↑\": \"uarr\", \"↓\": \"darr\", \"↔\": \"harr\", \"↮\": \"nharr\", \"↕\": \"varr\", \"↖\": \"nwarr\", \"↗\": \"nearr\", \"↘\": \"searr\", \"↙\": \"swarr\", \"↝\": \"rarrw\", \"↝̸\": \"nrarrw\", \"↞\": \"Larr\", \"↟\": \"Uarr\", \"↠\": \"Rarr\", \"↡\": \"Darr\", \"↢\": \"larrtl\", \"↣\": \"rarrtl\", \"↤\": \"mapstoleft\", \"↥\": \"mapstoup\", \"↦\": \"map\", \"↧\": \"mapstodown\", \"↩\": \"larrhk\", \"↪\": \"rarrhk\", \"↫\": \"larrlp\", \"↬\": \"rarrlp\", \"↭\": \"harrw\", \"↰\": \"lsh\", \"↱\": \"rsh\", \"↲\": \"ldsh\", \"↳\": \"rdsh\", \"↵\": \"crarr\", \"↶\": \"cularr\", \"↷\": \"curarr\", \"↺\": \"olarr\", \"↻\": \"orarr\", \"↼\": \"lharu\", \"↽\": \"lhard\", \"↾\": \"uharr\", \"↿\": \"uharl\", \"⇀\": \"rharu\", \"⇁\": \"rhard\", \"⇂\": \"dharr\", \"⇃\": \"dharl\", \"⇄\": \"rlarr\", \"⇅\": \"udarr\", \"⇆\": \"lrarr\", \"⇇\": \"llarr\", \"⇈\": \"uuarr\", \"⇉\": \"rrarr\", \"⇊\": \"ddarr\", \"⇋\": \"lrhar\", \"⇌\": \"rlhar\", \"⇐\": \"lArr\", \"⇍\": \"nlArr\", \"⇑\": \"uArr\", \"⇒\": \"rArr\", \"⇏\": \"nrArr\", \"⇓\": \"dArr\", \"⇔\": \"iff\", \"⇎\": \"nhArr\", \"⇕\": \"vArr\", \"⇖\": \"nwArr\", \"⇗\": \"neArr\", \"⇘\": \"seArr\", \"⇙\": \"swArr\", \"⇚\": \"lAarr\", \"⇛\": \"rAarr\", \"⇝\": \"zigrarr\", \"⇤\": \"larrb\", \"⇥\": \"rarrb\", \"⇵\": \"duarr\", \"⇽\": \"loarr\", \"⇾\": \"roarr\", \"⇿\": \"hoarr\", \"∀\": \"forall\", \"∁\": \"comp\", \"∂\": \"part\", \"∂̸\": \"npart\", \"∃\": \"exist\", \"∄\": \"nexist\", \"∅\": \"empty\", \"∇\": \"Del\", \"∈\": \"in\", \"∉\": \"notin\", \"∋\": \"ni\", \"∌\": \"notni\", \"϶\": \"bepsi\", \"∏\": \"prod\", \"∐\": \"coprod\", \"∑\": \"sum\", \"+\": \"plus\", \"±\": \"pm\", \"÷\": \"div\", \"×\": \"times\", \"<\": \"lt\", \"≮\": \"nlt\", \"<⃒\": \"nvlt\", \"=\": \"equals\", \"≠\": \"ne\", \"=⃥\": \"bne\", \"⩵\": \"Equal\", \">\": \"gt\", \"≯\": \"ngt\", \">⃒\": \"nvgt\", \"¬\": \"not\", \"|\": \"vert\", \"¦\": \"brvbar\", \"−\": \"minus\", \"∓\": \"mp\", \"∔\": \"plusdo\", \"⁄\": \"frasl\", \"∖\": \"setmn\", \"∗\": \"lowast\", \"∘\": \"compfn\", \"√\": \"Sqrt\", \"∝\": \"prop\", \"∞\": \"infin\", \"∟\": \"angrt\", \"∠\": \"ang\", \"∠⃒\": \"nang\", \"∡\": \"angmsd\", \"∢\": \"angsph\", \"∣\": \"mid\", \"∤\": \"nmid\", \"∥\": \"par\", \"∦\": \"npar\", \"∧\": \"and\", \"∨\": \"or\", \"∩\": \"cap\", \"∩︀\": \"caps\", \"∪\": \"cup\", \"∪︀\": \"cups\", \"∫\": \"int\", \"∬\": \"Int\", \"∭\": \"tint\", \"⨌\": \"qint\", \"∮\": \"oint\", \"∯\": \"Conint\", \"∰\": \"Cconint\", \"∱\": \"cwint\", \"∲\": \"cwconint\", \"∳\": \"awconint\", \"∴\": \"there4\", \"∵\": \"becaus\", \"∶\": \"ratio\", \"∷\": \"Colon\", \"∸\": \"minusd\", \"∺\": \"mDDot\", \"∻\": \"homtht\", \"∼\": \"sim\", \"≁\": \"nsim\", \"∼⃒\": \"nvsim\", \"∽\": \"bsim\", \"∽̱\": \"race\", \"∾\": \"ac\", \"∾̳\": \"acE\", \"∿\": \"acd\", \"≀\": \"wr\", \"≂\": \"esim\", \"≂̸\": \"nesim\", \"≃\": \"sime\", \"≄\": \"nsime\", \"≅\": \"cong\", \"≇\": \"ncong\", \"≆\": \"simne\", \"≈\": \"ap\", \"≉\": \"nap\", \"≊\": \"ape\", \"≋\": \"apid\", \"≋̸\": \"napid\", \"≌\": \"bcong\", \"≍\": \"CupCap\", \"≭\": \"NotCupCap\", \"≍⃒\": \"nvap\", \"≎\": \"bump\", \"≎̸\": \"nbump\", \"≏\": \"bumpe\", \"≏̸\": \"nbumpe\", \"≐\": \"doteq\", \"≐̸\": \"nedot\", \"≑\": \"eDot\", \"≒\": \"efDot\", \"≓\": \"erDot\", \"≔\": \"colone\", \"≕\": \"ecolon\", \"≖\": \"ecir\", \"≗\": \"cire\", \"≙\": \"wedgeq\", \"≚\": \"veeeq\", \"≜\": \"trie\", \"≟\": \"equest\", \"≡\": \"equiv\", \"≢\": \"nequiv\", \"≡⃥\": \"bnequiv\", \"≤\": \"le\", \"≰\": \"nle\", \"≤⃒\": \"nvle\", \"≥\": \"ge\", \"≱\": \"nge\", \"≥⃒\": \"nvge\", \"≦\": \"lE\", \"≦̸\": \"nlE\", \"≧\": \"gE\", \"≧̸\": \"ngE\", \"≨︀\": \"lvnE\", \"≨\": \"lnE\", \"≩\": \"gnE\", \"≩︀\": \"gvnE\", \"≪\": \"ll\", \"≪̸\": \"nLtv\", \"≪⃒\": \"nLt\", \"≫\": \"gg\", \"≫̸\": \"nGtv\", \"≫⃒\": \"nGt\", \"≬\": \"twixt\", \"≲\": \"lsim\", \"≴\": \"nlsim\", \"≳\": \"gsim\", \"≵\": \"ngsim\", \"≶\": \"lg\", \"≸\": \"ntlg\", \"≷\": \"gl\", \"≹\": \"ntgl\", \"≺\": \"pr\", \"⊀\": \"npr\", \"≻\": \"sc\", \"⊁\": \"nsc\", \"≼\": \"prcue\", \"⋠\": \"nprcue\", \"≽\": \"sccue\", \"⋡\": \"nsccue\", \"≾\": \"prsim\", \"≿\": \"scsim\", \"≿̸\": \"NotSucceedsTilde\", \"⊂\": \"sub\", \"⊄\": \"nsub\", \"⊂⃒\": \"vnsub\", \"⊃\": \"sup\", \"⊅\": \"nsup\", \"⊃⃒\": \"vnsup\", \"⊆\": \"sube\", \"⊈\": \"nsube\", \"⊇\": \"supe\", \"⊉\": \"nsupe\", \"⊊︀\": \"vsubne\", \"⊊\": \"subne\", \"⊋︀\": \"vsupne\", \"⊋\": \"supne\", \"⊍\": \"cupdot\", \"⊎\": \"uplus\", \"⊏\": \"sqsub\", \"⊏̸\": \"NotSquareSubset\", \"⊐\": \"sqsup\", \"⊐̸\": \"NotSquareSuperset\", \"⊑\": \"sqsube\", \"⋢\": \"nsqsube\", \"⊒\": \"sqsupe\", \"⋣\": \"nsqsupe\", \"⊓\": \"sqcap\", \"⊓︀\": \"sqcaps\", \"⊔\": \"sqcup\", \"⊔︀\": \"sqcups\", \"⊕\": \"oplus\", \"⊖\": \"ominus\", \"⊗\": \"otimes\", \"⊘\": \"osol\", \"⊙\": \"odot\", \"⊚\": \"ocir\", \"⊛\": \"oast\", \"⊝\": \"odash\", \"⊞\": \"plusb\", \"⊟\": \"minusb\", \"⊠\": \"timesb\", \"⊡\": \"sdotb\", \"⊢\": \"vdash\", \"⊬\": \"nvdash\", \"⊣\": \"dashv\", \"⊤\": \"top\", \"⊥\": \"bot\", \"⊧\": \"models\", \"⊨\": \"vDash\", \"⊭\": \"nvDash\", \"⊩\": \"Vdash\", \"⊮\": \"nVdash\", \"⊪\": \"Vvdash\", \"⊫\": \"VDash\", \"⊯\": \"nVDash\", \"⊰\": \"prurel\", \"⊲\": \"vltri\", \"⋪\": \"nltri\", \"⊳\": \"vrtri\", \"⋫\": \"nrtri\", \"⊴\": \"ltrie\", \"⋬\": \"nltrie\", \"⊴⃒\": \"nvltrie\", \"⊵\": \"rtrie\", \"⋭\": \"nrtrie\", \"⊵⃒\": \"nvrtrie\", \"⊶\": \"origof\", \"⊷\": \"imof\", \"⊸\": \"mumap\", \"⊹\": \"hercon\", \"⊺\": \"intcal\", \"⊻\": \"veebar\", \"⊽\": \"barvee\", \"⊾\": \"angrtvb\", \"⊿\": \"lrtri\", \"⋀\": \"Wedge\", \"⋁\": \"Vee\", \"⋂\": \"xcap\", \"⋃\": \"xcup\", \"⋄\": \"diam\", \"⋅\": \"sdot\", \"⋆\": \"Star\", \"⋇\": \"divonx\", \"⋈\": \"bowtie\", \"⋉\": \"ltimes\", \"⋊\": \"rtimes\", \"⋋\": \"lthree\", \"⋌\": \"rthree\", \"⋍\": \"bsime\", \"⋎\": \"cuvee\", \"⋏\": \"cuwed\", \"⋐\": \"Sub\", \"⋑\": \"Sup\", \"⋒\": \"Cap\", \"⋓\": \"Cup\", \"⋔\": \"fork\", \"⋕\": \"epar\", \"⋖\": \"ltdot\", \"⋗\": \"gtdot\", \"⋘\": \"Ll\", \"⋘̸\": \"nLl\", \"⋙\": \"Gg\", \"⋙̸\": \"nGg\", \"⋚︀\": \"lesg\", \"⋚\": \"leg\", \"⋛\": \"gel\", \"⋛︀\": \"gesl\", \"⋞\": \"cuepr\", \"⋟\": \"cuesc\", \"⋦\": \"lnsim\", \"⋧\": \"gnsim\", \"⋨\": \"prnsim\", \"⋩\": \"scnsim\", \"⋮\": \"vellip\", \"⋯\": \"ctdot\", \"⋰\": \"utdot\", \"⋱\": \"dtdot\", \"⋲\": \"disin\", \"⋳\": \"isinsv\", \"⋴\": \"isins\", \"⋵\": \"isindot\", \"⋵̸\": \"notindot\", \"⋶\": \"notinvc\", \"⋷\": \"notinvb\", \"⋹\": \"isinE\", \"⋹̸\": \"notinE\", \"⋺\": \"nisd\", \"⋻\": \"xnis\", \"⋼\": \"nis\", \"⋽\": \"notnivc\", \"⋾\": \"notnivb\", \"⌅\": \"barwed\", \"⌆\": \"Barwed\", \"⌌\": \"drcrop\", \"⌍\": \"dlcrop\", \"⌎\": \"urcrop\", \"⌏\": \"ulcrop\", \"⌐\": \"bnot\", \"⌒\": \"profline\", \"⌓\": \"profsurf\", \"⌕\": \"telrec\", \"⌖\": \"target\", \"⌜\": \"ulcorn\", \"⌝\": \"urcorn\", \"⌞\": \"dlcorn\", \"⌟\": \"drcorn\", \"⌢\": \"frown\", \"⌣\": \"smile\", \"⌭\": \"cylcty\", \"⌮\": \"profalar\", \"⌶\": \"topbot\", \"⌽\": \"ovbar\", \"⌿\": \"solbar\", \"⍼\": \"angzarr\", \"⎰\": \"lmoust\", \"⎱\": \"rmoust\", \"⎴\": \"tbrk\", \"⎵\": \"bbrk\", \"⎶\": \"bbrktbrk\", \"⏜\": \"OverParenthesis\", \"⏝\": \"UnderParenthesis\", \"⏞\": \"OverBrace\", \"⏟\": \"UnderBrace\", \"⏢\": \"trpezium\", \"⏧\": \"elinters\", \"␣\": \"blank\", \"─\": \"boxh\", \"│\": \"boxv\", \"┌\": \"boxdr\", \"┐\": \"boxdl\", \"└\": \"boxur\", \"┘\": \"boxul\", \"├\": \"boxvr\", \"┤\": \"boxvl\", \"┬\": \"boxhd\", \"┴\": \"boxhu\", \"┼\": \"boxvh\", \"═\": \"boxH\", \"║\": \"boxV\", \"╒\": \"boxdR\", \"╓\": \"boxDr\", \"╔\": \"boxDR\", \"╕\": \"boxdL\", \"╖\": \"boxDl\", \"╗\": \"boxDL\", \"╘\": \"boxuR\", \"╙\": \"boxUr\", \"╚\": \"boxUR\", \"╛\": \"boxuL\", \"╜\": \"boxUl\", \"╝\": \"boxUL\", \"╞\": \"boxvR\", \"╟\": \"boxVr\", \"╠\": \"boxVR\", \"╡\": \"boxvL\", \"╢\": \"boxVl\", \"╣\": \"boxVL\", \"╤\": \"boxHd\", \"╥\": \"boxhD\", \"╦\": \"boxHD\", \"╧\": \"boxHu\", \"╨\": \"boxhU\", \"╩\": \"boxHU\", \"╪\": \"boxvH\", \"╫\": \"boxVh\", \"╬\": \"boxVH\", \"▀\": \"uhblk\", \"▄\": \"lhblk\", \"█\": \"block\", \"░\": \"blk14\", \"▒\": \"blk12\", \"▓\": \"blk34\", \"□\": \"squ\", \"▪\": \"squf\", \"▫\": \"EmptyVerySmallSquare\", \"▭\": \"rect\", \"▮\": \"marker\", \"▱\": \"fltns\", \"△\": \"xutri\", \"▴\": \"utrif\", \"▵\": \"utri\", \"▸\": \"rtrif\", \"▹\": \"rtri\", \"▽\": \"xdtri\", \"▾\": \"dtrif\", \"▿\": \"dtri\", \"◂\": \"ltrif\", \"◃\": \"ltri\", \"◊\": \"loz\", \"○\": \"cir\", \"◬\": \"tridot\", \"◯\": \"xcirc\", \"◸\": \"ultri\", \"◹\": \"urtri\", \"◺\": \"lltri\", \"◻\": \"EmptySmallSquare\", \"◼\": \"FilledSmallSquare\", \"★\": \"starf\", \"☆\": \"star\", \"☎\": \"phone\", \"♀\": \"female\", \"♂\": \"male\", \"♠\": \"spades\", \"♣\": \"clubs\", \"♥\": \"hearts\", \"♦\": \"diams\", \"♪\": \"sung\", \"✓\": \"check\", \"✗\": \"cross\", \"✠\": \"malt\", \"✶\": \"sext\", \"❘\": \"VerticalSeparator\", \"⟈\": \"bsolhsub\", \"⟉\": \"suphsol\", \"⟵\": \"xlarr\", \"⟶\": \"xrarr\", \"⟷\": \"xharr\", \"⟸\": \"xlArr\", \"⟹\": \"xrArr\", \"⟺\": \"xhArr\", \"⟼\": \"xmap\", \"⟿\": \"dzigrarr\", \"⤂\": \"nvlArr\", \"⤃\": \"nvrArr\", \"⤄\": \"nvHarr\", \"⤅\": \"Map\", \"⤌\": \"lbarr\", \"⤍\": \"rbarr\", \"⤎\": \"lBarr\", \"⤏\": \"rBarr\", \"⤐\": \"RBarr\", \"⤑\": \"DDotrahd\", \"⤒\": \"UpArrowBar\", \"⤓\": \"DownArrowBar\", \"⤖\": \"Rarrtl\", \"⤙\": \"latail\", \"⤚\": \"ratail\", \"⤛\": \"lAtail\", \"⤜\": \"rAtail\", \"⤝\": \"larrfs\", \"⤞\": \"rarrfs\", \"⤟\": \"larrbfs\", \"⤠\": \"rarrbfs\", \"⤣\": \"nwarhk\", \"⤤\": \"nearhk\", \"⤥\": \"searhk\", \"⤦\": \"swarhk\", \"⤧\": \"nwnear\", \"⤨\": \"toea\", \"⤩\": \"tosa\", \"⤪\": \"swnwar\", \"⤳\": \"rarrc\", \"⤳̸\": \"nrarrc\", \"⤵\": \"cudarrr\", \"⤶\": \"ldca\", \"⤷\": \"rdca\", \"⤸\": \"cudarrl\", \"⤹\": \"larrpl\", \"⤼\": \"curarrm\", \"⤽\": \"cularrp\", \"⥅\": \"rarrpl\", \"⥈\": \"harrcir\", \"⥉\": \"Uarrocir\", \"⥊\": \"lurdshar\", \"⥋\": \"ldrushar\", \"⥎\": \"LeftRightVector\", \"⥏\": \"RightUpDownVector\", \"⥐\": \"DownLeftRightVector\", \"⥑\": \"LeftUpDownVector\", \"⥒\": \"LeftVectorBar\", \"⥓\": \"RightVectorBar\", \"⥔\": \"RightUpVectorBar\", \"⥕\": \"RightDownVectorBar\", \"⥖\": \"DownLeftVectorBar\", \"⥗\": \"DownRightVectorBar\", \"⥘\": \"LeftUpVectorBar\", \"⥙\": \"LeftDownVectorBar\", \"⥚\": \"LeftTeeVector\", \"⥛\": \"RightTeeVector\", \"⥜\": \"RightUpTeeVector\", \"⥝\": \"RightDownTeeVector\", \"⥞\": \"DownLeftTeeVector\", \"⥟\": \"DownRightTeeVector\", \"⥠\": \"LeftUpTeeVector\", \"⥡\": \"LeftDownTeeVector\", \"⥢\": \"lHar\", \"⥣\": \"uHar\", \"⥤\": \"rHar\", \"⥥\": \"dHar\", \"⥦\": \"luruhar\", \"⥧\": \"ldrdhar\", \"⥨\": \"ruluhar\", \"⥩\": \"rdldhar\", \"⥪\": \"lharul\", \"⥫\": \"llhard\", \"⥬\": \"rharul\", \"⥭\": \"lrhard\", \"⥮\": \"udhar\", \"⥯\": \"duhar\", \"⥰\": \"RoundImplies\", \"⥱\": \"erarr\", \"⥲\": \"simrarr\", \"⥳\": \"larrsim\", \"⥴\": \"rarrsim\", \"⥵\": \"rarrap\", \"⥶\": \"ltlarr\", \"⥸\": \"gtrarr\", \"⥹\": \"subrarr\", \"⥻\": \"suplarr\", \"⥼\": \"lfisht\", \"⥽\": \"rfisht\", \"⥾\": \"ufisht\", \"⥿\": \"dfisht\", \"⦚\": \"vzigzag\", \"⦜\": \"vangrt\", \"⦝\": \"angrtvbd\", \"⦤\": \"ange\", \"⦥\": \"range\", \"⦦\": \"dwangle\", \"⦧\": \"uwangle\", \"⦨\": \"angmsdaa\", \"⦩\": \"angmsdab\", \"⦪\": \"angmsdac\", \"⦫\": \"angmsdad\", \"⦬\": \"angmsdae\", \"⦭\": \"angmsdaf\", \"⦮\": \"angmsdag\", \"⦯\": \"angmsdah\", \"⦰\": \"bemptyv\", \"⦱\": \"demptyv\", \"⦲\": \"cemptyv\", \"⦳\": \"raemptyv\", \"⦴\": \"laemptyv\", \"⦵\": \"ohbar\", \"⦶\": \"omid\", \"⦷\": \"opar\", \"⦹\": \"operp\", \"⦻\": \"olcross\", \"⦼\": \"odsold\", \"⦾\": \"olcir\", \"⦿\": \"ofcir\", \"⧀\": \"olt\", \"⧁\": \"ogt\", \"⧂\": \"cirscir\", \"⧃\": \"cirE\", \"⧄\": \"solb\", \"⧅\": \"bsolb\", \"⧉\": \"boxbox\", \"⧍\": \"trisb\", \"⧎\": \"rtriltri\", \"⧏\": \"LeftTriangleBar\", \"⧏̸\": \"NotLeftTriangleBar\", \"⧐\": \"RightTriangleBar\", \"⧐̸\": \"NotRightTriangleBar\", \"⧜\": \"iinfin\", \"⧝\": \"infintie\", \"⧞\": \"nvinfin\", \"⧣\": \"eparsl\", \"⧤\": \"smeparsl\", \"⧥\": \"eqvparsl\", \"⧫\": \"lozf\", \"⧴\": \"RuleDelayed\", \"⧶\": \"dsol\", \"⨀\": \"xodot\", \"⨁\": \"xoplus\", \"⨂\": \"xotime\", \"⨄\": \"xuplus\", \"⨆\": \"xsqcup\", \"⨍\": \"fpartint\", \"⨐\": \"cirfnint\", \"⨑\": \"awint\", \"⨒\": \"rppolint\", \"⨓\": \"scpolint\", \"⨔\": \"npolint\", \"⨕\": \"pointint\", \"⨖\": \"quatint\", \"⨗\": \"intlarhk\", \"⨢\": \"pluscir\", \"⨣\": \"plusacir\", \"⨤\": \"simplus\", \"⨥\": \"plusdu\", \"⨦\": \"plussim\", \"⨧\": \"plustwo\", \"⨩\": \"mcomma\", \"⨪\": \"minusdu\", \"⨭\": \"loplus\", \"⨮\": \"roplus\", \"⨯\": \"Cross\", \"⨰\": \"timesd\", \"⨱\": \"timesbar\", \"⨳\": \"smashp\", \"⨴\": \"lotimes\", \"⨵\": \"rotimes\", \"⨶\": \"otimesas\", \"⨷\": \"Otimes\", \"⨸\": \"odiv\", \"⨹\": \"triplus\", \"⨺\": \"triminus\", \"⨻\": \"tritime\", \"⨼\": \"iprod\", \"⨿\": \"amalg\", \"⩀\": \"capdot\", \"⩂\": \"ncup\", \"⩃\": \"ncap\", \"⩄\": \"capand\", \"⩅\": \"cupor\", \"⩆\": \"cupcap\", \"⩇\": \"capcup\", \"⩈\": \"cupbrcap\", \"⩉\": \"capbrcup\", \"⩊\": \"cupcup\", \"⩋\": \"capcap\", \"⩌\": \"ccups\", \"⩍\": \"ccaps\", \"⩐\": \"ccupssm\", \"⩓\": \"And\", \"⩔\": \"Or\", \"⩕\": \"andand\", \"⩖\": \"oror\", \"⩗\": \"orslope\", \"⩘\": \"andslope\", \"⩚\": \"andv\", \"⩛\": \"orv\", \"⩜\": \"andd\", \"⩝\": \"ord\", \"⩟\": \"wedbar\", \"⩦\": \"sdote\", \"⩪\": \"simdot\", \"⩭\": \"congdot\", \"⩭̸\": \"ncongdot\", \"⩮\": \"easter\", \"⩯\": \"apacir\", \"⩰\": \"apE\", \"⩰̸\": \"napE\", \"⩱\": \"eplus\", \"⩲\": \"pluse\", \"⩳\": \"Esim\", \"⩷\": \"eDDot\", \"⩸\": \"equivDD\", \"⩹\": \"ltcir\", \"⩺\": \"gtcir\", \"⩻\": \"ltquest\", \"⩼\": \"gtquest\", \"⩽\": \"les\", \"⩽̸\": \"nles\", \"⩾\": \"ges\", \"⩾̸\": \"nges\", \"⩿\": \"lesdot\", \"⪀\": \"gesdot\", \"⪁\": \"lesdoto\", \"⪂\": \"gesdoto\", \"⪃\": \"lesdotor\", \"⪄\": \"gesdotol\", \"⪅\": \"lap\", \"⪆\": \"gap\", \"⪇\": \"lne\", \"⪈\": \"gne\", \"⪉\": \"lnap\", \"⪊\": \"gnap\", \"⪋\": \"lEg\", \"⪌\": \"gEl\", \"⪍\": \"lsime\", \"⪎\": \"gsime\", \"⪏\": \"lsimg\", \"⪐\": \"gsiml\", \"⪑\": \"lgE\", \"⪒\": \"glE\", \"⪓\": \"lesges\", \"⪔\": \"gesles\", \"⪕\": \"els\", \"⪖\": \"egs\", \"⪗\": \"elsdot\", \"⪘\": \"egsdot\", \"⪙\": \"el\", \"⪚\": \"eg\", \"⪝\": \"siml\", \"⪞\": \"simg\", \"⪟\": \"simlE\", \"⪠\": \"simgE\", \"⪡\": \"LessLess\", \"⪡̸\": \"NotNestedLessLess\", \"⪢\": \"GreaterGreater\", \"⪢̸\": \"NotNestedGreaterGreater\", \"⪤\": \"glj\", \"⪥\": \"gla\", \"⪦\": \"ltcc\", \"⪧\": \"gtcc\", \"⪨\": \"lescc\", \"⪩\": \"gescc\", \"⪪\": \"smt\", \"⪫\": \"lat\", \"⪬\": \"smte\", \"⪬︀\": \"smtes\", \"⪭\": \"late\", \"⪭︀\": \"lates\", \"⪮\": \"bumpE\", \"⪯\": \"pre\", \"⪯̸\": \"npre\", \"⪰\": \"sce\", \"⪰̸\": \"nsce\", \"⪳\": \"prE\", \"⪴\": \"scE\", \"⪵\": \"prnE\", \"⪶\": \"scnE\", \"⪷\": \"prap\", \"⪸\": \"scap\", \"⪹\": \"prnap\", \"⪺\": \"scnap\", \"⪻\": \"Pr\", \"⪼\": \"Sc\", \"⪽\": \"subdot\", \"⪾\": \"supdot\", \"⪿\": \"subplus\", \"⫀\": \"supplus\", \"⫁\": \"submult\", \"⫂\": \"supmult\", \"⫃\": \"subedot\", \"⫄\": \"supedot\", \"⫅\": \"subE\", \"⫅̸\": \"nsubE\", \"⫆\": \"supE\", \"⫆̸\": \"nsupE\", \"⫇\": \"subsim\", \"⫈\": \"supsim\", \"⫋︀\": \"vsubnE\", \"⫋\": \"subnE\", \"⫌︀\": \"vsupnE\", \"⫌\": \"supnE\", \"⫏\": \"csub\", \"⫐\": \"csup\", \"⫑\": \"csube\", \"⫒\": \"csupe\", \"⫓\": \"subsup\", \"⫔\": \"supsub\", \"⫕\": \"subsub\", \"⫖\": \"supsup\", \"⫗\": \"suphsub\", \"⫘\": \"supdsub\", \"⫙\": \"forkv\", \"⫚\": \"topfork\", \"⫛\": \"mlcp\", \"⫤\": \"Dashv\", \"⫦\": \"Vdashl\", \"⫧\": \"Barv\", \"⫨\": \"vBar\", \"⫩\": \"vBarv\", \"⫫\": \"Vbar\", \"⫬\": \"Not\", \"⫭\": \"bNot\", \"⫮\": \"rnmid\", \"⫯\": \"cirmid\", \"⫰\": \"midcir\", \"⫱\": \"topcir\", \"⫲\": \"nhpar\", \"⫳\": \"parsim\", \"⫽\": \"parsl\", \"⫽⃥\": \"nparsl\", \"♭\": \"flat\", \"♮\": \"natur\", \"♯\": \"sharp\", \"¤\": \"curren\", \"¢\": \"cent\", \"$\": \"dollar\", \"£\": \"pound\", \"¥\": \"yen\", \"€\": \"euro\", \"¹\": \"sup1\", \"½\": \"half\", \"⅓\": \"frac13\", \"¼\": \"frac14\", \"⅕\": \"frac15\", \"⅙\": \"frac16\", \"⅛\": \"frac18\", \"²\": \"sup2\", \"⅔\": \"frac23\", \"⅖\": \"frac25\", \"³\": \"sup3\", \"¾\": \"frac34\", \"⅗\": \"frac35\", \"⅜\": \"frac38\", \"⅘\": \"frac45\", \"⅚\": \"frac56\", \"⅝\": \"frac58\", \"⅞\": \"frac78\", \"𝒶\": \"ascr\", \"𝕒\": \"aopf\", \"𝔞\": \"afr\", \"𝔸\": \"Aopf\", \"𝔄\": \"Afr\", \"𝒜\": \"Ascr\", \"ª\": \"ordf\", \"á\": \"aacute\", \"Á\": \"Aacute\", \"à\": \"agrave\", \"À\": \"Agrave\", \"ă\": \"abreve\", \"Ă\": \"Abreve\", \"â\": \"acirc\", \"Â\": \"Acirc\", \"å\": \"aring\", \"Å\": \"angst\", \"ä\": \"auml\", \"Ä\": \"Auml\", \"ã\": \"atilde\", \"Ã\": \"Atilde\", \"ą\": \"aogon\", \"Ą\": \"Aogon\", \"ā\": \"amacr\", \"Ā\": \"Amacr\", \"æ\": \"aelig\", \"Æ\": \"AElig\", \"𝒷\": \"bscr\", \"𝕓\": \"bopf\", \"𝔟\": \"bfr\", \"𝔹\": \"Bopf\", \"ℬ\": \"Bscr\", \"𝔅\": \"Bfr\", \"𝔠\": \"cfr\", \"𝒸\": \"cscr\", \"𝕔\": \"copf\", \"ℭ\": \"Cfr\", \"𝒞\": \"Cscr\", \"ℂ\": \"Copf\", \"ć\": \"cacute\", \"Ć\": \"Cacute\", \"ĉ\": \"ccirc\", \"Ĉ\": \"Ccirc\", \"č\": \"ccaron\", \"Č\": \"Ccaron\", \"ċ\": \"cdot\", \"Ċ\": \"Cdot\", \"ç\": \"ccedil\", \"Ç\": \"Ccedil\", \"℅\": \"incare\", \"𝔡\": \"dfr\", \"ⅆ\": \"dd\", \"𝕕\": \"dopf\", \"𝒹\": \"dscr\", \"𝒟\": \"Dscr\", \"𝔇\": \"Dfr\", \"ⅅ\": \"DD\", \"𝔻\": \"Dopf\", \"ď\": \"dcaron\", \"Ď\": \"Dcaron\", \"đ\": \"dstrok\", \"Đ\": \"Dstrok\", \"ð\": \"eth\", \"Ð\": \"ETH\", \"ⅇ\": \"ee\", \"ℯ\": \"escr\", \"𝔢\": \"efr\", \"𝕖\": \"eopf\", \"ℰ\": \"Escr\", \"𝔈\": \"Efr\", \"𝔼\": \"Eopf\", \"é\": \"eacute\", \"É\": \"Eacute\", \"è\": \"egrave\", \"È\": \"Egrave\", \"ê\": \"ecirc\", \"Ê\": \"Ecirc\", \"ě\": \"ecaron\", \"Ě\": \"Ecaron\", \"ë\": \"euml\", \"Ë\": \"Euml\", \"ė\": \"edot\", \"Ė\": \"Edot\", \"ę\": \"eogon\", \"Ę\": \"Eogon\", \"ē\": \"emacr\", \"Ē\": \"Emacr\", \"𝔣\": \"ffr\", \"𝕗\": \"fopf\", \"𝒻\": \"fscr\", \"𝔉\": \"Ffr\", \"𝔽\": \"Fopf\", \"ℱ\": \"Fscr\", \"ff\": \"fflig\", \"ffi\": \"ffilig\", \"ffl\": \"ffllig\", \"fi\": \"filig\", \"fj\": \"fjlig\", \"fl\": \"fllig\", \"ƒ\": \"fnof\", \"ℊ\": \"gscr\", \"𝕘\": \"gopf\", \"𝔤\": \"gfr\", \"𝒢\": \"Gscr\", \"𝔾\": \"Gopf\", \"𝔊\": \"Gfr\", \"ǵ\": \"gacute\", \"ğ\": \"gbreve\", \"Ğ\": \"Gbreve\", \"ĝ\": \"gcirc\", \"Ĝ\": \"Gcirc\", \"ġ\": \"gdot\", \"Ġ\": \"Gdot\", \"Ģ\": \"Gcedil\", \"𝔥\": \"hfr\", \"ℎ\": \"planckh\", \"𝒽\": \"hscr\", \"𝕙\": \"hopf\", \"ℋ\": \"Hscr\", \"ℌ\": \"Hfr\", \"ℍ\": \"Hopf\", \"ĥ\": \"hcirc\", \"Ĥ\": \"Hcirc\", \"ℏ\": \"hbar\", \"ħ\": \"hstrok\", \"Ħ\": \"Hstrok\", \"𝕚\": \"iopf\", \"𝔦\": \"ifr\", \"𝒾\": \"iscr\", \"ⅈ\": \"ii\", \"𝕀\": \"Iopf\", \"ℐ\": \"Iscr\", \"ℑ\": \"Im\", \"í\": \"iacute\", \"Í\": \"Iacute\", \"ì\": \"igrave\", \"Ì\": \"Igrave\", \"î\": \"icirc\", \"Î\": \"Icirc\", \"ï\": \"iuml\", \"Ï\": \"Iuml\", \"ĩ\": \"itilde\", \"Ĩ\": \"Itilde\", \"İ\": \"Idot\", \"į\": \"iogon\", \"Į\": \"Iogon\", \"ī\": \"imacr\", \"Ī\": \"Imacr\", \"ij\": \"ijlig\", \"IJ\": \"IJlig\", \"ı\": \"imath\", \"𝒿\": \"jscr\", \"𝕛\": \"jopf\", \"𝔧\": \"jfr\", \"𝒥\": \"Jscr\", \"𝔍\": \"Jfr\", \"𝕁\": \"Jopf\", \"ĵ\": \"jcirc\", \"Ĵ\": \"Jcirc\", \"ȷ\": \"jmath\", \"𝕜\": \"kopf\", \"𝓀\": \"kscr\", \"𝔨\": \"kfr\", \"𝒦\": \"Kscr\", \"𝕂\": \"Kopf\", \"𝔎\": \"Kfr\", \"ķ\": \"kcedil\", \"Ķ\": \"Kcedil\", \"𝔩\": \"lfr\", \"𝓁\": \"lscr\", \"ℓ\": \"ell\", \"𝕝\": \"lopf\", \"ℒ\": \"Lscr\", \"𝔏\": \"Lfr\", \"𝕃\": \"Lopf\", \"ĺ\": \"lacute\", \"Ĺ\": \"Lacute\", \"ľ\": \"lcaron\", \"Ľ\": \"Lcaron\", \"ļ\": \"lcedil\", \"Ļ\": \"Lcedil\", \"ł\": \"lstrok\", \"Ł\": \"Lstrok\", \"ŀ\": \"lmidot\", \"Ŀ\": \"Lmidot\", \"𝔪\": \"mfr\", \"𝕞\": \"mopf\", \"𝓂\": \"mscr\", \"𝔐\": \"Mfr\", \"𝕄\": \"Mopf\", \"ℳ\": \"Mscr\", \"𝔫\": \"nfr\", \"𝕟\": \"nopf\", \"𝓃\": \"nscr\", \"ℕ\": \"Nopf\", \"𝒩\": \"Nscr\", \"𝔑\": \"Nfr\", \"ń\": \"nacute\", \"Ń\": \"Nacute\", \"ň\": \"ncaron\", \"Ň\": \"Ncaron\", \"ñ\": \"ntilde\", \"Ñ\": \"Ntilde\", \"ņ\": \"ncedil\", \"Ņ\": \"Ncedil\", \"№\": \"numero\", \"ŋ\": \"eng\", \"Ŋ\": \"ENG\", \"𝕠\": \"oopf\", \"𝔬\": \"ofr\", \"ℴ\": \"oscr\", \"𝒪\": \"Oscr\", \"𝔒\": \"Ofr\", \"𝕆\": \"Oopf\", \"º\": \"ordm\", \"ó\": \"oacute\", \"Ó\": \"Oacute\", \"ò\": \"ograve\", \"Ò\": \"Ograve\", \"ô\": \"ocirc\", \"Ô\": \"Ocirc\", \"ö\": \"ouml\", \"Ö\": \"Ouml\", \"ő\": \"odblac\", \"Ő\": \"Odblac\", \"õ\": \"otilde\", \"Õ\": \"Otilde\", \"ø\": \"oslash\", \"Ø\": \"Oslash\", \"ō\": \"omacr\", \"Ō\": \"Omacr\", \"œ\": \"oelig\", \"Œ\": \"OElig\", \"𝔭\": \"pfr\", \"𝓅\": \"pscr\", \"𝕡\": \"popf\", \"ℙ\": \"Popf\", \"𝔓\": \"Pfr\", \"𝒫\": \"Pscr\", \"𝕢\": \"qopf\", \"𝔮\": \"qfr\", \"𝓆\": \"qscr\", \"𝒬\": \"Qscr\", \"𝔔\": \"Qfr\", \"ℚ\": \"Qopf\", \"ĸ\": \"kgreen\", \"𝔯\": \"rfr\", \"𝕣\": \"ropf\", \"𝓇\": \"rscr\", \"ℛ\": \"Rscr\", \"ℜ\": \"Re\", \"ℝ\": \"Ropf\", \"ŕ\": \"racute\", \"Ŕ\": \"Racute\", \"ř\": \"rcaron\", \"Ř\": \"Rcaron\", \"ŗ\": \"rcedil\", \"Ŗ\": \"Rcedil\", \"𝕤\": \"sopf\", \"𝓈\": \"sscr\", \"𝔰\": \"sfr\", \"𝕊\": \"Sopf\", \"𝔖\": \"Sfr\", \"𝒮\": \"Sscr\", \"Ⓢ\": \"oS\", \"ś\": \"sacute\", \"Ś\": \"Sacute\", \"ŝ\": \"scirc\", \"Ŝ\": \"Scirc\", \"š\": \"scaron\", \"Š\": \"Scaron\", \"ş\": \"scedil\", \"Ş\": \"Scedil\", \"ß\": \"szlig\", \"𝔱\": \"tfr\", \"𝓉\": \"tscr\", \"𝕥\": \"topf\", \"𝒯\": \"Tscr\", \"𝔗\": \"Tfr\", \"𝕋\": \"Topf\", \"ť\": \"tcaron\", \"Ť\": \"Tcaron\", \"ţ\": \"tcedil\", \"Ţ\": \"Tcedil\", \"™\": \"trade\", \"ŧ\": \"tstrok\", \"Ŧ\": \"Tstrok\", \"𝓊\": \"uscr\", \"𝕦\": \"uopf\", \"𝔲\": \"ufr\", \"𝕌\": \"Uopf\", \"𝔘\": \"Ufr\", \"𝒰\": \"Uscr\", \"ú\": \"uacute\", \"Ú\": \"Uacute\", \"ù\": \"ugrave\", \"Ù\": \"Ugrave\", \"ŭ\": \"ubreve\", \"Ŭ\": \"Ubreve\", \"û\": \"ucirc\", \"Û\": \"Ucirc\", \"ů\": \"uring\", \"Ů\": \"Uring\", \"ü\": \"uuml\", \"Ü\": \"Uuml\", \"ű\": \"udblac\", \"Ű\": \"Udblac\", \"ũ\": \"utilde\", \"Ũ\": \"Utilde\", \"ų\": \"uogon\", \"Ų\": \"Uogon\", \"ū\": \"umacr\", \"Ū\": \"Umacr\", \"𝔳\": \"vfr\", \"𝕧\": \"vopf\", \"𝓋\": \"vscr\", \"𝔙\": \"Vfr\", \"𝕍\": \"Vopf\", \"𝒱\": \"Vscr\", \"𝕨\": \"wopf\", \"𝓌\": \"wscr\", \"𝔴\": \"wfr\", \"𝒲\": \"Wscr\", \"𝕎\": \"Wopf\", \"𝔚\": \"Wfr\", \"ŵ\": \"wcirc\", \"Ŵ\": \"Wcirc\", \"𝔵\": \"xfr\", \"𝓍\": \"xscr\", \"𝕩\": \"xopf\", \"𝕏\": \"Xopf\", \"𝔛\": \"Xfr\", \"𝒳\": \"Xscr\", \"𝔶\": \"yfr\", \"𝓎\": \"yscr\", \"𝕪\": \"yopf\", \"𝒴\": \"Yscr\", \"𝔜\": \"Yfr\", \"𝕐\": \"Yopf\", \"ý\": \"yacute\", \"Ý\": \"Yacute\", \"ŷ\": \"ycirc\", \"Ŷ\": \"Ycirc\", \"ÿ\": \"yuml\", \"Ÿ\": \"Yuml\", \"𝓏\": \"zscr\", \"𝔷\": \"zfr\", \"𝕫\": \"zopf\", \"ℨ\": \"Zfr\", \"ℤ\": \"Zopf\", \"𝒵\": \"Zscr\", \"ź\": \"zacute\", \"Ź\": \"Zacute\", \"ž\": \"zcaron\", \"Ž\": \"Zcaron\", \"ż\": \"zdot\", \"Ż\": \"Zdot\", \"Ƶ\": \"imped\", \"þ\": \"thorn\", \"Þ\": \"THORN\", \"ʼn\": \"napos\", \"α\": \"alpha\", \"Α\": \"Alpha\", \"β\": \"beta\", \"Β\": \"Beta\", \"γ\": \"gamma\", \"Γ\": \"Gamma\", \"δ\": \"delta\", \"Δ\": \"Delta\", \"ε\": \"epsi\", \"ϵ\": \"epsiv\", \"Ε\": \"Epsilon\", \"ϝ\": \"gammad\", \"Ϝ\": \"Gammad\", \"ζ\": \"zeta\", \"Ζ\": \"Zeta\", \"η\": \"eta\", \"Η\": \"Eta\", \"θ\": \"theta\", \"ϑ\": \"thetav\", \"Θ\": \"Theta\", \"ι\": \"iota\", \"Ι\": \"Iota\", \"κ\": \"kappa\", \"ϰ\": \"kappav\", \"Κ\": \"Kappa\", \"λ\": \"lambda\", \"Λ\": \"Lambda\", \"μ\": \"mu\", \"µ\": \"micro\", \"Μ\": \"Mu\", \"ν\": \"nu\", \"Ν\": \"Nu\", \"ξ\": \"xi\", \"Ξ\": \"Xi\", \"ο\": \"omicron\", \"Ο\": \"Omicron\", \"π\": \"pi\", \"ϖ\": \"piv\", \"Π\": \"Pi\", \"ρ\": \"rho\", \"ϱ\": \"rhov\", \"Ρ\": \"Rho\", \"σ\": \"sigma\", \"Σ\": \"Sigma\", \"ς\": \"sigmaf\", \"τ\": \"tau\", \"Τ\": \"Tau\", \"υ\": \"upsi\", \"Υ\": \"Upsilon\", \"ϒ\": \"Upsi\", \"φ\": \"phi\", \"ϕ\": \"phiv\", \"Φ\": \"Phi\", \"χ\": \"chi\", \"Χ\": \"Chi\", \"ψ\": \"psi\", \"Ψ\": \"Psi\", \"ω\": \"omega\", \"Ω\": \"ohm\", \"а\": \"acy\", \"А\": \"Acy\", \"б\": \"bcy\", \"Б\": \"Bcy\", \"в\": \"vcy\", \"В\": \"Vcy\", \"г\": \"gcy\", \"Г\": \"Gcy\", \"ѓ\": \"gjcy\", \"Ѓ\": \"GJcy\", \"д\": \"dcy\", \"Д\": \"Dcy\", \"ђ\": \"djcy\", \"Ђ\": \"DJcy\", \"е\": \"iecy\", \"Е\": \"IEcy\", \"ё\": \"iocy\", \"Ё\": \"IOcy\", \"є\": \"jukcy\", \"Є\": \"Jukcy\", \"ж\": \"zhcy\", \"Ж\": \"ZHcy\", \"з\": \"zcy\", \"З\": \"Zcy\", \"ѕ\": \"dscy\", \"Ѕ\": \"DScy\", \"и\": \"icy\", \"И\": \"Icy\", \"і\": \"iukcy\", \"І\": \"Iukcy\", \"ї\": \"yicy\", \"Ї\": \"YIcy\", \"й\": \"jcy\", \"Й\": \"Jcy\", \"ј\": \"jsercy\", \"Ј\": \"Jsercy\", \"к\": \"kcy\", \"К\": \"Kcy\", \"ќ\": \"kjcy\", \"Ќ\": \"KJcy\", \"л\": \"lcy\", \"Л\": \"Lcy\", \"љ\": \"ljcy\", \"Љ\": \"LJcy\", \"м\": \"mcy\", \"М\": \"Mcy\", \"н\": \"ncy\", \"Н\": \"Ncy\", \"њ\": \"njcy\", \"Њ\": \"NJcy\", \"о\": \"ocy\", \"О\": \"Ocy\", \"п\": \"pcy\", \"П\": \"Pcy\", \"р\": \"rcy\", \"Р\": \"Rcy\", \"с\": \"scy\", \"С\": \"Scy\", \"т\": \"tcy\", \"Т\": \"Tcy\", \"ћ\": \"tshcy\", \"Ћ\": \"TSHcy\", \"у\": \"ucy\", \"У\": \"Ucy\", \"ў\": \"ubrcy\", \"Ў\": \"Ubrcy\", \"ф\": \"fcy\", \"Ф\": \"Fcy\", \"х\": \"khcy\", \"Х\": \"KHcy\", \"ц\": \"tscy\", \"Ц\": \"TScy\", \"ч\": \"chcy\", \"Ч\": \"CHcy\", \"џ\": \"dzcy\", \"Џ\": \"DZcy\", \"ш\": \"shcy\", \"Ш\": \"SHcy\", \"щ\": \"shchcy\", \"Щ\": \"SHCHcy\", \"ъ\": \"hardcy\", \"Ъ\": \"HARDcy\", \"ы\": \"ycy\", \"Ы\": \"Ycy\", \"ь\": \"softcy\", \"Ь\": \"SOFTcy\", \"э\": \"ecy\", \"Э\": \"Ecy\", \"ю\": \"yucy\", \"Ю\": \"YUcy\", \"я\": \"yacy\", \"Я\": \"YAcy\", \"ℵ\": \"aleph\", \"ℶ\": \"beth\", \"ℷ\": \"gimel\", \"ℸ\": \"daleth\" };\n var regexEscape = /[\"&'<>`]/g;\n var escapeMap = {\n '\"': \""\",\n \"&\": \"&\",\n \"'\": \"'\",\n \"<\": \"<\",\n // See https://mathiasbynens.be/notes/ambiguous-ampersands: in HTML, the\n // following is not strictly necessary unless it’s part of a tag or an\n // unquoted attribute value. We’re only escaping it to support those\n // situations, and for XML support.\n \">\": \">\",\n // In Internet Explorer ≤ 8, the backtick character can be used\n // to break out of (un)quoted attribute values or HTML comments.\n // See http://html5sec.org/#102, http://html5sec.org/#108, and\n // http://html5sec.org/#133.\n \"`\": \"`\"\n };\n var regexInvalidEntity = /&#(?:[xX][^a-fA-F0-9]|[^0-9xX])/;\n var regexInvalidRawCodePoint = /[\\0-\\x08\\x0B\\x0E-\\x1F\\x7F-\\x9F\\uFDD0-\\uFDEF\\uFFFE\\uFFFF]|[\\uD83F\\uD87F\\uD8BF\\uD8FF\\uD93F\\uD97F\\uD9BF\\uD9FF\\uDA3F\\uDA7F\\uDABF\\uDAFF\\uDB3F\\uDB7F\\uDBBF\\uDBFF][\\uDFFE\\uDFFF]|[\\uD800-\\uDBFF](?![\\uDC00-\\uDFFF])|(?:[^\\uD800-\\uDBFF]|^)[\\uDC00-\\uDFFF]/;\n var regexDecode = /&(CounterClockwiseContourIntegral|DoubleLongLeftRightArrow|ClockwiseContourIntegral|NotNestedGreaterGreater|NotSquareSupersetEqual|DiacriticalDoubleAcute|NotRightTriangleEqual|NotSucceedsSlantEqual|NotPrecedesSlantEqual|CloseCurlyDoubleQuote|NegativeVeryThinSpace|DoubleContourIntegral|FilledVerySmallSquare|CapitalDifferentialD|OpenCurlyDoubleQuote|EmptyVerySmallSquare|NestedGreaterGreater|DoubleLongRightArrow|NotLeftTriangleEqual|NotGreaterSlantEqual|ReverseUpEquilibrium|DoubleLeftRightArrow|NotSquareSubsetEqual|NotDoubleVerticalBar|RightArrowLeftArrow|NotGreaterFullEqual|NotRightTriangleBar|SquareSupersetEqual|DownLeftRightVector|DoubleLongLeftArrow|leftrightsquigarrow|LeftArrowRightArrow|NegativeMediumSpace|blacktriangleright|RightDownVectorBar|PrecedesSlantEqual|RightDoubleBracket|SucceedsSlantEqual|NotLeftTriangleBar|RightTriangleEqual|SquareIntersection|RightDownTeeVector|ReverseEquilibrium|NegativeThickSpace|longleftrightarrow|Longleftrightarrow|LongLeftRightArrow|DownRightTeeVector|DownRightVectorBar|GreaterSlantEqual|SquareSubsetEqual|LeftDownVectorBar|LeftDoubleBracket|VerticalSeparator|rightleftharpoons|NotGreaterGreater|NotSquareSuperset|blacktriangleleft|blacktriangledown|NegativeThinSpace|LeftDownTeeVector|NotLessSlantEqual|leftrightharpoons|DoubleUpDownArrow|DoubleVerticalBar|LeftTriangleEqual|FilledSmallSquare|twoheadrightarrow|NotNestedLessLess|DownLeftTeeVector|DownLeftVectorBar|RightAngleBracket|NotTildeFullEqual|NotReverseElement|RightUpDownVector|DiacriticalTilde|NotSucceedsTilde|circlearrowright|NotPrecedesEqual|rightharpoondown|DoubleRightArrow|NotSucceedsEqual|NonBreakingSpace|NotRightTriangle|LessEqualGreater|RightUpTeeVector|LeftAngleBracket|GreaterFullEqual|DownArrowUpArrow|RightUpVectorBar|twoheadleftarrow|GreaterEqualLess|downharpoonright|RightTriangleBar|ntrianglerighteq|NotSupersetEqual|LeftUpDownVector|DiacriticalAcute|rightrightarrows|vartriangleright|UpArrowDownArrow|DiacriticalGrave|UnderParenthesis|EmptySmallSquare|LeftUpVectorBar|leftrightarrows|DownRightVector|downharpoonleft|trianglerighteq|ShortRightArrow|OverParenthesis|DoubleLeftArrow|DoubleDownArrow|NotSquareSubset|bigtriangledown|ntrianglelefteq|UpperRightArrow|curvearrowright|vartriangleleft|NotLeftTriangle|nleftrightarrow|LowerRightArrow|NotHumpDownHump|NotGreaterTilde|rightthreetimes|LeftUpTeeVector|NotGreaterEqual|straightepsilon|LeftTriangleBar|rightsquigarrow|ContourIntegral|rightleftarrows|CloseCurlyQuote|RightDownVector|LeftRightVector|nLeftrightarrow|leftharpoondown|circlearrowleft|SquareSuperset|OpenCurlyQuote|hookrightarrow|HorizontalLine|DiacriticalDot|NotLessGreater|ntriangleright|DoubleRightTee|InvisibleComma|InvisibleTimes|LowerLeftArrow|DownLeftVector|NotSubsetEqual|curvearrowleft|trianglelefteq|NotVerticalBar|TildeFullEqual|downdownarrows|NotGreaterLess|RightTeeVector|ZeroWidthSpace|looparrowright|LongRightArrow|doublebarwedge|ShortLeftArrow|ShortDownArrow|RightVectorBar|GreaterGreater|ReverseElement|rightharpoonup|LessSlantEqual|leftthreetimes|upharpoonright|rightarrowtail|LeftDownVector|Longrightarrow|NestedLessLess|UpperLeftArrow|nshortparallel|leftleftarrows|leftrightarrow|Leftrightarrow|LeftRightArrow|longrightarrow|upharpoonleft|RightArrowBar|ApplyFunction|LeftTeeVector|leftarrowtail|NotEqualTilde|varsubsetneqq|varsupsetneqq|RightTeeArrow|SucceedsEqual|SucceedsTilde|LeftVectorBar|SupersetEqual|hookleftarrow|DifferentialD|VerticalTilde|VeryThinSpace|blacktriangle|bigtriangleup|LessFullEqual|divideontimes|leftharpoonup|UpEquilibrium|ntriangleleft|RightTriangle|measuredangle|shortparallel|longleftarrow|Longleftarrow|LongLeftArrow|DoubleLeftTee|Poincareplane|PrecedesEqual|triangleright|DoubleUpArrow|RightUpVector|fallingdotseq|looparrowleft|PrecedesTilde|NotTildeEqual|NotTildeTilde|smallsetminus|Proportional|triangleleft|triangledown|UnderBracket|NotHumpEqual|exponentiale|ExponentialE|NotLessTilde|HilbertSpace|RightCeiling|blacklozenge|varsupsetneq|HumpDownHump|GreaterEqual|VerticalLine|LeftTeeArrow|NotLessEqual|DownTeeArrow|LeftTriangle|varsubsetneq|Intersection|NotCongruent|DownArrowBar|LeftUpVector|LeftArrowBar|risingdotseq|GreaterTilde|RoundImplies|SquareSubset|ShortUpArrow|NotSuperset|quaternions|precnapprox|backepsilon|preccurlyeq|OverBracket|blacksquare|MediumSpace|VerticalBar|circledcirc|circleddash|CircleMinus|CircleTimes|LessGreater|curlyeqprec|curlyeqsucc|diamondsuit|UpDownArrow|Updownarrow|RuleDelayed|Rrightarrow|updownarrow|RightVector|nRightarrow|nrightarrow|eqslantless|LeftCeiling|Equilibrium|SmallCircle|expectation|NotSucceeds|thickapprox|GreaterLess|SquareUnion|NotPrecedes|NotLessLess|straightphi|succnapprox|succcurlyeq|SubsetEqual|sqsupseteq|Proportion|Laplacetrf|ImaginaryI|supsetneqq|NotGreater|gtreqqless|NotElement|ThickSpace|TildeEqual|TildeTilde|Fouriertrf|rmoustache|EqualTilde|eqslantgtr|UnderBrace|LeftVector|UpArrowBar|nLeftarrow|nsubseteqq|subsetneqq|nsupseteqq|nleftarrow|succapprox|lessapprox|UpTeeArrow|upuparrows|curlywedge|lesseqqgtr|varepsilon|varnothing|RightFloor|complement|CirclePlus|sqsubseteq|Lleftarrow|circledast|RightArrow|Rightarrow|rightarrow|lmoustache|Bernoullis|precapprox|mapstoleft|mapstodown|longmapsto|dotsquare|downarrow|DoubleDot|nsubseteq|supsetneq|leftarrow|nsupseteq|subsetneq|ThinSpace|ngeqslant|subseteqq|HumpEqual|NotSubset|triangleq|NotCupCap|lesseqgtr|heartsuit|TripleDot|Leftarrow|Coproduct|Congruent|varpropto|complexes|gvertneqq|LeftArrow|LessTilde|supseteqq|MinusPlus|CircleDot|nleqslant|NotExists|gtreqless|nparallel|UnionPlus|LeftFloor|checkmark|CenterDot|centerdot|Mellintrf|gtrapprox|bigotimes|OverBrace|spadesuit|therefore|pitchfork|rationals|PlusMinus|Backslash|Therefore|DownBreve|backsimeq|backprime|DownArrow|nshortmid|Downarrow|lvertneqq|eqvparsl|imagline|imagpart|infintie|integers|Integral|intercal|LessLess|Uarrocir|intlarhk|sqsupset|angmsdaf|sqsubset|llcorner|vartheta|cupbrcap|lnapprox|Superset|SuchThat|succnsim|succneqq|angmsdag|biguplus|curlyvee|trpezium|Succeeds|NotTilde|bigwedge|angmsdah|angrtvbd|triminus|cwconint|fpartint|lrcorner|smeparsl|subseteq|urcorner|lurdshar|laemptyv|DDotrahd|approxeq|ldrushar|awconint|mapstoup|backcong|shortmid|triangle|geqslant|gesdotol|timesbar|circledR|circledS|setminus|multimap|naturals|scpolint|ncongdot|RightTee|boxminus|gnapprox|boxtimes|andslope|thicksim|angmsdaa|varsigma|cirfnint|rtriltri|angmsdab|rppolint|angmsdac|barwedge|drbkarow|clubsuit|thetasym|bsolhsub|capbrcup|dzigrarr|doteqdot|DotEqual|dotminus|UnderBar|NotEqual|realpart|otimesas|ulcorner|hksearow|hkswarow|parallel|PartialD|elinters|emptyset|plusacir|bbrktbrk|angmsdad|pointint|bigoplus|angmsdae|Precedes|bigsqcup|varkappa|notindot|supseteq|precneqq|precnsim|profalar|profline|profsurf|leqslant|lesdotor|raemptyv|subplus|notnivb|notnivc|subrarr|zigrarr|vzigzag|submult|subedot|Element|between|cirscir|larrbfs|larrsim|lotimes|lbrksld|lbrkslu|lozenge|ldrdhar|dbkarow|bigcirc|epsilon|simrarr|simplus|ltquest|Epsilon|luruhar|gtquest|maltese|npolint|eqcolon|npreceq|bigodot|ddagger|gtrless|bnequiv|harrcir|ddotseq|equivDD|backsim|demptyv|nsqsube|nsqsupe|Upsilon|nsubset|upsilon|minusdu|nsucceq|swarrow|nsupset|coloneq|searrow|boxplus|napprox|natural|asympeq|alefsym|congdot|nearrow|bigstar|diamond|supplus|tritime|LeftTee|nvinfin|triplus|NewLine|nvltrie|nvrtrie|nwarrow|nexists|Diamond|ruluhar|Implies|supmult|angzarr|suplarr|suphsub|questeq|because|digamma|Because|olcross|bemptyv|omicron|Omicron|rotimes|NoBreak|intprod|angrtvb|orderof|uwangle|suphsol|lesdoto|orslope|DownTee|realine|cudarrl|rdldhar|OverBar|supedot|lessdot|supdsub|topfork|succsim|rbrkslu|rbrksld|pertenk|cudarrr|isindot|planckh|lessgtr|pluscir|gesdoto|plussim|plustwo|lesssim|cularrp|rarrsim|Cayleys|notinva|notinvb|notinvc|UpArrow|Uparrow|uparrow|NotLess|dwangle|precsim|Product|curarrm|Cconint|dotplus|rarrbfs|ccupssm|Cedilla|cemptyv|notniva|quatint|frac35|frac38|frac45|frac56|frac58|frac78|tridot|xoplus|gacute|gammad|Gammad|lfisht|lfloor|bigcup|sqsupe|gbreve|Gbreve|lharul|sqsube|sqcups|Gcedil|apacir|llhard|lmidot|Lmidot|lmoust|andand|sqcaps|approx|Abreve|spades|circeq|tprime|divide|topcir|Assign|topbot|gesdot|divonx|xuplus|timesd|gesles|atilde|solbar|SOFTcy|loplus|timesb|lowast|lowbar|dlcorn|dlcrop|softcy|dollar|lparlt|thksim|lrhard|Atilde|lsaquo|smashp|bigvee|thinsp|wreath|bkarow|lsquor|lstrok|Lstrok|lthree|ltimes|ltlarr|DotDot|simdot|ltrPar|weierp|xsqcup|angmsd|sigmav|sigmaf|zeetrf|Zcaron|zcaron|mapsto|vsupne|thetav|cirmid|marker|mcomma|Zacute|vsubnE|there4|gtlPar|vsubne|bottom|gtrarr|SHCHcy|shchcy|midast|midcir|middot|minusb|minusd|gtrdot|bowtie|sfrown|mnplus|models|colone|seswar|Colone|mstpos|searhk|gtrsim|nacute|Nacute|boxbox|telrec|hairsp|Tcedil|nbumpe|scnsim|ncaron|Ncaron|ncedil|Ncedil|hamilt|Scedil|nearhk|hardcy|HARDcy|tcedil|Tcaron|commat|nequiv|nesear|tcaron|target|hearts|nexist|varrho|scedil|Scaron|scaron|hellip|Sacute|sacute|hercon|swnwar|compfn|rtimes|rthree|rsquor|rsaquo|zacute|wedgeq|homtht|barvee|barwed|Barwed|rpargt|horbar|conint|swarhk|roplus|nltrie|hslash|hstrok|Hstrok|rmoust|Conint|bprime|hybull|hyphen|iacute|Iacute|supsup|supsub|supsim|varphi|coprod|brvbar|agrave|Supset|supset|igrave|Igrave|notinE|Agrave|iiiint|iinfin|copysr|wedbar|Verbar|vangrt|becaus|incare|verbar|inodot|bullet|drcorn|intcal|drcrop|cularr|vellip|Utilde|bumpeq|cupcap|dstrok|Dstrok|CupCap|cupcup|cupdot|eacute|Eacute|supdot|iquest|easter|ecaron|Ecaron|ecolon|isinsv|utilde|itilde|Itilde|curarr|succeq|Bumpeq|cacute|ulcrop|nparsl|Cacute|nprcue|egrave|Egrave|nrarrc|nrarrw|subsup|subsub|nrtrie|jsercy|nsccue|Jsercy|kappav|kcedil|Kcedil|subsim|ulcorn|nsimeq|egsdot|veebar|kgreen|capand|elsdot|Subset|subset|curren|aacute|lacute|Lacute|emptyv|ntilde|Ntilde|lagran|lambda|Lambda|capcap|Ugrave|langle|subdot|emsp13|numero|emsp14|nvdash|nvDash|nVdash|nVDash|ugrave|ufisht|nvHarr|larrfs|nvlArr|larrhk|larrlp|larrpl|nvrArr|Udblac|nwarhk|larrtl|nwnear|oacute|Oacute|latail|lAtail|sstarf|lbrace|odblac|Odblac|lbrack|udblac|odsold|eparsl|lcaron|Lcaron|ograve|Ograve|lcedil|Lcedil|Aacute|ssmile|ssetmn|squarf|ldquor|capcup|ominus|cylcty|rharul|eqcirc|dagger|rfloor|rfisht|Dagger|daleth|equals|origof|capdot|equest|dcaron|Dcaron|rdquor|oslash|Oslash|otilde|Otilde|otimes|Otimes|urcrop|Ubreve|ubreve|Yacute|Uacute|uacute|Rcedil|rcedil|urcorn|parsim|Rcaron|Vdashl|rcaron|Tstrok|percnt|period|permil|Exists|yacute|rbrack|rbrace|phmmat|ccaron|Ccaron|planck|ccedil|plankv|tstrok|female|plusdo|plusdu|ffilig|plusmn|ffllig|Ccedil|rAtail|dfisht|bernou|ratail|Rarrtl|rarrtl|angsph|rarrpl|rarrlp|rarrhk|xwedge|xotime|forall|ForAll|Vvdash|vsupnE|preceq|bigcap|frac12|frac13|frac14|primes|rarrfs|prnsim|frac15|Square|frac16|square|lesdot|frac18|frac23|propto|prurel|rarrap|rangle|puncsp|frac25|Racute|qprime|racute|lesges|frac34|abreve|AElig|eqsim|utdot|setmn|urtri|Equal|Uring|seArr|uring|searr|dashv|Dashv|mumap|nabla|iogon|Iogon|sdote|sdotb|scsim|napid|napos|equiv|natur|Acirc|dblac|erarr|nbump|iprod|erDot|ucirc|awint|esdot|angrt|ncong|isinE|scnap|Scirc|scirc|ndash|isins|Ubrcy|nearr|neArr|isinv|nedot|ubrcy|acute|Ycirc|iukcy|Iukcy|xutri|nesim|caret|jcirc|Jcirc|caron|twixt|ddarr|sccue|exist|jmath|sbquo|ngeqq|angst|ccaps|lceil|ngsim|UpTee|delta|Delta|rtrif|nharr|nhArr|nhpar|rtrie|jukcy|Jukcy|kappa|rsquo|Kappa|nlarr|nlArr|TSHcy|rrarr|aogon|Aogon|fflig|xrarr|tshcy|ccirc|nleqq|filig|upsih|nless|dharl|nlsim|fjlig|ropar|nltri|dharr|robrk|roarr|fllig|fltns|roang|rnmid|subnE|subne|lAarr|trisb|Ccirc|acirc|ccups|blank|VDash|forkv|Vdash|langd|cedil|blk12|blk14|laquo|strns|diams|notin|vDash|larrb|blk34|block|disin|uplus|vdash|vBarv|aelig|starf|Wedge|check|xrArr|lates|lbarr|lBarr|notni|lbbrk|bcong|frasl|lbrke|frown|vrtri|vprop|vnsup|gamma|Gamma|wedge|xodot|bdquo|srarr|doteq|ldquo|boxdl|boxdL|gcirc|Gcirc|boxDl|boxDL|boxdr|boxdR|boxDr|TRADE|trade|rlhar|boxDR|vnsub|npart|vltri|rlarr|boxhd|boxhD|nprec|gescc|nrarr|nrArr|boxHd|boxHD|boxhu|boxhU|nrtri|boxHu|clubs|boxHU|times|colon|Colon|gimel|xlArr|Tilde|nsime|tilde|nsmid|nspar|THORN|thorn|xlarr|nsube|nsubE|thkap|xhArr|comma|nsucc|boxul|boxuL|nsupe|nsupE|gneqq|gnsim|boxUl|boxUL|grave|boxur|boxuR|boxUr|boxUR|lescc|angle|bepsi|boxvh|varpi|boxvH|numsp|Theta|gsime|gsiml|theta|boxVh|boxVH|boxvl|gtcir|gtdot|boxvL|boxVl|boxVL|crarr|cross|Cross|nvsim|boxvr|nwarr|nwArr|sqsup|dtdot|Uogon|lhard|lharu|dtrif|ocirc|Ocirc|lhblk|duarr|odash|sqsub|Hacek|sqcup|llarr|duhar|oelig|OElig|ofcir|boxvR|uogon|lltri|boxVr|csube|uuarr|ohbar|csupe|ctdot|olarr|olcir|harrw|oline|sqcap|omacr|Omacr|omega|Omega|boxVR|aleph|lneqq|lnsim|loang|loarr|rharu|lobrk|hcirc|operp|oplus|rhard|Hcirc|orarr|Union|order|ecirc|Ecirc|cuepr|szlig|cuesc|breve|reals|eDDot|Breve|hoarr|lopar|utrif|rdquo|Umacr|umacr|efDot|swArr|ultri|alpha|rceil|ovbar|swarr|Wcirc|wcirc|smtes|smile|bsemi|lrarr|aring|parsl|lrhar|bsime|uhblk|lrtri|cupor|Aring|uharr|uharl|slarr|rbrke|bsolb|lsime|rbbrk|RBarr|lsimg|phone|rBarr|rbarr|icirc|lsquo|Icirc|emacr|Emacr|ratio|simne|plusb|simlE|simgE|simeq|pluse|ltcir|ltdot|empty|xharr|xdtri|iexcl|Alpha|ltrie|rarrw|pound|ltrif|xcirc|bumpe|prcue|bumpE|asymp|amacr|cuvee|Sigma|sigma|iiint|udhar|iiota|ijlig|IJlig|supnE|imacr|Imacr|prime|Prime|image|prnap|eogon|Eogon|rarrc|mdash|mDDot|cuwed|imath|supne|imped|Amacr|udarr|prsim|micro|rarrb|cwint|raquo|infin|eplus|range|rangd|Ucirc|radic|minus|amalg|veeeq|rAarr|epsiv|ycirc|quest|sharp|quot|zwnj|Qscr|race|qscr|Qopf|qopf|qint|rang|Rang|Zscr|zscr|Zopf|zopf|rarr|rArr|Rarr|Pscr|pscr|prop|prod|prnE|prec|ZHcy|zhcy|prap|Zeta|zeta|Popf|popf|Zdot|plus|zdot|Yuml|yuml|phiv|YUcy|yucy|Yscr|yscr|perp|Yopf|yopf|part|para|YIcy|Ouml|rcub|yicy|YAcy|rdca|ouml|osol|Oscr|rdsh|yacy|real|oscr|xvee|andd|rect|andv|Xscr|oror|ordm|ordf|xscr|ange|aopf|Aopf|rHar|Xopf|opar|Oopf|xopf|xnis|rhov|oopf|omid|xmap|oint|apid|apos|ogon|ascr|Ascr|odot|odiv|xcup|xcap|ocir|oast|nvlt|nvle|nvgt|nvge|nvap|Wscr|wscr|auml|ntlg|ntgl|nsup|nsub|nsim|Nscr|nscr|nsce|Wopf|ring|npre|wopf|npar|Auml|Barv|bbrk|Nopf|nopf|nmid|nLtv|beta|ropf|Ropf|Beta|beth|nles|rpar|nleq|bnot|bNot|nldr|NJcy|rscr|Rscr|Vscr|vscr|rsqb|njcy|bopf|nisd|Bopf|rtri|Vopf|nGtv|ngtr|vopf|boxh|boxH|boxv|nges|ngeq|boxV|bscr|scap|Bscr|bsim|Vert|vert|bsol|bull|bump|caps|cdot|ncup|scnE|ncap|nbsp|napE|Cdot|cent|sdot|Vbar|nang|vBar|chcy|Mscr|mscr|sect|semi|CHcy|Mopf|mopf|sext|circ|cire|mldr|mlcp|cirE|comp|shcy|SHcy|vArr|varr|cong|copf|Copf|copy|COPY|malt|male|macr|lvnE|cscr|ltri|sime|ltcc|simg|Cscr|siml|csub|Uuml|lsqb|lsim|uuml|csup|Lscr|lscr|utri|smid|lpar|cups|smte|lozf|darr|Lopf|Uscr|solb|lopf|sopf|Sopf|lneq|uscr|spar|dArr|lnap|Darr|dash|Sqrt|LJcy|ljcy|lHar|dHar|Upsi|upsi|diam|lesg|djcy|DJcy|leqq|dopf|Dopf|dscr|Dscr|dscy|ldsh|ldca|squf|DScy|sscr|Sscr|dsol|lcub|late|star|Star|Uopf|Larr|lArr|larr|uopf|dtri|dzcy|sube|subE|Lang|lang|Kscr|kscr|Kopf|kopf|KJcy|kjcy|KHcy|khcy|DZcy|ecir|edot|eDot|Jscr|jscr|succ|Jopf|jopf|Edot|uHar|emsp|ensp|Iuml|iuml|eopf|isin|Iscr|iscr|Eopf|epar|sung|epsi|escr|sup1|sup2|sup3|Iota|iota|supe|supE|Iopf|iopf|IOcy|iocy|Escr|esim|Esim|imof|Uarr|QUOT|uArr|uarr|euml|IEcy|iecy|Idot|Euml|euro|excl|Hscr|hscr|Hopf|hopf|TScy|tscy|Tscr|hbar|tscr|flat|tbrk|fnof|hArr|harr|half|fopf|Fopf|tdot|gvnE|fork|trie|gtcc|fscr|Fscr|gdot|gsim|Gscr|gscr|Gopf|gopf|gneq|Gdot|tosa|gnap|Topf|topf|geqq|toea|GJcy|gjcy|tint|gesl|mid|Sfr|ggg|top|ges|gla|glE|glj|geq|gne|gEl|gel|gnE|Gcy|gcy|gap|Tfr|tfr|Tcy|tcy|Hat|Tau|Ffr|tau|Tab|hfr|Hfr|ffr|Fcy|fcy|icy|Icy|iff|ETH|eth|ifr|Ifr|Eta|eta|int|Int|Sup|sup|ucy|Ucy|Sum|sum|jcy|ENG|ufr|Ufr|eng|Jcy|jfr|els|ell|egs|Efr|efr|Jfr|uml|kcy|Kcy|Ecy|ecy|kfr|Kfr|lap|Sub|sub|lat|lcy|Lcy|leg|Dot|dot|lEg|leq|les|squ|div|die|lfr|Lfr|lgE|Dfr|dfr|Del|deg|Dcy|dcy|lne|lnE|sol|loz|smt|Cup|lrm|cup|lsh|Lsh|sim|shy|map|Map|mcy|Mcy|mfr|Mfr|mho|gfr|Gfr|sfr|cir|Chi|chi|nap|Cfr|vcy|Vcy|cfr|Scy|scy|ncy|Ncy|vee|Vee|Cap|cap|nfr|scE|sce|Nfr|nge|ngE|nGg|vfr|Vfr|ngt|bot|nGt|nis|niv|Rsh|rsh|nle|nlE|bne|Bfr|bfr|nLl|nlt|nLt|Bcy|bcy|not|Not|rlm|wfr|Wfr|npr|nsc|num|ocy|ast|Ocy|ofr|xfr|Xfr|Ofr|ogt|ohm|apE|olt|Rho|ape|rho|Rfr|rfr|ord|REG|ang|reg|orv|And|and|AMP|Rcy|amp|Afr|ycy|Ycy|yen|yfr|Yfr|rcy|par|pcy|Pcy|pfr|Pfr|phi|Phi|afr|Acy|acy|zcy|Zcy|piv|acE|acd|zfr|Zfr|pre|prE|psi|Psi|qfr|Qfr|zwj|Or|ge|Gg|gt|gg|el|oS|lt|Lt|LT|Re|lg|gl|eg|ne|Im|it|le|DD|wp|wr|nu|Nu|dd|lE|Sc|sc|pi|Pi|ee|af|ll|Ll|rx|gE|xi|pm|Xi|ic|pr|Pr|in|ni|mp|mu|ac|Mu|or|ap|Gt|GT|ii);|&(Aacute|Agrave|Atilde|Ccedil|Eacute|Egrave|Iacute|Igrave|Ntilde|Oacute|Ograve|Oslash|Otilde|Uacute|Ugrave|Yacute|aacute|agrave|atilde|brvbar|ccedil|curren|divide|eacute|egrave|frac12|frac14|frac34|iacute|igrave|iquest|middot|ntilde|oacute|ograve|oslash|otilde|plusmn|uacute|ugrave|yacute|AElig|Acirc|Aring|Ecirc|Icirc|Ocirc|THORN|Ucirc|acirc|acute|aelig|aring|cedil|ecirc|icirc|iexcl|laquo|micro|ocirc|pound|raquo|szlig|thorn|times|ucirc|Auml|COPY|Euml|Iuml|Ouml|QUOT|Uuml|auml|cent|copy|euml|iuml|macr|nbsp|ordf|ordm|ouml|para|quot|sect|sup1|sup2|sup3|uuml|yuml|AMP|ETH|REG|amp|deg|eth|not|reg|shy|uml|yen|GT|LT|gt|lt)(?!;)([=a-zA-Z0-9]?)|&#([0-9]+)(;?)|&#[xX]([a-fA-F0-9]+)(;?)|&([0-9a-zA-Z]+)/g;\n var decodeMap2 = { \"aacute\": \"á\", \"Aacute\": \"Á\", \"abreve\": \"ă\", \"Abreve\": \"Ă\", \"ac\": \"∾\", \"acd\": \"∿\", \"acE\": \"∾̳\", \"acirc\": \"â\", \"Acirc\": \"Â\", \"acute\": \"´\", \"acy\": \"а\", \"Acy\": \"А\", \"aelig\": \"æ\", \"AElig\": \"Æ\", \"af\": \"⁡\", \"afr\": \"𝔞\", \"Afr\": \"𝔄\", \"agrave\": \"à\", \"Agrave\": \"À\", \"alefsym\": \"ℵ\", \"aleph\": \"ℵ\", \"alpha\": \"α\", \"Alpha\": \"Α\", \"amacr\": \"ā\", \"Amacr\": \"Ā\", \"amalg\": \"⨿\", \"amp\": \"&\", \"AMP\": \"&\", \"and\": \"∧\", \"And\": \"⩓\", \"andand\": \"⩕\", \"andd\": \"⩜\", \"andslope\": \"⩘\", \"andv\": \"⩚\", \"ang\": \"∠\", \"ange\": \"⦤\", \"angle\": \"∠\", \"angmsd\": \"∡\", \"angmsdaa\": \"⦨\", \"angmsdab\": \"⦩\", \"angmsdac\": \"⦪\", \"angmsdad\": \"⦫\", \"angmsdae\": \"⦬\", \"angmsdaf\": \"⦭\", \"angmsdag\": \"⦮\", \"angmsdah\": \"⦯\", \"angrt\": \"∟\", \"angrtvb\": \"⊾\", \"angrtvbd\": \"⦝\", \"angsph\": \"∢\", \"angst\": \"Å\", \"angzarr\": \"⍼\", \"aogon\": \"ą\", \"Aogon\": \"Ą\", \"aopf\": \"𝕒\", \"Aopf\": \"𝔸\", \"ap\": \"≈\", \"apacir\": \"⩯\", \"ape\": \"≊\", \"apE\": \"⩰\", \"apid\": \"≋\", \"apos\": \"'\", \"ApplyFunction\": \"⁡\", \"approx\": \"≈\", \"approxeq\": \"≊\", \"aring\": \"å\", \"Aring\": \"Å\", \"ascr\": \"𝒶\", \"Ascr\": \"𝒜\", \"Assign\": \"≔\", \"ast\": \"*\", \"asymp\": \"≈\", \"asympeq\": \"≍\", \"atilde\": \"ã\", \"Atilde\": \"Ã\", \"auml\": \"ä\", \"Auml\": \"Ä\", \"awconint\": \"∳\", \"awint\": \"⨑\", \"backcong\": \"≌\", \"backepsilon\": \"϶\", \"backprime\": \"‵\", \"backsim\": \"∽\", \"backsimeq\": \"⋍\", \"Backslash\": \"∖\", \"Barv\": \"⫧\", \"barvee\": \"⊽\", \"barwed\": \"⌅\", \"Barwed\": \"⌆\", \"barwedge\": \"⌅\", \"bbrk\": \"⎵\", \"bbrktbrk\": \"⎶\", \"bcong\": \"≌\", \"bcy\": \"б\", \"Bcy\": \"Б\", \"bdquo\": \"„\", \"becaus\": \"∵\", \"because\": \"∵\", \"Because\": \"∵\", \"bemptyv\": \"⦰\", \"bepsi\": \"϶\", \"bernou\": \"ℬ\", \"Bernoullis\": \"ℬ\", \"beta\": \"β\", \"Beta\": \"Β\", \"beth\": \"ℶ\", \"between\": \"≬\", \"bfr\": \"𝔟\", \"Bfr\": \"𝔅\", \"bigcap\": \"⋂\", \"bigcirc\": \"◯\", \"bigcup\": \"⋃\", \"bigodot\": \"⨀\", \"bigoplus\": \"⨁\", \"bigotimes\": \"⨂\", \"bigsqcup\": \"⨆\", \"bigstar\": \"★\", \"bigtriangledown\": \"▽\", \"bigtriangleup\": \"△\", \"biguplus\": \"⨄\", \"bigvee\": \"⋁\", \"bigwedge\": \"⋀\", \"bkarow\": \"⤍\", \"blacklozenge\": \"⧫\", \"blacksquare\": \"▪\", \"blacktriangle\": \"▴\", \"blacktriangledown\": \"▾\", \"blacktriangleleft\": \"◂\", \"blacktriangleright\": \"▸\", \"blank\": \"␣\", \"blk12\": \"▒\", \"blk14\": \"░\", \"blk34\": \"▓\", \"block\": \"█\", \"bne\": \"=⃥\", \"bnequiv\": \"≡⃥\", \"bnot\": \"⌐\", \"bNot\": \"⫭\", \"bopf\": \"𝕓\", \"Bopf\": \"𝔹\", \"bot\": \"⊥\", \"bottom\": \"⊥\", \"bowtie\": \"⋈\", \"boxbox\": \"⧉\", \"boxdl\": \"┐\", \"boxdL\": \"╕\", \"boxDl\": \"╖\", \"boxDL\": \"╗\", \"boxdr\": \"┌\", \"boxdR\": \"╒\", \"boxDr\": \"╓\", \"boxDR\": \"╔\", \"boxh\": \"─\", \"boxH\": \"═\", \"boxhd\": \"┬\", \"boxhD\": \"╥\", \"boxHd\": \"╤\", \"boxHD\": \"╦\", \"boxhu\": \"┴\", \"boxhU\": \"╨\", \"boxHu\": \"╧\", \"boxHU\": \"╩\", \"boxminus\": \"⊟\", \"boxplus\": \"⊞\", \"boxtimes\": \"⊠\", \"boxul\": \"┘\", \"boxuL\": \"╛\", \"boxUl\": \"╜\", \"boxUL\": \"╝\", \"boxur\": \"└\", \"boxuR\": \"╘\", \"boxUr\": \"╙\", \"boxUR\": \"╚\", \"boxv\": \"│\", \"boxV\": \"║\", \"boxvh\": \"┼\", \"boxvH\": \"╪\", \"boxVh\": \"╫\", \"boxVH\": \"╬\", \"boxvl\": \"┤\", \"boxvL\": \"╡\", \"boxVl\": \"╢\", \"boxVL\": \"╣\", \"boxvr\": \"├\", \"boxvR\": \"╞\", \"boxVr\": \"╟\", \"boxVR\": \"╠\", \"bprime\": \"‵\", \"breve\": \"˘\", \"Breve\": \"˘\", \"brvbar\": \"¦\", \"bscr\": \"𝒷\", \"Bscr\": \"ℬ\", \"bsemi\": \"⁏\", \"bsim\": \"∽\", \"bsime\": \"⋍\", \"bsol\": \"\\\\\", \"bsolb\": \"⧅\", \"bsolhsub\": \"⟈\", \"bull\": \"•\", \"bullet\": \"•\", \"bump\": \"≎\", \"bumpe\": \"≏\", \"bumpE\": \"⪮\", \"bumpeq\": \"≏\", \"Bumpeq\": \"≎\", \"cacute\": \"ć\", \"Cacute\": \"Ć\", \"cap\": \"∩\", \"Cap\": \"⋒\", \"capand\": \"⩄\", \"capbrcup\": \"⩉\", \"capcap\": \"⩋\", \"capcup\": \"⩇\", \"capdot\": \"⩀\", \"CapitalDifferentialD\": \"ⅅ\", \"caps\": \"∩︀\", \"caret\": \"⁁\", \"caron\": \"ˇ\", \"Cayleys\": \"ℭ\", \"ccaps\": \"⩍\", \"ccaron\": \"č\", \"Ccaron\": \"Č\", \"ccedil\": \"ç\", \"Ccedil\": \"Ç\", \"ccirc\": \"ĉ\", \"Ccirc\": \"Ĉ\", \"Cconint\": \"∰\", \"ccups\": \"⩌\", \"ccupssm\": \"⩐\", \"cdot\": \"ċ\", \"Cdot\": \"Ċ\", \"cedil\": \"¸\", \"Cedilla\": \"¸\", \"cemptyv\": \"⦲\", \"cent\": \"¢\", \"centerdot\": \"·\", \"CenterDot\": \"·\", \"cfr\": \"𝔠\", \"Cfr\": \"ℭ\", \"chcy\": \"ч\", \"CHcy\": \"Ч\", \"check\": \"✓\", \"checkmark\": \"✓\", \"chi\": \"χ\", \"Chi\": \"Χ\", \"cir\": \"○\", \"circ\": \"ˆ\", \"circeq\": \"≗\", \"circlearrowleft\": \"↺\", \"circlearrowright\": \"↻\", \"circledast\": \"⊛\", \"circledcirc\": \"⊚\", \"circleddash\": \"⊝\", \"CircleDot\": \"⊙\", \"circledR\": \"®\", \"circledS\": \"Ⓢ\", \"CircleMinus\": \"⊖\", \"CirclePlus\": \"⊕\", \"CircleTimes\": \"⊗\", \"cire\": \"≗\", \"cirE\": \"⧃\", \"cirfnint\": \"⨐\", \"cirmid\": \"⫯\", \"cirscir\": \"⧂\", \"ClockwiseContourIntegral\": \"∲\", \"CloseCurlyDoubleQuote\": \"”\", \"CloseCurlyQuote\": \"’\", \"clubs\": \"♣\", \"clubsuit\": \"♣\", \"colon\": \":\", \"Colon\": \"∷\", \"colone\": \"≔\", \"Colone\": \"⩴\", \"coloneq\": \"≔\", \"comma\": \",\", \"commat\": \"@\", \"comp\": \"∁\", \"compfn\": \"∘\", \"complement\": \"∁\", \"complexes\": \"ℂ\", \"cong\": \"≅\", \"congdot\": \"⩭\", \"Congruent\": \"≡\", \"conint\": \"∮\", \"Conint\": \"∯\", \"ContourIntegral\": \"∮\", \"copf\": \"𝕔\", \"Copf\": \"ℂ\", \"coprod\": \"∐\", \"Coproduct\": \"∐\", \"copy\": \"©\", \"COPY\": \"©\", \"copysr\": \"℗\", \"CounterClockwiseContourIntegral\": \"∳\", \"crarr\": \"↵\", \"cross\": \"✗\", \"Cross\": \"⨯\", \"cscr\": \"𝒸\", \"Cscr\": \"𝒞\", \"csub\": \"⫏\", \"csube\": \"⫑\", \"csup\": \"⫐\", \"csupe\": \"⫒\", \"ctdot\": \"⋯\", \"cudarrl\": \"⤸\", \"cudarrr\": \"⤵\", \"cuepr\": \"⋞\", \"cuesc\": \"⋟\", \"cularr\": \"↶\", \"cularrp\": \"⤽\", \"cup\": \"∪\", \"Cup\": \"⋓\", \"cupbrcap\": \"⩈\", \"cupcap\": \"⩆\", \"CupCap\": \"≍\", \"cupcup\": \"⩊\", \"cupdot\": \"⊍\", \"cupor\": \"⩅\", \"cups\": \"∪︀\", \"curarr\": \"↷\", \"curarrm\": \"⤼\", \"curlyeqprec\": \"⋞\", \"curlyeqsucc\": \"⋟\", \"curlyvee\": \"⋎\", \"curlywedge\": \"⋏\", \"curren\": \"¤\", \"curvearrowleft\": \"↶\", \"curvearrowright\": \"↷\", \"cuvee\": \"⋎\", \"cuwed\": \"⋏\", \"cwconint\": \"∲\", \"cwint\": \"∱\", \"cylcty\": \"⌭\", \"dagger\": \"†\", \"Dagger\": \"‡\", \"daleth\": \"ℸ\", \"darr\": \"↓\", \"dArr\": \"⇓\", \"Darr\": \"↡\", \"dash\": \"‐\", \"dashv\": \"⊣\", \"Dashv\": \"⫤\", \"dbkarow\": \"⤏\", \"dblac\": \"˝\", \"dcaron\": \"ď\", \"Dcaron\": \"Ď\", \"dcy\": \"д\", \"Dcy\": \"Д\", \"dd\": \"ⅆ\", \"DD\": \"ⅅ\", \"ddagger\": \"‡\", \"ddarr\": \"⇊\", \"DDotrahd\": \"⤑\", \"ddotseq\": \"⩷\", \"deg\": \"°\", \"Del\": \"∇\", \"delta\": \"δ\", \"Delta\": \"Δ\", \"demptyv\": \"⦱\", \"dfisht\": \"⥿\", \"dfr\": \"𝔡\", \"Dfr\": \"𝔇\", \"dHar\": \"⥥\", \"dharl\": \"⇃\", \"dharr\": \"⇂\", \"DiacriticalAcute\": \"´\", \"DiacriticalDot\": \"˙\", \"DiacriticalDoubleAcute\": \"˝\", \"DiacriticalGrave\": \"`\", \"DiacriticalTilde\": \"˜\", \"diam\": \"⋄\", \"diamond\": \"⋄\", \"Diamond\": \"⋄\", \"diamondsuit\": \"♦\", \"diams\": \"♦\", \"die\": \"¨\", \"DifferentialD\": \"ⅆ\", \"digamma\": \"ϝ\", \"disin\": \"⋲\", \"div\": \"÷\", \"divide\": \"÷\", \"divideontimes\": \"⋇\", \"divonx\": \"⋇\", \"djcy\": \"ђ\", \"DJcy\": \"Ђ\", \"dlcorn\": \"⌞\", \"dlcrop\": \"⌍\", \"dollar\": \"$\", \"dopf\": \"𝕕\", \"Dopf\": \"𝔻\", \"dot\": \"˙\", \"Dot\": \"¨\", \"DotDot\": \"⃜\", \"doteq\": \"≐\", \"doteqdot\": \"≑\", \"DotEqual\": \"≐\", \"dotminus\": \"∸\", \"dotplus\": \"∔\", \"dotsquare\": \"⊡\", \"doublebarwedge\": \"⌆\", \"DoubleContourIntegral\": \"∯\", \"DoubleDot\": \"¨\", \"DoubleDownArrow\": \"⇓\", \"DoubleLeftArrow\": \"⇐\", \"DoubleLeftRightArrow\": \"⇔\", \"DoubleLeftTee\": \"⫤\", \"DoubleLongLeftArrow\": \"⟸\", \"DoubleLongLeftRightArrow\": \"⟺\", \"DoubleLongRightArrow\": \"⟹\", \"DoubleRightArrow\": \"⇒\", \"DoubleRightTee\": \"⊨\", \"DoubleUpArrow\": \"⇑\", \"DoubleUpDownArrow\": \"⇕\", \"DoubleVerticalBar\": \"∥\", \"downarrow\": \"↓\", \"Downarrow\": \"⇓\", \"DownArrow\": \"↓\", \"DownArrowBar\": \"⤓\", \"DownArrowUpArrow\": \"⇵\", \"DownBreve\": \"̑\", \"downdownarrows\": \"⇊\", \"downharpoonleft\": \"⇃\", \"downharpoonright\": \"⇂\", \"DownLeftRightVector\": \"⥐\", \"DownLeftTeeVector\": \"⥞\", \"DownLeftVector\": \"↽\", \"DownLeftVectorBar\": \"⥖\", \"DownRightTeeVector\": \"⥟\", \"DownRightVector\": \"⇁\", \"DownRightVectorBar\": \"⥗\", \"DownTee\": \"⊤\", \"DownTeeArrow\": \"↧\", \"drbkarow\": \"⤐\", \"drcorn\": \"⌟\", \"drcrop\": \"⌌\", \"dscr\": \"𝒹\", \"Dscr\": \"𝒟\", \"dscy\": \"ѕ\", \"DScy\": \"Ѕ\", \"dsol\": \"⧶\", \"dstrok\": \"đ\", \"Dstrok\": \"Đ\", \"dtdot\": \"⋱\", \"dtri\": \"▿\", \"dtrif\": \"▾\", \"duarr\": \"⇵\", \"duhar\": \"⥯\", \"dwangle\": \"⦦\", \"dzcy\": \"џ\", \"DZcy\": \"Џ\", \"dzigrarr\": \"⟿\", \"eacute\": \"é\", \"Eacute\": \"É\", \"easter\": \"⩮\", \"ecaron\": \"ě\", \"Ecaron\": \"Ě\", \"ecir\": \"≖\", \"ecirc\": \"ê\", \"Ecirc\": \"Ê\", \"ecolon\": \"≕\", \"ecy\": \"э\", \"Ecy\": \"Э\", \"eDDot\": \"⩷\", \"edot\": \"ė\", \"eDot\": \"≑\", \"Edot\": \"Ė\", \"ee\": \"ⅇ\", \"efDot\": \"≒\", \"efr\": \"𝔢\", \"Efr\": \"𝔈\", \"eg\": \"⪚\", \"egrave\": \"è\", \"Egrave\": \"È\", \"egs\": \"⪖\", \"egsdot\": \"⪘\", \"el\": \"⪙\", \"Element\": \"∈\", \"elinters\": \"⏧\", \"ell\": \"ℓ\", \"els\": \"⪕\", \"elsdot\": \"⪗\", \"emacr\": \"ē\", \"Emacr\": \"Ē\", \"empty\": \"∅\", \"emptyset\": \"∅\", \"EmptySmallSquare\": \"◻\", \"emptyv\": \"∅\", \"EmptyVerySmallSquare\": \"▫\", \"emsp\": \" \", \"emsp13\": \" \", \"emsp14\": \" \", \"eng\": \"ŋ\", \"ENG\": \"Ŋ\", \"ensp\": \" \", \"eogon\": \"ę\", \"Eogon\": \"Ę\", \"eopf\": \"𝕖\", \"Eopf\": \"𝔼\", \"epar\": \"⋕\", \"eparsl\": \"⧣\", \"eplus\": \"⩱\", \"epsi\": \"ε\", \"epsilon\": \"ε\", \"Epsilon\": \"Ε\", \"epsiv\": \"ϵ\", \"eqcirc\": \"≖\", \"eqcolon\": \"≕\", \"eqsim\": \"≂\", \"eqslantgtr\": \"⪖\", \"eqslantless\": \"⪕\", \"Equal\": \"⩵\", \"equals\": \"=\", \"EqualTilde\": \"≂\", \"equest\": \"≟\", \"Equilibrium\": \"⇌\", \"equiv\": \"≡\", \"equivDD\": \"⩸\", \"eqvparsl\": \"⧥\", \"erarr\": \"⥱\", \"erDot\": \"≓\", \"escr\": \"ℯ\", \"Escr\": \"ℰ\", \"esdot\": \"≐\", \"esim\": \"≂\", \"Esim\": \"⩳\", \"eta\": \"η\", \"Eta\": \"Η\", \"eth\": \"ð\", \"ETH\": \"Ð\", \"euml\": \"ë\", \"Euml\": \"Ë\", \"euro\": \"€\", \"excl\": \"!\", \"exist\": \"∃\", \"Exists\": \"∃\", \"expectation\": \"ℰ\", \"exponentiale\": \"ⅇ\", \"ExponentialE\": \"ⅇ\", \"fallingdotseq\": \"≒\", \"fcy\": \"ф\", \"Fcy\": \"Ф\", \"female\": \"♀\", \"ffilig\": \"ffi\", \"fflig\": \"ff\", \"ffllig\": \"ffl\", \"ffr\": \"𝔣\", \"Ffr\": \"𝔉\", \"filig\": \"fi\", \"FilledSmallSquare\": \"◼\", \"FilledVerySmallSquare\": \"▪\", \"fjlig\": \"fj\", \"flat\": \"♭\", \"fllig\": \"fl\", \"fltns\": \"▱\", \"fnof\": \"ƒ\", \"fopf\": \"𝕗\", \"Fopf\": \"𝔽\", \"forall\": \"∀\", \"ForAll\": \"∀\", \"fork\": \"⋔\", \"forkv\": \"⫙\", \"Fouriertrf\": \"ℱ\", \"fpartint\": \"⨍\", \"frac12\": \"½\", \"frac13\": \"⅓\", \"frac14\": \"¼\", \"frac15\": \"⅕\", \"frac16\": \"⅙\", \"frac18\": \"⅛\", \"frac23\": \"⅔\", \"frac25\": \"⅖\", \"frac34\": \"¾\", \"frac35\": \"⅗\", \"frac38\": \"⅜\", \"frac45\": \"⅘\", \"frac56\": \"⅚\", \"frac58\": \"⅝\", \"frac78\": \"⅞\", \"frasl\": \"⁄\", \"frown\": \"⌢\", \"fscr\": \"𝒻\", \"Fscr\": \"ℱ\", \"gacute\": \"ǵ\", \"gamma\": \"γ\", \"Gamma\": \"Γ\", \"gammad\": \"ϝ\", \"Gammad\": \"Ϝ\", \"gap\": \"⪆\", \"gbreve\": \"ğ\", \"Gbreve\": \"Ğ\", \"Gcedil\": \"Ģ\", \"gcirc\": \"ĝ\", \"Gcirc\": \"Ĝ\", \"gcy\": \"г\", \"Gcy\": \"Г\", \"gdot\": \"ġ\", \"Gdot\": \"Ġ\", \"ge\": \"≥\", \"gE\": \"≧\", \"gel\": \"⋛\", \"gEl\": \"⪌\", \"geq\": \"≥\", \"geqq\": \"≧\", \"geqslant\": \"⩾\", \"ges\": \"⩾\", \"gescc\": \"⪩\", \"gesdot\": \"⪀\", \"gesdoto\": \"⪂\", \"gesdotol\": \"⪄\", \"gesl\": \"⋛︀\", \"gesles\": \"⪔\", \"gfr\": \"𝔤\", \"Gfr\": \"𝔊\", \"gg\": \"≫\", \"Gg\": \"⋙\", \"ggg\": \"⋙\", \"gimel\": \"ℷ\", \"gjcy\": \"ѓ\", \"GJcy\": \"Ѓ\", \"gl\": \"≷\", \"gla\": \"⪥\", \"glE\": \"⪒\", \"glj\": \"⪤\", \"gnap\": \"⪊\", \"gnapprox\": \"⪊\", \"gne\": \"⪈\", \"gnE\": \"≩\", \"gneq\": \"⪈\", \"gneqq\": \"≩\", \"gnsim\": \"⋧\", \"gopf\": \"𝕘\", \"Gopf\": \"𝔾\", \"grave\": \"`\", \"GreaterEqual\": \"≥\", \"GreaterEqualLess\": \"⋛\", \"GreaterFullEqual\": \"≧\", \"GreaterGreater\": \"⪢\", \"GreaterLess\": \"≷\", \"GreaterSlantEqual\": \"⩾\", \"GreaterTilde\": \"≳\", \"gscr\": \"ℊ\", \"Gscr\": \"𝒢\", \"gsim\": \"≳\", \"gsime\": \"⪎\", \"gsiml\": \"⪐\", \"gt\": \">\", \"Gt\": \"≫\", \"GT\": \">\", \"gtcc\": \"⪧\", \"gtcir\": \"⩺\", \"gtdot\": \"⋗\", \"gtlPar\": \"⦕\", \"gtquest\": \"⩼\", \"gtrapprox\": \"⪆\", \"gtrarr\": \"⥸\", \"gtrdot\": \"⋗\", \"gtreqless\": \"⋛\", \"gtreqqless\": \"⪌\", \"gtrless\": \"≷\", \"gtrsim\": \"≳\", \"gvertneqq\": \"≩︀\", \"gvnE\": \"≩︀\", \"Hacek\": \"ˇ\", \"hairsp\": \" \", \"half\": \"½\", \"hamilt\": \"ℋ\", \"hardcy\": \"ъ\", \"HARDcy\": \"Ъ\", \"harr\": \"↔\", \"hArr\": \"⇔\", \"harrcir\": \"⥈\", \"harrw\": \"↭\", \"Hat\": \"^\", \"hbar\": \"ℏ\", \"hcirc\": \"ĥ\", \"Hcirc\": \"Ĥ\", \"hearts\": \"♥\", \"heartsuit\": \"♥\", \"hellip\": \"…\", \"hercon\": \"⊹\", \"hfr\": \"𝔥\", \"Hfr\": \"ℌ\", \"HilbertSpace\": \"ℋ\", \"hksearow\": \"⤥\", \"hkswarow\": \"⤦\", \"hoarr\": \"⇿\", \"homtht\": \"∻\", \"hookleftarrow\": \"↩\", \"hookrightarrow\": \"↪\", \"hopf\": \"𝕙\", \"Hopf\": \"ℍ\", \"horbar\": \"―\", \"HorizontalLine\": \"─\", \"hscr\": \"𝒽\", \"Hscr\": \"ℋ\", \"hslash\": \"ℏ\", \"hstrok\": \"ħ\", \"Hstrok\": \"Ħ\", \"HumpDownHump\": \"≎\", \"HumpEqual\": \"≏\", \"hybull\": \"⁃\", \"hyphen\": \"‐\", \"iacute\": \"í\", \"Iacute\": \"Í\", \"ic\": \"⁣\", \"icirc\": \"î\", \"Icirc\": \"Î\", \"icy\": \"и\", \"Icy\": \"И\", \"Idot\": \"İ\", \"iecy\": \"е\", \"IEcy\": \"Е\", \"iexcl\": \"¡\", \"iff\": \"⇔\", \"ifr\": \"𝔦\", \"Ifr\": \"ℑ\", \"igrave\": \"ì\", \"Igrave\": \"Ì\", \"ii\": \"ⅈ\", \"iiiint\": \"⨌\", \"iiint\": \"∭\", \"iinfin\": \"⧜\", \"iiota\": \"℩\", \"ijlig\": \"ij\", \"IJlig\": \"IJ\", \"Im\": \"ℑ\", \"imacr\": \"ī\", \"Imacr\": \"Ī\", \"image\": \"ℑ\", \"ImaginaryI\": \"ⅈ\", \"imagline\": \"ℐ\", \"imagpart\": \"ℑ\", \"imath\": \"ı\", \"imof\": \"⊷\", \"imped\": \"Ƶ\", \"Implies\": \"⇒\", \"in\": \"∈\", \"incare\": \"℅\", \"infin\": \"∞\", \"infintie\": \"⧝\", \"inodot\": \"ı\", \"int\": \"∫\", \"Int\": \"∬\", \"intcal\": \"⊺\", \"integers\": \"ℤ\", \"Integral\": \"∫\", \"intercal\": \"⊺\", \"Intersection\": \"⋂\", \"intlarhk\": \"⨗\", \"intprod\": \"⨼\", \"InvisibleComma\": \"⁣\", \"InvisibleTimes\": \"⁢\", \"iocy\": \"ё\", \"IOcy\": \"Ё\", \"iogon\": \"į\", \"Iogon\": \"Į\", \"iopf\": \"𝕚\", \"Iopf\": \"𝕀\", \"iota\": \"ι\", \"Iota\": \"Ι\", \"iprod\": \"⨼\", \"iquest\": \"¿\", \"iscr\": \"𝒾\", \"Iscr\": \"ℐ\", \"isin\": \"∈\", \"isindot\": \"⋵\", \"isinE\": \"⋹\", \"isins\": \"⋴\", \"isinsv\": \"⋳\", \"isinv\": \"∈\", \"it\": \"⁢\", \"itilde\": \"ĩ\", \"Itilde\": \"Ĩ\", \"iukcy\": \"і\", \"Iukcy\": \"І\", \"iuml\": \"ï\", \"Iuml\": \"Ï\", \"jcirc\": \"ĵ\", \"Jcirc\": \"Ĵ\", \"jcy\": \"й\", \"Jcy\": \"Й\", \"jfr\": \"𝔧\", \"Jfr\": \"𝔍\", \"jmath\": \"ȷ\", \"jopf\": \"𝕛\", \"Jopf\": \"𝕁\", \"jscr\": \"𝒿\", \"Jscr\": \"𝒥\", \"jsercy\": \"ј\", \"Jsercy\": \"Ј\", \"jukcy\": \"є\", \"Jukcy\": \"Є\", \"kappa\": \"κ\", \"Kappa\": \"Κ\", \"kappav\": \"ϰ\", \"kcedil\": \"ķ\", \"Kcedil\": \"Ķ\", \"kcy\": \"к\", \"Kcy\": \"К\", \"kfr\": \"𝔨\", \"Kfr\": \"𝔎\", \"kgreen\": \"ĸ\", \"khcy\": \"х\", \"KHcy\": \"Х\", \"kjcy\": \"ќ\", \"KJcy\": \"Ќ\", \"kopf\": \"𝕜\", \"Kopf\": \"𝕂\", \"kscr\": \"𝓀\", \"Kscr\": \"𝒦\", \"lAarr\": \"⇚\", \"lacute\": \"ĺ\", \"Lacute\": \"Ĺ\", \"laemptyv\": \"⦴\", \"lagran\": \"ℒ\", \"lambda\": \"λ\", \"Lambda\": \"Λ\", \"lang\": \"⟨\", \"Lang\": \"⟪\", \"langd\": \"⦑\", \"langle\": \"⟨\", \"lap\": \"⪅\", \"Laplacetrf\": \"ℒ\", \"laquo\": \"«\", \"larr\": \"←\", \"lArr\": \"⇐\", \"Larr\": \"↞\", \"larrb\": \"⇤\", \"larrbfs\": \"⤟\", \"larrfs\": \"⤝\", \"larrhk\": \"↩\", \"larrlp\": \"↫\", \"larrpl\": \"⤹\", \"larrsim\": \"⥳\", \"larrtl\": \"↢\", \"lat\": \"⪫\", \"latail\": \"⤙\", \"lAtail\": \"⤛\", \"late\": \"⪭\", \"lates\": \"⪭︀\", \"lbarr\": \"⤌\", \"lBarr\": \"⤎\", \"lbbrk\": \"❲\", \"lbrace\": \"{\", \"lbrack\": \"[\", \"lbrke\": \"⦋\", \"lbrksld\": \"⦏\", \"lbrkslu\": \"⦍\", \"lcaron\": \"ľ\", \"Lcaron\": \"Ľ\", \"lcedil\": \"ļ\", \"Lcedil\": \"Ļ\", \"lceil\": \"⌈\", \"lcub\": \"{\", \"lcy\": \"л\", \"Lcy\": \"Л\", \"ldca\": \"⤶\", \"ldquo\": \"“\", \"ldquor\": \"„\", \"ldrdhar\": \"⥧\", \"ldrushar\": \"⥋\", \"ldsh\": \"↲\", \"le\": \"≤\", \"lE\": \"≦\", \"LeftAngleBracket\": \"⟨\", \"leftarrow\": \"←\", \"Leftarrow\": \"⇐\", \"LeftArrow\": \"←\", \"LeftArrowBar\": \"⇤\", \"LeftArrowRightArrow\": \"⇆\", \"leftarrowtail\": \"↢\", \"LeftCeiling\": \"⌈\", \"LeftDoubleBracket\": \"⟦\", \"LeftDownTeeVector\": \"⥡\", \"LeftDownVector\": \"⇃\", \"LeftDownVectorBar\": \"⥙\", \"LeftFloor\": \"⌊\", \"leftharpoondown\": \"↽\", \"leftharpoonup\": \"↼\", \"leftleftarrows\": \"⇇\", \"leftrightarrow\": \"↔\", \"Leftrightarrow\": \"⇔\", \"LeftRightArrow\": \"↔\", \"leftrightarrows\": \"⇆\", \"leftrightharpoons\": \"⇋\", \"leftrightsquigarrow\": \"↭\", \"LeftRightVector\": \"⥎\", \"LeftTee\": \"⊣\", \"LeftTeeArrow\": \"↤\", \"LeftTeeVector\": \"⥚\", \"leftthreetimes\": \"⋋\", \"LeftTriangle\": \"⊲\", \"LeftTriangleBar\": \"⧏\", \"LeftTriangleEqual\": \"⊴\", \"LeftUpDownVector\": \"⥑\", \"LeftUpTeeVector\": \"⥠\", \"LeftUpVector\": \"↿\", \"LeftUpVectorBar\": \"⥘\", \"LeftVector\": \"↼\", \"LeftVectorBar\": \"⥒\", \"leg\": \"⋚\", \"lEg\": \"⪋\", \"leq\": \"≤\", \"leqq\": \"≦\", \"leqslant\": \"⩽\", \"les\": \"⩽\", \"lescc\": \"⪨\", \"lesdot\": \"⩿\", \"lesdoto\": \"⪁\", \"lesdotor\": \"⪃\", \"lesg\": \"⋚︀\", \"lesges\": \"⪓\", \"lessapprox\": \"⪅\", \"lessdot\": \"⋖\", \"lesseqgtr\": \"⋚\", \"lesseqqgtr\": \"⪋\", \"LessEqualGreater\": \"⋚\", \"LessFullEqual\": \"≦\", \"LessGreater\": \"≶\", \"lessgtr\": \"≶\", \"LessLess\": \"⪡\", \"lesssim\": \"≲\", \"LessSlantEqual\": \"⩽\", \"LessTilde\": \"≲\", \"lfisht\": \"⥼\", \"lfloor\": \"⌊\", \"lfr\": \"𝔩\", \"Lfr\": \"𝔏\", \"lg\": \"≶\", \"lgE\": \"⪑\", \"lHar\": \"⥢\", \"lhard\": \"↽\", \"lharu\": \"↼\", \"lharul\": \"⥪\", \"lhblk\": \"▄\", \"ljcy\": \"љ\", \"LJcy\": \"Љ\", \"ll\": \"≪\", \"Ll\": \"⋘\", \"llarr\": \"⇇\", \"llcorner\": \"⌞\", \"Lleftarrow\": \"⇚\", \"llhard\": \"⥫\", \"lltri\": \"◺\", \"lmidot\": \"ŀ\", \"Lmidot\": \"Ŀ\", \"lmoust\": \"⎰\", \"lmoustache\": \"⎰\", \"lnap\": \"⪉\", \"lnapprox\": \"⪉\", \"lne\": \"⪇\", \"lnE\": \"≨\", \"lneq\": \"⪇\", \"lneqq\": \"≨\", \"lnsim\": \"⋦\", \"loang\": \"⟬\", \"loarr\": \"⇽\", \"lobrk\": \"⟦\", \"longleftarrow\": \"⟵\", \"Longleftarrow\": \"⟸\", \"LongLeftArrow\": \"⟵\", \"longleftrightarrow\": \"⟷\", \"Longleftrightarrow\": \"⟺\", \"LongLeftRightArrow\": \"⟷\", \"longmapsto\": \"⟼\", \"longrightarrow\": \"⟶\", \"Longrightarrow\": \"⟹\", \"LongRightArrow\": \"⟶\", \"looparrowleft\": \"↫\", \"looparrowright\": \"↬\", \"lopar\": \"⦅\", \"lopf\": \"𝕝\", \"Lopf\": \"𝕃\", \"loplus\": \"⨭\", \"lotimes\": \"⨴\", \"lowast\": \"∗\", \"lowbar\": \"_\", \"LowerLeftArrow\": \"↙\", \"LowerRightArrow\": \"↘\", \"loz\": \"◊\", \"lozenge\": \"◊\", \"lozf\": \"⧫\", \"lpar\": \"(\", \"lparlt\": \"⦓\", \"lrarr\": \"⇆\", \"lrcorner\": \"⌟\", \"lrhar\": \"⇋\", \"lrhard\": \"⥭\", \"lrm\": \"‎\", \"lrtri\": \"⊿\", \"lsaquo\": \"‹\", \"lscr\": \"𝓁\", \"Lscr\": \"ℒ\", \"lsh\": \"↰\", \"Lsh\": \"↰\", \"lsim\": \"≲\", \"lsime\": \"⪍\", \"lsimg\": \"⪏\", \"lsqb\": \"[\", \"lsquo\": \"‘\", \"lsquor\": \"‚\", \"lstrok\": \"ł\", \"Lstrok\": \"Ł\", \"lt\": \"<\", \"Lt\": \"≪\", \"LT\": \"<\", \"ltcc\": \"⪦\", \"ltcir\": \"⩹\", \"ltdot\": \"⋖\", \"lthree\": \"⋋\", \"ltimes\": \"⋉\", \"ltlarr\": \"⥶\", \"ltquest\": \"⩻\", \"ltri\": \"◃\", \"ltrie\": \"⊴\", \"ltrif\": \"◂\", \"ltrPar\": \"⦖\", \"lurdshar\": \"⥊\", \"luruhar\": \"⥦\", \"lvertneqq\": \"≨︀\", \"lvnE\": \"≨︀\", \"macr\": \"¯\", \"male\": \"♂\", \"malt\": \"✠\", \"maltese\": \"✠\", \"map\": \"↦\", \"Map\": \"⤅\", \"mapsto\": \"↦\", \"mapstodown\": \"↧\", \"mapstoleft\": \"↤\", \"mapstoup\": \"↥\", \"marker\": \"▮\", \"mcomma\": \"⨩\", \"mcy\": \"м\", \"Mcy\": \"М\", \"mdash\": \"—\", \"mDDot\": \"∺\", \"measuredangle\": \"∡\", \"MediumSpace\": \" \", \"Mellintrf\": \"ℳ\", \"mfr\": \"𝔪\", \"Mfr\": \"𝔐\", \"mho\": \"℧\", \"micro\": \"µ\", \"mid\": \"∣\", \"midast\": \"*\", \"midcir\": \"⫰\", \"middot\": \"·\", \"minus\": \"−\", \"minusb\": \"⊟\", \"minusd\": \"∸\", \"minusdu\": \"⨪\", \"MinusPlus\": \"∓\", \"mlcp\": \"⫛\", \"mldr\": \"…\", \"mnplus\": \"∓\", \"models\": \"⊧\", \"mopf\": \"𝕞\", \"Mopf\": \"𝕄\", \"mp\": \"∓\", \"mscr\": \"𝓂\", \"Mscr\": \"ℳ\", \"mstpos\": \"∾\", \"mu\": \"μ\", \"Mu\": \"Μ\", \"multimap\": \"⊸\", \"mumap\": \"⊸\", \"nabla\": \"∇\", \"nacute\": \"ń\", \"Nacute\": \"Ń\", \"nang\": \"∠⃒\", \"nap\": \"≉\", \"napE\": \"⩰̸\", \"napid\": \"≋̸\", \"napos\": \"ʼn\", \"napprox\": \"≉\", \"natur\": \"♮\", \"natural\": \"♮\", \"naturals\": \"ℕ\", \"nbsp\": \" \", \"nbump\": \"≎̸\", \"nbumpe\": \"≏̸\", \"ncap\": \"⩃\", \"ncaron\": \"ň\", \"Ncaron\": \"Ň\", \"ncedil\": \"ņ\", \"Ncedil\": \"Ņ\", \"ncong\": \"≇\", \"ncongdot\": \"⩭̸\", \"ncup\": \"⩂\", \"ncy\": \"н\", \"Ncy\": \"Н\", \"ndash\": \"–\", \"ne\": \"≠\", \"nearhk\": \"⤤\", \"nearr\": \"↗\", \"neArr\": \"⇗\", \"nearrow\": \"↗\", \"nedot\": \"≐̸\", \"NegativeMediumSpace\": \"​\", \"NegativeThickSpace\": \"​\", \"NegativeThinSpace\": \"​\", \"NegativeVeryThinSpace\": \"​\", \"nequiv\": \"≢\", \"nesear\": \"⤨\", \"nesim\": \"≂̸\", \"NestedGreaterGreater\": \"≫\", \"NestedLessLess\": \"≪\", \"NewLine\": \"\\n\", \"nexist\": \"∄\", \"nexists\": \"∄\", \"nfr\": \"𝔫\", \"Nfr\": \"𝔑\", \"nge\": \"≱\", \"ngE\": \"≧̸\", \"ngeq\": \"≱\", \"ngeqq\": \"≧̸\", \"ngeqslant\": \"⩾̸\", \"nges\": \"⩾̸\", \"nGg\": \"⋙̸\", \"ngsim\": \"≵\", \"ngt\": \"≯\", \"nGt\": \"≫⃒\", \"ngtr\": \"≯\", \"nGtv\": \"≫̸\", \"nharr\": \"↮\", \"nhArr\": \"⇎\", \"nhpar\": \"⫲\", \"ni\": \"∋\", \"nis\": \"⋼\", \"nisd\": \"⋺\", \"niv\": \"∋\", \"njcy\": \"њ\", \"NJcy\": \"Њ\", \"nlarr\": \"↚\", \"nlArr\": \"⇍\", \"nldr\": \"‥\", \"nle\": \"≰\", \"nlE\": \"≦̸\", \"nleftarrow\": \"↚\", \"nLeftarrow\": \"⇍\", \"nleftrightarrow\": \"↮\", \"nLeftrightarrow\": \"⇎\", \"nleq\": \"≰\", \"nleqq\": \"≦̸\", \"nleqslant\": \"⩽̸\", \"nles\": \"⩽̸\", \"nless\": \"≮\", \"nLl\": \"⋘̸\", \"nlsim\": \"≴\", \"nlt\": \"≮\", \"nLt\": \"≪⃒\", \"nltri\": \"⋪\", \"nltrie\": \"⋬\", \"nLtv\": \"≪̸\", \"nmid\": \"∤\", \"NoBreak\": \"⁠\", \"NonBreakingSpace\": \" \", \"nopf\": \"𝕟\", \"Nopf\": \"ℕ\", \"not\": \"¬\", \"Not\": \"⫬\", \"NotCongruent\": \"≢\", \"NotCupCap\": \"≭\", \"NotDoubleVerticalBar\": \"∦\", \"NotElement\": \"∉\", \"NotEqual\": \"≠\", \"NotEqualTilde\": \"≂̸\", \"NotExists\": \"∄\", \"NotGreater\": \"≯\", \"NotGreaterEqual\": \"≱\", \"NotGreaterFullEqual\": \"≧̸\", \"NotGreaterGreater\": \"≫̸\", \"NotGreaterLess\": \"≹\", \"NotGreaterSlantEqual\": \"⩾̸\", \"NotGreaterTilde\": \"≵\", \"NotHumpDownHump\": \"≎̸\", \"NotHumpEqual\": \"≏̸\", \"notin\": \"∉\", \"notindot\": \"⋵̸\", \"notinE\": \"⋹̸\", \"notinva\": \"∉\", \"notinvb\": \"⋷\", \"notinvc\": \"⋶\", \"NotLeftTriangle\": \"⋪\", \"NotLeftTriangleBar\": \"⧏̸\", \"NotLeftTriangleEqual\": \"⋬\", \"NotLess\": \"≮\", \"NotLessEqual\": \"≰\", \"NotLessGreater\": \"≸\", \"NotLessLess\": \"≪̸\", \"NotLessSlantEqual\": \"⩽̸\", \"NotLessTilde\": \"≴\", \"NotNestedGreaterGreater\": \"⪢̸\", \"NotNestedLessLess\": \"⪡̸\", \"notni\": \"∌\", \"notniva\": \"∌\", \"notnivb\": \"⋾\", \"notnivc\": \"⋽\", \"NotPrecedes\": \"⊀\", \"NotPrecedesEqual\": \"⪯̸\", \"NotPrecedesSlantEqual\": \"⋠\", \"NotReverseElement\": \"∌\", \"NotRightTriangle\": \"⋫\", \"NotRightTriangleBar\": \"⧐̸\", \"NotRightTriangleEqual\": \"⋭\", \"NotSquareSubset\": \"⊏̸\", \"NotSquareSubsetEqual\": \"⋢\", \"NotSquareSuperset\": \"⊐̸\", \"NotSquareSupersetEqual\": \"⋣\", \"NotSubset\": \"⊂⃒\", \"NotSubsetEqual\": \"⊈\", \"NotSucceeds\": \"⊁\", \"NotSucceedsEqual\": \"⪰̸\", \"NotSucceedsSlantEqual\": \"⋡\", \"NotSucceedsTilde\": \"≿̸\", \"NotSuperset\": \"⊃⃒\", \"NotSupersetEqual\": \"⊉\", \"NotTilde\": \"≁\", \"NotTildeEqual\": \"≄\", \"NotTildeFullEqual\": \"≇\", \"NotTildeTilde\": \"≉\", \"NotVerticalBar\": \"∤\", \"npar\": \"∦\", \"nparallel\": \"∦\", \"nparsl\": \"⫽⃥\", \"npart\": \"∂̸\", \"npolint\": \"⨔\", \"npr\": \"⊀\", \"nprcue\": \"⋠\", \"npre\": \"⪯̸\", \"nprec\": \"⊀\", \"npreceq\": \"⪯̸\", \"nrarr\": \"↛\", \"nrArr\": \"⇏\", \"nrarrc\": \"⤳̸\", \"nrarrw\": \"↝̸\", \"nrightarrow\": \"↛\", \"nRightarrow\": \"⇏\", \"nrtri\": \"⋫\", \"nrtrie\": \"⋭\", \"nsc\": \"⊁\", \"nsccue\": \"⋡\", \"nsce\": \"⪰̸\", \"nscr\": \"𝓃\", \"Nscr\": \"𝒩\", \"nshortmid\": \"∤\", \"nshortparallel\": \"∦\", \"nsim\": \"≁\", \"nsime\": \"≄\", \"nsimeq\": \"≄\", \"nsmid\": \"∤\", \"nspar\": \"∦\", \"nsqsube\": \"⋢\", \"nsqsupe\": \"⋣\", \"nsub\": \"⊄\", \"nsube\": \"⊈\", \"nsubE\": \"⫅̸\", \"nsubset\": \"⊂⃒\", \"nsubseteq\": \"⊈\", \"nsubseteqq\": \"⫅̸\", \"nsucc\": \"⊁\", \"nsucceq\": \"⪰̸\", \"nsup\": \"⊅\", \"nsupe\": \"⊉\", \"nsupE\": \"⫆̸\", \"nsupset\": \"⊃⃒\", \"nsupseteq\": \"⊉\", \"nsupseteqq\": \"⫆̸\", \"ntgl\": \"≹\", \"ntilde\": \"ñ\", \"Ntilde\": \"Ñ\", \"ntlg\": \"≸\", \"ntriangleleft\": \"⋪\", \"ntrianglelefteq\": \"⋬\", \"ntriangleright\": \"⋫\", \"ntrianglerighteq\": \"⋭\", \"nu\": \"ν\", \"Nu\": \"Ν\", \"num\": \"#\", \"numero\": \"№\", \"numsp\": \" \", \"nvap\": \"≍⃒\", \"nvdash\": \"⊬\", \"nvDash\": \"⊭\", \"nVdash\": \"⊮\", \"nVDash\": \"⊯\", \"nvge\": \"≥⃒\", \"nvgt\": \">⃒\", \"nvHarr\": \"⤄\", \"nvinfin\": \"⧞\", \"nvlArr\": \"⤂\", \"nvle\": \"≤⃒\", \"nvlt\": \"<⃒\", \"nvltrie\": \"⊴⃒\", \"nvrArr\": \"⤃\", \"nvrtrie\": \"⊵⃒\", \"nvsim\": \"∼⃒\", \"nwarhk\": \"⤣\", \"nwarr\": \"↖\", \"nwArr\": \"⇖\", \"nwarrow\": \"↖\", \"nwnear\": \"⤧\", \"oacute\": \"ó\", \"Oacute\": \"Ó\", \"oast\": \"⊛\", \"ocir\": \"⊚\", \"ocirc\": \"ô\", \"Ocirc\": \"Ô\", \"ocy\": \"о\", \"Ocy\": \"О\", \"odash\": \"⊝\", \"odblac\": \"ő\", \"Odblac\": \"Ő\", \"odiv\": \"⨸\", \"odot\": \"⊙\", \"odsold\": \"⦼\", \"oelig\": \"œ\", \"OElig\": \"Œ\", \"ofcir\": \"⦿\", \"ofr\": \"𝔬\", \"Ofr\": \"𝔒\", \"ogon\": \"˛\", \"ograve\": \"ò\", \"Ograve\": \"Ò\", \"ogt\": \"⧁\", \"ohbar\": \"⦵\", \"ohm\": \"Ω\", \"oint\": \"∮\", \"olarr\": \"↺\", \"olcir\": \"⦾\", \"olcross\": \"⦻\", \"oline\": \"‾\", \"olt\": \"⧀\", \"omacr\": \"ō\", \"Omacr\": \"Ō\", \"omega\": \"ω\", \"Omega\": \"Ω\", \"omicron\": \"ο\", \"Omicron\": \"Ο\", \"omid\": \"⦶\", \"ominus\": \"⊖\", \"oopf\": \"𝕠\", \"Oopf\": \"𝕆\", \"opar\": \"⦷\", \"OpenCurlyDoubleQuote\": \"“\", \"OpenCurlyQuote\": \"‘\", \"operp\": \"⦹\", \"oplus\": \"⊕\", \"or\": \"∨\", \"Or\": \"⩔\", \"orarr\": \"↻\", \"ord\": \"⩝\", \"order\": \"ℴ\", \"orderof\": \"ℴ\", \"ordf\": \"ª\", \"ordm\": \"º\", \"origof\": \"⊶\", \"oror\": \"⩖\", \"orslope\": \"⩗\", \"orv\": \"⩛\", \"oS\": \"Ⓢ\", \"oscr\": \"ℴ\", \"Oscr\": \"𝒪\", \"oslash\": \"ø\", \"Oslash\": \"Ø\", \"osol\": \"⊘\", \"otilde\": \"õ\", \"Otilde\": \"Õ\", \"otimes\": \"⊗\", \"Otimes\": \"⨷\", \"otimesas\": \"⨶\", \"ouml\": \"ö\", \"Ouml\": \"Ö\", \"ovbar\": \"⌽\", \"OverBar\": \"‾\", \"OverBrace\": \"⏞\", \"OverBracket\": \"⎴\", \"OverParenthesis\": \"⏜\", \"par\": \"∥\", \"para\": \"¶\", \"parallel\": \"∥\", \"parsim\": \"⫳\", \"parsl\": \"⫽\", \"part\": \"∂\", \"PartialD\": \"∂\", \"pcy\": \"п\", \"Pcy\": \"П\", \"percnt\": \"%\", \"period\": \".\", \"permil\": \"‰\", \"perp\": \"⊥\", \"pertenk\": \"‱\", \"pfr\": \"𝔭\", \"Pfr\": \"𝔓\", \"phi\": \"φ\", \"Phi\": \"Φ\", \"phiv\": \"ϕ\", \"phmmat\": \"ℳ\", \"phone\": \"☎\", \"pi\": \"π\", \"Pi\": \"Π\", \"pitchfork\": \"⋔\", \"piv\": \"ϖ\", \"planck\": \"ℏ\", \"planckh\": \"ℎ\", \"plankv\": \"ℏ\", \"plus\": \"+\", \"plusacir\": \"⨣\", \"plusb\": \"⊞\", \"pluscir\": \"⨢\", \"plusdo\": \"∔\", \"plusdu\": \"⨥\", \"pluse\": \"⩲\", \"PlusMinus\": \"±\", \"plusmn\": \"±\", \"plussim\": \"⨦\", \"plustwo\": \"⨧\", \"pm\": \"±\", \"Poincareplane\": \"ℌ\", \"pointint\": \"⨕\", \"popf\": \"𝕡\", \"Popf\": \"ℙ\", \"pound\": \"£\", \"pr\": \"≺\", \"Pr\": \"⪻\", \"prap\": \"⪷\", \"prcue\": \"≼\", \"pre\": \"⪯\", \"prE\": \"⪳\", \"prec\": \"≺\", \"precapprox\": \"⪷\", \"preccurlyeq\": \"≼\", \"Precedes\": \"≺\", \"PrecedesEqual\": \"⪯\", \"PrecedesSlantEqual\": \"≼\", \"PrecedesTilde\": \"≾\", \"preceq\": \"⪯\", \"precnapprox\": \"⪹\", \"precneqq\": \"⪵\", \"precnsim\": \"⋨\", \"precsim\": \"≾\", \"prime\": \"′\", \"Prime\": \"″\", \"primes\": \"ℙ\", \"prnap\": \"⪹\", \"prnE\": \"⪵\", \"prnsim\": \"⋨\", \"prod\": \"∏\", \"Product\": \"∏\", \"profalar\": \"⌮\", \"profline\": \"⌒\", \"profsurf\": \"⌓\", \"prop\": \"∝\", \"Proportion\": \"∷\", \"Proportional\": \"∝\", \"propto\": \"∝\", \"prsim\": \"≾\", \"prurel\": \"⊰\", \"pscr\": \"𝓅\", \"Pscr\": \"𝒫\", \"psi\": \"ψ\", \"Psi\": \"Ψ\", \"puncsp\": \" \", \"qfr\": \"𝔮\", \"Qfr\": \"𝔔\", \"qint\": \"⨌\", \"qopf\": \"𝕢\", \"Qopf\": \"ℚ\", \"qprime\": \"⁗\", \"qscr\": \"𝓆\", \"Qscr\": \"𝒬\", \"quaternions\": \"ℍ\", \"quatint\": \"⨖\", \"quest\": \"?\", \"questeq\": \"≟\", \"quot\": '\"', \"QUOT\": '\"', \"rAarr\": \"⇛\", \"race\": \"∽̱\", \"racute\": \"ŕ\", \"Racute\": \"Ŕ\", \"radic\": \"√\", \"raemptyv\": \"⦳\", \"rang\": \"⟩\", \"Rang\": \"⟫\", \"rangd\": \"⦒\", \"range\": \"⦥\", \"rangle\": \"⟩\", \"raquo\": \"»\", \"rarr\": \"→\", \"rArr\": \"⇒\", \"Rarr\": \"↠\", \"rarrap\": \"⥵\", \"rarrb\": \"⇥\", \"rarrbfs\": \"⤠\", \"rarrc\": \"⤳\", \"rarrfs\": \"⤞\", \"rarrhk\": \"↪\", \"rarrlp\": \"↬\", \"rarrpl\": \"⥅\", \"rarrsim\": \"⥴\", \"rarrtl\": \"↣\", \"Rarrtl\": \"⤖\", \"rarrw\": \"↝\", \"ratail\": \"⤚\", \"rAtail\": \"⤜\", \"ratio\": \"∶\", \"rationals\": \"ℚ\", \"rbarr\": \"⤍\", \"rBarr\": \"⤏\", \"RBarr\": \"⤐\", \"rbbrk\": \"❳\", \"rbrace\": \"}\", \"rbrack\": \"]\", \"rbrke\": \"⦌\", \"rbrksld\": \"⦎\", \"rbrkslu\": \"⦐\", \"rcaron\": \"ř\", \"Rcaron\": \"Ř\", \"rcedil\": \"ŗ\", \"Rcedil\": \"Ŗ\", \"rceil\": \"⌉\", \"rcub\": \"}\", \"rcy\": \"р\", \"Rcy\": \"Р\", \"rdca\": \"⤷\", \"rdldhar\": \"⥩\", \"rdquo\": \"”\", \"rdquor\": \"”\", \"rdsh\": \"↳\", \"Re\": \"ℜ\", \"real\": \"ℜ\", \"realine\": \"ℛ\", \"realpart\": \"ℜ\", \"reals\": \"ℝ\", \"rect\": \"▭\", \"reg\": \"®\", \"REG\": \"®\", \"ReverseElement\": \"∋\", \"ReverseEquilibrium\": \"⇋\", \"ReverseUpEquilibrium\": \"⥯\", \"rfisht\": \"⥽\", \"rfloor\": \"⌋\", \"rfr\": \"𝔯\", \"Rfr\": \"ℜ\", \"rHar\": \"⥤\", \"rhard\": \"⇁\", \"rharu\": \"⇀\", \"rharul\": \"⥬\", \"rho\": \"ρ\", \"Rho\": \"Ρ\", \"rhov\": \"ϱ\", \"RightAngleBracket\": \"⟩\", \"rightarrow\": \"→\", \"Rightarrow\": \"⇒\", \"RightArrow\": \"→\", \"RightArrowBar\": \"⇥\", \"RightArrowLeftArrow\": \"⇄\", \"rightarrowtail\": \"↣\", \"RightCeiling\": \"⌉\", \"RightDoubleBracket\": \"⟧\", \"RightDownTeeVector\": \"⥝\", \"RightDownVector\": \"⇂\", \"RightDownVectorBar\": \"⥕\", \"RightFloor\": \"⌋\", \"rightharpoondown\": \"⇁\", \"rightharpoonup\": \"⇀\", \"rightleftarrows\": \"⇄\", \"rightleftharpoons\": \"⇌\", \"rightrightarrows\": \"⇉\", \"rightsquigarrow\": \"↝\", \"RightTee\": \"⊢\", \"RightTeeArrow\": \"↦\", \"RightTeeVector\": \"⥛\", \"rightthreetimes\": \"⋌\", \"RightTriangle\": \"⊳\", \"RightTriangleBar\": \"⧐\", \"RightTriangleEqual\": \"⊵\", \"RightUpDownVector\": \"⥏\", \"RightUpTeeVector\": \"⥜\", \"RightUpVector\": \"↾\", \"RightUpVectorBar\": \"⥔\", \"RightVector\": \"⇀\", \"RightVectorBar\": \"⥓\", \"ring\": \"˚\", \"risingdotseq\": \"≓\", \"rlarr\": \"⇄\", \"rlhar\": \"⇌\", \"rlm\": \"‏\", \"rmoust\": \"⎱\", \"rmoustache\": \"⎱\", \"rnmid\": \"⫮\", \"roang\": \"⟭\", \"roarr\": \"⇾\", \"robrk\": \"⟧\", \"ropar\": \"⦆\", \"ropf\": \"𝕣\", \"Ropf\": \"ℝ\", \"roplus\": \"⨮\", \"rotimes\": \"⨵\", \"RoundImplies\": \"⥰\", \"rpar\": \")\", \"rpargt\": \"⦔\", \"rppolint\": \"⨒\", \"rrarr\": \"⇉\", \"Rrightarrow\": \"⇛\", \"rsaquo\": \"›\", \"rscr\": \"𝓇\", \"Rscr\": \"ℛ\", \"rsh\": \"↱\", \"Rsh\": \"↱\", \"rsqb\": \"]\", \"rsquo\": \"’\", \"rsquor\": \"’\", \"rthree\": \"⋌\", \"rtimes\": \"⋊\", \"rtri\": \"▹\", \"rtrie\": \"⊵\", \"rtrif\": \"▸\", \"rtriltri\": \"⧎\", \"RuleDelayed\": \"⧴\", \"ruluhar\": \"⥨\", \"rx\": \"℞\", \"sacute\": \"ś\", \"Sacute\": \"Ś\", \"sbquo\": \"‚\", \"sc\": \"≻\", \"Sc\": \"⪼\", \"scap\": \"⪸\", \"scaron\": \"š\", \"Scaron\": \"Š\", \"sccue\": \"≽\", \"sce\": \"⪰\", \"scE\": \"⪴\", \"scedil\": \"ş\", \"Scedil\": \"Ş\", \"scirc\": \"ŝ\", \"Scirc\": \"Ŝ\", \"scnap\": \"⪺\", \"scnE\": \"⪶\", \"scnsim\": \"⋩\", \"scpolint\": \"⨓\", \"scsim\": \"≿\", \"scy\": \"с\", \"Scy\": \"С\", \"sdot\": \"⋅\", \"sdotb\": \"⊡\", \"sdote\": \"⩦\", \"searhk\": \"⤥\", \"searr\": \"↘\", \"seArr\": \"⇘\", \"searrow\": \"↘\", \"sect\": \"§\", \"semi\": \";\", \"seswar\": \"⤩\", \"setminus\": \"∖\", \"setmn\": \"∖\", \"sext\": \"✶\", \"sfr\": \"𝔰\", \"Sfr\": \"𝔖\", \"sfrown\": \"⌢\", \"sharp\": \"♯\", \"shchcy\": \"щ\", \"SHCHcy\": \"Щ\", \"shcy\": \"ш\", \"SHcy\": \"Ш\", \"ShortDownArrow\": \"↓\", \"ShortLeftArrow\": \"←\", \"shortmid\": \"∣\", \"shortparallel\": \"∥\", \"ShortRightArrow\": \"→\", \"ShortUpArrow\": \"↑\", \"shy\": \"­\", \"sigma\": \"σ\", \"Sigma\": \"Σ\", \"sigmaf\": \"ς\", \"sigmav\": \"ς\", \"sim\": \"∼\", \"simdot\": \"⩪\", \"sime\": \"≃\", \"simeq\": \"≃\", \"simg\": \"⪞\", \"simgE\": \"⪠\", \"siml\": \"⪝\", \"simlE\": \"⪟\", \"simne\": \"≆\", \"simplus\": \"⨤\", \"simrarr\": \"⥲\", \"slarr\": \"←\", \"SmallCircle\": \"∘\", \"smallsetminus\": \"∖\", \"smashp\": \"⨳\", \"smeparsl\": \"⧤\", \"smid\": \"∣\", \"smile\": \"⌣\", \"smt\": \"⪪\", \"smte\": \"⪬\", \"smtes\": \"⪬︀\", \"softcy\": \"ь\", \"SOFTcy\": \"Ь\", \"sol\": \"/\", \"solb\": \"⧄\", \"solbar\": \"⌿\", \"sopf\": \"𝕤\", \"Sopf\": \"𝕊\", \"spades\": \"♠\", \"spadesuit\": \"♠\", \"spar\": \"∥\", \"sqcap\": \"⊓\", \"sqcaps\": \"⊓︀\", \"sqcup\": \"⊔\", \"sqcups\": \"⊔︀\", \"Sqrt\": \"√\", \"sqsub\": \"⊏\", \"sqsube\": \"⊑\", \"sqsubset\": \"⊏\", \"sqsubseteq\": \"⊑\", \"sqsup\": \"⊐\", \"sqsupe\": \"⊒\", \"sqsupset\": \"⊐\", \"sqsupseteq\": \"⊒\", \"squ\": \"□\", \"square\": \"□\", \"Square\": \"□\", \"SquareIntersection\": \"⊓\", \"SquareSubset\": \"⊏\", \"SquareSubsetEqual\": \"⊑\", \"SquareSuperset\": \"⊐\", \"SquareSupersetEqual\": \"⊒\", \"SquareUnion\": \"⊔\", \"squarf\": \"▪\", \"squf\": \"▪\", \"srarr\": \"→\", \"sscr\": \"𝓈\", \"Sscr\": \"𝒮\", \"ssetmn\": \"∖\", \"ssmile\": \"⌣\", \"sstarf\": \"⋆\", \"star\": \"☆\", \"Star\": \"⋆\", \"starf\": \"★\", \"straightepsilon\": \"ϵ\", \"straightphi\": \"ϕ\", \"strns\": \"¯\", \"sub\": \"⊂\", \"Sub\": \"⋐\", \"subdot\": \"⪽\", \"sube\": \"⊆\", \"subE\": \"⫅\", \"subedot\": \"⫃\", \"submult\": \"⫁\", \"subne\": \"⊊\", \"subnE\": \"⫋\", \"subplus\": \"⪿\", \"subrarr\": \"⥹\", \"subset\": \"⊂\", \"Subset\": \"⋐\", \"subseteq\": \"⊆\", \"subseteqq\": \"⫅\", \"SubsetEqual\": \"⊆\", \"subsetneq\": \"⊊\", \"subsetneqq\": \"⫋\", \"subsim\": \"⫇\", \"subsub\": \"⫕\", \"subsup\": \"⫓\", \"succ\": \"≻\", \"succapprox\": \"⪸\", \"succcurlyeq\": \"≽\", \"Succeeds\": \"≻\", \"SucceedsEqual\": \"⪰\", \"SucceedsSlantEqual\": \"≽\", \"SucceedsTilde\": \"≿\", \"succeq\": \"⪰\", \"succnapprox\": \"⪺\", \"succneqq\": \"⪶\", \"succnsim\": \"⋩\", \"succsim\": \"≿\", \"SuchThat\": \"∋\", \"sum\": \"∑\", \"Sum\": \"∑\", \"sung\": \"♪\", \"sup\": \"⊃\", \"Sup\": \"⋑\", \"sup1\": \"¹\", \"sup2\": \"²\", \"sup3\": \"³\", \"supdot\": \"⪾\", \"supdsub\": \"⫘\", \"supe\": \"⊇\", \"supE\": \"⫆\", \"supedot\": \"⫄\", \"Superset\": \"⊃\", \"SupersetEqual\": \"⊇\", \"suphsol\": \"⟉\", \"suphsub\": \"⫗\", \"suplarr\": \"⥻\", \"supmult\": \"⫂\", \"supne\": \"⊋\", \"supnE\": \"⫌\", \"supplus\": \"⫀\", \"supset\": \"⊃\", \"Supset\": \"⋑\", \"supseteq\": \"⊇\", \"supseteqq\": \"⫆\", \"supsetneq\": \"⊋\", \"supsetneqq\": \"⫌\", \"supsim\": \"⫈\", \"supsub\": \"⫔\", \"supsup\": \"⫖\", \"swarhk\": \"⤦\", \"swarr\": \"↙\", \"swArr\": \"⇙\", \"swarrow\": \"↙\", \"swnwar\": \"⤪\", \"szlig\": \"ß\", \"Tab\": \"\t\", \"target\": \"⌖\", \"tau\": \"τ\", \"Tau\": \"Τ\", \"tbrk\": \"⎴\", \"tcaron\": \"ť\", \"Tcaron\": \"Ť\", \"tcedil\": \"ţ\", \"Tcedil\": \"Ţ\", \"tcy\": \"т\", \"Tcy\": \"Т\", \"tdot\": \"⃛\", \"telrec\": \"⌕\", \"tfr\": \"𝔱\", \"Tfr\": \"𝔗\", \"there4\": \"∴\", \"therefore\": \"∴\", \"Therefore\": \"∴\", \"theta\": \"θ\", \"Theta\": \"Θ\", \"thetasym\": \"ϑ\", \"thetav\": \"ϑ\", \"thickapprox\": \"≈\", \"thicksim\": \"∼\", \"ThickSpace\": \"  \", \"thinsp\": \" \", \"ThinSpace\": \" \", \"thkap\": \"≈\", \"thksim\": \"∼\", \"thorn\": \"þ\", \"THORN\": \"Þ\", \"tilde\": \"˜\", \"Tilde\": \"∼\", \"TildeEqual\": \"≃\", \"TildeFullEqual\": \"≅\", \"TildeTilde\": \"≈\", \"times\": \"×\", \"timesb\": \"⊠\", \"timesbar\": \"⨱\", \"timesd\": \"⨰\", \"tint\": \"∭\", \"toea\": \"⤨\", \"top\": \"⊤\", \"topbot\": \"⌶\", \"topcir\": \"⫱\", \"topf\": \"𝕥\", \"Topf\": \"𝕋\", \"topfork\": \"⫚\", \"tosa\": \"⤩\", \"tprime\": \"‴\", \"trade\": \"™\", \"TRADE\": \"™\", \"triangle\": \"▵\", \"triangledown\": \"▿\", \"triangleleft\": \"◃\", \"trianglelefteq\": \"⊴\", \"triangleq\": \"≜\", \"triangleright\": \"▹\", \"trianglerighteq\": \"⊵\", \"tridot\": \"◬\", \"trie\": \"≜\", \"triminus\": \"⨺\", \"TripleDot\": \"⃛\", \"triplus\": \"⨹\", \"trisb\": \"⧍\", \"tritime\": \"⨻\", \"trpezium\": \"⏢\", \"tscr\": \"𝓉\", \"Tscr\": \"𝒯\", \"tscy\": \"ц\", \"TScy\": \"Ц\", \"tshcy\": \"ћ\", \"TSHcy\": \"Ћ\", \"tstrok\": \"ŧ\", \"Tstrok\": \"Ŧ\", \"twixt\": \"≬\", \"twoheadleftarrow\": \"↞\", \"twoheadrightarrow\": \"↠\", \"uacute\": \"ú\", \"Uacute\": \"Ú\", \"uarr\": \"↑\", \"uArr\": \"⇑\", \"Uarr\": \"↟\", \"Uarrocir\": \"⥉\", \"ubrcy\": \"ў\", \"Ubrcy\": \"Ў\", \"ubreve\": \"ŭ\", \"Ubreve\": \"Ŭ\", \"ucirc\": \"û\", \"Ucirc\": \"Û\", \"ucy\": \"у\", \"Ucy\": \"У\", \"udarr\": \"⇅\", \"udblac\": \"ű\", \"Udblac\": \"Ű\", \"udhar\": \"⥮\", \"ufisht\": \"⥾\", \"ufr\": \"𝔲\", \"Ufr\": \"𝔘\", \"ugrave\": \"ù\", \"Ugrave\": \"Ù\", \"uHar\": \"⥣\", \"uharl\": \"↿\", \"uharr\": \"↾\", \"uhblk\": \"▀\", \"ulcorn\": \"⌜\", \"ulcorner\": \"⌜\", \"ulcrop\": \"⌏\", \"ultri\": \"◸\", \"umacr\": \"ū\", \"Umacr\": \"Ū\", \"uml\": \"¨\", \"UnderBar\": \"_\", \"UnderBrace\": \"⏟\", \"UnderBracket\": \"⎵\", \"UnderParenthesis\": \"⏝\", \"Union\": \"⋃\", \"UnionPlus\": \"⊎\", \"uogon\": \"ų\", \"Uogon\": \"Ų\", \"uopf\": \"𝕦\", \"Uopf\": \"𝕌\", \"uparrow\": \"↑\", \"Uparrow\": \"⇑\", \"UpArrow\": \"↑\", \"UpArrowBar\": \"⤒\", \"UpArrowDownArrow\": \"⇅\", \"updownarrow\": \"↕\", \"Updownarrow\": \"⇕\", \"UpDownArrow\": \"↕\", \"UpEquilibrium\": \"⥮\", \"upharpoonleft\": \"↿\", \"upharpoonright\": \"↾\", \"uplus\": \"⊎\", \"UpperLeftArrow\": \"↖\", \"UpperRightArrow\": \"↗\", \"upsi\": \"υ\", \"Upsi\": \"ϒ\", \"upsih\": \"ϒ\", \"upsilon\": \"υ\", \"Upsilon\": \"Υ\", \"UpTee\": \"⊥\", \"UpTeeArrow\": \"↥\", \"upuparrows\": \"⇈\", \"urcorn\": \"⌝\", \"urcorner\": \"⌝\", \"urcrop\": \"⌎\", \"uring\": \"ů\", \"Uring\": \"Ů\", \"urtri\": \"◹\", \"uscr\": \"𝓊\", \"Uscr\": \"𝒰\", \"utdot\": \"⋰\", \"utilde\": \"ũ\", \"Utilde\": \"Ũ\", \"utri\": \"▵\", \"utrif\": \"▴\", \"uuarr\": \"⇈\", \"uuml\": \"ü\", \"Uuml\": \"Ü\", \"uwangle\": \"⦧\", \"vangrt\": \"⦜\", \"varepsilon\": \"ϵ\", \"varkappa\": \"ϰ\", \"varnothing\": \"∅\", \"varphi\": \"ϕ\", \"varpi\": \"ϖ\", \"varpropto\": \"∝\", \"varr\": \"↕\", \"vArr\": \"⇕\", \"varrho\": \"ϱ\", \"varsigma\": \"ς\", \"varsubsetneq\": \"⊊︀\", \"varsubsetneqq\": \"⫋︀\", \"varsupsetneq\": \"⊋︀\", \"varsupsetneqq\": \"⫌︀\", \"vartheta\": \"ϑ\", \"vartriangleleft\": \"⊲\", \"vartriangleright\": \"⊳\", \"vBar\": \"⫨\", \"Vbar\": \"⫫\", \"vBarv\": \"⫩\", \"vcy\": \"в\", \"Vcy\": \"В\", \"vdash\": \"⊢\", \"vDash\": \"⊨\", \"Vdash\": \"⊩\", \"VDash\": \"⊫\", \"Vdashl\": \"⫦\", \"vee\": \"∨\", \"Vee\": \"⋁\", \"veebar\": \"⊻\", \"veeeq\": \"≚\", \"vellip\": \"⋮\", \"verbar\": \"|\", \"Verbar\": \"‖\", \"vert\": \"|\", \"Vert\": \"‖\", \"VerticalBar\": \"∣\", \"VerticalLine\": \"|\", \"VerticalSeparator\": \"❘\", \"VerticalTilde\": \"≀\", \"VeryThinSpace\": \" \", \"vfr\": \"𝔳\", \"Vfr\": \"𝔙\", \"vltri\": \"⊲\", \"vnsub\": \"⊂⃒\", \"vnsup\": \"⊃⃒\", \"vopf\": \"𝕧\", \"Vopf\": \"𝕍\", \"vprop\": \"∝\", \"vrtri\": \"⊳\", \"vscr\": \"𝓋\", \"Vscr\": \"𝒱\", \"vsubne\": \"⊊︀\", \"vsubnE\": \"⫋︀\", \"vsupne\": \"⊋︀\", \"vsupnE\": \"⫌︀\", \"Vvdash\": \"⊪\", \"vzigzag\": \"⦚\", \"wcirc\": \"ŵ\", \"Wcirc\": \"Ŵ\", \"wedbar\": \"⩟\", \"wedge\": \"∧\", \"Wedge\": \"⋀\", \"wedgeq\": \"≙\", \"weierp\": \"℘\", \"wfr\": \"𝔴\", \"Wfr\": \"𝔚\", \"wopf\": \"𝕨\", \"Wopf\": \"𝕎\", \"wp\": \"℘\", \"wr\": \"≀\", \"wreath\": \"≀\", \"wscr\": \"𝓌\", \"Wscr\": \"𝒲\", \"xcap\": \"⋂\", \"xcirc\": \"◯\", \"xcup\": \"⋃\", \"xdtri\": \"▽\", \"xfr\": \"𝔵\", \"Xfr\": \"𝔛\", \"xharr\": \"⟷\", \"xhArr\": \"⟺\", \"xi\": \"ξ\", \"Xi\": \"Ξ\", \"xlarr\": \"⟵\", \"xlArr\": \"⟸\", \"xmap\": \"⟼\", \"xnis\": \"⋻\", \"xodot\": \"⨀\", \"xopf\": \"𝕩\", \"Xopf\": \"𝕏\", \"xoplus\": \"⨁\", \"xotime\": \"⨂\", \"xrarr\": \"⟶\", \"xrArr\": \"⟹\", \"xscr\": \"𝓍\", \"Xscr\": \"𝒳\", \"xsqcup\": \"⨆\", \"xuplus\": \"⨄\", \"xutri\": \"△\", \"xvee\": \"⋁\", \"xwedge\": \"⋀\", \"yacute\": \"ý\", \"Yacute\": \"Ý\", \"yacy\": \"я\", \"YAcy\": \"Я\", \"ycirc\": \"ŷ\", \"Ycirc\": \"Ŷ\", \"ycy\": \"ы\", \"Ycy\": \"Ы\", \"yen\": \"¥\", \"yfr\": \"𝔶\", \"Yfr\": \"𝔜\", \"yicy\": \"ї\", \"YIcy\": \"Ї\", \"yopf\": \"𝕪\", \"Yopf\": \"𝕐\", \"yscr\": \"𝓎\", \"Yscr\": \"𝒴\", \"yucy\": \"ю\", \"YUcy\": \"Ю\", \"yuml\": \"ÿ\", \"Yuml\": \"Ÿ\", \"zacute\": \"ź\", \"Zacute\": \"Ź\", \"zcaron\": \"ž\", \"Zcaron\": \"Ž\", \"zcy\": \"з\", \"Zcy\": \"З\", \"zdot\": \"ż\", \"Zdot\": \"Ż\", \"zeetrf\": \"ℨ\", \"ZeroWidthSpace\": \"​\", \"zeta\": \"ζ\", \"Zeta\": \"Ζ\", \"zfr\": \"𝔷\", \"Zfr\": \"ℨ\", \"zhcy\": \"ж\", \"ZHcy\": \"Ж\", \"zigrarr\": \"⇝\", \"zopf\": \"𝕫\", \"Zopf\": \"ℤ\", \"zscr\": \"𝓏\", \"Zscr\": \"𝒵\", \"zwj\": \"‍\", \"zwnj\": \"‌\" };\n var decodeMapLegacy = { \"aacute\": \"á\", \"Aacute\": \"Á\", \"acirc\": \"â\", \"Acirc\": \"Â\", \"acute\": \"´\", \"aelig\": \"æ\", \"AElig\": \"Æ\", \"agrave\": \"à\", \"Agrave\": \"À\", \"amp\": \"&\", \"AMP\": \"&\", \"aring\": \"å\", \"Aring\": \"Å\", \"atilde\": \"ã\", \"Atilde\": \"Ã\", \"auml\": \"ä\", \"Auml\": \"Ä\", \"brvbar\": \"¦\", \"ccedil\": \"ç\", \"Ccedil\": \"Ç\", \"cedil\": \"¸\", \"cent\": \"¢\", \"copy\": \"©\", \"COPY\": \"©\", \"curren\": \"¤\", \"deg\": \"°\", \"divide\": \"÷\", \"eacute\": \"é\", \"Eacute\": \"É\", \"ecirc\": \"ê\", \"Ecirc\": \"Ê\", \"egrave\": \"è\", \"Egrave\": \"È\", \"eth\": \"ð\", \"ETH\": \"Ð\", \"euml\": \"ë\", \"Euml\": \"Ë\", \"frac12\": \"½\", \"frac14\": \"¼\", \"frac34\": \"¾\", \"gt\": \">\", \"GT\": \">\", \"iacute\": \"í\", \"Iacute\": \"Í\", \"icirc\": \"î\", \"Icirc\": \"Î\", \"iexcl\": \"¡\", \"igrave\": \"ì\", \"Igrave\": \"Ì\", \"iquest\": \"¿\", \"iuml\": \"ï\", \"Iuml\": \"Ï\", \"laquo\": \"«\", \"lt\": \"<\", \"LT\": \"<\", \"macr\": \"¯\", \"micro\": \"µ\", \"middot\": \"·\", \"nbsp\": \" \", \"not\": \"¬\", \"ntilde\": \"ñ\", \"Ntilde\": \"Ñ\", \"oacute\": \"ó\", \"Oacute\": \"Ó\", \"ocirc\": \"ô\", \"Ocirc\": \"Ô\", \"ograve\": \"ò\", \"Ograve\": \"Ò\", \"ordf\": \"ª\", \"ordm\": \"º\", \"oslash\": \"ø\", \"Oslash\": \"Ø\", \"otilde\": \"õ\", \"Otilde\": \"Õ\", \"ouml\": \"ö\", \"Ouml\": \"Ö\", \"para\": \"¶\", \"plusmn\": \"±\", \"pound\": \"£\", \"quot\": '\"', \"QUOT\": '\"', \"raquo\": \"»\", \"reg\": \"®\", \"REG\": \"®\", \"sect\": \"§\", \"shy\": \"­\", \"sup1\": \"¹\", \"sup2\": \"²\", \"sup3\": \"³\", \"szlig\": \"ß\", \"thorn\": \"þ\", \"THORN\": \"Þ\", \"times\": \"×\", \"uacute\": \"ú\", \"Uacute\": \"Ú\", \"ucirc\": \"û\", \"Ucirc\": \"Û\", \"ugrave\": \"ù\", \"Ugrave\": \"Ù\", \"uml\": \"¨\", \"uuml\": \"ü\", \"Uuml\": \"Ü\", \"yacute\": \"ý\", \"Yacute\": \"Ý\", \"yen\": \"¥\", \"yuml\": \"ÿ\" };\n var decodeMapNumeric = { \"0\": \"�\", \"128\": \"€\", \"130\": \"‚\", \"131\": \"ƒ\", \"132\": \"„\", \"133\": \"…\", \"134\": \"†\", \"135\": \"‡\", \"136\": \"ˆ\", \"137\": \"‰\", \"138\": \"Š\", \"139\": \"‹\", \"140\": \"Œ\", \"142\": \"Ž\", \"145\": \"‘\", \"146\": \"’\", \"147\": \"“\", \"148\": \"”\", \"149\": \"•\", \"150\": \"–\", \"151\": \"—\", \"152\": \"˜\", \"153\": \"™\", \"154\": \"š\", \"155\": \"›\", \"156\": \"œ\", \"158\": \"ž\", \"159\": \"Ÿ\" };\n var invalidReferenceCodePoints = [1, 2, 3, 4, 5, 6, 7, 8, 11, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 127, 128, 129, 130, 131, 132, 133, 134, 135, 136, 137, 138, 139, 140, 141, 142, 143, 144, 145, 146, 147, 148, 149, 150, 151, 152, 153, 154, 155, 156, 157, 158, 159, 64976, 64977, 64978, 64979, 64980, 64981, 64982, 64983, 64984, 64985, 64986, 64987, 64988, 64989, 64990, 64991, 64992, 64993, 64994, 64995, 64996, 64997, 64998, 64999, 65e3, 65001, 65002, 65003, 65004, 65005, 65006, 65007, 65534, 65535, 131070, 131071, 196606, 196607, 262142, 262143, 327678, 327679, 393214, 393215, 458750, 458751, 524286, 524287, 589822, 589823, 655358, 655359, 720894, 720895, 786430, 786431, 851966, 851967, 917502, 917503, 983038, 983039, 1048574, 1048575, 1114110, 1114111];\n var stringFromCharCode2 = String.fromCharCode;\n var object = {};\n var hasOwnProperty = object.hasOwnProperty;\n var has2 = function(object2, propertyName) {\n return hasOwnProperty.call(object2, propertyName);\n };\n var contains = function(array, value) {\n var index = -1;\n var length = array.length;\n while (++index < length) {\n if (array[index] == value) {\n return true;\n }\n }\n return false;\n };\n var merge = function(options, defaults) {\n if (!options) {\n return defaults;\n }\n var result = {};\n var key2;\n for (key2 in defaults) {\n result[key2] = has2(options, key2) ? options[key2] : defaults[key2];\n }\n return result;\n };\n var codePointToSymbol = function(codePoint, strict) {\n var output = \"\";\n if (codePoint >= 55296 && codePoint <= 57343 || codePoint > 1114111) {\n if (strict) {\n parseError(\"character reference outside the permissible Unicode range\");\n }\n return \"�\";\n }\n if (has2(decodeMapNumeric, codePoint)) {\n if (strict) {\n parseError(\"disallowed character reference\");\n }\n return decodeMapNumeric[codePoint];\n }\n if (strict && contains(invalidReferenceCodePoints, codePoint)) {\n parseError(\"disallowed character reference\");\n }\n if (codePoint > 65535) {\n codePoint -= 65536;\n output += stringFromCharCode2(codePoint >>> 10 & 1023 | 55296);\n codePoint = 56320 | codePoint & 1023;\n }\n output += stringFromCharCode2(codePoint);\n return output;\n };\n var hexEscape = function(codePoint) {\n return \"&#x\" + codePoint.toString(16).toUpperCase() + \";\";\n };\n var decEscape = function(codePoint) {\n return \"&#\" + codePoint + \";\";\n };\n var parseError = function(message) {\n throw Error(\"Parse error: \" + message);\n };\n var encode3 = function(string, options) {\n options = merge(options, encode3.options);\n var strict = options.strict;\n if (strict && regexInvalidRawCodePoint.test(string)) {\n parseError(\"forbidden code point\");\n }\n var encodeEverything = options.encodeEverything;\n var useNamedReferences = options.useNamedReferences;\n var allowUnsafeSymbols = options.allowUnsafeSymbols;\n var escapeCodePoint = options.decimal ? decEscape : hexEscape;\n var escapeBmpSymbol = function(symbol) {\n return escapeCodePoint(symbol.charCodeAt(0));\n };\n if (encodeEverything) {\n string = string.replace(regexAsciiWhitelist, function(symbol) {\n if (useNamedReferences && has2(encodeMap, symbol)) {\n return \"&\" + encodeMap[symbol] + \";\";\n }\n return escapeBmpSymbol(symbol);\n });\n if (useNamedReferences) {\n string = string.replace(/>\\u20D2/g, \">⃒\").replace(/<\\u20D2/g, \"<⃒\").replace(/fj/g, \"fj\");\n }\n if (useNamedReferences) {\n string = string.replace(regexEncodeNonAscii, function(string2) {\n return \"&\" + encodeMap[string2] + \";\";\n });\n }\n } else if (useNamedReferences) {\n if (!allowUnsafeSymbols) {\n string = string.replace(regexEscape, function(string2) {\n return \"&\" + encodeMap[string2] + \";\";\n });\n }\n string = string.replace(/>\\u20D2/g, \">⃒\").replace(/<\\u20D2/g, \"<⃒\");\n string = string.replace(regexEncodeNonAscii, function(string2) {\n return \"&\" + encodeMap[string2] + \";\";\n });\n } else if (!allowUnsafeSymbols) {\n string = string.replace(regexEscape, escapeBmpSymbol);\n }\n return string.replace(regexAstralSymbols, function($0) {\n var high = $0.charCodeAt(0);\n var low = $0.charCodeAt(1);\n var codePoint = (high - 55296) * 1024 + low - 56320 + 65536;\n return escapeCodePoint(codePoint);\n }).replace(regexBmpWhitelist, escapeBmpSymbol);\n };\n encode3.options = {\n \"allowUnsafeSymbols\": false,\n \"encodeEverything\": false,\n \"strict\": false,\n \"useNamedReferences\": false,\n \"decimal\": false\n };\n var decode3 = function(html, options) {\n options = merge(options, decode3.options);\n var strict = options.strict;\n if (strict && regexInvalidEntity.test(html)) {\n parseError(\"malformed character reference\");\n }\n return html.replace(regexDecode, function($0, $1, $2, $3, $4, $5, $6, $7, $8) {\n var codePoint;\n var semicolon;\n var decDigits;\n var hexDigits;\n var reference2;\n var next;\n if ($1) {\n reference2 = $1;\n return decodeMap2[reference2];\n }\n if ($2) {\n reference2 = $2;\n next = $3;\n if (next && options.isAttributeValue) {\n if (strict && next == \"=\") {\n parseError(\"`&` did not start a character reference\");\n }\n return $0;\n } else {\n if (strict) {\n parseError(\n \"named character reference was not terminated by a semicolon\"\n );\n }\n return decodeMapLegacy[reference2] + (next || \"\");\n }\n }\n if ($4) {\n decDigits = $4;\n semicolon = $5;\n if (strict && !semicolon) {\n parseError(\"character reference was not terminated by a semicolon\");\n }\n codePoint = parseInt(decDigits, 10);\n return codePointToSymbol(codePoint, strict);\n }\n if ($6) {\n hexDigits = $6;\n semicolon = $7;\n if (strict && !semicolon) {\n parseError(\"character reference was not terminated by a semicolon\");\n }\n codePoint = parseInt(hexDigits, 16);\n return codePointToSymbol(codePoint, strict);\n }\n if (strict) {\n parseError(\n \"named character reference was not terminated by a semicolon\"\n );\n }\n return $0;\n });\n };\n decode3.options = {\n \"isAttributeValue\": false,\n \"strict\": false\n };\n var escape3 = function(string) {\n return string.replace(regexEscape, function($0) {\n return escapeMap[$0];\n });\n };\n var he2 = {\n \"version\": \"1.2.0\",\n \"encode\": encode3,\n \"decode\": decode3,\n \"escape\": escape3,\n \"unescape\": decode3\n };\n if (typeof define == \"function\" && typeof define.amd == \"object\" && define.amd) {\n define(function() {\n return he2;\n });\n } else if (freeExports && !freeExports.nodeType) {\n if (freeModule) {\n freeModule.exports = he2;\n } else {\n for (var key in he2) {\n has2(he2, key) && (freeExports[key] = he2[key]);\n }\n }\n } else {\n root.he = he2;\n }\n })(exports);\n }\n});\n\n// node_modules/.pnpm/json-logic-js@2.0.5/node_modules/json-logic-js/logic.js\nvar require_logic = __commonJS({\n \"node_modules/.pnpm/json-logic-js@2.0.5/node_modules/json-logic-js/logic.js\"(exports, module) {\n (function(root, factory) {\n if (typeof define === \"function\" && define.amd) {\n define(factory);\n } else if (typeof exports === \"object\") {\n module.exports = factory();\n } else {\n root.jsonLogic = factory();\n }\n })(exports, function() {\n \"use strict\";\n if (!Array.isArray) {\n Array.isArray = function(arg) {\n return Object.prototype.toString.call(arg) === \"[object Array]\";\n };\n }\n function arrayUnique(array) {\n var a = [];\n for (var i = 0, l = array.length; i < l; i++) {\n if (a.indexOf(array[i]) === -1) {\n a.push(array[i]);\n }\n }\n return a;\n }\n var jsonLogic2 = {};\n var operations = {\n \"==\": function(a, b) {\n return a == b;\n },\n \"===\": function(a, b) {\n return a === b;\n },\n \"!=\": function(a, b) {\n return a != b;\n },\n \"!==\": function(a, b) {\n return a !== b;\n },\n \">\": function(a, b) {\n return a > b;\n },\n \">=\": function(a, b) {\n return a >= b;\n },\n \"<\": function(a, b, c) {\n return c === void 0 ? a < b : a < b && b < c;\n },\n \"<=\": function(a, b, c) {\n return c === void 0 ? a <= b : a <= b && b <= c;\n },\n \"!!\": function(a) {\n return jsonLogic2.truthy(a);\n },\n \"!\": function(a) {\n return !jsonLogic2.truthy(a);\n },\n \"%\": function(a, b) {\n return a % b;\n },\n \"log\": function(a) {\n console.log(a);\n return a;\n },\n \"in\": function(a, b) {\n if (!b || typeof b.indexOf === \"undefined\") return false;\n return b.indexOf(a) !== -1;\n },\n \"cat\": function() {\n return Array.prototype.join.call(arguments, \"\");\n },\n \"substr\": function(source, start, end) {\n if (end < 0) {\n var temp = String(source).substr(start);\n return temp.substr(0, temp.length + end);\n }\n return String(source).substr(start, end);\n },\n \"+\": function() {\n return Array.prototype.reduce.call(arguments, function(a, b) {\n return parseFloat(a, 10) + parseFloat(b, 10);\n }, 0);\n },\n \"*\": function() {\n return Array.prototype.reduce.call(arguments, function(a, b) {\n return parseFloat(a, 10) * parseFloat(b, 10);\n });\n },\n \"-\": function(a, b) {\n if (b === void 0) {\n return -a;\n } else {\n return a - b;\n }\n },\n \"/\": function(a, b) {\n return a / b;\n },\n \"min\": function() {\n return Math.min.apply(this, arguments);\n },\n \"max\": function() {\n return Math.max.apply(this, arguments);\n },\n \"merge\": function() {\n return Array.prototype.reduce.call(arguments, function(a, b) {\n return a.concat(b);\n }, []);\n },\n \"var\": function(a, b) {\n var not_found = b === void 0 ? null : b;\n var data = this;\n if (typeof a === \"undefined\" || a === \"\" || a === null) {\n return data;\n }\n var sub_props = String(a).split(\".\");\n for (var i = 0; i < sub_props.length; i++) {\n if (data === null || data === void 0) {\n return not_found;\n }\n data = data[sub_props[i]];\n if (data === void 0) {\n return not_found;\n }\n }\n return data;\n },\n \"missing\": function() {\n var missing = [];\n var keys = Array.isArray(arguments[0]) ? arguments[0] : arguments;\n for (var i = 0; i < keys.length; i++) {\n var key = keys[i];\n var value = jsonLogic2.apply({ \"var\": key }, this);\n if (value === null || value === \"\") {\n missing.push(key);\n }\n }\n return missing;\n },\n \"missing_some\": function(need_count, options) {\n var are_missing = jsonLogic2.apply({ \"missing\": options }, this);\n if (options.length - are_missing.length >= need_count) {\n return [];\n } else {\n return are_missing;\n }\n }\n };\n jsonLogic2.is_logic = function(logic) {\n return typeof logic === \"object\" && // An object\n logic !== null && // but not null\n !Array.isArray(logic) && // and not an array\n Object.keys(logic).length === 1;\n };\n jsonLogic2.truthy = function(value) {\n if (Array.isArray(value) && value.length === 0) {\n return false;\n }\n return !!value;\n };\n jsonLogic2.get_operator = function(logic) {\n return Object.keys(logic)[0];\n };\n jsonLogic2.get_values = function(logic) {\n return logic[jsonLogic2.get_operator(logic)];\n };\n jsonLogic2.apply = function(logic, data) {\n if (Array.isArray(logic)) {\n return logic.map(function(l) {\n return jsonLogic2.apply(l, data);\n });\n }\n if (!jsonLogic2.is_logic(logic)) {\n return logic;\n }\n var op = jsonLogic2.get_operator(logic);\n var values = logic[op];\n var i;\n var current;\n var scopedLogic;\n var scopedData;\n var initial;\n if (!Array.isArray(values)) {\n values = [values];\n }\n if (op === \"if\" || op == \"?:\") {\n for (i = 0; i < values.length - 1; i += 2) {\n if (jsonLogic2.truthy(jsonLogic2.apply(values[i], data))) {\n return jsonLogic2.apply(values[i + 1], data);\n }\n }\n if (values.length === i + 1) {\n return jsonLogic2.apply(values[i], data);\n }\n return null;\n } else if (op === \"and\") {\n for (i = 0; i < values.length; i += 1) {\n current = jsonLogic2.apply(values[i], data);\n if (!jsonLogic2.truthy(current)) {\n return current;\n }\n }\n return current;\n } else if (op === \"or\") {\n for (i = 0; i < values.length; i += 1) {\n current = jsonLogic2.apply(values[i], data);\n if (jsonLogic2.truthy(current)) {\n return current;\n }\n }\n return current;\n } else if (op === \"filter\") {\n scopedData = jsonLogic2.apply(values[0], data);\n scopedLogic = values[1];\n if (!Array.isArray(scopedData)) {\n return [];\n }\n return scopedData.filter(function(datum) {\n return jsonLogic2.truthy(jsonLogic2.apply(scopedLogic, datum));\n });\n } else if (op === \"map\") {\n scopedData = jsonLogic2.apply(values[0], data);\n scopedLogic = values[1];\n if (!Array.isArray(scopedData)) {\n return [];\n }\n return scopedData.map(function(datum) {\n return jsonLogic2.apply(scopedLogic, datum);\n });\n } else if (op === \"reduce\") {\n scopedData = jsonLogic2.apply(values[0], data);\n scopedLogic = values[1];\n initial = typeof values[2] !== \"undefined\" ? jsonLogic2.apply(values[2], data) : null;\n if (!Array.isArray(scopedData)) {\n return initial;\n }\n return scopedData.reduce(\n function(accumulator, current2) {\n return jsonLogic2.apply(\n scopedLogic,\n { current: current2, accumulator }\n );\n },\n initial\n );\n } else if (op === \"all\") {\n scopedData = jsonLogic2.apply(values[0], data);\n scopedLogic = values[1];\n if (!Array.isArray(scopedData) || !scopedData.length) {\n return false;\n }\n for (i = 0; i < scopedData.length; i += 1) {\n if (!jsonLogic2.truthy(jsonLogic2.apply(scopedLogic, scopedData[i]))) {\n return false;\n }\n }\n return true;\n } else if (op === \"none\") {\n scopedData = jsonLogic2.apply(values[0], data);\n scopedLogic = values[1];\n if (!Array.isArray(scopedData) || !scopedData.length) {\n return true;\n }\n for (i = 0; i < scopedData.length; i += 1) {\n if (jsonLogic2.truthy(jsonLogic2.apply(scopedLogic, scopedData[i]))) {\n return false;\n }\n }\n return true;\n } else if (op === \"some\") {\n scopedData = jsonLogic2.apply(values[0], data);\n scopedLogic = values[1];\n if (!Array.isArray(scopedData) || !scopedData.length) {\n return false;\n }\n for (i = 0; i < scopedData.length; i += 1) {\n if (jsonLogic2.truthy(jsonLogic2.apply(scopedLogic, scopedData[i]))) {\n return true;\n }\n }\n return false;\n }\n values = values.map(function(val) {\n return jsonLogic2.apply(val, data);\n });\n if (operations.hasOwnProperty(op) && typeof operations[op] === \"function\") {\n return operations[op].apply(data, values);\n } else if (op.indexOf(\".\") > 0) {\n var sub_ops = String(op).split(\".\");\n var operation = operations;\n for (i = 0; i < sub_ops.length; i++) {\n if (!operation.hasOwnProperty(sub_ops[i])) {\n throw new Error(\"Unrecognized operation \" + op + \" (failed at \" + sub_ops.slice(0, i + 1).join(\".\") + \")\");\n }\n operation = operation[sub_ops[i]];\n }\n return operation.apply(data, values);\n }\n throw new Error(\"Unrecognized operation \" + op);\n };\n jsonLogic2.uses_data = function(logic) {\n var collection = [];\n if (jsonLogic2.is_logic(logic)) {\n var op = jsonLogic2.get_operator(logic);\n var values = logic[op];\n if (!Array.isArray(values)) {\n values = [values];\n }\n if (op === \"var\") {\n collection.push(values[0]);\n } else {\n values.forEach(function(val) {\n collection.push.apply(collection, jsonLogic2.uses_data(val));\n });\n }\n }\n return arrayUnique(collection);\n };\n jsonLogic2.add_operation = function(name, code2) {\n operations[name] = code2;\n };\n jsonLogic2.rm_operation = function(name) {\n delete operations[name];\n };\n jsonLogic2.rule_like = function(rule, pattern) {\n if (pattern === rule) {\n return true;\n }\n if (pattern === \"@\") {\n return true;\n }\n if (pattern === \"number\") {\n return typeof rule === \"number\";\n }\n if (pattern === \"string\") {\n return typeof rule === \"string\";\n }\n if (pattern === \"array\") {\n return Array.isArray(rule) && !jsonLogic2.is_logic(rule);\n }\n if (jsonLogic2.is_logic(pattern)) {\n if (jsonLogic2.is_logic(rule)) {\n var pattern_op = jsonLogic2.get_operator(pattern);\n var rule_op = jsonLogic2.get_operator(rule);\n if (pattern_op === \"@\" || pattern_op === rule_op) {\n return jsonLogic2.rule_like(\n jsonLogic2.get_values(rule, false),\n jsonLogic2.get_values(pattern, false)\n );\n }\n }\n return false;\n }\n if (Array.isArray(pattern)) {\n if (Array.isArray(rule)) {\n if (pattern.length !== rule.length) {\n return false;\n }\n for (var i = 0; i < pattern.length; i += 1) {\n if (!jsonLogic2.rule_like(rule[i], pattern[i])) {\n return false;\n }\n }\n return true;\n } else {\n return false;\n }\n }\n return false;\n };\n return jsonLogic2;\n });\n }\n});\n\n// node_modules/.pnpm/path-to-regexp@8.3.0/node_modules/path-to-regexp/dist/index.js\nvar require_dist = __commonJS({\n \"node_modules/.pnpm/path-to-regexp@8.3.0/node_modules/path-to-regexp/dist/index.js\"(exports) {\n \"use strict\";\n Object.defineProperty(exports, \"__esModule\", { value: true });\n exports.PathError = exports.TokenData = void 0;\n exports.parse = parse;\n exports.compile = compile2;\n exports.match = match2;\n exports.pathToRegexp = pathToRegexp;\n exports.stringify = stringify;\n var DEFAULT_DELIMITER = \"/\";\n var NOOP_VALUE = (value) => value;\n var ID_START = /^[$_\\p{ID_Start}]$/u;\n var ID_CONTINUE = /^[$\\u200c\\u200d\\p{ID_Continue}]$/u;\n var SIMPLE_TOKENS = {\n // Groups.\n \"{\": \"{\",\n \"}\": \"}\",\n // Reserved.\n \"(\": \"(\",\n \")\": \")\",\n \"[\": \"[\",\n \"]\": \"]\",\n \"+\": \"+\",\n \"?\": \"?\",\n \"!\": \"!\"\n };\n function escapeText2(str) {\n return str.replace(/[{}()\\[\\]+?!:*\\\\]/g, \"\\\\$&\");\n }\n function escape3(str) {\n return str.replace(/[.+*?^${}()[\\]|/\\\\]/g, \"\\\\$&\");\n }\n var TokenData = class {\n constructor(tokens, originalPath) {\n this.tokens = tokens;\n this.originalPath = originalPath;\n }\n };\n exports.TokenData = TokenData;\n var PathError = class extends TypeError {\n constructor(message, originalPath) {\n let text2 = message;\n if (originalPath)\n text2 += `: ${originalPath}`;\n text2 += `; visit https://git.new/pathToRegexpError for info`;\n super(text2);\n this.originalPath = originalPath;\n }\n };\n exports.PathError = PathError;\n function parse(str, options = {}) {\n const { encodePath = NOOP_VALUE } = options;\n const chars = [...str];\n const tokens = [];\n let index = 0;\n let pos = 0;\n function name() {\n let value = \"\";\n if (ID_START.test(chars[index])) {\n do {\n value += chars[index++];\n } while (ID_CONTINUE.test(chars[index]));\n } else if (chars[index] === '\"') {\n let quoteStart = index;\n while (index++ < chars.length) {\n if (chars[index] === '\"') {\n index++;\n quoteStart = 0;\n break;\n }\n if (chars[index] === \"\\\\\")\n index++;\n value += chars[index];\n }\n if (quoteStart) {\n throw new PathError(`Unterminated quote at index ${quoteStart}`, str);\n }\n }\n if (!value) {\n throw new PathError(`Missing parameter name at index ${index}`, str);\n }\n return value;\n }\n while (index < chars.length) {\n const value = chars[index];\n const type = SIMPLE_TOKENS[value];\n if (type) {\n tokens.push({ type, index: index++, value });\n } else if (value === \"\\\\\") {\n tokens.push({ type: \"escape\", index: index++, value: chars[index++] });\n } else if (value === \":\") {\n tokens.push({ type: \"param\", index: index++, value: name() });\n } else if (value === \"*\") {\n tokens.push({ type: \"wildcard\", index: index++, value: name() });\n } else {\n tokens.push({ type: \"char\", index: index++, value });\n }\n }\n tokens.push({ type: \"end\", index, value: \"\" });\n function consumeUntil(endType) {\n const output = [];\n while (true) {\n const token = tokens[pos++];\n if (token.type === endType)\n break;\n if (token.type === \"char\" || token.type === \"escape\") {\n let path = token.value;\n let cur = tokens[pos];\n while (cur.type === \"char\" || cur.type === \"escape\") {\n path += cur.value;\n cur = tokens[++pos];\n }\n output.push({\n type: \"text\",\n value: encodePath(path)\n });\n continue;\n }\n if (token.type === \"param\" || token.type === \"wildcard\") {\n output.push({\n type: token.type,\n name: token.value\n });\n continue;\n }\n if (token.type === \"{\") {\n output.push({\n type: \"group\",\n tokens: consumeUntil(\"}\")\n });\n continue;\n }\n throw new PathError(`Unexpected ${token.type} at index ${token.index}, expected ${endType}`, str);\n }\n return output;\n }\n return new TokenData(consumeUntil(\"end\"), str);\n }\n function compile2(path, options = {}) {\n const { encode: encode3 = encodeURIComponent, delimiter: delimiter2 = DEFAULT_DELIMITER } = options;\n const data = typeof path === \"object\" ? path : parse(path, options);\n const fn = tokensToFunction(data.tokens, delimiter2, encode3);\n return function path2(params = {}) {\n const [path3, ...missing] = fn(params);\n if (missing.length) {\n throw new TypeError(`Missing parameters: ${missing.join(\", \")}`);\n }\n return path3;\n };\n }\n function tokensToFunction(tokens, delimiter2, encode3) {\n const encoders = tokens.map((token) => tokenToFunction(token, delimiter2, encode3));\n return (data) => {\n const result = [\"\"];\n for (const encoder of encoders) {\n const [value, ...extras] = encoder(data);\n result[0] += value;\n result.push(...extras);\n }\n return result;\n };\n }\n function tokenToFunction(token, delimiter2, encode3) {\n if (token.type === \"text\")\n return () => [token.value];\n if (token.type === \"group\") {\n const fn = tokensToFunction(token.tokens, delimiter2, encode3);\n return (data) => {\n const [value, ...missing] = fn(data);\n if (!missing.length)\n return [value];\n return [\"\"];\n };\n }\n const encodeValue = encode3 || NOOP_VALUE;\n if (token.type === \"wildcard\" && encode3 !== false) {\n return (data) => {\n const value = data[token.name];\n if (value == null)\n return [\"\", token.name];\n if (!Array.isArray(value) || value.length === 0) {\n throw new TypeError(`Expected \"${token.name}\" to be a non-empty array`);\n }\n return [\n value.map((value2, index) => {\n if (typeof value2 !== \"string\") {\n throw new TypeError(`Expected \"${token.name}/${index}\" to be a string`);\n }\n return encodeValue(value2);\n }).join(delimiter2)\n ];\n };\n }\n return (data) => {\n const value = data[token.name];\n if (value == null)\n return [\"\", token.name];\n if (typeof value !== \"string\") {\n throw new TypeError(`Expected \"${token.name}\" to be a string`);\n }\n return [encodeValue(value)];\n };\n }\n function match2(path, options = {}) {\n const { decode: decode3 = decodeURIComponent, delimiter: delimiter2 = DEFAULT_DELIMITER } = options;\n const { regexp, keys } = pathToRegexp(path, options);\n const decoders = keys.map((key) => {\n if (decode3 === false)\n return NOOP_VALUE;\n if (key.type === \"param\")\n return decode3;\n return (value) => value.split(delimiter2).map(decode3);\n });\n return function match3(input) {\n const m = regexp.exec(input);\n if (!m)\n return false;\n const path2 = m[0];\n const params = /* @__PURE__ */ Object.create(null);\n for (let i = 1; i < m.length; i++) {\n if (m[i] === void 0)\n continue;\n const key = keys[i - 1];\n const decoder = decoders[i - 1];\n params[key.name] = decoder(m[i]);\n }\n return { path: path2, params };\n };\n }\n function pathToRegexp(path, options = {}) {\n const { delimiter: delimiter2 = DEFAULT_DELIMITER, end = true, sensitive = false, trailing = true } = options;\n const keys = [];\n const flags = sensitive ? \"\" : \"i\";\n const sources = [];\n for (const input of pathsToArray(path, [])) {\n const data = typeof input === \"object\" ? input : parse(input, options);\n for (const tokens of flatten(data.tokens, 0, [])) {\n sources.push(toRegExpSource(tokens, delimiter2, keys, data.originalPath));\n }\n }\n let pattern = `^(?:${sources.join(\"|\")})`;\n if (trailing)\n pattern += `(?:${escape3(delimiter2)}$)?`;\n pattern += end ? \"$\" : `(?=${escape3(delimiter2)}|$)`;\n const regexp = new RegExp(pattern, flags);\n return { regexp, keys };\n }\n function pathsToArray(paths, init) {\n if (Array.isArray(paths)) {\n for (const p of paths)\n pathsToArray(p, init);\n } else {\n init.push(paths);\n }\n return init;\n }\n function* flatten(tokens, index, init) {\n if (index === tokens.length) {\n return yield init;\n }\n const token = tokens[index];\n if (token.type === \"group\") {\n for (const seq of flatten(token.tokens, 0, init.slice())) {\n yield* flatten(tokens, index + 1, seq);\n }\n } else {\n init.push(token);\n }\n yield* flatten(tokens, index + 1, init);\n }\n function toRegExpSource(tokens, delimiter2, keys, originalPath) {\n let result = \"\";\n let backtrack = \"\";\n let isSafeSegmentParam = true;\n for (const token of tokens) {\n if (token.type === \"text\") {\n result += escape3(token.value);\n backtrack += token.value;\n isSafeSegmentParam || (isSafeSegmentParam = token.value.includes(delimiter2));\n continue;\n }\n if (token.type === \"param\" || token.type === \"wildcard\") {\n if (!isSafeSegmentParam && !backtrack) {\n throw new PathError(`Missing text before \"${token.name}\" ${token.type}`, originalPath);\n }\n if (token.type === \"param\") {\n result += `(${negate(delimiter2, isSafeSegmentParam ? \"\" : backtrack)}+)`;\n } else {\n result += `([\\\\s\\\\S]+)`;\n }\n keys.push(token);\n backtrack = \"\";\n isSafeSegmentParam = false;\n continue;\n }\n }\n return result;\n }\n function negate(delimiter2, backtrack) {\n if (backtrack.length < 2) {\n if (delimiter2.length < 2)\n return `[^${escape3(delimiter2 + backtrack)}]`;\n return `(?:(?!${escape3(delimiter2)})[^${escape3(backtrack)}])`;\n }\n if (delimiter2.length < 2) {\n return `(?:(?!${escape3(backtrack)})[^${escape3(delimiter2)}])`;\n }\n return `(?:(?!${escape3(backtrack)}|${escape3(delimiter2)})[\\\\s\\\\S])`;\n }\n function stringifyTokens(tokens) {\n let value = \"\";\n let i = 0;\n function name(value2) {\n const isSafe = isNameSafe(value2) && isNextNameSafe(tokens[i]);\n return isSafe ? value2 : JSON.stringify(value2);\n }\n while (i < tokens.length) {\n const token = tokens[i++];\n if (token.type === \"text\") {\n value += escapeText2(token.value);\n continue;\n }\n if (token.type === \"group\") {\n value += `{${stringifyTokens(token.tokens)}}`;\n continue;\n }\n if (token.type === \"param\") {\n value += `:${name(token.name)}`;\n continue;\n }\n if (token.type === \"wildcard\") {\n value += `*${name(token.name)}`;\n continue;\n }\n throw new TypeError(`Unknown token type: ${token.type}`);\n }\n return value;\n }\n function stringify(data) {\n return stringifyTokens(data.tokens);\n }\n function isNameSafe(name) {\n const [first, ...rest] = name;\n return ID_START.test(first) && rest.every((char) => ID_CONTINUE.test(char));\n }\n function isNextNameSafe(token) {\n if (token && token.type === \"text\")\n return !ID_CONTINUE.test(token.value[0]);\n return true;\n }\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/constants.js\nvar require_constants = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/constants.js\"(exports, module) {\n \"use strict\";\n var SEMVER_SPEC_VERSION = \"2.0.0\";\n var MAX_LENGTH = 256;\n var MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER || /* istanbul ignore next */\n 9007199254740991;\n var MAX_SAFE_COMPONENT_LENGTH = 16;\n var MAX_SAFE_BUILD_LENGTH = MAX_LENGTH - 6;\n var RELEASE_TYPES = [\n \"major\",\n \"premajor\",\n \"minor\",\n \"preminor\",\n \"patch\",\n \"prepatch\",\n \"prerelease\"\n ];\n module.exports = {\n MAX_LENGTH,\n MAX_SAFE_COMPONENT_LENGTH,\n MAX_SAFE_BUILD_LENGTH,\n MAX_SAFE_INTEGER,\n RELEASE_TYPES,\n SEMVER_SPEC_VERSION,\n FLAG_INCLUDE_PRERELEASE: 1,\n FLAG_LOOSE: 2\n };\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/debug.js\nvar require_debug = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/debug.js\"(exports, module) {\n \"use strict\";\n var debug = typeof process === \"object\" && process.env && process.env.NODE_DEBUG && /\\bsemver\\b/i.test(process.env.NODE_DEBUG) ? (...args) => console.error(\"SEMVER\", ...args) : () => {\n };\n module.exports = debug;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/re.js\nvar require_re = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/re.js\"(exports, module) {\n \"use strict\";\n var {\n MAX_SAFE_COMPONENT_LENGTH,\n MAX_SAFE_BUILD_LENGTH,\n MAX_LENGTH\n } = require_constants();\n var debug = require_debug();\n exports = module.exports = {};\n var re = exports.re = [];\n var safeRe = exports.safeRe = [];\n var src = exports.src = [];\n var safeSrc = exports.safeSrc = [];\n var t = exports.t = {};\n var R = 0;\n var LETTERDASHNUMBER = \"[a-zA-Z0-9-]\";\n var safeRegexReplacements = [\n [\"\\\\s\", 1],\n [\"\\\\d\", MAX_LENGTH],\n [LETTERDASHNUMBER, MAX_SAFE_BUILD_LENGTH]\n ];\n var makeSafeRegex = (value) => {\n for (const [token, max2] of safeRegexReplacements) {\n value = value.split(`${token}*`).join(`${token}{0,${max2}}`).split(`${token}+`).join(`${token}{1,${max2}}`);\n }\n return value;\n };\n var createToken = (name, value, isGlobal) => {\n const safe = makeSafeRegex(value);\n const index = R++;\n debug(name, index, value);\n t[name] = index;\n src[index] = value;\n safeSrc[index] = safe;\n re[index] = new RegExp(value, isGlobal ? \"g\" : void 0);\n safeRe[index] = new RegExp(safe, isGlobal ? \"g\" : void 0);\n };\n createToken(\"NUMERICIDENTIFIER\", \"0|[1-9]\\\\d*\");\n createToken(\"NUMERICIDENTIFIERLOOSE\", \"\\\\d+\");\n createToken(\"NONNUMERICIDENTIFIER\", `\\\\d*[a-zA-Z-]${LETTERDASHNUMBER}*`);\n createToken(\"MAINVERSION\", `(${src[t.NUMERICIDENTIFIER]})\\\\.(${src[t.NUMERICIDENTIFIER]})\\\\.(${src[t.NUMERICIDENTIFIER]})`);\n createToken(\"MAINVERSIONLOOSE\", `(${src[t.NUMERICIDENTIFIERLOOSE]})\\\\.(${src[t.NUMERICIDENTIFIERLOOSE]})\\\\.(${src[t.NUMERICIDENTIFIERLOOSE]})`);\n createToken(\"PRERELEASEIDENTIFIER\", `(?:${src[t.NONNUMERICIDENTIFIER]}|${src[t.NUMERICIDENTIFIER]})`);\n createToken(\"PRERELEASEIDENTIFIERLOOSE\", `(?:${src[t.NONNUMERICIDENTIFIER]}|${src[t.NUMERICIDENTIFIERLOOSE]})`);\n createToken(\"PRERELEASE\", `(?:-(${src[t.PRERELEASEIDENTIFIER]}(?:\\\\.${src[t.PRERELEASEIDENTIFIER]})*))`);\n createToken(\"PRERELEASELOOSE\", `(?:-?(${src[t.PRERELEASEIDENTIFIERLOOSE]}(?:\\\\.${src[t.PRERELEASEIDENTIFIERLOOSE]})*))`);\n createToken(\"BUILDIDENTIFIER\", `${LETTERDASHNUMBER}+`);\n createToken(\"BUILD\", `(?:\\\\+(${src[t.BUILDIDENTIFIER]}(?:\\\\.${src[t.BUILDIDENTIFIER]})*))`);\n createToken(\"FULLPLAIN\", `v?${src[t.MAINVERSION]}${src[t.PRERELEASE]}?${src[t.BUILD]}?`);\n createToken(\"FULL\", `^${src[t.FULLPLAIN]}$`);\n createToken(\"LOOSEPLAIN\", `[v=\\\\s]*${src[t.MAINVERSIONLOOSE]}${src[t.PRERELEASELOOSE]}?${src[t.BUILD]}?`);\n createToken(\"LOOSE\", `^${src[t.LOOSEPLAIN]}$`);\n createToken(\"GTLT\", \"((?:<|>)?=?)\");\n createToken(\"XRANGEIDENTIFIERLOOSE\", `${src[t.NUMERICIDENTIFIERLOOSE]}|x|X|\\\\*`);\n createToken(\"XRANGEIDENTIFIER\", `${src[t.NUMERICIDENTIFIER]}|x|X|\\\\*`);\n createToken(\"XRANGEPLAIN\", `[v=\\\\s]*(${src[t.XRANGEIDENTIFIER]})(?:\\\\.(${src[t.XRANGEIDENTIFIER]})(?:\\\\.(${src[t.XRANGEIDENTIFIER]})(?:${src[t.PRERELEASE]})?${src[t.BUILD]}?)?)?`);\n createToken(\"XRANGEPLAINLOOSE\", `[v=\\\\s]*(${src[t.XRANGEIDENTIFIERLOOSE]})(?:\\\\.(${src[t.XRANGEIDENTIFIERLOOSE]})(?:\\\\.(${src[t.XRANGEIDENTIFIERLOOSE]})(?:${src[t.PRERELEASELOOSE]})?${src[t.BUILD]}?)?)?`);\n createToken(\"XRANGE\", `^${src[t.GTLT]}\\\\s*${src[t.XRANGEPLAIN]}$`);\n createToken(\"XRANGELOOSE\", `^${src[t.GTLT]}\\\\s*${src[t.XRANGEPLAINLOOSE]}$`);\n createToken(\"COERCEPLAIN\", `${\"(^|[^\\\\d])(\\\\d{1,\"}${MAX_SAFE_COMPONENT_LENGTH}})(?:\\\\.(\\\\d{1,${MAX_SAFE_COMPONENT_LENGTH}}))?(?:\\\\.(\\\\d{1,${MAX_SAFE_COMPONENT_LENGTH}}))?`);\n createToken(\"COERCE\", `${src[t.COERCEPLAIN]}(?:$|[^\\\\d])`);\n createToken(\"COERCEFULL\", src[t.COERCEPLAIN] + `(?:${src[t.PRERELEASE]})?(?:${src[t.BUILD]})?(?:$|[^\\\\d])`);\n createToken(\"COERCERTL\", src[t.COERCE], true);\n createToken(\"COERCERTLFULL\", src[t.COERCEFULL], true);\n createToken(\"LONETILDE\", \"(?:~>?)\");\n createToken(\"TILDETRIM\", `(\\\\s*)${src[t.LONETILDE]}\\\\s+`, true);\n exports.tildeTrimReplace = \"$1~\";\n createToken(\"TILDE\", `^${src[t.LONETILDE]}${src[t.XRANGEPLAIN]}$`);\n createToken(\"TILDELOOSE\", `^${src[t.LONETILDE]}${src[t.XRANGEPLAINLOOSE]}$`);\n createToken(\"LONECARET\", \"(?:\\\\^)\");\n createToken(\"CARETTRIM\", `(\\\\s*)${src[t.LONECARET]}\\\\s+`, true);\n exports.caretTrimReplace = \"$1^\";\n createToken(\"CARET\", `^${src[t.LONECARET]}${src[t.XRANGEPLAIN]}$`);\n createToken(\"CARETLOOSE\", `^${src[t.LONECARET]}${src[t.XRANGEPLAINLOOSE]}$`);\n createToken(\"COMPARATORLOOSE\", `^${src[t.GTLT]}\\\\s*(${src[t.LOOSEPLAIN]})$|^$`);\n createToken(\"COMPARATOR\", `^${src[t.GTLT]}\\\\s*(${src[t.FULLPLAIN]})$|^$`);\n createToken(\"COMPARATORTRIM\", `(\\\\s*)${src[t.GTLT]}\\\\s*(${src[t.LOOSEPLAIN]}|${src[t.XRANGEPLAIN]})`, true);\n exports.comparatorTrimReplace = \"$1$2$3\";\n createToken(\"HYPHENRANGE\", `^\\\\s*(${src[t.XRANGEPLAIN]})\\\\s+-\\\\s+(${src[t.XRANGEPLAIN]})\\\\s*$`);\n createToken(\"HYPHENRANGELOOSE\", `^\\\\s*(${src[t.XRANGEPLAINLOOSE]})\\\\s+-\\\\s+(${src[t.XRANGEPLAINLOOSE]})\\\\s*$`);\n createToken(\"STAR\", \"(<|>)?=?\\\\s*\\\\*\");\n createToken(\"GTE0\", \"^\\\\s*>=\\\\s*0\\\\.0\\\\.0\\\\s*$\");\n createToken(\"GTE0PRE\", \"^\\\\s*>=\\\\s*0\\\\.0\\\\.0-0\\\\s*$\");\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/parse-options.js\nvar require_parse_options = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/parse-options.js\"(exports, module) {\n \"use strict\";\n var looseOption = Object.freeze({ loose: true });\n var emptyOpts = Object.freeze({});\n var parseOptions = (options) => {\n if (!options) {\n return emptyOpts;\n }\n if (typeof options !== \"object\") {\n return looseOption;\n }\n return options;\n };\n module.exports = parseOptions;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/identifiers.js\nvar require_identifiers = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/identifiers.js\"(exports, module) {\n \"use strict\";\n var numeric = /^[0-9]+$/;\n var compareIdentifiers = (a, b) => {\n if (typeof a === \"number\" && typeof b === \"number\") {\n return a === b ? 0 : a < b ? -1 : 1;\n }\n const anum = numeric.test(a);\n const bnum = numeric.test(b);\n if (anum && bnum) {\n a = +a;\n b = +b;\n }\n return a === b ? 0 : anum && !bnum ? -1 : bnum && !anum ? 1 : a < b ? -1 : 1;\n };\n var rcompareIdentifiers = (a, b) => compareIdentifiers(b, a);\n module.exports = {\n compareIdentifiers,\n rcompareIdentifiers\n };\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/semver.js\nvar require_semver = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/semver.js\"(exports, module) {\n \"use strict\";\n var debug = require_debug();\n var { MAX_LENGTH, MAX_SAFE_INTEGER } = require_constants();\n var { safeRe: re, t } = require_re();\n var parseOptions = require_parse_options();\n var { compareIdentifiers } = require_identifiers();\n var SemVer = class _SemVer {\n constructor(version, options) {\n options = parseOptions(options);\n if (version instanceof _SemVer) {\n if (version.loose === !!options.loose && version.includePrerelease === !!options.includePrerelease) {\n return version;\n } else {\n version = version.version;\n }\n } else if (typeof version !== \"string\") {\n throw new TypeError(`Invalid version. Must be a string. Got type \"${typeof version}\".`);\n }\n if (version.length > MAX_LENGTH) {\n throw new TypeError(\n `version is longer than ${MAX_LENGTH} characters`\n );\n }\n debug(\"SemVer\", version, options);\n this.options = options;\n this.loose = !!options.loose;\n this.includePrerelease = !!options.includePrerelease;\n const m = version.trim().match(options.loose ? re[t.LOOSE] : re[t.FULL]);\n if (!m) {\n throw new TypeError(`Invalid Version: ${version}`);\n }\n this.raw = version;\n this.major = +m[1];\n this.minor = +m[2];\n this.patch = +m[3];\n if (this.major > MAX_SAFE_INTEGER || this.major < 0) {\n throw new TypeError(\"Invalid major version\");\n }\n if (this.minor > MAX_SAFE_INTEGER || this.minor < 0) {\n throw new TypeError(\"Invalid minor version\");\n }\n if (this.patch > MAX_SAFE_INTEGER || this.patch < 0) {\n throw new TypeError(\"Invalid patch version\");\n }\n if (!m[4]) {\n this.prerelease = [];\n } else {\n this.prerelease = m[4].split(\".\").map((id) => {\n if (/^[0-9]+$/.test(id)) {\n const num = +id;\n if (num >= 0 && num < MAX_SAFE_INTEGER) {\n return num;\n }\n }\n return id;\n });\n }\n this.build = m[5] ? m[5].split(\".\") : [];\n this.format();\n }\n format() {\n this.version = `${this.major}.${this.minor}.${this.patch}`;\n if (this.prerelease.length) {\n this.version += `-${this.prerelease.join(\".\")}`;\n }\n return this.version;\n }\n toString() {\n return this.version;\n }\n compare(other) {\n debug(\"SemVer.compare\", this.version, this.options, other);\n if (!(other instanceof _SemVer)) {\n if (typeof other === \"string\" && other === this.version) {\n return 0;\n }\n other = new _SemVer(other, this.options);\n }\n if (other.version === this.version) {\n return 0;\n }\n return this.compareMain(other) || this.comparePre(other);\n }\n compareMain(other) {\n if (!(other instanceof _SemVer)) {\n other = new _SemVer(other, this.options);\n }\n if (this.major < other.major) {\n return -1;\n }\n if (this.major > other.major) {\n return 1;\n }\n if (this.minor < other.minor) {\n return -1;\n }\n if (this.minor > other.minor) {\n return 1;\n }\n if (this.patch < other.patch) {\n return -1;\n }\n if (this.patch > other.patch) {\n return 1;\n }\n return 0;\n }\n comparePre(other) {\n if (!(other instanceof _SemVer)) {\n other = new _SemVer(other, this.options);\n }\n if (this.prerelease.length && !other.prerelease.length) {\n return -1;\n } else if (!this.prerelease.length && other.prerelease.length) {\n return 1;\n } else if (!this.prerelease.length && !other.prerelease.length) {\n return 0;\n }\n let i = 0;\n do {\n const a = this.prerelease[i];\n const b = other.prerelease[i];\n debug(\"prerelease compare\", i, a, b);\n if (a === void 0 && b === void 0) {\n return 0;\n } else if (b === void 0) {\n return 1;\n } else if (a === void 0) {\n return -1;\n } else if (a === b) {\n continue;\n } else {\n return compareIdentifiers(a, b);\n }\n } while (++i);\n }\n compareBuild(other) {\n if (!(other instanceof _SemVer)) {\n other = new _SemVer(other, this.options);\n }\n let i = 0;\n do {\n const a = this.build[i];\n const b = other.build[i];\n debug(\"build compare\", i, a, b);\n if (a === void 0 && b === void 0) {\n return 0;\n } else if (b === void 0) {\n return 1;\n } else if (a === void 0) {\n return -1;\n } else if (a === b) {\n continue;\n } else {\n return compareIdentifiers(a, b);\n }\n } while (++i);\n }\n // preminor will bump the version up to the next minor release, and immediately\n // down to pre-release. premajor and prepatch work the same way.\n inc(release, identifier, identifierBase) {\n if (release.startsWith(\"pre\")) {\n if (!identifier && identifierBase === false) {\n throw new Error(\"invalid increment argument: identifier is empty\");\n }\n if (identifier) {\n const match2 = `-${identifier}`.match(this.options.loose ? re[t.PRERELEASELOOSE] : re[t.PRERELEASE]);\n if (!match2 || match2[1] !== identifier) {\n throw new Error(`invalid identifier: ${identifier}`);\n }\n }\n }\n switch (release) {\n case \"premajor\":\n this.prerelease.length = 0;\n this.patch = 0;\n this.minor = 0;\n this.major++;\n this.inc(\"pre\", identifier, identifierBase);\n break;\n case \"preminor\":\n this.prerelease.length = 0;\n this.patch = 0;\n this.minor++;\n this.inc(\"pre\", identifier, identifierBase);\n break;\n case \"prepatch\":\n this.prerelease.length = 0;\n this.inc(\"patch\", identifier, identifierBase);\n this.inc(\"pre\", identifier, identifierBase);\n break;\n // If the input is a non-prerelease version, this acts the same as\n // prepatch.\n case \"prerelease\":\n if (this.prerelease.length === 0) {\n this.inc(\"patch\", identifier, identifierBase);\n }\n this.inc(\"pre\", identifier, identifierBase);\n break;\n case \"release\":\n if (this.prerelease.length === 0) {\n throw new Error(`version ${this.raw} is not a prerelease`);\n }\n this.prerelease.length = 0;\n break;\n case \"major\":\n if (this.minor !== 0 || this.patch !== 0 || this.prerelease.length === 0) {\n this.major++;\n }\n this.minor = 0;\n this.patch = 0;\n this.prerelease = [];\n break;\n case \"minor\":\n if (this.patch !== 0 || this.prerelease.length === 0) {\n this.minor++;\n }\n this.patch = 0;\n this.prerelease = [];\n break;\n case \"patch\":\n if (this.prerelease.length === 0) {\n this.patch++;\n }\n this.prerelease = [];\n break;\n // This probably shouldn't be used publicly.\n // 1.0.0 'pre' would become 1.0.0-0 which is the wrong direction.\n case \"pre\": {\n const base2 = Number(identifierBase) ? 1 : 0;\n if (this.prerelease.length === 0) {\n this.prerelease = [base2];\n } else {\n let i = this.prerelease.length;\n while (--i >= 0) {\n if (typeof this.prerelease[i] === \"number\") {\n this.prerelease[i]++;\n i = -2;\n }\n }\n if (i === -1) {\n if (identifier === this.prerelease.join(\".\") && identifierBase === false) {\n throw new Error(\"invalid increment argument: identifier already exists\");\n }\n this.prerelease.push(base2);\n }\n }\n if (identifier) {\n let prerelease = [identifier, base2];\n if (identifierBase === false) {\n prerelease = [identifier];\n }\n if (compareIdentifiers(this.prerelease[0], identifier) === 0) {\n if (isNaN(this.prerelease[1])) {\n this.prerelease = prerelease;\n }\n } else {\n this.prerelease = prerelease;\n }\n }\n break;\n }\n default:\n throw new Error(`invalid increment argument: ${release}`);\n }\n this.raw = this.format();\n if (this.build.length) {\n this.raw += `+${this.build.join(\".\")}`;\n }\n return this;\n }\n };\n module.exports = SemVer;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/parse.js\nvar require_parse = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/parse.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var parse = (version, options, throwErrors = false) => {\n if (version instanceof SemVer) {\n return version;\n }\n try {\n return new SemVer(version, options);\n } catch (er) {\n if (!throwErrors) {\n return null;\n }\n throw er;\n }\n };\n module.exports = parse;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/valid.js\nvar require_valid = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/valid.js\"(exports, module) {\n \"use strict\";\n var parse = require_parse();\n var valid = (version, options) => {\n const v = parse(version, options);\n return v ? v.version : null;\n };\n module.exports = valid;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/clean.js\nvar require_clean = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/clean.js\"(exports, module) {\n \"use strict\";\n var parse = require_parse();\n var clean2 = (version, options) => {\n const s = parse(version.trim().replace(/^[=v]+/, \"\"), options);\n return s ? s.version : null;\n };\n module.exports = clean2;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/inc.js\nvar require_inc = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/inc.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var inc = (version, release, options, identifier, identifierBase) => {\n if (typeof options === \"string\") {\n identifierBase = identifier;\n identifier = options;\n options = void 0;\n }\n try {\n return new SemVer(\n version instanceof SemVer ? version.version : version,\n options\n ).inc(release, identifier, identifierBase).version;\n } catch (er) {\n return null;\n }\n };\n module.exports = inc;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/diff.js\nvar require_diff = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/diff.js\"(exports, module) {\n \"use strict\";\n var parse = require_parse();\n var diff = (version1, version2) => {\n const v1 = parse(version1, null, true);\n const v2 = parse(version2, null, true);\n const comparison = v1.compare(v2);\n if (comparison === 0) {\n return null;\n }\n const v1Higher = comparison > 0;\n const highVersion = v1Higher ? v1 : v2;\n const lowVersion = v1Higher ? v2 : v1;\n const highHasPre = !!highVersion.prerelease.length;\n const lowHasPre = !!lowVersion.prerelease.length;\n if (lowHasPre && !highHasPre) {\n if (!lowVersion.patch && !lowVersion.minor) {\n return \"major\";\n }\n if (lowVersion.compareMain(highVersion) === 0) {\n if (lowVersion.minor && !lowVersion.patch) {\n return \"minor\";\n }\n return \"patch\";\n }\n }\n const prefix = highHasPre ? \"pre\" : \"\";\n if (v1.major !== v2.major) {\n return prefix + \"major\";\n }\n if (v1.minor !== v2.minor) {\n return prefix + \"minor\";\n }\n if (v1.patch !== v2.patch) {\n return prefix + \"patch\";\n }\n return \"prerelease\";\n };\n module.exports = diff;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/major.js\nvar require_major = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/major.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var major = (a, loose) => new SemVer(a, loose).major;\n module.exports = major;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/minor.js\nvar require_minor = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/minor.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var minor = (a, loose) => new SemVer(a, loose).minor;\n module.exports = minor;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/patch.js\nvar require_patch = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/patch.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var patch = (a, loose) => new SemVer(a, loose).patch;\n module.exports = patch;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/prerelease.js\nvar require_prerelease = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/prerelease.js\"(exports, module) {\n \"use strict\";\n var parse = require_parse();\n var prerelease = (version, options) => {\n const parsed = parse(version, options);\n return parsed && parsed.prerelease.length ? parsed.prerelease : null;\n };\n module.exports = prerelease;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare.js\nvar require_compare = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var compare = (a, b, loose) => new SemVer(a, loose).compare(new SemVer(b, loose));\n module.exports = compare;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/rcompare.js\nvar require_rcompare = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/rcompare.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var rcompare = (a, b, loose) => compare(b, a, loose);\n module.exports = rcompare;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare-loose.js\nvar require_compare_loose = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare-loose.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var compareLoose = (a, b) => compare(a, b, true);\n module.exports = compareLoose;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare-build.js\nvar require_compare_build = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare-build.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var compareBuild = (a, b, loose) => {\n const versionA = new SemVer(a, loose);\n const versionB = new SemVer(b, loose);\n return versionA.compare(versionB) || versionA.compareBuild(versionB);\n };\n module.exports = compareBuild;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/sort.js\nvar require_sort = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/sort.js\"(exports, module) {\n \"use strict\";\n var compareBuild = require_compare_build();\n var sort = (list2, loose) => list2.sort((a, b) => compareBuild(a, b, loose));\n module.exports = sort;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/rsort.js\nvar require_rsort = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/rsort.js\"(exports, module) {\n \"use strict\";\n var compareBuild = require_compare_build();\n var rsort = (list2, loose) => list2.sort((a, b) => compareBuild(b, a, loose));\n module.exports = rsort;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/gt.js\nvar require_gt = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/gt.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var gt = (a, b, loose) => compare(a, b, loose) > 0;\n module.exports = gt;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/lt.js\nvar require_lt = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/lt.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var lt = (a, b, loose) => compare(a, b, loose) < 0;\n module.exports = lt;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/eq.js\nvar require_eq = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/eq.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var eq = (a, b, loose) => compare(a, b, loose) === 0;\n module.exports = eq;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/neq.js\nvar require_neq = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/neq.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var neq = (a, b, loose) => compare(a, b, loose) !== 0;\n module.exports = neq;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/gte.js\nvar require_gte = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/gte.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var gte = (a, b, loose) => compare(a, b, loose) >= 0;\n module.exports = gte;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/lte.js\nvar require_lte = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/lte.js\"(exports, module) {\n \"use strict\";\n var compare = require_compare();\n var lte = (a, b, loose) => compare(a, b, loose) <= 0;\n module.exports = lte;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/cmp.js\nvar require_cmp = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/cmp.js\"(exports, module) {\n \"use strict\";\n var eq = require_eq();\n var neq = require_neq();\n var gt = require_gt();\n var gte = require_gte();\n var lt = require_lt();\n var lte = require_lte();\n var cmp = (a, op, b, loose) => {\n switch (op) {\n case \"===\":\n if (typeof a === \"object\") {\n a = a.version;\n }\n if (typeof b === \"object\") {\n b = b.version;\n }\n return a === b;\n case \"!==\":\n if (typeof a === \"object\") {\n a = a.version;\n }\n if (typeof b === \"object\") {\n b = b.version;\n }\n return a !== b;\n case \"\":\n case \"=\":\n case \"==\":\n return eq(a, b, loose);\n case \"!=\":\n return neq(a, b, loose);\n case \">\":\n return gt(a, b, loose);\n case \">=\":\n return gte(a, b, loose);\n case \"<\":\n return lt(a, b, loose);\n case \"<=\":\n return lte(a, b, loose);\n default:\n throw new TypeError(`Invalid operator: ${op}`);\n }\n };\n module.exports = cmp;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/coerce.js\nvar require_coerce = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/coerce.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var parse = require_parse();\n var { safeRe: re, t } = require_re();\n var coerce = (version, options) => {\n if (version instanceof SemVer) {\n return version;\n }\n if (typeof version === \"number\") {\n version = String(version);\n }\n if (typeof version !== \"string\") {\n return null;\n }\n options = options || {};\n let match2 = null;\n if (!options.rtl) {\n match2 = version.match(options.includePrerelease ? re[t.COERCEFULL] : re[t.COERCE]);\n } else {\n const coerceRtlRegex = options.includePrerelease ? re[t.COERCERTLFULL] : re[t.COERCERTL];\n let next;\n while ((next = coerceRtlRegex.exec(version)) && (!match2 || match2.index + match2[0].length !== version.length)) {\n if (!match2 || next.index + next[0].length !== match2.index + match2[0].length) {\n match2 = next;\n }\n coerceRtlRegex.lastIndex = next.index + next[1].length + next[2].length;\n }\n coerceRtlRegex.lastIndex = -1;\n }\n if (match2 === null) {\n return null;\n }\n const major = match2[2];\n const minor = match2[3] || \"0\";\n const patch = match2[4] || \"0\";\n const prerelease = options.includePrerelease && match2[5] ? `-${match2[5]}` : \"\";\n const build = options.includePrerelease && match2[6] ? `+${match2[6]}` : \"\";\n return parse(`${major}.${minor}.${patch}${prerelease}${build}`, options);\n };\n module.exports = coerce;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/lrucache.js\nvar require_lrucache = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/lrucache.js\"(exports, module) {\n \"use strict\";\n var LRUCache = class {\n constructor() {\n this.max = 1e3;\n this.map = /* @__PURE__ */ new Map();\n }\n get(key) {\n const value = this.map.get(key);\n if (value === void 0) {\n return void 0;\n } else {\n this.map.delete(key);\n this.map.set(key, value);\n return value;\n }\n }\n delete(key) {\n return this.map.delete(key);\n }\n set(key, value) {\n const deleted = this.delete(key);\n if (!deleted && value !== void 0) {\n if (this.map.size >= this.max) {\n const firstKey = this.map.keys().next().value;\n this.delete(firstKey);\n }\n this.map.set(key, value);\n }\n return this;\n }\n };\n module.exports = LRUCache;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/range.js\nvar require_range = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/range.js\"(exports, module) {\n \"use strict\";\n var SPACE_CHARACTERS = /\\s+/g;\n var Range = class _Range {\n constructor(range, options) {\n options = parseOptions(options);\n if (range instanceof _Range) {\n if (range.loose === !!options.loose && range.includePrerelease === !!options.includePrerelease) {\n return range;\n } else {\n return new _Range(range.raw, options);\n }\n }\n if (range instanceof Comparator) {\n this.raw = range.value;\n this.set = [[range]];\n this.formatted = void 0;\n return this;\n }\n this.options = options;\n this.loose = !!options.loose;\n this.includePrerelease = !!options.includePrerelease;\n this.raw = range.trim().replace(SPACE_CHARACTERS, \" \");\n this.set = this.raw.split(\"||\").map((r) => this.parseRange(r.trim())).filter((c) => c.length);\n if (!this.set.length) {\n throw new TypeError(`Invalid SemVer Range: ${this.raw}`);\n }\n if (this.set.length > 1) {\n const first = this.set[0];\n this.set = this.set.filter((c) => !isNullSet(c[0]));\n if (this.set.length === 0) {\n this.set = [first];\n } else if (this.set.length > 1) {\n for (const c of this.set) {\n if (c.length === 1 && isAny(c[0])) {\n this.set = [c];\n break;\n }\n }\n }\n }\n this.formatted = void 0;\n }\n get range() {\n if (this.formatted === void 0) {\n this.formatted = \"\";\n for (let i = 0; i < this.set.length; i++) {\n if (i > 0) {\n this.formatted += \"||\";\n }\n const comps = this.set[i];\n for (let k = 0; k < comps.length; k++) {\n if (k > 0) {\n this.formatted += \" \";\n }\n this.formatted += comps[k].toString().trim();\n }\n }\n }\n return this.formatted;\n }\n format() {\n return this.range;\n }\n toString() {\n return this.range;\n }\n parseRange(range) {\n const memoOpts = (this.options.includePrerelease && FLAG_INCLUDE_PRERELEASE) | (this.options.loose && FLAG_LOOSE);\n const memoKey = memoOpts + \":\" + range;\n const cached = cache.get(memoKey);\n if (cached) {\n return cached;\n }\n const loose = this.options.loose;\n const hr2 = loose ? re[t.HYPHENRANGELOOSE] : re[t.HYPHENRANGE];\n range = range.replace(hr2, hyphenReplace(this.options.includePrerelease));\n debug(\"hyphen replace\", range);\n range = range.replace(re[t.COMPARATORTRIM], comparatorTrimReplace);\n debug(\"comparator trim\", range);\n range = range.replace(re[t.TILDETRIM], tildeTrimReplace);\n debug(\"tilde trim\", range);\n range = range.replace(re[t.CARETTRIM], caretTrimReplace);\n debug(\"caret trim\", range);\n let rangeList = range.split(\" \").map((comp) => parseComparator(comp, this.options)).join(\" \").split(/\\s+/).map((comp) => replaceGTE0(comp, this.options));\n if (loose) {\n rangeList = rangeList.filter((comp) => {\n debug(\"loose invalid filter\", comp, this.options);\n return !!comp.match(re[t.COMPARATORLOOSE]);\n });\n }\n debug(\"range list\", rangeList);\n const rangeMap = /* @__PURE__ */ new Map();\n const comparators = rangeList.map((comp) => new Comparator(comp, this.options));\n for (const comp of comparators) {\n if (isNullSet(comp)) {\n return [comp];\n }\n rangeMap.set(comp.value, comp);\n }\n if (rangeMap.size > 1 && rangeMap.has(\"\")) {\n rangeMap.delete(\"\");\n }\n const result = [...rangeMap.values()];\n cache.set(memoKey, result);\n return result;\n }\n intersects(range, options) {\n if (!(range instanceof _Range)) {\n throw new TypeError(\"a Range is required\");\n }\n return this.set.some((thisComparators) => {\n return isSatisfiable(thisComparators, options) && range.set.some((rangeComparators) => {\n return isSatisfiable(rangeComparators, options) && thisComparators.every((thisComparator) => {\n return rangeComparators.every((rangeComparator) => {\n return thisComparator.intersects(rangeComparator, options);\n });\n });\n });\n });\n }\n // if ANY of the sets match ALL of its comparators, then pass\n test(version) {\n if (!version) {\n return false;\n }\n if (typeof version === \"string\") {\n try {\n version = new SemVer(version, this.options);\n } catch (er) {\n return false;\n }\n }\n for (let i = 0; i < this.set.length; i++) {\n if (testSet(this.set[i], version, this.options)) {\n return true;\n }\n }\n return false;\n }\n };\n module.exports = Range;\n var LRU = require_lrucache();\n var cache = new LRU();\n var parseOptions = require_parse_options();\n var Comparator = require_comparator();\n var debug = require_debug();\n var SemVer = require_semver();\n var {\n safeRe: re,\n t,\n comparatorTrimReplace,\n tildeTrimReplace,\n caretTrimReplace\n } = require_re();\n var { FLAG_INCLUDE_PRERELEASE, FLAG_LOOSE } = require_constants();\n var isNullSet = (c) => c.value === \"<0.0.0-0\";\n var isAny = (c) => c.value === \"\";\n var isSatisfiable = (comparators, options) => {\n let result = true;\n const remainingComparators = comparators.slice();\n let testComparator = remainingComparators.pop();\n while (result && remainingComparators.length) {\n result = remainingComparators.every((otherComparator) => {\n return testComparator.intersects(otherComparator, options);\n });\n testComparator = remainingComparators.pop();\n }\n return result;\n };\n var parseComparator = (comp, options) => {\n comp = comp.replace(re[t.BUILD], \"\");\n debug(\"comp\", comp, options);\n comp = replaceCarets(comp, options);\n debug(\"caret\", comp);\n comp = replaceTildes(comp, options);\n debug(\"tildes\", comp);\n comp = replaceXRanges(comp, options);\n debug(\"xrange\", comp);\n comp = replaceStars(comp, options);\n debug(\"stars\", comp);\n return comp;\n };\n var isX = (id) => !id || id.toLowerCase() === \"x\" || id === \"*\";\n var replaceTildes = (comp, options) => {\n return comp.trim().split(/\\s+/).map((c) => replaceTilde(c, options)).join(\" \");\n };\n var replaceTilde = (comp, options) => {\n const r = options.loose ? re[t.TILDELOOSE] : re[t.TILDE];\n return comp.replace(r, (_, M, m, p, pr) => {\n debug(\"tilde\", comp, _, M, m, p, pr);\n let ret;\n if (isX(M)) {\n ret = \"\";\n } else if (isX(m)) {\n ret = `>=${M}.0.0 <${+M + 1}.0.0-0`;\n } else if (isX(p)) {\n ret = `>=${M}.${m}.0 <${M}.${+m + 1}.0-0`;\n } else if (pr) {\n debug(\"replaceTilde pr\", pr);\n ret = `>=${M}.${m}.${p}-${pr} <${M}.${+m + 1}.0-0`;\n } else {\n ret = `>=${M}.${m}.${p} <${M}.${+m + 1}.0-0`;\n }\n debug(\"tilde return\", ret);\n return ret;\n });\n };\n var replaceCarets = (comp, options) => {\n return comp.trim().split(/\\s+/).map((c) => replaceCaret(c, options)).join(\" \");\n };\n var replaceCaret = (comp, options) => {\n debug(\"caret\", comp, options);\n const r = options.loose ? re[t.CARETLOOSE] : re[t.CARET];\n const z = options.includePrerelease ? \"-0\" : \"\";\n return comp.replace(r, (_, M, m, p, pr) => {\n debug(\"caret\", comp, _, M, m, p, pr);\n let ret;\n if (isX(M)) {\n ret = \"\";\n } else if (isX(m)) {\n ret = `>=${M}.0.0${z} <${+M + 1}.0.0-0`;\n } else if (isX(p)) {\n if (M === \"0\") {\n ret = `>=${M}.${m}.0${z} <${M}.${+m + 1}.0-0`;\n } else {\n ret = `>=${M}.${m}.0${z} <${+M + 1}.0.0-0`;\n }\n } else if (pr) {\n debug(\"replaceCaret pr\", pr);\n if (M === \"0\") {\n if (m === \"0\") {\n ret = `>=${M}.${m}.${p}-${pr} <${M}.${m}.${+p + 1}-0`;\n } else {\n ret = `>=${M}.${m}.${p}-${pr} <${M}.${+m + 1}.0-0`;\n }\n } else {\n ret = `>=${M}.${m}.${p}-${pr} <${+M + 1}.0.0-0`;\n }\n } else {\n debug(\"no pr\");\n if (M === \"0\") {\n if (m === \"0\") {\n ret = `>=${M}.${m}.${p}${z} <${M}.${m}.${+p + 1}-0`;\n } else {\n ret = `>=${M}.${m}.${p}${z} <${M}.${+m + 1}.0-0`;\n }\n } else {\n ret = `>=${M}.${m}.${p} <${+M + 1}.0.0-0`;\n }\n }\n debug(\"caret return\", ret);\n return ret;\n });\n };\n var replaceXRanges = (comp, options) => {\n debug(\"replaceXRanges\", comp, options);\n return comp.split(/\\s+/).map((c) => replaceXRange(c, options)).join(\" \");\n };\n var replaceXRange = (comp, options) => {\n comp = comp.trim();\n const r = options.loose ? re[t.XRANGELOOSE] : re[t.XRANGE];\n return comp.replace(r, (ret, gtlt, M, m, p, pr) => {\n debug(\"xRange\", comp, ret, gtlt, M, m, p, pr);\n const xM = isX(M);\n const xm = xM || isX(m);\n const xp = xm || isX(p);\n const anyX = xp;\n if (gtlt === \"=\" && anyX) {\n gtlt = \"\";\n }\n pr = options.includePrerelease ? \"-0\" : \"\";\n if (xM) {\n if (gtlt === \">\" || gtlt === \"<\") {\n ret = \"<0.0.0-0\";\n } else {\n ret = \"*\";\n }\n } else if (gtlt && anyX) {\n if (xm) {\n m = 0;\n }\n p = 0;\n if (gtlt === \">\") {\n gtlt = \">=\";\n if (xm) {\n M = +M + 1;\n m = 0;\n p = 0;\n } else {\n m = +m + 1;\n p = 0;\n }\n } else if (gtlt === \"<=\") {\n gtlt = \"<\";\n if (xm) {\n M = +M + 1;\n } else {\n m = +m + 1;\n }\n }\n if (gtlt === \"<\") {\n pr = \"-0\";\n }\n ret = `${gtlt + M}.${m}.${p}${pr}`;\n } else if (xm) {\n ret = `>=${M}.0.0${pr} <${+M + 1}.0.0-0`;\n } else if (xp) {\n ret = `>=${M}.${m}.0${pr} <${M}.${+m + 1}.0-0`;\n }\n debug(\"xRange return\", ret);\n return ret;\n });\n };\n var replaceStars = (comp, options) => {\n debug(\"replaceStars\", comp, options);\n return comp.trim().replace(re[t.STAR], \"\");\n };\n var replaceGTE0 = (comp, options) => {\n debug(\"replaceGTE0\", comp, options);\n return comp.trim().replace(re[options.includePrerelease ? t.GTE0PRE : t.GTE0], \"\");\n };\n var hyphenReplace = (incPr) => ($0, from, fM, fm, fp, fpr, fb, to, tM, tm, tp, tpr) => {\n if (isX(fM)) {\n from = \"\";\n } else if (isX(fm)) {\n from = `>=${fM}.0.0${incPr ? \"-0\" : \"\"}`;\n } else if (isX(fp)) {\n from = `>=${fM}.${fm}.0${incPr ? \"-0\" : \"\"}`;\n } else if (fpr) {\n from = `>=${from}`;\n } else {\n from = `>=${from}${incPr ? \"-0\" : \"\"}`;\n }\n if (isX(tM)) {\n to = \"\";\n } else if (isX(tm)) {\n to = `<${+tM + 1}.0.0-0`;\n } else if (isX(tp)) {\n to = `<${tM}.${+tm + 1}.0-0`;\n } else if (tpr) {\n to = `<=${tM}.${tm}.${tp}-${tpr}`;\n } else if (incPr) {\n to = `<${tM}.${tm}.${+tp + 1}-0`;\n } else {\n to = `<=${to}`;\n }\n return `${from} ${to}`.trim();\n };\n var testSet = (set2, version, options) => {\n for (let i = 0; i < set2.length; i++) {\n if (!set2[i].test(version)) {\n return false;\n }\n }\n if (version.prerelease.length && !options.includePrerelease) {\n for (let i = 0; i < set2.length; i++) {\n debug(set2[i].semver);\n if (set2[i].semver === Comparator.ANY) {\n continue;\n }\n if (set2[i].semver.prerelease.length > 0) {\n const allowed = set2[i].semver;\n if (allowed.major === version.major && allowed.minor === version.minor && allowed.patch === version.patch) {\n return true;\n }\n }\n }\n return false;\n }\n return true;\n };\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/comparator.js\nvar require_comparator = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/comparator.js\"(exports, module) {\n \"use strict\";\n var ANY = /* @__PURE__ */ Symbol(\"SemVer ANY\");\n var Comparator = class _Comparator {\n static get ANY() {\n return ANY;\n }\n constructor(comp, options) {\n options = parseOptions(options);\n if (comp instanceof _Comparator) {\n if (comp.loose === !!options.loose) {\n return comp;\n } else {\n comp = comp.value;\n }\n }\n comp = comp.trim().split(/\\s+/).join(\" \");\n debug(\"comparator\", comp, options);\n this.options = options;\n this.loose = !!options.loose;\n this.parse(comp);\n if (this.semver === ANY) {\n this.value = \"\";\n } else {\n this.value = this.operator + this.semver.version;\n }\n debug(\"comp\", this);\n }\n parse(comp) {\n const r = this.options.loose ? re[t.COMPARATORLOOSE] : re[t.COMPARATOR];\n const m = comp.match(r);\n if (!m) {\n throw new TypeError(`Invalid comparator: ${comp}`);\n }\n this.operator = m[1] !== void 0 ? m[1] : \"\";\n if (this.operator === \"=\") {\n this.operator = \"\";\n }\n if (!m[2]) {\n this.semver = ANY;\n } else {\n this.semver = new SemVer(m[2], this.options.loose);\n }\n }\n toString() {\n return this.value;\n }\n test(version) {\n debug(\"Comparator.test\", version, this.options.loose);\n if (this.semver === ANY || version === ANY) {\n return true;\n }\n if (typeof version === \"string\") {\n try {\n version = new SemVer(version, this.options);\n } catch (er) {\n return false;\n }\n }\n return cmp(version, this.operator, this.semver, this.options);\n }\n intersects(comp, options) {\n if (!(comp instanceof _Comparator)) {\n throw new TypeError(\"a Comparator is required\");\n }\n if (this.operator === \"\") {\n if (this.value === \"\") {\n return true;\n }\n return new Range(comp.value, options).test(this.value);\n } else if (comp.operator === \"\") {\n if (comp.value === \"\") {\n return true;\n }\n return new Range(this.value, options).test(comp.semver);\n }\n options = parseOptions(options);\n if (options.includePrerelease && (this.value === \"<0.0.0-0\" || comp.value === \"<0.0.0-0\")) {\n return false;\n }\n if (!options.includePrerelease && (this.value.startsWith(\"<0.0.0\") || comp.value.startsWith(\"<0.0.0\"))) {\n return false;\n }\n if (this.operator.startsWith(\">\") && comp.operator.startsWith(\">\")) {\n return true;\n }\n if (this.operator.startsWith(\"<\") && comp.operator.startsWith(\"<\")) {\n return true;\n }\n if (this.semver.version === comp.semver.version && this.operator.includes(\"=\") && comp.operator.includes(\"=\")) {\n return true;\n }\n if (cmp(this.semver, \"<\", comp.semver, options) && this.operator.startsWith(\">\") && comp.operator.startsWith(\"<\")) {\n return true;\n }\n if (cmp(this.semver, \">\", comp.semver, options) && this.operator.startsWith(\"<\") && comp.operator.startsWith(\">\")) {\n return true;\n }\n return false;\n }\n };\n module.exports = Comparator;\n var parseOptions = require_parse_options();\n var { safeRe: re, t } = require_re();\n var cmp = require_cmp();\n var debug = require_debug();\n var SemVer = require_semver();\n var Range = require_range();\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/satisfies.js\nvar require_satisfies = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/satisfies.js\"(exports, module) {\n \"use strict\";\n var Range = require_range();\n var satisfies = (version, range, options) => {\n try {\n range = new Range(range, options);\n } catch (er) {\n return false;\n }\n return range.test(version);\n };\n module.exports = satisfies;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/to-comparators.js\nvar require_to_comparators = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/to-comparators.js\"(exports, module) {\n \"use strict\";\n var Range = require_range();\n var toComparators = (range, options) => new Range(range, options).set.map((comp) => comp.map((c) => c.value).join(\" \").trim().split(\" \"));\n module.exports = toComparators;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/max-satisfying.js\nvar require_max_satisfying = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/max-satisfying.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var Range = require_range();\n var maxSatisfying = (versions, range, options) => {\n let max2 = null;\n let maxSV = null;\n let rangeObj = null;\n try {\n rangeObj = new Range(range, options);\n } catch (er) {\n return null;\n }\n versions.forEach((v) => {\n if (rangeObj.test(v)) {\n if (!max2 || maxSV.compare(v) === -1) {\n max2 = v;\n maxSV = new SemVer(max2, options);\n }\n }\n });\n return max2;\n };\n module.exports = maxSatisfying;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/min-satisfying.js\nvar require_min_satisfying = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/min-satisfying.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var Range = require_range();\n var minSatisfying = (versions, range, options) => {\n let min = null;\n let minSV = null;\n let rangeObj = null;\n try {\n rangeObj = new Range(range, options);\n } catch (er) {\n return null;\n }\n versions.forEach((v) => {\n if (rangeObj.test(v)) {\n if (!min || minSV.compare(v) === 1) {\n min = v;\n minSV = new SemVer(min, options);\n }\n }\n });\n return min;\n };\n module.exports = minSatisfying;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/min-version.js\nvar require_min_version = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/min-version.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var Range = require_range();\n var gt = require_gt();\n var minVersion = (range, loose) => {\n range = new Range(range, loose);\n let minver = new SemVer(\"0.0.0\");\n if (range.test(minver)) {\n return minver;\n }\n minver = new SemVer(\"0.0.0-0\");\n if (range.test(minver)) {\n return minver;\n }\n minver = null;\n for (let i = 0; i < range.set.length; ++i) {\n const comparators = range.set[i];\n let setMin = null;\n comparators.forEach((comparator) => {\n const compver = new SemVer(comparator.semver.version);\n switch (comparator.operator) {\n case \">\":\n if (compver.prerelease.length === 0) {\n compver.patch++;\n } else {\n compver.prerelease.push(0);\n }\n compver.raw = compver.format();\n /* fallthrough */\n case \"\":\n case \">=\":\n if (!setMin || gt(compver, setMin)) {\n setMin = compver;\n }\n break;\n case \"<\":\n case \"<=\":\n break;\n /* istanbul ignore next */\n default:\n throw new Error(`Unexpected operation: ${comparator.operator}`);\n }\n });\n if (setMin && (!minver || gt(minver, setMin))) {\n minver = setMin;\n }\n }\n if (minver && range.test(minver)) {\n return minver;\n }\n return null;\n };\n module.exports = minVersion;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/valid.js\nvar require_valid2 = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/valid.js\"(exports, module) {\n \"use strict\";\n var Range = require_range();\n var validRange = (range, options) => {\n try {\n return new Range(range, options).range || \"*\";\n } catch (er) {\n return null;\n }\n };\n module.exports = validRange;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/outside.js\nvar require_outside = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/outside.js\"(exports, module) {\n \"use strict\";\n var SemVer = require_semver();\n var Comparator = require_comparator();\n var { ANY } = Comparator;\n var Range = require_range();\n var satisfies = require_satisfies();\n var gt = require_gt();\n var lt = require_lt();\n var lte = require_lte();\n var gte = require_gte();\n var outside = (version, range, hilo, options) => {\n version = new SemVer(version, options);\n range = new Range(range, options);\n let gtfn, ltefn, ltfn, comp, ecomp;\n switch (hilo) {\n case \">\":\n gtfn = gt;\n ltefn = lte;\n ltfn = lt;\n comp = \">\";\n ecomp = \">=\";\n break;\n case \"<\":\n gtfn = lt;\n ltefn = gte;\n ltfn = gt;\n comp = \"<\";\n ecomp = \"<=\";\n break;\n default:\n throw new TypeError('Must provide a hilo val of \"<\" or \">\"');\n }\n if (satisfies(version, range, options)) {\n return false;\n }\n for (let i = 0; i < range.set.length; ++i) {\n const comparators = range.set[i];\n let high = null;\n let low = null;\n comparators.forEach((comparator) => {\n if (comparator.semver === ANY) {\n comparator = new Comparator(\">=0.0.0\");\n }\n high = high || comparator;\n low = low || comparator;\n if (gtfn(comparator.semver, high.semver, options)) {\n high = comparator;\n } else if (ltfn(comparator.semver, low.semver, options)) {\n low = comparator;\n }\n });\n if (high.operator === comp || high.operator === ecomp) {\n return false;\n }\n if ((!low.operator || low.operator === comp) && ltefn(version, low.semver)) {\n return false;\n } else if (low.operator === ecomp && ltfn(version, low.semver)) {\n return false;\n }\n }\n return true;\n };\n module.exports = outside;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/gtr.js\nvar require_gtr = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/gtr.js\"(exports, module) {\n \"use strict\";\n var outside = require_outside();\n var gtr = (version, range, options) => outside(version, range, \">\", options);\n module.exports = gtr;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/ltr.js\nvar require_ltr = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/ltr.js\"(exports, module) {\n \"use strict\";\n var outside = require_outside();\n var ltr = (version, range, options) => outside(version, range, \"<\", options);\n module.exports = ltr;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/intersects.js\nvar require_intersects = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/intersects.js\"(exports, module) {\n \"use strict\";\n var Range = require_range();\n var intersects = (r1, r2, options) => {\n r1 = new Range(r1, options);\n r2 = new Range(r2, options);\n return r1.intersects(r2, options);\n };\n module.exports = intersects;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/simplify.js\nvar require_simplify = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/simplify.js\"(exports, module) {\n \"use strict\";\n var satisfies = require_satisfies();\n var compare = require_compare();\n module.exports = (versions, range, options) => {\n const set2 = [];\n let first = null;\n let prev = null;\n const v = versions.sort((a, b) => compare(a, b, options));\n for (const version of v) {\n const included = satisfies(version, range, options);\n if (included) {\n prev = version;\n if (!first) {\n first = version;\n }\n } else {\n if (prev) {\n set2.push([first, prev]);\n }\n prev = null;\n first = null;\n }\n }\n if (first) {\n set2.push([first, null]);\n }\n const ranges = [];\n for (const [min, max2] of set2) {\n if (min === max2) {\n ranges.push(min);\n } else if (!max2 && min === v[0]) {\n ranges.push(\"*\");\n } else if (!max2) {\n ranges.push(`>=${min}`);\n } else if (min === v[0]) {\n ranges.push(`<=${max2}`);\n } else {\n ranges.push(`${min} - ${max2}`);\n }\n }\n const simplified = ranges.join(\" || \");\n const original = typeof range.raw === \"string\" ? range.raw : String(range);\n return simplified.length < original.length ? simplified : range;\n };\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/subset.js\nvar require_subset = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/subset.js\"(exports, module) {\n \"use strict\";\n var Range = require_range();\n var Comparator = require_comparator();\n var { ANY } = Comparator;\n var satisfies = require_satisfies();\n var compare = require_compare();\n var subset = (sub, dom, options = {}) => {\n if (sub === dom) {\n return true;\n }\n sub = new Range(sub, options);\n dom = new Range(dom, options);\n let sawNonNull = false;\n OUTER: for (const simpleSub of sub.set) {\n for (const simpleDom of dom.set) {\n const isSub = simpleSubset(simpleSub, simpleDom, options);\n sawNonNull = sawNonNull || isSub !== null;\n if (isSub) {\n continue OUTER;\n }\n }\n if (sawNonNull) {\n return false;\n }\n }\n return true;\n };\n var minimumVersionWithPreRelease = [new Comparator(\">=0.0.0-0\")];\n var minimumVersion = [new Comparator(\">=0.0.0\")];\n var simpleSubset = (sub, dom, options) => {\n if (sub === dom) {\n return true;\n }\n if (sub.length === 1 && sub[0].semver === ANY) {\n if (dom.length === 1 && dom[0].semver === ANY) {\n return true;\n } else if (options.includePrerelease) {\n sub = minimumVersionWithPreRelease;\n } else {\n sub = minimumVersion;\n }\n }\n if (dom.length === 1 && dom[0].semver === ANY) {\n if (options.includePrerelease) {\n return true;\n } else {\n dom = minimumVersion;\n }\n }\n const eqSet = /* @__PURE__ */ new Set();\n let gt, lt;\n for (const c of sub) {\n if (c.operator === \">\" || c.operator === \">=\") {\n gt = higherGT(gt, c, options);\n } else if (c.operator === \"<\" || c.operator === \"<=\") {\n lt = lowerLT(lt, c, options);\n } else {\n eqSet.add(c.semver);\n }\n }\n if (eqSet.size > 1) {\n return null;\n }\n let gtltComp;\n if (gt && lt) {\n gtltComp = compare(gt.semver, lt.semver, options);\n if (gtltComp > 0) {\n return null;\n } else if (gtltComp === 0 && (gt.operator !== \">=\" || lt.operator !== \"<=\")) {\n return null;\n }\n }\n for (const eq of eqSet) {\n if (gt && !satisfies(eq, String(gt), options)) {\n return null;\n }\n if (lt && !satisfies(eq, String(lt), options)) {\n return null;\n }\n for (const c of dom) {\n if (!satisfies(eq, String(c), options)) {\n return false;\n }\n }\n return true;\n }\n let higher, lower;\n let hasDomLT, hasDomGT;\n let needDomLTPre = lt && !options.includePrerelease && lt.semver.prerelease.length ? lt.semver : false;\n let needDomGTPre = gt && !options.includePrerelease && gt.semver.prerelease.length ? gt.semver : false;\n if (needDomLTPre && needDomLTPre.prerelease.length === 1 && lt.operator === \"<\" && needDomLTPre.prerelease[0] === 0) {\n needDomLTPre = false;\n }\n for (const c of dom) {\n hasDomGT = hasDomGT || c.operator === \">\" || c.operator === \">=\";\n hasDomLT = hasDomLT || c.operator === \"<\" || c.operator === \"<=\";\n if (gt) {\n if (needDomGTPre) {\n if (c.semver.prerelease && c.semver.prerelease.length && c.semver.major === needDomGTPre.major && c.semver.minor === needDomGTPre.minor && c.semver.patch === needDomGTPre.patch) {\n needDomGTPre = false;\n }\n }\n if (c.operator === \">\" || c.operator === \">=\") {\n higher = higherGT(gt, c, options);\n if (higher === c && higher !== gt) {\n return false;\n }\n } else if (gt.operator === \">=\" && !satisfies(gt.semver, String(c), options)) {\n return false;\n }\n }\n if (lt) {\n if (needDomLTPre) {\n if (c.semver.prerelease && c.semver.prerelease.length && c.semver.major === needDomLTPre.major && c.semver.minor === needDomLTPre.minor && c.semver.patch === needDomLTPre.patch) {\n needDomLTPre = false;\n }\n }\n if (c.operator === \"<\" || c.operator === \"<=\") {\n lower = lowerLT(lt, c, options);\n if (lower === c && lower !== lt) {\n return false;\n }\n } else if (lt.operator === \"<=\" && !satisfies(lt.semver, String(c), options)) {\n return false;\n }\n }\n if (!c.operator && (lt || gt) && gtltComp !== 0) {\n return false;\n }\n }\n if (gt && hasDomLT && !lt && gtltComp !== 0) {\n return false;\n }\n if (lt && hasDomGT && !gt && gtltComp !== 0) {\n return false;\n }\n if (needDomGTPre || needDomLTPre) {\n return false;\n }\n return true;\n };\n var higherGT = (a, b, options) => {\n if (!a) {\n return b;\n }\n const comp = compare(a.semver, b.semver, options);\n return comp > 0 ? a : comp < 0 ? b : b.operator === \">\" && a.operator === \">=\" ? b : a;\n };\n var lowerLT = (a, b, options) => {\n if (!a) {\n return b;\n }\n const comp = compare(a.semver, b.semver, options);\n return comp < 0 ? a : comp > 0 ? b : b.operator === \"<\" && a.operator === \"<=\" ? b : a;\n };\n module.exports = subset;\n }\n});\n\n// node_modules/.pnpm/semver@7.7.3/node_modules/semver/index.js\nvar require_semver2 = __commonJS({\n \"node_modules/.pnpm/semver@7.7.3/node_modules/semver/index.js\"(exports, module) {\n \"use strict\";\n var internalRe = require_re();\n var constants = require_constants();\n var SemVer = require_semver();\n var identifiers = require_identifiers();\n var parse = require_parse();\n var valid = require_valid();\n var clean2 = require_clean();\n var inc = require_inc();\n var diff = require_diff();\n var major = require_major();\n var minor = require_minor();\n var patch = require_patch();\n var prerelease = require_prerelease();\n var compare = require_compare();\n var rcompare = require_rcompare();\n var compareLoose = require_compare_loose();\n var compareBuild = require_compare_build();\n var sort = require_sort();\n var rsort = require_rsort();\n var gt = require_gt();\n var lt = require_lt();\n var eq = require_eq();\n var neq = require_neq();\n var gte = require_gte();\n var lte = require_lte();\n var cmp = require_cmp();\n var coerce = require_coerce();\n var Comparator = require_comparator();\n var Range = require_range();\n var satisfies = require_satisfies();\n var toComparators = require_to_comparators();\n var maxSatisfying = require_max_satisfying();\n var minSatisfying = require_min_satisfying();\n var minVersion = require_min_version();\n var validRange = require_valid2();\n var outside = require_outside();\n var gtr = require_gtr();\n var ltr = require_ltr();\n var intersects = require_intersects();\n var simplifyRange = require_simplify();\n var subset = require_subset();\n module.exports = {\n parse,\n valid,\n clean: clean2,\n inc,\n diff,\n major,\n minor,\n patch,\n prerelease,\n compare,\n rcompare,\n compareLoose,\n compareBuild,\n sort,\n rsort,\n gt,\n lt,\n eq,\n neq,\n gte,\n lte,\n cmp,\n coerce,\n Comparator,\n Range,\n satisfies,\n toComparators,\n maxSatisfying,\n minSatisfying,\n minVersion,\n validRange,\n outside,\n gtr,\n ltr,\n intersects,\n simplifyRange,\n subset,\n SemVer,\n re: internalRe.re,\n src: internalRe.src,\n tokens: internalRe.t,\n SEMVER_SPEC_VERSION: constants.SEMVER_SPEC_VERSION,\n RELEASE_TYPES: constants.RELEASE_TYPES,\n compareIdentifiers: identifiers.compareIdentifiers,\n rcompareIdentifiers: identifiers.rcompareIdentifiers\n };\n }\n});\n\n// node_modules/.pnpm/crc-32@1.2.2/node_modules/crc-32/crc32.js\nvar require_crc32 = __commonJS({\n \"node_modules/.pnpm/crc-32@1.2.2/node_modules/crc-32/crc32.js\"(exports) {\n var CRC322;\n (function(factory) {\n if (typeof DO_NOT_EXPORT_CRC === \"undefined\") {\n if (\"object\" === typeof exports) {\n factory(exports);\n } else if (\"function\" === typeof define && define.amd) {\n define(function() {\n var module2 = {};\n factory(module2);\n return module2;\n });\n } else {\n factory(CRC322 = {});\n }\n } else {\n factory(CRC322 = {});\n }\n })(function(CRC323) {\n CRC323.version = \"1.2.2\";\n function signed_crc_table() {\n var c = 0, table2 = new Array(256);\n for (var n = 0; n != 256; ++n) {\n c = n;\n c = c & 1 ? -306674912 ^ c >>> 1 : c >>> 1;\n c = c & 1 ? -306674912 ^ c >>> 1 : c >>> 1;\n c = c & 1 ? -306674912 ^ c >>> 1 : c >>> 1;\n c = c & 1 ? -306674912 ^ c >>> 1 : c >>> 1;\n c = c & 1 ? -306674912 ^ c >>> 1 : c >>> 1;\n c = c & 1 ? -306674912 ^ c >>> 1 : c >>> 1;\n c = c & 1 ? -306674912 ^ c >>> 1 : c >>> 1;\n c = c & 1 ? -306674912 ^ c >>> 1 : c >>> 1;\n table2[n] = c;\n }\n return typeof Int32Array !== \"undefined\" ? new Int32Array(table2) : table2;\n }\n var T0 = signed_crc_table();\n function slice_by_16_tables(T) {\n var c = 0, v = 0, n = 0, table2 = typeof Int32Array !== \"undefined\" ? new Int32Array(4096) : new Array(4096);\n for (n = 0; n != 256; ++n) table2[n] = T[n];\n for (n = 0; n != 256; ++n) {\n v = T[n];\n for (c = 256 + n; c < 4096; c += 256) v = table2[c] = v >>> 8 ^ T[v & 255];\n }\n var out = [];\n for (n = 1; n != 16; ++n) out[n - 1] = typeof Int32Array !== \"undefined\" ? table2.subarray(n * 256, n * 256 + 256) : table2.slice(n * 256, n * 256 + 256);\n return out;\n }\n var TT = slice_by_16_tables(T0);\n var T1 = TT[0], T2 = TT[1], T3 = TT[2], T4 = TT[3], T5 = TT[4];\n var T6 = TT[5], T7 = TT[6], T8 = TT[7], T9 = TT[8], Ta = TT[9];\n var Tb = TT[10], Tc = TT[11], Td = TT[12], Te = TT[13], Tf = TT[14];\n function crc32_bstr(bstr, seed) {\n var C = seed ^ -1;\n for (var i = 0, L = bstr.length; i < L; ) C = C >>> 8 ^ T0[(C ^ bstr.charCodeAt(i++)) & 255];\n return ~C;\n }\n function crc32_buf(B, seed) {\n var C = seed ^ -1, L = B.length - 15, i = 0;\n for (; i < L; ) C = Tf[B[i++] ^ C & 255] ^ Te[B[i++] ^ C >> 8 & 255] ^ Td[B[i++] ^ C >> 16 & 255] ^ Tc[B[i++] ^ C >>> 24] ^ Tb[B[i++]] ^ Ta[B[i++]] ^ T9[B[i++]] ^ T8[B[i++]] ^ T7[B[i++]] ^ T6[B[i++]] ^ T5[B[i++]] ^ T4[B[i++]] ^ T3[B[i++]] ^ T2[B[i++]] ^ T1[B[i++]] ^ T0[B[i++]];\n L += 15;\n while (i < L) C = C >>> 8 ^ T0[(C ^ B[i++]) & 255];\n return ~C;\n }\n function crc32_str(str, seed) {\n var C = seed ^ -1;\n for (var i = 0, L = str.length, c = 0, d = 0; i < L; ) {\n c = str.charCodeAt(i++);\n if (c < 128) {\n C = C >>> 8 ^ T0[(C ^ c) & 255];\n } else if (c < 2048) {\n C = C >>> 8 ^ T0[(C ^ (192 | c >> 6 & 31)) & 255];\n C = C >>> 8 ^ T0[(C ^ (128 | c & 63)) & 255];\n } else if (c >= 55296 && c < 57344) {\n c = (c & 1023) + 64;\n d = str.charCodeAt(i++) & 1023;\n C = C >>> 8 ^ T0[(C ^ (240 | c >> 8 & 7)) & 255];\n C = C >>> 8 ^ T0[(C ^ (128 | c >> 2 & 63)) & 255];\n C = C >>> 8 ^ T0[(C ^ (128 | d >> 6 & 15 | (c & 3) << 4)) & 255];\n C = C >>> 8 ^ T0[(C ^ (128 | d & 63)) & 255];\n } else {\n C = C >>> 8 ^ T0[(C ^ (224 | c >> 12 & 15)) & 255];\n C = C >>> 8 ^ T0[(C ^ (128 | c >> 6 & 63)) & 255];\n C = C >>> 8 ^ T0[(C ^ (128 | c & 63)) & 255];\n }\n }\n return ~C;\n }\n CRC323.table = T0;\n CRC323.bstr = crc32_bstr;\n CRC323.buf = crc32_buf;\n CRC323.str = crc32_str;\n });\n }\n});\n\n// apps/ecosystem-certifier/fixtures/flagship/knowledge-pack-entry.ts\nvar import_base64_js = __toESM(require_base64_js(), 1);\n\n// node_modules/.pnpm/fflate@0.8.2/node_modules/fflate/esm/browser.js\nvar u8 = Uint8Array;\nvar u16 = Uint16Array;\nvar i32 = Int32Array;\nvar fleb = new u8([\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 0,\n 1,\n 1,\n 1,\n 1,\n 2,\n 2,\n 2,\n 2,\n 3,\n 3,\n 3,\n 3,\n 4,\n 4,\n 4,\n 4,\n 5,\n 5,\n 5,\n 5,\n 0,\n /* unused */\n 0,\n 0,\n /* impossible */\n 0\n]);\nvar fdeb = new u8([\n 0,\n 0,\n 0,\n 0,\n 1,\n 1,\n 2,\n 2,\n 3,\n 3,\n 4,\n 4,\n 5,\n 5,\n 6,\n 6,\n 7,\n 7,\n 8,\n 8,\n 9,\n 9,\n 10,\n 10,\n 11,\n 11,\n 12,\n 12,\n 13,\n 13,\n /* unused */\n 0,\n 0\n]);\nvar clim = new u8([16, 17, 18, 0, 8, 7, 9, 6, 10, 5, 11, 4, 12, 3, 13, 2, 14, 1, 15]);\nvar freb = function(eb, start) {\n var b = new u16(31);\n for (var i = 0; i < 31; ++i) {\n b[i] = start += 1 << eb[i - 1];\n }\n var r = new i32(b[30]);\n for (var i = 1; i < 30; ++i) {\n for (var j = b[i]; j < b[i + 1]; ++j) {\n r[j] = j - b[i] << 5 | i;\n }\n }\n return { b, r };\n};\nvar _a = freb(fleb, 2);\nvar fl = _a.b;\nvar revfl = _a.r;\nfl[28] = 258, revfl[258] = 28;\nvar _b = freb(fdeb, 0);\nvar fd = _b.b;\nvar revfd = _b.r;\nvar rev = new u16(32768);\nfor (i = 0; i < 32768; ++i) {\n x = (i & 43690) >> 1 | (i & 21845) << 1;\n x = (x & 52428) >> 2 | (x & 13107) << 2;\n x = (x & 61680) >> 4 | (x & 3855) << 4;\n rev[i] = ((x & 65280) >> 8 | (x & 255) << 8) >> 1;\n}\nvar x;\nvar i;\nvar hMap = (function(cd, mb, r) {\n var s = cd.length;\n var i = 0;\n var l = new u16(mb);\n for (; i < s; ++i) {\n if (cd[i])\n ++l[cd[i] - 1];\n }\n var le = new u16(mb);\n for (i = 1; i < mb; ++i) {\n le[i] = le[i - 1] + l[i - 1] << 1;\n }\n var co;\n if (r) {\n co = new u16(1 << mb);\n var rvb = 15 - mb;\n for (i = 0; i < s; ++i) {\n if (cd[i]) {\n var sv = i << 4 | cd[i];\n var r_1 = mb - cd[i];\n var v = le[cd[i] - 1]++ << r_1;\n for (var m = v | (1 << r_1) - 1; v <= m; ++v) {\n co[rev[v] >> rvb] = sv;\n }\n }\n }\n } else {\n co = new u16(s);\n for (i = 0; i < s; ++i) {\n if (cd[i]) {\n co[i] = rev[le[cd[i] - 1]++] >> 15 - cd[i];\n }\n }\n }\n return co;\n});\nvar flt = new u8(288);\nfor (i = 0; i < 144; ++i)\n flt[i] = 8;\nvar i;\nfor (i = 144; i < 256; ++i)\n flt[i] = 9;\nvar i;\nfor (i = 256; i < 280; ++i)\n flt[i] = 7;\nvar i;\nfor (i = 280; i < 288; ++i)\n flt[i] = 8;\nvar i;\nvar fdt = new u8(32);\nfor (i = 0; i < 32; ++i)\n fdt[i] = 5;\nvar i;\nvar flrm = /* @__PURE__ */ hMap(flt, 9, 1);\nvar fdrm = /* @__PURE__ */ hMap(fdt, 5, 1);\nvar max = function(a) {\n var m = a[0];\n for (var i = 1; i < a.length; ++i) {\n if (a[i] > m)\n m = a[i];\n }\n return m;\n};\nvar bits = function(d, p, m) {\n var o = p / 8 | 0;\n return (d[o] | d[o + 1] << 8) >> (p & 7) & m;\n};\nvar bits16 = function(d, p) {\n var o = p / 8 | 0;\n return (d[o] | d[o + 1] << 8 | d[o + 2] << 16) >> (p & 7);\n};\nvar shft = function(p) {\n return (p + 7) / 8 | 0;\n};\nvar slc = function(v, s, e) {\n if (s == null || s < 0)\n s = 0;\n if (e == null || e > v.length)\n e = v.length;\n return new u8(v.subarray(s, e));\n};\nvar ec = [\n \"unexpected EOF\",\n \"invalid block type\",\n \"invalid length/literal\",\n \"invalid distance\",\n \"stream finished\",\n \"no stream handler\",\n ,\n \"no callback\",\n \"invalid UTF-8 data\",\n \"extra field too long\",\n \"date not in range 1980-2099\",\n \"filename too long\",\n \"stream finishing\",\n \"invalid zip data\"\n // determined by unknown compression method\n];\nvar err = function(ind, msg, nt) {\n var e = new Error(msg || ec[ind]);\n e.code = ind;\n if (Error.captureStackTrace)\n Error.captureStackTrace(e, err);\n if (!nt)\n throw e;\n return e;\n};\nvar inflt = function(dat, st, buf, dict) {\n var sl = dat.length, dl = dict ? dict.length : 0;\n if (!sl || st.f && !st.l)\n return buf || new u8(0);\n var noBuf = !buf;\n var resize = noBuf || st.i != 2;\n var noSt = st.i;\n if (noBuf)\n buf = new u8(sl * 3);\n var cbuf = function(l2) {\n var bl = buf.length;\n if (l2 > bl) {\n var nbuf = new u8(Math.max(bl * 2, l2));\n nbuf.set(buf);\n buf = nbuf;\n }\n };\n var final = st.f || 0, pos = st.p || 0, bt = st.b || 0, lm = st.l, dm = st.d, lbt = st.m, dbt = st.n;\n var tbts = sl * 8;\n do {\n if (!lm) {\n final = bits(dat, pos, 1);\n var type = bits(dat, pos + 1, 3);\n pos += 3;\n if (!type) {\n var s = shft(pos) + 4, l = dat[s - 4] | dat[s - 3] << 8, t = s + l;\n if (t > sl) {\n if (noSt)\n err(0);\n break;\n }\n if (resize)\n cbuf(bt + l);\n buf.set(dat.subarray(s, t), bt);\n st.b = bt += l, st.p = pos = t * 8, st.f = final;\n continue;\n } else if (type == 1)\n lm = flrm, dm = fdrm, lbt = 9, dbt = 5;\n else if (type == 2) {\n var hLit = bits(dat, pos, 31) + 257, hcLen = bits(dat, pos + 10, 15) + 4;\n var tl = hLit + bits(dat, pos + 5, 31) + 1;\n pos += 14;\n var ldt = new u8(tl);\n var clt = new u8(19);\n for (var i = 0; i < hcLen; ++i) {\n clt[clim[i]] = bits(dat, pos + i * 3, 7);\n }\n pos += hcLen * 3;\n var clb = max(clt), clbmsk = (1 << clb) - 1;\n var clm = hMap(clt, clb, 1);\n for (var i = 0; i < tl; ) {\n var r = clm[bits(dat, pos, clbmsk)];\n pos += r & 15;\n var s = r >> 4;\n if (s < 16) {\n ldt[i++] = s;\n } else {\n var c = 0, n = 0;\n if (s == 16)\n n = 3 + bits(dat, pos, 3), pos += 2, c = ldt[i - 1];\n else if (s == 17)\n n = 3 + bits(dat, pos, 7), pos += 3;\n else if (s == 18)\n n = 11 + bits(dat, pos, 127), pos += 7;\n while (n--)\n ldt[i++] = c;\n }\n }\n var lt = ldt.subarray(0, hLit), dt = ldt.subarray(hLit);\n lbt = max(lt);\n dbt = max(dt);\n lm = hMap(lt, lbt, 1);\n dm = hMap(dt, dbt, 1);\n } else\n err(1);\n if (pos > tbts) {\n if (noSt)\n err(0);\n break;\n }\n }\n if (resize)\n cbuf(bt + 131072);\n var lms = (1 << lbt) - 1, dms = (1 << dbt) - 1;\n var lpos = pos;\n for (; ; lpos = pos) {\n var c = lm[bits16(dat, pos) & lms], sym = c >> 4;\n pos += c & 15;\n if (pos > tbts) {\n if (noSt)\n err(0);\n break;\n }\n if (!c)\n err(2);\n if (sym < 256)\n buf[bt++] = sym;\n else if (sym == 256) {\n lpos = pos, lm = null;\n break;\n } else {\n var add2 = sym - 254;\n if (sym > 264) {\n var i = sym - 257, b = fleb[i];\n add2 = bits(dat, pos, (1 << b) - 1) + fl[i];\n pos += b;\n }\n var d = dm[bits16(dat, pos) & dms], dsym = d >> 4;\n if (!d)\n err(3);\n pos += d & 15;\n var dt = fd[dsym];\n if (dsym > 3) {\n var b = fdeb[dsym];\n dt += bits16(dat, pos) & (1 << b) - 1, pos += b;\n }\n if (pos > tbts) {\n if (noSt)\n err(0);\n break;\n }\n if (resize)\n cbuf(bt + 131072);\n var end = bt + add2;\n if (bt < dt) {\n var shift = dl - dt, dend = Math.min(dt, end);\n if (shift + bt < 0)\n err(3);\n for (; bt < dend; ++bt)\n buf[bt] = dict[shift + bt];\n }\n for (; bt < end; ++bt)\n buf[bt] = buf[bt - dt];\n }\n }\n st.l = lm, st.p = lpos, st.b = bt, st.f = final;\n if (lm)\n final = 1, st.m = lbt, st.d = dm, st.n = dbt;\n } while (!final);\n return bt != buf.length && noBuf ? slc(buf, 0, bt) : buf.subarray(0, bt);\n};\nvar et = /* @__PURE__ */ new u8(0);\nfunction inflateSync(data, opts) {\n return inflt(data, { i: 2 }, opts && opts.out, opts && opts.dictionary);\n}\nvar td = typeof TextDecoder != \"undefined\" && /* @__PURE__ */ new TextDecoder();\nvar tds = 0;\ntry {\n td.decode(et, { stream: true });\n tds = 1;\n} catch (e) {\n}\n\n// apps/ecosystem-certifier/fixtures/flagship/knowledge-pack-entry.ts\nvar import_fast_deep_equal = __toESM(require_fast_deep_equal(), 1);\nvar import_fast_json_stable_stringify = __toESM(require_fast_json_stable_stringify(), 1);\nvar import_he = __toESM(require_he(), 1);\nvar import_json_logic_js = __toESM(require_logic(), 1);\n\n// node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/index.mjs\nvar uc_exports = {};\n__export(uc_exports, {\n Any: () => regex_default,\n Cc: () => regex_default2,\n Cf: () => regex_default3,\n P: () => regex_default4,\n S: () => regex_default5,\n Z: () => regex_default6\n});\n\n// node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/properties/Any/regex.mjs\nvar regex_default = /[\\0-\\uD7FF\\uE000-\\uFFFF]|[\\uD800-\\uDBFF][\\uDC00-\\uDFFF]|[\\uD800-\\uDBFF](?![\\uDC00-\\uDFFF])|(?:[^\\uD800-\\uDBFF]|^)[\\uDC00-\\uDFFF]/;\n\n// node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/Cc/regex.mjs\nvar regex_default2 = /[\\0-\\x1F\\x7F-\\x9F]/;\n\n// node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/Cf/regex.mjs\nvar regex_default3 = /[\\xAD\\u0600-\\u0605\\u061C\\u06DD\\u070F\\u0890\\u0891\\u08E2\\u180E\\u200B-\\u200F\\u202A-\\u202E\\u2060-\\u2064\\u2066-\\u206F\\uFEFF\\uFFF9-\\uFFFB]|\\uD804[\\uDCBD\\uDCCD]|\\uD80D[\\uDC30-\\uDC3F]|\\uD82F[\\uDCA0-\\uDCA3]|\\uD834[\\uDD73-\\uDD7A]|\\uDB40[\\uDC01\\uDC20-\\uDC7F]/;\n\n// node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/P/regex.mjs\nvar regex_default4 = /[!-#%-\\*,-\\/:;\\?@\\[-\\]_\\{\\}\\xA1\\xA7\\xAB\\xB6\\xB7\\xBB\\xBF\\u037E\\u0387\\u055A-\\u055F\\u0589\\u058A\\u05BE\\u05C0\\u05C3\\u05C6\\u05F3\\u05F4\\u0609\\u060A\\u060C\\u060D\\u061B\\u061D-\\u061F\\u066A-\\u066D\\u06D4\\u0700-\\u070D\\u07F7-\\u07F9\\u0830-\\u083E\\u085E\\u0964\\u0965\\u0970\\u09FD\\u0A76\\u0AF0\\u0C77\\u0C84\\u0DF4\\u0E4F\\u0E5A\\u0E5B\\u0F04-\\u0F12\\u0F14\\u0F3A-\\u0F3D\\u0F85\\u0FD0-\\u0FD4\\u0FD9\\u0FDA\\u104A-\\u104F\\u10FB\\u1360-\\u1368\\u1400\\u166E\\u169B\\u169C\\u16EB-\\u16ED\\u1735\\u1736\\u17D4-\\u17D6\\u17D8-\\u17DA\\u1800-\\u180A\\u1944\\u1945\\u1A1E\\u1A1F\\u1AA0-\\u1AA6\\u1AA8-\\u1AAD\\u1B5A-\\u1B60\\u1B7D\\u1B7E\\u1BFC-\\u1BFF\\u1C3B-\\u1C3F\\u1C7E\\u1C7F\\u1CC0-\\u1CC7\\u1CD3\\u2010-\\u2027\\u2030-\\u2043\\u2045-\\u2051\\u2053-\\u205E\\u207D\\u207E\\u208D\\u208E\\u2308-\\u230B\\u2329\\u232A\\u2768-\\u2775\\u27C5\\u27C6\\u27E6-\\u27EF\\u2983-\\u2998\\u29D8-\\u29DB\\u29FC\\u29FD\\u2CF9-\\u2CFC\\u2CFE\\u2CFF\\u2D70\\u2E00-\\u2E2E\\u2E30-\\u2E4F\\u2E52-\\u2E5D\\u3001-\\u3003\\u3008-\\u3011\\u3014-\\u301F\\u3030\\u303D\\u30A0\\u30FB\\uA4FE\\uA4FF\\uA60D-\\uA60F\\uA673\\uA67E\\uA6F2-\\uA6F7\\uA874-\\uA877\\uA8CE\\uA8CF\\uA8F8-\\uA8FA\\uA8FC\\uA92E\\uA92F\\uA95F\\uA9C1-\\uA9CD\\uA9DE\\uA9DF\\uAA5C-\\uAA5F\\uAADE\\uAADF\\uAAF0\\uAAF1\\uABEB\\uFD3E\\uFD3F\\uFE10-\\uFE19\\uFE30-\\uFE52\\uFE54-\\uFE61\\uFE63\\uFE68\\uFE6A\\uFE6B\\uFF01-\\uFF03\\uFF05-\\uFF0A\\uFF0C-\\uFF0F\\uFF1A\\uFF1B\\uFF1F\\uFF20\\uFF3B-\\uFF3D\\uFF3F\\uFF5B\\uFF5D\\uFF5F-\\uFF65]|\\uD800[\\uDD00-\\uDD02\\uDF9F\\uDFD0]|\\uD801\\uDD6F|\\uD802[\\uDC57\\uDD1F\\uDD3F\\uDE50-\\uDE58\\uDE7F\\uDEF0-\\uDEF6\\uDF39-\\uDF3F\\uDF99-\\uDF9C]|\\uD803[\\uDEAD\\uDF55-\\uDF59\\uDF86-\\uDF89]|\\uD804[\\uDC47-\\uDC4D\\uDCBB\\uDCBC\\uDCBE-\\uDCC1\\uDD40-\\uDD43\\uDD74\\uDD75\\uDDC5-\\uDDC8\\uDDCD\\uDDDB\\uDDDD-\\uDDDF\\uDE38-\\uDE3D\\uDEA9]|\\uD805[\\uDC4B-\\uDC4F\\uDC5A\\uDC5B\\uDC5D\\uDCC6\\uDDC1-\\uDDD7\\uDE41-\\uDE43\\uDE60-\\uDE6C\\uDEB9\\uDF3C-\\uDF3E]|\\uD806[\\uDC3B\\uDD44-\\uDD46\\uDDE2\\uDE3F-\\uDE46\\uDE9A-\\uDE9C\\uDE9E-\\uDEA2\\uDF00-\\uDF09]|\\uD807[\\uDC41-\\uDC45\\uDC70\\uDC71\\uDEF7\\uDEF8\\uDF43-\\uDF4F\\uDFFF]|\\uD809[\\uDC70-\\uDC74]|\\uD80B[\\uDFF1\\uDFF2]|\\uD81A[\\uDE6E\\uDE6F\\uDEF5\\uDF37-\\uDF3B\\uDF44]|\\uD81B[\\uDE97-\\uDE9A\\uDFE2]|\\uD82F\\uDC9F|\\uD836[\\uDE87-\\uDE8B]|\\uD83A[\\uDD5E\\uDD5F]/;\n\n// node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/S/regex.mjs\nvar regex_default5 = /[\\$\\+<->\\^`\\|~\\xA2-\\xA6\\xA8\\xA9\\xAC\\xAE-\\xB1\\xB4\\xB8\\xD7\\xF7\\u02C2-\\u02C5\\u02D2-\\u02DF\\u02E5-\\u02EB\\u02ED\\u02EF-\\u02FF\\u0375\\u0384\\u0385\\u03F6\\u0482\\u058D-\\u058F\\u0606-\\u0608\\u060B\\u060E\\u060F\\u06DE\\u06E9\\u06FD\\u06FE\\u07F6\\u07FE\\u07FF\\u0888\\u09F2\\u09F3\\u09FA\\u09FB\\u0AF1\\u0B70\\u0BF3-\\u0BFA\\u0C7F\\u0D4F\\u0D79\\u0E3F\\u0F01-\\u0F03\\u0F13\\u0F15-\\u0F17\\u0F1A-\\u0F1F\\u0F34\\u0F36\\u0F38\\u0FBE-\\u0FC5\\u0FC7-\\u0FCC\\u0FCE\\u0FCF\\u0FD5-\\u0FD8\\u109E\\u109F\\u1390-\\u1399\\u166D\\u17DB\\u1940\\u19DE-\\u19FF\\u1B61-\\u1B6A\\u1B74-\\u1B7C\\u1FBD\\u1FBF-\\u1FC1\\u1FCD-\\u1FCF\\u1FDD-\\u1FDF\\u1FED-\\u1FEF\\u1FFD\\u1FFE\\u2044\\u2052\\u207A-\\u207C\\u208A-\\u208C\\u20A0-\\u20C0\\u2100\\u2101\\u2103-\\u2106\\u2108\\u2109\\u2114\\u2116-\\u2118\\u211E-\\u2123\\u2125\\u2127\\u2129\\u212E\\u213A\\u213B\\u2140-\\u2144\\u214A-\\u214D\\u214F\\u218A\\u218B\\u2190-\\u2307\\u230C-\\u2328\\u232B-\\u2426\\u2440-\\u244A\\u249C-\\u24E9\\u2500-\\u2767\\u2794-\\u27C4\\u27C7-\\u27E5\\u27F0-\\u2982\\u2999-\\u29D7\\u29DC-\\u29FB\\u29FE-\\u2B73\\u2B76-\\u2B95\\u2B97-\\u2BFF\\u2CE5-\\u2CEA\\u2E50\\u2E51\\u2E80-\\u2E99\\u2E9B-\\u2EF3\\u2F00-\\u2FD5\\u2FF0-\\u2FFF\\u3004\\u3012\\u3013\\u3020\\u3036\\u3037\\u303E\\u303F\\u309B\\u309C\\u3190\\u3191\\u3196-\\u319F\\u31C0-\\u31E3\\u31EF\\u3200-\\u321E\\u322A-\\u3247\\u3250\\u3260-\\u327F\\u328A-\\u32B0\\u32C0-\\u33FF\\u4DC0-\\u4DFF\\uA490-\\uA4C6\\uA700-\\uA716\\uA720\\uA721\\uA789\\uA78A\\uA828-\\uA82B\\uA836-\\uA839\\uAA77-\\uAA79\\uAB5B\\uAB6A\\uAB6B\\uFB29\\uFBB2-\\uFBC2\\uFD40-\\uFD4F\\uFDCF\\uFDFC-\\uFDFF\\uFE62\\uFE64-\\uFE66\\uFE69\\uFF04\\uFF0B\\uFF1C-\\uFF1E\\uFF3E\\uFF40\\uFF5C\\uFF5E\\uFFE0-\\uFFE6\\uFFE8-\\uFFEE\\uFFFC\\uFFFD]|\\uD800[\\uDD37-\\uDD3F\\uDD79-\\uDD89\\uDD8C-\\uDD8E\\uDD90-\\uDD9C\\uDDA0\\uDDD0-\\uDDFC]|\\uD802[\\uDC77\\uDC78\\uDEC8]|\\uD805\\uDF3F|\\uD807[\\uDFD5-\\uDFF1]|\\uD81A[\\uDF3C-\\uDF3F\\uDF45]|\\uD82F\\uDC9C|\\uD833[\\uDF50-\\uDFC3]|\\uD834[\\uDC00-\\uDCF5\\uDD00-\\uDD26\\uDD29-\\uDD64\\uDD6A-\\uDD6C\\uDD83\\uDD84\\uDD8C-\\uDDA9\\uDDAE-\\uDDEA\\uDE00-\\uDE41\\uDE45\\uDF00-\\uDF56]|\\uD835[\\uDEC1\\uDEDB\\uDEFB\\uDF15\\uDF35\\uDF4F\\uDF6F\\uDF89\\uDFA9\\uDFC3]|\\uD836[\\uDC00-\\uDDFF\\uDE37-\\uDE3A\\uDE6D-\\uDE74\\uDE76-\\uDE83\\uDE85\\uDE86]|\\uD838[\\uDD4F\\uDEFF]|\\uD83B[\\uDCAC\\uDCB0\\uDD2E\\uDEF0\\uDEF1]|\\uD83C[\\uDC00-\\uDC2B\\uDC30-\\uDC93\\uDCA0-\\uDCAE\\uDCB1-\\uDCBF\\uDCC1-\\uDCCF\\uDCD1-\\uDCF5\\uDD0D-\\uDDAD\\uDDE6-\\uDE02\\uDE10-\\uDE3B\\uDE40-\\uDE48\\uDE50\\uDE51\\uDE60-\\uDE65\\uDF00-\\uDFFF]|\\uD83D[\\uDC00-\\uDED7\\uDEDC-\\uDEEC\\uDEF0-\\uDEFC\\uDF00-\\uDF76\\uDF7B-\\uDFD9\\uDFE0-\\uDFEB\\uDFF0]|\\uD83E[\\uDC00-\\uDC0B\\uDC10-\\uDC47\\uDC50-\\uDC59\\uDC60-\\uDC87\\uDC90-\\uDCAD\\uDCB0\\uDCB1\\uDD00-\\uDE53\\uDE60-\\uDE6D\\uDE70-\\uDE7C\\uDE80-\\uDE88\\uDE90-\\uDEBD\\uDEBF-\\uDEC5\\uDECE-\\uDEDB\\uDEE0-\\uDEE8\\uDEF0-\\uDEF8\\uDF00-\\uDF92\\uDF94-\\uDFCA]/;\n\n// node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/Z/regex.mjs\nvar regex_default6 = /[ \\xA0\\u1680\\u2000-\\u200A\\u2028\\u2029\\u202F\\u205F\\u3000]/;\n\n// node_modules/.pnpm/linkify-it@5.0.0/node_modules/linkify-it/lib/re.mjs\nfunction re_default(opts) {\n const re = {};\n opts = opts || {};\n re.src_Any = regex_default.source;\n re.src_Cc = regex_default2.source;\n re.src_Z = regex_default6.source;\n re.src_P = regex_default4.source;\n re.src_ZPCc = [re.src_Z, re.src_P, re.src_Cc].join(\"|\");\n re.src_ZCc = [re.src_Z, re.src_Cc].join(\"|\");\n const text_separators = \"[><|]\";\n re.src_pseudo_letter = \"(?:(?!\" + text_separators + \"|\" + re.src_ZPCc + \")\" + re.src_Any + \")\";\n re.src_ip4 = \"(?:(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\";\n re.src_auth = \"(?:(?:(?!\" + re.src_ZCc + \"|[@/\\\\[\\\\]()]).)+@)?\";\n re.src_port = \"(?::(?:6(?:[0-4]\\\\d{3}|5(?:[0-4]\\\\d{2}|5(?:[0-2]\\\\d|3[0-5])))|[1-5]?\\\\d{1,4}))?\";\n re.src_host_terminator = \"(?=$|\" + text_separators + \"|\" + re.src_ZPCc + \")(?!\" + (opts[\"---\"] ? \"-(?!--)|\" : \"-|\") + \"_|:\\\\d|\\\\.-|\\\\.(?!$|\" + re.src_ZPCc + \"))\";\n re.src_path = \"(?:[/?#](?:(?!\" + re.src_ZCc + \"|\" + text_separators + `|[()[\\\\]{}.,\"'?!\\\\-;]).|\\\\[(?:(?!` + re.src_ZCc + \"|\\\\]).)*\\\\]|\\\\((?:(?!\" + re.src_ZCc + \"|[)]).)*\\\\)|\\\\{(?:(?!\" + re.src_ZCc + '|[}]).)*\\\\}|\\\\\"(?:(?!' + re.src_ZCc + `|[\"]).)+\\\\\"|\\\\'(?:(?!` + re.src_ZCc + \"|[']).)+\\\\'|\\\\'(?=\" + re.src_pseudo_letter + \"|[-])|\\\\.{2,}[a-zA-Z0-9%/&]|\\\\.(?!\" + re.src_ZCc + \"|[.]|$)|\" + (opts[\"---\"] ? \"\\\\-(?!--(?:[^-]|$))(?:-*)|\" : \"\\\\-+|\") + // allow `,,,` in paths\n \",(?!\" + re.src_ZCc + \"|$)|;(?!\" + re.src_ZCc + \"|$)|\\\\!+(?!\" + re.src_ZCc + \"|[!]|$)|\\\\?(?!\" + re.src_ZCc + \"|[?]|$))+|\\\\/)?\";\n re.src_email_name = '[\\\\-;:&=\\\\+\\\\$,\\\\.a-zA-Z0-9_][\\\\-;:&=\\\\+\\\\$,\\\\\"\\\\.a-zA-Z0-9_]*';\n re.src_xn = \"xn--[a-z0-9\\\\-]{1,59}\";\n re.src_domain_root = // Allow letters & digits (http://test1)\n \"(?:\" + re.src_xn + \"|\" + re.src_pseudo_letter + \"{1,63})\";\n re.src_domain = \"(?:\" + re.src_xn + \"|(?:\" + re.src_pseudo_letter + \")|(?:\" + re.src_pseudo_letter + \"(?:-|\" + re.src_pseudo_letter + \"){0,61}\" + re.src_pseudo_letter + \"))\";\n re.src_host = \"(?:(?:(?:(?:\" + re.src_domain + \")\\\\.)*\" + re.src_domain + \"))\";\n re.tpl_host_fuzzy = \"(?:\" + re.src_ip4 + \"|(?:(?:(?:\" + re.src_domain + \")\\\\.)+(?:%TLDS%)))\";\n re.tpl_host_no_ip_fuzzy = \"(?:(?:(?:\" + re.src_domain + \")\\\\.)+(?:%TLDS%))\";\n re.src_host_strict = re.src_host + re.src_host_terminator;\n re.tpl_host_fuzzy_strict = re.tpl_host_fuzzy + re.src_host_terminator;\n re.src_host_port_strict = re.src_host + re.src_port + re.src_host_terminator;\n re.tpl_host_port_fuzzy_strict = re.tpl_host_fuzzy + re.src_port + re.src_host_terminator;\n re.tpl_host_port_no_ip_fuzzy_strict = re.tpl_host_no_ip_fuzzy + re.src_port + re.src_host_terminator;\n re.tpl_host_fuzzy_test = \"localhost|www\\\\.|\\\\.\\\\d{1,3}\\\\.|(?:\\\\.(?:%TLDS%)(?:\" + re.src_ZPCc + \"|>|$))\";\n re.tpl_email_fuzzy = \"(^|\" + text_separators + '|\"|\\\\(|' + re.src_ZCc + \")(\" + re.src_email_name + \"@\" + re.tpl_host_fuzzy_strict + \")\";\n re.tpl_link_fuzzy = // Fuzzy link can't be prepended with .:/\\- and non punctuation.\n // but can start with > (markdown blockquote)\n \"(^|(?![.:/\\\\-_@])(?:[$+<=>^`||]|\" + re.src_ZPCc + \"))((?![$+<=>^`||])\" + re.tpl_host_port_fuzzy_strict + re.src_path + \")\";\n re.tpl_link_no_ip_fuzzy = // Fuzzy link can't be prepended with .:/\\- and non punctuation.\n // but can start with > (markdown blockquote)\n \"(^|(?![.:/\\\\-_@])(?:[$+<=>^`||]|\" + re.src_ZPCc + \"))((?![$+<=>^`||])\" + re.tpl_host_port_no_ip_fuzzy_strict + re.src_path + \")\";\n return re;\n}\n\n// node_modules/.pnpm/linkify-it@5.0.0/node_modules/linkify-it/index.mjs\nfunction assign(obj) {\n const sources = Array.prototype.slice.call(arguments, 1);\n sources.forEach(function(source) {\n if (!source) {\n return;\n }\n Object.keys(source).forEach(function(key) {\n obj[key] = source[key];\n });\n });\n return obj;\n}\nfunction _class(obj) {\n return Object.prototype.toString.call(obj);\n}\nfunction isString(obj) {\n return _class(obj) === \"[object String]\";\n}\nfunction isObject(obj) {\n return _class(obj) === \"[object Object]\";\n}\nfunction isRegExp(obj) {\n return _class(obj) === \"[object RegExp]\";\n}\nfunction isFunction(obj) {\n return _class(obj) === \"[object Function]\";\n}\nfunction escapeRE(str) {\n return str.replace(/[.?*+^$[\\]\\\\(){}|-]/g, \"\\\\$&\");\n}\nvar defaultOptions = {\n fuzzyLink: true,\n fuzzyEmail: true,\n fuzzyIP: false\n};\nfunction isOptionsObj(obj) {\n return Object.keys(obj || {}).reduce(function(acc, k) {\n return acc || defaultOptions.hasOwnProperty(k);\n }, false);\n}\nvar defaultSchemas = {\n \"http:\": {\n validate: function(text2, pos, self) {\n const tail = text2.slice(pos);\n if (!self.re.http) {\n self.re.http = new RegExp(\n \"^\\\\/\\\\/\" + self.re.src_auth + self.re.src_host_port_strict + self.re.src_path,\n \"i\"\n );\n }\n if (self.re.http.test(tail)) {\n return tail.match(self.re.http)[0].length;\n }\n return 0;\n }\n },\n \"https:\": \"http:\",\n \"ftp:\": \"http:\",\n \"//\": {\n validate: function(text2, pos, self) {\n const tail = text2.slice(pos);\n if (!self.re.no_http) {\n self.re.no_http = new RegExp(\n \"^\" + self.re.src_auth + // Don't allow single-level domains, because of false positives like '//test'\n // with code comments\n \"(?:localhost|(?:(?:\" + self.re.src_domain + \")\\\\.)+\" + self.re.src_domain_root + \")\" + self.re.src_port + self.re.src_host_terminator + self.re.src_path,\n \"i\"\n );\n }\n if (self.re.no_http.test(tail)) {\n if (pos >= 3 && text2[pos - 3] === \":\") {\n return 0;\n }\n if (pos >= 3 && text2[pos - 3] === \"/\") {\n return 0;\n }\n return tail.match(self.re.no_http)[0].length;\n }\n return 0;\n }\n },\n \"mailto:\": {\n validate: function(text2, pos, self) {\n const tail = text2.slice(pos);\n if (!self.re.mailto) {\n self.re.mailto = new RegExp(\n \"^\" + self.re.src_email_name + \"@\" + self.re.src_host_strict,\n \"i\"\n );\n }\n if (self.re.mailto.test(tail)) {\n return tail.match(self.re.mailto)[0].length;\n }\n return 0;\n }\n }\n};\nvar tlds_2ch_src_re = \"a[cdefgilmnoqrstuwxz]|b[abdefghijmnorstvwyz]|c[acdfghiklmnoruvwxyz]|d[ejkmoz]|e[cegrstu]|f[ijkmor]|g[abdefghilmnpqrstuwy]|h[kmnrtu]|i[delmnoqrst]|j[emop]|k[eghimnprwyz]|l[abcikrstuvy]|m[acdeghklmnopqrstuvwxyz]|n[acefgilopruz]|om|p[aefghklmnrstwy]|qa|r[eosuw]|s[abcdeghijklmnortuvxyz]|t[cdfghjklmnortvwz]|u[agksyz]|v[aceginu]|w[fs]|y[et]|z[amw]\";\nvar tlds_default = \"biz|com|edu|gov|net|org|pro|web|xxx|aero|asia|coop|info|museum|name|shop|рф\".split(\"|\");\nfunction resetScanCache(self) {\n self.__index__ = -1;\n self.__text_cache__ = \"\";\n}\nfunction createValidator(re) {\n return function(text2, pos) {\n const tail = text2.slice(pos);\n if (re.test(tail)) {\n return tail.match(re)[0].length;\n }\n return 0;\n };\n}\nfunction createNormalizer() {\n return function(match2, self) {\n self.normalize(match2);\n };\n}\nfunction compile(self) {\n const re = self.re = re_default(self.__opts__);\n const tlds2 = self.__tlds__.slice();\n self.onCompile();\n if (!self.__tlds_replaced__) {\n tlds2.push(tlds_2ch_src_re);\n }\n tlds2.push(re.src_xn);\n re.src_tlds = tlds2.join(\"|\");\n function untpl(tpl) {\n return tpl.replace(\"%TLDS%\", re.src_tlds);\n }\n re.email_fuzzy = RegExp(untpl(re.tpl_email_fuzzy), \"i\");\n re.link_fuzzy = RegExp(untpl(re.tpl_link_fuzzy), \"i\");\n re.link_no_ip_fuzzy = RegExp(untpl(re.tpl_link_no_ip_fuzzy), \"i\");\n re.host_fuzzy_test = RegExp(untpl(re.tpl_host_fuzzy_test), \"i\");\n const aliases = [];\n self.__compiled__ = {};\n function schemaError(name, val) {\n throw new Error('(LinkifyIt) Invalid schema \"' + name + '\": ' + val);\n }\n Object.keys(self.__schemas__).forEach(function(name) {\n const val = self.__schemas__[name];\n if (val === null) {\n return;\n }\n const compiled = { validate: null, link: null };\n self.__compiled__[name] = compiled;\n if (isObject(val)) {\n if (isRegExp(val.validate)) {\n compiled.validate = createValidator(val.validate);\n } else if (isFunction(val.validate)) {\n compiled.validate = val.validate;\n } else {\n schemaError(name, val);\n }\n if (isFunction(val.normalize)) {\n compiled.normalize = val.normalize;\n } else if (!val.normalize) {\n compiled.normalize = createNormalizer();\n } else {\n schemaError(name, val);\n }\n return;\n }\n if (isString(val)) {\n aliases.push(name);\n return;\n }\n schemaError(name, val);\n });\n aliases.forEach(function(alias) {\n if (!self.__compiled__[self.__schemas__[alias]]) {\n return;\n }\n self.__compiled__[alias].validate = self.__compiled__[self.__schemas__[alias]].validate;\n self.__compiled__[alias].normalize = self.__compiled__[self.__schemas__[alias]].normalize;\n });\n self.__compiled__[\"\"] = { validate: null, normalize: createNormalizer() };\n const slist = Object.keys(self.__compiled__).filter(function(name) {\n return name.length > 0 && self.__compiled__[name];\n }).map(escapeRE).join(\"|\");\n self.re.schema_test = RegExp(\"(^|(?!_)(?:[><|]|\" + re.src_ZPCc + \"))(\" + slist + \")\", \"i\");\n self.re.schema_search = RegExp(\"(^|(?!_)(?:[><|]|\" + re.src_ZPCc + \"))(\" + slist + \")\", \"ig\");\n self.re.schema_at_start = RegExp(\"^\" + self.re.schema_search.source, \"i\");\n self.re.pretest = RegExp(\n \"(\" + self.re.schema_test.source + \")|(\" + self.re.host_fuzzy_test.source + \")|@\",\n \"i\"\n );\n resetScanCache(self);\n}\nfunction Match(self, shift) {\n const start = self.__index__;\n const end = self.__last_index__;\n const text2 = self.__text_cache__.slice(start, end);\n this.schema = self.__schema__.toLowerCase();\n this.index = start + shift;\n this.lastIndex = end + shift;\n this.raw = text2;\n this.text = text2;\n this.url = text2;\n}\nfunction createMatch(self, shift) {\n const match2 = new Match(self, shift);\n self.__compiled__[match2.schema].normalize(match2, self);\n return match2;\n}\nfunction LinkifyIt(schemas, options) {\n if (!(this instanceof LinkifyIt)) {\n return new LinkifyIt(schemas, options);\n }\n if (!options) {\n if (isOptionsObj(schemas)) {\n options = schemas;\n schemas = {};\n }\n }\n this.__opts__ = assign({}, defaultOptions, options);\n this.__index__ = -1;\n this.__last_index__ = -1;\n this.__schema__ = \"\";\n this.__text_cache__ = \"\";\n this.__schemas__ = assign({}, defaultSchemas, schemas);\n this.__compiled__ = {};\n this.__tlds__ = tlds_default;\n this.__tlds_replaced__ = false;\n this.re = {};\n compile(this);\n}\nLinkifyIt.prototype.add = function add(schema, definition) {\n this.__schemas__[schema] = definition;\n compile(this);\n return this;\n};\nLinkifyIt.prototype.set = function set(options) {\n this.__opts__ = assign(this.__opts__, options);\n return this;\n};\nLinkifyIt.prototype.test = function test(text2) {\n this.__text_cache__ = text2;\n this.__index__ = -1;\n if (!text2.length) {\n return false;\n }\n let m, ml, me, len, shift, next, re, tld_pos, at_pos;\n if (this.re.schema_test.test(text2)) {\n re = this.re.schema_search;\n re.lastIndex = 0;\n while ((m = re.exec(text2)) !== null) {\n len = this.testSchemaAt(text2, m[2], re.lastIndex);\n if (len) {\n this.__schema__ = m[2];\n this.__index__ = m.index + m[1].length;\n this.__last_index__ = m.index + m[0].length + len;\n break;\n }\n }\n }\n if (this.__opts__.fuzzyLink && this.__compiled__[\"http:\"]) {\n tld_pos = text2.search(this.re.host_fuzzy_test);\n if (tld_pos >= 0) {\n if (this.__index__ < 0 || tld_pos < this.__index__) {\n if ((ml = text2.match(this.__opts__.fuzzyIP ? this.re.link_fuzzy : this.re.link_no_ip_fuzzy)) !== null) {\n shift = ml.index + ml[1].length;\n if (this.__index__ < 0 || shift < this.__index__) {\n this.__schema__ = \"\";\n this.__index__ = shift;\n this.__last_index__ = ml.index + ml[0].length;\n }\n }\n }\n }\n }\n if (this.__opts__.fuzzyEmail && this.__compiled__[\"mailto:\"]) {\n at_pos = text2.indexOf(\"@\");\n if (at_pos >= 0) {\n if ((me = text2.match(this.re.email_fuzzy)) !== null) {\n shift = me.index + me[1].length;\n next = me.index + me[0].length;\n if (this.__index__ < 0 || shift < this.__index__ || shift === this.__index__ && next > this.__last_index__) {\n this.__schema__ = \"mailto:\";\n this.__index__ = shift;\n this.__last_index__ = next;\n }\n }\n }\n }\n return this.__index__ >= 0;\n};\nLinkifyIt.prototype.pretest = function pretest(text2) {\n return this.re.pretest.test(text2);\n};\nLinkifyIt.prototype.testSchemaAt = function testSchemaAt(text2, schema, pos) {\n if (!this.__compiled__[schema.toLowerCase()]) {\n return 0;\n }\n return this.__compiled__[schema.toLowerCase()].validate(text2, pos, this);\n};\nLinkifyIt.prototype.match = function match(text2) {\n const result = [];\n let shift = 0;\n if (this.__index__ >= 0 && this.__text_cache__ === text2) {\n result.push(createMatch(this, shift));\n shift = this.__last_index__;\n }\n let tail = shift ? text2.slice(shift) : text2;\n while (this.test(tail)) {\n result.push(createMatch(this, shift));\n tail = tail.slice(this.__last_index__);\n shift += this.__last_index__;\n }\n if (result.length) {\n return result;\n }\n return null;\n};\nLinkifyIt.prototype.matchAtStart = function matchAtStart(text2) {\n this.__text_cache__ = text2;\n this.__index__ = -1;\n if (!text2.length) return null;\n const m = this.re.schema_at_start.exec(text2);\n if (!m) return null;\n const len = this.testSchemaAt(text2, m[2], m[0].length);\n if (!len) return null;\n this.__schema__ = m[2];\n this.__index__ = m.index + m[1].length;\n this.__last_index__ = m.index + m[0].length + len;\n return createMatch(this, 0);\n};\nLinkifyIt.prototype.tlds = function tlds(list2, keepOld) {\n list2 = Array.isArray(list2) ? list2 : [list2];\n if (!keepOld) {\n this.__tlds__ = list2.slice();\n this.__tlds_replaced__ = true;\n compile(this);\n return this;\n }\n this.__tlds__ = this.__tlds__.concat(list2).sort().filter(function(el, idx, arr) {\n return el !== arr[idx - 1];\n }).reverse();\n compile(this);\n return this;\n};\nLinkifyIt.prototype.normalize = function normalize(match2) {\n if (!match2.schema) {\n match2.url = \"http://\" + match2.url;\n }\n if (match2.schema === \"mailto:\" && !/^mailto:/i.test(match2.url)) {\n match2.url = \"mailto:\" + match2.url;\n }\n};\nLinkifyIt.prototype.onCompile = function onCompile() {\n};\nvar linkify_it_default = LinkifyIt;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/common/utils.mjs\nvar utils_exports = {};\n__export(utils_exports, {\n arrayReplaceAt: () => arrayReplaceAt,\n assign: () => assign2,\n escapeHtml: () => escapeHtml,\n escapeRE: () => escapeRE2,\n fromCodePoint: () => fromCodePoint2,\n has: () => has,\n isMdAsciiPunct: () => isMdAsciiPunct,\n isPunctChar: () => isPunctChar,\n isSpace: () => isSpace,\n isString: () => isString2,\n isValidEntityCode: () => isValidEntityCode,\n isWhiteSpace: () => isWhiteSpace,\n lib: () => lib,\n normalizeReference: () => normalizeReference,\n unescapeAll: () => unescapeAll,\n unescapeMd: () => unescapeMd\n});\n\n// node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/index.mjs\nvar mdurl_exports = {};\n__export(mdurl_exports, {\n decode: () => decode_default,\n encode: () => encode_default,\n format: () => format,\n parse: () => parse_default\n});\n\n// node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/decode.mjs\nvar decodeCache = {};\nfunction getDecodeCache(exclude) {\n let cache = decodeCache[exclude];\n if (cache) {\n return cache;\n }\n cache = decodeCache[exclude] = [];\n for (let i = 0; i < 128; i++) {\n const ch = String.fromCharCode(i);\n cache.push(ch);\n }\n for (let i = 0; i < exclude.length; i++) {\n const ch = exclude.charCodeAt(i);\n cache[ch] = \"%\" + (\"0\" + ch.toString(16).toUpperCase()).slice(-2);\n }\n return cache;\n}\nfunction decode(string, exclude) {\n if (typeof exclude !== \"string\") {\n exclude = decode.defaultChars;\n }\n const cache = getDecodeCache(exclude);\n return string.replace(/(%[a-f0-9]{2})+/gi, function(seq) {\n let result = \"\";\n for (let i = 0, l = seq.length; i < l; i += 3) {\n const b1 = parseInt(seq.slice(i + 1, i + 3), 16);\n if (b1 < 128) {\n result += cache[b1];\n continue;\n }\n if ((b1 & 224) === 192 && i + 3 < l) {\n const b2 = parseInt(seq.slice(i + 4, i + 6), 16);\n if ((b2 & 192) === 128) {\n const chr = b1 << 6 & 1984 | b2 & 63;\n if (chr < 128) {\n result += \"��\";\n } else {\n result += String.fromCharCode(chr);\n }\n i += 3;\n continue;\n }\n }\n if ((b1 & 240) === 224 && i + 6 < l) {\n const b2 = parseInt(seq.slice(i + 4, i + 6), 16);\n const b3 = parseInt(seq.slice(i + 7, i + 9), 16);\n if ((b2 & 192) === 128 && (b3 & 192) === 128) {\n const chr = b1 << 12 & 61440 | b2 << 6 & 4032 | b3 & 63;\n if (chr < 2048 || chr >= 55296 && chr <= 57343) {\n result += \"���\";\n } else {\n result += String.fromCharCode(chr);\n }\n i += 6;\n continue;\n }\n }\n if ((b1 & 248) === 240 && i + 9 < l) {\n const b2 = parseInt(seq.slice(i + 4, i + 6), 16);\n const b3 = parseInt(seq.slice(i + 7, i + 9), 16);\n const b4 = parseInt(seq.slice(i + 10, i + 12), 16);\n if ((b2 & 192) === 128 && (b3 & 192) === 128 && (b4 & 192) === 128) {\n let chr = b1 << 18 & 1835008 | b2 << 12 & 258048 | b3 << 6 & 4032 | b4 & 63;\n if (chr < 65536 || chr > 1114111) {\n result += \"����\";\n } else {\n chr -= 65536;\n result += String.fromCharCode(55296 + (chr >> 10), 56320 + (chr & 1023));\n }\n i += 9;\n continue;\n }\n }\n result += \"�\";\n }\n return result;\n });\n}\ndecode.defaultChars = \";/?:@&=+$,#\";\ndecode.componentChars = \"\";\nvar decode_default = decode;\n\n// node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/encode.mjs\nvar encodeCache = {};\nfunction getEncodeCache(exclude) {\n let cache = encodeCache[exclude];\n if (cache) {\n return cache;\n }\n cache = encodeCache[exclude] = [];\n for (let i = 0; i < 128; i++) {\n const ch = String.fromCharCode(i);\n if (/^[0-9a-z]$/i.test(ch)) {\n cache.push(ch);\n } else {\n cache.push(\"%\" + (\"0\" + i.toString(16).toUpperCase()).slice(-2));\n }\n }\n for (let i = 0; i < exclude.length; i++) {\n cache[exclude.charCodeAt(i)] = exclude[i];\n }\n return cache;\n}\nfunction encode(string, exclude, keepEscaped) {\n if (typeof exclude !== \"string\") {\n keepEscaped = exclude;\n exclude = encode.defaultChars;\n }\n if (typeof keepEscaped === \"undefined\") {\n keepEscaped = true;\n }\n const cache = getEncodeCache(exclude);\n let result = \"\";\n for (let i = 0, l = string.length; i < l; i++) {\n const code2 = string.charCodeAt(i);\n if (keepEscaped && code2 === 37 && i + 2 < l) {\n if (/^[0-9a-f]{2}$/i.test(string.slice(i + 1, i + 3))) {\n result += string.slice(i, i + 3);\n i += 2;\n continue;\n }\n }\n if (code2 < 128) {\n result += cache[code2];\n continue;\n }\n if (code2 >= 55296 && code2 <= 57343) {\n if (code2 >= 55296 && code2 <= 56319 && i + 1 < l) {\n const nextCode = string.charCodeAt(i + 1);\n if (nextCode >= 56320 && nextCode <= 57343) {\n result += encodeURIComponent(string[i] + string[i + 1]);\n i++;\n continue;\n }\n }\n result += \"%EF%BF%BD\";\n continue;\n }\n result += encodeURIComponent(string[i]);\n }\n return result;\n}\nencode.defaultChars = \";/?:@&=+$,-_.!~*'()#\";\nencode.componentChars = \"-_.!~*'()\";\nvar encode_default = encode;\n\n// node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/format.mjs\nfunction format(url) {\n let result = \"\";\n result += url.protocol || \"\";\n result += url.slashes ? \"//\" : \"\";\n result += url.auth ? url.auth + \"@\" : \"\";\n if (url.hostname && url.hostname.indexOf(\":\") !== -1) {\n result += \"[\" + url.hostname + \"]\";\n } else {\n result += url.hostname || \"\";\n }\n result += url.port ? \":\" + url.port : \"\";\n result += url.pathname || \"\";\n result += url.search || \"\";\n result += url.hash || \"\";\n return result;\n}\n\n// node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/parse.mjs\nfunction Url() {\n this.protocol = null;\n this.slashes = null;\n this.auth = null;\n this.port = null;\n this.hostname = null;\n this.hash = null;\n this.search = null;\n this.pathname = null;\n}\nvar protocolPattern = /^([a-z0-9.+-]+:)/i;\nvar portPattern = /:[0-9]*$/;\nvar simplePathPattern = /^(\\/\\/?(?!\\/)[^\\?\\s]*)(\\?[^\\s]*)?$/;\nvar delims = [\"<\", \">\", '\"', \"`\", \" \", \"\\r\", \"\\n\", \"\t\"];\nvar unwise = [\"{\", \"}\", \"|\", \"\\\\\", \"^\", \"`\"].concat(delims);\nvar autoEscape = [\"'\"].concat(unwise);\nvar nonHostChars = [\"%\", \"/\", \"?\", \";\", \"#\"].concat(autoEscape);\nvar hostEndingChars = [\"/\", \"?\", \"#\"];\nvar hostnameMaxLen = 255;\nvar hostnamePartPattern = /^[+a-z0-9A-Z_-]{0,63}$/;\nvar hostnamePartStart = /^([+a-z0-9A-Z_-]{0,63})(.*)$/;\nvar hostlessProtocol = {\n javascript: true,\n \"javascript:\": true\n};\nvar slashedProtocol = {\n http: true,\n https: true,\n ftp: true,\n gopher: true,\n file: true,\n \"http:\": true,\n \"https:\": true,\n \"ftp:\": true,\n \"gopher:\": true,\n \"file:\": true\n};\nfunction urlParse(url, slashesDenoteHost) {\n if (url && url instanceof Url) return url;\n const u = new Url();\n u.parse(url, slashesDenoteHost);\n return u;\n}\nUrl.prototype.parse = function(url, slashesDenoteHost) {\n let lowerProto, hec, slashes;\n let rest = url;\n rest = rest.trim();\n if (!slashesDenoteHost && url.split(\"#\").length === 1) {\n const simplePath = simplePathPattern.exec(rest);\n if (simplePath) {\n this.pathname = simplePath[1];\n if (simplePath[2]) {\n this.search = simplePath[2];\n }\n return this;\n }\n }\n let proto = protocolPattern.exec(rest);\n if (proto) {\n proto = proto[0];\n lowerProto = proto.toLowerCase();\n this.protocol = proto;\n rest = rest.substr(proto.length);\n }\n if (slashesDenoteHost || proto || rest.match(/^\\/\\/[^@\\/]+@[^@\\/]+/)) {\n slashes = rest.substr(0, 2) === \"//\";\n if (slashes && !(proto && hostlessProtocol[proto])) {\n rest = rest.substr(2);\n this.slashes = true;\n }\n }\n if (!hostlessProtocol[proto] && (slashes || proto && !slashedProtocol[proto])) {\n let hostEnd = -1;\n for (let i = 0; i < hostEndingChars.length; i++) {\n hec = rest.indexOf(hostEndingChars[i]);\n if (hec !== -1 && (hostEnd === -1 || hec < hostEnd)) {\n hostEnd = hec;\n }\n }\n let auth, atSign;\n if (hostEnd === -1) {\n atSign = rest.lastIndexOf(\"@\");\n } else {\n atSign = rest.lastIndexOf(\"@\", hostEnd);\n }\n if (atSign !== -1) {\n auth = rest.slice(0, atSign);\n rest = rest.slice(atSign + 1);\n this.auth = auth;\n }\n hostEnd = -1;\n for (let i = 0; i < nonHostChars.length; i++) {\n hec = rest.indexOf(nonHostChars[i]);\n if (hec !== -1 && (hostEnd === -1 || hec < hostEnd)) {\n hostEnd = hec;\n }\n }\n if (hostEnd === -1) {\n hostEnd = rest.length;\n }\n if (rest[hostEnd - 1] === \":\") {\n hostEnd--;\n }\n const host = rest.slice(0, hostEnd);\n rest = rest.slice(hostEnd);\n this.parseHost(host);\n this.hostname = this.hostname || \"\";\n const ipv6Hostname = this.hostname[0] === \"[\" && this.hostname[this.hostname.length - 1] === \"]\";\n if (!ipv6Hostname) {\n const hostparts = this.hostname.split(/\\./);\n for (let i = 0, l = hostparts.length; i < l; i++) {\n const part = hostparts[i];\n if (!part) {\n continue;\n }\n if (!part.match(hostnamePartPattern)) {\n let newpart = \"\";\n for (let j = 0, k = part.length; j < k; j++) {\n if (part.charCodeAt(j) > 127) {\n newpart += \"x\";\n } else {\n newpart += part[j];\n }\n }\n if (!newpart.match(hostnamePartPattern)) {\n const validParts = hostparts.slice(0, i);\n const notHost = hostparts.slice(i + 1);\n const bit = part.match(hostnamePartStart);\n if (bit) {\n validParts.push(bit[1]);\n notHost.unshift(bit[2]);\n }\n if (notHost.length) {\n rest = notHost.join(\".\") + rest;\n }\n this.hostname = validParts.join(\".\");\n break;\n }\n }\n }\n }\n if (this.hostname.length > hostnameMaxLen) {\n this.hostname = \"\";\n }\n if (ipv6Hostname) {\n this.hostname = this.hostname.substr(1, this.hostname.length - 2);\n }\n }\n const hash = rest.indexOf(\"#\");\n if (hash !== -1) {\n this.hash = rest.substr(hash);\n rest = rest.slice(0, hash);\n }\n const qm = rest.indexOf(\"?\");\n if (qm !== -1) {\n this.search = rest.substr(qm);\n rest = rest.slice(0, qm);\n }\n if (rest) {\n this.pathname = rest;\n }\n if (slashedProtocol[lowerProto] && this.hostname && !this.pathname) {\n this.pathname = \"\";\n }\n return this;\n};\nUrl.prototype.parseHost = function(host) {\n let port = portPattern.exec(host);\n if (port) {\n port = port[0];\n if (port !== \":\") {\n this.port = port.substr(1);\n }\n host = host.substr(0, host.length - port.length);\n }\n if (host) {\n this.hostname = host;\n }\n};\nvar parse_default = urlParse;\n\n// node_modules/.pnpm/entities@4.5.0/node_modules/entities/lib/esm/generated/decode-data-html.js\nvar decode_data_html_default = new Uint16Array(\n // prettier-ignore\n 'ᵁ<Õıʊҝջאٵ۞ޢߖࠏ੊ઑඡ๭༉༦჊ረዡᐕᒝᓃᓟᔥ\\0\\0\\0\\0\\0\\0ᕫᛍᦍᰒᷝ὾⁠↰⊍⏀⏻⑂⠤⤒ⴈ⹈⿎〖㊺㘹㞬㣾㨨㩱㫠㬮ࠀEMabcfglmnoprstu\\\\bfms„‹•˜¦³¹ÈÏlig耻Æ䃆P耻&䀦cute耻Á䃁reve;䄂Āiyx}rc耻Â䃂;䐐r;쀀𝔄rave耻À䃀pha;䎑acr;䄀d;橓Āgp¡on;䄄f;쀀𝔸plyFunction;恡ing耻Å䃅Ācs¾Ãr;쀀𝒜ign;扔ilde耻Ã䃃ml耻Ä䃄ЀaceforsuåûþėĜĢħĪĀcrêòkslash;或Ŷöø;櫧ed;挆y;䐑ƀcrtąċĔause;戵noullis;愬a;䎒r;쀀𝔅pf;쀀𝔹eve;䋘còēmpeq;扎܀HOacdefhilorsuōőŖƀƞƢƵƷƺǜȕɳɸɾcy;䐧PY耻©䂩ƀcpyŝŢźute;䄆Ā;iŧŨ拒talDifferentialD;慅leys;愭ȀaeioƉƎƔƘron;䄌dil耻Ç䃇rc;䄈nint;戰ot;䄊ĀdnƧƭilla;䂸terDot;䂷òſi;䎧rcleȀDMPTLJNjǑǖot;抙inus;抖lus;投imes;抗oĀcsǢǸkwiseContourIntegral;戲eCurlyĀDQȃȏoubleQuote;思uote;怙ȀlnpuȞȨɇɕonĀ;eȥȦ户;橴ƀgitȯȶȺruent;扡nt;戯ourIntegral;戮ĀfrɌɎ;愂oduct;成nterClockwiseContourIntegral;戳oss;樯cr;쀀𝒞pĀ;Cʄʅ拓ap;才րDJSZacefiosʠʬʰʴʸˋ˗ˡ˦̳ҍĀ;oŹʥtrahd;椑cy;䐂cy;䐅cy;䐏ƀgrsʿ˄ˇger;怡r;憡hv;櫤Āayː˕ron;䄎;䐔lĀ;t˝˞戇a;䎔r;쀀𝔇Āaf˫̧Ācm˰̢riticalȀADGT̖̜̀̆cute;䂴oŴ̋̍;䋙bleAcute;䋝rave;䁠ilde;䋜ond;拄ferentialD;慆Ѱ̽\\0\\0\\0͔͂\\0Ѕf;쀀𝔻ƀ;DE͈͉͍䂨ot;惜qual;扐blèCDLRUVͣͲ΂ϏϢϸontourIntegraìȹoɴ͹\\0\\0ͻ»͉nArrow;懓Āeo·ΤftƀARTΐΖΡrrow;懐ightArrow;懔eåˊngĀLRΫτeftĀARγιrrow;柸ightArrow;柺ightArrow;柹ightĀATϘϞrrow;懒ee;抨pɁϩ\\0\\0ϯrrow;懑ownArrow;懕erticalBar;戥ǹABLRTaВЪаўѿͼrrowƀ;BUНОТ憓ar;椓pArrow;懵reve;䌑eft˒к\\0ц\\0ѐightVector;楐eeVector;楞ectorĀ;Bљњ憽ar;楖ightǔѧ\\0ѱeeVector;楟ectorĀ;BѺѻ懁ar;楗eeĀ;A҆҇护rrow;憧ĀctҒҗr;쀀𝒟rok;䄐ࠀNTacdfglmopqstuxҽӀӄӋӞӢӧӮӵԡԯԶՒ՝ՠեG;䅊H耻Ð䃐cute耻É䃉ƀaiyӒӗӜron;䄚rc耻Ê䃊;䐭ot;䄖r;쀀𝔈rave耻È䃈ement;戈ĀapӺӾcr;䄒tyɓԆ\\0\\0ԒmallSquare;旻erySmallSquare;斫ĀgpԦԪon;䄘f;쀀𝔼silon;䎕uĀaiԼՉlĀ;TՂՃ橵ilde;扂librium;懌Āci՗՚r;愰m;橳a;䎗ml耻Ë䃋Āipժկsts;戃onentialE;慇ʀcfiosօֈ֍ֲ׌y;䐤r;쀀𝔉lledɓ֗\\0\\0֣mallSquare;旼erySmallSquare;斪Ͱֺ\\0ֿ\\0\\0ׄf;쀀𝔽All;戀riertrf;愱cò׋؀JTabcdfgorstר׬ׯ׺؀ؒؖ؛؝أ٬ٲcy;䐃耻>䀾mmaĀ;d׷׸䎓;䏜reve;䄞ƀeiy؇،ؐdil;䄢rc;䄜;䐓ot;䄠r;쀀𝔊;拙pf;쀀𝔾eater̀EFGLSTصلَٖٛ٦qualĀ;Lؾؿ扥ess;招ullEqual;执reater;檢ess;扷lantEqual;橾ilde;扳cr;쀀𝒢;扫ЀAacfiosuڅڋږڛڞڪھۊRDcy;䐪Āctڐڔek;䋇;䁞irc;䄤r;愌lbertSpace;愋ǰگ\\0ڲf;愍izontalLine;攀Āctۃۅòکrok;䄦mpńېۘownHumðįqual;扏܀EJOacdfgmnostuۺ۾܃܇܎ܚܞܡܨ݄ݸދޏޕcy;䐕lig;䄲cy;䐁cute耻Í䃍Āiyܓܘrc耻Î䃎;䐘ot;䄰r;愑rave耻Ì䃌ƀ;apܠܯܿĀcgܴܷr;䄪inaryI;慈lieóϝǴ݉\\0ݢĀ;eݍݎ戬Āgrݓݘral;戫section;拂isibleĀCTݬݲomma;恣imes;恢ƀgptݿރވon;䄮f;쀀𝕀a;䎙cr;愐ilde;䄨ǫޚ\\0ޞcy;䐆l耻Ï䃏ʀcfosuެ޷޼߂ߐĀiyޱ޵rc;䄴;䐙r;쀀𝔍pf;쀀𝕁ǣ߇\\0ߌr;쀀𝒥rcy;䐈kcy;䐄΀HJacfosߤߨ߽߬߱ࠂࠈcy;䐥cy;䐌ppa;䎚Āey߶߻dil;䄶;䐚r;쀀𝔎pf;쀀𝕂cr;쀀𝒦րJTaceflmostࠥࠩࠬࡐࡣ঳সে্਷ੇcy;䐉耻<䀼ʀcmnpr࠷࠼ࡁࡄࡍute;䄹bda;䎛g;柪lacetrf;愒r;憞ƀaeyࡗ࡜ࡡron;䄽dil;䄻;䐛Āfsࡨ॰tԀACDFRTUVarࡾࢩࢱࣦ࣠ࣼयज़ΐ४Ānrࢃ࢏gleBracket;柨rowƀ;BR࢙࢚࢞憐ar;懤ightArrow;懆eiling;挈oǵࢷ\\0ࣃbleBracket;柦nǔࣈ\\0࣒eeVector;楡ectorĀ;Bࣛࣜ懃ar;楙loor;挊ightĀAV࣯ࣵrrow;憔ector;楎Āerँगeƀ;AVउऊऐ抣rrow;憤ector;楚iangleƀ;BEतथऩ抲ar;槏qual;抴pƀDTVषूौownVector;楑eeVector;楠ectorĀ;Bॖॗ憿ar;楘ectorĀ;B॥०憼ar;楒ightáΜs̀EFGLSTॾঋকঝঢভqualGreater;拚ullEqual;扦reater;扶ess;檡lantEqual;橽ilde;扲r;쀀𝔏Ā;eঽা拘ftarrow;懚idot;䄿ƀnpw৔ਖਛgȀLRlr৞৷ਂਐeftĀAR০৬rrow;柵ightArrow;柷ightArrow;柶eftĀarγਊightáοightáϊf;쀀𝕃erĀLRਢਬeftArrow;憙ightArrow;憘ƀchtਾੀੂòࡌ;憰rok;䅁;扪Ѐacefiosuਗ਼੝੠੷੼અઋ઎p;椅y;䐜Ādl੥੯iumSpace;恟lintrf;愳r;쀀𝔐nusPlus;戓pf;쀀𝕄cò੶;䎜ҀJacefostuણધભીଔଙඑ඗ඞcy;䐊cute;䅃ƀaey઴હાron;䅇dil;䅅;䐝ƀgswે૰଎ativeƀMTV૓૟૨ediumSpace;怋hiĀcn૦૘ë૙eryThiî૙tedĀGL૸ଆreaterGreateòٳessLesóੈLine;䀊r;쀀𝔑ȀBnptଢନଷ଺reak;恠BreakingSpace;䂠f;愕ڀ;CDEGHLNPRSTV୕ୖ୪୼஡௫ఄ౞಄ದ೘ൡඅ櫬Āou୛୤ngruent;扢pCap;扭oubleVerticalBar;戦ƀlqxஃஊ஛ement;戉ualĀ;Tஒஓ扠ilde;쀀≂̸ists;戄reater΀;EFGLSTஶஷ஽௉௓௘௥扯qual;扱ullEqual;쀀≧̸reater;쀀≫̸ess;批lantEqual;쀀⩾̸ilde;扵umpń௲௽ownHump;쀀≎̸qual;쀀≏̸eĀfsఊధtTriangleƀ;BEచఛడ拪ar;쀀⧏̸qual;括s̀;EGLSTవశ఼ౄోౘ扮qual;扰reater;扸ess;쀀≪̸lantEqual;쀀⩽̸ilde;扴estedĀGL౨౹reaterGreater;쀀⪢̸essLess;쀀⪡̸recedesƀ;ESಒಓಛ技qual;쀀⪯̸lantEqual;拠ĀeiಫಹverseElement;戌ghtTriangleƀ;BEೋೌ೒拫ar;쀀⧐̸qual;拭ĀquೝഌuareSuĀbp೨೹setĀ;E೰ೳ쀀⊏̸qual;拢ersetĀ;Eഃആ쀀⊐̸qual;拣ƀbcpഓതൎsetĀ;Eഛഞ쀀⊂⃒qual;抈ceedsȀ;ESTലള഻െ抁qual;쀀⪰̸lantEqual;拡ilde;쀀≿̸ersetĀ;E൘൛쀀⊃⃒qual;抉ildeȀ;EFT൮൯൵ൿ扁qual;扄ullEqual;扇ilde;扉erticalBar;戤cr;쀀𝒩ilde耻Ñ䃑;䎝܀Eacdfgmoprstuvලෂ෉෕ෛ෠෧෼ขภยา฿ไlig;䅒cute耻Ó䃓Āiy෎ීrc耻Ô䃔;䐞blac;䅐r;쀀𝔒rave耻Ò䃒ƀaei෮ෲ෶cr;䅌ga;䎩cron;䎟pf;쀀𝕆enCurlyĀDQฎบoubleQuote;怜uote;怘;橔Āclวฬr;쀀𝒪ash耻Ø䃘iŬื฼de耻Õ䃕es;樷ml耻Ö䃖erĀBP๋๠Āar๐๓r;怾acĀek๚๜;揞et;掴arenthesis;揜Ҁacfhilors๿ງຊຏຒດຝະ໼rtialD;戂y;䐟r;쀀𝔓i;䎦;䎠usMinus;䂱Āipຢອncareplanåڝf;愙Ȁ;eio຺ູ໠໤檻cedesȀ;EST່້໏໚扺qual;檯lantEqual;扼ilde;找me;怳Ādp໩໮uct;戏ortionĀ;aȥ໹l;戝Āci༁༆r;쀀𝒫;䎨ȀUfos༑༖༛༟OT耻\"䀢r;쀀𝔔pf;愚cr;쀀𝒬؀BEacefhiorsu༾གྷཇའཱིྦྷྪྭ႖ႩႴႾarr;椐G耻®䂮ƀcnrཎནབute;䅔g;柫rĀ;tཛྷཝ憠l;椖ƀaeyཧཬཱron;䅘dil;䅖;䐠Ā;vླྀཹ愜erseĀEUྂྙĀlq྇ྎement;戋uilibrium;懋pEquilibrium;楯r»ཹo;䎡ghtЀACDFTUVa࿁࿫࿳ဢဨၛႇϘĀnr࿆࿒gleBracket;柩rowƀ;BL࿜࿝࿡憒ar;懥eftArrow;懄eiling;按oǵ࿹\\0စbleBracket;柧nǔည\\0နeeVector;楝ectorĀ;Bဝသ懂ar;楕loor;挋Āerိ၃eƀ;AVဵံြ抢rrow;憦ector;楛iangleƀ;BEၐၑၕ抳ar;槐qual;抵pƀDTVၣၮၸownVector;楏eeVector;楜ectorĀ;Bႂႃ憾ar;楔ectorĀ;B႑႒懀ar;楓Āpuႛ႞f;愝ndImplies;楰ightarrow;懛ĀchႹႼr;愛;憱leDelayed;槴ڀHOacfhimoqstuფჱჷჽᄙᄞᅑᅖᅡᅧᆵᆻᆿĀCcჩხHcy;䐩y;䐨FTcy;䐬cute;䅚ʀ;aeiyᄈᄉᄎᄓᄗ檼ron;䅠dil;䅞rc;䅜;䐡r;쀀𝔖ortȀDLRUᄪᄴᄾᅉownArrow»ОeftArrow»࢚ightArrow»࿝pArrow;憑gma;䎣allCircle;战pf;쀀𝕊ɲᅭ\\0\\0ᅰt;戚areȀ;ISUᅻᅼᆉᆯ斡ntersection;抓uĀbpᆏᆞsetĀ;Eᆗᆘ抏qual;抑ersetĀ;Eᆨᆩ抐qual;抒nion;抔cr;쀀𝒮ar;拆ȀbcmpᇈᇛሉላĀ;sᇍᇎ拐etĀ;Eᇍᇕqual;抆ĀchᇠህeedsȀ;ESTᇭᇮᇴᇿ扻qual;檰lantEqual;扽ilde;承Tháྌ;我ƀ;esሒሓሣ拑rsetĀ;Eሜም抃qual;抇et»ሓրHRSacfhiorsሾቄ቉ቕ቞ቱቶኟዂወዑORN耻Þ䃞ADE;愢ĀHc቎ቒcy;䐋y;䐦Ābuቚቜ;䀉;䎤ƀaeyብቪቯron;䅤dil;䅢;䐢r;쀀𝔗Āeiቻ኉Dzኀ\\0ኇefore;戴a;䎘Ācn኎ኘkSpace;쀀  Space;怉ldeȀ;EFTካኬኲኼ戼qual;扃ullEqual;扅ilde;扈pf;쀀𝕋ipleDot;惛Āctዖዛr;쀀𝒯rok;䅦ૡዷጎጚጦ\\0ጬጱ\\0\\0\\0\\0\\0ጸጽ፷ᎅ\\0᏿ᐄᐊᐐĀcrዻጁute耻Ú䃚rĀ;oጇገ憟cir;楉rǣጓ\\0጖y;䐎ve;䅬Āiyጞጣrc耻Û䃛;䐣blac;䅰r;쀀𝔘rave耻Ù䃙acr;䅪Ādiፁ፩erĀBPፈ፝Āarፍፐr;䁟acĀekፗፙ;揟et;掵arenthesis;揝onĀ;P፰፱拃lus;抎Āgp፻፿on;䅲f;쀀𝕌ЀADETadps᎕ᎮᎸᏄϨᏒᏗᏳrrowƀ;BDᅐᎠᎤar;椒ownArrow;懅ownArrow;憕quilibrium;楮eeĀ;AᏋᏌ报rrow;憥ownáϳerĀLRᏞᏨeftArrow;憖ightArrow;憗iĀ;lᏹᏺ䏒on;䎥ing;䅮cr;쀀𝒰ilde;䅨ml耻Ü䃜ҀDbcdefosvᐧᐬᐰᐳᐾᒅᒊᒐᒖash;披ar;櫫y;䐒ashĀ;lᐻᐼ抩;櫦Āerᑃᑅ;拁ƀbtyᑌᑐᑺar;怖Ā;iᑏᑕcalȀBLSTᑡᑥᑪᑴar;戣ine;䁼eparator;杘ilde;所ThinSpace;怊r;쀀𝔙pf;쀀𝕍cr;쀀𝒱dash;抪ʀcefosᒧᒬᒱᒶᒼirc;䅴dge;拀r;쀀𝔚pf;쀀𝕎cr;쀀𝒲Ȁfiosᓋᓐᓒᓘr;쀀𝔛;䎞pf;쀀𝕏cr;쀀𝒳ҀAIUacfosuᓱᓵᓹᓽᔄᔏᔔᔚᔠcy;䐯cy;䐇cy;䐮cute耻Ý䃝Āiyᔉᔍrc;䅶;䐫r;쀀𝔜pf;쀀𝕐cr;쀀𝒴ml;䅸ЀHacdefosᔵᔹᔿᕋᕏᕝᕠᕤcy;䐖cute;䅹Āayᕄᕉron;䅽;䐗ot;䅻Dzᕔ\\0ᕛoWidtè૙a;䎖r;愨pf;愤cr;쀀𝒵௡ᖃᖊᖐ\\0ᖰᖶᖿ\\0\\0\\0\\0ᗆᗛᗫᙟ᙭\\0ᚕ᚛ᚲᚹ\\0ᚾcute耻á䃡reve;䄃̀;Ediuyᖜᖝᖡᖣᖨᖭ戾;쀀∾̳;房rc耻â䃢te肻´̆;䐰lig耻æ䃦Ā;r²ᖺ;쀀𝔞rave耻à䃠ĀepᗊᗖĀfpᗏᗔsym;愵èᗓha;䎱ĀapᗟcĀclᗤᗧr;䄁g;樿ɤᗰ\\0\\0ᘊʀ;adsvᗺᗻᗿᘁᘇ戧nd;橕;橜lope;橘;橚΀;elmrszᘘᘙᘛᘞᘿᙏᙙ戠;榤e»ᘙsdĀ;aᘥᘦ戡ѡᘰᘲᘴᘶᘸᘺᘼᘾ;榨;榩;榪;榫;榬;榭;榮;榯tĀ;vᙅᙆ戟bĀ;dᙌᙍ抾;榝Āptᙔᙗh;戢»¹arr;捼Āgpᙣᙧon;䄅f;쀀𝕒΀;Eaeiop዁ᙻᙽᚂᚄᚇᚊ;橰cir;橯;扊d;手s;䀧roxĀ;e዁ᚒñᚃing耻å䃥ƀctyᚡᚦᚨr;쀀𝒶;䀪mpĀ;e዁ᚯñʈilde耻ã䃣ml耻ä䃤Āciᛂᛈoninôɲnt;樑ࠀNabcdefiklnoprsu᛭ᛱᜰ᜼ᝃᝈ᝸᝽០៦ᠹᡐᜍ᤽᥈ᥰot;櫭Ācrᛶ᜞kȀcepsᜀᜅᜍᜓong;扌psilon;䏶rime;怵imĀ;e᜚᜛戽q;拍Ŷᜢᜦee;抽edĀ;gᜬᜭ挅e»ᜭrkĀ;t፜᜷brk;掶Āoyᜁᝁ;䐱quo;怞ʀcmprtᝓ᝛ᝡᝤᝨausĀ;eĊĉptyv;榰séᜌnoõēƀahwᝯ᝱ᝳ;䎲;愶een;扬r;쀀𝔟g΀costuvwឍឝឳេ៕៛៞ƀaiuបពរðݠrc;旯p»፱ƀdptឤឨឭot;樀lus;樁imes;樂ɱឹ\\0\\0ើcup;樆ar;昅riangleĀdu៍្own;施p;斳plus;樄eåᑄåᒭarow;植ƀako៭ᠦᠵĀcn៲ᠣkƀlst៺֫᠂ozenge;槫riangleȀ;dlr᠒᠓᠘᠝斴own;斾eft;旂ight;斸k;搣Ʊᠫ\\0ᠳƲᠯ\\0ᠱ;斒;斑4;斓ck;斈ĀeoᠾᡍĀ;qᡃᡆ쀀=⃥uiv;쀀≡⃥t;挐Ȁptwxᡙᡞᡧᡬf;쀀𝕓Ā;tᏋᡣom»Ꮜtie;拈؀DHUVbdhmptuvᢅᢖᢪᢻᣗᣛᣬ᣿ᤅᤊᤐᤡȀLRlrᢎᢐᢒᢔ;敗;敔;敖;敓ʀ;DUduᢡᢢᢤᢦᢨ敐;敦;敩;敤;敧ȀLRlrᢳᢵᢷᢹ;敝;敚;敜;教΀;HLRhlrᣊᣋᣍᣏᣑᣓᣕ救;敬;散;敠;敫;敢;敟ox;槉ȀLRlrᣤᣦᣨᣪ;敕;敒;攐;攌ʀ;DUduڽ᣷᣹᣻᣽;敥;敨;攬;攴inus;抟lus;択imes;抠ȀLRlrᤙᤛᤝ᤟;敛;敘;攘;攔΀;HLRhlrᤰᤱᤳᤵᤷ᤻᤹攂;敪;敡;敞;攼;攤;攜Āevģ᥂bar耻¦䂦Ȁceioᥑᥖᥚᥠr;쀀𝒷mi;恏mĀ;e᜚᜜lƀ;bhᥨᥩᥫ䁜;槅sub;柈Ŭᥴ᥾lĀ;e᥹᥺怢t»᥺pƀ;Eeįᦅᦇ;檮Ā;qۜۛೡᦧ\\0᧨ᨑᨕᨲ\\0ᨷᩐ\\0\\0᪴\\0\\0᫁\\0\\0ᬡᬮ᭍᭒\\0᯽\\0ᰌƀcpr᦭ᦲ᧝ute;䄇̀;abcdsᦿᧀᧄ᧊᧕᧙戩nd;橄rcup;橉Āau᧏᧒p;橋p;橇ot;橀;쀀∩︀Āeo᧢᧥t;恁îړȀaeiu᧰᧻ᨁᨅǰ᧵\\0᧸s;橍on;䄍dil耻ç䃧rc;䄉psĀ;sᨌᨍ橌m;橐ot;䄋ƀdmnᨛᨠᨦil肻¸ƭptyv;榲t脀¢;eᨭᨮ䂢räƲr;쀀𝔠ƀceiᨽᩀᩍy;䑇ckĀ;mᩇᩈ朓ark»ᩈ;䏇r΀;Ecefms᩟᩠ᩢᩫ᪤᪪᪮旋;槃ƀ;elᩩᩪᩭ䋆q;扗eɡᩴ\\0\\0᪈rrowĀlr᩼᪁eft;憺ight;憻ʀRSacd᪒᪔᪖᪚᪟»ཇ;擈st;抛irc;抚ash;抝nint;樐id;櫯cir;槂ubsĀ;u᪻᪼晣it»᪼ˬ᫇᫔᫺\\0ᬊonĀ;eᫍᫎ䀺Ā;qÇÆɭ᫙\\0\\0᫢aĀ;t᫞᫟䀬;䁀ƀ;fl᫨᫩᫫戁îᅠeĀmx᫱᫶ent»᫩eóɍǧ᫾\\0ᬇĀ;dኻᬂot;橭nôɆƀfryᬐᬔᬗ;쀀𝕔oäɔ脀©;sŕᬝr;愗Āaoᬥᬩrr;憵ss;朗Ācuᬲᬷr;쀀𝒸Ābpᬼ᭄Ā;eᭁᭂ櫏;櫑Ā;eᭉᭊ櫐;櫒dot;拯΀delprvw᭠᭬᭷ᮂᮬᯔ᯹arrĀlr᭨᭪;椸;椵ɰ᭲\\0\\0᭵r;拞c;拟arrĀ;p᭿ᮀ憶;椽̀;bcdosᮏᮐᮖᮡᮥᮨ截rcap;橈Āauᮛᮞp;橆p;橊ot;抍r;橅;쀀∪︀Ȁalrv᮵ᮿᯞᯣrrĀ;mᮼᮽ憷;椼yƀevwᯇᯔᯘqɰᯎ\\0\\0ᯒreã᭳uã᭵ee;拎edge;拏en耻¤䂤earrowĀlrᯮ᯳eft»ᮀight»ᮽeäᯝĀciᰁᰇoninôǷnt;戱lcty;挭ঀAHabcdefhijlorstuwz᰸᰻᰿ᱝᱩᱵᲊᲞᲬᲷ᳻᳿ᴍᵻᶑᶫᶻ᷆᷍rò΁ar;楥Ȁglrs᱈ᱍ᱒᱔ger;怠eth;愸òᄳhĀ;vᱚᱛ怐»ऊūᱡᱧarow;椏aã̕Āayᱮᱳron;䄏;䐴ƀ;ao̲ᱼᲄĀgrʿᲁr;懊tseq;橷ƀglmᲑᲔᲘ耻°䂰ta;䎴ptyv;榱ĀirᲣᲨsht;楿;쀀𝔡arĀlrᲳᲵ»ࣜ»သʀaegsv᳂͸᳖᳜᳠mƀ;oș᳊᳔ndĀ;ș᳑uit;晦amma;䏝in;拲ƀ;io᳧᳨᳸䃷de脀÷;o᳧ᳰntimes;拇nø᳷cy;䑒cɯᴆ\\0\\0ᴊrn;挞op;挍ʀlptuwᴘᴝᴢᵉᵕlar;䀤f;쀀𝕕ʀ;emps̋ᴭᴷᴽᵂqĀ;d͒ᴳot;扑inus;戸lus;戔quare;抡blebarwedgåúnƀadhᄮᵝᵧownarrowóᲃarpoonĀlrᵲᵶefôᲴighôᲶŢᵿᶅkaro÷གɯᶊ\\0\\0ᶎrn;挟op;挌ƀcotᶘᶣᶦĀryᶝᶡ;쀀𝒹;䑕l;槶rok;䄑Ādrᶰᶴot;拱iĀ;fᶺ᠖斿Āah᷀᷃ròЩaòྦangle;榦Āci᷒ᷕy;䑟grarr;柿ऀDacdefglmnopqrstuxḁḉḙḸոḼṉṡṾấắẽỡἪἷὄ὎὚ĀDoḆᴴoôᲉĀcsḎḔute耻é䃩ter;橮ȀaioyḢḧḱḶron;䄛rĀ;cḭḮ扖耻ê䃪lon;払;䑍ot;䄗ĀDrṁṅot;扒;쀀𝔢ƀ;rsṐṑṗ檚ave耻è䃨Ā;dṜṝ檖ot;檘Ȁ;ilsṪṫṲṴ檙nters;揧;愓Ā;dṹṺ檕ot;檗ƀapsẅẉẗcr;䄓tyƀ;svẒẓẕ戅et»ẓpĀ1;ẝẤijạả;怄;怅怃ĀgsẪẬ;䅋p;怂ĀgpẴẸon;䄙f;쀀𝕖ƀalsỄỎỒrĀ;sỊị拕l;槣us;橱iƀ;lvỚớở䎵on»ớ;䏵ȀcsuvỪỳἋἣĀioữḱrc»Ḯɩỹ\\0\\0ỻíՈantĀglἂἆtr»ṝess»Ṻƀaeiἒ἖Ἒls;䀽st;扟vĀ;DȵἠD;橸parsl;槥ĀDaἯἳot;打rr;楱ƀcdiἾὁỸr;愯oô͒ĀahὉὋ;䎷耻ð䃰Āmrὓὗl耻ë䃫o;悬ƀcipὡὤὧl;䀡sôծĀeoὬὴctatioîՙnentialåչৡᾒ\\0ᾞ\\0ᾡᾧ\\0\\0ῆῌ\\0ΐ\\0ῦῪ \\0 ⁚llingdotseñṄy;䑄male;晀ƀilrᾭᾳ῁lig;耀ffiɩᾹ\\0\\0᾽g;耀ffig;耀ffl;쀀𝔣lig;耀filig;쀀fjƀaltῙ῜ῡt;晭ig;耀flns;斱of;䆒ǰ΅\\0ῳf;쀀𝕗ĀakֿῷĀ;vῼ´拔;櫙artint;樍Āao‌⁕Ācs‑⁒ႉ‸⁅⁈\\0⁐β•‥‧‪‬\\0‮耻½䂽;慓耻¼䂼;慕;慙;慛Ƴ‴\\0‶;慔;慖ʴ‾⁁\\0\\0⁃耻¾䂾;慗;慜5;慘ƶ⁌\\0⁎;慚;慝8;慞l;恄wn;挢cr;쀀𝒻ࢀEabcdefgijlnorstv₂₉₟₥₰₴⃰⃵⃺⃿℃ℒℸ̗ℾ⅒↞Ā;lٍ₇;檌ƀcmpₐₕ₝ute;䇵maĀ;dₜ᳚䎳;檆reve;䄟Āiy₪₮rc;䄝;䐳ot;䄡Ȁ;lqsؾق₽⃉ƀ;qsؾٌ⃄lanô٥Ȁ;cdl٥⃒⃥⃕c;檩otĀ;o⃜⃝檀Ā;l⃢⃣檂;檄Ā;e⃪⃭쀀⋛︀s;檔r;쀀𝔤Ā;gٳ؛mel;愷cy;䑓Ȁ;Eajٚℌℎℐ;檒;檥;檤ȀEaesℛℝ℩ℴ;扩pĀ;p℣ℤ檊rox»ℤĀ;q℮ℯ檈Ā;q℮ℛim;拧pf;쀀𝕘Āci⅃ⅆr;愊mƀ;el٫ⅎ⅐;檎;檐茀>;cdlqr׮ⅠⅪⅮⅳⅹĀciⅥⅧ;檧r;橺ot;拗Par;榕uest;橼ʀadelsↄⅪ←ٖ↛ǰ↉\\0↎proø₞r;楸qĀlqؿ↖lesó₈ií٫Āen↣↭rtneqq;쀀≩︀Å↪ԀAabcefkosy⇄⇇⇱⇵⇺∘∝∯≨≽ròΠȀilmr⇐⇔⇗⇛rsðᒄf»․ilôکĀdr⇠⇤cy;䑊ƀ;cwࣴ⇫⇯ir;楈;憭ar;意irc;䄥ƀalr∁∎∓rtsĀ;u∉∊晥it»∊lip;怦con;抹r;쀀𝔥sĀew∣∩arow;椥arow;椦ʀamopr∺∾≃≞≣rr;懿tht;戻kĀlr≉≓eftarrow;憩ightarrow;憪f;쀀𝕙bar;怕ƀclt≯≴≸r;쀀𝒽asè⇴rok;䄧Ābp⊂⊇ull;恃hen»ᱛૡ⊣\\0⊪\\0⊸⋅⋎\\0⋕⋳\\0\\0⋸⌢⍧⍢⍿\\0⎆⎪⎴cute耻í䃭ƀ;iyݱ⊰⊵rc耻î䃮;䐸Ācx⊼⊿y;䐵cl耻¡䂡ĀfrΟ⋉;쀀𝔦rave耻ì䃬Ȁ;inoܾ⋝⋩⋮Āin⋢⋦nt;樌t;戭fin;槜ta;愩lig;䄳ƀaop⋾⌚⌝ƀcgt⌅⌈⌗r;䄫ƀelpܟ⌏⌓inåގarôܠh;䄱f;抷ed;䆵ʀ;cfotӴ⌬⌱⌽⍁are;愅inĀ;t⌸⌹戞ie;槝doô⌙ʀ;celpݗ⍌⍐⍛⍡al;抺Āgr⍕⍙eróᕣã⍍arhk;樗rod;樼Ȁcgpt⍯⍲⍶⍻y;䑑on;䄯f;쀀𝕚a;䎹uest耻¿䂿Āci⎊⎏r;쀀𝒾nʀ;EdsvӴ⎛⎝⎡ӳ;拹ot;拵Ā;v⎦⎧拴;拳Ā;iݷ⎮lde;䄩ǫ⎸\\0⎼cy;䑖l耻ï䃯̀cfmosu⏌⏗⏜⏡⏧⏵Āiy⏑⏕rc;䄵;䐹r;쀀𝔧ath;䈷pf;쀀𝕛ǣ⏬\\0⏱r;쀀𝒿rcy;䑘kcy;䑔Ѐacfghjos␋␖␢␧␭␱␵␻ppaĀ;v␓␔䎺;䏰Āey␛␠dil;䄷;䐺r;쀀𝔨reen;䄸cy;䑅cy;䑜pf;쀀𝕜cr;쀀𝓀஀ABEHabcdefghjlmnoprstuv⑰⒁⒆⒍⒑┎┽╚▀♎♞♥♹♽⚚⚲⛘❝❨➋⟀⠁⠒ƀart⑷⑺⑼rò৆òΕail;椛arr;椎Ā;gঔ⒋;檋ar;楢ॣ⒥\\0⒪\\0⒱\\0\\0\\0\\0\\0⒵Ⓔ\\0ⓆⓈⓍ\\0⓹ute;䄺mptyv;榴raîࡌbda;䎻gƀ;dlࢎⓁⓃ;榑åࢎ;檅uo耻«䂫rЀ;bfhlpst࢙ⓞⓦⓩ⓫⓮⓱⓵Ā;f࢝ⓣs;椟s;椝ë≒p;憫l;椹im;楳l;憢ƀ;ae⓿─┄檫il;椙Ā;s┉┊檭;쀀⪭︀ƀabr┕┙┝rr;椌rk;杲Āak┢┬cĀek┨┪;䁻;䁛Āes┱┳;榋lĀdu┹┻;榏;榍Ȁaeuy╆╋╖╘ron;䄾Ādi═╔il;䄼ìࢰâ┩;䐻Ȁcqrs╣╦╭╽a;椶uoĀ;rนᝆĀdu╲╷har;楧shar;楋h;憲ʀ;fgqs▋▌উ◳◿扤tʀahlrt▘▤▷◂◨rrowĀ;t࢙□aé⓶arpoonĀdu▯▴own»њp»०eftarrows;懇ightƀahs◍◖◞rrowĀ;sࣴࢧarpoonó྘quigarro÷⇰hreetimes;拋ƀ;qs▋ও◺lanôবʀ;cdgsব☊☍☝☨c;檨otĀ;o☔☕橿Ā;r☚☛檁;檃Ā;e☢☥쀀⋚︀s;檓ʀadegs☳☹☽♉♋pproøⓆot;拖qĀgq♃♅ôউgtò⒌ôছiíলƀilr♕࣡♚sht;楼;쀀𝔩Ā;Eজ♣;檑š♩♶rĀdu▲♮Ā;l॥♳;楪lk;斄cy;䑙ʀ;achtੈ⚈⚋⚑⚖rò◁orneòᴈard;楫ri;旺Āio⚟⚤dot;䅀ustĀ;a⚬⚭掰che»⚭ȀEaes⚻⚽⛉⛔;扨pĀ;p⛃⛄檉rox»⛄Ā;q⛎⛏檇Ā;q⛎⚻im;拦Ѐabnoptwz⛩⛴⛷✚✯❁❇❐Ānr⛮⛱g;柬r;懽rëࣁgƀlmr⛿✍✔eftĀar০✇ightá৲apsto;柼ightá৽parrowĀlr✥✩efô⓭ight;憬ƀafl✶✹✽r;榅;쀀𝕝us;樭imes;樴š❋❏st;戗áፎƀ;ef❗❘᠀旊nge»❘arĀ;l❤❥䀨t;榓ʀachmt❳❶❼➅➇ròࢨorneòᶌarĀ;d྘➃;業;怎ri;抿̀achiqt➘➝ੀ➢➮➻quo;怹r;쀀𝓁mƀ;egল➪➬;檍;檏Ābu┪➳oĀ;rฟ➹;怚rok;䅂萀<;cdhilqrࠫ⟒☹⟜⟠⟥⟪⟰Āci⟗⟙;檦r;橹reå◲mes;拉arr;楶uest;橻ĀPi⟵⟹ar;榖ƀ;ef⠀भ᠛旃rĀdu⠇⠍shar;楊har;楦Āen⠗⠡rtneqq;쀀≨︀Å⠞܀Dacdefhilnopsu⡀⡅⢂⢎⢓⢠⢥⢨⣚⣢⣤ઃ⣳⤂Dot;戺Ȁclpr⡎⡒⡣⡽r耻¯䂯Āet⡗⡙;時Ā;e⡞⡟朠se»⡟Ā;sျ⡨toȀ;dluျ⡳⡷⡻owîҌefôएðᏑker;斮Āoy⢇⢌mma;権;䐼ash;怔asuredangle»ᘦr;쀀𝔪o;愧ƀcdn⢯⢴⣉ro耻µ䂵Ȁ;acdᑤ⢽⣀⣄sôᚧir;櫰ot肻·Ƶusƀ;bd⣒ᤃ⣓戒Ā;uᴼ⣘;横ţ⣞⣡p;櫛ò−ðઁĀdp⣩⣮els;抧f;쀀𝕞Āct⣸⣽r;쀀𝓂pos»ᖝƀ;lm⤉⤊⤍䎼timap;抸ఀGLRVabcdefghijlmoprstuvw⥂⥓⥾⦉⦘⧚⧩⨕⨚⩘⩝⪃⪕⪤⪨⬄⬇⭄⭿⮮ⰴⱧⱼ⳩Āgt⥇⥋;쀀⋙̸Ā;v⥐௏쀀≫⃒ƀelt⥚⥲⥶ftĀar⥡⥧rrow;懍ightarrow;懎;쀀⋘̸Ā;v⥻ే쀀≪⃒ightarrow;懏ĀDd⦎⦓ash;抯ash;抮ʀbcnpt⦣⦧⦬⦱⧌la»˞ute;䅄g;쀀∠⃒ʀ;Eiop඄⦼⧀⧅⧈;쀀⩰̸d;쀀≋̸s;䅉roø඄urĀ;a⧓⧔普lĀ;s⧓ସdz⧟\\0⧣p肻 ଷmpĀ;e௹ఀʀaeouy⧴⧾⨃⨐⨓ǰ⧹\\0⧻;橃on;䅈dil;䅆ngĀ;dൾ⨊ot;쀀⩭̸p;橂;䐽ash;怓΀;Aadqsxஒ⨩⨭⨻⩁⩅⩐rr;懗rĀhr⨳⨶k;椤Ā;oᏲᏰot;쀀≐̸uiöୣĀei⩊⩎ar;椨í஘istĀ;s஠டr;쀀𝔫ȀEest௅⩦⩹⩼ƀ;qs஼⩭௡ƀ;qs஼௅⩴lanô௢ií௪Ā;rஶ⪁»ஷƀAap⪊⪍⪑rò⥱rr;憮ar;櫲ƀ;svྍ⪜ྌĀ;d⪡⪢拼;拺cy;䑚΀AEadest⪷⪺⪾⫂⫅⫶⫹rò⥦;쀀≦̸rr;憚r;急Ȁ;fqs఻⫎⫣⫯tĀar⫔⫙rro÷⫁ightarro÷⪐ƀ;qs఻⪺⫪lanôౕĀ;sౕ⫴»శiíౝĀ;rవ⫾iĀ;eచథiäඐĀpt⬌⬑f;쀀𝕟膀¬;in⬙⬚⬶䂬nȀ;Edvஉ⬤⬨⬮;쀀⋹̸ot;쀀⋵̸ǡஉ⬳⬵;拷;拶iĀ;vಸ⬼ǡಸ⭁⭃;拾;拽ƀaor⭋⭣⭩rȀ;ast୻⭕⭚⭟lleì୻l;쀀⫽⃥;쀀∂̸lint;樔ƀ;ceಒ⭰⭳uåಥĀ;cಘ⭸Ā;eಒ⭽ñಘȀAait⮈⮋⮝⮧rò⦈rrƀ;cw⮔⮕⮙憛;쀀⤳̸;쀀↝̸ghtarrow»⮕riĀ;eೋೖ΀chimpqu⮽⯍⯙⬄୸⯤⯯Ȁ;cerല⯆ഷ⯉uå൅;쀀𝓃ortɭ⬅\\0\\0⯖ará⭖mĀ;e൮⯟Ā;q൴൳suĀbp⯫⯭å೸åഋƀbcp⯶ⰑⰙȀ;Ees⯿ⰀഢⰄ抄;쀀⫅̸etĀ;eഛⰋqĀ;qണⰀcĀ;eലⰗñസȀ;EesⰢⰣൟⰧ抅;쀀⫆̸etĀ;e൘ⰮqĀ;qൠⰣȀgilrⰽⰿⱅⱇìௗlde耻ñ䃱çృiangleĀlrⱒⱜeftĀ;eచⱚñదightĀ;eೋⱥñ೗Ā;mⱬⱭ䎽ƀ;esⱴⱵⱹ䀣ro;愖p;怇ҀDHadgilrsⲏⲔⲙⲞⲣⲰⲶⳓⳣash;抭arr;椄p;쀀≍⃒ash;抬ĀetⲨⲬ;쀀≥⃒;쀀>⃒nfin;槞ƀAetⲽⳁⳅrr;椂;쀀≤⃒Ā;rⳊⳍ쀀<⃒ie;쀀⊴⃒ĀAtⳘⳜrr;椃rie;쀀⊵⃒im;쀀∼⃒ƀAan⳰⳴ⴂrr;懖rĀhr⳺⳽k;椣Ā;oᏧᏥear;椧ቓ᪕\\0\\0\\0\\0\\0\\0\\0\\0\\0\\0\\0\\0\\0ⴭ\\0ⴸⵈⵠⵥ⵲ⶄᬇ\\0\\0ⶍⶫ\\0ⷈⷎ\\0ⷜ⸙⸫⸾⹃Ācsⴱ᪗ute耻ó䃳ĀiyⴼⵅrĀ;c᪞ⵂ耻ô䃴;䐾ʀabios᪠ⵒⵗLjⵚlac;䅑v;樸old;榼lig;䅓Ācr⵩⵭ir;榿;쀀𝔬ͯ⵹\\0\\0⵼\\0ⶂn;䋛ave耻ò䃲;槁Ābmⶈ෴ar;榵Ȁacitⶕ⶘ⶥⶨrò᪀Āir⶝ⶠr;榾oss;榻nå๒;槀ƀaeiⶱⶵⶹcr;䅍ga;䏉ƀcdnⷀⷅǍron;䎿;榶pf;쀀𝕠ƀaelⷔ⷗ǒr;榷rp;榹΀;adiosvⷪⷫⷮ⸈⸍⸐⸖戨rò᪆Ȁ;efmⷷⷸ⸂⸅橝rĀ;oⷾⷿ愴f»ⷿ耻ª䂪耻º䂺gof;抶r;橖lope;橗;橛ƀclo⸟⸡⸧ò⸁ash耻ø䃸l;折iŬⸯ⸴de耻õ䃵esĀ;aǛ⸺s;樶ml耻ö䃶bar;挽ૡ⹞\\0⹽\\0⺀⺝\\0⺢⺹\\0\\0⻋ຜ\\0⼓\\0\\0⼫⾼\\0⿈rȀ;astЃ⹧⹲຅脀¶;l⹭⹮䂶leìЃɩ⹸\\0\\0⹻m;櫳;櫽y;䐿rʀcimpt⺋⺏⺓ᡥ⺗nt;䀥od;䀮il;怰enk;怱r;쀀𝔭ƀimo⺨⺰⺴Ā;v⺭⺮䏆;䏕maô੶ne;明ƀ;tv⺿⻀⻈䏀chfork»´;䏖Āau⻏⻟nĀck⻕⻝kĀ;h⇴⻛;愎ö⇴sҀ;abcdemst⻳⻴ᤈ⻹⻽⼄⼆⼊⼎䀫cir;樣ir;樢Āouᵀ⼂;樥;橲n肻±ຝim;樦wo;樧ƀipu⼙⼠⼥ntint;樕f;쀀𝕡nd耻£䂣Ԁ;Eaceinosu່⼿⽁⽄⽇⾁⾉⾒⽾⾶;檳p;檷uå໙Ā;c໎⽌̀;acens່⽙⽟⽦⽨⽾pproø⽃urlyeñ໙ñ໎ƀaes⽯⽶⽺pprox;檹qq;檵im;拨iíໟmeĀ;s⾈ຮ怲ƀEas⽸⾐⽺ð⽵ƀdfp໬⾙⾯ƀals⾠⾥⾪lar;挮ine;挒urf;挓Ā;t໻⾴ï໻rel;抰Āci⿀⿅r;쀀𝓅;䏈ncsp;怈̀fiopsu⿚⋢⿟⿥⿫⿱r;쀀𝔮pf;쀀𝕢rime;恗cr;쀀𝓆ƀaeo⿸〉〓tĀei⿾々rnionóڰnt;樖stĀ;e【】䀿ñἙô༔઀ABHabcdefhilmnoprstux぀けさすムㄎㄫㅇㅢㅲㆎ㈆㈕㈤㈩㉘㉮㉲㊐㊰㊷ƀartぇおがròႳòϝail;検aròᱥar;楤΀cdenqrtとふへみわゔヌĀeuねぱ;쀀∽̱te;䅕iãᅮmptyv;榳gȀ;del࿑らるろ;榒;榥å࿑uo耻»䂻rր;abcfhlpstw࿜ガクシスゼゾダッデナp;極Ā;f࿠ゴs;椠;椳s;椞ë≝ð✮l;楅im;楴l;憣;憝Āaiパフil;椚oĀ;nホボ戶aló༞ƀabrョリヮrò៥rk;杳ĀakンヽcĀekヹ・;䁽;䁝Āes㄂㄄;榌lĀduㄊㄌ;榎;榐Ȁaeuyㄗㄜㄧㄩron;䅙Ādiㄡㄥil;䅗ì࿲âヺ;䑀Ȁclqsㄴㄷㄽㅄa;椷dhar;楩uoĀ;rȎȍh;憳ƀacgㅎㅟངlȀ;ipsླྀㅘㅛႜnåႻarôྩt;断ƀilrㅩဣㅮsht;楽;쀀𝔯ĀaoㅷㆆrĀduㅽㅿ»ѻĀ;l႑ㆄ;楬Ā;vㆋㆌ䏁;䏱ƀgns㆕ㇹㇼht̀ahlrstㆤㆰ㇂㇘㇤㇮rrowĀ;t࿜ㆭaéトarpoonĀduㆻㆿowîㅾp»႒eftĀah㇊㇐rrowó࿪arpoonóՑightarrows;應quigarro÷ニhreetimes;拌g;䋚ingdotseñἲƀahm㈍㈐㈓rò࿪aòՑ;怏oustĀ;a㈞㈟掱che»㈟mid;櫮Ȁabpt㈲㈽㉀㉒Ānr㈷㈺g;柭r;懾rëဃƀafl㉇㉊㉎r;榆;쀀𝕣us;樮imes;樵Āap㉝㉧rĀ;g㉣㉤䀩t;榔olint;樒arò㇣Ȁachq㉻㊀Ⴜ㊅quo;怺r;쀀𝓇Ābu・㊊oĀ;rȔȓƀhir㊗㊛㊠reåㇸmes;拊iȀ;efl㊪ၙᠡ㊫方tri;槎luhar;楨;愞ൡ㋕㋛㋟㌬㌸㍱\\0㍺㎤\\0\\0㏬㏰\\0㐨㑈㑚㒭㒱㓊㓱\\0㘖\\0\\0㘳cute;䅛quï➺Ԁ;Eaceinpsyᇭ㋳㋵㋿㌂㌋㌏㌟㌦㌩;檴ǰ㋺\\0㋼;檸on;䅡uåᇾĀ;dᇳ㌇il;䅟rc;䅝ƀEas㌖㌘㌛;檶p;檺im;择olint;樓iíሄ;䑁otƀ;be㌴ᵇ㌵担;橦΀Aacmstx㍆㍊㍗㍛㍞㍣㍭rr;懘rĀhr㍐㍒ë∨Ā;oਸ਼਴t耻§䂧i;䀻war;椩mĀin㍩ðnuóñt;朶rĀ;o㍶⁕쀀𝔰Ȁacoy㎂㎆㎑㎠rp;景Āhy㎋㎏cy;䑉;䑈rtɭ㎙\\0\\0㎜iäᑤaraì⹯耻­䂭Āgm㎨㎴maƀ;fv㎱㎲㎲䏃;䏂Ѐ;deglnprካ㏅㏉㏎㏖㏞㏡㏦ot;橪Ā;q኱ኰĀ;E㏓㏔檞;檠Ā;E㏛㏜檝;檟e;扆lus;樤arr;楲aròᄽȀaeit㏸㐈㐏㐗Āls㏽㐄lsetmé㍪hp;樳parsl;槤Ādlᑣ㐔e;挣Ā;e㐜㐝檪Ā;s㐢㐣檬;쀀⪬︀ƀflp㐮㐳㑂tcy;䑌Ā;b㐸㐹䀯Ā;a㐾㐿槄r;挿f;쀀𝕤aĀdr㑍ЂesĀ;u㑔㑕晠it»㑕ƀcsu㑠㑹㒟Āau㑥㑯pĀ;sᆈ㑫;쀀⊓︀pĀ;sᆴ㑵;쀀⊔︀uĀbp㑿㒏ƀ;esᆗᆜ㒆etĀ;eᆗ㒍ñᆝƀ;esᆨᆭ㒖etĀ;eᆨ㒝ñᆮƀ;afᅻ㒦ְrť㒫ֱ»ᅼaròᅈȀcemt㒹㒾㓂㓅r;쀀𝓈tmîñiì㐕aræᆾĀar㓎㓕rĀ;f㓔ឿ昆Āan㓚㓭ightĀep㓣㓪psiloîỠhé⺯s»⡒ʀbcmnp㓻㕞ሉ㖋㖎Ҁ;Edemnprs㔎㔏㔑㔕㔞㔣㔬㔱㔶抂;櫅ot;檽Ā;dᇚ㔚ot;櫃ult;櫁ĀEe㔨㔪;櫋;把lus;檿arr;楹ƀeiu㔽㕒㕕tƀ;en㔎㕅㕋qĀ;qᇚ㔏eqĀ;q㔫㔨m;櫇Ābp㕚㕜;櫕;櫓c̀;acensᇭ㕬㕲㕹㕻㌦pproø㋺urlyeñᇾñᇳƀaes㖂㖈㌛pproø㌚qñ㌗g;晪ڀ123;Edehlmnps㖩㖬㖯ሜ㖲㖴㗀㗉㗕㗚㗟㗨㗭耻¹䂹耻²䂲耻³䂳;櫆Āos㖹㖼t;檾ub;櫘Ā;dሢ㗅ot;櫄sĀou㗏㗒l;柉b;櫗arr;楻ult;櫂ĀEe㗤㗦;櫌;抋lus;櫀ƀeiu㗴㘉㘌tƀ;enሜ㗼㘂qĀ;qሢ㖲eqĀ;q㗧㗤m;櫈Ābp㘑㘓;櫔;櫖ƀAan㘜㘠㘭rr;懙rĀhr㘦㘨ë∮Ā;oਫ਩war;椪lig耻ß䃟௡㙑㙝㙠ዎ㙳㙹\\0㙾㛂\\0\\0\\0\\0\\0㛛㜃\\0㜉㝬\\0\\0\\0㞇ɲ㙖\\0\\0㙛get;挖;䏄rë๟ƀaey㙦㙫㙰ron;䅥dil;䅣;䑂lrec;挕r;쀀𝔱Ȁeiko㚆㚝㚵㚼Dz㚋\\0㚑eĀ4fኄኁaƀ;sv㚘㚙㚛䎸ym;䏑Ācn㚢㚲kĀas㚨㚮pproø዁im»ኬsðኞĀas㚺㚮ð዁rn耻þ䃾Ǭ̟㛆⋧es膀×;bd㛏㛐㛘䃗Ā;aᤏ㛕r;樱;樰ƀeps㛡㛣㜀á⩍Ȁ;bcf҆㛬㛰㛴ot;挶ir;櫱Ā;o㛹㛼쀀𝕥rk;櫚á㍢rime;怴ƀaip㜏㜒㝤dåቈ΀adempst㜡㝍㝀㝑㝗㝜㝟ngleʀ;dlqr㜰㜱㜶㝀㝂斵own»ᶻeftĀ;e⠀㜾ñम;扜ightĀ;e㊪㝋ñၚot;旬inus;樺lus;樹b;槍ime;樻ezium;揢ƀcht㝲㝽㞁Āry㝷㝻;쀀𝓉;䑆cy;䑛rok;䅧Āio㞋㞎xô᝷headĀlr㞗㞠eftarro÷ࡏightarrow»ཝऀAHabcdfghlmoprstuw㟐㟓㟗㟤㟰㟼㠎㠜㠣㠴㡑㡝㡫㢩㣌㣒㣪㣶ròϭar;楣Ācr㟜㟢ute耻ú䃺òᅐrǣ㟪\\0㟭y;䑞ve;䅭Āiy㟵㟺rc耻û䃻;䑃ƀabh㠃㠆㠋ròᎭlac;䅱aòᏃĀir㠓㠘sht;楾;쀀𝔲rave耻ù䃹š㠧㠱rĀlr㠬㠮»ॗ»ႃlk;斀Āct㠹㡍ɯ㠿\\0\\0㡊rnĀ;e㡅㡆挜r»㡆op;挏ri;旸Āal㡖㡚cr;䅫肻¨͉Āgp㡢㡦on;䅳f;쀀𝕦̀adhlsuᅋ㡸㡽፲㢑㢠ownáᎳarpoonĀlr㢈㢌efô㠭ighô㠯iƀ;hl㢙㢚㢜䏅»ᏺon»㢚parrows;懈ƀcit㢰㣄㣈ɯ㢶\\0\\0㣁rnĀ;e㢼㢽挝r»㢽op;挎ng;䅯ri;旹cr;쀀𝓊ƀdir㣙㣝㣢ot;拰lde;䅩iĀ;f㜰㣨»᠓Āam㣯㣲rò㢨l耻ü䃼angle;榧ހABDacdeflnoprsz㤜㤟㤩㤭㦵㦸㦽㧟㧤㧨㧳㧹㧽㨁㨠ròϷarĀ;v㤦㤧櫨;櫩asèϡĀnr㤲㤷grt;榜΀eknprst㓣㥆㥋㥒㥝㥤㦖appá␕othinçẖƀhir㓫⻈㥙opô⾵Ā;hᎷ㥢ïㆍĀiu㥩㥭gmá㎳Ābp㥲㦄setneqĀ;q㥽㦀쀀⊊︀;쀀⫋︀setneqĀ;q㦏㦒쀀⊋︀;쀀⫌︀Āhr㦛㦟etá㚜iangleĀlr㦪㦯eft»थight»ၑy;䐲ash»ံƀelr㧄㧒㧗ƀ;beⷪ㧋㧏ar;抻q;扚lip;拮Ābt㧜ᑨaòᑩr;쀀𝔳tré㦮suĀbp㧯㧱»ജ»൙pf;쀀𝕧roð໻tré㦴Ācu㨆㨋r;쀀𝓋Ābp㨐㨘nĀEe㦀㨖»㥾nĀEe㦒㨞»㦐igzag;榚΀cefoprs㨶㨻㩖㩛㩔㩡㩪irc;䅵Ādi㩀㩑Ābg㩅㩉ar;機eĀ;qᗺ㩏;扙erp;愘r;쀀𝔴pf;쀀𝕨Ā;eᑹ㩦atèᑹcr;쀀𝓌ૣណ㪇\\0㪋\\0㪐㪛\\0\\0㪝㪨㪫㪯\\0\\0㫃㫎\\0㫘ៜ៟tré៑r;쀀𝔵ĀAa㪔㪗ròσrò৶;䎾ĀAa㪡㪤ròθrò৫að✓is;拻ƀdptឤ㪵㪾Āfl㪺ឩ;쀀𝕩imåឲĀAa㫇㫊ròώròਁĀcq㫒ីr;쀀𝓍Āpt៖㫜ré។Ѐacefiosu㫰㫽㬈㬌㬑㬕㬛㬡cĀuy㫶㫻te耻ý䃽;䑏Āiy㬂㬆rc;䅷;䑋n耻¥䂥r;쀀𝔶cy;䑗pf;쀀𝕪cr;쀀𝓎Ācm㬦㬩y;䑎l耻ÿ䃿Ԁacdefhiosw㭂㭈㭔㭘㭤㭩㭭㭴㭺㮀cute;䅺Āay㭍㭒ron;䅾;䐷ot;䅼Āet㭝㭡træᕟa;䎶r;쀀𝔷cy;䐶grarr;懝pf;쀀𝕫cr;쀀𝓏Ājn㮅㮇;怍j;怌'.split(\"\").map((c) => c.charCodeAt(0))\n);\n\n// node_modules/.pnpm/entities@4.5.0/node_modules/entities/lib/esm/generated/decode-data-xml.js\nvar decode_data_xml_default = new Uint16Array(\n // prettier-ignore\n \"Ȁaglq\t\u0015\u0018\\x1Bɭ\u000f\\0\\0\u0012p;䀦os;䀧t;䀾t;䀼uot;䀢\".split(\"\").map((c) => c.charCodeAt(0))\n);\n\n// node_modules/.pnpm/entities@4.5.0/node_modules/entities/lib/esm/decode_codepoint.js\nvar _a2;\nvar decodeMap = /* @__PURE__ */ new Map([\n [0, 65533],\n // C1 Unicode control character reference replacements\n [128, 8364],\n [130, 8218],\n [131, 402],\n [132, 8222],\n [133, 8230],\n [134, 8224],\n [135, 8225],\n [136, 710],\n [137, 8240],\n [138, 352],\n [139, 8249],\n [140, 338],\n [142, 381],\n [145, 8216],\n [146, 8217],\n [147, 8220],\n [148, 8221],\n [149, 8226],\n [150, 8211],\n [151, 8212],\n [152, 732],\n [153, 8482],\n [154, 353],\n [155, 8250],\n [156, 339],\n [158, 382],\n [159, 376]\n]);\nvar fromCodePoint = (\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition, node/no-unsupported-features/es-builtins\n (_a2 = String.fromCodePoint) !== null && _a2 !== void 0 ? _a2 : function(codePoint) {\n let output = \"\";\n if (codePoint > 65535) {\n codePoint -= 65536;\n output += String.fromCharCode(codePoint >>> 10 & 1023 | 55296);\n codePoint = 56320 | codePoint & 1023;\n }\n output += String.fromCharCode(codePoint);\n return output;\n }\n);\nfunction replaceCodePoint(codePoint) {\n var _a3;\n if (codePoint >= 55296 && codePoint <= 57343 || codePoint > 1114111) {\n return 65533;\n }\n return (_a3 = decodeMap.get(codePoint)) !== null && _a3 !== void 0 ? _a3 : codePoint;\n}\n\n// node_modules/.pnpm/entities@4.5.0/node_modules/entities/lib/esm/decode.js\nvar CharCodes;\n(function(CharCodes2) {\n CharCodes2[CharCodes2[\"NUM\"] = 35] = \"NUM\";\n CharCodes2[CharCodes2[\"SEMI\"] = 59] = \"SEMI\";\n CharCodes2[CharCodes2[\"EQUALS\"] = 61] = \"EQUALS\";\n CharCodes2[CharCodes2[\"ZERO\"] = 48] = \"ZERO\";\n CharCodes2[CharCodes2[\"NINE\"] = 57] = \"NINE\";\n CharCodes2[CharCodes2[\"LOWER_A\"] = 97] = \"LOWER_A\";\n CharCodes2[CharCodes2[\"LOWER_F\"] = 102] = \"LOWER_F\";\n CharCodes2[CharCodes2[\"LOWER_X\"] = 120] = \"LOWER_X\";\n CharCodes2[CharCodes2[\"LOWER_Z\"] = 122] = \"LOWER_Z\";\n CharCodes2[CharCodes2[\"UPPER_A\"] = 65] = \"UPPER_A\";\n CharCodes2[CharCodes2[\"UPPER_F\"] = 70] = \"UPPER_F\";\n CharCodes2[CharCodes2[\"UPPER_Z\"] = 90] = \"UPPER_Z\";\n})(CharCodes || (CharCodes = {}));\nvar TO_LOWER_BIT = 32;\nvar BinTrieFlags;\n(function(BinTrieFlags2) {\n BinTrieFlags2[BinTrieFlags2[\"VALUE_LENGTH\"] = 49152] = \"VALUE_LENGTH\";\n BinTrieFlags2[BinTrieFlags2[\"BRANCH_LENGTH\"] = 16256] = \"BRANCH_LENGTH\";\n BinTrieFlags2[BinTrieFlags2[\"JUMP_TABLE\"] = 127] = \"JUMP_TABLE\";\n})(BinTrieFlags || (BinTrieFlags = {}));\nfunction isNumber(code2) {\n return code2 >= CharCodes.ZERO && code2 <= CharCodes.NINE;\n}\nfunction isHexadecimalCharacter(code2) {\n return code2 >= CharCodes.UPPER_A && code2 <= CharCodes.UPPER_F || code2 >= CharCodes.LOWER_A && code2 <= CharCodes.LOWER_F;\n}\nfunction isAsciiAlphaNumeric(code2) {\n return code2 >= CharCodes.UPPER_A && code2 <= CharCodes.UPPER_Z || code2 >= CharCodes.LOWER_A && code2 <= CharCodes.LOWER_Z || isNumber(code2);\n}\nfunction isEntityInAttributeInvalidEnd(code2) {\n return code2 === CharCodes.EQUALS || isAsciiAlphaNumeric(code2);\n}\nvar EntityDecoderState;\n(function(EntityDecoderState2) {\n EntityDecoderState2[EntityDecoderState2[\"EntityStart\"] = 0] = \"EntityStart\";\n EntityDecoderState2[EntityDecoderState2[\"NumericStart\"] = 1] = \"NumericStart\";\n EntityDecoderState2[EntityDecoderState2[\"NumericDecimal\"] = 2] = \"NumericDecimal\";\n EntityDecoderState2[EntityDecoderState2[\"NumericHex\"] = 3] = \"NumericHex\";\n EntityDecoderState2[EntityDecoderState2[\"NamedEntity\"] = 4] = \"NamedEntity\";\n})(EntityDecoderState || (EntityDecoderState = {}));\nvar DecodingMode;\n(function(DecodingMode2) {\n DecodingMode2[DecodingMode2[\"Legacy\"] = 0] = \"Legacy\";\n DecodingMode2[DecodingMode2[\"Strict\"] = 1] = \"Strict\";\n DecodingMode2[DecodingMode2[\"Attribute\"] = 2] = \"Attribute\";\n})(DecodingMode || (DecodingMode = {}));\nvar EntityDecoder = class {\n constructor(decodeTree, emitCodePoint, errors2) {\n this.decodeTree = decodeTree;\n this.emitCodePoint = emitCodePoint;\n this.errors = errors2;\n this.state = EntityDecoderState.EntityStart;\n this.consumed = 1;\n this.result = 0;\n this.treeIndex = 0;\n this.excess = 1;\n this.decodeMode = DecodingMode.Strict;\n }\n /** Resets the instance to make it reusable. */\n startEntity(decodeMode) {\n this.decodeMode = decodeMode;\n this.state = EntityDecoderState.EntityStart;\n this.result = 0;\n this.treeIndex = 0;\n this.excess = 1;\n this.consumed = 1;\n }\n /**\n * Write an entity to the decoder. This can be called multiple times with partial entities.\n * If the entity is incomplete, the decoder will return -1.\n *\n * Mirrors the implementation of `getDecoder`, but with the ability to stop decoding if the\n * entity is incomplete, and resume when the next string is written.\n *\n * @param string The string containing the entity (or a continuation of the entity).\n * @param offset The offset at which the entity begins. Should be 0 if this is not the first call.\n * @returns The number of characters that were consumed, or -1 if the entity is incomplete.\n */\n write(str, offset) {\n switch (this.state) {\n case EntityDecoderState.EntityStart: {\n if (str.charCodeAt(offset) === CharCodes.NUM) {\n this.state = EntityDecoderState.NumericStart;\n this.consumed += 1;\n return this.stateNumericStart(str, offset + 1);\n }\n this.state = EntityDecoderState.NamedEntity;\n return this.stateNamedEntity(str, offset);\n }\n case EntityDecoderState.NumericStart: {\n return this.stateNumericStart(str, offset);\n }\n case EntityDecoderState.NumericDecimal: {\n return this.stateNumericDecimal(str, offset);\n }\n case EntityDecoderState.NumericHex: {\n return this.stateNumericHex(str, offset);\n }\n case EntityDecoderState.NamedEntity: {\n return this.stateNamedEntity(str, offset);\n }\n }\n }\n /**\n * Switches between the numeric decimal and hexadecimal states.\n *\n * Equivalent to the `Numeric character reference state` in the HTML spec.\n *\n * @param str The string containing the entity (or a continuation of the entity).\n * @param offset The current offset.\n * @returns The number of characters that were consumed, or -1 if the entity is incomplete.\n */\n stateNumericStart(str, offset) {\n if (offset >= str.length) {\n return -1;\n }\n if ((str.charCodeAt(offset) | TO_LOWER_BIT) === CharCodes.LOWER_X) {\n this.state = EntityDecoderState.NumericHex;\n this.consumed += 1;\n return this.stateNumericHex(str, offset + 1);\n }\n this.state = EntityDecoderState.NumericDecimal;\n return this.stateNumericDecimal(str, offset);\n }\n addToNumericResult(str, start, end, base2) {\n if (start !== end) {\n const digitCount = end - start;\n this.result = this.result * Math.pow(base2, digitCount) + parseInt(str.substr(start, digitCount), base2);\n this.consumed += digitCount;\n }\n }\n /**\n * Parses a hexadecimal numeric entity.\n *\n * Equivalent to the `Hexademical character reference state` in the HTML spec.\n *\n * @param str The string containing the entity (or a continuation of the entity).\n * @param offset The current offset.\n * @returns The number of characters that were consumed, or -1 if the entity is incomplete.\n */\n stateNumericHex(str, offset) {\n const startIdx = offset;\n while (offset < str.length) {\n const char = str.charCodeAt(offset);\n if (isNumber(char) || isHexadecimalCharacter(char)) {\n offset += 1;\n } else {\n this.addToNumericResult(str, startIdx, offset, 16);\n return this.emitNumericEntity(char, 3);\n }\n }\n this.addToNumericResult(str, startIdx, offset, 16);\n return -1;\n }\n /**\n * Parses a decimal numeric entity.\n *\n * Equivalent to the `Decimal character reference state` in the HTML spec.\n *\n * @param str The string containing the entity (or a continuation of the entity).\n * @param offset The current offset.\n * @returns The number of characters that were consumed, or -1 if the entity is incomplete.\n */\n stateNumericDecimal(str, offset) {\n const startIdx = offset;\n while (offset < str.length) {\n const char = str.charCodeAt(offset);\n if (isNumber(char)) {\n offset += 1;\n } else {\n this.addToNumericResult(str, startIdx, offset, 10);\n return this.emitNumericEntity(char, 2);\n }\n }\n this.addToNumericResult(str, startIdx, offset, 10);\n return -1;\n }\n /**\n * Validate and emit a numeric entity.\n *\n * Implements the logic from the `Hexademical character reference start\n * state` and `Numeric character reference end state` in the HTML spec.\n *\n * @param lastCp The last code point of the entity. Used to see if the\n * entity was terminated with a semicolon.\n * @param expectedLength The minimum number of characters that should be\n * consumed. Used to validate that at least one digit\n * was consumed.\n * @returns The number of characters that were consumed.\n */\n emitNumericEntity(lastCp, expectedLength) {\n var _a3;\n if (this.consumed <= expectedLength) {\n (_a3 = this.errors) === null || _a3 === void 0 ? void 0 : _a3.absenceOfDigitsInNumericCharacterReference(this.consumed);\n return 0;\n }\n if (lastCp === CharCodes.SEMI) {\n this.consumed += 1;\n } else if (this.decodeMode === DecodingMode.Strict) {\n return 0;\n }\n this.emitCodePoint(replaceCodePoint(this.result), this.consumed);\n if (this.errors) {\n if (lastCp !== CharCodes.SEMI) {\n this.errors.missingSemicolonAfterCharacterReference();\n }\n this.errors.validateNumericCharacterReference(this.result);\n }\n return this.consumed;\n }\n /**\n * Parses a named entity.\n *\n * Equivalent to the `Named character reference state` in the HTML spec.\n *\n * @param str The string containing the entity (or a continuation of the entity).\n * @param offset The current offset.\n * @returns The number of characters that were consumed, or -1 if the entity is incomplete.\n */\n stateNamedEntity(str, offset) {\n const { decodeTree } = this;\n let current = decodeTree[this.treeIndex];\n let valueLength = (current & BinTrieFlags.VALUE_LENGTH) >> 14;\n for (; offset < str.length; offset++, this.excess++) {\n const char = str.charCodeAt(offset);\n this.treeIndex = determineBranch(decodeTree, current, this.treeIndex + Math.max(1, valueLength), char);\n if (this.treeIndex < 0) {\n return this.result === 0 || // If we are parsing an attribute\n this.decodeMode === DecodingMode.Attribute && // We shouldn't have consumed any characters after the entity,\n (valueLength === 0 || // And there should be no invalid characters.\n isEntityInAttributeInvalidEnd(char)) ? 0 : this.emitNotTerminatedNamedEntity();\n }\n current = decodeTree[this.treeIndex];\n valueLength = (current & BinTrieFlags.VALUE_LENGTH) >> 14;\n if (valueLength !== 0) {\n if (char === CharCodes.SEMI) {\n return this.emitNamedEntityData(this.treeIndex, valueLength, this.consumed + this.excess);\n }\n if (this.decodeMode !== DecodingMode.Strict) {\n this.result = this.treeIndex;\n this.consumed += this.excess;\n this.excess = 0;\n }\n }\n }\n return -1;\n }\n /**\n * Emit a named entity that was not terminated with a semicolon.\n *\n * @returns The number of characters consumed.\n */\n emitNotTerminatedNamedEntity() {\n var _a3;\n const { result, decodeTree } = this;\n const valueLength = (decodeTree[result] & BinTrieFlags.VALUE_LENGTH) >> 14;\n this.emitNamedEntityData(result, valueLength, this.consumed);\n (_a3 = this.errors) === null || _a3 === void 0 ? void 0 : _a3.missingSemicolonAfterCharacterReference();\n return this.consumed;\n }\n /**\n * Emit a named entity.\n *\n * @param result The index of the entity in the decode tree.\n * @param valueLength The number of bytes in the entity.\n * @param consumed The number of characters consumed.\n *\n * @returns The number of characters consumed.\n */\n emitNamedEntityData(result, valueLength, consumed) {\n const { decodeTree } = this;\n this.emitCodePoint(valueLength === 1 ? decodeTree[result] & ~BinTrieFlags.VALUE_LENGTH : decodeTree[result + 1], consumed);\n if (valueLength === 3) {\n this.emitCodePoint(decodeTree[result + 2], consumed);\n }\n return consumed;\n }\n /**\n * Signal to the parser that the end of the input was reached.\n *\n * Remaining data will be emitted and relevant errors will be produced.\n *\n * @returns The number of characters consumed.\n */\n end() {\n var _a3;\n switch (this.state) {\n case EntityDecoderState.NamedEntity: {\n return this.result !== 0 && (this.decodeMode !== DecodingMode.Attribute || this.result === this.treeIndex) ? this.emitNotTerminatedNamedEntity() : 0;\n }\n // Otherwise, emit a numeric entity if we have one.\n case EntityDecoderState.NumericDecimal: {\n return this.emitNumericEntity(0, 2);\n }\n case EntityDecoderState.NumericHex: {\n return this.emitNumericEntity(0, 3);\n }\n case EntityDecoderState.NumericStart: {\n (_a3 = this.errors) === null || _a3 === void 0 ? void 0 : _a3.absenceOfDigitsInNumericCharacterReference(this.consumed);\n return 0;\n }\n case EntityDecoderState.EntityStart: {\n return 0;\n }\n }\n }\n};\nfunction getDecoder(decodeTree) {\n let ret = \"\";\n const decoder = new EntityDecoder(decodeTree, (str) => ret += fromCodePoint(str));\n return function decodeWithTrie(str, decodeMode) {\n let lastIndex = 0;\n let offset = 0;\n while ((offset = str.indexOf(\"&\", offset)) >= 0) {\n ret += str.slice(lastIndex, offset);\n decoder.startEntity(decodeMode);\n const len = decoder.write(\n str,\n // Skip the \"&\"\n offset + 1\n );\n if (len < 0) {\n lastIndex = offset + decoder.end();\n break;\n }\n lastIndex = offset + len;\n offset = len === 0 ? lastIndex + 1 : lastIndex;\n }\n const result = ret + str.slice(lastIndex);\n ret = \"\";\n return result;\n };\n}\nfunction determineBranch(decodeTree, current, nodeIdx, char) {\n const branchCount = (current & BinTrieFlags.BRANCH_LENGTH) >> 7;\n const jumpOffset = current & BinTrieFlags.JUMP_TABLE;\n if (branchCount === 0) {\n return jumpOffset !== 0 && char === jumpOffset ? nodeIdx : -1;\n }\n if (jumpOffset) {\n const value = char - jumpOffset;\n return value < 0 || value >= branchCount ? -1 : decodeTree[nodeIdx + value] - 1;\n }\n let lo = nodeIdx;\n let hi = lo + branchCount - 1;\n while (lo <= hi) {\n const mid = lo + hi >>> 1;\n const midVal = decodeTree[mid];\n if (midVal < char) {\n lo = mid + 1;\n } else if (midVal > char) {\n hi = mid - 1;\n } else {\n return decodeTree[mid + branchCount];\n }\n }\n return -1;\n}\nvar htmlDecoder = getDecoder(decode_data_html_default);\nvar xmlDecoder = getDecoder(decode_data_xml_default);\nfunction decodeHTML(str, mode = DecodingMode.Legacy) {\n return htmlDecoder(str, mode);\n}\n\n// node_modules/.pnpm/entities@4.5.0/node_modules/entities/lib/esm/generated/encode-html.js\nfunction restoreDiff(arr) {\n for (let i = 1; i < arr.length; i++) {\n arr[i][0] += arr[i - 1][0] + 1;\n }\n return arr;\n}\nvar encode_html_default = new Map(/* @__PURE__ */ restoreDiff([[9, \" \"], [0, \" \"], [22, \"!\"], [0, \""\"], [0, \"#\"], [0, \"$\"], [0, \"%\"], [0, \"&\"], [0, \"'\"], [0, \"(\"], [0, \")\"], [0, \"*\"], [0, \"+\"], [0, \",\"], [1, \".\"], [0, \"/\"], [10, \":\"], [0, \";\"], [0, { v: \"<\", n: 8402, o: \"<⃒\" }], [0, { v: \"=\", n: 8421, o: \"=⃥\" }], [0, { v: \">\", n: 8402, o: \">⃒\" }], [0, \"?\"], [0, \"@\"], [26, \"[\"], [0, \"\\"], [0, \"]\"], [0, \"^\"], [0, \"_\"], [0, \"`\"], [5, { n: 106, o: \"fj\" }], [20, \"{\"], [0, \"|\"], [0, \"}\"], [34, \" \"], [0, \"¡\"], [0, \"¢\"], [0, \"£\"], [0, \"¤\"], [0, \"¥\"], [0, \"¦\"], [0, \"§\"], [0, \"¨\"], [0, \"©\"], [0, \"ª\"], [0, \"«\"], [0, \"¬\"], [0, \"­\"], [0, \"®\"], [0, \"¯\"], [0, \"°\"], [0, \"±\"], [0, \"²\"], [0, \"³\"], [0, \"´\"], [0, \"µ\"], [0, \"¶\"], [0, \"·\"], [0, \"¸\"], [0, \"¹\"], [0, \"º\"], [0, \"»\"], [0, \"¼\"], [0, \"½\"], [0, \"¾\"], [0, \"¿\"], [0, \"À\"], [0, \"Á\"], [0, \"Â\"], [0, \"Ã\"], [0, \"Ä\"], [0, \"Å\"], [0, \"Æ\"], [0, \"Ç\"], [0, \"È\"], [0, \"É\"], [0, \"Ê\"], [0, \"Ë\"], [0, \"Ì\"], [0, \"Í\"], [0, \"Î\"], [0, \"Ï\"], [0, \"Ð\"], [0, \"Ñ\"], [0, \"Ò\"], [0, \"Ó\"], [0, \"Ô\"], [0, \"Õ\"], [0, \"Ö\"], [0, \"×\"], [0, \"Ø\"], [0, \"Ù\"], [0, \"Ú\"], [0, \"Û\"], [0, \"Ü\"], [0, \"Ý\"], [0, \"Þ\"], [0, \"ß\"], [0, \"à\"], [0, \"á\"], [0, \"â\"], [0, \"ã\"], [0, \"ä\"], [0, \"å\"], [0, \"æ\"], [0, \"ç\"], [0, \"è\"], [0, \"é\"], [0, \"ê\"], [0, \"ë\"], [0, \"ì\"], [0, \"í\"], [0, \"î\"], [0, \"ï\"], [0, \"ð\"], [0, \"ñ\"], [0, \"ò\"], [0, \"ó\"], [0, \"ô\"], [0, \"õ\"], [0, \"ö\"], [0, \"÷\"], [0, \"ø\"], [0, \"ù\"], [0, \"ú\"], [0, \"û\"], [0, \"ü\"], [0, \"ý\"], [0, \"þ\"], [0, \"ÿ\"], [0, \"Ā\"], [0, \"ā\"], [0, \"Ă\"], [0, \"ă\"], [0, \"Ą\"], [0, \"ą\"], [0, \"Ć\"], [0, \"ć\"], [0, \"Ĉ\"], [0, \"ĉ\"], [0, \"Ċ\"], [0, \"ċ\"], [0, \"Č\"], [0, \"č\"], [0, \"Ď\"], [0, \"ď\"], [0, \"Đ\"], [0, \"đ\"], [0, \"Ē\"], [0, \"ē\"], [2, \"Ė\"], [0, \"ė\"], [0, \"Ę\"], [0, \"ę\"], [0, \"Ě\"], [0, \"ě\"], [0, \"Ĝ\"], [0, \"ĝ\"], [0, \"Ğ\"], [0, \"ğ\"], [0, \"Ġ\"], [0, \"ġ\"], [0, \"Ģ\"], [1, \"Ĥ\"], [0, \"ĥ\"], [0, \"Ħ\"], [0, \"ħ\"], [0, \"Ĩ\"], [0, \"ĩ\"], [0, \"Ī\"], [0, \"ī\"], [2, \"Į\"], [0, \"į\"], [0, \"İ\"], [0, \"ı\"], [0, \"IJ\"], [0, \"ij\"], [0, \"Ĵ\"], [0, \"ĵ\"], [0, \"Ķ\"], [0, \"ķ\"], [0, \"ĸ\"], [0, \"Ĺ\"], [0, \"ĺ\"], [0, \"Ļ\"], [0, \"ļ\"], [0, \"Ľ\"], [0, \"ľ\"], [0, \"Ŀ\"], [0, \"ŀ\"], [0, \"Ł\"], [0, \"ł\"], [0, \"Ń\"], [0, \"ń\"], [0, \"Ņ\"], [0, \"ņ\"], [0, \"Ň\"], [0, \"ň\"], [0, \"ʼn\"], [0, \"Ŋ\"], [0, \"ŋ\"], [0, \"Ō\"], [0, \"ō\"], [2, \"Ő\"], [0, \"ő\"], [0, \"Œ\"], [0, \"œ\"], [0, \"Ŕ\"], [0, \"ŕ\"], [0, \"Ŗ\"], [0, \"ŗ\"], [0, \"Ř\"], [0, \"ř\"], [0, \"Ś\"], [0, \"ś\"], [0, \"Ŝ\"], [0, \"ŝ\"], [0, \"Ş\"], [0, \"ş\"], [0, \"Š\"], [0, \"š\"], [0, \"Ţ\"], [0, \"ţ\"], [0, \"Ť\"], [0, \"ť\"], [0, \"Ŧ\"], [0, \"ŧ\"], [0, \"Ũ\"], [0, \"ũ\"], [0, \"Ū\"], [0, \"ū\"], [0, \"Ŭ\"], [0, \"ŭ\"], [0, \"Ů\"], [0, \"ů\"], [0, \"Ű\"], [0, \"ű\"], [0, \"Ų\"], [0, \"ų\"], [0, \"Ŵ\"], [0, \"ŵ\"], [0, \"Ŷ\"], [0, \"ŷ\"], [0, \"Ÿ\"], [0, \"Ź\"], [0, \"ź\"], [0, \"Ż\"], [0, \"ż\"], [0, \"Ž\"], [0, \"ž\"], [19, \"ƒ\"], [34, \"Ƶ\"], [63, \"ǵ\"], [65, \"ȷ\"], [142, \"ˆ\"], [0, \"ˇ\"], [16, \"˘\"], [0, \"˙\"], [0, \"˚\"], [0, \"˛\"], [0, \"˜\"], [0, \"˝\"], [51, \"̑\"], [127, \"Α\"], [0, \"Β\"], [0, \"Γ\"], [0, \"Δ\"], [0, \"Ε\"], [0, \"Ζ\"], [0, \"Η\"], [0, \"Θ\"], [0, \"Ι\"], [0, \"Κ\"], [0, \"Λ\"], [0, \"Μ\"], [0, \"Ν\"], [0, \"Ξ\"], [0, \"Ο\"], [0, \"Π\"], [0, \"Ρ\"], [1, \"Σ\"], [0, \"Τ\"], [0, \"Υ\"], [0, \"Φ\"], [0, \"Χ\"], [0, \"Ψ\"], [0, \"Ω\"], [7, \"α\"], [0, \"β\"], [0, \"γ\"], [0, \"δ\"], [0, \"ε\"], [0, \"ζ\"], [0, \"η\"], [0, \"θ\"], [0, \"ι\"], [0, \"κ\"], [0, \"λ\"], [0, \"μ\"], [0, \"ν\"], [0, \"ξ\"], [0, \"ο\"], [0, \"π\"], [0, \"ρ\"], [0, \"ς\"], [0, \"σ\"], [0, \"τ\"], [0, \"υ\"], [0, \"φ\"], [0, \"χ\"], [0, \"ψ\"], [0, \"ω\"], [7, \"ϑ\"], [0, \"ϒ\"], [2, \"ϕ\"], [0, \"ϖ\"], [5, \"Ϝ\"], [0, \"ϝ\"], [18, \"ϰ\"], [0, \"ϱ\"], [3, \"ϵ\"], [0, \"϶\"], [10, \"Ё\"], [0, \"Ђ\"], [0, \"Ѓ\"], [0, \"Є\"], [0, \"Ѕ\"], [0, \"І\"], [0, \"Ї\"], [0, \"Ј\"], [0, \"Љ\"], [0, \"Њ\"], [0, \"Ћ\"], [0, \"Ќ\"], [1, \"Ў\"], [0, \"Џ\"], [0, \"А\"], [0, \"Б\"], [0, \"В\"], [0, \"Г\"], [0, \"Д\"], [0, \"Е\"], [0, \"Ж\"], [0, \"З\"], [0, \"И\"], [0, \"Й\"], [0, \"К\"], [0, \"Л\"], [0, \"М\"], [0, \"Н\"], [0, \"О\"], [0, \"П\"], [0, \"Р\"], [0, \"С\"], [0, \"Т\"], [0, \"У\"], [0, \"Ф\"], [0, \"Х\"], [0, \"Ц\"], [0, \"Ч\"], [0, \"Ш\"], [0, \"Щ\"], [0, \"Ъ\"], [0, \"Ы\"], [0, \"Ь\"], [0, \"Э\"], [0, \"Ю\"], [0, \"Я\"], [0, \"а\"], [0, \"б\"], [0, \"в\"], [0, \"г\"], [0, \"д\"], [0, \"е\"], [0, \"ж\"], [0, \"з\"], [0, \"и\"], [0, \"й\"], [0, \"к\"], [0, \"л\"], [0, \"м\"], [0, \"н\"], [0, \"о\"], [0, \"п\"], [0, \"р\"], [0, \"с\"], [0, \"т\"], [0, \"у\"], [0, \"ф\"], [0, \"х\"], [0, \"ц\"], [0, \"ч\"], [0, \"ш\"], [0, \"щ\"], [0, \"ъ\"], [0, \"ы\"], [0, \"ь\"], [0, \"э\"], [0, \"ю\"], [0, \"я\"], [1, \"ё\"], [0, \"ђ\"], [0, \"ѓ\"], [0, \"є\"], [0, \"ѕ\"], [0, \"і\"], [0, \"ї\"], [0, \"ј\"], [0, \"љ\"], [0, \"њ\"], [0, \"ћ\"], [0, \"ќ\"], [1, \"ў\"], [0, \"џ\"], [7074, \" \"], [0, \" \"], [0, \" \"], [0, \" \"], [1, \" \"], [0, \" \"], [0, \" \"], [0, \" \"], [0, \"​\"], [0, \"‌\"], [0, \"‍\"], [0, \"‎\"], [0, \"‏\"], [0, \"‐\"], [2, \"–\"], [0, \"—\"], [0, \"―\"], [0, \"‖\"], [1, \"‘\"], [0, \"’\"], [0, \"‚\"], [1, \"“\"], [0, \"”\"], [0, \"„\"], [1, \"†\"], [0, \"‡\"], [0, \"•\"], [2, \"‥\"], [0, \"…\"], [9, \"‰\"], [0, \"‱\"], [0, \"′\"], [0, \"″\"], [0, \"‴\"], [0, \"‵\"], [3, \"‹\"], [0, \"›\"], [3, \"‾\"], [2, \"⁁\"], [1, \"⁃\"], [0, \"⁄\"], [10, \"⁏\"], [7, \"⁗\"], [7, { v: \" \", n: 8202, o: \"  \" }], [0, \"⁠\"], [0, \"⁡\"], [0, \"⁢\"], [0, \"⁣\"], [72, \"€\"], [46, \"⃛\"], [0, \"⃜\"], [37, \"ℂ\"], [2, \"℅\"], [4, \"ℊ\"], [0, \"ℋ\"], [0, \"ℌ\"], [0, \"ℍ\"], [0, \"ℎ\"], [0, \"ℏ\"], [0, \"ℐ\"], [0, \"ℑ\"], [0, \"ℒ\"], [0, \"ℓ\"], [1, \"ℕ\"], [0, \"№\"], [0, \"℗\"], [0, \"℘\"], [0, \"ℙ\"], [0, \"ℚ\"], [0, \"ℛ\"], [0, \"ℜ\"], [0, \"ℝ\"], [0, \"℞\"], [3, \"™\"], [1, \"ℤ\"], [2, \"℧\"], [0, \"ℨ\"], [0, \"℩\"], [2, \"ℬ\"], [0, \"ℭ\"], [1, \"ℯ\"], [0, \"ℰ\"], [0, \"ℱ\"], [1, \"ℳ\"], [0, \"ℴ\"], [0, \"ℵ\"], [0, \"ℶ\"], [0, \"ℷ\"], [0, \"ℸ\"], [12, \"ⅅ\"], [0, \"ⅆ\"], [0, \"ⅇ\"], [0, \"ⅈ\"], [10, \"⅓\"], [0, \"⅔\"], [0, \"⅕\"], [0, \"⅖\"], [0, \"⅗\"], [0, \"⅘\"], [0, \"⅙\"], [0, \"⅚\"], [0, \"⅛\"], [0, \"⅜\"], [0, \"⅝\"], [0, \"⅞\"], [49, \"←\"], [0, \"↑\"], [0, \"→\"], [0, \"↓\"], [0, \"↔\"], [0, \"↕\"], [0, \"↖\"], [0, \"↗\"], [0, \"↘\"], [0, \"↙\"], [0, \"↚\"], [0, \"↛\"], [1, { v: \"↝\", n: 824, o: \"↝̸\" }], [0, \"↞\"], [0, \"↟\"], [0, \"↠\"], [0, \"↡\"], [0, \"↢\"], [0, \"↣\"], [0, \"↤\"], [0, \"↥\"], [0, \"↦\"], [0, \"↧\"], [1, \"↩\"], [0, \"↪\"], [0, \"↫\"], [0, \"↬\"], [0, \"↭\"], [0, \"↮\"], [1, \"↰\"], [0, \"↱\"], [0, \"↲\"], [0, \"↳\"], [1, \"↵\"], [0, \"↶\"], [0, \"↷\"], [2, \"↺\"], [0, \"↻\"], [0, \"↼\"], [0, \"↽\"], [0, \"↾\"], [0, \"↿\"], [0, \"⇀\"], [0, \"⇁\"], [0, \"⇂\"], [0, \"⇃\"], [0, \"⇄\"], [0, \"⇅\"], [0, \"⇆\"], [0, \"⇇\"], [0, \"⇈\"], [0, \"⇉\"], [0, \"⇊\"], [0, \"⇋\"], [0, \"⇌\"], [0, \"⇍\"], [0, \"⇎\"], [0, \"⇏\"], [0, \"⇐\"], [0, \"⇑\"], [0, \"⇒\"], [0, \"⇓\"], [0, \"⇔\"], [0, \"⇕\"], [0, \"⇖\"], [0, \"⇗\"], [0, \"⇘\"], [0, \"⇙\"], [0, \"⇚\"], [0, \"⇛\"], [1, \"⇝\"], [6, \"⇤\"], [0, \"⇥\"], [15, \"⇵\"], [7, \"⇽\"], [0, \"⇾\"], [0, \"⇿\"], [0, \"∀\"], [0, \"∁\"], [0, { v: \"∂\", n: 824, o: \"∂̸\" }], [0, \"∃\"], [0, \"∄\"], [0, \"∅\"], [1, \"∇\"], [0, \"∈\"], [0, \"∉\"], [1, \"∋\"], [0, \"∌\"], [2, \"∏\"], [0, \"∐\"], [0, \"∑\"], [0, \"−\"], [0, \"∓\"], [0, \"∔\"], [1, \"∖\"], [0, \"∗\"], [0, \"∘\"], [1, \"√\"], [2, \"∝\"], [0, \"∞\"], [0, \"∟\"], [0, { v: \"∠\", n: 8402, o: \"∠⃒\" }], [0, \"∡\"], [0, \"∢\"], [0, \"∣\"], [0, \"∤\"], [0, \"∥\"], [0, \"∦\"], [0, \"∧\"], [0, \"∨\"], [0, { v: \"∩\", n: 65024, o: \"∩︀\" }], [0, { v: \"∪\", n: 65024, o: \"∪︀\" }], [0, \"∫\"], [0, \"∬\"], [0, \"∭\"], [0, \"∮\"], [0, \"∯\"], [0, \"∰\"], [0, \"∱\"], [0, \"∲\"], [0, \"∳\"], [0, \"∴\"], [0, \"∵\"], [0, \"∶\"], [0, \"∷\"], [0, \"∸\"], [1, \"∺\"], [0, \"∻\"], [0, { v: \"∼\", n: 8402, o: \"∼⃒\" }], [0, { v: \"∽\", n: 817, o: \"∽̱\" }], [0, { v: \"∾\", n: 819, o: \"∾̳\" }], [0, \"∿\"], [0, \"≀\"], [0, \"≁\"], [0, { v: \"≂\", n: 824, o: \"≂̸\" }], [0, \"≃\"], [0, \"≄\"], [0, \"≅\"], [0, \"≆\"], [0, \"≇\"], [0, \"≈\"], [0, \"≉\"], [0, \"≊\"], [0, { v: \"≋\", n: 824, o: \"≋̸\" }], [0, \"≌\"], [0, { v: \"≍\", n: 8402, o: \"≍⃒\" }], [0, { v: \"≎\", n: 824, o: \"≎̸\" }], [0, { v: \"≏\", n: 824, o: \"≏̸\" }], [0, { v: \"≐\", n: 824, o: \"≐̸\" }], [0, \"≑\"], [0, \"≒\"], [0, \"≓\"], [0, \"≔\"], [0, \"≕\"], [0, \"≖\"], [0, \"≗\"], [1, \"≙\"], [0, \"≚\"], [1, \"≜\"], [2, \"≟\"], [0, \"≠\"], [0, { v: \"≡\", n: 8421, o: \"≡⃥\" }], [0, \"≢\"], [1, { v: \"≤\", n: 8402, o: \"≤⃒\" }], [0, { v: \"≥\", n: 8402, o: \"≥⃒\" }], [0, { v: \"≦\", n: 824, o: \"≦̸\" }], [0, { v: \"≧\", n: 824, o: \"≧̸\" }], [0, { v: \"≨\", n: 65024, o: \"≨︀\" }], [0, { v: \"≩\", n: 65024, o: \"≩︀\" }], [0, { v: \"≪\", n: new Map(/* @__PURE__ */ restoreDiff([[824, \"≪̸\"], [7577, \"≪⃒\"]])) }], [0, { v: \"≫\", n: new Map(/* @__PURE__ */ restoreDiff([[824, \"≫̸\"], [7577, \"≫⃒\"]])) }], [0, \"≬\"], [0, \"≭\"], [0, \"≮\"], [0, \"≯\"], [0, \"≰\"], [0, \"≱\"], [0, \"≲\"], [0, \"≳\"], [0, \"≴\"], [0, \"≵\"], [0, \"≶\"], [0, \"≷\"], [0, \"≸\"], [0, \"≹\"], [0, \"≺\"], [0, \"≻\"], [0, \"≼\"], [0, \"≽\"], [0, \"≾\"], [0, { v: \"≿\", n: 824, o: \"≿̸\" }], [0, \"⊀\"], [0, \"⊁\"], [0, { v: \"⊂\", n: 8402, o: \"⊂⃒\" }], [0, { v: \"⊃\", n: 8402, o: \"⊃⃒\" }], [0, \"⊄\"], [0, \"⊅\"], [0, \"⊆\"], [0, \"⊇\"], [0, \"⊈\"], [0, \"⊉\"], [0, { v: \"⊊\", n: 65024, o: \"⊊︀\" }], [0, { v: \"⊋\", n: 65024, o: \"⊋︀\" }], [1, \"⊍\"], [0, \"⊎\"], [0, { v: \"⊏\", n: 824, o: \"⊏̸\" }], [0, { v: \"⊐\", n: 824, o: \"⊐̸\" }], [0, \"⊑\"], [0, \"⊒\"], [0, { v: \"⊓\", n: 65024, o: \"⊓︀\" }], [0, { v: \"⊔\", n: 65024, o: \"⊔︀\" }], [0, \"⊕\"], [0, \"⊖\"], [0, \"⊗\"], [0, \"⊘\"], [0, \"⊙\"], [0, \"⊚\"], [0, \"⊛\"], [1, \"⊝\"], [0, \"⊞\"], [0, \"⊟\"], [0, \"⊠\"], [0, \"⊡\"], [0, \"⊢\"], [0, \"⊣\"], [0, \"⊤\"], [0, \"⊥\"], [1, \"⊧\"], [0, \"⊨\"], [0, \"⊩\"], [0, \"⊪\"], [0, \"⊫\"], [0, \"⊬\"], [0, \"⊭\"], [0, \"⊮\"], [0, \"⊯\"], [0, \"⊰\"], [1, \"⊲\"], [0, \"⊳\"], [0, { v: \"⊴\", n: 8402, o: \"⊴⃒\" }], [0, { v: \"⊵\", n: 8402, o: \"⊵⃒\" }], [0, \"⊶\"], [0, \"⊷\"], [0, \"⊸\"], [0, \"⊹\"], [0, \"⊺\"], [0, \"⊻\"], [1, \"⊽\"], [0, \"⊾\"], [0, \"⊿\"], [0, \"⋀\"], [0, \"⋁\"], [0, \"⋂\"], [0, \"⋃\"], [0, \"⋄\"], [0, \"⋅\"], [0, \"⋆\"], [0, \"⋇\"], [0, \"⋈\"], [0, \"⋉\"], [0, \"⋊\"], [0, \"⋋\"], [0, \"⋌\"], [0, \"⋍\"], [0, \"⋎\"], [0, \"⋏\"], [0, \"⋐\"], [0, \"⋑\"], [0, \"⋒\"], [0, \"⋓\"], [0, \"⋔\"], [0, \"⋕\"], [0, \"⋖\"], [0, \"⋗\"], [0, { v: \"⋘\", n: 824, o: \"⋘̸\" }], [0, { v: \"⋙\", n: 824, o: \"⋙̸\" }], [0, { v: \"⋚\", n: 65024, o: \"⋚︀\" }], [0, { v: \"⋛\", n: 65024, o: \"⋛︀\" }], [2, \"⋞\"], [0, \"⋟\"], [0, \"⋠\"], [0, \"⋡\"], [0, \"⋢\"], [0, \"⋣\"], [2, \"⋦\"], [0, \"⋧\"], [0, \"⋨\"], [0, \"⋩\"], [0, \"⋪\"], [0, \"⋫\"], [0, \"⋬\"], [0, \"⋭\"], [0, \"⋮\"], [0, \"⋯\"], [0, \"⋰\"], [0, \"⋱\"], [0, \"⋲\"], [0, \"⋳\"], [0, \"⋴\"], [0, { v: \"⋵\", n: 824, o: \"⋵̸\" }], [0, \"⋶\"], [0, \"⋷\"], [1, { v: \"⋹\", n: 824, o: \"⋹̸\" }], [0, \"⋺\"], [0, \"⋻\"], [0, \"⋼\"], [0, \"⋽\"], [0, \"⋾\"], [6, \"⌅\"], [0, \"⌆\"], [1, \"⌈\"], [0, \"⌉\"], [0, \"⌊\"], [0, \"⌋\"], [0, \"⌌\"], [0, \"⌍\"], [0, \"⌎\"], [0, \"⌏\"], [0, \"⌐\"], [1, \"⌒\"], [0, \"⌓\"], [1, \"⌕\"], [0, \"⌖\"], [5, \"⌜\"], [0, \"⌝\"], [0, \"⌞\"], [0, \"⌟\"], [2, \"⌢\"], [0, \"⌣\"], [9, \"⌭\"], [0, \"⌮\"], [7, \"⌶\"], [6, \"⌽\"], [1, \"⌿\"], [60, \"⍼\"], [51, \"⎰\"], [0, \"⎱\"], [2, \"⎴\"], [0, \"⎵\"], [0, \"⎶\"], [37, \"⏜\"], [0, \"⏝\"], [0, \"⏞\"], [0, \"⏟\"], [2, \"⏢\"], [4, \"⏧\"], [59, \"␣\"], [164, \"Ⓢ\"], [55, \"─\"], [1, \"│\"], [9, \"┌\"], [3, \"┐\"], [3, \"└\"], [3, \"┘\"], [3, \"├\"], [7, \"┤\"], [7, \"┬\"], [7, \"┴\"], [7, \"┼\"], [19, \"═\"], [0, \"║\"], [0, \"╒\"], [0, \"╓\"], [0, \"╔\"], [0, \"╕\"], [0, \"╖\"], [0, \"╗\"], [0, \"╘\"], [0, \"╙\"], [0, \"╚\"], [0, \"╛\"], [0, \"╜\"], [0, \"╝\"], [0, \"╞\"], [0, \"╟\"], [0, \"╠\"], [0, \"╡\"], [0, \"╢\"], [0, \"╣\"], [0, \"╤\"], [0, \"╥\"], [0, \"╦\"], [0, \"╧\"], [0, \"╨\"], [0, \"╩\"], [0, \"╪\"], [0, \"╫\"], [0, \"╬\"], [19, \"▀\"], [3, \"▄\"], [3, \"█\"], [8, \"░\"], [0, \"▒\"], [0, \"▓\"], [13, \"□\"], [8, \"▪\"], [0, \"▫\"], [1, \"▭\"], [0, \"▮\"], [2, \"▱\"], [1, \"△\"], [0, \"▴\"], [0, \"▵\"], [2, \"▸\"], [0, \"▹\"], [3, \"▽\"], [0, \"▾\"], [0, \"▿\"], [2, \"◂\"], [0, \"◃\"], [6, \"◊\"], [0, \"○\"], [32, \"◬\"], [2, \"◯\"], [8, \"◸\"], [0, \"◹\"], [0, \"◺\"], [0, \"◻\"], [0, \"◼\"], [8, \"★\"], [0, \"☆\"], [7, \"☎\"], [49, \"♀\"], [1, \"♂\"], [29, \"♠\"], [2, \"♣\"], [1, \"♥\"], [0, \"♦\"], [3, \"♪\"], [2, \"♭\"], [0, \"♮\"], [0, \"♯\"], [163, \"✓\"], [3, \"✗\"], [8, \"✠\"], [21, \"✶\"], [33, \"❘\"], [25, \"❲\"], [0, \"❳\"], [84, \"⟈\"], [0, \"⟉\"], [28, \"⟦\"], [0, \"⟧\"], [0, \"⟨\"], [0, \"⟩\"], [0, \"⟪\"], [0, \"⟫\"], [0, \"⟬\"], [0, \"⟭\"], [7, \"⟵\"], [0, \"⟶\"], [0, \"⟷\"], [0, \"⟸\"], [0, \"⟹\"], [0, \"⟺\"], [1, \"⟼\"], [2, \"⟿\"], [258, \"⤂\"], [0, \"⤃\"], [0, \"⤄\"], [0, \"⤅\"], [6, \"⤌\"], [0, \"⤍\"], [0, \"⤎\"], [0, \"⤏\"], [0, \"⤐\"], [0, \"⤑\"], [0, \"⤒\"], [0, \"⤓\"], [2, \"⤖\"], [2, \"⤙\"], [0, \"⤚\"], [0, \"⤛\"], [0, \"⤜\"], [0, \"⤝\"], [0, \"⤞\"], [0, \"⤟\"], [0, \"⤠\"], [2, \"⤣\"], [0, \"⤤\"], [0, \"⤥\"], [0, \"⤦\"], [0, \"⤧\"], [0, \"⤨\"], [0, \"⤩\"], [0, \"⤪\"], [8, { v: \"⤳\", n: 824, o: \"⤳̸\" }], [1, \"⤵\"], [0, \"⤶\"], [0, \"⤷\"], [0, \"⤸\"], [0, \"⤹\"], [2, \"⤼\"], [0, \"⤽\"], [7, \"⥅\"], [2, \"⥈\"], [0, \"⥉\"], [0, \"⥊\"], [0, \"⥋\"], [2, \"⥎\"], [0, \"⥏\"], [0, \"⥐\"], [0, \"⥑\"], [0, \"⥒\"], [0, \"⥓\"], [0, \"⥔\"], [0, \"⥕\"], [0, \"⥖\"], [0, \"⥗\"], [0, \"⥘\"], [0, \"⥙\"], [0, \"⥚\"], [0, \"⥛\"], [0, \"⥜\"], [0, \"⥝\"], [0, \"⥞\"], [0, \"⥟\"], [0, \"⥠\"], [0, \"⥡\"], [0, \"⥢\"], [0, \"⥣\"], [0, \"⥤\"], [0, \"⥥\"], [0, \"⥦\"], [0, \"⥧\"], [0, \"⥨\"], [0, \"⥩\"], [0, \"⥪\"], [0, \"⥫\"], [0, \"⥬\"], [0, \"⥭\"], [0, \"⥮\"], [0, \"⥯\"], [0, \"⥰\"], [0, \"⥱\"], [0, \"⥲\"], [0, \"⥳\"], [0, \"⥴\"], [0, \"⥵\"], [0, \"⥶\"], [1, \"⥸\"], [0, \"⥹\"], [1, \"⥻\"], [0, \"⥼\"], [0, \"⥽\"], [0, \"⥾\"], [0, \"⥿\"], [5, \"⦅\"], [0, \"⦆\"], [4, \"⦋\"], [0, \"⦌\"], [0, \"⦍\"], [0, \"⦎\"], [0, \"⦏\"], [0, \"⦐\"], [0, \"⦑\"], [0, \"⦒\"], [0, \"⦓\"], [0, \"⦔\"], [0, \"⦕\"], [0, \"⦖\"], [3, \"⦚\"], [1, \"⦜\"], [0, \"⦝\"], [6, \"⦤\"], [0, \"⦥\"], [0, \"⦦\"], [0, \"⦧\"], [0, \"⦨\"], [0, \"⦩\"], [0, \"⦪\"], [0, \"⦫\"], [0, \"⦬\"], [0, \"⦭\"], [0, \"⦮\"], [0, \"⦯\"], [0, \"⦰\"], [0, \"⦱\"], [0, \"⦲\"], [0, \"⦳\"], [0, \"⦴\"], [0, \"⦵\"], [0, \"⦶\"], [0, \"⦷\"], [1, \"⦹\"], [1, \"⦻\"], [0, \"⦼\"], [1, \"⦾\"], [0, \"⦿\"], [0, \"⧀\"], [0, \"⧁\"], [0, \"⧂\"], [0, \"⧃\"], [0, \"⧄\"], [0, \"⧅\"], [3, \"⧉\"], [3, \"⧍\"], [0, \"⧎\"], [0, { v: \"⧏\", n: 824, o: \"⧏̸\" }], [0, { v: \"⧐\", n: 824, o: \"⧐̸\" }], [11, \"⧜\"], [0, \"⧝\"], [0, \"⧞\"], [4, \"⧣\"], [0, \"⧤\"], [0, \"⧥\"], [5, \"⧫\"], [8, \"⧴\"], [1, \"⧶\"], [9, \"⨀\"], [0, \"⨁\"], [0, \"⨂\"], [1, \"⨄\"], [1, \"⨆\"], [5, \"⨌\"], [0, \"⨍\"], [2, \"⨐\"], [0, \"⨑\"], [0, \"⨒\"], [0, \"⨓\"], [0, \"⨔\"], [0, \"⨕\"], [0, \"⨖\"], [0, \"⨗\"], [10, \"⨢\"], [0, \"⨣\"], [0, \"⨤\"], [0, \"⨥\"], [0, \"⨦\"], [0, \"⨧\"], [1, \"⨩\"], [0, \"⨪\"], [2, \"⨭\"], [0, \"⨮\"], [0, \"⨯\"], [0, \"⨰\"], [0, \"⨱\"], [1, \"⨳\"], [0, \"⨴\"], [0, \"⨵\"], [0, \"⨶\"], [0, \"⨷\"], [0, \"⨸\"], [0, \"⨹\"], [0, \"⨺\"], [0, \"⨻\"], [0, \"⨼\"], [2, \"⨿\"], [0, \"⩀\"], [1, \"⩂\"], [0, \"⩃\"], [0, \"⩄\"], [0, \"⩅\"], [0, \"⩆\"], [0, \"⩇\"], [0, \"⩈\"], [0, \"⩉\"], [0, \"⩊\"], [0, \"⩋\"], [0, \"⩌\"], [0, \"⩍\"], [2, \"⩐\"], [2, \"⩓\"], [0, \"⩔\"], [0, \"⩕\"], [0, \"⩖\"], [0, \"⩗\"], [0, \"⩘\"], [1, \"⩚\"], [0, \"⩛\"], [0, \"⩜\"], [0, \"⩝\"], [1, \"⩟\"], [6, \"⩦\"], [3, \"⩪\"], [2, { v: \"⩭\", n: 824, o: \"⩭̸\" }], [0, \"⩮\"], [0, \"⩯\"], [0, { v: \"⩰\", n: 824, o: \"⩰̸\" }], [0, \"⩱\"], [0, \"⩲\"], [0, \"⩳\"], [0, \"⩴\"], [0, \"⩵\"], [1, \"⩷\"], [0, \"⩸\"], [0, \"⩹\"], [0, \"⩺\"], [0, \"⩻\"], [0, \"⩼\"], [0, { v: \"⩽\", n: 824, o: \"⩽̸\" }], [0, { v: \"⩾\", n: 824, o: \"⩾̸\" }], [0, \"⩿\"], [0, \"⪀\"], [0, \"⪁\"], [0, \"⪂\"], [0, \"⪃\"], [0, \"⪄\"], [0, \"⪅\"], [0, \"⪆\"], [0, \"⪇\"], [0, \"⪈\"], [0, \"⪉\"], [0, \"⪊\"], [0, \"⪋\"], [0, \"⪌\"], [0, \"⪍\"], [0, \"⪎\"], [0, \"⪏\"], [0, \"⪐\"], [0, \"⪑\"], [0, \"⪒\"], [0, \"⪓\"], [0, \"⪔\"], [0, \"⪕\"], [0, \"⪖\"], [0, \"⪗\"], [0, \"⪘\"], [0, \"⪙\"], [0, \"⪚\"], [2, \"⪝\"], [0, \"⪞\"], [0, \"⪟\"], [0, \"⪠\"], [0, { v: \"⪡\", n: 824, o: \"⪡̸\" }], [0, { v: \"⪢\", n: 824, o: \"⪢̸\" }], [1, \"⪤\"], [0, \"⪥\"], [0, \"⪦\"], [0, \"⪧\"], [0, \"⪨\"], [0, \"⪩\"], [0, \"⪪\"], [0, \"⪫\"], [0, { v: \"⪬\", n: 65024, o: \"⪬︀\" }], [0, { v: \"⪭\", n: 65024, o: \"⪭︀\" }], [0, \"⪮\"], [0, { v: \"⪯\", n: 824, o: \"⪯̸\" }], [0, { v: \"⪰\", n: 824, o: \"⪰̸\" }], [2, \"⪳\"], [0, \"⪴\"], [0, \"⪵\"], [0, \"⪶\"], [0, \"⪷\"], [0, \"⪸\"], [0, \"⪹\"], [0, \"⪺\"], [0, \"⪻\"], [0, \"⪼\"], [0, \"⪽\"], [0, \"⪾\"], [0, \"⪿\"], [0, \"⫀\"], [0, \"⫁\"], [0, \"⫂\"], [0, \"⫃\"], [0, \"⫄\"], [0, { v: \"⫅\", n: 824, o: \"⫅̸\" }], [0, { v: \"⫆\", n: 824, o: \"⫆̸\" }], [0, \"⫇\"], [0, \"⫈\"], [2, { v: \"⫋\", n: 65024, o: \"⫋︀\" }], [0, { v: \"⫌\", n: 65024, o: \"⫌︀\" }], [2, \"⫏\"], [0, \"⫐\"], [0, \"⫑\"], [0, \"⫒\"], [0, \"⫓\"], [0, \"⫔\"], [0, \"⫕\"], [0, \"⫖\"], [0, \"⫗\"], [0, \"⫘\"], [0, \"⫙\"], [0, \"⫚\"], [0, \"⫛\"], [8, \"⫤\"], [1, \"⫦\"], [0, \"⫧\"], [0, \"⫨\"], [0, \"⫩\"], [1, \"⫫\"], [0, \"⫬\"], [0, \"⫭\"], [0, \"⫮\"], [0, \"⫯\"], [0, \"⫰\"], [0, \"⫱\"], [0, \"⫲\"], [0, \"⫳\"], [9, { v: \"⫽\", n: 8421, o: \"⫽⃥\" }], [44343, { n: new Map(/* @__PURE__ */ restoreDiff([[56476, \"𝒜\"], [1, \"𝒞\"], [0, \"𝒟\"], [2, \"𝒢\"], [2, \"𝒥\"], [0, \"𝒦\"], [2, \"𝒩\"], [0, \"𝒪\"], [0, \"𝒫\"], [0, \"𝒬\"], [1, \"𝒮\"], [0, \"𝒯\"], [0, \"𝒰\"], [0, \"𝒱\"], [0, \"𝒲\"], [0, \"𝒳\"], [0, \"𝒴\"], [0, \"𝒵\"], [0, \"𝒶\"], [0, \"𝒷\"], [0, \"𝒸\"], [0, \"𝒹\"], [1, \"𝒻\"], [1, \"𝒽\"], [0, \"𝒾\"], [0, \"𝒿\"], [0, \"𝓀\"], [0, \"𝓁\"], [0, \"𝓂\"], [0, \"𝓃\"], [1, \"𝓅\"], [0, \"𝓆\"], [0, \"𝓇\"], [0, \"𝓈\"], [0, \"𝓉\"], [0, \"𝓊\"], [0, \"𝓋\"], [0, \"𝓌\"], [0, \"𝓍\"], [0, \"𝓎\"], [0, \"𝓏\"], [52, \"𝔄\"], [0, \"𝔅\"], [1, \"𝔇\"], [0, \"𝔈\"], [0, \"𝔉\"], [0, \"𝔊\"], [2, \"𝔍\"], [0, \"𝔎\"], [0, \"𝔏\"], [0, \"𝔐\"], [0, \"𝔑\"], [0, \"𝔒\"], [0, \"𝔓\"], [0, \"𝔔\"], [1, \"𝔖\"], [0, \"𝔗\"], [0, \"𝔘\"], [0, \"𝔙\"], [0, \"𝔚\"], [0, \"𝔛\"], [0, \"𝔜\"], [1, \"𝔞\"], [0, \"𝔟\"], [0, \"𝔠\"], [0, \"𝔡\"], [0, \"𝔢\"], [0, \"𝔣\"], [0, \"𝔤\"], [0, \"𝔥\"], [0, \"𝔦\"], [0, \"𝔧\"], [0, \"𝔨\"], [0, \"𝔩\"], [0, \"𝔪\"], [0, \"𝔫\"], [0, \"𝔬\"], [0, \"𝔭\"], [0, \"𝔮\"], [0, \"𝔯\"], [0, \"𝔰\"], [0, \"𝔱\"], [0, \"𝔲\"], [0, \"𝔳\"], [0, \"𝔴\"], [0, \"𝔵\"], [0, \"𝔶\"], [0, \"𝔷\"], [0, \"𝔸\"], [0, \"𝔹\"], [1, \"𝔻\"], [0, \"𝔼\"], [0, \"𝔽\"], [0, \"𝔾\"], [1, \"𝕀\"], [0, \"𝕁\"], [0, \"𝕂\"], [0, \"𝕃\"], [0, \"𝕄\"], [1, \"𝕆\"], [3, \"𝕊\"], [0, \"𝕋\"], [0, \"𝕌\"], [0, \"𝕍\"], [0, \"𝕎\"], [0, \"𝕏\"], [0, \"𝕐\"], [1, \"𝕒\"], [0, \"𝕓\"], [0, \"𝕔\"], [0, \"𝕕\"], [0, \"𝕖\"], [0, \"𝕗\"], [0, \"𝕘\"], [0, \"𝕙\"], [0, \"𝕚\"], [0, \"𝕛\"], [0, \"𝕜\"], [0, \"𝕝\"], [0, \"𝕞\"], [0, \"𝕟\"], [0, \"𝕠\"], [0, \"𝕡\"], [0, \"𝕢\"], [0, \"𝕣\"], [0, \"𝕤\"], [0, \"𝕥\"], [0, \"𝕦\"], [0, \"𝕧\"], [0, \"𝕨\"], [0, \"𝕩\"], [0, \"𝕪\"], [0, \"𝕫\"]])) }], [8906, \"ff\"], [0, \"fi\"], [0, \"fl\"], [0, \"ffi\"], [0, \"ffl\"]]));\n\n// node_modules/.pnpm/entities@4.5.0/node_modules/entities/lib/esm/escape.js\nvar xmlCodeMap = /* @__PURE__ */ new Map([\n [34, \""\"],\n [38, \"&\"],\n [39, \"'\"],\n [60, \"<\"],\n [62, \">\"]\n]);\nvar getCodePoint = (\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n String.prototype.codePointAt != null ? (str, index) => str.codePointAt(index) : (\n // http://mathiasbynens.be/notes/javascript-encoding#surrogate-formulae\n (c, index) => (c.charCodeAt(index) & 64512) === 55296 ? (c.charCodeAt(index) - 55296) * 1024 + c.charCodeAt(index + 1) - 56320 + 65536 : c.charCodeAt(index)\n )\n);\nfunction getEscaper(regex, map2) {\n return function escape3(data) {\n let match2;\n let lastIdx = 0;\n let result = \"\";\n while (match2 = regex.exec(data)) {\n if (lastIdx !== match2.index) {\n result += data.substring(lastIdx, match2.index);\n }\n result += map2.get(match2[0].charCodeAt(0));\n lastIdx = match2.index + 1;\n }\n return result + data.substring(lastIdx);\n };\n}\nvar escapeUTF8 = getEscaper(/[&<>'\"]/g, xmlCodeMap);\nvar escapeAttribute = getEscaper(/[\"&\\u00A0]/g, /* @__PURE__ */ new Map([\n [34, \""\"],\n [38, \"&\"],\n [160, \" \"]\n]));\nvar escapeText = getEscaper(/[&<>\\u00A0]/g, /* @__PURE__ */ new Map([\n [38, \"&\"],\n [60, \"<\"],\n [62, \">\"],\n [160, \" \"]\n]));\n\n// node_modules/.pnpm/entities@4.5.0/node_modules/entities/lib/esm/index.js\nvar EntityLevel;\n(function(EntityLevel2) {\n EntityLevel2[EntityLevel2[\"XML\"] = 0] = \"XML\";\n EntityLevel2[EntityLevel2[\"HTML\"] = 1] = \"HTML\";\n})(EntityLevel || (EntityLevel = {}));\nvar EncodingMode;\n(function(EncodingMode2) {\n EncodingMode2[EncodingMode2[\"UTF8\"] = 0] = \"UTF8\";\n EncodingMode2[EncodingMode2[\"ASCII\"] = 1] = \"ASCII\";\n EncodingMode2[EncodingMode2[\"Extensive\"] = 2] = \"Extensive\";\n EncodingMode2[EncodingMode2[\"Attribute\"] = 3] = \"Attribute\";\n EncodingMode2[EncodingMode2[\"Text\"] = 4] = \"Text\";\n})(EncodingMode || (EncodingMode = {}));\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/common/utils.mjs\nfunction _class2(obj) {\n return Object.prototype.toString.call(obj);\n}\nfunction isString2(obj) {\n return _class2(obj) === \"[object String]\";\n}\nvar _hasOwnProperty = Object.prototype.hasOwnProperty;\nfunction has(object, key) {\n return _hasOwnProperty.call(object, key);\n}\nfunction assign2(obj) {\n const sources = Array.prototype.slice.call(arguments, 1);\n sources.forEach(function(source) {\n if (!source) {\n return;\n }\n if (typeof source !== \"object\") {\n throw new TypeError(source + \"must be object\");\n }\n Object.keys(source).forEach(function(key) {\n obj[key] = source[key];\n });\n });\n return obj;\n}\nfunction arrayReplaceAt(src, pos, newElements) {\n return [].concat(src.slice(0, pos), newElements, src.slice(pos + 1));\n}\nfunction isValidEntityCode(c) {\n if (c >= 55296 && c <= 57343) {\n return false;\n }\n if (c >= 64976 && c <= 65007) {\n return false;\n }\n if ((c & 65535) === 65535 || (c & 65535) === 65534) {\n return false;\n }\n if (c >= 0 && c <= 8) {\n return false;\n }\n if (c === 11) {\n return false;\n }\n if (c >= 14 && c <= 31) {\n return false;\n }\n if (c >= 127 && c <= 159) {\n return false;\n }\n if (c > 1114111) {\n return false;\n }\n return true;\n}\nfunction fromCodePoint2(c) {\n if (c > 65535) {\n c -= 65536;\n const surrogate1 = 55296 + (c >> 10);\n const surrogate2 = 56320 + (c & 1023);\n return String.fromCharCode(surrogate1, surrogate2);\n }\n return String.fromCharCode(c);\n}\nvar UNESCAPE_MD_RE = /\\\\([!\"#$%&'()*+,\\-./:;<=>?@[\\\\\\]^_`{|}~])/g;\nvar ENTITY_RE = /&([a-z#][a-z0-9]{1,31});/gi;\nvar UNESCAPE_ALL_RE = new RegExp(UNESCAPE_MD_RE.source + \"|\" + ENTITY_RE.source, \"gi\");\nvar DIGITAL_ENTITY_TEST_RE = /^#((?:x[a-f0-9]{1,8}|[0-9]{1,8}))$/i;\nfunction replaceEntityPattern(match2, name) {\n if (name.charCodeAt(0) === 35 && DIGITAL_ENTITY_TEST_RE.test(name)) {\n const code2 = name[1].toLowerCase() === \"x\" ? parseInt(name.slice(2), 16) : parseInt(name.slice(1), 10);\n if (isValidEntityCode(code2)) {\n return fromCodePoint2(code2);\n }\n return match2;\n }\n const decoded = decodeHTML(match2);\n if (decoded !== match2) {\n return decoded;\n }\n return match2;\n}\nfunction unescapeMd(str) {\n if (str.indexOf(\"\\\\\") < 0) {\n return str;\n }\n return str.replace(UNESCAPE_MD_RE, \"$1\");\n}\nfunction unescapeAll(str) {\n if (str.indexOf(\"\\\\\") < 0 && str.indexOf(\"&\") < 0) {\n return str;\n }\n return str.replace(UNESCAPE_ALL_RE, function(match2, escaped, entity2) {\n if (escaped) {\n return escaped;\n }\n return replaceEntityPattern(match2, entity2);\n });\n}\nvar HTML_ESCAPE_TEST_RE = /[&<>\"]/;\nvar HTML_ESCAPE_REPLACE_RE = /[&<>\"]/g;\nvar HTML_REPLACEMENTS = {\n \"&\": \"&\",\n \"<\": \"<\",\n \">\": \">\",\n '\"': \""\"\n};\nfunction replaceUnsafeChar(ch) {\n return HTML_REPLACEMENTS[ch];\n}\nfunction escapeHtml(str) {\n if (HTML_ESCAPE_TEST_RE.test(str)) {\n return str.replace(HTML_ESCAPE_REPLACE_RE, replaceUnsafeChar);\n }\n return str;\n}\nvar REGEXP_ESCAPE_RE = /[.?*+^$[\\]\\\\(){}|-]/g;\nfunction escapeRE2(str) {\n return str.replace(REGEXP_ESCAPE_RE, \"\\\\$&\");\n}\nfunction isSpace(code2) {\n switch (code2) {\n case 9:\n case 32:\n return true;\n }\n return false;\n}\nfunction isWhiteSpace(code2) {\n if (code2 >= 8192 && code2 <= 8202) {\n return true;\n }\n switch (code2) {\n case 9:\n // \\t\n case 10:\n // \\n\n case 11:\n // \\v\n case 12:\n // \\f\n case 13:\n // \\r\n case 32:\n case 160:\n case 5760:\n case 8239:\n case 8287:\n case 12288:\n return true;\n }\n return false;\n}\nfunction isPunctChar(ch) {\n return regex_default4.test(ch) || regex_default5.test(ch);\n}\nfunction isMdAsciiPunct(ch) {\n switch (ch) {\n case 33:\n case 34:\n case 35:\n case 36:\n case 37:\n case 38:\n case 39:\n case 40:\n case 41:\n case 42:\n case 43:\n case 44:\n case 45:\n case 46:\n case 47:\n case 58:\n case 59:\n case 60:\n case 61:\n case 62:\n case 63:\n case 64:\n case 91:\n case 92:\n case 93:\n case 94:\n case 95:\n case 96:\n case 123:\n case 124:\n case 125:\n case 126:\n return true;\n default:\n return false;\n }\n}\nfunction normalizeReference(str) {\n str = str.trim().replace(/\\s+/g, \" \");\n if (\"ẞ\".toLowerCase() === \"Ṿ\") {\n str = str.replace(/ẞ/g, \"ß\");\n }\n return str.toLowerCase().toUpperCase();\n}\nvar lib = { mdurl: mdurl_exports, ucmicro: uc_exports };\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/index.mjs\nvar helpers_exports = {};\n__export(helpers_exports, {\n parseLinkDestination: () => parseLinkDestination,\n parseLinkLabel: () => parseLinkLabel,\n parseLinkTitle: () => parseLinkTitle\n});\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/parse_link_label.mjs\nfunction parseLinkLabel(state, start, disableNested) {\n let level, found, marker, prevPos;\n const max2 = state.posMax;\n const oldPos = state.pos;\n state.pos = start + 1;\n level = 1;\n while (state.pos < max2) {\n marker = state.src.charCodeAt(state.pos);\n if (marker === 93) {\n level--;\n if (level === 0) {\n found = true;\n break;\n }\n }\n prevPos = state.pos;\n state.md.inline.skipToken(state);\n if (marker === 91) {\n if (prevPos === state.pos - 1) {\n level++;\n } else if (disableNested) {\n state.pos = oldPos;\n return -1;\n }\n }\n }\n let labelEnd = -1;\n if (found) {\n labelEnd = state.pos;\n }\n state.pos = oldPos;\n return labelEnd;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/parse_link_destination.mjs\nfunction parseLinkDestination(str, start, max2) {\n let code2;\n let pos = start;\n const result = {\n ok: false,\n pos: 0,\n str: \"\"\n };\n if (str.charCodeAt(pos) === 60) {\n pos++;\n while (pos < max2) {\n code2 = str.charCodeAt(pos);\n if (code2 === 10) {\n return result;\n }\n if (code2 === 60) {\n return result;\n }\n if (code2 === 62) {\n result.pos = pos + 1;\n result.str = unescapeAll(str.slice(start + 1, pos));\n result.ok = true;\n return result;\n }\n if (code2 === 92 && pos + 1 < max2) {\n pos += 2;\n continue;\n }\n pos++;\n }\n return result;\n }\n let level = 0;\n while (pos < max2) {\n code2 = str.charCodeAt(pos);\n if (code2 === 32) {\n break;\n }\n if (code2 < 32 || code2 === 127) {\n break;\n }\n if (code2 === 92 && pos + 1 < max2) {\n if (str.charCodeAt(pos + 1) === 32) {\n break;\n }\n pos += 2;\n continue;\n }\n if (code2 === 40) {\n level++;\n if (level > 32) {\n return result;\n }\n }\n if (code2 === 41) {\n if (level === 0) {\n break;\n }\n level--;\n }\n pos++;\n }\n if (start === pos) {\n return result;\n }\n if (level !== 0) {\n return result;\n }\n result.str = unescapeAll(str.slice(start, pos));\n result.pos = pos;\n result.ok = true;\n return result;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/parse_link_title.mjs\nfunction parseLinkTitle(str, start, max2, prev_state) {\n let code2;\n let pos = start;\n const state = {\n // if `true`, this is a valid link title\n ok: false,\n // if `true`, this link can be continued on the next line\n can_continue: false,\n // if `ok`, it's the position of the first character after the closing marker\n pos: 0,\n // if `ok`, it's the unescaped title\n str: \"\",\n // expected closing marker character code\n marker: 0\n };\n if (prev_state) {\n state.str = prev_state.str;\n state.marker = prev_state.marker;\n } else {\n if (pos >= max2) {\n return state;\n }\n let marker = str.charCodeAt(pos);\n if (marker !== 34 && marker !== 39 && marker !== 40) {\n return state;\n }\n start++;\n pos++;\n if (marker === 40) {\n marker = 41;\n }\n state.marker = marker;\n }\n while (pos < max2) {\n code2 = str.charCodeAt(pos);\n if (code2 === state.marker) {\n state.pos = pos + 1;\n state.str += unescapeAll(str.slice(start, pos));\n state.ok = true;\n return state;\n } else if (code2 === 40 && state.marker === 41) {\n return state;\n } else if (code2 === 92 && pos + 1 < max2) {\n pos++;\n }\n pos++;\n }\n state.can_continue = true;\n state.str += unescapeAll(str.slice(start, pos));\n return state;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/renderer.mjs\nvar default_rules = {};\ndefault_rules.code_inline = function(tokens, idx, options, env, slf) {\n const token = tokens[idx];\n return \"\" + escapeHtml(token.content) + \"\";\n};\ndefault_rules.code_block = function(tokens, idx, options, env, slf) {\n const token = tokens[idx];\n return \"\" + escapeHtml(tokens[idx].content) + \"\\n\";\n};\ndefault_rules.fence = function(tokens, idx, options, env, slf) {\n const token = tokens[idx];\n const info = token.info ? unescapeAll(token.info).trim() : \"\";\n let langName = \"\";\n let langAttrs = \"\";\n if (info) {\n const arr = info.split(/(\\s+)/g);\n langName = arr[0];\n langAttrs = arr.slice(2).join(\"\");\n }\n let highlighted;\n if (options.highlight) {\n highlighted = options.highlight(token.content, langName, langAttrs) || escapeHtml(token.content);\n } else {\n highlighted = escapeHtml(token.content);\n }\n if (highlighted.indexOf(\"${highlighted}\n`;\n }\n return `

${highlighted}
\n`;\n};\ndefault_rules.image = function(tokens, idx, options, env, slf) {\n const token = tokens[idx];\n token.attrs[token.attrIndex(\"alt\")][1] = slf.renderInlineAsText(token.children, options, env);\n return slf.renderToken(tokens, idx, options);\n};\ndefault_rules.hardbreak = function(tokens, idx, options) {\n return options.xhtmlOut ? \"
\\n\" : \"
\\n\";\n};\ndefault_rules.softbreak = function(tokens, idx, options) {\n return options.breaks ? options.xhtmlOut ? \"
\\n\" : \"
\\n\" : \"\\n\";\n};\ndefault_rules.text = function(tokens, idx) {\n return escapeHtml(tokens[idx].content);\n};\ndefault_rules.html_block = function(tokens, idx) {\n return tokens[idx].content;\n};\ndefault_rules.html_inline = function(tokens, idx) {\n return tokens[idx].content;\n};\nfunction Renderer() {\n this.rules = assign2({}, default_rules);\n}\nRenderer.prototype.renderAttrs = function renderAttrs(token) {\n let i, l, result;\n if (!token.attrs) {\n return \"\";\n }\n result = \"\";\n for (i = 0, l = token.attrs.length; i < l; i++) {\n result += \" \" + escapeHtml(token.attrs[i][0]) + '=\"' + escapeHtml(token.attrs[i][1]) + '\"';\n }\n return result;\n};\nRenderer.prototype.renderToken = function renderToken(tokens, idx, options) {\n const token = tokens[idx];\n let result = \"\";\n if (token.hidden) {\n return \"\";\n }\n if (token.block && token.nesting !== -1 && idx && tokens[idx - 1].hidden) {\n result += \"\\n\";\n }\n result += (token.nesting === -1 ? \"\\n\" : \">\";\n return result;\n};\nRenderer.prototype.renderInline = function(tokens, options, env) {\n let result = \"\";\n const rules = this.rules;\n for (let i = 0, len = tokens.length; i < len; i++) {\n const type = tokens[i].type;\n if (typeof rules[type] !== \"undefined\") {\n result += rules[type](tokens, i, options, env, this);\n } else {\n result += this.renderToken(tokens, i, options);\n }\n }\n return result;\n};\nRenderer.prototype.renderInlineAsText = function(tokens, options, env) {\n let result = \"\";\n for (let i = 0, len = tokens.length; i < len; i++) {\n switch (tokens[i].type) {\n case \"text\":\n result += tokens[i].content;\n break;\n case \"image\":\n result += this.renderInlineAsText(tokens[i].children, options, env);\n break;\n case \"html_inline\":\n case \"html_block\":\n result += tokens[i].content;\n break;\n case \"softbreak\":\n case \"hardbreak\":\n result += \"\\n\";\n break;\n default:\n }\n }\n return result;\n};\nRenderer.prototype.render = function(tokens, options, env) {\n let result = \"\";\n const rules = this.rules;\n for (let i = 0, len = tokens.length; i < len; i++) {\n const type = tokens[i].type;\n if (type === \"inline\") {\n result += this.renderInline(tokens[i].children, options, env);\n } else if (typeof rules[type] !== \"undefined\") {\n result += rules[type](tokens, i, options, env, this);\n } else {\n result += this.renderToken(tokens, i, options, env);\n }\n }\n return result;\n};\nvar renderer_default = Renderer;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/ruler.mjs\nfunction Ruler() {\n this.__rules__ = [];\n this.__cache__ = null;\n}\nRuler.prototype.__find__ = function(name) {\n for (let i = 0; i < this.__rules__.length; i++) {\n if (this.__rules__[i].name === name) {\n return i;\n }\n }\n return -1;\n};\nRuler.prototype.__compile__ = function() {\n const self = this;\n const chains = [\"\"];\n self.__rules__.forEach(function(rule) {\n if (!rule.enabled) {\n return;\n }\n rule.alt.forEach(function(altName) {\n if (chains.indexOf(altName) < 0) {\n chains.push(altName);\n }\n });\n });\n self.__cache__ = {};\n chains.forEach(function(chain) {\n self.__cache__[chain] = [];\n self.__rules__.forEach(function(rule) {\n if (!rule.enabled) {\n return;\n }\n if (chain && rule.alt.indexOf(chain) < 0) {\n return;\n }\n self.__cache__[chain].push(rule.fn);\n });\n });\n};\nRuler.prototype.at = function(name, fn, options) {\n const index = this.__find__(name);\n const opt = options || {};\n if (index === -1) {\n throw new Error(\"Parser rule not found: \" + name);\n }\n this.__rules__[index].fn = fn;\n this.__rules__[index].alt = opt.alt || [];\n this.__cache__ = null;\n};\nRuler.prototype.before = function(beforeName, ruleName, fn, options) {\n const index = this.__find__(beforeName);\n const opt = options || {};\n if (index === -1) {\n throw new Error(\"Parser rule not found: \" + beforeName);\n }\n this.__rules__.splice(index, 0, {\n name: ruleName,\n enabled: true,\n fn,\n alt: opt.alt || []\n });\n this.__cache__ = null;\n};\nRuler.prototype.after = function(afterName, ruleName, fn, options) {\n const index = this.__find__(afterName);\n const opt = options || {};\n if (index === -1) {\n throw new Error(\"Parser rule not found: \" + afterName);\n }\n this.__rules__.splice(index + 1, 0, {\n name: ruleName,\n enabled: true,\n fn,\n alt: opt.alt || []\n });\n this.__cache__ = null;\n};\nRuler.prototype.push = function(ruleName, fn, options) {\n const opt = options || {};\n this.__rules__.push({\n name: ruleName,\n enabled: true,\n fn,\n alt: opt.alt || []\n });\n this.__cache__ = null;\n};\nRuler.prototype.enable = function(list2, ignoreInvalid) {\n if (!Array.isArray(list2)) {\n list2 = [list2];\n }\n const result = [];\n list2.forEach(function(name) {\n const idx = this.__find__(name);\n if (idx < 0) {\n if (ignoreInvalid) {\n return;\n }\n throw new Error(\"Rules manager: invalid rule name \" + name);\n }\n this.__rules__[idx].enabled = true;\n result.push(name);\n }, this);\n this.__cache__ = null;\n return result;\n};\nRuler.prototype.enableOnly = function(list2, ignoreInvalid) {\n if (!Array.isArray(list2)) {\n list2 = [list2];\n }\n this.__rules__.forEach(function(rule) {\n rule.enabled = false;\n });\n this.enable(list2, ignoreInvalid);\n};\nRuler.prototype.disable = function(list2, ignoreInvalid) {\n if (!Array.isArray(list2)) {\n list2 = [list2];\n }\n const result = [];\n list2.forEach(function(name) {\n const idx = this.__find__(name);\n if (idx < 0) {\n if (ignoreInvalid) {\n return;\n }\n throw new Error(\"Rules manager: invalid rule name \" + name);\n }\n this.__rules__[idx].enabled = false;\n result.push(name);\n }, this);\n this.__cache__ = null;\n return result;\n};\nRuler.prototype.getRules = function(chainName) {\n if (this.__cache__ === null) {\n this.__compile__();\n }\n return this.__cache__[chainName] || [];\n};\nvar ruler_default = Ruler;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/token.mjs\nfunction Token(type, tag, nesting) {\n this.type = type;\n this.tag = tag;\n this.attrs = null;\n this.map = null;\n this.nesting = nesting;\n this.level = 0;\n this.children = null;\n this.content = \"\";\n this.markup = \"\";\n this.info = \"\";\n this.meta = null;\n this.block = false;\n this.hidden = false;\n}\nToken.prototype.attrIndex = function attrIndex(name) {\n if (!this.attrs) {\n return -1;\n }\n const attrs = this.attrs;\n for (let i = 0, len = attrs.length; i < len; i++) {\n if (attrs[i][0] === name) {\n return i;\n }\n }\n return -1;\n};\nToken.prototype.attrPush = function attrPush(attrData) {\n if (this.attrs) {\n this.attrs.push(attrData);\n } else {\n this.attrs = [attrData];\n }\n};\nToken.prototype.attrSet = function attrSet(name, value) {\n const idx = this.attrIndex(name);\n const attrData = [name, value];\n if (idx < 0) {\n this.attrPush(attrData);\n } else {\n this.attrs[idx] = attrData;\n }\n};\nToken.prototype.attrGet = function attrGet(name) {\n const idx = this.attrIndex(name);\n let value = null;\n if (idx >= 0) {\n value = this.attrs[idx][1];\n }\n return value;\n};\nToken.prototype.attrJoin = function attrJoin(name, value) {\n const idx = this.attrIndex(name);\n if (idx < 0) {\n this.attrPush([name, value]);\n } else {\n this.attrs[idx][1] = this.attrs[idx][1] + \" \" + value;\n }\n};\nvar token_default = Token;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/state_core.mjs\nfunction StateCore(src, md, env) {\n this.src = src;\n this.env = env;\n this.tokens = [];\n this.inlineMode = false;\n this.md = md;\n}\nStateCore.prototype.Token = token_default;\nvar state_core_default = StateCore;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/normalize.mjs\nvar NEWLINES_RE = /\\r\\n?|\\n/g;\nvar NULL_RE = /\\0/g;\nfunction normalize2(state) {\n let str;\n str = state.src.replace(NEWLINES_RE, \"\\n\");\n str = str.replace(NULL_RE, \"�\");\n state.src = str;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/block.mjs\nfunction block(state) {\n let token;\n if (state.inlineMode) {\n token = new state.Token(\"inline\", \"\", 0);\n token.content = state.src;\n token.map = [0, 1];\n token.children = [];\n state.tokens.push(token);\n } else {\n state.md.block.parse(state.src, state.md, state.env, state.tokens);\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/inline.mjs\nfunction inline(state) {\n const tokens = state.tokens;\n for (let i = 0, l = tokens.length; i < l; i++) {\n const tok = tokens[i];\n if (tok.type === \"inline\") {\n state.md.inline.parse(tok.content, state.md, state.env, tok.children);\n }\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/linkify.mjs\nfunction isLinkOpen(str) {\n return /^\\s]/i.test(str);\n}\nfunction isLinkClose(str) {\n return /^<\\/a\\s*>/i.test(str);\n}\nfunction linkify(state) {\n const blockTokens = state.tokens;\n if (!state.md.options.linkify) {\n return;\n }\n for (let j = 0, l = blockTokens.length; j < l; j++) {\n if (blockTokens[j].type !== \"inline\" || !state.md.linkify.pretest(blockTokens[j].content)) {\n continue;\n }\n let tokens = blockTokens[j].children;\n let htmlLinkLevel = 0;\n for (let i = tokens.length - 1; i >= 0; i--) {\n const currentToken = tokens[i];\n if (currentToken.type === \"link_close\") {\n i--;\n while (tokens[i].level !== currentToken.level && tokens[i].type !== \"link_open\") {\n i--;\n }\n continue;\n }\n if (currentToken.type === \"html_inline\") {\n if (isLinkOpen(currentToken.content) && htmlLinkLevel > 0) {\n htmlLinkLevel--;\n }\n if (isLinkClose(currentToken.content)) {\n htmlLinkLevel++;\n }\n }\n if (htmlLinkLevel > 0) {\n continue;\n }\n if (currentToken.type === \"text\" && state.md.linkify.test(currentToken.content)) {\n const text2 = currentToken.content;\n let links = state.md.linkify.match(text2);\n const nodes = [];\n let level = currentToken.level;\n let lastPos = 0;\n if (links.length > 0 && links[0].index === 0 && i > 0 && tokens[i - 1].type === \"text_special\") {\n links = links.slice(1);\n }\n for (let ln = 0; ln < links.length; ln++) {\n const url = links[ln].url;\n const fullUrl = state.md.normalizeLink(url);\n if (!state.md.validateLink(fullUrl)) {\n continue;\n }\n let urlText = links[ln].text;\n if (!links[ln].schema) {\n urlText = state.md.normalizeLinkText(\"http://\" + urlText).replace(/^http:\\/\\//, \"\");\n } else if (links[ln].schema === \"mailto:\" && !/^mailto:/i.test(urlText)) {\n urlText = state.md.normalizeLinkText(\"mailto:\" + urlText).replace(/^mailto:/, \"\");\n } else {\n urlText = state.md.normalizeLinkText(urlText);\n }\n const pos = links[ln].index;\n if (pos > lastPos) {\n const token = new state.Token(\"text\", \"\", 0);\n token.content = text2.slice(lastPos, pos);\n token.level = level;\n nodes.push(token);\n }\n const token_o = new state.Token(\"link_open\", \"a\", 1);\n token_o.attrs = [[\"href\", fullUrl]];\n token_o.level = level++;\n token_o.markup = \"linkify\";\n token_o.info = \"auto\";\n nodes.push(token_o);\n const token_t = new state.Token(\"text\", \"\", 0);\n token_t.content = urlText;\n token_t.level = level;\n nodes.push(token_t);\n const token_c = new state.Token(\"link_close\", \"a\", -1);\n token_c.level = --level;\n token_c.markup = \"linkify\";\n token_c.info = \"auto\";\n nodes.push(token_c);\n lastPos = links[ln].lastIndex;\n }\n if (lastPos < text2.length) {\n const token = new state.Token(\"text\", \"\", 0);\n token.content = text2.slice(lastPos);\n token.level = level;\n nodes.push(token);\n }\n blockTokens[j].children = tokens = arrayReplaceAt(tokens, i, nodes);\n }\n }\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/replacements.mjs\nvar RARE_RE = /\\+-|\\.\\.|\\?\\?\\?\\?|!!!!|,,|--/;\nvar SCOPED_ABBR_TEST_RE = /\\((c|tm|r)\\)/i;\nvar SCOPED_ABBR_RE = /\\((c|tm|r)\\)/ig;\nvar SCOPED_ABBR = {\n c: \"©\",\n r: \"®\",\n tm: \"™\"\n};\nfunction replaceFn(match2, name) {\n return SCOPED_ABBR[name.toLowerCase()];\n}\nfunction replace_scoped(inlineTokens) {\n let inside_autolink = 0;\n for (let i = inlineTokens.length - 1; i >= 0; i--) {\n const token = inlineTokens[i];\n if (token.type === \"text\" && !inside_autolink) {\n token.content = token.content.replace(SCOPED_ABBR_RE, replaceFn);\n }\n if (token.type === \"link_open\" && token.info === \"auto\") {\n inside_autolink--;\n }\n if (token.type === \"link_close\" && token.info === \"auto\") {\n inside_autolink++;\n }\n }\n}\nfunction replace_rare(inlineTokens) {\n let inside_autolink = 0;\n for (let i = inlineTokens.length - 1; i >= 0; i--) {\n const token = inlineTokens[i];\n if (token.type === \"text\" && !inside_autolink) {\n if (RARE_RE.test(token.content)) {\n token.content = token.content.replace(/\\+-/g, \"±\").replace(/\\.{2,}/g, \"…\").replace(/([?!])…/g, \"$1..\").replace(/([?!]){4,}/g, \"$1$1$1\").replace(/,{2,}/g, \",\").replace(/(^|[^-])---(?=[^-]|$)/mg, \"$1—\").replace(/(^|\\s)--(?=\\s|$)/mg, \"$1–\").replace(/(^|[^-\\s])--(?=[^-\\s]|$)/mg, \"$1–\");\n }\n }\n if (token.type === \"link_open\" && token.info === \"auto\") {\n inside_autolink--;\n }\n if (token.type === \"link_close\" && token.info === \"auto\") {\n inside_autolink++;\n }\n }\n}\nfunction replace(state) {\n let blkIdx;\n if (!state.md.options.typographer) {\n return;\n }\n for (blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) {\n if (state.tokens[blkIdx].type !== \"inline\") {\n continue;\n }\n if (SCOPED_ABBR_TEST_RE.test(state.tokens[blkIdx].content)) {\n replace_scoped(state.tokens[blkIdx].children);\n }\n if (RARE_RE.test(state.tokens[blkIdx].content)) {\n replace_rare(state.tokens[blkIdx].children);\n }\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/smartquotes.mjs\nvar QUOTE_TEST_RE = /['\"]/;\nvar QUOTE_RE = /['\"]/g;\nvar APOSTROPHE = \"’\";\nfunction replaceAt(str, index, ch) {\n return str.slice(0, index) + ch + str.slice(index + 1);\n}\nfunction process_inlines(tokens, state) {\n let j;\n const stack = [];\n for (let i = 0; i < tokens.length; i++) {\n const token = tokens[i];\n const thisLevel = tokens[i].level;\n for (j = stack.length - 1; j >= 0; j--) {\n if (stack[j].level <= thisLevel) {\n break;\n }\n }\n stack.length = j + 1;\n if (token.type !== \"text\") {\n continue;\n }\n let text2 = token.content;\n let pos = 0;\n let max2 = text2.length;\n OUTER:\n while (pos < max2) {\n QUOTE_RE.lastIndex = pos;\n const t = QUOTE_RE.exec(text2);\n if (!t) {\n break;\n }\n let canOpen = true;\n let canClose = true;\n pos = t.index + 1;\n const isSingle = t[0] === \"'\";\n let lastChar = 32;\n if (t.index - 1 >= 0) {\n lastChar = text2.charCodeAt(t.index - 1);\n } else {\n for (j = i - 1; j >= 0; j--) {\n if (tokens[j].type === \"softbreak\" || tokens[j].type === \"hardbreak\") break;\n if (!tokens[j].content) continue;\n lastChar = tokens[j].content.charCodeAt(tokens[j].content.length - 1);\n break;\n }\n }\n let nextChar = 32;\n if (pos < max2) {\n nextChar = text2.charCodeAt(pos);\n } else {\n for (j = i + 1; j < tokens.length; j++) {\n if (tokens[j].type === \"softbreak\" || tokens[j].type === \"hardbreak\") break;\n if (!tokens[j].content) continue;\n nextChar = tokens[j].content.charCodeAt(0);\n break;\n }\n }\n const isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar));\n const isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar));\n const isLastWhiteSpace = isWhiteSpace(lastChar);\n const isNextWhiteSpace = isWhiteSpace(nextChar);\n if (isNextWhiteSpace) {\n canOpen = false;\n } else if (isNextPunctChar) {\n if (!(isLastWhiteSpace || isLastPunctChar)) {\n canOpen = false;\n }\n }\n if (isLastWhiteSpace) {\n canClose = false;\n } else if (isLastPunctChar) {\n if (!(isNextWhiteSpace || isNextPunctChar)) {\n canClose = false;\n }\n }\n if (nextChar === 34 && t[0] === '\"') {\n if (lastChar >= 48 && lastChar <= 57) {\n canClose = canOpen = false;\n }\n }\n if (canOpen && canClose) {\n canOpen = isLastPunctChar;\n canClose = isNextPunctChar;\n }\n if (!canOpen && !canClose) {\n if (isSingle) {\n token.content = replaceAt(token.content, t.index, APOSTROPHE);\n }\n continue;\n }\n if (canClose) {\n for (j = stack.length - 1; j >= 0; j--) {\n let item = stack[j];\n if (stack[j].level < thisLevel) {\n break;\n }\n if (item.single === isSingle && stack[j].level === thisLevel) {\n item = stack[j];\n let openQuote;\n let closeQuote;\n if (isSingle) {\n openQuote = state.md.options.quotes[2];\n closeQuote = state.md.options.quotes[3];\n } else {\n openQuote = state.md.options.quotes[0];\n closeQuote = state.md.options.quotes[1];\n }\n token.content = replaceAt(token.content, t.index, closeQuote);\n tokens[item.token].content = replaceAt(\n tokens[item.token].content,\n item.pos,\n openQuote\n );\n pos += closeQuote.length - 1;\n if (item.token === i) {\n pos += openQuote.length - 1;\n }\n text2 = token.content;\n max2 = text2.length;\n stack.length = j;\n continue OUTER;\n }\n }\n }\n if (canOpen) {\n stack.push({\n token: i,\n pos: t.index,\n single: isSingle,\n level: thisLevel\n });\n } else if (canClose && isSingle) {\n token.content = replaceAt(token.content, t.index, APOSTROPHE);\n }\n }\n }\n}\nfunction smartquotes(state) {\n if (!state.md.options.typographer) {\n return;\n }\n for (let blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) {\n if (state.tokens[blkIdx].type !== \"inline\" || !QUOTE_TEST_RE.test(state.tokens[blkIdx].content)) {\n continue;\n }\n process_inlines(state.tokens[blkIdx].children, state);\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/text_join.mjs\nfunction text_join(state) {\n let curr, last;\n const blockTokens = state.tokens;\n const l = blockTokens.length;\n for (let j = 0; j < l; j++) {\n if (blockTokens[j].type !== \"inline\") continue;\n const tokens = blockTokens[j].children;\n const max2 = tokens.length;\n for (curr = 0; curr < max2; curr++) {\n if (tokens[curr].type === \"text_special\") {\n tokens[curr].type = \"text\";\n }\n }\n for (curr = last = 0; curr < max2; curr++) {\n if (tokens[curr].type === \"text\" && curr + 1 < max2 && tokens[curr + 1].type === \"text\") {\n tokens[curr + 1].content = tokens[curr].content + tokens[curr + 1].content;\n } else {\n if (curr !== last) {\n tokens[last] = tokens[curr];\n }\n last++;\n }\n }\n if (curr !== last) {\n tokens.length = last;\n }\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/parser_core.mjs\nvar _rules = [\n [\"normalize\", normalize2],\n [\"block\", block],\n [\"inline\", inline],\n [\"linkify\", linkify],\n [\"replacements\", replace],\n [\"smartquotes\", smartquotes],\n // `text_join` finds `text_special` tokens (for escape sequences)\n // and joins them with the rest of the text\n [\"text_join\", text_join]\n];\nfunction Core() {\n this.ruler = new ruler_default();\n for (let i = 0; i < _rules.length; i++) {\n this.ruler.push(_rules[i][0], _rules[i][1]);\n }\n}\nCore.prototype.process = function(state) {\n const rules = this.ruler.getRules(\"\");\n for (let i = 0, l = rules.length; i < l; i++) {\n rules[i](state);\n }\n};\nCore.prototype.State = state_core_default;\nvar parser_core_default = Core;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/state_block.mjs\nfunction StateBlock(src, md, env, tokens) {\n this.src = src;\n this.md = md;\n this.env = env;\n this.tokens = tokens;\n this.bMarks = [];\n this.eMarks = [];\n this.tShift = [];\n this.sCount = [];\n this.bsCount = [];\n this.blkIndent = 0;\n this.line = 0;\n this.lineMax = 0;\n this.tight = false;\n this.ddIndent = -1;\n this.listIndent = -1;\n this.parentType = \"root\";\n this.level = 0;\n const s = this.src;\n for (let start = 0, pos = 0, indent = 0, offset = 0, len = s.length, indent_found = false; pos < len; pos++) {\n const ch = s.charCodeAt(pos);\n if (!indent_found) {\n if (isSpace(ch)) {\n indent++;\n if (ch === 9) {\n offset += 4 - offset % 4;\n } else {\n offset++;\n }\n continue;\n } else {\n indent_found = true;\n }\n }\n if (ch === 10 || pos === len - 1) {\n if (ch !== 10) {\n pos++;\n }\n this.bMarks.push(start);\n this.eMarks.push(pos);\n this.tShift.push(indent);\n this.sCount.push(offset);\n this.bsCount.push(0);\n indent_found = false;\n indent = 0;\n offset = 0;\n start = pos + 1;\n }\n }\n this.bMarks.push(s.length);\n this.eMarks.push(s.length);\n this.tShift.push(0);\n this.sCount.push(0);\n this.bsCount.push(0);\n this.lineMax = this.bMarks.length - 1;\n}\nStateBlock.prototype.push = function(type, tag, nesting) {\n const token = new token_default(type, tag, nesting);\n token.block = true;\n if (nesting < 0) this.level--;\n token.level = this.level;\n if (nesting > 0) this.level++;\n this.tokens.push(token);\n return token;\n};\nStateBlock.prototype.isEmpty = function isEmpty(line) {\n return this.bMarks[line] + this.tShift[line] >= this.eMarks[line];\n};\nStateBlock.prototype.skipEmptyLines = function skipEmptyLines(from) {\n for (let max2 = this.lineMax; from < max2; from++) {\n if (this.bMarks[from] + this.tShift[from] < this.eMarks[from]) {\n break;\n }\n }\n return from;\n};\nStateBlock.prototype.skipSpaces = function skipSpaces(pos) {\n for (let max2 = this.src.length; pos < max2; pos++) {\n const ch = this.src.charCodeAt(pos);\n if (!isSpace(ch)) {\n break;\n }\n }\n return pos;\n};\nStateBlock.prototype.skipSpacesBack = function skipSpacesBack(pos, min) {\n if (pos <= min) {\n return pos;\n }\n while (pos > min) {\n if (!isSpace(this.src.charCodeAt(--pos))) {\n return pos + 1;\n }\n }\n return pos;\n};\nStateBlock.prototype.skipChars = function skipChars(pos, code2) {\n for (let max2 = this.src.length; pos < max2; pos++) {\n if (this.src.charCodeAt(pos) !== code2) {\n break;\n }\n }\n return pos;\n};\nStateBlock.prototype.skipCharsBack = function skipCharsBack(pos, code2, min) {\n if (pos <= min) {\n return pos;\n }\n while (pos > min) {\n if (code2 !== this.src.charCodeAt(--pos)) {\n return pos + 1;\n }\n }\n return pos;\n};\nStateBlock.prototype.getLines = function getLines(begin, end, indent, keepLastLF) {\n if (begin >= end) {\n return \"\";\n }\n const queue = new Array(end - begin);\n for (let i = 0, line = begin; line < end; line++, i++) {\n let lineIndent = 0;\n const lineStart = this.bMarks[line];\n let first = lineStart;\n let last;\n if (line + 1 < end || keepLastLF) {\n last = this.eMarks[line] + 1;\n } else {\n last = this.eMarks[line];\n }\n while (first < last && lineIndent < indent) {\n const ch = this.src.charCodeAt(first);\n if (isSpace(ch)) {\n if (ch === 9) {\n lineIndent += 4 - (lineIndent + this.bsCount[line]) % 4;\n } else {\n lineIndent++;\n }\n } else if (first - lineStart < this.tShift[line]) {\n lineIndent++;\n } else {\n break;\n }\n first++;\n }\n if (lineIndent > indent) {\n queue[i] = new Array(lineIndent - indent + 1).join(\" \") + this.src.slice(first, last);\n } else {\n queue[i] = this.src.slice(first, last);\n }\n }\n return queue.join(\"\");\n};\nStateBlock.prototype.Token = token_default;\nvar state_block_default = StateBlock;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/table.mjs\nvar MAX_AUTOCOMPLETED_CELLS = 65536;\nfunction getLine(state, line) {\n const pos = state.bMarks[line] + state.tShift[line];\n const max2 = state.eMarks[line];\n return state.src.slice(pos, max2);\n}\nfunction escapedSplit(str) {\n const result = [];\n const max2 = str.length;\n let pos = 0;\n let ch = str.charCodeAt(pos);\n let isEscaped = false;\n let lastPos = 0;\n let current = \"\";\n while (pos < max2) {\n if (ch === 124) {\n if (!isEscaped) {\n result.push(current + str.substring(lastPos, pos));\n current = \"\";\n lastPos = pos + 1;\n } else {\n current += str.substring(lastPos, pos - 1);\n lastPos = pos;\n }\n }\n isEscaped = ch === 92;\n pos++;\n ch = str.charCodeAt(pos);\n }\n result.push(current + str.substring(lastPos));\n return result;\n}\nfunction table(state, startLine, endLine, silent) {\n if (startLine + 2 > endLine) {\n return false;\n }\n let nextLine = startLine + 1;\n if (state.sCount[nextLine] < state.blkIndent) {\n return false;\n }\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\n return false;\n }\n let pos = state.bMarks[nextLine] + state.tShift[nextLine];\n if (pos >= state.eMarks[nextLine]) {\n return false;\n }\n const firstCh = state.src.charCodeAt(pos++);\n if (firstCh !== 124 && firstCh !== 45 && firstCh !== 58) {\n return false;\n }\n if (pos >= state.eMarks[nextLine]) {\n return false;\n }\n const secondCh = state.src.charCodeAt(pos++);\n if (secondCh !== 124 && secondCh !== 45 && secondCh !== 58 && !isSpace(secondCh)) {\n return false;\n }\n if (firstCh === 45 && isSpace(secondCh)) {\n return false;\n }\n while (pos < state.eMarks[nextLine]) {\n const ch = state.src.charCodeAt(pos);\n if (ch !== 124 && ch !== 45 && ch !== 58 && !isSpace(ch)) {\n return false;\n }\n pos++;\n }\n let lineText = getLine(state, startLine + 1);\n let columns = lineText.split(\"|\");\n const aligns = [];\n for (let i = 0; i < columns.length; i++) {\n const t = columns[i].trim();\n if (!t) {\n if (i === 0 || i === columns.length - 1) {\n continue;\n } else {\n return false;\n }\n }\n if (!/^:?-+:?$/.test(t)) {\n return false;\n }\n if (t.charCodeAt(t.length - 1) === 58) {\n aligns.push(t.charCodeAt(0) === 58 ? \"center\" : \"right\");\n } else if (t.charCodeAt(0) === 58) {\n aligns.push(\"left\");\n } else {\n aligns.push(\"\");\n }\n }\n lineText = getLine(state, startLine).trim();\n if (lineText.indexOf(\"|\") === -1) {\n return false;\n }\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n columns = escapedSplit(lineText);\n if (columns.length && columns[0] === \"\") columns.shift();\n if (columns.length && columns[columns.length - 1] === \"\") columns.pop();\n const columnCount = columns.length;\n if (columnCount === 0 || columnCount !== aligns.length) {\n return false;\n }\n if (silent) {\n return true;\n }\n const oldParentType = state.parentType;\n state.parentType = \"table\";\n const terminatorRules = state.md.block.ruler.getRules(\"blockquote\");\n const token_to = state.push(\"table_open\", \"table\", 1);\n const tableLines = [startLine, 0];\n token_to.map = tableLines;\n const token_tho = state.push(\"thead_open\", \"thead\", 1);\n token_tho.map = [startLine, startLine + 1];\n const token_htro = state.push(\"tr_open\", \"tr\", 1);\n token_htro.map = [startLine, startLine + 1];\n for (let i = 0; i < columns.length; i++) {\n const token_ho = state.push(\"th_open\", \"th\", 1);\n if (aligns[i]) {\n token_ho.attrs = [[\"style\", \"text-align:\" + aligns[i]]];\n }\n const token_il = state.push(\"inline\", \"\", 0);\n token_il.content = columns[i].trim();\n token_il.children = [];\n state.push(\"th_close\", \"th\", -1);\n }\n state.push(\"tr_close\", \"tr\", -1);\n state.push(\"thead_close\", \"thead\", -1);\n let tbodyLines;\n let autocompletedCells = 0;\n for (nextLine = startLine + 2; nextLine < endLine; nextLine++) {\n if (state.sCount[nextLine] < state.blkIndent) {\n break;\n }\n let terminate = false;\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\n if (terminatorRules[i](state, nextLine, endLine, true)) {\n terminate = true;\n break;\n }\n }\n if (terminate) {\n break;\n }\n lineText = getLine(state, nextLine).trim();\n if (!lineText) {\n break;\n }\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\n break;\n }\n columns = escapedSplit(lineText);\n if (columns.length && columns[0] === \"\") columns.shift();\n if (columns.length && columns[columns.length - 1] === \"\") columns.pop();\n autocompletedCells += columnCount - columns.length;\n if (autocompletedCells > MAX_AUTOCOMPLETED_CELLS) {\n break;\n }\n if (nextLine === startLine + 2) {\n const token_tbo = state.push(\"tbody_open\", \"tbody\", 1);\n token_tbo.map = tbodyLines = [startLine + 2, 0];\n }\n const token_tro = state.push(\"tr_open\", \"tr\", 1);\n token_tro.map = [nextLine, nextLine + 1];\n for (let i = 0; i < columnCount; i++) {\n const token_tdo = state.push(\"td_open\", \"td\", 1);\n if (aligns[i]) {\n token_tdo.attrs = [[\"style\", \"text-align:\" + aligns[i]]];\n }\n const token_il = state.push(\"inline\", \"\", 0);\n token_il.content = columns[i] ? columns[i].trim() : \"\";\n token_il.children = [];\n state.push(\"td_close\", \"td\", -1);\n }\n state.push(\"tr_close\", \"tr\", -1);\n }\n if (tbodyLines) {\n state.push(\"tbody_close\", \"tbody\", -1);\n tbodyLines[1] = nextLine;\n }\n state.push(\"table_close\", \"table\", -1);\n tableLines[1] = nextLine;\n state.parentType = oldParentType;\n state.line = nextLine;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/code.mjs\nfunction code(state, startLine, endLine) {\n if (state.sCount[startLine] - state.blkIndent < 4) {\n return false;\n }\n let nextLine = startLine + 1;\n let last = nextLine;\n while (nextLine < endLine) {\n if (state.isEmpty(nextLine)) {\n nextLine++;\n continue;\n }\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\n nextLine++;\n last = nextLine;\n continue;\n }\n break;\n }\n state.line = last;\n const token = state.push(\"code_block\", \"code\", 0);\n token.content = state.getLines(startLine, last, 4 + state.blkIndent, false) + \"\\n\";\n token.map = [startLine, state.line];\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/fence.mjs\nfunction fence(state, startLine, endLine, silent) {\n let pos = state.bMarks[startLine] + state.tShift[startLine];\n let max2 = state.eMarks[startLine];\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n if (pos + 3 > max2) {\n return false;\n }\n const marker = state.src.charCodeAt(pos);\n if (marker !== 126 && marker !== 96) {\n return false;\n }\n let mem = pos;\n pos = state.skipChars(pos, marker);\n let len = pos - mem;\n if (len < 3) {\n return false;\n }\n const markup = state.src.slice(mem, pos);\n const params = state.src.slice(pos, max2);\n if (marker === 96) {\n if (params.indexOf(String.fromCharCode(marker)) >= 0) {\n return false;\n }\n }\n if (silent) {\n return true;\n }\n let nextLine = startLine;\n let haveEndMarker = false;\n for (; ; ) {\n nextLine++;\n if (nextLine >= endLine) {\n break;\n }\n pos = mem = state.bMarks[nextLine] + state.tShift[nextLine];\n max2 = state.eMarks[nextLine];\n if (pos < max2 && state.sCount[nextLine] < state.blkIndent) {\n break;\n }\n if (state.src.charCodeAt(pos) !== marker) {\n continue;\n }\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\n continue;\n }\n pos = state.skipChars(pos, marker);\n if (pos - mem < len) {\n continue;\n }\n pos = state.skipSpaces(pos);\n if (pos < max2) {\n continue;\n }\n haveEndMarker = true;\n break;\n }\n len = state.sCount[startLine];\n state.line = nextLine + (haveEndMarker ? 1 : 0);\n const token = state.push(\"fence\", \"code\", 0);\n token.info = params;\n token.content = state.getLines(startLine + 1, nextLine, len, true);\n token.markup = markup;\n token.map = [startLine, state.line];\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/blockquote.mjs\nfunction blockquote(state, startLine, endLine, silent) {\n let pos = state.bMarks[startLine] + state.tShift[startLine];\n let max2 = state.eMarks[startLine];\n const oldLineMax = state.lineMax;\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n if (state.src.charCodeAt(pos) !== 62) {\n return false;\n }\n if (silent) {\n return true;\n }\n const oldBMarks = [];\n const oldBSCount = [];\n const oldSCount = [];\n const oldTShift = [];\n const terminatorRules = state.md.block.ruler.getRules(\"blockquote\");\n const oldParentType = state.parentType;\n state.parentType = \"blockquote\";\n let lastLineEmpty = false;\n let nextLine;\n for (nextLine = startLine; nextLine < endLine; nextLine++) {\n const isOutdented = state.sCount[nextLine] < state.blkIndent;\n pos = state.bMarks[nextLine] + state.tShift[nextLine];\n max2 = state.eMarks[nextLine];\n if (pos >= max2) {\n break;\n }\n if (state.src.charCodeAt(pos++) === 62 && !isOutdented) {\n let initial = state.sCount[nextLine] + 1;\n let spaceAfterMarker;\n let adjustTab;\n if (state.src.charCodeAt(pos) === 32) {\n pos++;\n initial++;\n adjustTab = false;\n spaceAfterMarker = true;\n } else if (state.src.charCodeAt(pos) === 9) {\n spaceAfterMarker = true;\n if ((state.bsCount[nextLine] + initial) % 4 === 3) {\n pos++;\n initial++;\n adjustTab = false;\n } else {\n adjustTab = true;\n }\n } else {\n spaceAfterMarker = false;\n }\n let offset = initial;\n oldBMarks.push(state.bMarks[nextLine]);\n state.bMarks[nextLine] = pos;\n while (pos < max2) {\n const ch = state.src.charCodeAt(pos);\n if (isSpace(ch)) {\n if (ch === 9) {\n offset += 4 - (offset + state.bsCount[nextLine] + (adjustTab ? 1 : 0)) % 4;\n } else {\n offset++;\n }\n } else {\n break;\n }\n pos++;\n }\n lastLineEmpty = pos >= max2;\n oldBSCount.push(state.bsCount[nextLine]);\n state.bsCount[nextLine] = state.sCount[nextLine] + 1 + (spaceAfterMarker ? 1 : 0);\n oldSCount.push(state.sCount[nextLine]);\n state.sCount[nextLine] = offset - initial;\n oldTShift.push(state.tShift[nextLine]);\n state.tShift[nextLine] = pos - state.bMarks[nextLine];\n continue;\n }\n if (lastLineEmpty) {\n break;\n }\n let terminate = false;\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\n if (terminatorRules[i](state, nextLine, endLine, true)) {\n terminate = true;\n break;\n }\n }\n if (terminate) {\n state.lineMax = nextLine;\n if (state.blkIndent !== 0) {\n oldBMarks.push(state.bMarks[nextLine]);\n oldBSCount.push(state.bsCount[nextLine]);\n oldTShift.push(state.tShift[nextLine]);\n oldSCount.push(state.sCount[nextLine]);\n state.sCount[nextLine] -= state.blkIndent;\n }\n break;\n }\n oldBMarks.push(state.bMarks[nextLine]);\n oldBSCount.push(state.bsCount[nextLine]);\n oldTShift.push(state.tShift[nextLine]);\n oldSCount.push(state.sCount[nextLine]);\n state.sCount[nextLine] = -1;\n }\n const oldIndent = state.blkIndent;\n state.blkIndent = 0;\n const token_o = state.push(\"blockquote_open\", \"blockquote\", 1);\n token_o.markup = \">\";\n const lines = [startLine, 0];\n token_o.map = lines;\n state.md.block.tokenize(state, startLine, nextLine);\n const token_c = state.push(\"blockquote_close\", \"blockquote\", -1);\n token_c.markup = \">\";\n state.lineMax = oldLineMax;\n state.parentType = oldParentType;\n lines[1] = state.line;\n for (let i = 0; i < oldTShift.length; i++) {\n state.bMarks[i + startLine] = oldBMarks[i];\n state.tShift[i + startLine] = oldTShift[i];\n state.sCount[i + startLine] = oldSCount[i];\n state.bsCount[i + startLine] = oldBSCount[i];\n }\n state.blkIndent = oldIndent;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/hr.mjs\nfunction hr(state, startLine, endLine, silent) {\n const max2 = state.eMarks[startLine];\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n let pos = state.bMarks[startLine] + state.tShift[startLine];\n const marker = state.src.charCodeAt(pos++);\n if (marker !== 42 && marker !== 45 && marker !== 95) {\n return false;\n }\n let cnt = 1;\n while (pos < max2) {\n const ch = state.src.charCodeAt(pos++);\n if (ch !== marker && !isSpace(ch)) {\n return false;\n }\n if (ch === marker) {\n cnt++;\n }\n }\n if (cnt < 3) {\n return false;\n }\n if (silent) {\n return true;\n }\n state.line = startLine + 1;\n const token = state.push(\"hr\", \"hr\", 0);\n token.map = [startLine, state.line];\n token.markup = Array(cnt + 1).join(String.fromCharCode(marker));\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/list.mjs\nfunction skipBulletListMarker(state, startLine) {\n const max2 = state.eMarks[startLine];\n let pos = state.bMarks[startLine] + state.tShift[startLine];\n const marker = state.src.charCodeAt(pos++);\n if (marker !== 42 && marker !== 45 && marker !== 43) {\n return -1;\n }\n if (pos < max2) {\n const ch = state.src.charCodeAt(pos);\n if (!isSpace(ch)) {\n return -1;\n }\n }\n return pos;\n}\nfunction skipOrderedListMarker(state, startLine) {\n const start = state.bMarks[startLine] + state.tShift[startLine];\n const max2 = state.eMarks[startLine];\n let pos = start;\n if (pos + 1 >= max2) {\n return -1;\n }\n let ch = state.src.charCodeAt(pos++);\n if (ch < 48 || ch > 57) {\n return -1;\n }\n for (; ; ) {\n if (pos >= max2) {\n return -1;\n }\n ch = state.src.charCodeAt(pos++);\n if (ch >= 48 && ch <= 57) {\n if (pos - start >= 10) {\n return -1;\n }\n continue;\n }\n if (ch === 41 || ch === 46) {\n break;\n }\n return -1;\n }\n if (pos < max2) {\n ch = state.src.charCodeAt(pos);\n if (!isSpace(ch)) {\n return -1;\n }\n }\n return pos;\n}\nfunction markTightParagraphs(state, idx) {\n const level = state.level + 2;\n for (let i = idx + 2, l = state.tokens.length - 2; i < l; i++) {\n if (state.tokens[i].level === level && state.tokens[i].type === \"paragraph_open\") {\n state.tokens[i + 2].hidden = true;\n state.tokens[i].hidden = true;\n i += 2;\n }\n }\n}\nfunction list(state, startLine, endLine, silent) {\n let max2, pos, start, token;\n let nextLine = startLine;\n let tight = true;\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\n return false;\n }\n if (state.listIndent >= 0 && state.sCount[nextLine] - state.listIndent >= 4 && state.sCount[nextLine] < state.blkIndent) {\n return false;\n }\n let isTerminatingParagraph = false;\n if (silent && state.parentType === \"paragraph\") {\n if (state.sCount[nextLine] >= state.blkIndent) {\n isTerminatingParagraph = true;\n }\n }\n let isOrdered;\n let markerValue;\n let posAfterMarker;\n if ((posAfterMarker = skipOrderedListMarker(state, nextLine)) >= 0) {\n isOrdered = true;\n start = state.bMarks[nextLine] + state.tShift[nextLine];\n markerValue = Number(state.src.slice(start, posAfterMarker - 1));\n if (isTerminatingParagraph && markerValue !== 1) return false;\n } else if ((posAfterMarker = skipBulletListMarker(state, nextLine)) >= 0) {\n isOrdered = false;\n } else {\n return false;\n }\n if (isTerminatingParagraph) {\n if (state.skipSpaces(posAfterMarker) >= state.eMarks[nextLine]) return false;\n }\n if (silent) {\n return true;\n }\n const markerCharCode = state.src.charCodeAt(posAfterMarker - 1);\n const listTokIdx = state.tokens.length;\n if (isOrdered) {\n token = state.push(\"ordered_list_open\", \"ol\", 1);\n if (markerValue !== 1) {\n token.attrs = [[\"start\", markerValue]];\n }\n } else {\n token = state.push(\"bullet_list_open\", \"ul\", 1);\n }\n const listLines = [nextLine, 0];\n token.map = listLines;\n token.markup = String.fromCharCode(markerCharCode);\n let prevEmptyEnd = false;\n const terminatorRules = state.md.block.ruler.getRules(\"list\");\n const oldParentType = state.parentType;\n state.parentType = \"list\";\n while (nextLine < endLine) {\n pos = posAfterMarker;\n max2 = state.eMarks[nextLine];\n const initial = state.sCount[nextLine] + posAfterMarker - (state.bMarks[nextLine] + state.tShift[nextLine]);\n let offset = initial;\n while (pos < max2) {\n const ch = state.src.charCodeAt(pos);\n if (ch === 9) {\n offset += 4 - (offset + state.bsCount[nextLine]) % 4;\n } else if (ch === 32) {\n offset++;\n } else {\n break;\n }\n pos++;\n }\n const contentStart = pos;\n let indentAfterMarker;\n if (contentStart >= max2) {\n indentAfterMarker = 1;\n } else {\n indentAfterMarker = offset - initial;\n }\n if (indentAfterMarker > 4) {\n indentAfterMarker = 1;\n }\n const indent = initial + indentAfterMarker;\n token = state.push(\"list_item_open\", \"li\", 1);\n token.markup = String.fromCharCode(markerCharCode);\n const itemLines = [nextLine, 0];\n token.map = itemLines;\n if (isOrdered) {\n token.info = state.src.slice(start, posAfterMarker - 1);\n }\n const oldTight = state.tight;\n const oldTShift = state.tShift[nextLine];\n const oldSCount = state.sCount[nextLine];\n const oldListIndent = state.listIndent;\n state.listIndent = state.blkIndent;\n state.blkIndent = indent;\n state.tight = true;\n state.tShift[nextLine] = contentStart - state.bMarks[nextLine];\n state.sCount[nextLine] = offset;\n if (contentStart >= max2 && state.isEmpty(nextLine + 1)) {\n state.line = Math.min(state.line + 2, endLine);\n } else {\n state.md.block.tokenize(state, nextLine, endLine, true);\n }\n if (!state.tight || prevEmptyEnd) {\n tight = false;\n }\n prevEmptyEnd = state.line - nextLine > 1 && state.isEmpty(state.line - 1);\n state.blkIndent = state.listIndent;\n state.listIndent = oldListIndent;\n state.tShift[nextLine] = oldTShift;\n state.sCount[nextLine] = oldSCount;\n state.tight = oldTight;\n token = state.push(\"list_item_close\", \"li\", -1);\n token.markup = String.fromCharCode(markerCharCode);\n nextLine = state.line;\n itemLines[1] = nextLine;\n if (nextLine >= endLine) {\n break;\n }\n if (state.sCount[nextLine] < state.blkIndent) {\n break;\n }\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\n break;\n }\n let terminate = false;\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\n if (terminatorRules[i](state, nextLine, endLine, true)) {\n terminate = true;\n break;\n }\n }\n if (terminate) {\n break;\n }\n if (isOrdered) {\n posAfterMarker = skipOrderedListMarker(state, nextLine);\n if (posAfterMarker < 0) {\n break;\n }\n start = state.bMarks[nextLine] + state.tShift[nextLine];\n } else {\n posAfterMarker = skipBulletListMarker(state, nextLine);\n if (posAfterMarker < 0) {\n break;\n }\n }\n if (markerCharCode !== state.src.charCodeAt(posAfterMarker - 1)) {\n break;\n }\n }\n if (isOrdered) {\n token = state.push(\"ordered_list_close\", \"ol\", -1);\n } else {\n token = state.push(\"bullet_list_close\", \"ul\", -1);\n }\n token.markup = String.fromCharCode(markerCharCode);\n listLines[1] = nextLine;\n state.line = nextLine;\n state.parentType = oldParentType;\n if (tight) {\n markTightParagraphs(state, listTokIdx);\n }\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/reference.mjs\nfunction reference(state, startLine, _endLine, silent) {\n let pos = state.bMarks[startLine] + state.tShift[startLine];\n let max2 = state.eMarks[startLine];\n let nextLine = startLine + 1;\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n if (state.src.charCodeAt(pos) !== 91) {\n return false;\n }\n function getNextLine(nextLine2) {\n const endLine = state.lineMax;\n if (nextLine2 >= endLine || state.isEmpty(nextLine2)) {\n return null;\n }\n let isContinuation = false;\n if (state.sCount[nextLine2] - state.blkIndent > 3) {\n isContinuation = true;\n }\n if (state.sCount[nextLine2] < 0) {\n isContinuation = true;\n }\n if (!isContinuation) {\n const terminatorRules = state.md.block.ruler.getRules(\"reference\");\n const oldParentType = state.parentType;\n state.parentType = \"reference\";\n let terminate = false;\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\n if (terminatorRules[i](state, nextLine2, endLine, true)) {\n terminate = true;\n break;\n }\n }\n state.parentType = oldParentType;\n if (terminate) {\n return null;\n }\n }\n const pos2 = state.bMarks[nextLine2] + state.tShift[nextLine2];\n const max3 = state.eMarks[nextLine2];\n return state.src.slice(pos2, max3 + 1);\n }\n let str = state.src.slice(pos, max2 + 1);\n max2 = str.length;\n let labelEnd = -1;\n for (pos = 1; pos < max2; pos++) {\n const ch = str.charCodeAt(pos);\n if (ch === 91) {\n return false;\n } else if (ch === 93) {\n labelEnd = pos;\n break;\n } else if (ch === 10) {\n const lineContent = getNextLine(nextLine);\n if (lineContent !== null) {\n str += lineContent;\n max2 = str.length;\n nextLine++;\n }\n } else if (ch === 92) {\n pos++;\n if (pos < max2 && str.charCodeAt(pos) === 10) {\n const lineContent = getNextLine(nextLine);\n if (lineContent !== null) {\n str += lineContent;\n max2 = str.length;\n nextLine++;\n }\n }\n }\n }\n if (labelEnd < 0 || str.charCodeAt(labelEnd + 1) !== 58) {\n return false;\n }\n for (pos = labelEnd + 2; pos < max2; pos++) {\n const ch = str.charCodeAt(pos);\n if (ch === 10) {\n const lineContent = getNextLine(nextLine);\n if (lineContent !== null) {\n str += lineContent;\n max2 = str.length;\n nextLine++;\n }\n } else if (isSpace(ch)) {\n } else {\n break;\n }\n }\n const destRes = state.md.helpers.parseLinkDestination(str, pos, max2);\n if (!destRes.ok) {\n return false;\n }\n const href = state.md.normalizeLink(destRes.str);\n if (!state.md.validateLink(href)) {\n return false;\n }\n pos = destRes.pos;\n const destEndPos = pos;\n const destEndLineNo = nextLine;\n const start = pos;\n for (; pos < max2; pos++) {\n const ch = str.charCodeAt(pos);\n if (ch === 10) {\n const lineContent = getNextLine(nextLine);\n if (lineContent !== null) {\n str += lineContent;\n max2 = str.length;\n nextLine++;\n }\n } else if (isSpace(ch)) {\n } else {\n break;\n }\n }\n let titleRes = state.md.helpers.parseLinkTitle(str, pos, max2);\n while (titleRes.can_continue) {\n const lineContent = getNextLine(nextLine);\n if (lineContent === null) break;\n str += lineContent;\n pos = max2;\n max2 = str.length;\n nextLine++;\n titleRes = state.md.helpers.parseLinkTitle(str, pos, max2, titleRes);\n }\n let title;\n if (pos < max2 && start !== pos && titleRes.ok) {\n title = titleRes.str;\n pos = titleRes.pos;\n } else {\n title = \"\";\n pos = destEndPos;\n nextLine = destEndLineNo;\n }\n while (pos < max2) {\n const ch = str.charCodeAt(pos);\n if (!isSpace(ch)) {\n break;\n }\n pos++;\n }\n if (pos < max2 && str.charCodeAt(pos) !== 10) {\n if (title) {\n title = \"\";\n pos = destEndPos;\n nextLine = destEndLineNo;\n while (pos < max2) {\n const ch = str.charCodeAt(pos);\n if (!isSpace(ch)) {\n break;\n }\n pos++;\n }\n }\n }\n if (pos < max2 && str.charCodeAt(pos) !== 10) {\n return false;\n }\n const label = normalizeReference(str.slice(1, labelEnd));\n if (!label) {\n return false;\n }\n if (silent) {\n return true;\n }\n if (typeof state.env.references === \"undefined\") {\n state.env.references = {};\n }\n if (typeof state.env.references[label] === \"undefined\") {\n state.env.references[label] = { title, href };\n }\n state.line = nextLine;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/common/html_blocks.mjs\nvar html_blocks_default = [\n \"address\",\n \"article\",\n \"aside\",\n \"base\",\n \"basefont\",\n \"blockquote\",\n \"body\",\n \"caption\",\n \"center\",\n \"col\",\n \"colgroup\",\n \"dd\",\n \"details\",\n \"dialog\",\n \"dir\",\n \"div\",\n \"dl\",\n \"dt\",\n \"fieldset\",\n \"figcaption\",\n \"figure\",\n \"footer\",\n \"form\",\n \"frame\",\n \"frameset\",\n \"h1\",\n \"h2\",\n \"h3\",\n \"h4\",\n \"h5\",\n \"h6\",\n \"head\",\n \"header\",\n \"hr\",\n \"html\",\n \"iframe\",\n \"legend\",\n \"li\",\n \"link\",\n \"main\",\n \"menu\",\n \"menuitem\",\n \"nav\",\n \"noframes\",\n \"ol\",\n \"optgroup\",\n \"option\",\n \"p\",\n \"param\",\n \"search\",\n \"section\",\n \"summary\",\n \"table\",\n \"tbody\",\n \"td\",\n \"tfoot\",\n \"th\",\n \"thead\",\n \"title\",\n \"tr\",\n \"track\",\n \"ul\"\n];\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/common/html_re.mjs\nvar attr_name = \"[a-zA-Z_:][a-zA-Z0-9:._-]*\";\nvar unquoted = \"[^\\\"'=<>`\\\\x00-\\\\x20]+\";\nvar single_quoted = \"'[^']*'\";\nvar double_quoted = '\"[^\"]*\"';\nvar attr_value = \"(?:\" + unquoted + \"|\" + single_quoted + \"|\" + double_quoted + \")\";\nvar attribute = \"(?:\\\\s+\" + attr_name + \"(?:\\\\s*=\\\\s*\" + attr_value + \")?)\";\nvar open_tag = \"<[A-Za-z][A-Za-z0-9\\\\-]*\" + attribute + \"*\\\\s*\\\\/?>\";\nvar close_tag = \"<\\\\/[A-Za-z][A-Za-z0-9\\\\-]*\\\\s*>\";\nvar comment = \"\";\nvar processing = \"<[?][\\\\s\\\\S]*?[?]>\";\nvar declaration = \"]*>\";\nvar cdata = \"\";\nvar HTML_TAG_RE = new RegExp(\"^(?:\" + open_tag + \"|\" + close_tag + \"|\" + comment + \"|\" + processing + \"|\" + declaration + \"|\" + cdata + \")\");\nvar HTML_OPEN_CLOSE_TAG_RE = new RegExp(\"^(?:\" + open_tag + \"|\" + close_tag + \")\");\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/html_block.mjs\nvar HTML_SEQUENCES = [\n [/^<(script|pre|style|textarea)(?=(\\s|>|$))/i, /<\\/(script|pre|style|textarea)>/i, true],\n [/^/, true],\n [/^<\\?/, /\\?>/, true],\n [/^/, true],\n [/^/, true],\n [new RegExp(\"^|$))\", \"i\"), /^$/, true],\n [new RegExp(HTML_OPEN_CLOSE_TAG_RE.source + \"\\\\s*$\"), /^$/, false]\n];\nfunction html_block(state, startLine, endLine, silent) {\n let pos = state.bMarks[startLine] + state.tShift[startLine];\n let max2 = state.eMarks[startLine];\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n if (!state.md.options.html) {\n return false;\n }\n if (state.src.charCodeAt(pos) !== 60) {\n return false;\n }\n let lineText = state.src.slice(pos, max2);\n let i = 0;\n for (; i < HTML_SEQUENCES.length; i++) {\n if (HTML_SEQUENCES[i][0].test(lineText)) {\n break;\n }\n }\n if (i === HTML_SEQUENCES.length) {\n return false;\n }\n if (silent) {\n return HTML_SEQUENCES[i][2];\n }\n let nextLine = startLine + 1;\n if (!HTML_SEQUENCES[i][1].test(lineText)) {\n for (; nextLine < endLine; nextLine++) {\n if (state.sCount[nextLine] < state.blkIndent) {\n break;\n }\n pos = state.bMarks[nextLine] + state.tShift[nextLine];\n max2 = state.eMarks[nextLine];\n lineText = state.src.slice(pos, max2);\n if (HTML_SEQUENCES[i][1].test(lineText)) {\n if (lineText.length !== 0) {\n nextLine++;\n }\n break;\n }\n }\n }\n state.line = nextLine;\n const token = state.push(\"html_block\", \"\", 0);\n token.map = [startLine, nextLine];\n token.content = state.getLines(startLine, nextLine, state.blkIndent, true);\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/heading.mjs\nfunction heading(state, startLine, endLine, silent) {\n let pos = state.bMarks[startLine] + state.tShift[startLine];\n let max2 = state.eMarks[startLine];\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n let ch = state.src.charCodeAt(pos);\n if (ch !== 35 || pos >= max2) {\n return false;\n }\n let level = 1;\n ch = state.src.charCodeAt(++pos);\n while (ch === 35 && pos < max2 && level <= 6) {\n level++;\n ch = state.src.charCodeAt(++pos);\n }\n if (level > 6 || pos < max2 && !isSpace(ch)) {\n return false;\n }\n if (silent) {\n return true;\n }\n max2 = state.skipSpacesBack(max2, pos);\n const tmp = state.skipCharsBack(max2, 35, pos);\n if (tmp > pos && isSpace(state.src.charCodeAt(tmp - 1))) {\n max2 = tmp;\n }\n state.line = startLine + 1;\n const token_o = state.push(\"heading_open\", \"h\" + String(level), 1);\n token_o.markup = \"########\".slice(0, level);\n token_o.map = [startLine, state.line];\n const token_i = state.push(\"inline\", \"\", 0);\n token_i.content = state.src.slice(pos, max2).trim();\n token_i.map = [startLine, state.line];\n token_i.children = [];\n const token_c = state.push(\"heading_close\", \"h\" + String(level), -1);\n token_c.markup = \"########\".slice(0, level);\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/lheading.mjs\nfunction lheading(state, startLine, endLine) {\n const terminatorRules = state.md.block.ruler.getRules(\"paragraph\");\n if (state.sCount[startLine] - state.blkIndent >= 4) {\n return false;\n }\n const oldParentType = state.parentType;\n state.parentType = \"paragraph\";\n let level = 0;\n let marker;\n let nextLine = startLine + 1;\n for (; nextLine < endLine && !state.isEmpty(nextLine); nextLine++) {\n if (state.sCount[nextLine] - state.blkIndent > 3) {\n continue;\n }\n if (state.sCount[nextLine] >= state.blkIndent) {\n let pos = state.bMarks[nextLine] + state.tShift[nextLine];\n const max2 = state.eMarks[nextLine];\n if (pos < max2) {\n marker = state.src.charCodeAt(pos);\n if (marker === 45 || marker === 61) {\n pos = state.skipChars(pos, marker);\n pos = state.skipSpaces(pos);\n if (pos >= max2) {\n level = marker === 61 ? 1 : 2;\n break;\n }\n }\n }\n }\n if (state.sCount[nextLine] < 0) {\n continue;\n }\n let terminate = false;\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\n if (terminatorRules[i](state, nextLine, endLine, true)) {\n terminate = true;\n break;\n }\n }\n if (terminate) {\n break;\n }\n }\n if (!level) {\n return false;\n }\n const content = state.getLines(startLine, nextLine, state.blkIndent, false).trim();\n state.line = nextLine + 1;\n const token_o = state.push(\"heading_open\", \"h\" + String(level), 1);\n token_o.markup = String.fromCharCode(marker);\n token_o.map = [startLine, state.line];\n const token_i = state.push(\"inline\", \"\", 0);\n token_i.content = content;\n token_i.map = [startLine, state.line - 1];\n token_i.children = [];\n const token_c = state.push(\"heading_close\", \"h\" + String(level), -1);\n token_c.markup = String.fromCharCode(marker);\n state.parentType = oldParentType;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/paragraph.mjs\nfunction paragraph(state, startLine, endLine) {\n const terminatorRules = state.md.block.ruler.getRules(\"paragraph\");\n const oldParentType = state.parentType;\n let nextLine = startLine + 1;\n state.parentType = \"paragraph\";\n for (; nextLine < endLine && !state.isEmpty(nextLine); nextLine++) {\n if (state.sCount[nextLine] - state.blkIndent > 3) {\n continue;\n }\n if (state.sCount[nextLine] < 0) {\n continue;\n }\n let terminate = false;\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\n if (terminatorRules[i](state, nextLine, endLine, true)) {\n terminate = true;\n break;\n }\n }\n if (terminate) {\n break;\n }\n }\n const content = state.getLines(startLine, nextLine, state.blkIndent, false).trim();\n state.line = nextLine;\n const token_o = state.push(\"paragraph_open\", \"p\", 1);\n token_o.map = [startLine, state.line];\n const token_i = state.push(\"inline\", \"\", 0);\n token_i.content = content;\n token_i.map = [startLine, state.line];\n token_i.children = [];\n state.push(\"paragraph_close\", \"p\", -1);\n state.parentType = oldParentType;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/parser_block.mjs\nvar _rules2 = [\n // First 2 params - rule name & source. Secondary array - list of rules,\n // which can be terminated by this one.\n [\"table\", table, [\"paragraph\", \"reference\"]],\n [\"code\", code],\n [\"fence\", fence, [\"paragraph\", \"reference\", \"blockquote\", \"list\"]],\n [\"blockquote\", blockquote, [\"paragraph\", \"reference\", \"blockquote\", \"list\"]],\n [\"hr\", hr, [\"paragraph\", \"reference\", \"blockquote\", \"list\"]],\n [\"list\", list, [\"paragraph\", \"reference\", \"blockquote\"]],\n [\"reference\", reference],\n [\"html_block\", html_block, [\"paragraph\", \"reference\", \"blockquote\"]],\n [\"heading\", heading, [\"paragraph\", \"reference\", \"blockquote\"]],\n [\"lheading\", lheading],\n [\"paragraph\", paragraph]\n];\nfunction ParserBlock() {\n this.ruler = new ruler_default();\n for (let i = 0; i < _rules2.length; i++) {\n this.ruler.push(_rules2[i][0], _rules2[i][1], { alt: (_rules2[i][2] || []).slice() });\n }\n}\nParserBlock.prototype.tokenize = function(state, startLine, endLine) {\n const rules = this.ruler.getRules(\"\");\n const len = rules.length;\n const maxNesting = state.md.options.maxNesting;\n let line = startLine;\n let hasEmptyLines = false;\n while (line < endLine) {\n state.line = line = state.skipEmptyLines(line);\n if (line >= endLine) {\n break;\n }\n if (state.sCount[line] < state.blkIndent) {\n break;\n }\n if (state.level >= maxNesting) {\n state.line = endLine;\n break;\n }\n const prevLine = state.line;\n let ok = false;\n for (let i = 0; i < len; i++) {\n ok = rules[i](state, line, endLine, false);\n if (ok) {\n if (prevLine >= state.line) {\n throw new Error(\"block rule didn't increment state.line\");\n }\n break;\n }\n }\n if (!ok) throw new Error(\"none of the block rules matched\");\n state.tight = !hasEmptyLines;\n if (state.isEmpty(state.line - 1)) {\n hasEmptyLines = true;\n }\n line = state.line;\n if (line < endLine && state.isEmpty(line)) {\n hasEmptyLines = true;\n line++;\n state.line = line;\n }\n }\n};\nParserBlock.prototype.parse = function(src, md, env, outTokens) {\n if (!src) {\n return;\n }\n const state = new this.State(src, md, env, outTokens);\n this.tokenize(state, state.line, state.lineMax);\n};\nParserBlock.prototype.State = state_block_default;\nvar parser_block_default = ParserBlock;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/state_inline.mjs\nfunction StateInline(src, md, env, outTokens) {\n this.src = src;\n this.env = env;\n this.md = md;\n this.tokens = outTokens;\n this.tokens_meta = Array(outTokens.length);\n this.pos = 0;\n this.posMax = this.src.length;\n this.level = 0;\n this.pending = \"\";\n this.pendingLevel = 0;\n this.cache = {};\n this.delimiters = [];\n this._prev_delimiters = [];\n this.backticks = {};\n this.backticksScanned = false;\n this.linkLevel = 0;\n}\nStateInline.prototype.pushPending = function() {\n const token = new token_default(\"text\", \"\", 0);\n token.content = this.pending;\n token.level = this.pendingLevel;\n this.tokens.push(token);\n this.pending = \"\";\n return token;\n};\nStateInline.prototype.push = function(type, tag, nesting) {\n if (this.pending) {\n this.pushPending();\n }\n const token = new token_default(type, tag, nesting);\n let token_meta = null;\n if (nesting < 0) {\n this.level--;\n this.delimiters = this._prev_delimiters.pop();\n }\n token.level = this.level;\n if (nesting > 0) {\n this.level++;\n this._prev_delimiters.push(this.delimiters);\n this.delimiters = [];\n token_meta = { delimiters: this.delimiters };\n }\n this.pendingLevel = this.level;\n this.tokens.push(token);\n this.tokens_meta.push(token_meta);\n return token;\n};\nStateInline.prototype.scanDelims = function(start, canSplitWord) {\n const max2 = this.posMax;\n const marker = this.src.charCodeAt(start);\n const lastChar = start > 0 ? this.src.charCodeAt(start - 1) : 32;\n let pos = start;\n while (pos < max2 && this.src.charCodeAt(pos) === marker) {\n pos++;\n }\n const count = pos - start;\n const nextChar = pos < max2 ? this.src.charCodeAt(pos) : 32;\n const isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar));\n const isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar));\n const isLastWhiteSpace = isWhiteSpace(lastChar);\n const isNextWhiteSpace = isWhiteSpace(nextChar);\n const left_flanking = !isNextWhiteSpace && (!isNextPunctChar || isLastWhiteSpace || isLastPunctChar);\n const right_flanking = !isLastWhiteSpace && (!isLastPunctChar || isNextWhiteSpace || isNextPunctChar);\n const can_open = left_flanking && (canSplitWord || !right_flanking || isLastPunctChar);\n const can_close = right_flanking && (canSplitWord || !left_flanking || isNextPunctChar);\n return { can_open, can_close, length: count };\n};\nStateInline.prototype.Token = token_default;\nvar state_inline_default = StateInline;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/text.mjs\nfunction isTerminatorChar(ch) {\n switch (ch) {\n case 10:\n case 33:\n case 35:\n case 36:\n case 37:\n case 38:\n case 42:\n case 43:\n case 45:\n case 58:\n case 60:\n case 61:\n case 62:\n case 64:\n case 91:\n case 92:\n case 93:\n case 94:\n case 95:\n case 96:\n case 123:\n case 125:\n case 126:\n return true;\n default:\n return false;\n }\n}\nfunction text(state, silent) {\n let pos = state.pos;\n while (pos < state.posMax && !isTerminatorChar(state.src.charCodeAt(pos))) {\n pos++;\n }\n if (pos === state.pos) {\n return false;\n }\n if (!silent) {\n state.pending += state.src.slice(state.pos, pos);\n }\n state.pos = pos;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/linkify.mjs\nvar SCHEME_RE = /(?:^|[^a-z0-9.+-])([a-z][a-z0-9.+-]*)$/i;\nfunction linkify2(state, silent) {\n if (!state.md.options.linkify) return false;\n if (state.linkLevel > 0) return false;\n const pos = state.pos;\n const max2 = state.posMax;\n if (pos + 3 > max2) return false;\n if (state.src.charCodeAt(pos) !== 58) return false;\n if (state.src.charCodeAt(pos + 1) !== 47) return false;\n if (state.src.charCodeAt(pos + 2) !== 47) return false;\n const match2 = state.pending.match(SCHEME_RE);\n if (!match2) return false;\n const proto = match2[1];\n const link2 = state.md.linkify.matchAtStart(state.src.slice(pos - proto.length));\n if (!link2) return false;\n let url = link2.url;\n if (url.length <= proto.length) return false;\n let urlEnd = url.length;\n while (urlEnd > 0 && url.charCodeAt(urlEnd - 1) === 42) {\n urlEnd--;\n }\n if (urlEnd !== url.length) {\n url = url.slice(0, urlEnd);\n }\n const fullUrl = state.md.normalizeLink(url);\n if (!state.md.validateLink(fullUrl)) return false;\n if (!silent) {\n state.pending = state.pending.slice(0, -proto.length);\n const token_o = state.push(\"link_open\", \"a\", 1);\n token_o.attrs = [[\"href\", fullUrl]];\n token_o.markup = \"linkify\";\n token_o.info = \"auto\";\n const token_t = state.push(\"text\", \"\", 0);\n token_t.content = state.md.normalizeLinkText(url);\n const token_c = state.push(\"link_close\", \"a\", -1);\n token_c.markup = \"linkify\";\n token_c.info = \"auto\";\n }\n state.pos += url.length - proto.length;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/newline.mjs\nfunction newline(state, silent) {\n let pos = state.pos;\n if (state.src.charCodeAt(pos) !== 10) {\n return false;\n }\n const pmax = state.pending.length - 1;\n const max2 = state.posMax;\n if (!silent) {\n if (pmax >= 0 && state.pending.charCodeAt(pmax) === 32) {\n if (pmax >= 1 && state.pending.charCodeAt(pmax - 1) === 32) {\n let ws = pmax - 1;\n while (ws >= 1 && state.pending.charCodeAt(ws - 1) === 32) ws--;\n state.pending = state.pending.slice(0, ws);\n state.push(\"hardbreak\", \"br\", 0);\n } else {\n state.pending = state.pending.slice(0, -1);\n state.push(\"softbreak\", \"br\", 0);\n }\n } else {\n state.push(\"softbreak\", \"br\", 0);\n }\n }\n pos++;\n while (pos < max2 && isSpace(state.src.charCodeAt(pos))) {\n pos++;\n }\n state.pos = pos;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/escape.mjs\nvar ESCAPED = [];\nfor (let i = 0; i < 256; i++) {\n ESCAPED.push(0);\n}\n\"\\\\!\\\"#$%&'()*+,./:;<=>?@[]^_`{|}~-\".split(\"\").forEach(function(ch) {\n ESCAPED[ch.charCodeAt(0)] = 1;\n});\nfunction escape2(state, silent) {\n let pos = state.pos;\n const max2 = state.posMax;\n if (state.src.charCodeAt(pos) !== 92) return false;\n pos++;\n if (pos >= max2) return false;\n let ch1 = state.src.charCodeAt(pos);\n if (ch1 === 10) {\n if (!silent) {\n state.push(\"hardbreak\", \"br\", 0);\n }\n pos++;\n while (pos < max2) {\n ch1 = state.src.charCodeAt(pos);\n if (!isSpace(ch1)) break;\n pos++;\n }\n state.pos = pos;\n return true;\n }\n let escapedStr = state.src[pos];\n if (ch1 >= 55296 && ch1 <= 56319 && pos + 1 < max2) {\n const ch2 = state.src.charCodeAt(pos + 1);\n if (ch2 >= 56320 && ch2 <= 57343) {\n escapedStr += state.src[pos + 1];\n pos++;\n }\n }\n const origStr = \"\\\\\" + escapedStr;\n if (!silent) {\n const token = state.push(\"text_special\", \"\", 0);\n if (ch1 < 256 && ESCAPED[ch1] !== 0) {\n token.content = escapedStr;\n } else {\n token.content = origStr;\n }\n token.markup = origStr;\n token.info = \"escape\";\n }\n state.pos = pos + 1;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/backticks.mjs\nfunction backtick(state, silent) {\n let pos = state.pos;\n const ch = state.src.charCodeAt(pos);\n if (ch !== 96) {\n return false;\n }\n const start = pos;\n pos++;\n const max2 = state.posMax;\n while (pos < max2 && state.src.charCodeAt(pos) === 96) {\n pos++;\n }\n const marker = state.src.slice(start, pos);\n const openerLength = marker.length;\n if (state.backticksScanned && (state.backticks[openerLength] || 0) <= start) {\n if (!silent) state.pending += marker;\n state.pos += openerLength;\n return true;\n }\n let matchEnd = pos;\n let matchStart;\n while ((matchStart = state.src.indexOf(\"`\", matchEnd)) !== -1) {\n matchEnd = matchStart + 1;\n while (matchEnd < max2 && state.src.charCodeAt(matchEnd) === 96) {\n matchEnd++;\n }\n const closerLength = matchEnd - matchStart;\n if (closerLength === openerLength) {\n if (!silent) {\n const token = state.push(\"code_inline\", \"code\", 0);\n token.markup = marker;\n token.content = state.src.slice(pos, matchStart).replace(/\\n/g, \" \").replace(/^ (.+) $/, \"$1\");\n }\n state.pos = matchEnd;\n return true;\n }\n state.backticks[closerLength] = matchStart;\n }\n state.backticksScanned = true;\n if (!silent) state.pending += marker;\n state.pos += openerLength;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/strikethrough.mjs\nfunction strikethrough_tokenize(state, silent) {\n const start = state.pos;\n const marker = state.src.charCodeAt(start);\n if (silent) {\n return false;\n }\n if (marker !== 126) {\n return false;\n }\n const scanned = state.scanDelims(state.pos, true);\n let len = scanned.length;\n const ch = String.fromCharCode(marker);\n if (len < 2) {\n return false;\n }\n let token;\n if (len % 2) {\n token = state.push(\"text\", \"\", 0);\n token.content = ch;\n len--;\n }\n for (let i = 0; i < len; i += 2) {\n token = state.push(\"text\", \"\", 0);\n token.content = ch + ch;\n state.delimiters.push({\n marker,\n length: 0,\n // disable \"rule of 3\" length checks meant for emphasis\n token: state.tokens.length - 1,\n end: -1,\n open: scanned.can_open,\n close: scanned.can_close\n });\n }\n state.pos += scanned.length;\n return true;\n}\nfunction postProcess(state, delimiters) {\n let token;\n const loneMarkers = [];\n const max2 = delimiters.length;\n for (let i = 0; i < max2; i++) {\n const startDelim = delimiters[i];\n if (startDelim.marker !== 126) {\n continue;\n }\n if (startDelim.end === -1) {\n continue;\n }\n const endDelim = delimiters[startDelim.end];\n token = state.tokens[startDelim.token];\n token.type = \"s_open\";\n token.tag = \"s\";\n token.nesting = 1;\n token.markup = \"~~\";\n token.content = \"\";\n token = state.tokens[endDelim.token];\n token.type = \"s_close\";\n token.tag = \"s\";\n token.nesting = -1;\n token.markup = \"~~\";\n token.content = \"\";\n if (state.tokens[endDelim.token - 1].type === \"text\" && state.tokens[endDelim.token - 1].content === \"~\") {\n loneMarkers.push(endDelim.token - 1);\n }\n }\n while (loneMarkers.length) {\n const i = loneMarkers.pop();\n let j = i + 1;\n while (j < state.tokens.length && state.tokens[j].type === \"s_close\") {\n j++;\n }\n j--;\n if (i !== j) {\n token = state.tokens[j];\n state.tokens[j] = state.tokens[i];\n state.tokens[i] = token;\n }\n }\n}\nfunction strikethrough_postProcess(state) {\n const tokens_meta = state.tokens_meta;\n const max2 = state.tokens_meta.length;\n postProcess(state, state.delimiters);\n for (let curr = 0; curr < max2; curr++) {\n if (tokens_meta[curr] && tokens_meta[curr].delimiters) {\n postProcess(state, tokens_meta[curr].delimiters);\n }\n }\n}\nvar strikethrough_default = {\n tokenize: strikethrough_tokenize,\n postProcess: strikethrough_postProcess\n};\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/emphasis.mjs\nfunction emphasis_tokenize(state, silent) {\n const start = state.pos;\n const marker = state.src.charCodeAt(start);\n if (silent) {\n return false;\n }\n if (marker !== 95 && marker !== 42) {\n return false;\n }\n const scanned = state.scanDelims(state.pos, marker === 42);\n for (let i = 0; i < scanned.length; i++) {\n const token = state.push(\"text\", \"\", 0);\n token.content = String.fromCharCode(marker);\n state.delimiters.push({\n // Char code of the starting marker (number).\n //\n marker,\n // Total length of these series of delimiters.\n //\n length: scanned.length,\n // A position of the token this delimiter corresponds to.\n //\n token: state.tokens.length - 1,\n // If this delimiter is matched as a valid opener, `end` will be\n // equal to its position, otherwise it's `-1`.\n //\n end: -1,\n // Boolean flags that determine if this delimiter could open or close\n // an emphasis.\n //\n open: scanned.can_open,\n close: scanned.can_close\n });\n }\n state.pos += scanned.length;\n return true;\n}\nfunction postProcess2(state, delimiters) {\n const max2 = delimiters.length;\n for (let i = max2 - 1; i >= 0; i--) {\n const startDelim = delimiters[i];\n if (startDelim.marker !== 95 && startDelim.marker !== 42) {\n continue;\n }\n if (startDelim.end === -1) {\n continue;\n }\n const endDelim = delimiters[startDelim.end];\n const isStrong = i > 0 && delimiters[i - 1].end === startDelim.end + 1 && // check that first two markers match and adjacent\n delimiters[i - 1].marker === startDelim.marker && delimiters[i - 1].token === startDelim.token - 1 && // check that last two markers are adjacent (we can safely assume they match)\n delimiters[startDelim.end + 1].token === endDelim.token + 1;\n const ch = String.fromCharCode(startDelim.marker);\n const token_o = state.tokens[startDelim.token];\n token_o.type = isStrong ? \"strong_open\" : \"em_open\";\n token_o.tag = isStrong ? \"strong\" : \"em\";\n token_o.nesting = 1;\n token_o.markup = isStrong ? ch + ch : ch;\n token_o.content = \"\";\n const token_c = state.tokens[endDelim.token];\n token_c.type = isStrong ? \"strong_close\" : \"em_close\";\n token_c.tag = isStrong ? \"strong\" : \"em\";\n token_c.nesting = -1;\n token_c.markup = isStrong ? ch + ch : ch;\n token_c.content = \"\";\n if (isStrong) {\n state.tokens[delimiters[i - 1].token].content = \"\";\n state.tokens[delimiters[startDelim.end + 1].token].content = \"\";\n i--;\n }\n }\n}\nfunction emphasis_post_process(state) {\n const tokens_meta = state.tokens_meta;\n const max2 = state.tokens_meta.length;\n postProcess2(state, state.delimiters);\n for (let curr = 0; curr < max2; curr++) {\n if (tokens_meta[curr] && tokens_meta[curr].delimiters) {\n postProcess2(state, tokens_meta[curr].delimiters);\n }\n }\n}\nvar emphasis_default = {\n tokenize: emphasis_tokenize,\n postProcess: emphasis_post_process\n};\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/link.mjs\nfunction link(state, silent) {\n let code2, label, res, ref;\n let href = \"\";\n let title = \"\";\n let start = state.pos;\n let parseReference = true;\n if (state.src.charCodeAt(state.pos) !== 91) {\n return false;\n }\n const oldPos = state.pos;\n const max2 = state.posMax;\n const labelStart = state.pos + 1;\n const labelEnd = state.md.helpers.parseLinkLabel(state, state.pos, true);\n if (labelEnd < 0) {\n return false;\n }\n let pos = labelEnd + 1;\n if (pos < max2 && state.src.charCodeAt(pos) === 40) {\n parseReference = false;\n pos++;\n for (; pos < max2; pos++) {\n code2 = state.src.charCodeAt(pos);\n if (!isSpace(code2) && code2 !== 10) {\n break;\n }\n }\n if (pos >= max2) {\n return false;\n }\n start = pos;\n res = state.md.helpers.parseLinkDestination(state.src, pos, state.posMax);\n if (res.ok) {\n href = state.md.normalizeLink(res.str);\n if (state.md.validateLink(href)) {\n pos = res.pos;\n } else {\n href = \"\";\n }\n start = pos;\n for (; pos < max2; pos++) {\n code2 = state.src.charCodeAt(pos);\n if (!isSpace(code2) && code2 !== 10) {\n break;\n }\n }\n res = state.md.helpers.parseLinkTitle(state.src, pos, state.posMax);\n if (pos < max2 && start !== pos && res.ok) {\n title = res.str;\n pos = res.pos;\n for (; pos < max2; pos++) {\n code2 = state.src.charCodeAt(pos);\n if (!isSpace(code2) && code2 !== 10) {\n break;\n }\n }\n }\n }\n if (pos >= max2 || state.src.charCodeAt(pos) !== 41) {\n parseReference = true;\n }\n pos++;\n }\n if (parseReference) {\n if (typeof state.env.references === \"undefined\") {\n return false;\n }\n if (pos < max2 && state.src.charCodeAt(pos) === 91) {\n start = pos + 1;\n pos = state.md.helpers.parseLinkLabel(state, pos);\n if (pos >= 0) {\n label = state.src.slice(start, pos++);\n } else {\n pos = labelEnd + 1;\n }\n } else {\n pos = labelEnd + 1;\n }\n if (!label) {\n label = state.src.slice(labelStart, labelEnd);\n }\n ref = state.env.references[normalizeReference(label)];\n if (!ref) {\n state.pos = oldPos;\n return false;\n }\n href = ref.href;\n title = ref.title;\n }\n if (!silent) {\n state.pos = labelStart;\n state.posMax = labelEnd;\n const token_o = state.push(\"link_open\", \"a\", 1);\n const attrs = [[\"href\", href]];\n token_o.attrs = attrs;\n if (title) {\n attrs.push([\"title\", title]);\n }\n state.linkLevel++;\n state.md.inline.tokenize(state);\n state.linkLevel--;\n state.push(\"link_close\", \"a\", -1);\n }\n state.pos = pos;\n state.posMax = max2;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/image.mjs\nfunction image(state, silent) {\n let code2, content, label, pos, ref, res, title, start;\n let href = \"\";\n const oldPos = state.pos;\n const max2 = state.posMax;\n if (state.src.charCodeAt(state.pos) !== 33) {\n return false;\n }\n if (state.src.charCodeAt(state.pos + 1) !== 91) {\n return false;\n }\n const labelStart = state.pos + 2;\n const labelEnd = state.md.helpers.parseLinkLabel(state, state.pos + 1, false);\n if (labelEnd < 0) {\n return false;\n }\n pos = labelEnd + 1;\n if (pos < max2 && state.src.charCodeAt(pos) === 40) {\n pos++;\n for (; pos < max2; pos++) {\n code2 = state.src.charCodeAt(pos);\n if (!isSpace(code2) && code2 !== 10) {\n break;\n }\n }\n if (pos >= max2) {\n return false;\n }\n start = pos;\n res = state.md.helpers.parseLinkDestination(state.src, pos, state.posMax);\n if (res.ok) {\n href = state.md.normalizeLink(res.str);\n if (state.md.validateLink(href)) {\n pos = res.pos;\n } else {\n href = \"\";\n }\n }\n start = pos;\n for (; pos < max2; pos++) {\n code2 = state.src.charCodeAt(pos);\n if (!isSpace(code2) && code2 !== 10) {\n break;\n }\n }\n res = state.md.helpers.parseLinkTitle(state.src, pos, state.posMax);\n if (pos < max2 && start !== pos && res.ok) {\n title = res.str;\n pos = res.pos;\n for (; pos < max2; pos++) {\n code2 = state.src.charCodeAt(pos);\n if (!isSpace(code2) && code2 !== 10) {\n break;\n }\n }\n } else {\n title = \"\";\n }\n if (pos >= max2 || state.src.charCodeAt(pos) !== 41) {\n state.pos = oldPos;\n return false;\n }\n pos++;\n } else {\n if (typeof state.env.references === \"undefined\") {\n return false;\n }\n if (pos < max2 && state.src.charCodeAt(pos) === 91) {\n start = pos + 1;\n pos = state.md.helpers.parseLinkLabel(state, pos);\n if (pos >= 0) {\n label = state.src.slice(start, pos++);\n } else {\n pos = labelEnd + 1;\n }\n } else {\n pos = labelEnd + 1;\n }\n if (!label) {\n label = state.src.slice(labelStart, labelEnd);\n }\n ref = state.env.references[normalizeReference(label)];\n if (!ref) {\n state.pos = oldPos;\n return false;\n }\n href = ref.href;\n title = ref.title;\n }\n if (!silent) {\n content = state.src.slice(labelStart, labelEnd);\n const tokens = [];\n state.md.inline.parse(\n content,\n state.md,\n state.env,\n tokens\n );\n const token = state.push(\"image\", \"img\", 0);\n const attrs = [[\"src\", href], [\"alt\", \"\"]];\n token.attrs = attrs;\n token.children = tokens;\n token.content = content;\n if (title) {\n attrs.push([\"title\", title]);\n }\n }\n state.pos = pos;\n state.posMax = max2;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/autolink.mjs\nvar EMAIL_RE = /^([a-zA-Z0-9.!#$%&'*+/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*)$/;\nvar AUTOLINK_RE = /^([a-zA-Z][a-zA-Z0-9+.-]{1,31}):([^<>\\x00-\\x20]*)$/;\nfunction autolink(state, silent) {\n let pos = state.pos;\n if (state.src.charCodeAt(pos) !== 60) {\n return false;\n }\n const start = state.pos;\n const max2 = state.posMax;\n for (; ; ) {\n if (++pos >= max2) return false;\n const ch = state.src.charCodeAt(pos);\n if (ch === 60) return false;\n if (ch === 62) break;\n }\n const url = state.src.slice(start + 1, pos);\n if (AUTOLINK_RE.test(url)) {\n const fullUrl = state.md.normalizeLink(url);\n if (!state.md.validateLink(fullUrl)) {\n return false;\n }\n if (!silent) {\n const token_o = state.push(\"link_open\", \"a\", 1);\n token_o.attrs = [[\"href\", fullUrl]];\n token_o.markup = \"autolink\";\n token_o.info = \"auto\";\n const token_t = state.push(\"text\", \"\", 0);\n token_t.content = state.md.normalizeLinkText(url);\n const token_c = state.push(\"link_close\", \"a\", -1);\n token_c.markup = \"autolink\";\n token_c.info = \"auto\";\n }\n state.pos += url.length + 2;\n return true;\n }\n if (EMAIL_RE.test(url)) {\n const fullUrl = state.md.normalizeLink(\"mailto:\" + url);\n if (!state.md.validateLink(fullUrl)) {\n return false;\n }\n if (!silent) {\n const token_o = state.push(\"link_open\", \"a\", 1);\n token_o.attrs = [[\"href\", fullUrl]];\n token_o.markup = \"autolink\";\n token_o.info = \"auto\";\n const token_t = state.push(\"text\", \"\", 0);\n token_t.content = state.md.normalizeLinkText(url);\n const token_c = state.push(\"link_close\", \"a\", -1);\n token_c.markup = \"autolink\";\n token_c.info = \"auto\";\n }\n state.pos += url.length + 2;\n return true;\n }\n return false;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/html_inline.mjs\nfunction isLinkOpen2(str) {\n return /^\\s]/i.test(str);\n}\nfunction isLinkClose2(str) {\n return /^<\\/a\\s*>/i.test(str);\n}\nfunction isLetter(ch) {\n const lc = ch | 32;\n return lc >= 97 && lc <= 122;\n}\nfunction html_inline(state, silent) {\n if (!state.md.options.html) {\n return false;\n }\n const max2 = state.posMax;\n const pos = state.pos;\n if (state.src.charCodeAt(pos) !== 60 || pos + 2 >= max2) {\n return false;\n }\n const ch = state.src.charCodeAt(pos + 1);\n if (ch !== 33 && ch !== 63 && ch !== 47 && !isLetter(ch)) {\n return false;\n }\n const match2 = state.src.slice(pos).match(HTML_TAG_RE);\n if (!match2) {\n return false;\n }\n if (!silent) {\n const token = state.push(\"html_inline\", \"\", 0);\n token.content = match2[0];\n if (isLinkOpen2(token.content)) state.linkLevel++;\n if (isLinkClose2(token.content)) state.linkLevel--;\n }\n state.pos += match2[0].length;\n return true;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/entity.mjs\nvar DIGITAL_RE = /^&#((?:x[a-f0-9]{1,6}|[0-9]{1,7}));/i;\nvar NAMED_RE = /^&([a-z][a-z0-9]{1,31});/i;\nfunction entity(state, silent) {\n const pos = state.pos;\n const max2 = state.posMax;\n if (state.src.charCodeAt(pos) !== 38) return false;\n if (pos + 1 >= max2) return false;\n const ch = state.src.charCodeAt(pos + 1);\n if (ch === 35) {\n const match2 = state.src.slice(pos).match(DIGITAL_RE);\n if (match2) {\n if (!silent) {\n const code2 = match2[1][0].toLowerCase() === \"x\" ? parseInt(match2[1].slice(1), 16) : parseInt(match2[1], 10);\n const token = state.push(\"text_special\", \"\", 0);\n token.content = isValidEntityCode(code2) ? fromCodePoint2(code2) : fromCodePoint2(65533);\n token.markup = match2[0];\n token.info = \"entity\";\n }\n state.pos += match2[0].length;\n return true;\n }\n } else {\n const match2 = state.src.slice(pos).match(NAMED_RE);\n if (match2) {\n const decoded = decodeHTML(match2[0]);\n if (decoded !== match2[0]) {\n if (!silent) {\n const token = state.push(\"text_special\", \"\", 0);\n token.content = decoded;\n token.markup = match2[0];\n token.info = \"entity\";\n }\n state.pos += match2[0].length;\n return true;\n }\n }\n }\n return false;\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/balance_pairs.mjs\nfunction processDelimiters(delimiters) {\n const openersBottom = {};\n const max2 = delimiters.length;\n if (!max2) return;\n let headerIdx = 0;\n let lastTokenIdx = -2;\n const jumps = [];\n for (let closerIdx = 0; closerIdx < max2; closerIdx++) {\n const closer = delimiters[closerIdx];\n jumps.push(0);\n if (delimiters[headerIdx].marker !== closer.marker || lastTokenIdx !== closer.token - 1) {\n headerIdx = closerIdx;\n }\n lastTokenIdx = closer.token;\n closer.length = closer.length || 0;\n if (!closer.close) continue;\n if (!openersBottom.hasOwnProperty(closer.marker)) {\n openersBottom[closer.marker] = [-1, -1, -1, -1, -1, -1];\n }\n const minOpenerIdx = openersBottom[closer.marker][(closer.open ? 3 : 0) + closer.length % 3];\n let openerIdx = headerIdx - jumps[headerIdx] - 1;\n let newMinOpenerIdx = openerIdx;\n for (; openerIdx > minOpenerIdx; openerIdx -= jumps[openerIdx] + 1) {\n const opener = delimiters[openerIdx];\n if (opener.marker !== closer.marker) continue;\n if (opener.open && opener.end < 0) {\n let isOddMatch = false;\n if (opener.close || closer.open) {\n if ((opener.length + closer.length) % 3 === 0) {\n if (opener.length % 3 !== 0 || closer.length % 3 !== 0) {\n isOddMatch = true;\n }\n }\n }\n if (!isOddMatch) {\n const lastJump = openerIdx > 0 && !delimiters[openerIdx - 1].open ? jumps[openerIdx - 1] + 1 : 0;\n jumps[closerIdx] = closerIdx - openerIdx + lastJump;\n jumps[openerIdx] = lastJump;\n closer.open = false;\n opener.end = closerIdx;\n opener.close = false;\n newMinOpenerIdx = -1;\n lastTokenIdx = -2;\n break;\n }\n }\n }\n if (newMinOpenerIdx !== -1) {\n openersBottom[closer.marker][(closer.open ? 3 : 0) + (closer.length || 0) % 3] = newMinOpenerIdx;\n }\n }\n}\nfunction link_pairs(state) {\n const tokens_meta = state.tokens_meta;\n const max2 = state.tokens_meta.length;\n processDelimiters(state.delimiters);\n for (let curr = 0; curr < max2; curr++) {\n if (tokens_meta[curr] && tokens_meta[curr].delimiters) {\n processDelimiters(tokens_meta[curr].delimiters);\n }\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/fragments_join.mjs\nfunction fragments_join(state) {\n let curr, last;\n let level = 0;\n const tokens = state.tokens;\n const max2 = state.tokens.length;\n for (curr = last = 0; curr < max2; curr++) {\n if (tokens[curr].nesting < 0) level--;\n tokens[curr].level = level;\n if (tokens[curr].nesting > 0) level++;\n if (tokens[curr].type === \"text\" && curr + 1 < max2 && tokens[curr + 1].type === \"text\") {\n tokens[curr + 1].content = tokens[curr].content + tokens[curr + 1].content;\n } else {\n if (curr !== last) {\n tokens[last] = tokens[curr];\n }\n last++;\n }\n }\n if (curr !== last) {\n tokens.length = last;\n }\n}\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/parser_inline.mjs\nvar _rules3 = [\n [\"text\", text],\n [\"linkify\", linkify2],\n [\"newline\", newline],\n [\"escape\", escape2],\n [\"backticks\", backtick],\n [\"strikethrough\", strikethrough_default.tokenize],\n [\"emphasis\", emphasis_default.tokenize],\n [\"link\", link],\n [\"image\", image],\n [\"autolink\", autolink],\n [\"html_inline\", html_inline],\n [\"entity\", entity]\n];\nvar _rules22 = [\n [\"balance_pairs\", link_pairs],\n [\"strikethrough\", strikethrough_default.postProcess],\n [\"emphasis\", emphasis_default.postProcess],\n // rules for pairs separate '**' into its own text tokens, which may be left unused,\n // rule below merges unused segments back with the rest of the text\n [\"fragments_join\", fragments_join]\n];\nfunction ParserInline() {\n this.ruler = new ruler_default();\n for (let i = 0; i < _rules3.length; i++) {\n this.ruler.push(_rules3[i][0], _rules3[i][1]);\n }\n this.ruler2 = new ruler_default();\n for (let i = 0; i < _rules22.length; i++) {\n this.ruler2.push(_rules22[i][0], _rules22[i][1]);\n }\n}\nParserInline.prototype.skipToken = function(state) {\n const pos = state.pos;\n const rules = this.ruler.getRules(\"\");\n const len = rules.length;\n const maxNesting = state.md.options.maxNesting;\n const cache = state.cache;\n if (typeof cache[pos] !== \"undefined\") {\n state.pos = cache[pos];\n return;\n }\n let ok = false;\n if (state.level < maxNesting) {\n for (let i = 0; i < len; i++) {\n state.level++;\n ok = rules[i](state, true);\n state.level--;\n if (ok) {\n if (pos >= state.pos) {\n throw new Error(\"inline rule didn't increment state.pos\");\n }\n break;\n }\n }\n } else {\n state.pos = state.posMax;\n }\n if (!ok) {\n state.pos++;\n }\n cache[pos] = state.pos;\n};\nParserInline.prototype.tokenize = function(state) {\n const rules = this.ruler.getRules(\"\");\n const len = rules.length;\n const end = state.posMax;\n const maxNesting = state.md.options.maxNesting;\n while (state.pos < end) {\n const prevPos = state.pos;\n let ok = false;\n if (state.level < maxNesting) {\n for (let i = 0; i < len; i++) {\n ok = rules[i](state, false);\n if (ok) {\n if (prevPos >= state.pos) {\n throw new Error(\"inline rule didn't increment state.pos\");\n }\n break;\n }\n }\n }\n if (ok) {\n if (state.pos >= end) {\n break;\n }\n continue;\n }\n state.pending += state.src[state.pos++];\n }\n if (state.pending) {\n state.pushPending();\n }\n};\nParserInline.prototype.parse = function(str, md, env, outTokens) {\n const state = new this.State(str, md, env, outTokens);\n this.tokenize(state);\n const rules = this.ruler2.getRules(\"\");\n const len = rules.length;\n for (let i = 0; i < len; i++) {\n rules[i](state);\n }\n};\nParserInline.prototype.State = state_inline_default;\nvar parser_inline_default = ParserInline;\n\n// node_modules/.pnpm/punycode.js@2.3.1/node_modules/punycode.js/punycode.es6.js\nvar maxInt = 2147483647;\nvar base = 36;\nvar tMin = 1;\nvar tMax = 26;\nvar skew = 38;\nvar damp = 700;\nvar initialBias = 72;\nvar initialN = 128;\nvar delimiter = \"-\";\nvar regexPunycode = /^xn--/;\nvar regexNonASCII = /[^\\0-\\x7F]/;\nvar regexSeparators = /[\\x2E\\u3002\\uFF0E\\uFF61]/g;\nvar errors = {\n \"overflow\": \"Overflow: input needs wider integers to process\",\n \"not-basic\": \"Illegal input >= 0x80 (not a basic code point)\",\n \"invalid-input\": \"Invalid input\"\n};\nvar baseMinusTMin = base - tMin;\nvar floor = Math.floor;\nvar stringFromCharCode = String.fromCharCode;\nfunction error(type) {\n throw new RangeError(errors[type]);\n}\nfunction map(array, callback) {\n const result = [];\n let length = array.length;\n while (length--) {\n result[length] = callback(array[length]);\n }\n return result;\n}\nfunction mapDomain(domain, callback) {\n const parts = domain.split(\"@\");\n let result = \"\";\n if (parts.length > 1) {\n result = parts[0] + \"@\";\n domain = parts[1];\n }\n domain = domain.replace(regexSeparators, \".\");\n const labels = domain.split(\".\");\n const encoded = map(labels, callback).join(\".\");\n return result + encoded;\n}\nfunction ucs2decode(string) {\n const output = [];\n let counter = 0;\n const length = string.length;\n while (counter < length) {\n const value = string.charCodeAt(counter++);\n if (value >= 55296 && value <= 56319 && counter < length) {\n const extra = string.charCodeAt(counter++);\n if ((extra & 64512) == 56320) {\n output.push(((value & 1023) << 10) + (extra & 1023) + 65536);\n } else {\n output.push(value);\n counter--;\n }\n } else {\n output.push(value);\n }\n }\n return output;\n}\nvar ucs2encode = (codePoints) => String.fromCodePoint(...codePoints);\nvar basicToDigit = function(codePoint) {\n if (codePoint >= 48 && codePoint < 58) {\n return 26 + (codePoint - 48);\n }\n if (codePoint >= 65 && codePoint < 91) {\n return codePoint - 65;\n }\n if (codePoint >= 97 && codePoint < 123) {\n return codePoint - 97;\n }\n return base;\n};\nvar digitToBasic = function(digit, flag) {\n return digit + 22 + 75 * (digit < 26) - ((flag != 0) << 5);\n};\nvar adapt = function(delta, numPoints, firstTime) {\n let k = 0;\n delta = firstTime ? floor(delta / damp) : delta >> 1;\n delta += floor(delta / numPoints);\n for (; delta > baseMinusTMin * tMax >> 1; k += base) {\n delta = floor(delta / baseMinusTMin);\n }\n return floor(k + (baseMinusTMin + 1) * delta / (delta + skew));\n};\nvar decode2 = function(input) {\n const output = [];\n const inputLength = input.length;\n let i = 0;\n let n = initialN;\n let bias = initialBias;\n let basic = input.lastIndexOf(delimiter);\n if (basic < 0) {\n basic = 0;\n }\n for (let j = 0; j < basic; ++j) {\n if (input.charCodeAt(j) >= 128) {\n error(\"not-basic\");\n }\n output.push(input.charCodeAt(j));\n }\n for (let index = basic > 0 ? basic + 1 : 0; index < inputLength; ) {\n const oldi = i;\n for (let w = 1, k = base; ; k += base) {\n if (index >= inputLength) {\n error(\"invalid-input\");\n }\n const digit = basicToDigit(input.charCodeAt(index++));\n if (digit >= base) {\n error(\"invalid-input\");\n }\n if (digit > floor((maxInt - i) / w)) {\n error(\"overflow\");\n }\n i += digit * w;\n const t = k <= bias ? tMin : k >= bias + tMax ? tMax : k - bias;\n if (digit < t) {\n break;\n }\n const baseMinusT = base - t;\n if (w > floor(maxInt / baseMinusT)) {\n error(\"overflow\");\n }\n w *= baseMinusT;\n }\n const out = output.length + 1;\n bias = adapt(i - oldi, out, oldi == 0);\n if (floor(i / out) > maxInt - n) {\n error(\"overflow\");\n }\n n += floor(i / out);\n i %= out;\n output.splice(i++, 0, n);\n }\n return String.fromCodePoint(...output);\n};\nvar encode2 = function(input) {\n const output = [];\n input = ucs2decode(input);\n const inputLength = input.length;\n let n = initialN;\n let delta = 0;\n let bias = initialBias;\n for (const currentValue of input) {\n if (currentValue < 128) {\n output.push(stringFromCharCode(currentValue));\n }\n }\n const basicLength = output.length;\n let handledCPCount = basicLength;\n if (basicLength) {\n output.push(delimiter);\n }\n while (handledCPCount < inputLength) {\n let m = maxInt;\n for (const currentValue of input) {\n if (currentValue >= n && currentValue < m) {\n m = currentValue;\n }\n }\n const handledCPCountPlusOne = handledCPCount + 1;\n if (m - n > floor((maxInt - delta) / handledCPCountPlusOne)) {\n error(\"overflow\");\n }\n delta += (m - n) * handledCPCountPlusOne;\n n = m;\n for (const currentValue of input) {\n if (currentValue < n && ++delta > maxInt) {\n error(\"overflow\");\n }\n if (currentValue === n) {\n let q = delta;\n for (let k = base; ; k += base) {\n const t = k <= bias ? tMin : k >= bias + tMax ? tMax : k - bias;\n if (q < t) {\n break;\n }\n const qMinusT = q - t;\n const baseMinusT = base - t;\n output.push(\n stringFromCharCode(digitToBasic(t + qMinusT % baseMinusT, 0))\n );\n q = floor(qMinusT / baseMinusT);\n }\n output.push(stringFromCharCode(digitToBasic(q, 0)));\n bias = adapt(delta, handledCPCountPlusOne, handledCPCount === basicLength);\n delta = 0;\n ++handledCPCount;\n }\n }\n ++delta;\n ++n;\n }\n return output.join(\"\");\n};\nvar toUnicode = function(input) {\n return mapDomain(input, function(string) {\n return regexPunycode.test(string) ? decode2(string.slice(4).toLowerCase()) : string;\n });\n};\nvar toASCII = function(input) {\n return mapDomain(input, function(string) {\n return regexNonASCII.test(string) ? \"xn--\" + encode2(string) : string;\n });\n};\nvar punycode = {\n /**\n * A string representing the current Punycode.js version number.\n * @memberOf punycode\n * @type String\n */\n \"version\": \"2.3.1\",\n /**\n * An object of methods to convert from JavaScript's internal character\n * representation (UCS-2) to Unicode code points, and back.\n * @see \n * @memberOf punycode\n * @type Object\n */\n \"ucs2\": {\n \"decode\": ucs2decode,\n \"encode\": ucs2encode\n },\n \"decode\": decode2,\n \"encode\": encode2,\n \"toASCII\": toASCII,\n \"toUnicode\": toUnicode\n};\nvar punycode_es6_default = punycode;\n\n// node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/presets/default.mjs\nvar default_default = {\n options: {\n // Enable HTML tags in source\n html: false,\n // Use '/' to close single tags (
)\n xhtmlOut: false,\n // Convert '\\n' in paragraphs into
\n breaks: false,\n // CSS language prefix for fenced blocks\n langPrefix: \"language-\",\n // autoconvert URL-like texts to links\n linkify: false,\n // Enable some language-neutral replacements + quotes beautification\n typographer: false,\n // Double + single quotes replacement pairs, when typographer enabled,\n // and smartquotes on. Could be either a String or an Array.\n //\n // For example, you can use '«»„“' for Russian, '„“‚‘' for German,\n // and ['«\\xA0', '\\xA0»', '‹\\xA0', '\\xA0›'] for French (including nbsp).\n quotes: \"“”‘’\",\n /* “”‘’ */\n // Highlighter function. Should return escaped HTML,\n // or '' if the source string is not changed and should be escaped externaly.\n // If result starts with )\n xhtmlOut: false,\n // Convert '\\n' in paragraphs into
\n breaks: false,\n // CSS language prefix for fenced blocks\n langPrefix: \"language-\",\n // autoconvert URL-like texts to links\n linkify: false,\n // Enable some language-neutral replacements + quotes beautification\n typographer: false,\n // Double + single quotes replacement pairs, when typographer enabled,\n // and smartquotes on. Could be either a String or an Array.\n //\n // For example, you can use '«»„“' for Russian, '„“‚‘' for German,\n // and ['«\\xA0', '\\xA0»', '‹\\xA0', '\\xA0›'] for French (including nbsp).\n quotes: \"“”‘’\",\n /* “”‘’ */\n // Highlighter function. Should return escaped HTML,\n // or '' if the source string is not changed and should be escaped externaly.\n // If result starts with )\n xhtmlOut: true,\n // Convert '\\n' in paragraphs into
\n breaks: false,\n // CSS language prefix for fenced blocks\n langPrefix: \"language-\",\n // autoconvert URL-like texts to links\n linkify: false,\n // Enable some language-neutral replacements + quotes beautification\n typographer: false,\n // Double + single quotes replacement pairs, when typographer enabled,\n // and smartquotes on. Could be either a String or an Array.\n //\n // For example, you can use '«»„“' for Russian, '„“‚‘' for German,\n // and ['«\\xA0', '\\xA0»', '‹\\xA0', '\\xA0›'] for French (including nbsp).\n quotes: \"“”‘’\",\n /* “”‘’ */\n // Highlighter function. Should return escaped HTML,\n // or '' if the source string is not changed and should be escaped externaly.\n // If result starts with = 0) {\n try {\n parsed.hostname = punycode_es6_default.toASCII(parsed.hostname);\n } catch (er) {\n }\n }\n }\n return encode_default(format(parsed));\n}\nfunction normalizeLinkText(url) {\n const parsed = parse_default(url, true);\n if (parsed.hostname) {\n if (!parsed.protocol || RECODE_HOSTNAME_FOR.indexOf(parsed.protocol) >= 0) {\n try {\n parsed.hostname = punycode_es6_default.toUnicode(parsed.hostname);\n } catch (er) {\n }\n }\n }\n return decode_default(format(parsed), decode_default.defaultChars + \"%\");\n}\nfunction MarkdownIt(presetName, options) {\n if (!(this instanceof MarkdownIt)) {\n return new MarkdownIt(presetName, options);\n }\n if (!options) {\n if (!isString2(presetName)) {\n options = presetName || {};\n presetName = \"default\";\n }\n }\n this.inline = new parser_inline_default();\n this.block = new parser_block_default();\n this.core = new parser_core_default();\n this.renderer = new renderer_default();\n this.linkify = new linkify_it_default();\n this.validateLink = validateLink;\n this.normalizeLink = normalizeLink;\n this.normalizeLinkText = normalizeLinkText;\n this.utils = utils_exports;\n this.helpers = assign2({}, helpers_exports);\n this.options = {};\n this.configure(presetName);\n if (options) {\n this.set(options);\n }\n}\nMarkdownIt.prototype.set = function(options) {\n assign2(this.options, options);\n return this;\n};\nMarkdownIt.prototype.configure = function(presets) {\n const self = this;\n if (isString2(presets)) {\n const presetName = presets;\n presets = config[presetName];\n if (!presets) {\n throw new Error('Wrong `markdown-it` preset \"' + presetName + '\", check name');\n }\n }\n if (!presets) {\n throw new Error(\"Wrong `markdown-it` preset, can't be empty\");\n }\n if (presets.options) {\n self.set(presets.options);\n }\n if (presets.components) {\n Object.keys(presets.components).forEach(function(name) {\n if (presets.components[name].rules) {\n self[name].ruler.enableOnly(presets.components[name].rules);\n }\n if (presets.components[name].rules2) {\n self[name].ruler2.enableOnly(presets.components[name].rules2);\n }\n });\n }\n return this;\n};\nMarkdownIt.prototype.enable = function(list2, ignoreInvalid) {\n let result = [];\n if (!Array.isArray(list2)) {\n list2 = [list2];\n }\n [\"core\", \"block\", \"inline\"].forEach(function(chain) {\n result = result.concat(this[chain].ruler.enable(list2, true));\n }, this);\n result = result.concat(this.inline.ruler2.enable(list2, true));\n const missed = list2.filter(function(name) {\n return result.indexOf(name) < 0;\n });\n if (missed.length && !ignoreInvalid) {\n throw new Error(\"MarkdownIt. Failed to enable unknown rule(s): \" + missed);\n }\n return this;\n};\nMarkdownIt.prototype.disable = function(list2, ignoreInvalid) {\n let result = [];\n if (!Array.isArray(list2)) {\n list2 = [list2];\n }\n [\"core\", \"block\", \"inline\"].forEach(function(chain) {\n result = result.concat(this[chain].ruler.disable(list2, true));\n }, this);\n result = result.concat(this.inline.ruler2.disable(list2, true));\n const missed = list2.filter(function(name) {\n return result.indexOf(name) < 0;\n });\n if (missed.length && !ignoreInvalid) {\n throw new Error(\"MarkdownIt. Failed to disable unknown rule(s): \" + missed);\n }\n return this;\n};\nMarkdownIt.prototype.use = function(plugin) {\n const args = [this].concat(Array.prototype.slice.call(arguments, 1));\n plugin.apply(plugin, args);\n return this;\n};\nMarkdownIt.prototype.parse = function(src, env) {\n if (typeof src !== \"string\") {\n throw new Error(\"Input data should be a String\");\n }\n const state = new this.core.State(src, this, env);\n this.core.process(state);\n return state.tokens;\n};\nMarkdownIt.prototype.render = function(src, env) {\n env = env || {};\n return this.renderer.render(this.parse(src, env), this.options, env);\n};\nMarkdownIt.prototype.parseInline = function(src, env) {\n const state = new this.core.State(src, this, env);\n state.inlineMode = true;\n this.core.process(state);\n return state.tokens;\n};\nMarkdownIt.prototype.renderInline = function(src, env) {\n env = env || {};\n return this.renderer.render(this.parseInline(src, env), this.options, env);\n};\nvar lib_default = MarkdownIt;\n\n// node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/utils.js\nfunction isBytes(a) {\n return a instanceof Uint8Array || ArrayBuffer.isView(a) && a.constructor.name === \"Uint8Array\";\n}\nfunction abytes(b, ...lengths) {\n if (!isBytes(b))\n throw new Error(\"Uint8Array expected\");\n if (lengths.length > 0 && !lengths.includes(b.length))\n throw new Error(\"Uint8Array expected of length \" + lengths + \", got length=\" + b.length);\n}\nfunction aexists(instance, checkFinished = true) {\n if (instance.destroyed)\n throw new Error(\"Hash instance has been destroyed\");\n if (checkFinished && instance.finished)\n throw new Error(\"Hash#digest() has already been called\");\n}\nfunction aoutput(out, instance) {\n abytes(out);\n const min = instance.outputLen;\n if (out.length < min) {\n throw new Error(\"digestInto() expects output buffer of length at least \" + min);\n }\n}\nfunction clean(...arrays) {\n for (let i = 0; i < arrays.length; i++) {\n arrays[i].fill(0);\n }\n}\nfunction createView(arr) {\n return new DataView(arr.buffer, arr.byteOffset, arr.byteLength);\n}\nfunction rotr(word, shift) {\n return word << 32 - shift | word >>> shift;\n}\nvar hasHexBuiltin = /* @__PURE__ */ (() => (\n // @ts-ignore\n typeof Uint8Array.from([]).toHex === \"function\" && typeof Uint8Array.fromHex === \"function\"\n))();\nvar hexes = /* @__PURE__ */ Array.from({ length: 256 }, (_, i) => i.toString(16).padStart(2, \"0\"));\nfunction bytesToHex(bytes) {\n abytes(bytes);\n if (hasHexBuiltin)\n return bytes.toHex();\n let hex = \"\";\n for (let i = 0; i < bytes.length; i++) {\n hex += hexes[bytes[i]];\n }\n return hex;\n}\nfunction utf8ToBytes(str) {\n if (typeof str !== \"string\")\n throw new Error(\"string expected\");\n return new Uint8Array(new TextEncoder().encode(str));\n}\nfunction toBytes(data) {\n if (typeof data === \"string\")\n data = utf8ToBytes(data);\n abytes(data);\n return data;\n}\nvar Hash = class {\n};\nfunction createHasher(hashCons) {\n const hashC = (msg) => hashCons().update(toBytes(msg)).digest();\n const tmp = hashCons();\n hashC.outputLen = tmp.outputLen;\n hashC.blockLen = tmp.blockLen;\n hashC.create = () => hashCons();\n return hashC;\n}\n\n// node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/_md.js\nfunction setBigUint64(view, byteOffset, value, isLE) {\n if (typeof view.setBigUint64 === \"function\")\n return view.setBigUint64(byteOffset, value, isLE);\n const _32n = BigInt(32);\n const _u32_max = BigInt(4294967295);\n const wh = Number(value >> _32n & _u32_max);\n const wl = Number(value & _u32_max);\n const h = isLE ? 4 : 0;\n const l = isLE ? 0 : 4;\n view.setUint32(byteOffset + h, wh, isLE);\n view.setUint32(byteOffset + l, wl, isLE);\n}\nfunction Chi(a, b, c) {\n return a & b ^ ~a & c;\n}\nfunction Maj(a, b, c) {\n return a & b ^ a & c ^ b & c;\n}\nvar HashMD = class extends Hash {\n constructor(blockLen, outputLen, padOffset, isLE) {\n super();\n this.finished = false;\n this.length = 0;\n this.pos = 0;\n this.destroyed = false;\n this.blockLen = blockLen;\n this.outputLen = outputLen;\n this.padOffset = padOffset;\n this.isLE = isLE;\n this.buffer = new Uint8Array(blockLen);\n this.view = createView(this.buffer);\n }\n update(data) {\n aexists(this);\n data = toBytes(data);\n abytes(data);\n const { view, buffer, blockLen } = this;\n const len = data.length;\n for (let pos = 0; pos < len; ) {\n const take = Math.min(blockLen - this.pos, len - pos);\n if (take === blockLen) {\n const dataView = createView(data);\n for (; blockLen <= len - pos; pos += blockLen)\n this.process(dataView, pos);\n continue;\n }\n buffer.set(data.subarray(pos, pos + take), this.pos);\n this.pos += take;\n pos += take;\n if (this.pos === blockLen) {\n this.process(view, 0);\n this.pos = 0;\n }\n }\n this.length += data.length;\n this.roundClean();\n return this;\n }\n digestInto(out) {\n aexists(this);\n aoutput(out, this);\n this.finished = true;\n const { buffer, view, blockLen, isLE } = this;\n let { pos } = this;\n buffer[pos++] = 128;\n clean(this.buffer.subarray(pos));\n if (this.padOffset > blockLen - pos) {\n this.process(view, 0);\n pos = 0;\n }\n for (let i = pos; i < blockLen; i++)\n buffer[i] = 0;\n setBigUint64(view, blockLen - 8, BigInt(this.length * 8), isLE);\n this.process(view, 0);\n const oview = createView(out);\n const len = this.outputLen;\n if (len % 4)\n throw new Error(\"_sha2: outputLen should be aligned to 32bit\");\n const outLen = len / 4;\n const state = this.get();\n if (outLen > state.length)\n throw new Error(\"_sha2: outputLen bigger than state\");\n for (let i = 0; i < outLen; i++)\n oview.setUint32(4 * i, state[i], isLE);\n }\n digest() {\n const { buffer, outputLen } = this;\n this.digestInto(buffer);\n const res = buffer.slice(0, outputLen);\n this.destroy();\n return res;\n }\n _cloneInto(to) {\n to || (to = new this.constructor());\n to.set(...this.get());\n const { blockLen, buffer, length, finished, destroyed, pos } = this;\n to.destroyed = destroyed;\n to.finished = finished;\n to.length = length;\n to.pos = pos;\n if (length % blockLen)\n to.buffer.set(buffer);\n return to;\n }\n clone() {\n return this._cloneInto();\n }\n};\nvar SHA256_IV = /* @__PURE__ */ Uint32Array.from([\n 1779033703,\n 3144134277,\n 1013904242,\n 2773480762,\n 1359893119,\n 2600822924,\n 528734635,\n 1541459225\n]);\n\n// node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/sha2.js\nvar SHA256_K = /* @__PURE__ */ Uint32Array.from([\n 1116352408,\n 1899447441,\n 3049323471,\n 3921009573,\n 961987163,\n 1508970993,\n 2453635748,\n 2870763221,\n 3624381080,\n 310598401,\n 607225278,\n 1426881987,\n 1925078388,\n 2162078206,\n 2614888103,\n 3248222580,\n 3835390401,\n 4022224774,\n 264347078,\n 604807628,\n 770255983,\n 1249150122,\n 1555081692,\n 1996064986,\n 2554220882,\n 2821834349,\n 2952996808,\n 3210313671,\n 3336571891,\n 3584528711,\n 113926993,\n 338241895,\n 666307205,\n 773529912,\n 1294757372,\n 1396182291,\n 1695183700,\n 1986661051,\n 2177026350,\n 2456956037,\n 2730485921,\n 2820302411,\n 3259730800,\n 3345764771,\n 3516065817,\n 3600352804,\n 4094571909,\n 275423344,\n 430227734,\n 506948616,\n 659060556,\n 883997877,\n 958139571,\n 1322822218,\n 1537002063,\n 1747873779,\n 1955562222,\n 2024104815,\n 2227730452,\n 2361852424,\n 2428436474,\n 2756734187,\n 3204031479,\n 3329325298\n]);\nvar SHA256_W = /* @__PURE__ */ new Uint32Array(64);\nvar SHA256 = class extends HashMD {\n constructor(outputLen = 32) {\n super(64, outputLen, 8, false);\n this.A = SHA256_IV[0] | 0;\n this.B = SHA256_IV[1] | 0;\n this.C = SHA256_IV[2] | 0;\n this.D = SHA256_IV[3] | 0;\n this.E = SHA256_IV[4] | 0;\n this.F = SHA256_IV[5] | 0;\n this.G = SHA256_IV[6] | 0;\n this.H = SHA256_IV[7] | 0;\n }\n get() {\n const { A, B, C, D, E, F, G, H } = this;\n return [A, B, C, D, E, F, G, H];\n }\n // prettier-ignore\n set(A, B, C, D, E, F, G, H) {\n this.A = A | 0;\n this.B = B | 0;\n this.C = C | 0;\n this.D = D | 0;\n this.E = E | 0;\n this.F = F | 0;\n this.G = G | 0;\n this.H = H | 0;\n }\n process(view, offset) {\n for (let i = 0; i < 16; i++, offset += 4)\n SHA256_W[i] = view.getUint32(offset, false);\n for (let i = 16; i < 64; i++) {\n const W15 = SHA256_W[i - 15];\n const W2 = SHA256_W[i - 2];\n const s0 = rotr(W15, 7) ^ rotr(W15, 18) ^ W15 >>> 3;\n const s1 = rotr(W2, 17) ^ rotr(W2, 19) ^ W2 >>> 10;\n SHA256_W[i] = s1 + SHA256_W[i - 7] + s0 + SHA256_W[i - 16] | 0;\n }\n let { A, B, C, D, E, F, G, H } = this;\n for (let i = 0; i < 64; i++) {\n const sigma1 = rotr(E, 6) ^ rotr(E, 11) ^ rotr(E, 25);\n const T1 = H + sigma1 + Chi(E, F, G) + SHA256_K[i] + SHA256_W[i] | 0;\n const sigma0 = rotr(A, 2) ^ rotr(A, 13) ^ rotr(A, 22);\n const T2 = sigma0 + Maj(A, B, C) | 0;\n H = G;\n G = F;\n F = E;\n E = D + T1 | 0;\n D = C;\n C = B;\n B = A;\n A = T1 + T2 | 0;\n }\n A = A + this.A | 0;\n B = B + this.B | 0;\n C = C + this.C | 0;\n D = D + this.D | 0;\n E = E + this.E | 0;\n F = F + this.F | 0;\n G = G + this.G | 0;\n H = H + this.H | 0;\n this.set(A, B, C, D, E, F, G, H);\n }\n roundClean() {\n clean(SHA256_W);\n }\n destroy() {\n this.set(0, 0, 0, 0, 0, 0, 0, 0);\n clean(this.buffer);\n }\n};\nvar sha256 = /* @__PURE__ */ createHasher(() => new SHA256());\n\n// node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/sha256.js\nvar sha2562 = sha256;\n\n// apps/ecosystem-certifier/fixtures/flagship/knowledge-pack-entry.ts\nvar import_path_to_regexp = __toESM(require_dist(), 1);\nvar import_semver = __toESM(require_semver2(), 1);\n\n// node_modules/.pnpm/tinyqueue@3.0.0/node_modules/tinyqueue/index.js\nvar TinyQueue = class {\n constructor(data = [], compare = (a, b) => a < b ? -1 : a > b ? 1 : 0) {\n this.data = data;\n this.length = this.data.length;\n this.compare = compare;\n if (this.length > 0) {\n for (let i = (this.length >> 1) - 1; i >= 0; i--) this._down(i);\n }\n }\n push(item) {\n this.data.push(item);\n this._up(this.length++);\n }\n pop() {\n if (this.length === 0) return void 0;\n const top = this.data[0];\n const bottom = this.data.pop();\n if (--this.length > 0) {\n this.data[0] = bottom;\n this._down(0);\n }\n return top;\n }\n peek() {\n return this.data[0];\n }\n _up(pos) {\n const { data, compare } = this;\n const item = data[pos];\n while (pos > 0) {\n const parent = pos - 1 >> 1;\n const current = data[parent];\n if (compare(item, current) >= 0) break;\n data[pos] = current;\n pos = parent;\n }\n data[pos] = item;\n }\n _down(pos) {\n const { data, compare } = this;\n const halfLength = this.length >> 1;\n const item = data[pos];\n while (pos < halfLength) {\n let bestChild = (pos << 1) + 1;\n const right = bestChild + 1;\n if (right < this.length && compare(data[right], data[bestChild]) < 0) {\n bestChild = right;\n }\n if (compare(data[bestChild], item) >= 0) break;\n data[pos] = data[bestChild];\n pos = bestChild;\n }\n data[pos] = item;\n }\n};\n\n// apps/ecosystem-certifier/fixtures/flagship/knowledge-pack-entry.ts\nvar import_crc_32 = __toESM(require_crc32(), 1);\nvar summary;\ntry {\n const metadataText = Host.v2.document.get(\"pack/metadata.json\");\n const ruleText = Host.v2.document.get(\"rules/findings.json\");\n const compressedAttachment = Host.v2.document.get(\"pack/attachment.deflated\");\n const payload = Host.v2.document.get(\"bytes/payload\");\n const extraPayload = Host.v2.document.get(\"bytes/flagship-extra\");\n const metadata = JSON.parse(metadataText);\n const docPaths = metadata.links ?? [\"docs/a.md\", \"docs/b.md\"];\n const docs = docPaths.map((docPath) => ({\n docPath,\n text: Host.v2.document.get(docPath)\n }));\n const markdown = new lib_default({ linkify: true });\n const linkify3 = new linkify_it_default();\n const markdownSource = docs.map((doc) => doc.text).join(\"\\n\");\n const markdownTokens = markdown.parse(markdownSource, {});\n const linkMatches = docs.flatMap((doc) => linkify3.match(doc.text) ?? []).map((item) => item.url);\n const releaseChecks = (metadata.requires ?? []).map(\n (range) => import_semver.default.satisfies(metadata.release, range)\n );\n const rules = JSON.parse(ruleText);\n const findingInput = {\n linkCount: linkMatches.length,\n releaseOk: releaseChecks.every(Boolean)\n };\n const ruleInputStable = (0, import_fast_deep_equal.default)(\n findingInput,\n JSON.parse((0, import_fast_json_stable_stringify.default)(findingInput))\n );\n const rulePasses = Boolean(import_json_logic_js.default.apply(rules, findingInput));\n const queue = new TinyQueue([], (left, right) => left.priority - right.priority);\n for (const link2 of linkMatches) {\n queue.push({ link: link2, priority: link2.length });\n }\n const orderedLinks = [];\n while (queue.length > 0) {\n orderedLinks.push(queue.pop().link);\n }\n const decompressed = inflateSync(compressedAttachment);\n const attachmentRoundTrip = (0, import_base64_js.toByteArray)((0, import_base64_js.fromByteArray)(decompressed));\n const mergedBinary = new Uint8Array(\n attachmentRoundTrip.length + payload.length + extraPayload.length\n );\n mergedBinary.set(attachmentRoundTrip, 0);\n mergedBinary.set(payload, attachmentRoundTrip.length);\n mergedBinary.set(extraPayload, attachmentRoundTrip.length + payload.length);\n const digestHex = bytesToHex(sha2562(mergedBinary));\n const crc32 = (import_crc_32.default.buf(mergedBinary) >>> 0).toString(16).padStart(8, \"0\");\n const decodedEntities = import_he.default.decode(\"<b>safe</b>\");\n const versionCapture = (0, import_path_to_regexp.match)(\"/document/:id/version/:version\")(\n \"/document/42/version/1.2.3\"\n );\n const orderedFindings = [\n { id: \"links\", value: linkMatches.length },\n { id: \"rules\", value: Number(rulePasses) },\n { id: \"tokens\", value: markdownTokens.length }\n ].sort((left, right) => left.id.localeCompare(right.id));\n Promise.resolve(\"scheduled\").then(() => void 0);\n queueMicrotask(() => void 0);\n for (const doc of docs) {\n Host.v2.emit({\n type: \"knowledge-pack-doc\",\n docPath: doc.docPath,\n length: doc.text.length\n });\n }\n summary = {\n status: \"ok\",\n packId: metadata.packId,\n release: metadata.release,\n checks: releaseChecks,\n docTokenCount: markdownTokens.length,\n linkCount: linkMatches.length,\n uniqueLinks: [...new Set(orderedLinks)],\n binary: {\n byteLength: mergedBinary.length,\n digestHex,\n crc32\n },\n decodedEntities,\n versionCapture,\n findings: orderedFindings,\n ruleInputStable,\n rulePasses\n };\n} catch (error2) {\n summary = {\n status: \"error\",\n message: String(error2 instanceof Error ? error2.message : error2)\n };\n}\nHost.v2.emit({\n type: \"knowledge-pack-summary\",\n summaryHash: bytesToHex(\n sha2562(\n (0, import_base64_js.toByteArray)(\n (0, import_base64_js.fromByteArray)(\n new Uint8Array([\n ...Host.v2.document.get(\"bytes/payload\"),\n ...Host.v2.document.get(\"bytes/flagship-extra\")\n ])\n )\n )\n )\n ),\n status: summary.status\n});\nvar knowledge_pack_entry_default = summary;\nexport {\n knowledge_pack_entry_default as default\n};\n", + "sourceMap": "{\"mappings\":\"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,UAAS,KAAS,UAAS,KAAS,UAAS,KAAO,SAAQ,KAAO,SAAQ,KAAO,SAAQ,KAAO,SAAQ,KAAO,QAAO,KAAO,QAAO,KAAO,UAAS,KAAO,UAAS,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,KAAO,SAAQ,KAAO,SAAQ,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,KAAS,QAAO,MAAe,OAAM,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,KAAS,OAAM,MAAe,QAAO,KAAS,QAAO,KAAS,UAAS,KAAS,UAAS,KAAS,SAAQ,KAAS,SAAQ,KAAS,UAAS,KAAS,UAAS,KAAS,QAAO,KAAS,QAAO,KAAO,UAAS,KAAO,UAAS,KAAS,UAAS,MAAe,OAAM,KAAS,MAAK,MAAe,QAAO,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,KAAS,MAAK,MAAe,QAAO,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAO,OAAM,KAAO,OAAM,KAAS,MAAK,KAAS,QAAO,MAAe,OAAM,MAAe,QAAO,KAAS,QAAO,MAAe,OAAM,MAAe,QAAO,KAAO,UAAS,KAAO,UAAS,KAAO,UAAS,KAAO,UAAS,KAAO,SAAQ,KAAO,SAAQ,KAAS,UAAS,KAAS,UAAS,KAAO,QAAO,KAAO,QAAO,KAAS,QAAO,KAAS,QAAO,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,KAAS,QAAO,KAAS,SAAQ,KAAS,UAAS,KAAS,UAAS,KAAS,SAAQ,MAAK,SAAQ,KAAS,SAAQ,KAAS,QAAO,KAAS,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,SAAQ,KAAS,SAAQ,KAAS,QAAO,KAAS,QAAO,KAAS,UAAS,MAAe,OAAM,KAAS,WAAU,MAAe,QAAO,MAAe,QAAO,KAAS,QAAO,KAAS,OAAM,KAAS,QAAO,KAAS,SAAQ,KAAS,SAAQ,KAAS,QAAO,KAAS,UAAS,KAAS,UAAS,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,KAAS,MAAK,MAAe,QAAO,KAAS,QAAO,KAAS,MAAK,KAAO,UAAS,KAAO,UAAS,KAAO,UAAS,KAAO,UAAS,KAAO,SAAQ,KAAO,SAAQ,KAAO,QAAO,KAAO,QAAO,KAAS,UAAS,KAAS,UAAS,KAAS,QAAO,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,KAAS,UAAS,KAAS,UAAS,MAAe,OAAM,MAAe,QAAO,KAAS,OAAM,MAAe,QAAO,KAAS,QAAO,MAAe,OAAM,MAAe,QAAO,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,KAAS,QAAO,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,KAAS,QAAO,MAAe,QAAO,MAAe,OAAM,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAO,UAAS,KAAO,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,OAAM,KAAS,OAAM,MAAe,QAAO,MAAe,OAAM,KAAS,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,KAAO,QAAO,KAAO,UAAS,KAAO,UAAS,KAAO,UAAS,KAAO,UAAS,KAAO,SAAQ,KAAO,SAAQ,KAAO,QAAO,KAAO,QAAO,KAAS,UAAS,KAAS,UAAS,KAAO,UAAS,KAAO,UAAS,KAAO,UAAS,KAAO,UAAS,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,KAAS,QAAO,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,KAAS,QAAO,KAAS,UAAS,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,KAAS,QAAO,KAAS,MAAK,KAAS,QAAO,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,KAAS,MAAK,KAAS,UAAS,KAAS,UAAS,KAAS,SAAQ,KAAS,SAAQ,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAO,SAAQ,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,SAAQ,KAAS,UAAS,KAAS,UAAS,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,KAAO,UAAS,KAAO,UAAS,KAAO,UAAS,KAAO,UAAS,KAAS,UAAS,KAAS,UAAS,KAAO,SAAQ,KAAO,SAAQ,KAAS,SAAQ,KAAS,SAAQ,KAAO,QAAO,KAAO,QAAO,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,KAAS,SAAQ,KAAS,SAAQ,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,MAAe,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,KAAO,UAAS,KAAO,UAAS,KAAS,SAAQ,KAAS,SAAQ,KAAO,QAAO,KAAS,QAAO,MAAe,QAAO,MAAe,OAAM,MAAe,QAAO,KAAS,OAAM,KAAS,QAAO,MAAe,QAAO,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,UAAS,KAAS,QAAO,KAAS,QAAO,KAAS,SAAQ,KAAO,SAAQ,KAAO,SAAQ,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,KAAS,QAAO,KAAS,QAAO,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,KAAS,SAAQ,KAAS,QAAO,KAAS,SAAQ,KAAS,WAAU,KAAS,UAAS,KAAS,UAAS,KAAS,QAAO,KAAS,QAAO,KAAS,OAAM,KAAS,OAAM,KAAS,SAAQ,KAAS,UAAS,KAAS,SAAQ,KAAS,QAAO,KAAS,QAAO,KAAS,SAAQ,KAAS,UAAS,KAAS,SAAQ,KAAS,UAAS,KAAS,UAAS,KAAS,MAAK,KAAO,SAAQ,KAAS,MAAK,KAAS,MAAK,KAAS,MAAK,KAAS,MAAK,KAAS,MAAK,KAAS,WAAU,KAAS,WAAU,KAAS,MAAK,KAAS,OAAM,KAAS,MAAK,KAAS,OAAM,KAAS,QAAO,KAAS,OAAM,KAAS,SAAQ,KAAS,SAAQ,KAAS,UAAS,KAAS,OAAM,KAAS,OAAM,KAAS,QAAO,KAAS,WAAU,KAAS,QAAO,KAAS,OAAM,KAAS,QAAO,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,SAAQ,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,QAAO,KAAS,QAAO,KAAS,OAAM,KAAS,OAAM,KAAS,QAAO,KAAS,QAAO,KAAS,QAAO,KAAS,QAAO,KAAS,QAAO,KAAS,QAAO,KAAS,SAAQ,KAAS,SAAQ,KAAS,QAAO,KAAS,QAAO,KAAS,OAAM,KAAS,OAAM,KAAS,QAAO,KAAS,QAAO,KAAS,OAAM,KAAS,OAAM,KAAS,SAAQ,KAAS,SAAQ,KAAS,QAAO,KAAS,QAAO,KAAS,OAAM,KAAS,OAAM,KAAS,UAAS,KAAS,UAAS,KAAS,OAAM,KAAS,OAAM,KAAS,QAAO,KAAS,QAAO,KAAS,OAAM,KAAS,OAAM,KAAS,QAAO,KAAS,QAAO,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,QAAO,KAAS,QAAO,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,OAAM,KAAS,SAAQ,KAAS,SAAQ,KAAS,OAAM,KAAS,OAAM,KAAS,SAAQ,KAAS,SAAQ,KAAS,OAAM,KAAS,OAAM,KAAS,QAAO,KAAS,QAAO,KAAS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AAE,CAAC,IAAG,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,IAAG,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,YAAY,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,aAAa,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,G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AQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,SAAS,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,UAAU,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QA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AAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,IAAG,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,OAAO,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,GAAE,QAAQ,GAAE,CAAC,G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\",\"names\":[\"toByteArray\",\"fromByteArray\",\"code\",\"len\",\"i\",\"len2\",\"decodeMap\",\"stringFromCharCode\",\"has\",\"object\",\"key\",\"encode\",\"string\",\"decode\",\"reference\",\"escape\",\"he\",\"jsonLogic\",\"current\",\"code\",\"compile\",\"match\",\"escapeText\",\"escape\",\"text\",\"encode\",\"delimiter\",\"path\",\"value\",\"decode\",\"max\",\"match\",\"base\",\"clean\",\"list\",\"list\",\"match\",\"hr\",\"set\",\"max\",\"require_valid\",\"set\",\"max\",\"require_semver\",\"clean\",\"CRC32\",\"module\",\"table\",\"l\",\"add\",\"regex_default\",\"regex_default\",\"regex_default\",\"regex_default\",\"regex_default\",\"regex_default\",\"regex_default\",\"text\",\"match\",\"tlds\",\"list\",\"assign\",\"escapeRE\",\"fromCodePoint\",\"isString\",\"code\",\"_a\",\"CharCodes\",\"BinTrieFlags\",\"code\",\"EntityDecoderState\",\"DecodingMode\",\"errors\",\"base\",\"_a\",\"map\",\"escape\",\"match\",\"EntityLevel\",\"EncodingMode\",\"_class\",\"isString\",\"assign\",\"fromCodePoint\",\"match\",\"code\",\"entity\",\"escapeRE\",\"regex_default\",\"max\",\"max\",\"code\",\"max\",\"code\",\"assign\",\"list\",\"normalize\",\"text\",\"match\",\"text\",\"max\",\"max\",\"normalize\",\"max\",\"code\",\"max\",\"max\",\"max\",\"max\",\"max\",\"max\",\"nextLine\",\"pos\",\"max\",\"max\",\"max\",\"_rules\",\"max\",\"linkify\",\"max\",\"match\",\"link\",\"max\",\"escape\",\"max\",\"max\",\"max\",\"postProcess\",\"max\",\"code\",\"max\",\"code\",\"max\",\"max\",\"isLinkOpen\",\"isLinkClose\",\"max\",\"match\",\"max\",\"match\",\"code\",\"fromCodePoint\",\"max\",\"max\",\"_rules\",\"linkify\",\"escape\",\"_rules2\",\"decode\",\"encode\",\"isString\",\"assign\",\"list\",\"sha256\",\"linkify\",\"semver\",\"deepEqual\",\"stableStringify\",\"jsonLogic\",\"link\",\"sha256\",\"CRC32\",\"he\",\"pathMatch\",\"error\"],\"sources\":[\"../node_modules/.pnpm/base64-js@1.5.1/node_modules/base64-js/index.js\",\"../node_modules/.pnpm/fast-deep-equal@3.1.3/node_modules/fast-deep-equal/index.js\",\"../node_modules/.pnpm/fast-json-stable-stringify@2.1.0/node_modules/fast-json-stable-stringify/index.js\",\"../node_modules/.pnpm/he@1.2.0/node_modules/he/he.js\",\"../node_modules/.pnpm/json-logic-js@2.0.5/node_modules/json-logic-js/logic.js\",\"../node_modules/.pnpm/path-to-regexp@8.3.0/node_modules/path-to-regexp/src/index.ts\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/constants.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/debug.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/re.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/parse-options.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/identifiers.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/semver.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/parse.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/valid.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/clean.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/inc.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/diff.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/major.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/minor.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/patch.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/prerelease.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/rcompare.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare-loose.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/compare-build.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/sort.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/rsort.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/gt.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/lt.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/eq.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/neq.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/gte.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/lte.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/cmp.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/coerce.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/internal/lrucache.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/range.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/classes/comparator.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/functions/satisfies.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/to-comparators.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/max-satisfying.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/min-satisfying.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/min-version.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/valid.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/outside.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/gtr.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/ltr.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/intersects.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/simplify.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/ranges/subset.js\",\"../node_modules/.pnpm/semver@7.7.3/node_modules/semver/index.js\",\"../node_modules/.pnpm/crc-32@1.2.2/node_modules/crc-32/crc32.js\",\"../apps/ecosystem-certifier/fixtures/flagship/knowledge-pack-entry.ts\",\"../node_modules/.pnpm/fflate@0.8.2/node_modules/fflate/esm/browser.js\",\"../node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/index.mjs\",\"../node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/properties/Any/regex.mjs\",\"../node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/Cc/regex.mjs\",\"../node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/Cf/regex.mjs\",\"../node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/P/regex.mjs\",\"../node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/S/regex.mjs\",\"../node_modules/.pnpm/uc.micro@2.1.0/node_modules/uc.micro/categories/Z/regex.mjs\",\"../node_modules/.pnpm/linkify-it@5.0.0/node_modules/linkify-it/lib/re.mjs\",\"../node_modules/.pnpm/linkify-it@5.0.0/node_modules/linkify-it/index.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/common/utils.mjs\",\"../node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/index.mjs\",\"../node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/decode.mjs\",\"../node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/encode.mjs\",\"../node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/format.mjs\",\"../node_modules/.pnpm/mdurl@2.0.0/node_modules/mdurl/lib/parse.mjs\",\"https://raw.githubusercontent.com/fb55/entities/61afd4701eaa736978b13c7351cd3de9a96b04bc/src/generated/decode-data-html.ts\",\"https://raw.githubusercontent.com/fb55/entities/61afd4701eaa736978b13c7351cd3de9a96b04bc/src/generated/decode-data-xml.ts\",\"https://raw.githubusercontent.com/fb55/entities/61afd4701eaa736978b13c7351cd3de9a96b04bc/src/decode_codepoint.ts\",\"https://raw.githubusercontent.com/fb55/entities/61afd4701eaa736978b13c7351cd3de9a96b04bc/src/decode.ts\",\"https://raw.githubusercontent.com/fb55/entities/61afd4701eaa736978b13c7351cd3de9a96b04bc/src/generated/encode-html.ts\",\"https://raw.githubusercontent.com/fb55/entities/61afd4701eaa736978b13c7351cd3de9a96b04bc/src/escape.ts\",\"https://raw.githubusercontent.com/fb55/entities/61afd4701eaa736978b13c7351cd3de9a96b04bc/src/index.ts\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/index.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/parse_link_label.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/parse_link_destination.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/helpers/parse_link_title.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/renderer.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/ruler.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/token.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/state_core.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/normalize.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/block.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/inline.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/linkify.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/replacements.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/smartquotes.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_core/text_join.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/parser_core.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/state_block.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/table.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/code.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/fence.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/blockquote.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/hr.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/list.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/reference.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/common/html_blocks.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/common/html_re.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/html_block.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/heading.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/lheading.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_block/paragraph.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/parser_block.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/state_inline.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/text.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/linkify.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/newline.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/escape.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/backticks.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/strikethrough.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/emphasis.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/link.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/image.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/autolink.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/html_inline.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/entity.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/balance_pairs.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/rules_inline/fragments_join.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/parser_inline.mjs\",\"../node_modules/.pnpm/punycode.js@2.3.1/node_modules/punycode.js/punycode.es6.js\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/presets/default.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/presets/zero.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/presets/commonmark.mjs\",\"../node_modules/.pnpm/markdown-it@14.1.1/node_modules/markdown-it/lib/index.mjs\",\"../node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/src/utils.ts\",\"../node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/src/_md.ts\",\"../node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/src/sha2.ts\",\"../node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/src/sha256.ts\",\"../node_modules/.pnpm/tinyqueue@3.0.0/node_modules/tinyqueue/index.js\"],\"sourcesContent\":[\"'use strict'\\n\\nexports.byteLength = byteLength\\nexports.toByteArray = toByteArray\\nexports.fromByteArray = fromByteArray\\n\\nvar lookup = []\\nvar revLookup = []\\nvar Arr = typeof Uint8Array !== 'undefined' ? Uint8Array : Array\\n\\nvar code = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/'\\nfor (var i = 0, len = code.length; i < len; ++i) {\\n lookup[i] = code[i]\\n revLookup[code.charCodeAt(i)] = i\\n}\\n\\n// Support decoding URL-safe base64 strings, as Node.js does.\\n// See: https://en.wikipedia.org/wiki/Base64#URL_applications\\nrevLookup['-'.charCodeAt(0)] = 62\\nrevLookup['_'.charCodeAt(0)] = 63\\n\\nfunction getLens (b64) {\\n var len = b64.length\\n\\n if (len % 4 > 0) {\\n throw new Error('Invalid string. Length must be a multiple of 4')\\n }\\n\\n // Trim off extra bytes after placeholder bytes are found\\n // See: https://github.com/beatgammit/base64-js/issues/42\\n var validLen = b64.indexOf('=')\\n if (validLen === -1) validLen = len\\n\\n var placeHoldersLen = validLen === len\\n ? 0\\n : 4 - (validLen % 4)\\n\\n return [validLen, placeHoldersLen]\\n}\\n\\n// base64 is 4/3 + up to two characters of the original data\\nfunction byteLength (b64) {\\n var lens = getLens(b64)\\n var validLen = lens[0]\\n var placeHoldersLen = lens[1]\\n return ((validLen + placeHoldersLen) * 3 / 4) - placeHoldersLen\\n}\\n\\nfunction _byteLength (b64, validLen, placeHoldersLen) {\\n return ((validLen + placeHoldersLen) * 3 / 4) - placeHoldersLen\\n}\\n\\nfunction toByteArray (b64) {\\n var tmp\\n var lens = getLens(b64)\\n var validLen = lens[0]\\n var placeHoldersLen = lens[1]\\n\\n var arr = new Arr(_byteLength(b64, validLen, placeHoldersLen))\\n\\n var curByte = 0\\n\\n // if there are placeholders, only get up to the last complete 4 chars\\n var len = placeHoldersLen > 0\\n ? validLen - 4\\n : validLen\\n\\n var i\\n for (i = 0; i < len; i += 4) {\\n tmp =\\n (revLookup[b64.charCodeAt(i)] << 18) |\\n (revLookup[b64.charCodeAt(i + 1)] << 12) |\\n (revLookup[b64.charCodeAt(i + 2)] << 6) |\\n revLookup[b64.charCodeAt(i + 3)]\\n arr[curByte++] = (tmp >> 16) & 0xFF\\n arr[curByte++] = (tmp >> 8) & 0xFF\\n arr[curByte++] = tmp & 0xFF\\n }\\n\\n if (placeHoldersLen === 2) {\\n tmp =\\n (revLookup[b64.charCodeAt(i)] << 2) |\\n (revLookup[b64.charCodeAt(i + 1)] >> 4)\\n arr[curByte++] = tmp & 0xFF\\n }\\n\\n if (placeHoldersLen === 1) {\\n tmp =\\n (revLookup[b64.charCodeAt(i)] << 10) |\\n (revLookup[b64.charCodeAt(i + 1)] << 4) |\\n (revLookup[b64.charCodeAt(i + 2)] >> 2)\\n arr[curByte++] = (tmp >> 8) & 0xFF\\n arr[curByte++] = tmp & 0xFF\\n }\\n\\n return arr\\n}\\n\\nfunction tripletToBase64 (num) {\\n return lookup[num >> 18 & 0x3F] +\\n lookup[num >> 12 & 0x3F] +\\n lookup[num >> 6 & 0x3F] +\\n lookup[num & 0x3F]\\n}\\n\\nfunction encodeChunk (uint8, start, end) {\\n var tmp\\n var output = []\\n for (var i = start; i < end; i += 3) {\\n tmp =\\n ((uint8[i] << 16) & 0xFF0000) +\\n ((uint8[i + 1] << 8) & 0xFF00) +\\n (uint8[i + 2] & 0xFF)\\n output.push(tripletToBase64(tmp))\\n }\\n return output.join('')\\n}\\n\\nfunction fromByteArray (uint8) {\\n var tmp\\n var len = uint8.length\\n var extraBytes = len % 3 // if we have 1 byte left, pad 2 bytes\\n var parts = []\\n var maxChunkLength = 16383 // must be multiple of 3\\n\\n // go through the array every three bytes, we'll deal with trailing stuff later\\n for (var i = 0, len2 = len - extraBytes; i < len2; i += maxChunkLength) {\\n parts.push(encodeChunk(uint8, i, (i + maxChunkLength) > len2 ? len2 : (i + maxChunkLength)))\\n }\\n\\n // pad the end with zeros, but make sure to not forget the extra bytes\\n if (extraBytes === 1) {\\n tmp = uint8[len - 1]\\n parts.push(\\n lookup[tmp >> 2] +\\n lookup[(tmp << 4) & 0x3F] +\\n '=='\\n )\\n } else if (extraBytes === 2) {\\n tmp = (uint8[len - 2] << 8) + uint8[len - 1]\\n parts.push(\\n lookup[tmp >> 10] +\\n lookup[(tmp >> 4) & 0x3F] +\\n lookup[(tmp << 2) & 0x3F] +\\n '='\\n )\\n }\\n\\n return parts.join('')\\n}\\n\",\"'use strict';\\n\\n// do not edit .js files directly - edit src/index.jst\\n\\n\\n\\nmodule.exports = function equal(a, b) {\\n if (a === b) return true;\\n\\n if (a && b && typeof a == 'object' && typeof b == 'object') {\\n if (a.constructor !== b.constructor) return false;\\n\\n var length, i, keys;\\n if (Array.isArray(a)) {\\n length = a.length;\\n if (length != b.length) return false;\\n for (i = length; i-- !== 0;)\\n if (!equal(a[i], b[i])) return false;\\n return true;\\n }\\n\\n\\n\\n if (a.constructor === RegExp) return a.source === b.source && a.flags === b.flags;\\n if (a.valueOf !== Object.prototype.valueOf) return a.valueOf() === b.valueOf();\\n if (a.toString !== Object.prototype.toString) return a.toString() === b.toString();\\n\\n keys = Object.keys(a);\\n length = keys.length;\\n if (length !== Object.keys(b).length) return false;\\n\\n for (i = length; i-- !== 0;)\\n if (!Object.prototype.hasOwnProperty.call(b, keys[i])) return false;\\n\\n for (i = length; i-- !== 0;) {\\n var key = keys[i];\\n\\n if (!equal(a[key], b[key])) return false;\\n }\\n\\n return true;\\n }\\n\\n // true if both NaN, false otherwise\\n return a!==a && b!==b;\\n};\\n\",\"'use strict';\\n\\nmodule.exports = function (data, opts) {\\n if (!opts) opts = {};\\n if (typeof opts === 'function') opts = { cmp: opts };\\n var cycles = (typeof opts.cycles === 'boolean') ? opts.cycles : false;\\n\\n var cmp = opts.cmp && (function (f) {\\n return function (node) {\\n return function (a, b) {\\n var aobj = { key: a, value: node[a] };\\n var bobj = { key: b, value: node[b] };\\n return f(aobj, bobj);\\n };\\n };\\n })(opts.cmp);\\n\\n var seen = [];\\n return (function stringify (node) {\\n if (node && node.toJSON && typeof node.toJSON === 'function') {\\n node = node.toJSON();\\n }\\n\\n if (node === undefined) return;\\n if (typeof node == 'number') return isFinite(node) ? '' + node : 'null';\\n if (typeof node !== 'object') return JSON.stringify(node);\\n\\n var i, out;\\n if (Array.isArray(node)) {\\n out = '[';\\n for (i = 0; i < node.length; i++) {\\n if (i) out += ',';\\n out += stringify(node[i]) || 'null';\\n }\\n return out + ']';\\n }\\n\\n if (node === null) return 'null';\\n\\n if (seen.indexOf(node) !== -1) {\\n if (cycles) return JSON.stringify('__cycle__');\\n throw new TypeError('Converting circular structure to JSON');\\n }\\n\\n var seenIndex = seen.push(node) - 1;\\n var keys = Object.keys(node).sort(cmp && cmp(node));\\n out = '';\\n for (i = 0; i < keys.length; i++) {\\n var key = keys[i];\\n var value = stringify(node[key]);\\n\\n if (!value) continue;\\n if (out) out += ',';\\n out += JSON.stringify(key) + ':' + value;\\n }\\n seen.splice(seenIndex, 1);\\n return '{' + out + '}';\\n })(data);\\n};\\n\",\"/*! https://mths.be/he v1.2.0 by @mathias | MIT license */\\n;(function(root) {\\n\\n\\t// Detect free variables `exports`.\\n\\tvar freeExports = typeof exports == 'object' && exports;\\n\\n\\t// Detect free variable `module`.\\n\\tvar freeModule = typeof module == 'object' && module &&\\n\\t\\tmodule.exports == freeExports && module;\\n\\n\\t// Detect free variable `global`, from Node.js or Browserified code,\\n\\t// and use it as `root`.\\n\\tvar freeGlobal = typeof global == 'object' && global;\\n\\tif (freeGlobal.global === freeGlobal || freeGlobal.window === freeGlobal) {\\n\\t\\troot = freeGlobal;\\n\\t}\\n\\n\\t/*--------------------------------------------------------------------------*/\\n\\n\\t// All astral symbols.\\n\\tvar regexAstralSymbols = /[\\\\uD800-\\\\uDBFF][\\\\uDC00-\\\\uDFFF]/g;\\n\\t// All ASCII symbols (not just printable ASCII) except those listed in the\\n\\t// first column of the overrides table.\\n\\t// https://html.spec.whatwg.org/multipage/syntax.html#table-charref-overrides\\n\\tvar regexAsciiWhitelist = /[\\\\x01-\\\\x7F]/g;\\n\\t// All BMP symbols that are not ASCII newlines, printable ASCII symbols, or\\n\\t// code points listed in the first column of the overrides table on\\n\\t// https://html.spec.whatwg.org/multipage/syntax.html#table-charref-overrides.\\n\\tvar regexBmpWhitelist = /[\\\\x01-\\\\t\\\\x0B\\\\f\\\\x0E-\\\\x1F\\\\x7F\\\\x81\\\\x8D\\\\x8F\\\\x90\\\\x9D\\\\xA0-\\\\uFFFF]/g;\\n\\n\\tvar regexEncodeNonAscii = /<\\\\u20D2|=\\\\u20E5|>\\\\u20D2|\\\\u205F\\\\u200A|\\\\u219D\\\\u0338|\\\\u2202\\\\u0338|\\\\u2220\\\\u20D2|\\\\u2229\\\\uFE00|\\\\u222A\\\\uFE00|\\\\u223C\\\\u20D2|\\\\u223D\\\\u0331|\\\\u223E\\\\u0333|\\\\u2242\\\\u0338|\\\\u224B\\\\u0338|\\\\u224D\\\\u20D2|\\\\u224E\\\\u0338|\\\\u224F\\\\u0338|\\\\u2250\\\\u0338|\\\\u2261\\\\u20E5|\\\\u2264\\\\u20D2|\\\\u2265\\\\u20D2|\\\\u2266\\\\u0338|\\\\u2267\\\\u0338|\\\\u2268\\\\uFE00|\\\\u2269\\\\uFE00|\\\\u226A\\\\u0338|\\\\u226A\\\\u20D2|\\\\u226B\\\\u0338|\\\\u226B\\\\u20D2|\\\\u227F\\\\u0338|\\\\u2282\\\\u20D2|\\\\u2283\\\\u20D2|\\\\u228A\\\\uFE00|\\\\u228B\\\\uFE00|\\\\u228F\\\\u0338|\\\\u2290\\\\u0338|\\\\u2293\\\\uFE00|\\\\u2294\\\\uFE00|\\\\u22B4\\\\u20D2|\\\\u22B5\\\\u20D2|\\\\u22D8\\\\u0338|\\\\u22D9\\\\u0338|\\\\u22DA\\\\uFE00|\\\\u22DB\\\\uFE00|\\\\u22F5\\\\u0338|\\\\u22F9\\\\u0338|\\\\u2933\\\\u0338|\\\\u29CF\\\\u0338|\\\\u29D0\\\\u0338|\\\\u2A6D\\\\u0338|\\\\u2A70\\\\u0338|\\\\u2A7D\\\\u0338|\\\\u2A7E\\\\u0338|\\\\u2AA1\\\\u0338|\\\\u2AA2\\\\u0338|\\\\u2AAC\\\\uFE00|\\\\u2AAD\\\\uFE00|\\\\u2AAF\\\\u0338|\\\\u2AB0\\\\u0338|\\\\u2AC5\\\\u0338|\\\\u2AC6\\\\u0338|\\\\u2ACB\\\\uFE00|\\\\u2ACC\\\\uFE00|\\\\u2AFD\\\\u20E5|[\\\\xA0-\\\\u0113\\\\u0116-\\\\u0122\\\\u0124-\\\\u012B\\\\u012E-\\\\u014D\\\\u0150-\\\\u017E\\\\u0192\\\\u01B5\\\\u01F5\\\\u0237\\\\u02C6\\\\u02C7\\\\u02D8-\\\\u02DD\\\\u0311\\\\u0391-\\\\u03A1\\\\u03A3-\\\\u03A9\\\\u03B1-\\\\u03C9\\\\u03D1\\\\u03D2\\\\u03D5\\\\u03D6\\\\u03DC\\\\u03DD\\\\u03F0\\\\u03F1\\\\u03F5\\\\u03F6\\\\u0401-\\\\u040C\\\\u040E-\\\\u044F\\\\u0451-\\\\u045C\\\\u045E\\\\u045F\\\\u2002-\\\\u2005\\\\u2007-\\\\u2010\\\\u2013-\\\\u2016\\\\u2018-\\\\u201A\\\\u201C-\\\\u201E\\\\u2020-\\\\u2022\\\\u2025\\\\u2026\\\\u2030-\\\\u2035\\\\u2039\\\\u203A\\\\u203E\\\\u2041\\\\u2043\\\\u2044\\\\u204F\\\\u2057\\\\u205F-\\\\u2063\\\\u20AC\\\\u20DB\\\\u20DC\\\\u2102\\\\u2105\\\\u210A-\\\\u2113\\\\u2115-\\\\u211E\\\\u2122\\\\u2124\\\\u2127-\\\\u2129\\\\u212C\\\\u212D\\\\u212F-\\\\u2131\\\\u2133-\\\\u2138\\\\u2145-\\\\u2148\\\\u2153-\\\\u215E\\\\u2190-\\\\u219B\\\\u219D-\\\\u21A7\\\\u21A9-\\\\u21AE\\\\u21B0-\\\\u21B3\\\\u21B5-\\\\u21B7\\\\u21BA-\\\\u21DB\\\\u21DD\\\\u21E4\\\\u21E5\\\\u21F5\\\\u21FD-\\\\u2205\\\\u2207-\\\\u2209\\\\u220B\\\\u220C\\\\u220F-\\\\u2214\\\\u2216-\\\\u2218\\\\u221A\\\\u221D-\\\\u2238\\\\u223A-\\\\u2257\\\\u2259\\\\u225A\\\\u225C\\\\u225F-\\\\u2262\\\\u2264-\\\\u228B\\\\u228D-\\\\u229B\\\\u229D-\\\\u22A5\\\\u22A7-\\\\u22B0\\\\u22B2-\\\\u22BB\\\\u22BD-\\\\u22DB\\\\u22DE-\\\\u22E3\\\\u22E6-\\\\u22F7\\\\u22F9-\\\\u22FE\\\\u2305\\\\u2306\\\\u2308-\\\\u2310\\\\u2312\\\\u2313\\\\u2315\\\\u2316\\\\u231C-\\\\u231F\\\\u2322\\\\u2323\\\\u232D\\\\u232E\\\\u2336\\\\u233D\\\\u233F\\\\u237C\\\\u23B0\\\\u23B1\\\\u23B4-\\\\u23B6\\\\u23DC-\\\\u23DF\\\\u23E2\\\\u23E7\\\\u2423\\\\u24C8\\\\u2500\\\\u2502\\\\u250C\\\\u2510\\\\u2514\\\\u2518\\\\u251C\\\\u2524\\\\u252C\\\\u2534\\\\u253C\\\\u2550-\\\\u256C\\\\u2580\\\\u2584\\\\u2588\\\\u2591-\\\\u2593\\\\u25A1\\\\u25AA\\\\u25AB\\\\u25AD\\\\u25AE\\\\u25B1\\\\u25B3-\\\\u25B5\\\\u25B8\\\\u25B9\\\\u25BD-\\\\u25BF\\\\u25C2\\\\u25C3\\\\u25CA\\\\u25CB\\\\u25EC\\\\u25EF\\\\u25F8-\\\\u25FC\\\\u2605\\\\u2606\\\\u260E\\\\u2640\\\\u2642\\\\u2660\\\\u2663\\\\u2665\\\\u2666\\\\u266A\\\\u266D-\\\\u266F\\\\u2713\\\\u2717\\\\u2720\\\\u2736\\\\u2758\\\\u2772\\\\u2773\\\\u27C8\\\\u27C9\\\\u27E6-\\\\u27ED\\\\u27F5-\\\\u27FA\\\\u27FC\\\\u27FF\\\\u2902-\\\\u2905\\\\u290C-\\\\u2913\\\\u2916\\\\u2919-\\\\u2920\\\\u2923-\\\\u292A\\\\u2933\\\\u2935-\\\\u2939\\\\u293C\\\\u293D\\\\u2945\\\\u2948-\\\\u294B\\\\u294E-\\\\u2976\\\\u2978\\\\u2979\\\\u297B-\\\\u297F\\\\u2985\\\\u2986\\\\u298B-\\\\u2996\\\\u299A\\\\u299C\\\\u299D\\\\u29A4-\\\\u29B7\\\\u29B9\\\\u29BB\\\\u29BC\\\\u29BE-\\\\u29C5\\\\u29C9\\\\u29CD-\\\\u29D0\\\\u29DC-\\\\u29DE\\\\u29E3-\\\\u29E5\\\\u29EB\\\\u29F4\\\\u29F6\\\\u2A00-\\\\u2A02\\\\u2A04\\\\u2A06\\\\u2A0C\\\\u2A0D\\\\u2A10-\\\\u2A17\\\\u2A22-\\\\u2A27\\\\u2A29\\\\u2A2A\\\\u2A2D-\\\\u2A31\\\\u2A33-\\\\u2A3C\\\\u2A3F\\\\u2A40\\\\u2A42-\\\\u2A4D\\\\u2A50\\\\u2A53-\\\\u2A58\\\\u2A5A-\\\\u2A5D\\\\u2A5F\\\\u2A66\\\\u2A6A\\\\u2A6D-\\\\u2A75\\\\u2A77-\\\\u2A9A\\\\u2A9D-\\\\u2AA2\\\\u2AA4-\\\\u2AB0\\\\u2AB3-\\\\u2AC8\\\\u2ACB\\\\u2ACC\\\\u2ACF-\\\\u2ADB\\\\u2AE4\\\\u2AE6-\\\\u2AE9\\\\u2AEB-\\\\u2AF3\\\\u2AFD\\\\uFB00-\\\\uFB04]|\\\\uD835[\\\\uDC9C\\\\uDC9E\\\\uDC9F\\\\uDCA2\\\\uDCA5\\\\uDCA6\\\\uDCA9-\\\\uDCAC\\\\uDCAE-\\\\uDCB9\\\\uDCBB\\\\uDCBD-\\\\uDCC3\\\\uDCC5-\\\\uDCCF\\\\uDD04\\\\uDD05\\\\uDD07-\\\\uDD0A\\\\uDD0D-\\\\uDD14\\\\uDD16-\\\\uDD1C\\\\uDD1E-\\\\uDD39\\\\uDD3B-\\\\uDD3E\\\\uDD40-\\\\uDD44\\\\uDD46\\\\uDD4A-\\\\uDD50\\\\uDD52-\\\\uDD6B]/g;\\n\\tvar encodeMap = {'\\\\xAD':'shy','\\\\u200C':'zwnj','\\\\u200D':'zwj','\\\\u200E':'lrm','\\\\u2063':'ic','\\\\u2062':'it','\\\\u2061':'af','\\\\u200F':'rlm','\\\\u200B':'ZeroWidthSpace','\\\\u2060':'NoBreak','\\\\u0311':'DownBreve','\\\\u20DB':'tdot','\\\\u20DC':'DotDot','\\\\t':'Tab','\\\\n':'NewLine','\\\\u2008':'puncsp','\\\\u205F':'MediumSpace','\\\\u2009':'thinsp','\\\\u200A':'hairsp','\\\\u2004':'emsp13','\\\\u2002':'ensp','\\\\u2005':'emsp14','\\\\u2003':'emsp','\\\\u2007':'numsp','\\\\xA0':'nbsp','\\\\u205F\\\\u200A':'ThickSpace','\\\\u203E':'oline','_':'lowbar','\\\\u2010':'dash','\\\\u2013':'ndash','\\\\u2014':'mdash','\\\\u2015':'horbar',',':'comma',';':'semi','\\\\u204F':'bsemi',':':'colon','\\\\u2A74':'Colone','!':'excl','\\\\xA1':'iexcl','?':'quest','\\\\xBF':'iquest','.':'period','\\\\u2025':'nldr','\\\\u2026':'mldr','\\\\xB7':'middot','\\\\'':'apos','\\\\u2018':'lsquo','\\\\u2019':'rsquo','\\\\u201A':'sbquo','\\\\u2039':'lsaquo','\\\\u203A':'rsaquo','\\\"':'quot','\\\\u201C':'ldquo','\\\\u201D':'rdquo','\\\\u201E':'bdquo','\\\\xAB':'laquo','\\\\xBB':'raquo','(':'lpar',')':'rpar','[':'lsqb',']':'rsqb','{':'lcub','}':'rcub','\\\\u2308':'lceil','\\\\u2309':'rceil','\\\\u230A':'lfloor','\\\\u230B':'rfloor','\\\\u2985':'lopar','\\\\u2986':'ropar','\\\\u298B':'lbrke','\\\\u298C':'rbrke','\\\\u298D':'lbrkslu','\\\\u298E':'rbrksld','\\\\u298F':'lbrksld','\\\\u2990':'rbrkslu','\\\\u2991':'langd','\\\\u2992':'rangd','\\\\u2993':'lparlt','\\\\u2994':'rpargt','\\\\u2995':'gtlPar','\\\\u2996':'ltrPar','\\\\u27E6':'lobrk','\\\\u27E7':'robrk','\\\\u27E8':'lang','\\\\u27E9':'rang','\\\\u27EA':'Lang','\\\\u27EB':'Rang','\\\\u27EC':'loang','\\\\u27ED':'roang','\\\\u2772':'lbbrk','\\\\u2773':'rbbrk','\\\\u2016':'Vert','\\\\xA7':'sect','\\\\xB6':'para','@':'commat','*':'ast','/':'sol','undefined':null,'&':'amp','#':'num','%':'percnt','\\\\u2030':'permil','\\\\u2031':'pertenk','\\\\u2020':'dagger','\\\\u2021':'Dagger','\\\\u2022':'bull','\\\\u2043':'hybull','\\\\u2032':'prime','\\\\u2033':'Prime','\\\\u2034':'tprime','\\\\u2057':'qprime','\\\\u2035':'bprime','\\\\u2041':'caret','`':'grave','\\\\xB4':'acute','\\\\u02DC':'tilde','^':'Hat','\\\\xAF':'macr','\\\\u02D8':'breve','\\\\u02D9':'dot','\\\\xA8':'die','\\\\u02DA':'ring','\\\\u02DD':'dblac','\\\\xB8':'cedil','\\\\u02DB':'ogon','\\\\u02C6':'circ','\\\\u02C7':'caron','\\\\xB0':'deg','\\\\xA9':'copy','\\\\xAE':'reg','\\\\u2117':'copysr','\\\\u2118':'wp','\\\\u211E':'rx','\\\\u2127':'mho','\\\\u2129':'iiota','\\\\u2190':'larr','\\\\u219A':'nlarr','\\\\u2192':'rarr','\\\\u219B':'nrarr','\\\\u2191':'uarr','\\\\u2193':'darr','\\\\u2194':'harr','\\\\u21AE':'nharr','\\\\u2195':'varr','\\\\u2196':'nwarr','\\\\u2197':'nearr','\\\\u2198':'searr','\\\\u2199':'swarr','\\\\u219D':'rarrw','\\\\u219D\\\\u0338':'nrarrw','\\\\u219E':'Larr','\\\\u219F':'Uarr','\\\\u21A0':'Rarr','\\\\u21A1':'Darr','\\\\u21A2':'larrtl','\\\\u21A3':'rarrtl','\\\\u21A4':'mapstoleft','\\\\u21A5':'mapstoup','\\\\u21A6':'map','\\\\u21A7':'mapstodown','\\\\u21A9':'larrhk','\\\\u21AA':'rarrhk','\\\\u21AB':'larrlp','\\\\u21AC':'rarrlp','\\\\u21AD':'harrw','\\\\u21B0':'lsh','\\\\u21B1':'rsh','\\\\u21B2':'ldsh','\\\\u21B3':'rdsh','\\\\u21B5':'crarr','\\\\u21B6':'cularr','\\\\u21B7':'curarr','\\\\u21BA':'olarr','\\\\u21BB':'orarr','\\\\u21BC':'lharu','\\\\u21BD':'lhard','\\\\u21BE':'uharr','\\\\u21BF':'uharl','\\\\u21C0':'rharu','\\\\u21C1':'rhard','\\\\u21C2':'dharr','\\\\u21C3':'dharl','\\\\u21C4':'rlarr','\\\\u21C5':'udarr','\\\\u21C6':'lrarr','\\\\u21C7':'llarr','\\\\u21C8':'uuarr','\\\\u21C9':'rrarr','\\\\u21CA':'ddarr','\\\\u21CB':'lrhar','\\\\u21CC':'rlhar','\\\\u21D0':'lArr','\\\\u21CD':'nlArr','\\\\u21D1':'uArr','\\\\u21D2':'rArr','\\\\u21CF':'nrArr','\\\\u21D3':'dArr','\\\\u21D4':'iff','\\\\u21CE':'nhArr','\\\\u21D5':'vArr','\\\\u21D6':'nwArr','\\\\u21D7':'neArr','\\\\u21D8':'seArr','\\\\u21D9':'swArr','\\\\u21DA':'lAarr','\\\\u21DB':'rAarr','\\\\u21DD':'zigrarr','\\\\u21E4':'larrb','\\\\u21E5':'rarrb','\\\\u21F5':'duarr','\\\\u21FD':'loarr','\\\\u21FE':'roarr','\\\\u21FF':'hoarr','\\\\u2200':'forall','\\\\u2201':'comp','\\\\u2202':'part','\\\\u2202\\\\u0338':'npart','\\\\u2203':'exist','\\\\u2204':'nexist','\\\\u2205':'empty','\\\\u2207':'Del','\\\\u2208':'in','\\\\u2209':'notin','\\\\u220B':'ni','\\\\u220C':'notni','\\\\u03F6':'bepsi','\\\\u220F':'prod','\\\\u2210':'coprod','\\\\u2211':'sum','+':'plus','\\\\xB1':'pm','\\\\xF7':'div','\\\\xD7':'times','<':'lt','\\\\u226E':'nlt','<\\\\u20D2':'nvlt','=':'equals','\\\\u2260':'ne','=\\\\u20E5':'bne','\\\\u2A75':'Equal','>':'gt','\\\\u226F':'ngt','>\\\\u20D2':'nvgt','\\\\xAC':'not','|':'vert','\\\\xA6':'brvbar','\\\\u2212':'minus','\\\\u2213':'mp','\\\\u2214':'plusdo','\\\\u2044':'frasl','\\\\u2216':'setmn','\\\\u2217':'lowast','\\\\u2218':'compfn','\\\\u221A':'Sqrt','\\\\u221D':'prop','\\\\u221E':'infin','\\\\u221F':'angrt','\\\\u2220':'ang','\\\\u2220\\\\u20D2':'nang','\\\\u2221':'angmsd','\\\\u2222':'angsph','\\\\u2223':'mid','\\\\u2224':'nmid','\\\\u2225':'par','\\\\u2226':'npar','\\\\u2227':'and','\\\\u2228':'or','\\\\u2229':'cap','\\\\u2229\\\\uFE00':'caps','\\\\u222A':'cup','\\\\u222A\\\\uFE00':'cups','\\\\u222B':'int','\\\\u222C':'Int','\\\\u222D':'tint','\\\\u2A0C':'qint','\\\\u222E':'oint','\\\\u222F':'Conint','\\\\u2230':'Cconint','\\\\u2231':'cwint','\\\\u2232':'cwconint','\\\\u2233':'awconint','\\\\u2234':'there4','\\\\u2235':'becaus','\\\\u2236':'ratio','\\\\u2237':'Colon','\\\\u2238':'minusd','\\\\u223A':'mDDot','\\\\u223B':'homtht','\\\\u223C':'sim','\\\\u2241':'nsim','\\\\u223C\\\\u20D2':'nvsim','\\\\u223D':'bsim','\\\\u223D\\\\u0331':'race','\\\\u223E':'ac','\\\\u223E\\\\u0333':'acE','\\\\u223F':'acd','\\\\u2240':'wr','\\\\u2242':'esim','\\\\u2242\\\\u0338':'nesim','\\\\u2243':'sime','\\\\u2244':'nsime','\\\\u2245':'cong','\\\\u2247':'ncong','\\\\u2246':'simne','\\\\u2248':'ap','\\\\u2249':'nap','\\\\u224A':'ape','\\\\u224B':'apid','\\\\u224B\\\\u0338':'napid','\\\\u224C':'bcong','\\\\u224D':'CupCap','\\\\u226D':'NotCupCap','\\\\u224D\\\\u20D2':'nvap','\\\\u224E':'bump','\\\\u224E\\\\u0338':'nbump','\\\\u224F':'bumpe','\\\\u224F\\\\u0338':'nbumpe','\\\\u2250':'doteq','\\\\u2250\\\\u0338':'nedot','\\\\u2251':'eDot','\\\\u2252':'efDot','\\\\u2253':'erDot','\\\\u2254':'colone','\\\\u2255':'ecolon','\\\\u2256':'ecir','\\\\u2257':'cire','\\\\u2259':'wedgeq','\\\\u225A':'veeeq','\\\\u225C':'trie','\\\\u225F':'equest','\\\\u2261':'equiv','\\\\u2262':'nequiv','\\\\u2261\\\\u20E5':'bnequiv','\\\\u2264':'le','\\\\u2270':'nle','\\\\u2264\\\\u20D2':'nvle','\\\\u2265':'ge','\\\\u2271':'nge','\\\\u2265\\\\u20D2':'nvge','\\\\u2266':'lE','\\\\u2266\\\\u0338':'nlE','\\\\u2267':'gE','\\\\u2267\\\\u0338':'ngE','\\\\u2268\\\\uFE00':'lvnE','\\\\u2268':'lnE','\\\\u2269':'gnE','\\\\u2269\\\\uFE00':'gvnE','\\\\u226A':'ll','\\\\u226A\\\\u0338':'nLtv','\\\\u226A\\\\u20D2':'nLt','\\\\u226B':'gg','\\\\u226B\\\\u0338':'nGtv','\\\\u226B\\\\u20D2':'nGt','\\\\u226C':'twixt','\\\\u2272':'lsim','\\\\u2274':'nlsim','\\\\u2273':'gsim','\\\\u2275':'ngsim','\\\\u2276':'lg','\\\\u2278':'ntlg','\\\\u2277':'gl','\\\\u2279':'ntgl','\\\\u227A':'pr','\\\\u2280':'npr','\\\\u227B':'sc','\\\\u2281':'nsc','\\\\u227C':'prcue','\\\\u22E0':'nprcue','\\\\u227D':'sccue','\\\\u22E1':'nsccue','\\\\u227E':'prsim','\\\\u227F':'scsim','\\\\u227F\\\\u0338':'NotSucceedsTilde','\\\\u2282':'sub','\\\\u2284':'nsub','\\\\u2282\\\\u20D2':'vnsub','\\\\u2283':'sup','\\\\u2285':'nsup','\\\\u2283\\\\u20D2':'vnsup','\\\\u2286':'sube','\\\\u2288':'nsube','\\\\u2287':'supe','\\\\u2289':'nsupe','\\\\u228A\\\\uFE00':'vsubne','\\\\u228A':'subne','\\\\u228B\\\\uFE00':'vsupne','\\\\u228B':'supne','\\\\u228D':'cupdot','\\\\u228E':'uplus','\\\\u228F':'sqsub','\\\\u228F\\\\u0338':'NotSquareSubset','\\\\u2290':'sqsup','\\\\u2290\\\\u0338':'NotSquareSuperset','\\\\u2291':'sqsube','\\\\u22E2':'nsqsube','\\\\u2292':'sqsupe','\\\\u22E3':'nsqsupe','\\\\u2293':'sqcap','\\\\u2293\\\\uFE00':'sqcaps','\\\\u2294':'sqcup','\\\\u2294\\\\uFE00':'sqcups','\\\\u2295':'oplus','\\\\u2296':'ominus','\\\\u2297':'otimes','\\\\u2298':'osol','\\\\u2299':'odot','\\\\u229A':'ocir','\\\\u229B':'oast','\\\\u229D':'odash','\\\\u229E':'plusb','\\\\u229F':'minusb','\\\\u22A0':'timesb','\\\\u22A1':'sdotb','\\\\u22A2':'vdash','\\\\u22AC':'nvdash','\\\\u22A3':'dashv','\\\\u22A4':'top','\\\\u22A5':'bot','\\\\u22A7':'models','\\\\u22A8':'vDash','\\\\u22AD':'nvDash','\\\\u22A9':'Vdash','\\\\u22AE':'nVdash','\\\\u22AA':'Vvdash','\\\\u22AB':'VDash','\\\\u22AF':'nVDash','\\\\u22B0':'prurel','\\\\u22B2':'vltri','\\\\u22EA':'nltri','\\\\u22B3':'vrtri','\\\\u22EB':'nrtri','\\\\u22B4':'ltrie','\\\\u22EC':'nltrie','\\\\u22B4\\\\u20D2':'nvltrie','\\\\u22B5':'rtrie','\\\\u22ED':'nrtrie','\\\\u22B5\\\\u20D2':'nvrtrie','\\\\u22B6':'origof','\\\\u22B7':'imof','\\\\u22B8':'mumap','\\\\u22B9':'hercon','\\\\u22BA':'intcal','\\\\u22BB':'veebar','\\\\u22BD':'barvee','\\\\u22BE':'angrtvb','\\\\u22BF':'lrtri','\\\\u22C0':'Wedge','\\\\u22C1':'Vee','\\\\u22C2':'xcap','\\\\u22C3':'xcup','\\\\u22C4':'diam','\\\\u22C5':'sdot','\\\\u22C6':'Star','\\\\u22C7':'divonx','\\\\u22C8':'bowtie','\\\\u22C9':'ltimes','\\\\u22CA':'rtimes','\\\\u22CB':'lthree','\\\\u22CC':'rthree','\\\\u22CD':'bsime','\\\\u22CE':'cuvee','\\\\u22CF':'cuwed','\\\\u22D0':'Sub','\\\\u22D1':'Sup','\\\\u22D2':'Cap','\\\\u22D3':'Cup','\\\\u22D4':'fork','\\\\u22D5':'epar','\\\\u22D6':'ltdot','\\\\u22D7':'gtdot','\\\\u22D8':'Ll','\\\\u22D8\\\\u0338':'nLl','\\\\u22D9':'Gg','\\\\u22D9\\\\u0338':'nGg','\\\\u22DA\\\\uFE00':'lesg','\\\\u22DA':'leg','\\\\u22DB':'gel','\\\\u22DB\\\\uFE00':'gesl','\\\\u22DE':'cuepr','\\\\u22DF':'cuesc','\\\\u22E6':'lnsim','\\\\u22E7':'gnsim','\\\\u22E8':'prnsim','\\\\u22E9':'scnsim','\\\\u22EE':'vellip','\\\\u22EF':'ctdot','\\\\u22F0':'utdot','\\\\u22F1':'dtdot','\\\\u22F2':'disin','\\\\u22F3':'isinsv','\\\\u22F4':'isins','\\\\u22F5':'isindot','\\\\u22F5\\\\u0338':'notindot','\\\\u22F6':'notinvc','\\\\u22F7':'notinvb','\\\\u22F9':'isinE','\\\\u22F9\\\\u0338':'notinE','\\\\u22FA':'nisd','\\\\u22FB':'xnis','\\\\u22FC':'nis','\\\\u22FD':'notnivc','\\\\u22FE':'notnivb','\\\\u2305':'barwed','\\\\u2306':'Barwed','\\\\u230C':'drcrop','\\\\u230D':'dlcrop','\\\\u230E':'urcrop','\\\\u230F':'ulcrop','\\\\u2310':'bnot','\\\\u2312':'profline','\\\\u2313':'profsurf','\\\\u2315':'telrec','\\\\u2316':'target','\\\\u231C':'ulcorn','\\\\u231D':'urcorn','\\\\u231E':'dlcorn','\\\\u231F':'drcorn','\\\\u2322':'frown','\\\\u2323':'smile','\\\\u232D':'cylcty','\\\\u232E':'profalar','\\\\u2336':'topbot','\\\\u233D':'ovbar','\\\\u233F':'solbar','\\\\u237C':'angzarr','\\\\u23B0':'lmoust','\\\\u23B1':'rmoust','\\\\u23B4':'tbrk','\\\\u23B5':'bbrk','\\\\u23B6':'bbrktbrk','\\\\u23DC':'OverParenthesis','\\\\u23DD':'UnderParenthesis','\\\\u23DE':'OverBrace','\\\\u23DF':'UnderBrace','\\\\u23E2':'trpezium','\\\\u23E7':'elinters','\\\\u2423':'blank','\\\\u2500':'boxh','\\\\u2502':'boxv','\\\\u250C':'boxdr','\\\\u2510':'boxdl','\\\\u2514':'boxur','\\\\u2518':'boxul','\\\\u251C':'boxvr','\\\\u2524':'boxvl','\\\\u252C':'boxhd','\\\\u2534':'boxhu','\\\\u253C':'boxvh','\\\\u2550':'boxH','\\\\u2551':'boxV','\\\\u2552':'boxdR','\\\\u2553':'boxDr','\\\\u2554':'boxDR','\\\\u2555':'boxdL','\\\\u2556':'boxDl','\\\\u2557':'boxDL','\\\\u2558':'boxuR','\\\\u2559':'boxUr','\\\\u255A':'boxUR','\\\\u255B':'boxuL','\\\\u255C':'boxUl','\\\\u255D':'boxUL','\\\\u255E':'boxvR','\\\\u255F':'boxVr','\\\\u2560':'boxVR','\\\\u2561':'boxvL','\\\\u2562':'boxVl','\\\\u2563':'boxVL','\\\\u2564':'boxHd','\\\\u2565':'boxhD','\\\\u2566':'boxHD','\\\\u2567':'boxHu','\\\\u2568':'boxhU','\\\\u2569':'boxHU','\\\\u256A':'boxvH','\\\\u256B':'boxVh','\\\\u256C':'boxVH','\\\\u2580':'uhblk','\\\\u2584':'lhblk','\\\\u2588':'block','\\\\u2591':'blk14','\\\\u2592':'blk12','\\\\u2593':'blk34','\\\\u25A1':'squ','\\\\u25AA':'squf','\\\\u25AB':'EmptyVerySmallSquare','\\\\u25AD':'rect','\\\\u25AE':'marker','\\\\u25B1':'fltns','\\\\u25B3':'xutri','\\\\u25B4':'utrif','\\\\u25B5':'utri','\\\\u25B8':'rtrif','\\\\u25B9':'rtri','\\\\u25BD':'xdtri','\\\\u25BE':'dtrif','\\\\u25BF':'dtri','\\\\u25C2':'ltrif','\\\\u25C3':'ltri','\\\\u25CA':'loz','\\\\u25CB':'cir','\\\\u25EC':'tridot','\\\\u25EF':'xcirc','\\\\u25F8':'ultri','\\\\u25F9':'urtri','\\\\u25FA':'lltri','\\\\u25FB':'EmptySmallSquare','\\\\u25FC':'FilledSmallSquare','\\\\u2605':'starf','\\\\u2606':'star','\\\\u260E':'phone','\\\\u2640':'female','\\\\u2642':'male','\\\\u2660':'spades','\\\\u2663':'clubs','\\\\u2665':'hearts','\\\\u2666':'diams','\\\\u266A':'sung','\\\\u2713':'check','\\\\u2717':'cross','\\\\u2720':'malt','\\\\u2736':'sext','\\\\u2758':'VerticalSeparator','\\\\u27C8':'bsolhsub','\\\\u27C9':'suphsol','\\\\u27F5':'xlarr','\\\\u27F6':'xrarr','\\\\u27F7':'xharr','\\\\u27F8':'xlArr','\\\\u27F9':'xrArr','\\\\u27FA':'xhArr','\\\\u27FC':'xmap','\\\\u27FF':'dzigrarr','\\\\u2902':'nvlArr','\\\\u2903':'nvrArr','\\\\u2904':'nvHarr','\\\\u2905':'Map','\\\\u290C':'lbarr','\\\\u290D':'rbarr','\\\\u290E':'lBarr','\\\\u290F':'rBarr','\\\\u2910':'RBarr','\\\\u2911':'DDotrahd','\\\\u2912':'UpArrowBar','\\\\u2913':'DownArrowBar','\\\\u2916':'Rarrtl','\\\\u2919':'latail','\\\\u291A':'ratail','\\\\u291B':'lAtail','\\\\u291C':'rAtail','\\\\u291D':'larrfs','\\\\u291E':'rarrfs','\\\\u291F':'larrbfs','\\\\u2920':'rarrbfs','\\\\u2923':'nwarhk','\\\\u2924':'nearhk','\\\\u2925':'searhk','\\\\u2926':'swarhk','\\\\u2927':'nwnear','\\\\u2928':'toea','\\\\u2929':'tosa','\\\\u292A':'swnwar','\\\\u2933':'rarrc','\\\\u2933\\\\u0338':'nrarrc','\\\\u2935':'cudarrr','\\\\u2936':'ldca','\\\\u2937':'rdca','\\\\u2938':'cudarrl','\\\\u2939':'larrpl','\\\\u293C':'curarrm','\\\\u293D':'cularrp','\\\\u2945':'rarrpl','\\\\u2948':'harrcir','\\\\u2949':'Uarrocir','\\\\u294A':'lurdshar','\\\\u294B':'ldrushar','\\\\u294E':'LeftRightVector','\\\\u294F':'RightUpDownVector','\\\\u2950':'DownLeftRightVector','\\\\u2951':'LeftUpDownVector','\\\\u2952':'LeftVectorBar','\\\\u2953':'RightVectorBar','\\\\u2954':'RightUpVectorBar','\\\\u2955':'RightDownVectorBar','\\\\u2956':'DownLeftVectorBar','\\\\u2957':'DownRightVectorBar','\\\\u2958':'LeftUpVectorBar','\\\\u2959':'LeftDownVectorBar','\\\\u295A':'LeftTeeVector','\\\\u295B':'RightTeeVector','\\\\u295C':'RightUpTeeVector','\\\\u295D':'RightDownTeeVector','\\\\u295E':'DownLeftTeeVector','\\\\u295F':'DownRightTeeVector','\\\\u2960':'LeftUpTeeVector','\\\\u2961':'LeftDownTeeVector','\\\\u2962':'lHar','\\\\u2963':'uHar','\\\\u2964':'rHar','\\\\u2965':'dHar','\\\\u2966':'luruhar','\\\\u2967':'ldrdhar','\\\\u2968':'ruluhar','\\\\u2969':'rdldhar','\\\\u296A':'lharul','\\\\u296B':'llhard','\\\\u296C':'rharul','\\\\u296D':'lrhard','\\\\u296E':'udhar','\\\\u296F':'duhar','\\\\u2970':'RoundImplies','\\\\u2971':'erarr','\\\\u2972':'simrarr','\\\\u2973':'larrsim','\\\\u2974':'rarrsim','\\\\u2975':'rarrap','\\\\u2976':'ltlarr','\\\\u2978':'gtrarr','\\\\u2979':'subrarr','\\\\u297B':'suplarr','\\\\u297C':'lfisht','\\\\u297D':'rfisht','\\\\u297E':'ufisht','\\\\u297F':'dfisht','\\\\u299A':'vzigzag','\\\\u299C':'vangrt','\\\\u299D':'angrtvbd','\\\\u29A4':'ange','\\\\u29A5':'range','\\\\u29A6':'dwangle','\\\\u29A7':'uwangle','\\\\u29A8':'angmsdaa','\\\\u29A9':'angmsdab','\\\\u29AA':'angmsdac','\\\\u29AB':'angmsdad','\\\\u29AC':'angmsdae','\\\\u29AD':'angmsdaf','\\\\u29AE':'angmsdag','\\\\u29AF':'angmsdah','\\\\u29B0':'bemptyv','\\\\u29B1':'demptyv','\\\\u29B2':'cemptyv','\\\\u29B3':'raemptyv','\\\\u29B4':'laemptyv','\\\\u29B5':'ohbar','\\\\u29B6':'omid','\\\\u29B7':'opar','\\\\u29B9':'operp','\\\\u29BB':'olcross','\\\\u29BC':'odsold','\\\\u29BE':'olcir','\\\\u29BF':'ofcir','\\\\u29C0':'olt','\\\\u29C1':'ogt','\\\\u29C2':'cirscir','\\\\u29C3':'cirE','\\\\u29C4':'solb','\\\\u29C5':'bsolb','\\\\u29C9':'boxbox','\\\\u29CD':'trisb','\\\\u29CE':'rtriltri','\\\\u29CF':'LeftTriangleBar','\\\\u29CF\\\\u0338':'NotLeftTriangleBar','\\\\u29D0':'RightTriangleBar','\\\\u29D0\\\\u0338':'NotRightTriangleBar','\\\\u29DC':'iinfin','\\\\u29DD':'infintie','\\\\u29DE':'nvinfin','\\\\u29E3':'eparsl','\\\\u29E4':'smeparsl','\\\\u29E5':'eqvparsl','\\\\u29EB':'lozf','\\\\u29F4':'RuleDelayed','\\\\u29F6':'dsol','\\\\u2A00':'xodot','\\\\u2A01':'xoplus','\\\\u2A02':'xotime','\\\\u2A04':'xuplus','\\\\u2A06':'xsqcup','\\\\u2A0D':'fpartint','\\\\u2A10':'cirfnint','\\\\u2A11':'awint','\\\\u2A12':'rppolint','\\\\u2A13':'scpolint','\\\\u2A14':'npolint','\\\\u2A15':'pointint','\\\\u2A16':'quatint','\\\\u2A17':'intlarhk','\\\\u2A22':'pluscir','\\\\u2A23':'plusacir','\\\\u2A24':'simplus','\\\\u2A25':'plusdu','\\\\u2A26':'plussim','\\\\u2A27':'plustwo','\\\\u2A29':'mcomma','\\\\u2A2A':'minusdu','\\\\u2A2D':'loplus','\\\\u2A2E':'roplus','\\\\u2A2F':'Cross','\\\\u2A30':'timesd','\\\\u2A31':'timesbar','\\\\u2A33':'smashp','\\\\u2A34':'lotimes','\\\\u2A35':'rotimes','\\\\u2A36':'otimesas','\\\\u2A37':'Otimes','\\\\u2A38':'odiv','\\\\u2A39':'triplus','\\\\u2A3A':'triminus','\\\\u2A3B':'tritime','\\\\u2A3C':'iprod','\\\\u2A3F':'amalg','\\\\u2A40':'capdot','\\\\u2A42':'ncup','\\\\u2A43':'ncap','\\\\u2A44':'capand','\\\\u2A45':'cupor','\\\\u2A46':'cupcap','\\\\u2A47':'capcup','\\\\u2A48':'cupbrcap','\\\\u2A49':'capbrcup','\\\\u2A4A':'cupcup','\\\\u2A4B':'capcap','\\\\u2A4C':'ccups','\\\\u2A4D':'ccaps','\\\\u2A50':'ccupssm','\\\\u2A53':'And','\\\\u2A54':'Or','\\\\u2A55':'andand','\\\\u2A56':'oror','\\\\u2A57':'orslope','\\\\u2A58':'andslope','\\\\u2A5A':'andv','\\\\u2A5B':'orv','\\\\u2A5C':'andd','\\\\u2A5D':'ord','\\\\u2A5F':'wedbar','\\\\u2A66':'sdote','\\\\u2A6A':'simdot','\\\\u2A6D':'congdot','\\\\u2A6D\\\\u0338':'ncongdot','\\\\u2A6E':'easter','\\\\u2A6F':'apacir','\\\\u2A70':'apE','\\\\u2A70\\\\u0338':'napE','\\\\u2A71':'eplus','\\\\u2A72':'pluse','\\\\u2A73':'Esim','\\\\u2A77':'eDDot','\\\\u2A78':'equivDD','\\\\u2A79':'ltcir','\\\\u2A7A':'gtcir','\\\\u2A7B':'ltquest','\\\\u2A7C':'gtquest','\\\\u2A7D':'les','\\\\u2A7D\\\\u0338':'nles','\\\\u2A7E':'ges','\\\\u2A7E\\\\u0338':'nges','\\\\u2A7F':'lesdot','\\\\u2A80':'gesdot','\\\\u2A81':'lesdoto','\\\\u2A82':'gesdoto','\\\\u2A83':'lesdotor','\\\\u2A84':'gesdotol','\\\\u2A85':'lap','\\\\u2A86':'gap','\\\\u2A87':'lne','\\\\u2A88':'gne','\\\\u2A89':'lnap','\\\\u2A8A':'gnap','\\\\u2A8B':'lEg','\\\\u2A8C':'gEl','\\\\u2A8D':'lsime','\\\\u2A8E':'gsime','\\\\u2A8F':'lsimg','\\\\u2A90':'gsiml','\\\\u2A91':'lgE','\\\\u2A92':'glE','\\\\u2A93':'lesges','\\\\u2A94':'gesles','\\\\u2A95':'els','\\\\u2A96':'egs','\\\\u2A97':'elsdot','\\\\u2A98':'egsdot','\\\\u2A99':'el','\\\\u2A9A':'eg','\\\\u2A9D':'siml','\\\\u2A9E':'simg','\\\\u2A9F':'simlE','\\\\u2AA0':'simgE','\\\\u2AA1':'LessLess','\\\\u2AA1\\\\u0338':'NotNestedLessLess','\\\\u2AA2':'GreaterGreater','\\\\u2AA2\\\\u0338':'NotNestedGreaterGreater','\\\\u2AA4':'glj','\\\\u2AA5':'gla','\\\\u2AA6':'ltcc','\\\\u2AA7':'gtcc','\\\\u2AA8':'lescc','\\\\u2AA9':'gescc','\\\\u2AAA':'smt','\\\\u2AAB':'lat','\\\\u2AAC':'smte','\\\\u2AAC\\\\uFE00':'smtes','\\\\u2AAD':'late','\\\\u2AAD\\\\uFE00':'lates','\\\\u2AAE':'bumpE','\\\\u2AAF':'pre','\\\\u2AAF\\\\u0338':'npre','\\\\u2AB0':'sce','\\\\u2AB0\\\\u0338':'nsce','\\\\u2AB3':'prE','\\\\u2AB4':'scE','\\\\u2AB5':'prnE','\\\\u2AB6':'scnE','\\\\u2AB7':'prap','\\\\u2AB8':'scap','\\\\u2AB9':'prnap','\\\\u2ABA':'scnap','\\\\u2ABB':'Pr','\\\\u2ABC':'Sc','\\\\u2ABD':'subdot','\\\\u2ABE':'supdot','\\\\u2ABF':'subplus','\\\\u2AC0':'supplus','\\\\u2AC1':'submult','\\\\u2AC2':'supmult','\\\\u2AC3':'subedot','\\\\u2AC4':'supedot','\\\\u2AC5':'subE','\\\\u2AC5\\\\u0338':'nsubE','\\\\u2AC6':'supE','\\\\u2AC6\\\\u0338':'nsupE','\\\\u2AC7':'subsim','\\\\u2AC8':'supsim','\\\\u2ACB\\\\uFE00':'vsubnE','\\\\u2ACB':'subnE','\\\\u2ACC\\\\uFE00':'vsupnE','\\\\u2ACC':'supnE','\\\\u2ACF':'csub','\\\\u2AD0':'csup','\\\\u2AD1':'csube','\\\\u2AD2':'csupe','\\\\u2AD3':'subsup','\\\\u2AD4':'supsub','\\\\u2AD5':'subsub','\\\\u2AD6':'supsup','\\\\u2AD7':'suphsub','\\\\u2AD8':'supdsub','\\\\u2AD9':'forkv','\\\\u2ADA':'topfork','\\\\u2ADB':'mlcp','\\\\u2AE4':'Dashv','\\\\u2AE6':'Vdashl','\\\\u2AE7':'Barv','\\\\u2AE8':'vBar','\\\\u2AE9':'vBarv','\\\\u2AEB':'Vbar','\\\\u2AEC':'Not','\\\\u2AED':'bNot','\\\\u2AEE':'rnmid','\\\\u2AEF':'cirmid','\\\\u2AF0':'midcir','\\\\u2AF1':'topcir','\\\\u2AF2':'nhpar','\\\\u2AF3':'parsim','\\\\u2AFD':'parsl','\\\\u2AFD\\\\u20E5':'nparsl','\\\\u266D':'flat','\\\\u266E':'natur','\\\\u266F':'sharp','\\\\xA4':'curren','\\\\xA2':'cent','$':'dollar','\\\\xA3':'pound','\\\\xA5':'yen','\\\\u20AC':'euro','\\\\xB9':'sup1','\\\\xBD':'half','\\\\u2153':'frac13','\\\\xBC':'frac14','\\\\u2155':'frac15','\\\\u2159':'frac16','\\\\u215B':'frac18','\\\\xB2':'sup2','\\\\u2154':'frac23','\\\\u2156':'frac25','\\\\xB3':'sup3','\\\\xBE':'frac34','\\\\u2157':'frac35','\\\\u215C':'frac38','\\\\u2158':'frac45','\\\\u215A':'frac56','\\\\u215D':'frac58','\\\\u215E':'frac78','\\\\uD835\\\\uDCB6':'ascr','\\\\uD835\\\\uDD52':'aopf','\\\\uD835\\\\uDD1E':'afr','\\\\uD835\\\\uDD38':'Aopf','\\\\uD835\\\\uDD04':'Afr','\\\\uD835\\\\uDC9C':'Ascr','\\\\xAA':'ordf','\\\\xE1':'aacute','\\\\xC1':'Aacute','\\\\xE0':'agrave','\\\\xC0':'Agrave','\\\\u0103':'abreve','\\\\u0102':'Abreve','\\\\xE2':'acirc','\\\\xC2':'Acirc','\\\\xE5':'aring','\\\\xC5':'angst','\\\\xE4':'auml','\\\\xC4':'Auml','\\\\xE3':'atilde','\\\\xC3':'Atilde','\\\\u0105':'aogon','\\\\u0104':'Aogon','\\\\u0101':'amacr','\\\\u0100':'Amacr','\\\\xE6':'aelig','\\\\xC6':'AElig','\\\\uD835\\\\uDCB7':'bscr','\\\\uD835\\\\uDD53':'bopf','\\\\uD835\\\\uDD1F':'bfr','\\\\uD835\\\\uDD39':'Bopf','\\\\u212C':'Bscr','\\\\uD835\\\\uDD05':'Bfr','\\\\uD835\\\\uDD20':'cfr','\\\\uD835\\\\uDCB8':'cscr','\\\\uD835\\\\uDD54':'copf','\\\\u212D':'Cfr','\\\\uD835\\\\uDC9E':'Cscr','\\\\u2102':'Copf','\\\\u0107':'cacute','\\\\u0106':'Cacute','\\\\u0109':'ccirc','\\\\u0108':'Ccirc','\\\\u010D':'ccaron','\\\\u010C':'Ccaron','\\\\u010B':'cdot','\\\\u010A':'Cdot','\\\\xE7':'ccedil','\\\\xC7':'Ccedil','\\\\u2105':'incare','\\\\uD835\\\\uDD21':'dfr','\\\\u2146':'dd','\\\\uD835\\\\uDD55':'dopf','\\\\uD835\\\\uDCB9':'dscr','\\\\uD835\\\\uDC9F':'Dscr','\\\\uD835\\\\uDD07':'Dfr','\\\\u2145':'DD','\\\\uD835\\\\uDD3B':'Dopf','\\\\u010F':'dcaron','\\\\u010E':'Dcaron','\\\\u0111':'dstrok','\\\\u0110':'Dstrok','\\\\xF0':'eth','\\\\xD0':'ETH','\\\\u2147':'ee','\\\\u212F':'escr','\\\\uD835\\\\uDD22':'efr','\\\\uD835\\\\uDD56':'eopf','\\\\u2130':'Escr','\\\\uD835\\\\uDD08':'Efr','\\\\uD835\\\\uDD3C':'Eopf','\\\\xE9':'eacute','\\\\xC9':'Eacute','\\\\xE8':'egrave','\\\\xC8':'Egrave','\\\\xEA':'ecirc','\\\\xCA':'Ecirc','\\\\u011B':'ecaron','\\\\u011A':'Ecaron','\\\\xEB':'euml','\\\\xCB':'Euml','\\\\u0117':'edot','\\\\u0116':'Edot','\\\\u0119':'eogon','\\\\u0118':'Eogon','\\\\u0113':'emacr','\\\\u0112':'Emacr','\\\\uD835\\\\uDD23':'ffr','\\\\uD835\\\\uDD57':'fopf','\\\\uD835\\\\uDCBB':'fscr','\\\\uD835\\\\uDD09':'Ffr','\\\\uD835\\\\uDD3D':'Fopf','\\\\u2131':'Fscr','\\\\uFB00':'fflig','\\\\uFB03':'ffilig','\\\\uFB04':'ffllig','\\\\uFB01':'filig','fj':'fjlig','\\\\uFB02':'fllig','\\\\u0192':'fnof','\\\\u210A':'gscr','\\\\uD835\\\\uDD58':'gopf','\\\\uD835\\\\uDD24':'gfr','\\\\uD835\\\\uDCA2':'Gscr','\\\\uD835\\\\uDD3E':'Gopf','\\\\uD835\\\\uDD0A':'Gfr','\\\\u01F5':'gacute','\\\\u011F':'gbreve','\\\\u011E':'Gbreve','\\\\u011D':'gcirc','\\\\u011C':'Gcirc','\\\\u0121':'gdot','\\\\u0120':'Gdot','\\\\u0122':'Gcedil','\\\\uD835\\\\uDD25':'hfr','\\\\u210E':'planckh','\\\\uD835\\\\uDCBD':'hscr','\\\\uD835\\\\uDD59':'hopf','\\\\u210B':'Hscr','\\\\u210C':'Hfr','\\\\u210D':'Hopf','\\\\u0125':'hcirc','\\\\u0124':'Hcirc','\\\\u210F':'hbar','\\\\u0127':'hstrok','\\\\u0126':'Hstrok','\\\\uD835\\\\uDD5A':'iopf','\\\\uD835\\\\uDD26':'ifr','\\\\uD835\\\\uDCBE':'iscr','\\\\u2148':'ii','\\\\uD835\\\\uDD40':'Iopf','\\\\u2110':'Iscr','\\\\u2111':'Im','\\\\xED':'iacute','\\\\xCD':'Iacute','\\\\xEC':'igrave','\\\\xCC':'Igrave','\\\\xEE':'icirc','\\\\xCE':'Icirc','\\\\xEF':'iuml','\\\\xCF':'Iuml','\\\\u0129':'itilde','\\\\u0128':'Itilde','\\\\u0130':'Idot','\\\\u012F':'iogon','\\\\u012E':'Iogon','\\\\u012B':'imacr','\\\\u012A':'Imacr','\\\\u0133':'ijlig','\\\\u0132':'IJlig','\\\\u0131':'imath','\\\\uD835\\\\uDCBF':'jscr','\\\\uD835\\\\uDD5B':'jopf','\\\\uD835\\\\uDD27':'jfr','\\\\uD835\\\\uDCA5':'Jscr','\\\\uD835\\\\uDD0D':'Jfr','\\\\uD835\\\\uDD41':'Jopf','\\\\u0135':'jcirc','\\\\u0134':'Jcirc','\\\\u0237':'jmath','\\\\uD835\\\\uDD5C':'kopf','\\\\uD835\\\\uDCC0':'kscr','\\\\uD835\\\\uDD28':'kfr','\\\\uD835\\\\uDCA6':'Kscr','\\\\uD835\\\\uDD42':'Kopf','\\\\uD835\\\\uDD0E':'Kfr','\\\\u0137':'kcedil','\\\\u0136':'Kcedil','\\\\uD835\\\\uDD29':'lfr','\\\\uD835\\\\uDCC1':'lscr','\\\\u2113':'ell','\\\\uD835\\\\uDD5D':'lopf','\\\\u2112':'Lscr','\\\\uD835\\\\uDD0F':'Lfr','\\\\uD835\\\\uDD43':'Lopf','\\\\u013A':'lacute','\\\\u0139':'Lacute','\\\\u013E':'lcaron','\\\\u013D':'Lcaron','\\\\u013C':'lcedil','\\\\u013B':'Lcedil','\\\\u0142':'lstrok','\\\\u0141':'Lstrok','\\\\u0140':'lmidot','\\\\u013F':'Lmidot','\\\\uD835\\\\uDD2A':'mfr','\\\\uD835\\\\uDD5E':'mopf','\\\\uD835\\\\uDCC2':'mscr','\\\\uD835\\\\uDD10':'Mfr','\\\\uD835\\\\uDD44':'Mopf','\\\\u2133':'Mscr','\\\\uD835\\\\uDD2B':'nfr','\\\\uD835\\\\uDD5F':'nopf','\\\\uD835\\\\uDCC3':'nscr','\\\\u2115':'Nopf','\\\\uD835\\\\uDCA9':'Nscr','\\\\uD835\\\\uDD11':'Nfr','\\\\u0144':'nacute','\\\\u0143':'Nacute','\\\\u0148':'ncaron','\\\\u0147':'Ncaron','\\\\xF1':'ntilde','\\\\xD1':'Ntilde','\\\\u0146':'ncedil','\\\\u0145':'Ncedil','\\\\u2116':'numero','\\\\u014B':'eng','\\\\u014A':'ENG','\\\\uD835\\\\uDD60':'oopf','\\\\uD835\\\\uDD2C':'ofr','\\\\u2134':'oscr','\\\\uD835\\\\uDCAA':'Oscr','\\\\uD835\\\\uDD12':'Ofr','\\\\uD835\\\\uDD46':'Oopf','\\\\xBA':'ordm','\\\\xF3':'oacute','\\\\xD3':'Oacute','\\\\xF2':'ograve','\\\\xD2':'Ograve','\\\\xF4':'ocirc','\\\\xD4':'Ocirc','\\\\xF6':'ouml','\\\\xD6':'Ouml','\\\\u0151':'odblac','\\\\u0150':'Odblac','\\\\xF5':'otilde','\\\\xD5':'Otilde','\\\\xF8':'oslash','\\\\xD8':'Oslash','\\\\u014D':'omacr','\\\\u014C':'Omacr','\\\\u0153':'oelig','\\\\u0152':'OElig','\\\\uD835\\\\uDD2D':'pfr','\\\\uD835\\\\uDCC5':'pscr','\\\\uD835\\\\uDD61':'popf','\\\\u2119':'Popf','\\\\uD835\\\\uDD13':'Pfr','\\\\uD835\\\\uDCAB':'Pscr','\\\\uD835\\\\uDD62':'qopf','\\\\uD835\\\\uDD2E':'qfr','\\\\uD835\\\\uDCC6':'qscr','\\\\uD835\\\\uDCAC':'Qscr','\\\\uD835\\\\uDD14':'Qfr','\\\\u211A':'Qopf','\\\\u0138':'kgreen','\\\\uD835\\\\uDD2F':'rfr','\\\\uD835\\\\uDD63':'ropf','\\\\uD835\\\\uDCC7':'rscr','\\\\u211B':'Rscr','\\\\u211C':'Re','\\\\u211D':'Ropf','\\\\u0155':'racute','\\\\u0154':'Racute','\\\\u0159':'rcaron','\\\\u0158':'Rcaron','\\\\u0157':'rcedil','\\\\u0156':'Rcedil','\\\\uD835\\\\uDD64':'sopf','\\\\uD835\\\\uDCC8':'sscr','\\\\uD835\\\\uDD30':'sfr','\\\\uD835\\\\uDD4A':'Sopf','\\\\uD835\\\\uDD16':'Sfr','\\\\uD835\\\\uDCAE':'Sscr','\\\\u24C8':'oS','\\\\u015B':'sacute','\\\\u015A':'Sacute','\\\\u015D':'scirc','\\\\u015C':'Scirc','\\\\u0161':'scaron','\\\\u0160':'Scaron','\\\\u015F':'scedil','\\\\u015E':'Scedil','\\\\xDF':'szlig','\\\\uD835\\\\uDD31':'tfr','\\\\uD835\\\\uDCC9':'tscr','\\\\uD835\\\\uDD65':'topf','\\\\uD835\\\\uDCAF':'Tscr','\\\\uD835\\\\uDD17':'Tfr','\\\\uD835\\\\uDD4B':'Topf','\\\\u0165':'tcaron','\\\\u0164':'Tcaron','\\\\u0163':'tcedil','\\\\u0162':'Tcedil','\\\\u2122':'trade','\\\\u0167':'tstrok','\\\\u0166':'Tstrok','\\\\uD835\\\\uDCCA':'uscr','\\\\uD835\\\\uDD66':'uopf','\\\\uD835\\\\uDD32':'ufr','\\\\uD835\\\\uDD4C':'Uopf','\\\\uD835\\\\uDD18':'Ufr','\\\\uD835\\\\uDCB0':'Uscr','\\\\xFA':'uacute','\\\\xDA':'Uacute','\\\\xF9':'ugrave','\\\\xD9':'Ugrave','\\\\u016D':'ubreve','\\\\u016C':'Ubreve','\\\\xFB':'ucirc','\\\\xDB':'Ucirc','\\\\u016F':'uring','\\\\u016E':'Uring','\\\\xFC':'uuml','\\\\xDC':'Uuml','\\\\u0171':'udblac','\\\\u0170':'Udblac','\\\\u0169':'utilde','\\\\u0168':'Utilde','\\\\u0173':'uogon','\\\\u0172':'Uogon','\\\\u016B':'umacr','\\\\u016A':'Umacr','\\\\uD835\\\\uDD33':'vfr','\\\\uD835\\\\uDD67':'vopf','\\\\uD835\\\\uDCCB':'vscr','\\\\uD835\\\\uDD19':'Vfr','\\\\uD835\\\\uDD4D':'Vopf','\\\\uD835\\\\uDCB1':'Vscr','\\\\uD835\\\\uDD68':'wopf','\\\\uD835\\\\uDCCC':'wscr','\\\\uD835\\\\uDD34':'wfr','\\\\uD835\\\\uDCB2':'Wscr','\\\\uD835\\\\uDD4E':'Wopf','\\\\uD835\\\\uDD1A':'Wfr','\\\\u0175':'wcirc','\\\\u0174':'Wcirc','\\\\uD835\\\\uDD35':'xfr','\\\\uD835\\\\uDCCD':'xscr','\\\\uD835\\\\uDD69':'xopf','\\\\uD835\\\\uDD4F':'Xopf','\\\\uD835\\\\uDD1B':'Xfr','\\\\uD835\\\\uDCB3':'Xscr','\\\\uD835\\\\uDD36':'yfr','\\\\uD835\\\\uDCCE':'yscr','\\\\uD835\\\\uDD6A':'yopf','\\\\uD835\\\\uDCB4':'Yscr','\\\\uD835\\\\uDD1C':'Yfr','\\\\uD835\\\\uDD50':'Yopf','\\\\xFD':'yacute','\\\\xDD':'Yacute','\\\\u0177':'ycirc','\\\\u0176':'Ycirc','\\\\xFF':'yuml','\\\\u0178':'Yuml','\\\\uD835\\\\uDCCF':'zscr','\\\\uD835\\\\uDD37':'zfr','\\\\uD835\\\\uDD6B':'zopf','\\\\u2128':'Zfr','\\\\u2124':'Zopf','\\\\uD835\\\\uDCB5':'Zscr','\\\\u017A':'zacute','\\\\u0179':'Zacute','\\\\u017E':'zcaron','\\\\u017D':'Zcaron','\\\\u017C':'zdot','\\\\u017B':'Zdot','\\\\u01B5':'imped','\\\\xFE':'thorn','\\\\xDE':'THORN','\\\\u0149':'napos','\\\\u03B1':'alpha','\\\\u0391':'Alpha','\\\\u03B2':'beta','\\\\u0392':'Beta','\\\\u03B3':'gamma','\\\\u0393':'Gamma','\\\\u03B4':'delta','\\\\u0394':'Delta','\\\\u03B5':'epsi','\\\\u03F5':'epsiv','\\\\u0395':'Epsilon','\\\\u03DD':'gammad','\\\\u03DC':'Gammad','\\\\u03B6':'zeta','\\\\u0396':'Zeta','\\\\u03B7':'eta','\\\\u0397':'Eta','\\\\u03B8':'theta','\\\\u03D1':'thetav','\\\\u0398':'Theta','\\\\u03B9':'iota','\\\\u0399':'Iota','\\\\u03BA':'kappa','\\\\u03F0':'kappav','\\\\u039A':'Kappa','\\\\u03BB':'lambda','\\\\u039B':'Lambda','\\\\u03BC':'mu','\\\\xB5':'micro','\\\\u039C':'Mu','\\\\u03BD':'nu','\\\\u039D':'Nu','\\\\u03BE':'xi','\\\\u039E':'Xi','\\\\u03BF':'omicron','\\\\u039F':'Omicron','\\\\u03C0':'pi','\\\\u03D6':'piv','\\\\u03A0':'Pi','\\\\u03C1':'rho','\\\\u03F1':'rhov','\\\\u03A1':'Rho','\\\\u03C3':'sigma','\\\\u03A3':'Sigma','\\\\u03C2':'sigmaf','\\\\u03C4':'tau','\\\\u03A4':'Tau','\\\\u03C5':'upsi','\\\\u03A5':'Upsilon','\\\\u03D2':'Upsi','\\\\u03C6':'phi','\\\\u03D5':'phiv','\\\\u03A6':'Phi','\\\\u03C7':'chi','\\\\u03A7':'Chi','\\\\u03C8':'psi','\\\\u03A8':'Psi','\\\\u03C9':'omega','\\\\u03A9':'ohm','\\\\u0430':'acy','\\\\u0410':'Acy','\\\\u0431':'bcy','\\\\u0411':'Bcy','\\\\u0432':'vcy','\\\\u0412':'Vcy','\\\\u0433':'gcy','\\\\u0413':'Gcy','\\\\u0453':'gjcy','\\\\u0403':'GJcy','\\\\u0434':'dcy','\\\\u0414':'Dcy','\\\\u0452':'djcy','\\\\u0402':'DJcy','\\\\u0435':'iecy','\\\\u0415':'IEcy','\\\\u0451':'iocy','\\\\u0401':'IOcy','\\\\u0454':'jukcy','\\\\u0404':'Jukcy','\\\\u0436':'zhcy','\\\\u0416':'ZHcy','\\\\u0437':'zcy','\\\\u0417':'Zcy','\\\\u0455':'dscy','\\\\u0405':'DScy','\\\\u0438':'icy','\\\\u0418':'Icy','\\\\u0456':'iukcy','\\\\u0406':'Iukcy','\\\\u0457':'yicy','\\\\u0407':'YIcy','\\\\u0439':'jcy','\\\\u0419':'Jcy','\\\\u0458':'jsercy','\\\\u0408':'Jsercy','\\\\u043A':'kcy','\\\\u041A':'Kcy','\\\\u045C':'kjcy','\\\\u040C':'KJcy','\\\\u043B':'lcy','\\\\u041B':'Lcy','\\\\u0459':'ljcy','\\\\u0409':'LJcy','\\\\u043C':'mcy','\\\\u041C':'Mcy','\\\\u043D':'ncy','\\\\u041D':'Ncy','\\\\u045A':'njcy','\\\\u040A':'NJcy','\\\\u043E':'ocy','\\\\u041E':'Ocy','\\\\u043F':'pcy','\\\\u041F':'Pcy','\\\\u0440':'rcy','\\\\u0420':'Rcy','\\\\u0441':'scy','\\\\u0421':'Scy','\\\\u0442':'tcy','\\\\u0422':'Tcy','\\\\u045B':'tshcy','\\\\u040B':'TSHcy','\\\\u0443':'ucy','\\\\u0423':'Ucy','\\\\u045E':'ubrcy','\\\\u040E':'Ubrcy','\\\\u0444':'fcy','\\\\u0424':'Fcy','\\\\u0445':'khcy','\\\\u0425':'KHcy','\\\\u0446':'tscy','\\\\u0426':'TScy','\\\\u0447':'chcy','\\\\u0427':'CHcy','\\\\u045F':'dzcy','\\\\u040F':'DZcy','\\\\u0448':'shcy','\\\\u0428':'SHcy','\\\\u0449':'shchcy','\\\\u0429':'SHCHcy','\\\\u044A':'hardcy','\\\\u042A':'HARDcy','\\\\u044B':'ycy','\\\\u042B':'Ycy','\\\\u044C':'softcy','\\\\u042C':'SOFTcy','\\\\u044D':'ecy','\\\\u042D':'Ecy','\\\\u044E':'yucy','\\\\u042E':'YUcy','\\\\u044F':'yacy','\\\\u042F':'YAcy','\\\\u2135':'aleph','\\\\u2136':'beth','\\\\u2137':'gimel','\\\\u2138':'daleth'};\\n\\n\\tvar regexEscape = /[\\\"&'<>`]/g;\\n\\tvar escapeMap = {\\n\\t\\t'\\\"': '"',\\n\\t\\t'&': '&',\\n\\t\\t'\\\\'': ''',\\n\\t\\t'<': '<',\\n\\t\\t// See https://mathiasbynens.be/notes/ambiguous-ampersands: in HTML, the\\n\\t\\t// following is not strictly necessary unless it’s part of a tag or an\\n\\t\\t// unquoted attribute value. We’re only escaping it to support those\\n\\t\\t// situations, and for XML support.\\n\\t\\t'>': '>',\\n\\t\\t// In Internet Explorer ≤ 8, the backtick character can be used\\n\\t\\t// to break out of (un)quoted attribute values or HTML comments.\\n\\t\\t// See http://html5sec.org/#102, http://html5sec.org/#108, and\\n\\t\\t// http://html5sec.org/#133.\\n\\t\\t'`': '`'\\n\\t};\\n\\n\\tvar regexInvalidEntity = /&#(?:[xX][^a-fA-F0-9]|[^0-9xX])/;\\n\\tvar regexInvalidRawCodePoint = /[\\\\0-\\\\x08\\\\x0B\\\\x0E-\\\\x1F\\\\x7F-\\\\x9F\\\\uFDD0-\\\\uFDEF\\\\uFFFE\\\\uFFFF]|[\\\\uD83F\\\\uD87F\\\\uD8BF\\\\uD8FF\\\\uD93F\\\\uD97F\\\\uD9BF\\\\uD9FF\\\\uDA3F\\\\uDA7F\\\\uDABF\\\\uDAFF\\\\uDB3F\\\\uDB7F\\\\uDBBF\\\\uDBFF][\\\\uDFFE\\\\uDFFF]|[\\\\uD800-\\\\uDBFF](?![\\\\uDC00-\\\\uDFFF])|(?:[^\\\\uD800-\\\\uDBFF]|^)[\\\\uDC00-\\\\uDFFF]/;\\n\\tvar regexDecode = /&(CounterClockwiseContourIntegral|DoubleLongLeftRightArrow|ClockwiseContourIntegral|NotNestedGreaterGreater|NotSquareSupersetEqual|DiacriticalDoubleAcute|NotRightTriangleEqual|NotSucceedsSlantEqual|NotPrecedesSlantEqual|CloseCurlyDoubleQuote|NegativeVeryThinSpace|DoubleContourIntegral|FilledVerySmallSquare|CapitalDifferentialD|OpenCurlyDoubleQuote|EmptyVerySmallSquare|NestedGreaterGreater|DoubleLongRightArrow|NotLeftTriangleEqual|NotGreaterSlantEqual|ReverseUpEquilibrium|DoubleLeftRightArrow|NotSquareSubsetEqual|NotDoubleVerticalBar|RightArrowLeftArrow|NotGreaterFullEqual|NotRightTriangleBar|SquareSupersetEqual|DownLeftRightVector|DoubleLongLeftArrow|leftrightsquigarrow|LeftArrowRightArrow|NegativeMediumSpace|blacktriangleright|RightDownVectorBar|PrecedesSlantEqual|RightDoubleBracket|SucceedsSlantEqual|NotLeftTriangleBar|RightTriangleEqual|SquareIntersection|RightDownTeeVector|ReverseEquilibrium|NegativeThickSpace|longleftrightarrow|Longleftrightarrow|LongLeftRightArrow|DownRightTeeVector|DownRightVectorBar|GreaterSlantEqual|SquareSubsetEqual|LeftDownVectorBar|LeftDoubleBracket|VerticalSeparator|rightleftharpoons|NotGreaterGreater|NotSquareSuperset|blacktriangleleft|blacktriangledown|NegativeThinSpace|LeftDownTeeVector|NotLessSlantEqual|leftrightharpoons|DoubleUpDownArrow|DoubleVerticalBar|LeftTriangleEqual|FilledSmallSquare|twoheadrightarrow|NotNestedLessLess|DownLeftTeeVector|DownLeftVectorBar|RightAngleBracket|NotTildeFullEqual|NotReverseElement|RightUpDownVector|DiacriticalTilde|NotSucceedsTilde|circlearrowright|NotPrecedesEqual|rightharpoondown|DoubleRightArrow|NotSucceedsEqual|NonBreakingSpace|NotRightTriangle|LessEqualGreater|RightUpTeeVector|LeftAngleBracket|GreaterFullEqual|DownArrowUpArrow|RightUpVectorBar|twoheadleftarrow|GreaterEqualLess|downharpoonright|RightTriangleBar|ntrianglerighteq|NotSupersetEqual|LeftUpDownVector|DiacriticalAcute|rightrightarrows|vartriangleright|UpArrowDownArrow|DiacriticalGrave|UnderParenthesis|EmptySmallSquare|LeftUpVectorBar|leftrightarrows|DownRightVector|downharpoonleft|trianglerighteq|ShortRightArrow|OverParenthesis|DoubleLeftArrow|DoubleDownArrow|NotSquareSubset|bigtriangledown|ntrianglelefteq|UpperRightArrow|curvearrowright|vartriangleleft|NotLeftTriangle|nleftrightarrow|LowerRightArrow|NotHumpDownHump|NotGreaterTilde|rightthreetimes|LeftUpTeeVector|NotGreaterEqual|straightepsilon|LeftTriangleBar|rightsquigarrow|ContourIntegral|rightleftarrows|CloseCurlyQuote|RightDownVector|LeftRightVector|nLeftrightarrow|leftharpoondown|circlearrowleft|SquareSuperset|OpenCurlyQuote|hookrightarrow|HorizontalLine|DiacriticalDot|NotLessGreater|ntriangleright|DoubleRightTee|InvisibleComma|InvisibleTimes|LowerLeftArrow|DownLeftVector|NotSubsetEqual|curvearrowleft|trianglelefteq|NotVerticalBar|TildeFullEqual|downdownarrows|NotGreaterLess|RightTeeVector|ZeroWidthSpace|looparrowright|LongRightArrow|doublebarwedge|ShortLeftArrow|ShortDownArrow|RightVectorBar|GreaterGreater|ReverseElement|rightharpoonup|LessSlantEqual|leftthreetimes|upharpoonright|rightarrowtail|LeftDownVector|Longrightarrow|NestedLessLess|UpperLeftArrow|nshortparallel|leftleftarrows|leftrightarrow|Leftrightarrow|LeftRightArrow|longrightarrow|upharpoonleft|RightArrowBar|ApplyFunction|LeftTeeVector|leftarrowtail|NotEqualTilde|varsubsetneqq|varsupsetneqq|RightTeeArrow|SucceedsEqual|SucceedsTilde|LeftVectorBar|SupersetEqual|hookleftarrow|DifferentialD|VerticalTilde|VeryThinSpace|blacktriangle|bigtriangleup|LessFullEqual|divideontimes|leftharpoonup|UpEquilibrium|ntriangleleft|RightTriangle|measuredangle|shortparallel|longleftarrow|Longleftarrow|LongLeftArrow|DoubleLeftTee|Poincareplane|PrecedesEqual|triangleright|DoubleUpArrow|RightUpVector|fallingdotseq|looparrowleft|PrecedesTilde|NotTildeEqual|NotTildeTilde|smallsetminus|Proportional|triangleleft|triangledown|UnderBracket|NotHumpEqual|exponentiale|ExponentialE|NotLessTilde|HilbertSpace|RightCeiling|blacklozenge|varsupsetneq|HumpDownHump|GreaterEqual|VerticalLine|LeftTeeArrow|NotLessEqual|DownTeeArrow|LeftTriangle|varsubsetneq|Intersection|NotCongruent|DownArrowBar|LeftUpVector|LeftArrowBar|risingdotseq|GreaterTilde|RoundImplies|SquareSubset|ShortUpArrow|NotSuperset|quaternions|precnapprox|backepsilon|preccurlyeq|OverBracket|blacksquare|MediumSpace|VerticalBar|circledcirc|circleddash|CircleMinus|CircleTimes|LessGreater|curlyeqprec|curlyeqsucc|diamondsuit|UpDownArrow|Updownarrow|RuleDelayed|Rrightarrow|updownarrow|RightVector|nRightarrow|nrightarrow|eqslantless|LeftCeiling|Equilibrium|SmallCircle|expectation|NotSucceeds|thickapprox|GreaterLess|SquareUnion|NotPrecedes|NotLessLess|straightphi|succnapprox|succcurlyeq|SubsetEqual|sqsupseteq|Proportion|Laplacetrf|ImaginaryI|supsetneqq|NotGreater|gtreqqless|NotElement|ThickSpace|TildeEqual|TildeTilde|Fouriertrf|rmoustache|EqualTilde|eqslantgtr|UnderBrace|LeftVector|UpArrowBar|nLeftarrow|nsubseteqq|subsetneqq|nsupseteqq|nleftarrow|succapprox|lessapprox|UpTeeArrow|upuparrows|curlywedge|lesseqqgtr|varepsilon|varnothing|RightFloor|complement|CirclePlus|sqsubseteq|Lleftarrow|circledast|RightArrow|Rightarrow|rightarrow|lmoustache|Bernoullis|precapprox|mapstoleft|mapstodown|longmapsto|dotsquare|downarrow|DoubleDot|nsubseteq|supsetneq|leftarrow|nsupseteq|subsetneq|ThinSpace|ngeqslant|subseteqq|HumpEqual|NotSubset|triangleq|NotCupCap|lesseqgtr|heartsuit|TripleDot|Leftarrow|Coproduct|Congruent|varpropto|complexes|gvertneqq|LeftArrow|LessTilde|supseteqq|MinusPlus|CircleDot|nleqslant|NotExists|gtreqless|nparallel|UnionPlus|LeftFloor|checkmark|CenterDot|centerdot|Mellintrf|gtrapprox|bigotimes|OverBrace|spadesuit|therefore|pitchfork|rationals|PlusMinus|Backslash|Therefore|DownBreve|backsimeq|backprime|DownArrow|nshortmid|Downarrow|lvertneqq|eqvparsl|imagline|imagpart|infintie|integers|Integral|intercal|LessLess|Uarrocir|intlarhk|sqsupset|angmsdaf|sqsubset|llcorner|vartheta|cupbrcap|lnapprox|Superset|SuchThat|succnsim|succneqq|angmsdag|biguplus|curlyvee|trpezium|Succeeds|NotTilde|bigwedge|angmsdah|angrtvbd|triminus|cwconint|fpartint|lrcorner|smeparsl|subseteq|urcorner|lurdshar|laemptyv|DDotrahd|approxeq|ldrushar|awconint|mapstoup|backcong|shortmid|triangle|geqslant|gesdotol|timesbar|circledR|circledS|setminus|multimap|naturals|scpolint|ncongdot|RightTee|boxminus|gnapprox|boxtimes|andslope|thicksim|angmsdaa|varsigma|cirfnint|rtriltri|angmsdab|rppolint|angmsdac|barwedge|drbkarow|clubsuit|thetasym|bsolhsub|capbrcup|dzigrarr|doteqdot|DotEqual|dotminus|UnderBar|NotEqual|realpart|otimesas|ulcorner|hksearow|hkswarow|parallel|PartialD|elinters|emptyset|plusacir|bbrktbrk|angmsdad|pointint|bigoplus|angmsdae|Precedes|bigsqcup|varkappa|notindot|supseteq|precneqq|precnsim|profalar|profline|profsurf|leqslant|lesdotor|raemptyv|subplus|notnivb|notnivc|subrarr|zigrarr|vzigzag|submult|subedot|Element|between|cirscir|larrbfs|larrsim|lotimes|lbrksld|lbrkslu|lozenge|ldrdhar|dbkarow|bigcirc|epsilon|simrarr|simplus|ltquest|Epsilon|luruhar|gtquest|maltese|npolint|eqcolon|npreceq|bigodot|ddagger|gtrless|bnequiv|harrcir|ddotseq|equivDD|backsim|demptyv|nsqsube|nsqsupe|Upsilon|nsubset|upsilon|minusdu|nsucceq|swarrow|nsupset|coloneq|searrow|boxplus|napprox|natural|asympeq|alefsym|congdot|nearrow|bigstar|diamond|supplus|tritime|LeftTee|nvinfin|triplus|NewLine|nvltrie|nvrtrie|nwarrow|nexists|Diamond|ruluhar|Implies|supmult|angzarr|suplarr|suphsub|questeq|because|digamma|Because|olcross|bemptyv|omicron|Omicron|rotimes|NoBreak|intprod|angrtvb|orderof|uwangle|suphsol|lesdoto|orslope|DownTee|realine|cudarrl|rdldhar|OverBar|supedot|lessdot|supdsub|topfork|succsim|rbrkslu|rbrksld|pertenk|cudarrr|isindot|planckh|lessgtr|pluscir|gesdoto|plussim|plustwo|lesssim|cularrp|rarrsim|Cayleys|notinva|notinvb|notinvc|UpArrow|Uparrow|uparrow|NotLess|dwangle|precsim|Product|curarrm|Cconint|dotplus|rarrbfs|ccupssm|Cedilla|cemptyv|notniva|quatint|frac35|frac38|frac45|frac56|frac58|frac78|tridot|xoplus|gacute|gammad|Gammad|lfisht|lfloor|bigcup|sqsupe|gbreve|Gbreve|lharul|sqsube|sqcups|Gcedil|apacir|llhard|lmidot|Lmidot|lmoust|andand|sqcaps|approx|Abreve|spades|circeq|tprime|divide|topcir|Assign|topbot|gesdot|divonx|xuplus|timesd|gesles|atilde|solbar|SOFTcy|loplus|timesb|lowast|lowbar|dlcorn|dlcrop|softcy|dollar|lparlt|thksim|lrhard|Atilde|lsaquo|smashp|bigvee|thinsp|wreath|bkarow|lsquor|lstrok|Lstrok|lthree|ltimes|ltlarr|DotDot|simdot|ltrPar|weierp|xsqcup|angmsd|sigmav|sigmaf|zeetrf|Zcaron|zcaron|mapsto|vsupne|thetav|cirmid|marker|mcomma|Zacute|vsubnE|there4|gtlPar|vsubne|bottom|gtrarr|SHCHcy|shchcy|midast|midcir|middot|minusb|minusd|gtrdot|bowtie|sfrown|mnplus|models|colone|seswar|Colone|mstpos|searhk|gtrsim|nacute|Nacute|boxbox|telrec|hairsp|Tcedil|nbumpe|scnsim|ncaron|Ncaron|ncedil|Ncedil|hamilt|Scedil|nearhk|hardcy|HARDcy|tcedil|Tcaron|commat|nequiv|nesear|tcaron|target|hearts|nexist|varrho|scedil|Scaron|scaron|hellip|Sacute|sacute|hercon|swnwar|compfn|rtimes|rthree|rsquor|rsaquo|zacute|wedgeq|homtht|barvee|barwed|Barwed|rpargt|horbar|conint|swarhk|roplus|nltrie|hslash|hstrok|Hstrok|rmoust|Conint|bprime|hybull|hyphen|iacute|Iacute|supsup|supsub|supsim|varphi|coprod|brvbar|agrave|Supset|supset|igrave|Igrave|notinE|Agrave|iiiint|iinfin|copysr|wedbar|Verbar|vangrt|becaus|incare|verbar|inodot|bullet|drcorn|intcal|drcrop|cularr|vellip|Utilde|bumpeq|cupcap|dstrok|Dstrok|CupCap|cupcup|cupdot|eacute|Eacute|supdot|iquest|easter|ecaron|Ecaron|ecolon|isinsv|utilde|itilde|Itilde|curarr|succeq|Bumpeq|cacute|ulcrop|nparsl|Cacute|nprcue|egrave|Egrave|nrarrc|nrarrw|subsup|subsub|nrtrie|jsercy|nsccue|Jsercy|kappav|kcedil|Kcedil|subsim|ulcorn|nsimeq|egsdot|veebar|kgreen|capand|elsdot|Subset|subset|curren|aacute|lacute|Lacute|emptyv|ntilde|Ntilde|lagran|lambda|Lambda|capcap|Ugrave|langle|subdot|emsp13|numero|emsp14|nvdash|nvDash|nVdash|nVDash|ugrave|ufisht|nvHarr|larrfs|nvlArr|larrhk|larrlp|larrpl|nvrArr|Udblac|nwarhk|larrtl|nwnear|oacute|Oacute|latail|lAtail|sstarf|lbrace|odblac|Odblac|lbrack|udblac|odsold|eparsl|lcaron|Lcaron|ograve|Ograve|lcedil|Lcedil|Aacute|ssmile|ssetmn|squarf|ldquor|capcup|ominus|cylcty|rharul|eqcirc|dagger|rfloor|rfisht|Dagger|daleth|equals|origof|capdot|equest|dcaron|Dcaron|rdquor|oslash|Oslash|otilde|Otilde|otimes|Otimes|urcrop|Ubreve|ubreve|Yacute|Uacute|uacute|Rcedil|rcedil|urcorn|parsim|Rcaron|Vdashl|rcaron|Tstrok|percnt|period|permil|Exists|yacute|rbrack|rbrace|phmmat|ccaron|Ccaron|planck|ccedil|plankv|tstrok|female|plusdo|plusdu|ffilig|plusmn|ffllig|Ccedil|rAtail|dfisht|bernou|ratail|Rarrtl|rarrtl|angsph|rarrpl|rarrlp|rarrhk|xwedge|xotime|forall|ForAll|Vvdash|vsupnE|preceq|bigcap|frac12|frac13|frac14|primes|rarrfs|prnsim|frac15|Square|frac16|square|lesdot|frac18|frac23|propto|prurel|rarrap|rangle|puncsp|frac25|Racute|qprime|racute|lesges|frac34|abreve|AElig|eqsim|utdot|setmn|urtri|Equal|Uring|seArr|uring|searr|dashv|Dashv|mumap|nabla|iogon|Iogon|sdote|sdotb|scsim|napid|napos|equiv|natur|Acirc|dblac|erarr|nbump|iprod|erDot|ucirc|awint|esdot|angrt|ncong|isinE|scnap|Scirc|scirc|ndash|isins|Ubrcy|nearr|neArr|isinv|nedot|ubrcy|acute|Ycirc|iukcy|Iukcy|xutri|nesim|caret|jcirc|Jcirc|caron|twixt|ddarr|sccue|exist|jmath|sbquo|ngeqq|angst|ccaps|lceil|ngsim|UpTee|delta|Delta|rtrif|nharr|nhArr|nhpar|rtrie|jukcy|Jukcy|kappa|rsquo|Kappa|nlarr|nlArr|TSHcy|rrarr|aogon|Aogon|fflig|xrarr|tshcy|ccirc|nleqq|filig|upsih|nless|dharl|nlsim|fjlig|ropar|nltri|dharr|robrk|roarr|fllig|fltns|roang|rnmid|subnE|subne|lAarr|trisb|Ccirc|acirc|ccups|blank|VDash|forkv|Vdash|langd|cedil|blk12|blk14|laquo|strns|diams|notin|vDash|larrb|blk34|block|disin|uplus|vdash|vBarv|aelig|starf|Wedge|check|xrArr|lates|lbarr|lBarr|notni|lbbrk|bcong|frasl|lbrke|frown|vrtri|vprop|vnsup|gamma|Gamma|wedge|xodot|bdquo|srarr|doteq|ldquo|boxdl|boxdL|gcirc|Gcirc|boxDl|boxDL|boxdr|boxdR|boxDr|TRADE|trade|rlhar|boxDR|vnsub|npart|vltri|rlarr|boxhd|boxhD|nprec|gescc|nrarr|nrArr|boxHd|boxHD|boxhu|boxhU|nrtri|boxHu|clubs|boxHU|times|colon|Colon|gimel|xlArr|Tilde|nsime|tilde|nsmid|nspar|THORN|thorn|xlarr|nsube|nsubE|thkap|xhArr|comma|nsucc|boxul|boxuL|nsupe|nsupE|gneqq|gnsim|boxUl|boxUL|grave|boxur|boxuR|boxUr|boxUR|lescc|angle|bepsi|boxvh|varpi|boxvH|numsp|Theta|gsime|gsiml|theta|boxVh|boxVH|boxvl|gtcir|gtdot|boxvL|boxVl|boxVL|crarr|cross|Cross|nvsim|boxvr|nwarr|nwArr|sqsup|dtdot|Uogon|lhard|lharu|dtrif|ocirc|Ocirc|lhblk|duarr|odash|sqsub|Hacek|sqcup|llarr|duhar|oelig|OElig|ofcir|boxvR|uogon|lltri|boxVr|csube|uuarr|ohbar|csupe|ctdot|olarr|olcir|harrw|oline|sqcap|omacr|Omacr|omega|Omega|boxVR|aleph|lneqq|lnsim|loang|loarr|rharu|lobrk|hcirc|operp|oplus|rhard|Hcirc|orarr|Union|order|ecirc|Ecirc|cuepr|szlig|cuesc|breve|reals|eDDot|Breve|hoarr|lopar|utrif|rdquo|Umacr|umacr|efDot|swArr|ultri|alpha|rceil|ovbar|swarr|Wcirc|wcirc|smtes|smile|bsemi|lrarr|aring|parsl|lrhar|bsime|uhblk|lrtri|cupor|Aring|uharr|uharl|slarr|rbrke|bsolb|lsime|rbbrk|RBarr|lsimg|phone|rBarr|rbarr|icirc|lsquo|Icirc|emacr|Emacr|ratio|simne|plusb|simlE|simgE|simeq|pluse|ltcir|ltdot|empty|xharr|xdtri|iexcl|Alpha|ltrie|rarrw|pound|ltrif|xcirc|bumpe|prcue|bumpE|asymp|amacr|cuvee|Sigma|sigma|iiint|udhar|iiota|ijlig|IJlig|supnE|imacr|Imacr|prime|Prime|image|prnap|eogon|Eogon|rarrc|mdash|mDDot|cuwed|imath|supne|imped|Amacr|udarr|prsim|micro|rarrb|cwint|raquo|infin|eplus|range|rangd|Ucirc|radic|minus|amalg|veeeq|rAarr|epsiv|ycirc|quest|sharp|quot|zwnj|Qscr|race|qscr|Qopf|qopf|qint|rang|Rang|Zscr|zscr|Zopf|zopf|rarr|rArr|Rarr|Pscr|pscr|prop|prod|prnE|prec|ZHcy|zhcy|prap|Zeta|zeta|Popf|popf|Zdot|plus|zdot|Yuml|yuml|phiv|YUcy|yucy|Yscr|yscr|perp|Yopf|yopf|part|para|YIcy|Ouml|rcub|yicy|YAcy|rdca|ouml|osol|Oscr|rdsh|yacy|real|oscr|xvee|andd|rect|andv|Xscr|oror|ordm|ordf|xscr|ange|aopf|Aopf|rHar|Xopf|opar|Oopf|xopf|xnis|rhov|oopf|omid|xmap|oint|apid|apos|ogon|ascr|Ascr|odot|odiv|xcup|xcap|ocir|oast|nvlt|nvle|nvgt|nvge|nvap|Wscr|wscr|auml|ntlg|ntgl|nsup|nsub|nsim|Nscr|nscr|nsce|Wopf|ring|npre|wopf|npar|Auml|Barv|bbrk|Nopf|nopf|nmid|nLtv|beta|ropf|Ropf|Beta|beth|nles|rpar|nleq|bnot|bNot|nldr|NJcy|rscr|Rscr|Vscr|vscr|rsqb|njcy|bopf|nisd|Bopf|rtri|Vopf|nGtv|ngtr|vopf|boxh|boxH|boxv|nges|ngeq|boxV|bscr|scap|Bscr|bsim|Vert|vert|bsol|bull|bump|caps|cdot|ncup|scnE|ncap|nbsp|napE|Cdot|cent|sdot|Vbar|nang|vBar|chcy|Mscr|mscr|sect|semi|CHcy|Mopf|mopf|sext|circ|cire|mldr|mlcp|cirE|comp|shcy|SHcy|vArr|varr|cong|copf|Copf|copy|COPY|malt|male|macr|lvnE|cscr|ltri|sime|ltcc|simg|Cscr|siml|csub|Uuml|lsqb|lsim|uuml|csup|Lscr|lscr|utri|smid|lpar|cups|smte|lozf|darr|Lopf|Uscr|solb|lopf|sopf|Sopf|lneq|uscr|spar|dArr|lnap|Darr|dash|Sqrt|LJcy|ljcy|lHar|dHar|Upsi|upsi|diam|lesg|djcy|DJcy|leqq|dopf|Dopf|dscr|Dscr|dscy|ldsh|ldca|squf|DScy|sscr|Sscr|dsol|lcub|late|star|Star|Uopf|Larr|lArr|larr|uopf|dtri|dzcy|sube|subE|Lang|lang|Kscr|kscr|Kopf|kopf|KJcy|kjcy|KHcy|khcy|DZcy|ecir|edot|eDot|Jscr|jscr|succ|Jopf|jopf|Edot|uHar|emsp|ensp|Iuml|iuml|eopf|isin|Iscr|iscr|Eopf|epar|sung|epsi|escr|sup1|sup2|sup3|Iota|iota|supe|supE|Iopf|iopf|IOcy|iocy|Escr|esim|Esim|imof|Uarr|QUOT|uArr|uarr|euml|IEcy|iecy|Idot|Euml|euro|excl|Hscr|hscr|Hopf|hopf|TScy|tscy|Tscr|hbar|tscr|flat|tbrk|fnof|hArr|harr|half|fopf|Fopf|tdot|gvnE|fork|trie|gtcc|fscr|Fscr|gdot|gsim|Gscr|gscr|Gopf|gopf|gneq|Gdot|tosa|gnap|Topf|topf|geqq|toea|GJcy|gjcy|tint|gesl|mid|Sfr|ggg|top|ges|gla|glE|glj|geq|gne|gEl|gel|gnE|Gcy|gcy|gap|Tfr|tfr|Tcy|tcy|Hat|Tau|Ffr|tau|Tab|hfr|Hfr|ffr|Fcy|fcy|icy|Icy|iff|ETH|eth|ifr|Ifr|Eta|eta|int|Int|Sup|sup|ucy|Ucy|Sum|sum|jcy|ENG|ufr|Ufr|eng|Jcy|jfr|els|ell|egs|Efr|efr|Jfr|uml|kcy|Kcy|Ecy|ecy|kfr|Kfr|lap|Sub|sub|lat|lcy|Lcy|leg|Dot|dot|lEg|leq|les|squ|div|die|lfr|Lfr|lgE|Dfr|dfr|Del|deg|Dcy|dcy|lne|lnE|sol|loz|smt|Cup|lrm|cup|lsh|Lsh|sim|shy|map|Map|mcy|Mcy|mfr|Mfr|mho|gfr|Gfr|sfr|cir|Chi|chi|nap|Cfr|vcy|Vcy|cfr|Scy|scy|ncy|Ncy|vee|Vee|Cap|cap|nfr|scE|sce|Nfr|nge|ngE|nGg|vfr|Vfr|ngt|bot|nGt|nis|niv|Rsh|rsh|nle|nlE|bne|Bfr|bfr|nLl|nlt|nLt|Bcy|bcy|not|Not|rlm|wfr|Wfr|npr|nsc|num|ocy|ast|Ocy|ofr|xfr|Xfr|Ofr|ogt|ohm|apE|olt|Rho|ape|rho|Rfr|rfr|ord|REG|ang|reg|orv|And|and|AMP|Rcy|amp|Afr|ycy|Ycy|yen|yfr|Yfr|rcy|par|pcy|Pcy|pfr|Pfr|phi|Phi|afr|Acy|acy|zcy|Zcy|piv|acE|acd|zfr|Zfr|pre|prE|psi|Psi|qfr|Qfr|zwj|Or|ge|Gg|gt|gg|el|oS|lt|Lt|LT|Re|lg|gl|eg|ne|Im|it|le|DD|wp|wr|nu|Nu|dd|lE|Sc|sc|pi|Pi|ee|af|ll|Ll|rx|gE|xi|pm|Xi|ic|pr|Pr|in|ni|mp|mu|ac|Mu|or|ap|Gt|GT|ii);|&(Aacute|Agrave|Atilde|Ccedil|Eacute|Egrave|Iacute|Igrave|Ntilde|Oacute|Ograve|Oslash|Otilde|Uacute|Ugrave|Yacute|aacute|agrave|atilde|brvbar|ccedil|curren|divide|eacute|egrave|frac12|frac14|frac34|iacute|igrave|iquest|middot|ntilde|oacute|ograve|oslash|otilde|plusmn|uacute|ugrave|yacute|AElig|Acirc|Aring|Ecirc|Icirc|Ocirc|THORN|Ucirc|acirc|acute|aelig|aring|cedil|ecirc|icirc|iexcl|laquo|micro|ocirc|pound|raquo|szlig|thorn|times|ucirc|Auml|COPY|Euml|Iuml|Ouml|QUOT|Uuml|auml|cent|copy|euml|iuml|macr|nbsp|ordf|ordm|ouml|para|quot|sect|sup1|sup2|sup3|uuml|yuml|AMP|ETH|REG|amp|deg|eth|not|reg|shy|uml|yen|GT|LT|gt|lt)(?!;)([=a-zA-Z0-9]?)|&#([0-9]+)(;?)|&#[xX]([a-fA-F0-9]+)(;?)|&([0-9a-zA-Z]+)/g;\\n\\tvar decodeMap = {'aacute':'\\\\xE1','Aacute':'\\\\xC1','abreve':'\\\\u0103','Abreve':'\\\\u0102','ac':'\\\\u223E','acd':'\\\\u223F','acE':'\\\\u223E\\\\u0333','acirc':'\\\\xE2','Acirc':'\\\\xC2','acute':'\\\\xB4','acy':'\\\\u0430','Acy':'\\\\u0410','aelig':'\\\\xE6','AElig':'\\\\xC6','af':'\\\\u2061','afr':'\\\\uD835\\\\uDD1E','Afr':'\\\\uD835\\\\uDD04','agrave':'\\\\xE0','Agrave':'\\\\xC0','alefsym':'\\\\u2135','aleph':'\\\\u2135','alpha':'\\\\u03B1','Alpha':'\\\\u0391','amacr':'\\\\u0101','Amacr':'\\\\u0100','amalg':'\\\\u2A3F','amp':'&','AMP':'&','and':'\\\\u2227','And':'\\\\u2A53','andand':'\\\\u2A55','andd':'\\\\u2A5C','andslope':'\\\\u2A58','andv':'\\\\u2A5A','ang':'\\\\u2220','ange':'\\\\u29A4','angle':'\\\\u2220','angmsd':'\\\\u2221','angmsdaa':'\\\\u29A8','angmsdab':'\\\\u29A9','angmsdac':'\\\\u29AA','angmsdad':'\\\\u29AB','angmsdae':'\\\\u29AC','angmsdaf':'\\\\u29AD','angmsdag':'\\\\u29AE','angmsdah':'\\\\u29AF','angrt':'\\\\u221F','angrtvb':'\\\\u22BE','angrtvbd':'\\\\u299D','angsph':'\\\\u2222','angst':'\\\\xC5','angzarr':'\\\\u237C','aogon':'\\\\u0105','Aogon':'\\\\u0104','aopf':'\\\\uD835\\\\uDD52','Aopf':'\\\\uD835\\\\uDD38','ap':'\\\\u2248','apacir':'\\\\u2A6F','ape':'\\\\u224A','apE':'\\\\u2A70','apid':'\\\\u224B','apos':'\\\\'','ApplyFunction':'\\\\u2061','approx':'\\\\u2248','approxeq':'\\\\u224A','aring':'\\\\xE5','Aring':'\\\\xC5','ascr':'\\\\uD835\\\\uDCB6','Ascr':'\\\\uD835\\\\uDC9C','Assign':'\\\\u2254','ast':'*','asymp':'\\\\u2248','asympeq':'\\\\u224D','atilde':'\\\\xE3','Atilde':'\\\\xC3','auml':'\\\\xE4','Auml':'\\\\xC4','awconint':'\\\\u2233','awint':'\\\\u2A11','backcong':'\\\\u224C','backepsilon':'\\\\u03F6','backprime':'\\\\u2035','backsim':'\\\\u223D','backsimeq':'\\\\u22CD','Backslash':'\\\\u2216','Barv':'\\\\u2AE7','barvee':'\\\\u22BD','barwed':'\\\\u2305','Barwed':'\\\\u2306','barwedge':'\\\\u2305','bbrk':'\\\\u23B5','bbrktbrk':'\\\\u23B6','bcong':'\\\\u224C','bcy':'\\\\u0431','Bcy':'\\\\u0411','bdquo':'\\\\u201E','becaus':'\\\\u2235','because':'\\\\u2235','Because':'\\\\u2235','bemptyv':'\\\\u29B0','bepsi':'\\\\u03F6','bernou':'\\\\u212C','Bernoullis':'\\\\u212C','beta':'\\\\u03B2','Beta':'\\\\u0392','beth':'\\\\u2136','between':'\\\\u226C','bfr':'\\\\uD835\\\\uDD1F','Bfr':'\\\\uD835\\\\uDD05','bigcap':'\\\\u22C2','bigcirc':'\\\\u25EF','bigcup':'\\\\u22C3','bigodot':'\\\\u2A00','bigoplus':'\\\\u2A01','bigotimes':'\\\\u2A02','bigsqcup':'\\\\u2A06','bigstar':'\\\\u2605','bigtriangledown':'\\\\u25BD','bigtriangleup':'\\\\u25B3','biguplus':'\\\\u2A04','bigvee':'\\\\u22C1','bigwedge':'\\\\u22C0','bkarow':'\\\\u290D','blacklozenge':'\\\\u29EB','blacksquare':'\\\\u25AA','blacktriangle':'\\\\u25B4','blacktriangledown':'\\\\u25BE','blacktriangleleft':'\\\\u25C2','blacktriangleright':'\\\\u25B8','blank':'\\\\u2423','blk12':'\\\\u2592','blk14':'\\\\u2591','blk34':'\\\\u2593','block':'\\\\u2588','bne':'=\\\\u20E5','bnequiv':'\\\\u2261\\\\u20E5','bnot':'\\\\u2310','bNot':'\\\\u2AED','bopf':'\\\\uD835\\\\uDD53','Bopf':'\\\\uD835\\\\uDD39','bot':'\\\\u22A5','bottom':'\\\\u22A5','bowtie':'\\\\u22C8','boxbox':'\\\\u29C9','boxdl':'\\\\u2510','boxdL':'\\\\u2555','boxDl':'\\\\u2556','boxDL':'\\\\u2557','boxdr':'\\\\u250C','boxdR':'\\\\u2552','boxDr':'\\\\u2553','boxDR':'\\\\u2554','boxh':'\\\\u2500','boxH':'\\\\u2550','boxhd':'\\\\u252C','boxhD':'\\\\u2565','boxHd':'\\\\u2564','boxHD':'\\\\u2566','boxhu':'\\\\u2534','boxhU':'\\\\u2568','boxHu':'\\\\u2567','boxHU':'\\\\u2569','boxminus':'\\\\u229F','boxplus':'\\\\u229E','boxtimes':'\\\\u22A0','boxul':'\\\\u2518','boxuL':'\\\\u255B','boxUl':'\\\\u255C','boxUL':'\\\\u255D','boxur':'\\\\u2514','boxuR':'\\\\u2558','boxUr':'\\\\u2559','boxUR':'\\\\u255A','boxv':'\\\\u2502','boxV':'\\\\u2551','boxvh':'\\\\u253C','boxvH':'\\\\u256A','boxVh':'\\\\u256B','boxVH':'\\\\u256C','boxvl':'\\\\u2524','boxvL':'\\\\u2561','boxVl':'\\\\u2562','boxVL':'\\\\u2563','boxvr':'\\\\u251C','boxvR':'\\\\u255E','boxVr':'\\\\u255F','boxVR':'\\\\u2560','bprime':'\\\\u2035','breve':'\\\\u02D8','Breve':'\\\\u02D8','brvbar':'\\\\xA6','bscr':'\\\\uD835\\\\uDCB7','Bscr':'\\\\u212C','bsemi':'\\\\u204F','bsim':'\\\\u223D','bsime':'\\\\u22CD','bsol':'\\\\\\\\','bsolb':'\\\\u29C5','bsolhsub':'\\\\u27C8','bull':'\\\\u2022','bullet':'\\\\u2022','bump':'\\\\u224E','bumpe':'\\\\u224F','bumpE':'\\\\u2AAE','bumpeq':'\\\\u224F','Bumpeq':'\\\\u224E','cacute':'\\\\u0107','Cacute':'\\\\u0106','cap':'\\\\u2229','Cap':'\\\\u22D2','capand':'\\\\u2A44','capbrcup':'\\\\u2A49','capcap':'\\\\u2A4B','capcup':'\\\\u2A47','capdot':'\\\\u2A40','CapitalDifferentialD':'\\\\u2145','caps':'\\\\u2229\\\\uFE00','caret':'\\\\u2041','caron':'\\\\u02C7','Cayleys':'\\\\u212D','ccaps':'\\\\u2A4D','ccaron':'\\\\u010D','Ccaron':'\\\\u010C','ccedil':'\\\\xE7','Ccedil':'\\\\xC7','ccirc':'\\\\u0109','Ccirc':'\\\\u0108','Cconint':'\\\\u2230','ccups':'\\\\u2A4C','ccupssm':'\\\\u2A50','cdot':'\\\\u010B','Cdot':'\\\\u010A','cedil':'\\\\xB8','Cedilla':'\\\\xB8','cemptyv':'\\\\u29B2','cent':'\\\\xA2','centerdot':'\\\\xB7','CenterDot':'\\\\xB7','cfr':'\\\\uD835\\\\uDD20','Cfr':'\\\\u212D','chcy':'\\\\u0447','CHcy':'\\\\u0427','check':'\\\\u2713','checkmark':'\\\\u2713','chi':'\\\\u03C7','Chi':'\\\\u03A7','cir':'\\\\u25CB','circ':'\\\\u02C6','circeq':'\\\\u2257','circlearrowleft':'\\\\u21BA','circlearrowright':'\\\\u21BB','circledast':'\\\\u229B','circledcirc':'\\\\u229A','circleddash':'\\\\u229D','CircleDot':'\\\\u2299','circledR':'\\\\xAE','circledS':'\\\\u24C8','CircleMinus':'\\\\u2296','CirclePlus':'\\\\u2295','CircleTimes':'\\\\u2297','cire':'\\\\u2257','cirE':'\\\\u29C3','cirfnint':'\\\\u2A10','cirmid':'\\\\u2AEF','cirscir':'\\\\u29C2','ClockwiseContourIntegral':'\\\\u2232','CloseCurlyDoubleQuote':'\\\\u201D','CloseCurlyQuote':'\\\\u2019','clubs':'\\\\u2663','clubsuit':'\\\\u2663','colon':':','Colon':'\\\\u2237','colone':'\\\\u2254','Colone':'\\\\u2A74','coloneq':'\\\\u2254','comma':',','commat':'@','comp':'\\\\u2201','compfn':'\\\\u2218','complement':'\\\\u2201','complexes':'\\\\u2102','cong':'\\\\u2245','congdot':'\\\\u2A6D','Congruent':'\\\\u2261','conint':'\\\\u222E','Conint':'\\\\u222F','ContourIntegral':'\\\\u222E','copf':'\\\\uD835\\\\uDD54','Copf':'\\\\u2102','coprod':'\\\\u2210','Coproduct':'\\\\u2210','copy':'\\\\xA9','COPY':'\\\\xA9','copysr':'\\\\u2117','CounterClockwiseContourIntegral':'\\\\u2233','crarr':'\\\\u21B5','cross':'\\\\u2717','Cross':'\\\\u2A2F','cscr':'\\\\uD835\\\\uDCB8','Cscr':'\\\\uD835\\\\uDC9E','csub':'\\\\u2ACF','csube':'\\\\u2AD1','csup':'\\\\u2AD0','csupe':'\\\\u2AD2','ctdot':'\\\\u22EF','cudarrl':'\\\\u2938','cudarrr':'\\\\u2935','cuepr':'\\\\u22DE','cuesc':'\\\\u22DF','cularr':'\\\\u21B6','cularrp':'\\\\u293D','cup':'\\\\u222A','Cup':'\\\\u22D3','cupbrcap':'\\\\u2A48','cupcap':'\\\\u2A46','CupCap':'\\\\u224D','cupcup':'\\\\u2A4A','cupdot':'\\\\u228D','cupor':'\\\\u2A45','cups':'\\\\u222A\\\\uFE00','curarr':'\\\\u21B7','curarrm':'\\\\u293C','curlyeqprec':'\\\\u22DE','curlyeqsucc':'\\\\u22DF','curlyvee':'\\\\u22CE','curlywedge':'\\\\u22CF','curren':'\\\\xA4','curvearrowleft':'\\\\u21B6','curvearrowright':'\\\\u21B7','cuvee':'\\\\u22CE','cuwed':'\\\\u22CF','cwconint':'\\\\u2232','cwint':'\\\\u2231','cylcty':'\\\\u232D','dagger':'\\\\u2020','Dagger':'\\\\u2021','daleth':'\\\\u2138','darr':'\\\\u2193','dArr':'\\\\u21D3','Darr':'\\\\u21A1','dash':'\\\\u2010','dashv':'\\\\u22A3','Dashv':'\\\\u2AE4','dbkarow':'\\\\u290F','dblac':'\\\\u02DD','dcaron':'\\\\u010F','Dcaron':'\\\\u010E','dcy':'\\\\u0434','Dcy':'\\\\u0414','dd':'\\\\u2146','DD':'\\\\u2145','ddagger':'\\\\u2021','ddarr':'\\\\u21CA','DDotrahd':'\\\\u2911','ddotseq':'\\\\u2A77','deg':'\\\\xB0','Del':'\\\\u2207','delta':'\\\\u03B4','Delta':'\\\\u0394','demptyv':'\\\\u29B1','dfisht':'\\\\u297F','dfr':'\\\\uD835\\\\uDD21','Dfr':'\\\\uD835\\\\uDD07','dHar':'\\\\u2965','dharl':'\\\\u21C3','dharr':'\\\\u21C2','DiacriticalAcute':'\\\\xB4','DiacriticalDot':'\\\\u02D9','DiacriticalDoubleAcute':'\\\\u02DD','DiacriticalGrave':'`','DiacriticalTilde':'\\\\u02DC','diam':'\\\\u22C4','diamond':'\\\\u22C4','Diamond':'\\\\u22C4','diamondsuit':'\\\\u2666','diams':'\\\\u2666','die':'\\\\xA8','DifferentialD':'\\\\u2146','digamma':'\\\\u03DD','disin':'\\\\u22F2','div':'\\\\xF7','divide':'\\\\xF7','divideontimes':'\\\\u22C7','divonx':'\\\\u22C7','djcy':'\\\\u0452','DJcy':'\\\\u0402','dlcorn':'\\\\u231E','dlcrop':'\\\\u230D','dollar':'$','dopf':'\\\\uD835\\\\uDD55','Dopf':'\\\\uD835\\\\uDD3B','dot':'\\\\u02D9','Dot':'\\\\xA8','DotDot':'\\\\u20DC','doteq':'\\\\u2250','doteqdot':'\\\\u2251','DotEqual':'\\\\u2250','dotminus':'\\\\u2238','dotplus':'\\\\u2214','dotsquare':'\\\\u22A1','doublebarwedge':'\\\\u2306','DoubleContourIntegral':'\\\\u222F','DoubleDot':'\\\\xA8','DoubleDownArrow':'\\\\u21D3','DoubleLeftArrow':'\\\\u21D0','DoubleLeftRightArrow':'\\\\u21D4','DoubleLeftTee':'\\\\u2AE4','DoubleLongLeftArrow':'\\\\u27F8','DoubleLongLeftRightArrow':'\\\\u27FA','DoubleLongRightArrow':'\\\\u27F9','DoubleRightArrow':'\\\\u21D2','DoubleRightTee':'\\\\u22A8','DoubleUpArrow':'\\\\u21D1','DoubleUpDownArrow':'\\\\u21D5','DoubleVerticalBar':'\\\\u2225','downarrow':'\\\\u2193','Downarrow':'\\\\u21D3','DownArrow':'\\\\u2193','DownArrowBar':'\\\\u2913','DownArrowUpArrow':'\\\\u21F5','DownBreve':'\\\\u0311','downdownarrows':'\\\\u21CA','downharpoonleft':'\\\\u21C3','downharpoonright':'\\\\u21C2','DownLeftRightVector':'\\\\u2950','DownLeftTeeVector':'\\\\u295E','DownLeftVector':'\\\\u21BD','DownLeftVectorBar':'\\\\u2956','DownRightTeeVector':'\\\\u295F','DownRightVector':'\\\\u21C1','DownRightVectorBar':'\\\\u2957','DownTee':'\\\\u22A4','DownTeeArrow':'\\\\u21A7','drbkarow':'\\\\u2910','drcorn':'\\\\u231F','drcrop':'\\\\u230C','dscr':'\\\\uD835\\\\uDCB9','Dscr':'\\\\uD835\\\\uDC9F','dscy':'\\\\u0455','DScy':'\\\\u0405','dsol':'\\\\u29F6','dstrok':'\\\\u0111','Dstrok':'\\\\u0110','dtdot':'\\\\u22F1','dtri':'\\\\u25BF','dtrif':'\\\\u25BE','duarr':'\\\\u21F5','duhar':'\\\\u296F','dwangle':'\\\\u29A6','dzcy':'\\\\u045F','DZcy':'\\\\u040F','dzigrarr':'\\\\u27FF','eacute':'\\\\xE9','Eacute':'\\\\xC9','easter':'\\\\u2A6E','ecaron':'\\\\u011B','Ecaron':'\\\\u011A','ecir':'\\\\u2256','ecirc':'\\\\xEA','Ecirc':'\\\\xCA','ecolon':'\\\\u2255','ecy':'\\\\u044D','Ecy':'\\\\u042D','eDDot':'\\\\u2A77','edot':'\\\\u0117','eDot':'\\\\u2251','Edot':'\\\\u0116','ee':'\\\\u2147','efDot':'\\\\u2252','efr':'\\\\uD835\\\\uDD22','Efr':'\\\\uD835\\\\uDD08','eg':'\\\\u2A9A','egrave':'\\\\xE8','Egrave':'\\\\xC8','egs':'\\\\u2A96','egsdot':'\\\\u2A98','el':'\\\\u2A99','Element':'\\\\u2208','elinters':'\\\\u23E7','ell':'\\\\u2113','els':'\\\\u2A95','elsdot':'\\\\u2A97','emacr':'\\\\u0113','Emacr':'\\\\u0112','empty':'\\\\u2205','emptyset':'\\\\u2205','EmptySmallSquare':'\\\\u25FB','emptyv':'\\\\u2205','EmptyVerySmallSquare':'\\\\u25AB','emsp':'\\\\u2003','emsp13':'\\\\u2004','emsp14':'\\\\u2005','eng':'\\\\u014B','ENG':'\\\\u014A','ensp':'\\\\u2002','eogon':'\\\\u0119','Eogon':'\\\\u0118','eopf':'\\\\uD835\\\\uDD56','Eopf':'\\\\uD835\\\\uDD3C','epar':'\\\\u22D5','eparsl':'\\\\u29E3','eplus':'\\\\u2A71','epsi':'\\\\u03B5','epsilon':'\\\\u03B5','Epsilon':'\\\\u0395','epsiv':'\\\\u03F5','eqcirc':'\\\\u2256','eqcolon':'\\\\u2255','eqsim':'\\\\u2242','eqslantgtr':'\\\\u2A96','eqslantless':'\\\\u2A95','Equal':'\\\\u2A75','equals':'=','EqualTilde':'\\\\u2242','equest':'\\\\u225F','Equilibrium':'\\\\u21CC','equiv':'\\\\u2261','equivDD':'\\\\u2A78','eqvparsl':'\\\\u29E5','erarr':'\\\\u2971','erDot':'\\\\u2253','escr':'\\\\u212F','Escr':'\\\\u2130','esdot':'\\\\u2250','esim':'\\\\u2242','Esim':'\\\\u2A73','eta':'\\\\u03B7','Eta':'\\\\u0397','eth':'\\\\xF0','ETH':'\\\\xD0','euml':'\\\\xEB','Euml':'\\\\xCB','euro':'\\\\u20AC','excl':'!','exist':'\\\\u2203','Exists':'\\\\u2203','expectation':'\\\\u2130','exponentiale':'\\\\u2147','ExponentialE':'\\\\u2147','fallingdotseq':'\\\\u2252','fcy':'\\\\u0444','Fcy':'\\\\u0424','female':'\\\\u2640','ffilig':'\\\\uFB03','fflig':'\\\\uFB00','ffllig':'\\\\uFB04','ffr':'\\\\uD835\\\\uDD23','Ffr':'\\\\uD835\\\\uDD09','filig':'\\\\uFB01','FilledSmallSquare':'\\\\u25FC','FilledVerySmallSquare':'\\\\u25AA','fjlig':'fj','flat':'\\\\u266D','fllig':'\\\\uFB02','fltns':'\\\\u25B1','fnof':'\\\\u0192','fopf':'\\\\uD835\\\\uDD57','Fopf':'\\\\uD835\\\\uDD3D','forall':'\\\\u2200','ForAll':'\\\\u2200','fork':'\\\\u22D4','forkv':'\\\\u2AD9','Fouriertrf':'\\\\u2131','fpartint':'\\\\u2A0D','frac12':'\\\\xBD','frac13':'\\\\u2153','frac14':'\\\\xBC','frac15':'\\\\u2155','frac16':'\\\\u2159','frac18':'\\\\u215B','frac23':'\\\\u2154','frac25':'\\\\u2156','frac34':'\\\\xBE','frac35':'\\\\u2157','frac38':'\\\\u215C','frac45':'\\\\u2158','frac56':'\\\\u215A','frac58':'\\\\u215D','frac78':'\\\\u215E','frasl':'\\\\u2044','frown':'\\\\u2322','fscr':'\\\\uD835\\\\uDCBB','Fscr':'\\\\u2131','gacute':'\\\\u01F5','gamma':'\\\\u03B3','Gamma':'\\\\u0393','gammad':'\\\\u03DD','Gammad':'\\\\u03DC','gap':'\\\\u2A86','gbreve':'\\\\u011F','Gbreve':'\\\\u011E','Gcedil':'\\\\u0122','gcirc':'\\\\u011D','Gcirc':'\\\\u011C','gcy':'\\\\u0433','Gcy':'\\\\u0413','gdot':'\\\\u0121','Gdot':'\\\\u0120','ge':'\\\\u2265','gE':'\\\\u2267','gel':'\\\\u22DB','gEl':'\\\\u2A8C','geq':'\\\\u2265','geqq':'\\\\u2267','geqslant':'\\\\u2A7E','ges':'\\\\u2A7E','gescc':'\\\\u2AA9','gesdot':'\\\\u2A80','gesdoto':'\\\\u2A82','gesdotol':'\\\\u2A84','gesl':'\\\\u22DB\\\\uFE00','gesles':'\\\\u2A94','gfr':'\\\\uD835\\\\uDD24','Gfr':'\\\\uD835\\\\uDD0A','gg':'\\\\u226B','Gg':'\\\\u22D9','ggg':'\\\\u22D9','gimel':'\\\\u2137','gjcy':'\\\\u0453','GJcy':'\\\\u0403','gl':'\\\\u2277','gla':'\\\\u2AA5','glE':'\\\\u2A92','glj':'\\\\u2AA4','gnap':'\\\\u2A8A','gnapprox':'\\\\u2A8A','gne':'\\\\u2A88','gnE':'\\\\u2269','gneq':'\\\\u2A88','gneqq':'\\\\u2269','gnsim':'\\\\u22E7','gopf':'\\\\uD835\\\\uDD58','Gopf':'\\\\uD835\\\\uDD3E','grave':'`','GreaterEqual':'\\\\u2265','GreaterEqualLess':'\\\\u22DB','GreaterFullEqual':'\\\\u2267','GreaterGreater':'\\\\u2AA2','GreaterLess':'\\\\u2277','GreaterSlantEqual':'\\\\u2A7E','GreaterTilde':'\\\\u2273','gscr':'\\\\u210A','Gscr':'\\\\uD835\\\\uDCA2','gsim':'\\\\u2273','gsime':'\\\\u2A8E','gsiml':'\\\\u2A90','gt':'>','Gt':'\\\\u226B','GT':'>','gtcc':'\\\\u2AA7','gtcir':'\\\\u2A7A','gtdot':'\\\\u22D7','gtlPar':'\\\\u2995','gtquest':'\\\\u2A7C','gtrapprox':'\\\\u2A86','gtrarr':'\\\\u2978','gtrdot':'\\\\u22D7','gtreqless':'\\\\u22DB','gtreqqless':'\\\\u2A8C','gtrless':'\\\\u2277','gtrsim':'\\\\u2273','gvertneqq':'\\\\u2269\\\\uFE00','gvnE':'\\\\u2269\\\\uFE00','Hacek':'\\\\u02C7','hairsp':'\\\\u200A','half':'\\\\xBD','hamilt':'\\\\u210B','hardcy':'\\\\u044A','HARDcy':'\\\\u042A','harr':'\\\\u2194','hArr':'\\\\u21D4','harrcir':'\\\\u2948','harrw':'\\\\u21AD','Hat':'^','hbar':'\\\\u210F','hcirc':'\\\\u0125','Hcirc':'\\\\u0124','hearts':'\\\\u2665','heartsuit':'\\\\u2665','hellip':'\\\\u2026','hercon':'\\\\u22B9','hfr':'\\\\uD835\\\\uDD25','Hfr':'\\\\u210C','HilbertSpace':'\\\\u210B','hksearow':'\\\\u2925','hkswarow':'\\\\u2926','hoarr':'\\\\u21FF','homtht':'\\\\u223B','hookleftarrow':'\\\\u21A9','hookrightarrow':'\\\\u21AA','hopf':'\\\\uD835\\\\uDD59','Hopf':'\\\\u210D','horbar':'\\\\u2015','HorizontalLine':'\\\\u2500','hscr':'\\\\uD835\\\\uDCBD','Hscr':'\\\\u210B','hslash':'\\\\u210F','hstrok':'\\\\u0127','Hstrok':'\\\\u0126','HumpDownHump':'\\\\u224E','HumpEqual':'\\\\u224F','hybull':'\\\\u2043','hyphen':'\\\\u2010','iacute':'\\\\xED','Iacute':'\\\\xCD','ic':'\\\\u2063','icirc':'\\\\xEE','Icirc':'\\\\xCE','icy':'\\\\u0438','Icy':'\\\\u0418','Idot':'\\\\u0130','iecy':'\\\\u0435','IEcy':'\\\\u0415','iexcl':'\\\\xA1','iff':'\\\\u21D4','ifr':'\\\\uD835\\\\uDD26','Ifr':'\\\\u2111','igrave':'\\\\xEC','Igrave':'\\\\xCC','ii':'\\\\u2148','iiiint':'\\\\u2A0C','iiint':'\\\\u222D','iinfin':'\\\\u29DC','iiota':'\\\\u2129','ijlig':'\\\\u0133','IJlig':'\\\\u0132','Im':'\\\\u2111','imacr':'\\\\u012B','Imacr':'\\\\u012A','image':'\\\\u2111','ImaginaryI':'\\\\u2148','imagline':'\\\\u2110','imagpart':'\\\\u2111','imath':'\\\\u0131','imof':'\\\\u22B7','imped':'\\\\u01B5','Implies':'\\\\u21D2','in':'\\\\u2208','incare':'\\\\u2105','infin':'\\\\u221E','infintie':'\\\\u29DD','inodot':'\\\\u0131','int':'\\\\u222B','Int':'\\\\u222C','intcal':'\\\\u22BA','integers':'\\\\u2124','Integral':'\\\\u222B','intercal':'\\\\u22BA','Intersection':'\\\\u22C2','intlarhk':'\\\\u2A17','intprod':'\\\\u2A3C','InvisibleComma':'\\\\u2063','InvisibleTimes':'\\\\u2062','iocy':'\\\\u0451','IOcy':'\\\\u0401','iogon':'\\\\u012F','Iogon':'\\\\u012E','iopf':'\\\\uD835\\\\uDD5A','Iopf':'\\\\uD835\\\\uDD40','iota':'\\\\u03B9','Iota':'\\\\u0399','iprod':'\\\\u2A3C','iquest':'\\\\xBF','iscr':'\\\\uD835\\\\uDCBE','Iscr':'\\\\u2110','isin':'\\\\u2208','isindot':'\\\\u22F5','isinE':'\\\\u22F9','isins':'\\\\u22F4','isinsv':'\\\\u22F3','isinv':'\\\\u2208','it':'\\\\u2062','itilde':'\\\\u0129','Itilde':'\\\\u0128','iukcy':'\\\\u0456','Iukcy':'\\\\u0406','iuml':'\\\\xEF','Iuml':'\\\\xCF','jcirc':'\\\\u0135','Jcirc':'\\\\u0134','jcy':'\\\\u0439','Jcy':'\\\\u0419','jfr':'\\\\uD835\\\\uDD27','Jfr':'\\\\uD835\\\\uDD0D','jmath':'\\\\u0237','jopf':'\\\\uD835\\\\uDD5B','Jopf':'\\\\uD835\\\\uDD41','jscr':'\\\\uD835\\\\uDCBF','Jscr':'\\\\uD835\\\\uDCA5','jsercy':'\\\\u0458','Jsercy':'\\\\u0408','jukcy':'\\\\u0454','Jukcy':'\\\\u0404','kappa':'\\\\u03BA','Kappa':'\\\\u039A','kappav':'\\\\u03F0','kcedil':'\\\\u0137','Kcedil':'\\\\u0136','kcy':'\\\\u043A','Kcy':'\\\\u041A','kfr':'\\\\uD835\\\\uDD28','Kfr':'\\\\uD835\\\\uDD0E','kgreen':'\\\\u0138','khcy':'\\\\u0445','KHcy':'\\\\u0425','kjcy':'\\\\u045C','KJcy':'\\\\u040C','kopf':'\\\\uD835\\\\uDD5C','Kopf':'\\\\uD835\\\\uDD42','kscr':'\\\\uD835\\\\uDCC0','Kscr':'\\\\uD835\\\\uDCA6','lAarr':'\\\\u21DA','lacute':'\\\\u013A','Lacute':'\\\\u0139','laemptyv':'\\\\u29B4','lagran':'\\\\u2112','lambda':'\\\\u03BB','Lambda':'\\\\u039B','lang':'\\\\u27E8','Lang':'\\\\u27EA','langd':'\\\\u2991','langle':'\\\\u27E8','lap':'\\\\u2A85','Laplacetrf':'\\\\u2112','laquo':'\\\\xAB','larr':'\\\\u2190','lArr':'\\\\u21D0','Larr':'\\\\u219E','larrb':'\\\\u21E4','larrbfs':'\\\\u291F','larrfs':'\\\\u291D','larrhk':'\\\\u21A9','larrlp':'\\\\u21AB','larrpl':'\\\\u2939','larrsim':'\\\\u2973','larrtl':'\\\\u21A2','lat':'\\\\u2AAB','latail':'\\\\u2919','lAtail':'\\\\u291B','late':'\\\\u2AAD','lates':'\\\\u2AAD\\\\uFE00','lbarr':'\\\\u290C','lBarr':'\\\\u290E','lbbrk':'\\\\u2772','lbrace':'{','lbrack':'[','lbrke':'\\\\u298B','lbrksld':'\\\\u298F','lbrkslu':'\\\\u298D','lcaron':'\\\\u013E','Lcaron':'\\\\u013D','lcedil':'\\\\u013C','Lcedil':'\\\\u013B','lceil':'\\\\u2308','lcub':'{','lcy':'\\\\u043B','Lcy':'\\\\u041B','ldca':'\\\\u2936','ldquo':'\\\\u201C','ldquor':'\\\\u201E','ldrdhar':'\\\\u2967','ldrushar':'\\\\u294B','ldsh':'\\\\u21B2','le':'\\\\u2264','lE':'\\\\u2266','LeftAngleBracket':'\\\\u27E8','leftarrow':'\\\\u2190','Leftarrow':'\\\\u21D0','LeftArrow':'\\\\u2190','LeftArrowBar':'\\\\u21E4','LeftArrowRightArrow':'\\\\u21C6','leftarrowtail':'\\\\u21A2','LeftCeiling':'\\\\u2308','LeftDoubleBracket':'\\\\u27E6','LeftDownTeeVector':'\\\\u2961','LeftDownVector':'\\\\u21C3','LeftDownVectorBar':'\\\\u2959','LeftFloor':'\\\\u230A','leftharpoondown':'\\\\u21BD','leftharpoonup':'\\\\u21BC','leftleftarrows':'\\\\u21C7','leftrightarrow':'\\\\u2194','Leftrightarrow':'\\\\u21D4','LeftRightArrow':'\\\\u2194','leftrightarrows':'\\\\u21C6','leftrightharpoons':'\\\\u21CB','leftrightsquigarrow':'\\\\u21AD','LeftRightVector':'\\\\u294E','LeftTee':'\\\\u22A3','LeftTeeArrow':'\\\\u21A4','LeftTeeVector':'\\\\u295A','leftthreetimes':'\\\\u22CB','LeftTriangle':'\\\\u22B2','LeftTriangleBar':'\\\\u29CF','LeftTriangleEqual':'\\\\u22B4','LeftUpDownVector':'\\\\u2951','LeftUpTeeVector':'\\\\u2960','LeftUpVector':'\\\\u21BF','LeftUpVectorBar':'\\\\u2958','LeftVector':'\\\\u21BC','LeftVectorBar':'\\\\u2952','leg':'\\\\u22DA','lEg':'\\\\u2A8B','leq':'\\\\u2264','leqq':'\\\\u2266','leqslant':'\\\\u2A7D','les':'\\\\u2A7D','lescc':'\\\\u2AA8','lesdot':'\\\\u2A7F','lesdoto':'\\\\u2A81','lesdotor':'\\\\u2A83','lesg':'\\\\u22DA\\\\uFE00','lesges':'\\\\u2A93','lessapprox':'\\\\u2A85','lessdot':'\\\\u22D6','lesseqgtr':'\\\\u22DA','lesseqqgtr':'\\\\u2A8B','LessEqualGreater':'\\\\u22DA','LessFullEqual':'\\\\u2266','LessGreater':'\\\\u2276','lessgtr':'\\\\u2276','LessLess':'\\\\u2AA1','lesssim':'\\\\u2272','LessSlantEqual':'\\\\u2A7D','LessTilde':'\\\\u2272','lfisht':'\\\\u297C','lfloor':'\\\\u230A','lfr':'\\\\uD835\\\\uDD29','Lfr':'\\\\uD835\\\\uDD0F','lg':'\\\\u2276','lgE':'\\\\u2A91','lHar':'\\\\u2962','lhard':'\\\\u21BD','lharu':'\\\\u21BC','lharul':'\\\\u296A','lhblk':'\\\\u2584','ljcy':'\\\\u0459','LJcy':'\\\\u0409','ll':'\\\\u226A','Ll':'\\\\u22D8','llarr':'\\\\u21C7','llcorner':'\\\\u231E','Lleftarrow':'\\\\u21DA','llhard':'\\\\u296B','lltri':'\\\\u25FA','lmidot':'\\\\u0140','Lmidot':'\\\\u013F','lmoust':'\\\\u23B0','lmoustache':'\\\\u23B0','lnap':'\\\\u2A89','lnapprox':'\\\\u2A89','lne':'\\\\u2A87','lnE':'\\\\u2268','lneq':'\\\\u2A87','lneqq':'\\\\u2268','lnsim':'\\\\u22E6','loang':'\\\\u27EC','loarr':'\\\\u21FD','lobrk':'\\\\u27E6','longleftarrow':'\\\\u27F5','Longleftarrow':'\\\\u27F8','LongLeftArrow':'\\\\u27F5','longleftrightarrow':'\\\\u27F7','Longleftrightarrow':'\\\\u27FA','LongLeftRightArrow':'\\\\u27F7','longmapsto':'\\\\u27FC','longrightarrow':'\\\\u27F6','Longrightarrow':'\\\\u27F9','LongRightArrow':'\\\\u27F6','looparrowleft':'\\\\u21AB','looparrowright':'\\\\u21AC','lopar':'\\\\u2985','lopf':'\\\\uD835\\\\uDD5D','Lopf':'\\\\uD835\\\\uDD43','loplus':'\\\\u2A2D','lotimes':'\\\\u2A34','lowast':'\\\\u2217','lowbar':'_','LowerLeftArrow':'\\\\u2199','LowerRightArrow':'\\\\u2198','loz':'\\\\u25CA','lozenge':'\\\\u25CA','lozf':'\\\\u29EB','lpar':'(','lparlt':'\\\\u2993','lrarr':'\\\\u21C6','lrcorner':'\\\\u231F','lrhar':'\\\\u21CB','lrhard':'\\\\u296D','lrm':'\\\\u200E','lrtri':'\\\\u22BF','lsaquo':'\\\\u2039','lscr':'\\\\uD835\\\\uDCC1','Lscr':'\\\\u2112','lsh':'\\\\u21B0','Lsh':'\\\\u21B0','lsim':'\\\\u2272','lsime':'\\\\u2A8D','lsimg':'\\\\u2A8F','lsqb':'[','lsquo':'\\\\u2018','lsquor':'\\\\u201A','lstrok':'\\\\u0142','Lstrok':'\\\\u0141','lt':'<','Lt':'\\\\u226A','LT':'<','ltcc':'\\\\u2AA6','ltcir':'\\\\u2A79','ltdot':'\\\\u22D6','lthree':'\\\\u22CB','ltimes':'\\\\u22C9','ltlarr':'\\\\u2976','ltquest':'\\\\u2A7B','ltri':'\\\\u25C3','ltrie':'\\\\u22B4','ltrif':'\\\\u25C2','ltrPar':'\\\\u2996','lurdshar':'\\\\u294A','luruhar':'\\\\u2966','lvertneqq':'\\\\u2268\\\\uFE00','lvnE':'\\\\u2268\\\\uFE00','macr':'\\\\xAF','male':'\\\\u2642','malt':'\\\\u2720','maltese':'\\\\u2720','map':'\\\\u21A6','Map':'\\\\u2905','mapsto':'\\\\u21A6','mapstodown':'\\\\u21A7','mapstoleft':'\\\\u21A4','mapstoup':'\\\\u21A5','marker':'\\\\u25AE','mcomma':'\\\\u2A29','mcy':'\\\\u043C','Mcy':'\\\\u041C','mdash':'\\\\u2014','mDDot':'\\\\u223A','measuredangle':'\\\\u2221','MediumSpace':'\\\\u205F','Mellintrf':'\\\\u2133','mfr':'\\\\uD835\\\\uDD2A','Mfr':'\\\\uD835\\\\uDD10','mho':'\\\\u2127','micro':'\\\\xB5','mid':'\\\\u2223','midast':'*','midcir':'\\\\u2AF0','middot':'\\\\xB7','minus':'\\\\u2212','minusb':'\\\\u229F','minusd':'\\\\u2238','minusdu':'\\\\u2A2A','MinusPlus':'\\\\u2213','mlcp':'\\\\u2ADB','mldr':'\\\\u2026','mnplus':'\\\\u2213','models':'\\\\u22A7','mopf':'\\\\uD835\\\\uDD5E','Mopf':'\\\\uD835\\\\uDD44','mp':'\\\\u2213','mscr':'\\\\uD835\\\\uDCC2','Mscr':'\\\\u2133','mstpos':'\\\\u223E','mu':'\\\\u03BC','Mu':'\\\\u039C','multimap':'\\\\u22B8','mumap':'\\\\u22B8','nabla':'\\\\u2207','nacute':'\\\\u0144','Nacute':'\\\\u0143','nang':'\\\\u2220\\\\u20D2','nap':'\\\\u2249','napE':'\\\\u2A70\\\\u0338','napid':'\\\\u224B\\\\u0338','napos':'\\\\u0149','napprox':'\\\\u2249','natur':'\\\\u266E','natural':'\\\\u266E','naturals':'\\\\u2115','nbsp':'\\\\xA0','nbump':'\\\\u224E\\\\u0338','nbumpe':'\\\\u224F\\\\u0338','ncap':'\\\\u2A43','ncaron':'\\\\u0148','Ncaron':'\\\\u0147','ncedil':'\\\\u0146','Ncedil':'\\\\u0145','ncong':'\\\\u2247','ncongdot':'\\\\u2A6D\\\\u0338','ncup':'\\\\u2A42','ncy':'\\\\u043D','Ncy':'\\\\u041D','ndash':'\\\\u2013','ne':'\\\\u2260','nearhk':'\\\\u2924','nearr':'\\\\u2197','neArr':'\\\\u21D7','nearrow':'\\\\u2197','nedot':'\\\\u2250\\\\u0338','NegativeMediumSpace':'\\\\u200B','NegativeThickSpace':'\\\\u200B','NegativeThinSpace':'\\\\u200B','NegativeVeryThinSpace':'\\\\u200B','nequiv':'\\\\u2262','nesear':'\\\\u2928','nesim':'\\\\u2242\\\\u0338','NestedGreaterGreater':'\\\\u226B','NestedLessLess':'\\\\u226A','NewLine':'\\\\n','nexist':'\\\\u2204','nexists':'\\\\u2204','nfr':'\\\\uD835\\\\uDD2B','Nfr':'\\\\uD835\\\\uDD11','nge':'\\\\u2271','ngE':'\\\\u2267\\\\u0338','ngeq':'\\\\u2271','ngeqq':'\\\\u2267\\\\u0338','ngeqslant':'\\\\u2A7E\\\\u0338','nges':'\\\\u2A7E\\\\u0338','nGg':'\\\\u22D9\\\\u0338','ngsim':'\\\\u2275','ngt':'\\\\u226F','nGt':'\\\\u226B\\\\u20D2','ngtr':'\\\\u226F','nGtv':'\\\\u226B\\\\u0338','nharr':'\\\\u21AE','nhArr':'\\\\u21CE','nhpar':'\\\\u2AF2','ni':'\\\\u220B','nis':'\\\\u22FC','nisd':'\\\\u22FA','niv':'\\\\u220B','njcy':'\\\\u045A','NJcy':'\\\\u040A','nlarr':'\\\\u219A','nlArr':'\\\\u21CD','nldr':'\\\\u2025','nle':'\\\\u2270','nlE':'\\\\u2266\\\\u0338','nleftarrow':'\\\\u219A','nLeftarrow':'\\\\u21CD','nleftrightarrow':'\\\\u21AE','nLeftrightarrow':'\\\\u21CE','nleq':'\\\\u2270','nleqq':'\\\\u2266\\\\u0338','nleqslant':'\\\\u2A7D\\\\u0338','nles':'\\\\u2A7D\\\\u0338','nless':'\\\\u226E','nLl':'\\\\u22D8\\\\u0338','nlsim':'\\\\u2274','nlt':'\\\\u226E','nLt':'\\\\u226A\\\\u20D2','nltri':'\\\\u22EA','nltrie':'\\\\u22EC','nLtv':'\\\\u226A\\\\u0338','nmid':'\\\\u2224','NoBreak':'\\\\u2060','NonBreakingSpace':'\\\\xA0','nopf':'\\\\uD835\\\\uDD5F','Nopf':'\\\\u2115','not':'\\\\xAC','Not':'\\\\u2AEC','NotCongruent':'\\\\u2262','NotCupCap':'\\\\u226D','NotDoubleVerticalBar':'\\\\u2226','NotElement':'\\\\u2209','NotEqual':'\\\\u2260','NotEqualTilde':'\\\\u2242\\\\u0338','NotExists':'\\\\u2204','NotGreater':'\\\\u226F','NotGreaterEqual':'\\\\u2271','NotGreaterFullEqual':'\\\\u2267\\\\u0338','NotGreaterGreater':'\\\\u226B\\\\u0338','NotGreaterLess':'\\\\u2279','NotGreaterSlantEqual':'\\\\u2A7E\\\\u0338','NotGreaterTilde':'\\\\u2275','NotHumpDownHump':'\\\\u224E\\\\u0338','NotHumpEqual':'\\\\u224F\\\\u0338','notin':'\\\\u2209','notindot':'\\\\u22F5\\\\u0338','notinE':'\\\\u22F9\\\\u0338','notinva':'\\\\u2209','notinvb':'\\\\u22F7','notinvc':'\\\\u22F6','NotLeftTriangle':'\\\\u22EA','NotLeftTriangleBar':'\\\\u29CF\\\\u0338','NotLeftTriangleEqual':'\\\\u22EC','NotLess':'\\\\u226E','NotLessEqual':'\\\\u2270','NotLessGreater':'\\\\u2278','NotLessLess':'\\\\u226A\\\\u0338','NotLessSlantEqual':'\\\\u2A7D\\\\u0338','NotLessTilde':'\\\\u2274','NotNestedGreaterGreater':'\\\\u2AA2\\\\u0338','NotNestedLessLess':'\\\\u2AA1\\\\u0338','notni':'\\\\u220C','notniva':'\\\\u220C','notnivb':'\\\\u22FE','notnivc':'\\\\u22FD','NotPrecedes':'\\\\u2280','NotPrecedesEqual':'\\\\u2AAF\\\\u0338','NotPrecedesSlantEqual':'\\\\u22E0','NotReverseElement':'\\\\u220C','NotRightTriangle':'\\\\u22EB','NotRightTriangleBar':'\\\\u29D0\\\\u0338','NotRightTriangleEqual':'\\\\u22ED','NotSquareSubset':'\\\\u228F\\\\u0338','NotSquareSubsetEqual':'\\\\u22E2','NotSquareSuperset':'\\\\u2290\\\\u0338','NotSquareSupersetEqual':'\\\\u22E3','NotSubset':'\\\\u2282\\\\u20D2','NotSubsetEqual':'\\\\u2288','NotSucceeds':'\\\\u2281','NotSucceedsEqual':'\\\\u2AB0\\\\u0338','NotSucceedsSlantEqual':'\\\\u22E1','NotSucceedsTilde':'\\\\u227F\\\\u0338','NotSuperset':'\\\\u2283\\\\u20D2','NotSupersetEqual':'\\\\u2289','NotTilde':'\\\\u2241','NotTildeEqual':'\\\\u2244','NotTildeFullEqual':'\\\\u2247','NotTildeTilde':'\\\\u2249','NotVerticalBar':'\\\\u2224','npar':'\\\\u2226','nparallel':'\\\\u2226','nparsl':'\\\\u2AFD\\\\u20E5','npart':'\\\\u2202\\\\u0338','npolint':'\\\\u2A14','npr':'\\\\u2280','nprcue':'\\\\u22E0','npre':'\\\\u2AAF\\\\u0338','nprec':'\\\\u2280','npreceq':'\\\\u2AAF\\\\u0338','nrarr':'\\\\u219B','nrArr':'\\\\u21CF','nrarrc':'\\\\u2933\\\\u0338','nrarrw':'\\\\u219D\\\\u0338','nrightarrow':'\\\\u219B','nRightarrow':'\\\\u21CF','nrtri':'\\\\u22EB','nrtrie':'\\\\u22ED','nsc':'\\\\u2281','nsccue':'\\\\u22E1','nsce':'\\\\u2AB0\\\\u0338','nscr':'\\\\uD835\\\\uDCC3','Nscr':'\\\\uD835\\\\uDCA9','nshortmid':'\\\\u2224','nshortparallel':'\\\\u2226','nsim':'\\\\u2241','nsime':'\\\\u2244','nsimeq':'\\\\u2244','nsmid':'\\\\u2224','nspar':'\\\\u2226','nsqsube':'\\\\u22E2','nsqsupe':'\\\\u22E3','nsub':'\\\\u2284','nsube':'\\\\u2288','nsubE':'\\\\u2AC5\\\\u0338','nsubset':'\\\\u2282\\\\u20D2','nsubseteq':'\\\\u2288','nsubseteqq':'\\\\u2AC5\\\\u0338','nsucc':'\\\\u2281','nsucceq':'\\\\u2AB0\\\\u0338','nsup':'\\\\u2285','nsupe':'\\\\u2289','nsupE':'\\\\u2AC6\\\\u0338','nsupset':'\\\\u2283\\\\u20D2','nsupseteq':'\\\\u2289','nsupseteqq':'\\\\u2AC6\\\\u0338','ntgl':'\\\\u2279','ntilde':'\\\\xF1','Ntilde':'\\\\xD1','ntlg':'\\\\u2278','ntriangleleft':'\\\\u22EA','ntrianglelefteq':'\\\\u22EC','ntriangleright':'\\\\u22EB','ntrianglerighteq':'\\\\u22ED','nu':'\\\\u03BD','Nu':'\\\\u039D','num':'#','numero':'\\\\u2116','numsp':'\\\\u2007','nvap':'\\\\u224D\\\\u20D2','nvdash':'\\\\u22AC','nvDash':'\\\\u22AD','nVdash':'\\\\u22AE','nVDash':'\\\\u22AF','nvge':'\\\\u2265\\\\u20D2','nvgt':'>\\\\u20D2','nvHarr':'\\\\u2904','nvinfin':'\\\\u29DE','nvlArr':'\\\\u2902','nvle':'\\\\u2264\\\\u20D2','nvlt':'<\\\\u20D2','nvltrie':'\\\\u22B4\\\\u20D2','nvrArr':'\\\\u2903','nvrtrie':'\\\\u22B5\\\\u20D2','nvsim':'\\\\u223C\\\\u20D2','nwarhk':'\\\\u2923','nwarr':'\\\\u2196','nwArr':'\\\\u21D6','nwarrow':'\\\\u2196','nwnear':'\\\\u2927','oacute':'\\\\xF3','Oacute':'\\\\xD3','oast':'\\\\u229B','ocir':'\\\\u229A','ocirc':'\\\\xF4','Ocirc':'\\\\xD4','ocy':'\\\\u043E','Ocy':'\\\\u041E','odash':'\\\\u229D','odblac':'\\\\u0151','Odblac':'\\\\u0150','odiv':'\\\\u2A38','odot':'\\\\u2299','odsold':'\\\\u29BC','oelig':'\\\\u0153','OElig':'\\\\u0152','ofcir':'\\\\u29BF','ofr':'\\\\uD835\\\\uDD2C','Ofr':'\\\\uD835\\\\uDD12','ogon':'\\\\u02DB','ograve':'\\\\xF2','Ograve':'\\\\xD2','ogt':'\\\\u29C1','ohbar':'\\\\u29B5','ohm':'\\\\u03A9','oint':'\\\\u222E','olarr':'\\\\u21BA','olcir':'\\\\u29BE','olcross':'\\\\u29BB','oline':'\\\\u203E','olt':'\\\\u29C0','omacr':'\\\\u014D','Omacr':'\\\\u014C','omega':'\\\\u03C9','Omega':'\\\\u03A9','omicron':'\\\\u03BF','Omicron':'\\\\u039F','omid':'\\\\u29B6','ominus':'\\\\u2296','oopf':'\\\\uD835\\\\uDD60','Oopf':'\\\\uD835\\\\uDD46','opar':'\\\\u29B7','OpenCurlyDoubleQuote':'\\\\u201C','OpenCurlyQuote':'\\\\u2018','operp':'\\\\u29B9','oplus':'\\\\u2295','or':'\\\\u2228','Or':'\\\\u2A54','orarr':'\\\\u21BB','ord':'\\\\u2A5D','order':'\\\\u2134','orderof':'\\\\u2134','ordf':'\\\\xAA','ordm':'\\\\xBA','origof':'\\\\u22B6','oror':'\\\\u2A56','orslope':'\\\\u2A57','orv':'\\\\u2A5B','oS':'\\\\u24C8','oscr':'\\\\u2134','Oscr':'\\\\uD835\\\\uDCAA','oslash':'\\\\xF8','Oslash':'\\\\xD8','osol':'\\\\u2298','otilde':'\\\\xF5','Otilde':'\\\\xD5','otimes':'\\\\u2297','Otimes':'\\\\u2A37','otimesas':'\\\\u2A36','ouml':'\\\\xF6','Ouml':'\\\\xD6','ovbar':'\\\\u233D','OverBar':'\\\\u203E','OverBrace':'\\\\u23DE','OverBracket':'\\\\u23B4','OverParenthesis':'\\\\u23DC','par':'\\\\u2225','para':'\\\\xB6','parallel':'\\\\u2225','parsim':'\\\\u2AF3','parsl':'\\\\u2AFD','part':'\\\\u2202','PartialD':'\\\\u2202','pcy':'\\\\u043F','Pcy':'\\\\u041F','percnt':'%','period':'.','permil':'\\\\u2030','perp':'\\\\u22A5','pertenk':'\\\\u2031','pfr':'\\\\uD835\\\\uDD2D','Pfr':'\\\\uD835\\\\uDD13','phi':'\\\\u03C6','Phi':'\\\\u03A6','phiv':'\\\\u03D5','phmmat':'\\\\u2133','phone':'\\\\u260E','pi':'\\\\u03C0','Pi':'\\\\u03A0','pitchfork':'\\\\u22D4','piv':'\\\\u03D6','planck':'\\\\u210F','planckh':'\\\\u210E','plankv':'\\\\u210F','plus':'+','plusacir':'\\\\u2A23','plusb':'\\\\u229E','pluscir':'\\\\u2A22','plusdo':'\\\\u2214','plusdu':'\\\\u2A25','pluse':'\\\\u2A72','PlusMinus':'\\\\xB1','plusmn':'\\\\xB1','plussim':'\\\\u2A26','plustwo':'\\\\u2A27','pm':'\\\\xB1','Poincareplane':'\\\\u210C','pointint':'\\\\u2A15','popf':'\\\\uD835\\\\uDD61','Popf':'\\\\u2119','pound':'\\\\xA3','pr':'\\\\u227A','Pr':'\\\\u2ABB','prap':'\\\\u2AB7','prcue':'\\\\u227C','pre':'\\\\u2AAF','prE':'\\\\u2AB3','prec':'\\\\u227A','precapprox':'\\\\u2AB7','preccurlyeq':'\\\\u227C','Precedes':'\\\\u227A','PrecedesEqual':'\\\\u2AAF','PrecedesSlantEqual':'\\\\u227C','PrecedesTilde':'\\\\u227E','preceq':'\\\\u2AAF','precnapprox':'\\\\u2AB9','precneqq':'\\\\u2AB5','precnsim':'\\\\u22E8','precsim':'\\\\u227E','prime':'\\\\u2032','Prime':'\\\\u2033','primes':'\\\\u2119','prnap':'\\\\u2AB9','prnE':'\\\\u2AB5','prnsim':'\\\\u22E8','prod':'\\\\u220F','Product':'\\\\u220F','profalar':'\\\\u232E','profline':'\\\\u2312','profsurf':'\\\\u2313','prop':'\\\\u221D','Proportion':'\\\\u2237','Proportional':'\\\\u221D','propto':'\\\\u221D','prsim':'\\\\u227E','prurel':'\\\\u22B0','pscr':'\\\\uD835\\\\uDCC5','Pscr':'\\\\uD835\\\\uDCAB','psi':'\\\\u03C8','Psi':'\\\\u03A8','puncsp':'\\\\u2008','qfr':'\\\\uD835\\\\uDD2E','Qfr':'\\\\uD835\\\\uDD14','qint':'\\\\u2A0C','qopf':'\\\\uD835\\\\uDD62','Qopf':'\\\\u211A','qprime':'\\\\u2057','qscr':'\\\\uD835\\\\uDCC6','Qscr':'\\\\uD835\\\\uDCAC','quaternions':'\\\\u210D','quatint':'\\\\u2A16','quest':'?','questeq':'\\\\u225F','quot':'\\\"','QUOT':'\\\"','rAarr':'\\\\u21DB','race':'\\\\u223D\\\\u0331','racute':'\\\\u0155','Racute':'\\\\u0154','radic':'\\\\u221A','raemptyv':'\\\\u29B3','rang':'\\\\u27E9','Rang':'\\\\u27EB','rangd':'\\\\u2992','range':'\\\\u29A5','rangle':'\\\\u27E9','raquo':'\\\\xBB','rarr':'\\\\u2192','rArr':'\\\\u21D2','Rarr':'\\\\u21A0','rarrap':'\\\\u2975','rarrb':'\\\\u21E5','rarrbfs':'\\\\u2920','rarrc':'\\\\u2933','rarrfs':'\\\\u291E','rarrhk':'\\\\u21AA','rarrlp':'\\\\u21AC','rarrpl':'\\\\u2945','rarrsim':'\\\\u2974','rarrtl':'\\\\u21A3','Rarrtl':'\\\\u2916','rarrw':'\\\\u219D','ratail':'\\\\u291A','rAtail':'\\\\u291C','ratio':'\\\\u2236','rationals':'\\\\u211A','rbarr':'\\\\u290D','rBarr':'\\\\u290F','RBarr':'\\\\u2910','rbbrk':'\\\\u2773','rbrace':'}','rbrack':']','rbrke':'\\\\u298C','rbrksld':'\\\\u298E','rbrkslu':'\\\\u2990','rcaron':'\\\\u0159','Rcaron':'\\\\u0158','rcedil':'\\\\u0157','Rcedil':'\\\\u0156','rceil':'\\\\u2309','rcub':'}','rcy':'\\\\u0440','Rcy':'\\\\u0420','rdca':'\\\\u2937','rdldhar':'\\\\u2969','rdquo':'\\\\u201D','rdquor':'\\\\u201D','rdsh':'\\\\u21B3','Re':'\\\\u211C','real':'\\\\u211C','realine':'\\\\u211B','realpart':'\\\\u211C','reals':'\\\\u211D','rect':'\\\\u25AD','reg':'\\\\xAE','REG':'\\\\xAE','ReverseElement':'\\\\u220B','ReverseEquilibrium':'\\\\u21CB','ReverseUpEquilibrium':'\\\\u296F','rfisht':'\\\\u297D','rfloor':'\\\\u230B','rfr':'\\\\uD835\\\\uDD2F','Rfr':'\\\\u211C','rHar':'\\\\u2964','rhard':'\\\\u21C1','rharu':'\\\\u21C0','rharul':'\\\\u296C','rho':'\\\\u03C1','Rho':'\\\\u03A1','rhov':'\\\\u03F1','RightAngleBracket':'\\\\u27E9','rightarrow':'\\\\u2192','Rightarrow':'\\\\u21D2','RightArrow':'\\\\u2192','RightArrowBar':'\\\\u21E5','RightArrowLeftArrow':'\\\\u21C4','rightarrowtail':'\\\\u21A3','RightCeiling':'\\\\u2309','RightDoubleBracket':'\\\\u27E7','RightDownTeeVector':'\\\\u295D','RightDownVector':'\\\\u21C2','RightDownVectorBar':'\\\\u2955','RightFloor':'\\\\u230B','rightharpoondown':'\\\\u21C1','rightharpoonup':'\\\\u21C0','rightleftarrows':'\\\\u21C4','rightleftharpoons':'\\\\u21CC','rightrightarrows':'\\\\u21C9','rightsquigarrow':'\\\\u219D','RightTee':'\\\\u22A2','RightTeeArrow':'\\\\u21A6','RightTeeVector':'\\\\u295B','rightthreetimes':'\\\\u22CC','RightTriangle':'\\\\u22B3','RightTriangleBar':'\\\\u29D0','RightTriangleEqual':'\\\\u22B5','RightUpDownVector':'\\\\u294F','RightUpTeeVector':'\\\\u295C','RightUpVector':'\\\\u21BE','RightUpVectorBar':'\\\\u2954','RightVector':'\\\\u21C0','RightVectorBar':'\\\\u2953','ring':'\\\\u02DA','risingdotseq':'\\\\u2253','rlarr':'\\\\u21C4','rlhar':'\\\\u21CC','rlm':'\\\\u200F','rmoust':'\\\\u23B1','rmoustache':'\\\\u23B1','rnmid':'\\\\u2AEE','roang':'\\\\u27ED','roarr':'\\\\u21FE','robrk':'\\\\u27E7','ropar':'\\\\u2986','ropf':'\\\\uD835\\\\uDD63','Ropf':'\\\\u211D','roplus':'\\\\u2A2E','rotimes':'\\\\u2A35','RoundImplies':'\\\\u2970','rpar':')','rpargt':'\\\\u2994','rppolint':'\\\\u2A12','rrarr':'\\\\u21C9','Rrightarrow':'\\\\u21DB','rsaquo':'\\\\u203A','rscr':'\\\\uD835\\\\uDCC7','Rscr':'\\\\u211B','rsh':'\\\\u21B1','Rsh':'\\\\u21B1','rsqb':']','rsquo':'\\\\u2019','rsquor':'\\\\u2019','rthree':'\\\\u22CC','rtimes':'\\\\u22CA','rtri':'\\\\u25B9','rtrie':'\\\\u22B5','rtrif':'\\\\u25B8','rtriltri':'\\\\u29CE','RuleDelayed':'\\\\u29F4','ruluhar':'\\\\u2968','rx':'\\\\u211E','sacute':'\\\\u015B','Sacute':'\\\\u015A','sbquo':'\\\\u201A','sc':'\\\\u227B','Sc':'\\\\u2ABC','scap':'\\\\u2AB8','scaron':'\\\\u0161','Scaron':'\\\\u0160','sccue':'\\\\u227D','sce':'\\\\u2AB0','scE':'\\\\u2AB4','scedil':'\\\\u015F','Scedil':'\\\\u015E','scirc':'\\\\u015D','Scirc':'\\\\u015C','scnap':'\\\\u2ABA','scnE':'\\\\u2AB6','scnsim':'\\\\u22E9','scpolint':'\\\\u2A13','scsim':'\\\\u227F','scy':'\\\\u0441','Scy':'\\\\u0421','sdot':'\\\\u22C5','sdotb':'\\\\u22A1','sdote':'\\\\u2A66','searhk':'\\\\u2925','searr':'\\\\u2198','seArr':'\\\\u21D8','searrow':'\\\\u2198','sect':'\\\\xA7','semi':';','seswar':'\\\\u2929','setminus':'\\\\u2216','setmn':'\\\\u2216','sext':'\\\\u2736','sfr':'\\\\uD835\\\\uDD30','Sfr':'\\\\uD835\\\\uDD16','sfrown':'\\\\u2322','sharp':'\\\\u266F','shchcy':'\\\\u0449','SHCHcy':'\\\\u0429','shcy':'\\\\u0448','SHcy':'\\\\u0428','ShortDownArrow':'\\\\u2193','ShortLeftArrow':'\\\\u2190','shortmid':'\\\\u2223','shortparallel':'\\\\u2225','ShortRightArrow':'\\\\u2192','ShortUpArrow':'\\\\u2191','shy':'\\\\xAD','sigma':'\\\\u03C3','Sigma':'\\\\u03A3','sigmaf':'\\\\u03C2','sigmav':'\\\\u03C2','sim':'\\\\u223C','simdot':'\\\\u2A6A','sime':'\\\\u2243','simeq':'\\\\u2243','simg':'\\\\u2A9E','simgE':'\\\\u2AA0','siml':'\\\\u2A9D','simlE':'\\\\u2A9F','simne':'\\\\u2246','simplus':'\\\\u2A24','simrarr':'\\\\u2972','slarr':'\\\\u2190','SmallCircle':'\\\\u2218','smallsetminus':'\\\\u2216','smashp':'\\\\u2A33','smeparsl':'\\\\u29E4','smid':'\\\\u2223','smile':'\\\\u2323','smt':'\\\\u2AAA','smte':'\\\\u2AAC','smtes':'\\\\u2AAC\\\\uFE00','softcy':'\\\\u044C','SOFTcy':'\\\\u042C','sol':'/','solb':'\\\\u29C4','solbar':'\\\\u233F','sopf':'\\\\uD835\\\\uDD64','Sopf':'\\\\uD835\\\\uDD4A','spades':'\\\\u2660','spadesuit':'\\\\u2660','spar':'\\\\u2225','sqcap':'\\\\u2293','sqcaps':'\\\\u2293\\\\uFE00','sqcup':'\\\\u2294','sqcups':'\\\\u2294\\\\uFE00','Sqrt':'\\\\u221A','sqsub':'\\\\u228F','sqsube':'\\\\u2291','sqsubset':'\\\\u228F','sqsubseteq':'\\\\u2291','sqsup':'\\\\u2290','sqsupe':'\\\\u2292','sqsupset':'\\\\u2290','sqsupseteq':'\\\\u2292','squ':'\\\\u25A1','square':'\\\\u25A1','Square':'\\\\u25A1','SquareIntersection':'\\\\u2293','SquareSubset':'\\\\u228F','SquareSubsetEqual':'\\\\u2291','SquareSuperset':'\\\\u2290','SquareSupersetEqual':'\\\\u2292','SquareUnion':'\\\\u2294','squarf':'\\\\u25AA','squf':'\\\\u25AA','srarr':'\\\\u2192','sscr':'\\\\uD835\\\\uDCC8','Sscr':'\\\\uD835\\\\uDCAE','ssetmn':'\\\\u2216','ssmile':'\\\\u2323','sstarf':'\\\\u22C6','star':'\\\\u2606','Star':'\\\\u22C6','starf':'\\\\u2605','straightepsilon':'\\\\u03F5','straightphi':'\\\\u03D5','strns':'\\\\xAF','sub':'\\\\u2282','Sub':'\\\\u22D0','subdot':'\\\\u2ABD','sube':'\\\\u2286','subE':'\\\\u2AC5','subedot':'\\\\u2AC3','submult':'\\\\u2AC1','subne':'\\\\u228A','subnE':'\\\\u2ACB','subplus':'\\\\u2ABF','subrarr':'\\\\u2979','subset':'\\\\u2282','Subset':'\\\\u22D0','subseteq':'\\\\u2286','subseteqq':'\\\\u2AC5','SubsetEqual':'\\\\u2286','subsetneq':'\\\\u228A','subsetneqq':'\\\\u2ACB','subsim':'\\\\u2AC7','subsub':'\\\\u2AD5','subsup':'\\\\u2AD3','succ':'\\\\u227B','succapprox':'\\\\u2AB8','succcurlyeq':'\\\\u227D','Succeeds':'\\\\u227B','SucceedsEqual':'\\\\u2AB0','SucceedsSlantEqual':'\\\\u227D','SucceedsTilde':'\\\\u227F','succeq':'\\\\u2AB0','succnapprox':'\\\\u2ABA','succneqq':'\\\\u2AB6','succnsim':'\\\\u22E9','succsim':'\\\\u227F','SuchThat':'\\\\u220B','sum':'\\\\u2211','Sum':'\\\\u2211','sung':'\\\\u266A','sup':'\\\\u2283','Sup':'\\\\u22D1','sup1':'\\\\xB9','sup2':'\\\\xB2','sup3':'\\\\xB3','supdot':'\\\\u2ABE','supdsub':'\\\\u2AD8','supe':'\\\\u2287','supE':'\\\\u2AC6','supedot':'\\\\u2AC4','Superset':'\\\\u2283','SupersetEqual':'\\\\u2287','suphsol':'\\\\u27C9','suphsub':'\\\\u2AD7','suplarr':'\\\\u297B','supmult':'\\\\u2AC2','supne':'\\\\u228B','supnE':'\\\\u2ACC','supplus':'\\\\u2AC0','supset':'\\\\u2283','Supset':'\\\\u22D1','supseteq':'\\\\u2287','supseteqq':'\\\\u2AC6','supsetneq':'\\\\u228B','supsetneqq':'\\\\u2ACC','supsim':'\\\\u2AC8','supsub':'\\\\u2AD4','supsup':'\\\\u2AD6','swarhk':'\\\\u2926','swarr':'\\\\u2199','swArr':'\\\\u21D9','swarrow':'\\\\u2199','swnwar':'\\\\u292A','szlig':'\\\\xDF','Tab':'\\\\t','target':'\\\\u2316','tau':'\\\\u03C4','Tau':'\\\\u03A4','tbrk':'\\\\u23B4','tcaron':'\\\\u0165','Tcaron':'\\\\u0164','tcedil':'\\\\u0163','Tcedil':'\\\\u0162','tcy':'\\\\u0442','Tcy':'\\\\u0422','tdot':'\\\\u20DB','telrec':'\\\\u2315','tfr':'\\\\uD835\\\\uDD31','Tfr':'\\\\uD835\\\\uDD17','there4':'\\\\u2234','therefore':'\\\\u2234','Therefore':'\\\\u2234','theta':'\\\\u03B8','Theta':'\\\\u0398','thetasym':'\\\\u03D1','thetav':'\\\\u03D1','thickapprox':'\\\\u2248','thicksim':'\\\\u223C','ThickSpace':'\\\\u205F\\\\u200A','thinsp':'\\\\u2009','ThinSpace':'\\\\u2009','thkap':'\\\\u2248','thksim':'\\\\u223C','thorn':'\\\\xFE','THORN':'\\\\xDE','tilde':'\\\\u02DC','Tilde':'\\\\u223C','TildeEqual':'\\\\u2243','TildeFullEqual':'\\\\u2245','TildeTilde':'\\\\u2248','times':'\\\\xD7','timesb':'\\\\u22A0','timesbar':'\\\\u2A31','timesd':'\\\\u2A30','tint':'\\\\u222D','toea':'\\\\u2928','top':'\\\\u22A4','topbot':'\\\\u2336','topcir':'\\\\u2AF1','topf':'\\\\uD835\\\\uDD65','Topf':'\\\\uD835\\\\uDD4B','topfork':'\\\\u2ADA','tosa':'\\\\u2929','tprime':'\\\\u2034','trade':'\\\\u2122','TRADE':'\\\\u2122','triangle':'\\\\u25B5','triangledown':'\\\\u25BF','triangleleft':'\\\\u25C3','trianglelefteq':'\\\\u22B4','triangleq':'\\\\u225C','triangleright':'\\\\u25B9','trianglerighteq':'\\\\u22B5','tridot':'\\\\u25EC','trie':'\\\\u225C','triminus':'\\\\u2A3A','TripleDot':'\\\\u20DB','triplus':'\\\\u2A39','trisb':'\\\\u29CD','tritime':'\\\\u2A3B','trpezium':'\\\\u23E2','tscr':'\\\\uD835\\\\uDCC9','Tscr':'\\\\uD835\\\\uDCAF','tscy':'\\\\u0446','TScy':'\\\\u0426','tshcy':'\\\\u045B','TSHcy':'\\\\u040B','tstrok':'\\\\u0167','Tstrok':'\\\\u0166','twixt':'\\\\u226C','twoheadleftarrow':'\\\\u219E','twoheadrightarrow':'\\\\u21A0','uacute':'\\\\xFA','Uacute':'\\\\xDA','uarr':'\\\\u2191','uArr':'\\\\u21D1','Uarr':'\\\\u219F','Uarrocir':'\\\\u2949','ubrcy':'\\\\u045E','Ubrcy':'\\\\u040E','ubreve':'\\\\u016D','Ubreve':'\\\\u016C','ucirc':'\\\\xFB','Ucirc':'\\\\xDB','ucy':'\\\\u0443','Ucy':'\\\\u0423','udarr':'\\\\u21C5','udblac':'\\\\u0171','Udblac':'\\\\u0170','udhar':'\\\\u296E','ufisht':'\\\\u297E','ufr':'\\\\uD835\\\\uDD32','Ufr':'\\\\uD835\\\\uDD18','ugrave':'\\\\xF9','Ugrave':'\\\\xD9','uHar':'\\\\u2963','uharl':'\\\\u21BF','uharr':'\\\\u21BE','uhblk':'\\\\u2580','ulcorn':'\\\\u231C','ulcorner':'\\\\u231C','ulcrop':'\\\\u230F','ultri':'\\\\u25F8','umacr':'\\\\u016B','Umacr':'\\\\u016A','uml':'\\\\xA8','UnderBar':'_','UnderBrace':'\\\\u23DF','UnderBracket':'\\\\u23B5','UnderParenthesis':'\\\\u23DD','Union':'\\\\u22C3','UnionPlus':'\\\\u228E','uogon':'\\\\u0173','Uogon':'\\\\u0172','uopf':'\\\\uD835\\\\uDD66','Uopf':'\\\\uD835\\\\uDD4C','uparrow':'\\\\u2191','Uparrow':'\\\\u21D1','UpArrow':'\\\\u2191','UpArrowBar':'\\\\u2912','UpArrowDownArrow':'\\\\u21C5','updownarrow':'\\\\u2195','Updownarrow':'\\\\u21D5','UpDownArrow':'\\\\u2195','UpEquilibrium':'\\\\u296E','upharpoonleft':'\\\\u21BF','upharpoonright':'\\\\u21BE','uplus':'\\\\u228E','UpperLeftArrow':'\\\\u2196','UpperRightArrow':'\\\\u2197','upsi':'\\\\u03C5','Upsi':'\\\\u03D2','upsih':'\\\\u03D2','upsilon':'\\\\u03C5','Upsilon':'\\\\u03A5','UpTee':'\\\\u22A5','UpTeeArrow':'\\\\u21A5','upuparrows':'\\\\u21C8','urcorn':'\\\\u231D','urcorner':'\\\\u231D','urcrop':'\\\\u230E','uring':'\\\\u016F','Uring':'\\\\u016E','urtri':'\\\\u25F9','uscr':'\\\\uD835\\\\uDCCA','Uscr':'\\\\uD835\\\\uDCB0','utdot':'\\\\u22F0','utilde':'\\\\u0169','Utilde':'\\\\u0168','utri':'\\\\u25B5','utrif':'\\\\u25B4','uuarr':'\\\\u21C8','uuml':'\\\\xFC','Uuml':'\\\\xDC','uwangle':'\\\\u29A7','vangrt':'\\\\u299C','varepsilon':'\\\\u03F5','varkappa':'\\\\u03F0','varnothing':'\\\\u2205','varphi':'\\\\u03D5','varpi':'\\\\u03D6','varpropto':'\\\\u221D','varr':'\\\\u2195','vArr':'\\\\u21D5','varrho':'\\\\u03F1','varsigma':'\\\\u03C2','varsubsetneq':'\\\\u228A\\\\uFE00','varsubsetneqq':'\\\\u2ACB\\\\uFE00','varsupsetneq':'\\\\u228B\\\\uFE00','varsupsetneqq':'\\\\u2ACC\\\\uFE00','vartheta':'\\\\u03D1','vartriangleleft':'\\\\u22B2','vartriangleright':'\\\\u22B3','vBar':'\\\\u2AE8','Vbar':'\\\\u2AEB','vBarv':'\\\\u2AE9','vcy':'\\\\u0432','Vcy':'\\\\u0412','vdash':'\\\\u22A2','vDash':'\\\\u22A8','Vdash':'\\\\u22A9','VDash':'\\\\u22AB','Vdashl':'\\\\u2AE6','vee':'\\\\u2228','Vee':'\\\\u22C1','veebar':'\\\\u22BB','veeeq':'\\\\u225A','vellip':'\\\\u22EE','verbar':'|','Verbar':'\\\\u2016','vert':'|','Vert':'\\\\u2016','VerticalBar':'\\\\u2223','VerticalLine':'|','VerticalSeparator':'\\\\u2758','VerticalTilde':'\\\\u2240','VeryThinSpace':'\\\\u200A','vfr':'\\\\uD835\\\\uDD33','Vfr':'\\\\uD835\\\\uDD19','vltri':'\\\\u22B2','vnsub':'\\\\u2282\\\\u20D2','vnsup':'\\\\u2283\\\\u20D2','vopf':'\\\\uD835\\\\uDD67','Vopf':'\\\\uD835\\\\uDD4D','vprop':'\\\\u221D','vrtri':'\\\\u22B3','vscr':'\\\\uD835\\\\uDCCB','Vscr':'\\\\uD835\\\\uDCB1','vsubne':'\\\\u228A\\\\uFE00','vsubnE':'\\\\u2ACB\\\\uFE00','vsupne':'\\\\u228B\\\\uFE00','vsupnE':'\\\\u2ACC\\\\uFE00','Vvdash':'\\\\u22AA','vzigzag':'\\\\u299A','wcirc':'\\\\u0175','Wcirc':'\\\\u0174','wedbar':'\\\\u2A5F','wedge':'\\\\u2227','Wedge':'\\\\u22C0','wedgeq':'\\\\u2259','weierp':'\\\\u2118','wfr':'\\\\uD835\\\\uDD34','Wfr':'\\\\uD835\\\\uDD1A','wopf':'\\\\uD835\\\\uDD68','Wopf':'\\\\uD835\\\\uDD4E','wp':'\\\\u2118','wr':'\\\\u2240','wreath':'\\\\u2240','wscr':'\\\\uD835\\\\uDCCC','Wscr':'\\\\uD835\\\\uDCB2','xcap':'\\\\u22C2','xcirc':'\\\\u25EF','xcup':'\\\\u22C3','xdtri':'\\\\u25BD','xfr':'\\\\uD835\\\\uDD35','Xfr':'\\\\uD835\\\\uDD1B','xharr':'\\\\u27F7','xhArr':'\\\\u27FA','xi':'\\\\u03BE','Xi':'\\\\u039E','xlarr':'\\\\u27F5','xlArr':'\\\\u27F8','xmap':'\\\\u27FC','xnis':'\\\\u22FB','xodot':'\\\\u2A00','xopf':'\\\\uD835\\\\uDD69','Xopf':'\\\\uD835\\\\uDD4F','xoplus':'\\\\u2A01','xotime':'\\\\u2A02','xrarr':'\\\\u27F6','xrArr':'\\\\u27F9','xscr':'\\\\uD835\\\\uDCCD','Xscr':'\\\\uD835\\\\uDCB3','xsqcup':'\\\\u2A06','xuplus':'\\\\u2A04','xutri':'\\\\u25B3','xvee':'\\\\u22C1','xwedge':'\\\\u22C0','yacute':'\\\\xFD','Yacute':'\\\\xDD','yacy':'\\\\u044F','YAcy':'\\\\u042F','ycirc':'\\\\u0177','Ycirc':'\\\\u0176','ycy':'\\\\u044B','Ycy':'\\\\u042B','yen':'\\\\xA5','yfr':'\\\\uD835\\\\uDD36','Yfr':'\\\\uD835\\\\uDD1C','yicy':'\\\\u0457','YIcy':'\\\\u0407','yopf':'\\\\uD835\\\\uDD6A','Yopf':'\\\\uD835\\\\uDD50','yscr':'\\\\uD835\\\\uDCCE','Yscr':'\\\\uD835\\\\uDCB4','yucy':'\\\\u044E','YUcy':'\\\\u042E','yuml':'\\\\xFF','Yuml':'\\\\u0178','zacute':'\\\\u017A','Zacute':'\\\\u0179','zcaron':'\\\\u017E','Zcaron':'\\\\u017D','zcy':'\\\\u0437','Zcy':'\\\\u0417','zdot':'\\\\u017C','Zdot':'\\\\u017B','zeetrf':'\\\\u2128','ZeroWidthSpace':'\\\\u200B','zeta':'\\\\u03B6','Zeta':'\\\\u0396','zfr':'\\\\uD835\\\\uDD37','Zfr':'\\\\u2128','zhcy':'\\\\u0436','ZHcy':'\\\\u0416','zigrarr':'\\\\u21DD','zopf':'\\\\uD835\\\\uDD6B','Zopf':'\\\\u2124','zscr':'\\\\uD835\\\\uDCCF','Zscr':'\\\\uD835\\\\uDCB5','zwj':'\\\\u200D','zwnj':'\\\\u200C'};\\n\\tvar decodeMapLegacy = {'aacute':'\\\\xE1','Aacute':'\\\\xC1','acirc':'\\\\xE2','Acirc':'\\\\xC2','acute':'\\\\xB4','aelig':'\\\\xE6','AElig':'\\\\xC6','agrave':'\\\\xE0','Agrave':'\\\\xC0','amp':'&','AMP':'&','aring':'\\\\xE5','Aring':'\\\\xC5','atilde':'\\\\xE3','Atilde':'\\\\xC3','auml':'\\\\xE4','Auml':'\\\\xC4','brvbar':'\\\\xA6','ccedil':'\\\\xE7','Ccedil':'\\\\xC7','cedil':'\\\\xB8','cent':'\\\\xA2','copy':'\\\\xA9','COPY':'\\\\xA9','curren':'\\\\xA4','deg':'\\\\xB0','divide':'\\\\xF7','eacute':'\\\\xE9','Eacute':'\\\\xC9','ecirc':'\\\\xEA','Ecirc':'\\\\xCA','egrave':'\\\\xE8','Egrave':'\\\\xC8','eth':'\\\\xF0','ETH':'\\\\xD0','euml':'\\\\xEB','Euml':'\\\\xCB','frac12':'\\\\xBD','frac14':'\\\\xBC','frac34':'\\\\xBE','gt':'>','GT':'>','iacute':'\\\\xED','Iacute':'\\\\xCD','icirc':'\\\\xEE','Icirc':'\\\\xCE','iexcl':'\\\\xA1','igrave':'\\\\xEC','Igrave':'\\\\xCC','iquest':'\\\\xBF','iuml':'\\\\xEF','Iuml':'\\\\xCF','laquo':'\\\\xAB','lt':'<','LT':'<','macr':'\\\\xAF','micro':'\\\\xB5','middot':'\\\\xB7','nbsp':'\\\\xA0','not':'\\\\xAC','ntilde':'\\\\xF1','Ntilde':'\\\\xD1','oacute':'\\\\xF3','Oacute':'\\\\xD3','ocirc':'\\\\xF4','Ocirc':'\\\\xD4','ograve':'\\\\xF2','Ograve':'\\\\xD2','ordf':'\\\\xAA','ordm':'\\\\xBA','oslash':'\\\\xF8','Oslash':'\\\\xD8','otilde':'\\\\xF5','Otilde':'\\\\xD5','ouml':'\\\\xF6','Ouml':'\\\\xD6','para':'\\\\xB6','plusmn':'\\\\xB1','pound':'\\\\xA3','quot':'\\\"','QUOT':'\\\"','raquo':'\\\\xBB','reg':'\\\\xAE','REG':'\\\\xAE','sect':'\\\\xA7','shy':'\\\\xAD','sup1':'\\\\xB9','sup2':'\\\\xB2','sup3':'\\\\xB3','szlig':'\\\\xDF','thorn':'\\\\xFE','THORN':'\\\\xDE','times':'\\\\xD7','uacute':'\\\\xFA','Uacute':'\\\\xDA','ucirc':'\\\\xFB','Ucirc':'\\\\xDB','ugrave':'\\\\xF9','Ugrave':'\\\\xD9','uml':'\\\\xA8','uuml':'\\\\xFC','Uuml':'\\\\xDC','yacute':'\\\\xFD','Yacute':'\\\\xDD','yen':'\\\\xA5','yuml':'\\\\xFF'};\\n\\tvar decodeMapNumeric = {'0':'\\\\uFFFD','128':'\\\\u20AC','130':'\\\\u201A','131':'\\\\u0192','132':'\\\\u201E','133':'\\\\u2026','134':'\\\\u2020','135':'\\\\u2021','136':'\\\\u02C6','137':'\\\\u2030','138':'\\\\u0160','139':'\\\\u2039','140':'\\\\u0152','142':'\\\\u017D','145':'\\\\u2018','146':'\\\\u2019','147':'\\\\u201C','148':'\\\\u201D','149':'\\\\u2022','150':'\\\\u2013','151':'\\\\u2014','152':'\\\\u02DC','153':'\\\\u2122','154':'\\\\u0161','155':'\\\\u203A','156':'\\\\u0153','158':'\\\\u017E','159':'\\\\u0178'};\\n\\tvar invalidReferenceCodePoints = [1,2,3,4,5,6,7,8,11,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,144,145,146,147,148,149,150,151,152,153,154,155,156,157,158,159,64976,64977,64978,64979,64980,64981,64982,64983,64984,64985,64986,64987,64988,64989,64990,64991,64992,64993,64994,64995,64996,64997,64998,64999,65000,65001,65002,65003,65004,65005,65006,65007,65534,65535,131070,131071,196606,196607,262142,262143,327678,327679,393214,393215,458750,458751,524286,524287,589822,589823,655358,655359,720894,720895,786430,786431,851966,851967,917502,917503,983038,983039,1048574,1048575,1114110,1114111];\\n\\n\\t/*--------------------------------------------------------------------------*/\\n\\n\\tvar stringFromCharCode = String.fromCharCode;\\n\\n\\tvar object = {};\\n\\tvar hasOwnProperty = object.hasOwnProperty;\\n\\tvar has = function(object, propertyName) {\\n\\t\\treturn hasOwnProperty.call(object, propertyName);\\n\\t};\\n\\n\\tvar contains = function(array, value) {\\n\\t\\tvar index = -1;\\n\\t\\tvar length = array.length;\\n\\t\\twhile (++index < length) {\\n\\t\\t\\tif (array[index] == value) {\\n\\t\\t\\t\\treturn true;\\n\\t\\t\\t}\\n\\t\\t}\\n\\t\\treturn false;\\n\\t};\\n\\n\\tvar merge = function(options, defaults) {\\n\\t\\tif (!options) {\\n\\t\\t\\treturn defaults;\\n\\t\\t}\\n\\t\\tvar result = {};\\n\\t\\tvar key;\\n\\t\\tfor (key in defaults) {\\n\\t\\t\\t// A `hasOwnProperty` check is not needed here, since only recognized\\n\\t\\t\\t// option names are used anyway. Any others are ignored.\\n\\t\\t\\tresult[key] = has(options, key) ? options[key] : defaults[key];\\n\\t\\t}\\n\\t\\treturn result;\\n\\t};\\n\\n\\t// Modified version of `ucs2encode`; see https://mths.be/punycode.\\n\\tvar codePointToSymbol = function(codePoint, strict) {\\n\\t\\tvar output = '';\\n\\t\\tif ((codePoint >= 0xD800 && codePoint <= 0xDFFF) || codePoint > 0x10FFFF) {\\n\\t\\t\\t// See issue #4:\\n\\t\\t\\t// “Otherwise, if the number is in the range 0xD800 to 0xDFFF or is\\n\\t\\t\\t// greater than 0x10FFFF, then this is a parse error. Return a U+FFFD\\n\\t\\t\\t// REPLACEMENT CHARACTER.”\\n\\t\\t\\tif (strict) {\\n\\t\\t\\t\\tparseError('character reference outside the permissible Unicode range');\\n\\t\\t\\t}\\n\\t\\t\\treturn '\\\\uFFFD';\\n\\t\\t}\\n\\t\\tif (has(decodeMapNumeric, codePoint)) {\\n\\t\\t\\tif (strict) {\\n\\t\\t\\t\\tparseError('disallowed character reference');\\n\\t\\t\\t}\\n\\t\\t\\treturn decodeMapNumeric[codePoint];\\n\\t\\t}\\n\\t\\tif (strict && contains(invalidReferenceCodePoints, codePoint)) {\\n\\t\\t\\tparseError('disallowed character reference');\\n\\t\\t}\\n\\t\\tif (codePoint > 0xFFFF) {\\n\\t\\t\\tcodePoint -= 0x10000;\\n\\t\\t\\toutput += stringFromCharCode(codePoint >>> 10 & 0x3FF | 0xD800);\\n\\t\\t\\tcodePoint = 0xDC00 | codePoint & 0x3FF;\\n\\t\\t}\\n\\t\\toutput += stringFromCharCode(codePoint);\\n\\t\\treturn output;\\n\\t};\\n\\n\\tvar hexEscape = function(codePoint) {\\n\\t\\treturn '&#x' + codePoint.toString(16).toUpperCase() + ';';\\n\\t};\\n\\n\\tvar decEscape = function(codePoint) {\\n\\t\\treturn '&#' + codePoint + ';';\\n\\t};\\n\\n\\tvar parseError = function(message) {\\n\\t\\tthrow Error('Parse error: ' + message);\\n\\t};\\n\\n\\t/*--------------------------------------------------------------------------*/\\n\\n\\tvar encode = function(string, options) {\\n\\t\\toptions = merge(options, encode.options);\\n\\t\\tvar strict = options.strict;\\n\\t\\tif (strict && regexInvalidRawCodePoint.test(string)) {\\n\\t\\t\\tparseError('forbidden code point');\\n\\t\\t}\\n\\t\\tvar encodeEverything = options.encodeEverything;\\n\\t\\tvar useNamedReferences = options.useNamedReferences;\\n\\t\\tvar allowUnsafeSymbols = options.allowUnsafeSymbols;\\n\\t\\tvar escapeCodePoint = options.decimal ? decEscape : hexEscape;\\n\\n\\t\\tvar escapeBmpSymbol = function(symbol) {\\n\\t\\t\\treturn escapeCodePoint(symbol.charCodeAt(0));\\n\\t\\t};\\n\\n\\t\\tif (encodeEverything) {\\n\\t\\t\\t// Encode ASCII symbols.\\n\\t\\t\\tstring = string.replace(regexAsciiWhitelist, function(symbol) {\\n\\t\\t\\t\\t// Use named references if requested & possible.\\n\\t\\t\\t\\tif (useNamedReferences && has(encodeMap, symbol)) {\\n\\t\\t\\t\\t\\treturn '&' + encodeMap[symbol] + ';';\\n\\t\\t\\t\\t}\\n\\t\\t\\t\\treturn escapeBmpSymbol(symbol);\\n\\t\\t\\t});\\n\\t\\t\\t// Shorten a few escapes that represent two symbols, of which at least one\\n\\t\\t\\t// is within the ASCII range.\\n\\t\\t\\tif (useNamedReferences) {\\n\\t\\t\\t\\tstring = string\\n\\t\\t\\t\\t\\t.replace(/>\\\\u20D2/g, '>⃒')\\n\\t\\t\\t\\t\\t.replace(/<\\\\u20D2/g, '<⃒')\\n\\t\\t\\t\\t\\t.replace(/fj/g, 'fj');\\n\\t\\t\\t}\\n\\t\\t\\t// Encode non-ASCII symbols.\\n\\t\\t\\tif (useNamedReferences) {\\n\\t\\t\\t\\t// Encode non-ASCII symbols that can be replaced with a named reference.\\n\\t\\t\\t\\tstring = string.replace(regexEncodeNonAscii, function(string) {\\n\\t\\t\\t\\t\\t// Note: there is no need to check `has(encodeMap, string)` here.\\n\\t\\t\\t\\t\\treturn '&' + encodeMap[string] + ';';\\n\\t\\t\\t\\t});\\n\\t\\t\\t}\\n\\t\\t\\t// Note: any remaining non-ASCII symbols are handled outside of the `if`.\\n\\t\\t} else if (useNamedReferences) {\\n\\t\\t\\t// Apply named character references.\\n\\t\\t\\t// Encode `<>\\\"'&` using named character references.\\n\\t\\t\\tif (!allowUnsafeSymbols) {\\n\\t\\t\\t\\tstring = string.replace(regexEscape, function(string) {\\n\\t\\t\\t\\t\\treturn '&' + encodeMap[string] + ';'; // no need to check `has()` here\\n\\t\\t\\t\\t});\\n\\t\\t\\t}\\n\\t\\t\\t// Shorten escapes that represent two symbols, of which at least one is\\n\\t\\t\\t// `<>\\\"'&`.\\n\\t\\t\\tstring = string\\n\\t\\t\\t\\t.replace(/>\\\\u20D2/g, '>⃒')\\n\\t\\t\\t\\t.replace(/<\\\\u20D2/g, '<⃒');\\n\\t\\t\\t// Encode non-ASCII symbols that can be replaced with a named reference.\\n\\t\\t\\tstring = string.replace(regexEncodeNonAscii, function(string) {\\n\\t\\t\\t\\t// Note: there is no need to check `has(encodeMap, string)` here.\\n\\t\\t\\t\\treturn '&' + encodeMap[string] + ';';\\n\\t\\t\\t});\\n\\t\\t} else if (!allowUnsafeSymbols) {\\n\\t\\t\\t// Encode `<>\\\"'&` using hexadecimal escapes, now that they’re not handled\\n\\t\\t\\t// using named character references.\\n\\t\\t\\tstring = string.replace(regexEscape, escapeBmpSymbol);\\n\\t\\t}\\n\\t\\treturn string\\n\\t\\t\\t// Encode astral symbols.\\n\\t\\t\\t.replace(regexAstralSymbols, function($0) {\\n\\t\\t\\t\\t// https://mathiasbynens.be/notes/javascript-encoding#surrogate-formulae\\n\\t\\t\\t\\tvar high = $0.charCodeAt(0);\\n\\t\\t\\t\\tvar low = $0.charCodeAt(1);\\n\\t\\t\\t\\tvar codePoint = (high - 0xD800) * 0x400 + low - 0xDC00 + 0x10000;\\n\\t\\t\\t\\treturn escapeCodePoint(codePoint);\\n\\t\\t\\t})\\n\\t\\t\\t// Encode any remaining BMP symbols that are not printable ASCII symbols\\n\\t\\t\\t// using a hexadecimal escape.\\n\\t\\t\\t.replace(regexBmpWhitelist, escapeBmpSymbol);\\n\\t};\\n\\t// Expose default options (so they can be overridden globally).\\n\\tencode.options = {\\n\\t\\t'allowUnsafeSymbols': false,\\n\\t\\t'encodeEverything': false,\\n\\t\\t'strict': false,\\n\\t\\t'useNamedReferences': false,\\n\\t\\t'decimal' : false\\n\\t};\\n\\n\\tvar decode = function(html, options) {\\n\\t\\toptions = merge(options, decode.options);\\n\\t\\tvar strict = options.strict;\\n\\t\\tif (strict && regexInvalidEntity.test(html)) {\\n\\t\\t\\tparseError('malformed character reference');\\n\\t\\t}\\n\\t\\treturn html.replace(regexDecode, function($0, $1, $2, $3, $4, $5, $6, $7, $8) {\\n\\t\\t\\tvar codePoint;\\n\\t\\t\\tvar semicolon;\\n\\t\\t\\tvar decDigits;\\n\\t\\t\\tvar hexDigits;\\n\\t\\t\\tvar reference;\\n\\t\\t\\tvar next;\\n\\n\\t\\t\\tif ($1) {\\n\\t\\t\\t\\treference = $1;\\n\\t\\t\\t\\t// Note: there is no need to check `has(decodeMap, reference)`.\\n\\t\\t\\t\\treturn decodeMap[reference];\\n\\t\\t\\t}\\n\\n\\t\\t\\tif ($2) {\\n\\t\\t\\t\\t// Decode named character references without trailing `;`, e.g. `&`.\\n\\t\\t\\t\\t// This is only a parse error if it gets converted to `&`, or if it is\\n\\t\\t\\t\\t// followed by `=` in an attribute context.\\n\\t\\t\\t\\treference = $2;\\n\\t\\t\\t\\tnext = $3;\\n\\t\\t\\t\\tif (next && options.isAttributeValue) {\\n\\t\\t\\t\\t\\tif (strict && next == '=') {\\n\\t\\t\\t\\t\\t\\tparseError('`&` did not start a character reference');\\n\\t\\t\\t\\t\\t}\\n\\t\\t\\t\\t\\treturn $0;\\n\\t\\t\\t\\t} else {\\n\\t\\t\\t\\t\\tif (strict) {\\n\\t\\t\\t\\t\\t\\tparseError(\\n\\t\\t\\t\\t\\t\\t\\t'named character reference was not terminated by a semicolon'\\n\\t\\t\\t\\t\\t\\t);\\n\\t\\t\\t\\t\\t}\\n\\t\\t\\t\\t\\t// Note: there is no need to check `has(decodeMapLegacy, reference)`.\\n\\t\\t\\t\\t\\treturn decodeMapLegacy[reference] + (next || '');\\n\\t\\t\\t\\t}\\n\\t\\t\\t}\\n\\n\\t\\t\\tif ($4) {\\n\\t\\t\\t\\t// Decode decimal escapes, e.g. `𝌆`.\\n\\t\\t\\t\\tdecDigits = $4;\\n\\t\\t\\t\\tsemicolon = $5;\\n\\t\\t\\t\\tif (strict && !semicolon) {\\n\\t\\t\\t\\t\\tparseError('character reference was not terminated by a semicolon');\\n\\t\\t\\t\\t}\\n\\t\\t\\t\\tcodePoint = parseInt(decDigits, 10);\\n\\t\\t\\t\\treturn codePointToSymbol(codePoint, strict);\\n\\t\\t\\t}\\n\\n\\t\\t\\tif ($6) {\\n\\t\\t\\t\\t// Decode hexadecimal escapes, e.g. `𝌆`.\\n\\t\\t\\t\\thexDigits = $6;\\n\\t\\t\\t\\tsemicolon = $7;\\n\\t\\t\\t\\tif (strict && !semicolon) {\\n\\t\\t\\t\\t\\tparseError('character reference was not terminated by a semicolon');\\n\\t\\t\\t\\t}\\n\\t\\t\\t\\tcodePoint = parseInt(hexDigits, 16);\\n\\t\\t\\t\\treturn codePointToSymbol(codePoint, strict);\\n\\t\\t\\t}\\n\\n\\t\\t\\t// If we’re still here, `if ($7)` is implied; it’s an ambiguous\\n\\t\\t\\t// ampersand for sure. https://mths.be/notes/ambiguous-ampersands\\n\\t\\t\\tif (strict) {\\n\\t\\t\\t\\tparseError(\\n\\t\\t\\t\\t\\t'named character reference was not terminated by a semicolon'\\n\\t\\t\\t\\t);\\n\\t\\t\\t}\\n\\t\\t\\treturn $0;\\n\\t\\t});\\n\\t};\\n\\t// Expose default options (so they can be overridden globally).\\n\\tdecode.options = {\\n\\t\\t'isAttributeValue': false,\\n\\t\\t'strict': false\\n\\t};\\n\\n\\tvar escape = function(string) {\\n\\t\\treturn string.replace(regexEscape, function($0) {\\n\\t\\t\\t// Note: there is no need to check `has(escapeMap, $0)` here.\\n\\t\\t\\treturn escapeMap[$0];\\n\\t\\t});\\n\\t};\\n\\n\\t/*--------------------------------------------------------------------------*/\\n\\n\\tvar he = {\\n\\t\\t'version': '1.2.0',\\n\\t\\t'encode': encode,\\n\\t\\t'decode': decode,\\n\\t\\t'escape': escape,\\n\\t\\t'unescape': decode\\n\\t};\\n\\n\\t// Some AMD build optimizers, like r.js, check for specific condition patterns\\n\\t// like the following:\\n\\tif (\\n\\t\\ttypeof define == 'function' &&\\n\\t\\ttypeof define.amd == 'object' &&\\n\\t\\tdefine.amd\\n\\t) {\\n\\t\\tdefine(function() {\\n\\t\\t\\treturn he;\\n\\t\\t});\\n\\t}\\telse if (freeExports && !freeExports.nodeType) {\\n\\t\\tif (freeModule) { // in Node.js, io.js, or RingoJS v0.8.0+\\n\\t\\t\\tfreeModule.exports = he;\\n\\t\\t} else { // in Narwhal or RingoJS v0.7.0-\\n\\t\\t\\tfor (var key in he) {\\n\\t\\t\\t\\thas(he, key) && (freeExports[key] = he[key]);\\n\\t\\t\\t}\\n\\t\\t}\\n\\t} else { // in Rhino or a web browser\\n\\t\\troot.he = he;\\n\\t}\\n\\n}(this));\\n\",\"/* globals define,module */\\n/*\\nUsing a Universal Module Loader that should be browser, require, and AMD friendly\\nhttp://ricostacruz.com/cheatsheets/umdjs.html\\n*/\\n;(function(root, factory) {\\n if (typeof define === \\\"function\\\" && define.amd) {\\n define(factory);\\n } else if (typeof exports === \\\"object\\\") {\\n module.exports = factory();\\n } else {\\n root.jsonLogic = factory();\\n }\\n}(this, function() {\\n \\\"use strict\\\";\\n /* globals console:false */\\n\\n if ( ! Array.isArray) {\\n Array.isArray = function(arg) {\\n return Object.prototype.toString.call(arg) === \\\"[object Array]\\\";\\n };\\n }\\n\\n /**\\n * Return an array that contains no duplicates (original not modified)\\n * @param {array} array Original reference array\\n * @return {array} New array with no duplicates\\n */\\n function arrayUnique(array) {\\n var a = [];\\n for (var i=0, l=array.length; i\\\": function(a, b) {\\n return a > b;\\n },\\n \\\">=\\\": function(a, b) {\\n return a >= b;\\n },\\n \\\"<\\\": function(a, b, c) {\\n return (c === undefined) ? a < b : (a < b) && (b < c);\\n },\\n \\\"<=\\\": function(a, b, c) {\\n return (c === undefined) ? a <= b : (a <= b) && (b <= c);\\n },\\n \\\"!!\\\": function(a) {\\n return jsonLogic.truthy(a);\\n },\\n \\\"!\\\": function(a) {\\n return !jsonLogic.truthy(a);\\n },\\n \\\"%\\\": function(a, b) {\\n return a % b;\\n },\\n \\\"log\\\": function(a) {\\n console.log(a); return a;\\n },\\n \\\"in\\\": function(a, b) {\\n if (!b || typeof b.indexOf === \\\"undefined\\\") return false;\\n return (b.indexOf(a) !== -1);\\n },\\n \\\"cat\\\": function() {\\n return Array.prototype.join.call(arguments, \\\"\\\");\\n },\\n \\\"substr\\\": function(source, start, end) {\\n if (end < 0) {\\n // JavaScript doesn't support negative end, this emulates PHP behavior\\n var temp = String(source).substr(start);\\n return temp.substr(0, temp.length + end);\\n }\\n return String(source).substr(start, end);\\n },\\n \\\"+\\\": function() {\\n return Array.prototype.reduce.call(arguments, function(a, b) {\\n return parseFloat(a, 10) + parseFloat(b, 10);\\n }, 0);\\n },\\n \\\"*\\\": function() {\\n return Array.prototype.reduce.call(arguments, function(a, b) {\\n return parseFloat(a, 10) * parseFloat(b, 10);\\n });\\n },\\n \\\"-\\\": function(a, b) {\\n if (b === undefined) {\\n return -a;\\n } else {\\n return a - b;\\n }\\n },\\n \\\"/\\\": function(a, b) {\\n return a / b;\\n },\\n \\\"min\\\": function() {\\n return Math.min.apply(this, arguments);\\n },\\n \\\"max\\\": function() {\\n return Math.max.apply(this, arguments);\\n },\\n \\\"merge\\\": function() {\\n return Array.prototype.reduce.call(arguments, function(a, b) {\\n return a.concat(b);\\n }, []);\\n },\\n \\\"var\\\": function(a, b) {\\n var not_found = (b === undefined) ? null : b;\\n var data = this;\\n if (typeof a === \\\"undefined\\\" || a===\\\"\\\" || a===null) {\\n return data;\\n }\\n var sub_props = String(a).split(\\\".\\\");\\n for (var i = 0; i < sub_props.length; i++) {\\n if (data === null || data === undefined) {\\n return not_found;\\n }\\n // Descending into data\\n data = data[sub_props[i]];\\n if (data === undefined) {\\n return not_found;\\n }\\n }\\n return data;\\n },\\n \\\"missing\\\": function() {\\n /*\\n Missing can receive many keys as many arguments, like {\\\"missing:[1,2]}\\n Missing can also receive *one* argument that is an array of keys,\\n which typically happens if it's actually acting on the output of another command\\n (like 'if' or 'merge')\\n */\\n\\n var missing = [];\\n var keys = Array.isArray(arguments[0]) ? arguments[0] : arguments;\\n\\n for (var i = 0; i < keys.length; i++) {\\n var key = keys[i];\\n var value = jsonLogic.apply({\\\"var\\\": key}, this);\\n if (value === null || value === \\\"\\\") {\\n missing.push(key);\\n }\\n }\\n\\n return missing;\\n },\\n \\\"missing_some\\\": function(need_count, options) {\\n // missing_some takes two arguments, how many (minimum) items must be present, and an array of keys (just like 'missing') to check for presence.\\n var are_missing = jsonLogic.apply({\\\"missing\\\": options}, this);\\n\\n if (options.length - are_missing.length >= need_count) {\\n return [];\\n } else {\\n return are_missing;\\n }\\n },\\n };\\n\\n jsonLogic.is_logic = function(logic) {\\n return (\\n typeof logic === \\\"object\\\" && // An object\\n logic !== null && // but not null\\n ! Array.isArray(logic) && // and not an array\\n Object.keys(logic).length === 1 // with exactly one key\\n );\\n };\\n\\n /*\\n This helper will defer to the JsonLogic spec as a tie-breaker when different language interpreters define different behavior for the truthiness of primitives. E.g., PHP considers empty arrays to be falsy, but Javascript considers them to be truthy. JsonLogic, as an ecosystem, needs one consistent answer.\\n\\n Spec and rationale here: http://jsonlogic.com/truthy\\n */\\n jsonLogic.truthy = function(value) {\\n if (Array.isArray(value) && value.length === 0) {\\n return false;\\n }\\n return !! value;\\n };\\n\\n\\n jsonLogic.get_operator = function(logic) {\\n return Object.keys(logic)[0];\\n };\\n\\n jsonLogic.get_values = function(logic) {\\n return logic[jsonLogic.get_operator(logic)];\\n };\\n\\n jsonLogic.apply = function(logic, data) {\\n // Does this array contain logic? Only one way to find out.\\n if (Array.isArray(logic)) {\\n return logic.map(function(l) {\\n return jsonLogic.apply(l, data);\\n });\\n }\\n // You've recursed to a primitive, stop!\\n if ( ! jsonLogic.is_logic(logic) ) {\\n return logic;\\n }\\n\\n var op = jsonLogic.get_operator(logic);\\n var values = logic[op];\\n var i;\\n var current;\\n var scopedLogic;\\n var scopedData;\\n var initial;\\n\\n // easy syntax for unary operators, like {\\\"var\\\" : \\\"x\\\"} instead of strict {\\\"var\\\" : [\\\"x\\\"]}\\n if ( ! Array.isArray(values)) {\\n values = [values];\\n }\\n\\n // 'if', 'and', and 'or' violate the normal rule of depth-first calculating consequents, let each manage recursion as needed.\\n if (op === \\\"if\\\" || op == \\\"?:\\\") {\\n /* 'if' should be called with a odd number of parameters, 3 or greater\\n This works on the pattern:\\n if( 0 ){ 1 }else{ 2 };\\n if( 0 ){ 1 }else if( 2 ){ 3 }else{ 4 };\\n if( 0 ){ 1 }else if( 2 ){ 3 }else if( 4 ){ 5 }else{ 6 };\\n\\n The implementation is:\\n For pairs of values (0,1 then 2,3 then 4,5 etc)\\n If the first evaluates truthy, evaluate and return the second\\n If the first evaluates falsy, jump to the next pair (e.g, 0,1 to 2,3)\\n given one parameter, evaluate and return it. (it's an Else and all the If/ElseIf were false)\\n given 0 parameters, return NULL (not great practice, but there was no Else)\\n */\\n for (i = 0; i < values.length - 1; i += 2) {\\n if ( jsonLogic.truthy( jsonLogic.apply(values[i], data) ) ) {\\n return jsonLogic.apply(values[i+1], data);\\n }\\n }\\n if (values.length === i+1) {\\n return jsonLogic.apply(values[i], data);\\n }\\n return null;\\n } else if (op === \\\"and\\\") { // Return first falsy, or last\\n for (i=0; i < values.length; i+=1) {\\n current = jsonLogic.apply(values[i], data);\\n if ( ! jsonLogic.truthy(current)) {\\n return current;\\n }\\n }\\n return current; // Last\\n } else if (op === \\\"or\\\") {// Return first truthy, or last\\n for (i=0; i < values.length; i+=1) {\\n current = jsonLogic.apply(values[i], data);\\n if ( jsonLogic.truthy(current) ) {\\n return current;\\n }\\n }\\n return current; // Last\\n } else if (op === \\\"filter\\\") {\\n scopedData = jsonLogic.apply(values[0], data);\\n scopedLogic = values[1];\\n\\n if ( ! Array.isArray(scopedData)) {\\n return [];\\n }\\n // Return only the elements from the array in the first argument,\\n // that return truthy when passed to the logic in the second argument.\\n // For parity with JavaScript, reindex the returned array\\n return scopedData.filter(function(datum) {\\n return jsonLogic.truthy( jsonLogic.apply(scopedLogic, datum));\\n });\\n } else if (op === \\\"map\\\") {\\n scopedData = jsonLogic.apply(values[0], data);\\n scopedLogic = values[1];\\n\\n if ( ! Array.isArray(scopedData)) {\\n return [];\\n }\\n\\n return scopedData.map(function(datum) {\\n return jsonLogic.apply(scopedLogic, datum);\\n });\\n } else if (op === \\\"reduce\\\") {\\n scopedData = jsonLogic.apply(values[0], data);\\n scopedLogic = values[1];\\n initial = typeof values[2] !== \\\"undefined\\\" ? jsonLogic.apply(values[2], data) : null;\\n\\n if ( ! Array.isArray(scopedData)) {\\n return initial;\\n }\\n\\n return scopedData.reduce(\\n function(accumulator, current) {\\n return jsonLogic.apply(\\n scopedLogic,\\n {current: current, accumulator: accumulator}\\n );\\n },\\n initial\\n );\\n } else if (op === \\\"all\\\") {\\n scopedData = jsonLogic.apply(values[0], data);\\n scopedLogic = values[1];\\n // All of an empty set is false. Note, some and none have correct fallback after the for loop\\n if ( ! Array.isArray(scopedData) || ! scopedData.length) {\\n return false;\\n }\\n for (i=0; i < scopedData.length; i+=1) {\\n if ( ! jsonLogic.truthy( jsonLogic.apply(scopedLogic, scopedData[i]) )) {\\n return false; // First falsy, short circuit\\n }\\n }\\n return true; // All were truthy\\n } else if (op === \\\"none\\\") {\\n scopedData = jsonLogic.apply(values[0], data);\\n scopedLogic = values[1];\\n\\n if ( ! Array.isArray(scopedData) || ! scopedData.length) {\\n return true;\\n }\\n for (i=0; i < scopedData.length; i+=1) {\\n if ( jsonLogic.truthy( jsonLogic.apply(scopedLogic, scopedData[i]) )) {\\n return false; // First truthy, short circuit\\n }\\n }\\n return true; // None were truthy\\n } else if (op === \\\"some\\\") {\\n scopedData = jsonLogic.apply(values[0], data);\\n scopedLogic = values[1];\\n\\n if ( ! Array.isArray(scopedData) || ! scopedData.length) {\\n return false;\\n }\\n for (i=0; i < scopedData.length; i+=1) {\\n if ( jsonLogic.truthy( jsonLogic.apply(scopedLogic, scopedData[i]) )) {\\n return true; // First truthy, short circuit\\n }\\n }\\n return false; // None were truthy\\n }\\n\\n // Everyone else gets immediate depth-first recursion\\n values = values.map(function(val) {\\n return jsonLogic.apply(val, data);\\n });\\n\\n\\n // The operation is called with \\\"data\\\" bound to its \\\"this\\\" and \\\"values\\\" passed as arguments.\\n // Structured commands like % or > can name formal arguments while flexible commands (like missing or merge) can operate on the pseudo-array arguments\\n // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Functions/arguments\\n if (operations.hasOwnProperty(op) && typeof operations[op] === \\\"function\\\") {\\n return operations[op].apply(data, values);\\n } else if (op.indexOf(\\\".\\\") > 0) { // Contains a dot, and not in the 0th position\\n var sub_ops = String(op).split(\\\".\\\");\\n var operation = operations;\\n for (i = 0; i < sub_ops.length; i++) {\\n if (!operation.hasOwnProperty(sub_ops[i])) {\\n throw new Error(\\\"Unrecognized operation \\\" + op +\\n \\\" (failed at \\\" + sub_ops.slice(0, i+1).join(\\\".\\\") + \\\")\\\");\\n }\\n // Descending into operations\\n operation = operation[sub_ops[i]];\\n }\\n\\n return operation.apply(data, values);\\n }\\n\\n throw new Error(\\\"Unrecognized operation \\\" + op );\\n };\\n\\n jsonLogic.uses_data = function(logic) {\\n var collection = [];\\n\\n if (jsonLogic.is_logic(logic)) {\\n var op = jsonLogic.get_operator(logic);\\n var values = logic[op];\\n\\n if ( ! Array.isArray(values)) {\\n values = [values];\\n }\\n\\n if (op === \\\"var\\\") {\\n // This doesn't cover the case where the arg to var is itself a rule.\\n collection.push(values[0]);\\n } else {\\n // Recursion!\\n values.forEach(function(val) {\\n collection.push.apply(collection, jsonLogic.uses_data(val) );\\n });\\n }\\n }\\n\\n return arrayUnique(collection);\\n };\\n\\n jsonLogic.add_operation = function(name, code) {\\n operations[name] = code;\\n };\\n\\n jsonLogic.rm_operation = function(name) {\\n delete operations[name];\\n };\\n\\n jsonLogic.rule_like = function(rule, pattern) {\\n // console.log(\\\"Is \\\". JSON.stringify(rule) . \\\" like \\\" . JSON.stringify(pattern) . \\\"?\\\");\\n if (pattern === rule) {\\n return true;\\n } // TODO : Deep object equivalency?\\n if (pattern === \\\"@\\\") {\\n return true;\\n } // Wildcard!\\n if (pattern === \\\"number\\\") {\\n return (typeof rule === \\\"number\\\");\\n }\\n if (pattern === \\\"string\\\") {\\n return (typeof rule === \\\"string\\\");\\n }\\n if (pattern === \\\"array\\\") {\\n // !logic test might be superfluous in JavaScript\\n return Array.isArray(rule) && ! jsonLogic.is_logic(rule);\\n }\\n\\n if (jsonLogic.is_logic(pattern)) {\\n if (jsonLogic.is_logic(rule)) {\\n var pattern_op = jsonLogic.get_operator(pattern);\\n var rule_op = jsonLogic.get_operator(rule);\\n\\n if (pattern_op === \\\"@\\\" || pattern_op === rule_op) {\\n // echo \\\"\\\\nOperators match, go deeper\\\\n\\\";\\n return jsonLogic.rule_like(\\n jsonLogic.get_values(rule, false),\\n jsonLogic.get_values(pattern, false)\\n );\\n }\\n }\\n return false; // pattern is logic, rule isn't, can't be eq\\n }\\n\\n if (Array.isArray(pattern)) {\\n if (Array.isArray(rule)) {\\n if (pattern.length !== rule.length) {\\n return false;\\n }\\n /*\\n Note, array order MATTERS, because we're using this array test logic to consider arguments, where order can matter. (e.g., + is commutative, but '-' or 'if' or 'var' are NOT)\\n */\\n for (var i = 0; i < pattern.length; i += 1) {\\n // If any fail, we fail\\n if ( ! jsonLogic.rule_like(rule[i], pattern[i])) {\\n return false;\\n }\\n }\\n return true; // If they *all* passed, we pass\\n } else {\\n return false; // Pattern is array, rule isn't\\n }\\n }\\n\\n // Not logic, not array, not a === match for rule.\\n return false;\\n };\\n\\n return jsonLogic;\\n}));\\n\",\"const DEFAULT_DELIMITER = \\\"/\\\";\\nconst NOOP_VALUE = (value: string) => value;\\nconst ID_START = /^[$_\\\\p{ID_Start}]$/u;\\nconst ID_CONTINUE = /^[$\\\\u200c\\\\u200d\\\\p{ID_Continue}]$/u;\\n\\n/**\\n * Encode a string into another string.\\n */\\nexport type Encode = (value: string) => string;\\n\\n/**\\n * Decode a string into another string.\\n */\\nexport type Decode = (value: string) => string;\\n\\nexport interface ParseOptions {\\n /**\\n * A function for encoding input strings.\\n */\\n encodePath?: Encode;\\n}\\n\\nexport interface PathToRegexpOptions {\\n /**\\n * Matches the path completely without trailing characters. (default: `true`)\\n */\\n end?: boolean;\\n /**\\n * Allows optional trailing delimiter to match. (default: `true`)\\n */\\n trailing?: boolean;\\n /**\\n * Match will be case sensitive. (default: `false`)\\n */\\n sensitive?: boolean;\\n /**\\n * The default delimiter for segments. (default: `'/'`)\\n */\\n delimiter?: string;\\n}\\n\\nexport interface MatchOptions extends PathToRegexpOptions {\\n /**\\n * Function for decoding strings for params, or `false` to disable entirely. (default: `decodeURIComponent`)\\n */\\n decode?: Decode | false;\\n}\\n\\nexport interface CompileOptions {\\n /**\\n * Function for encoding input strings for output into the path, or `false` to disable entirely. (default: `encodeURIComponent`)\\n */\\n encode?: Encode | false;\\n /**\\n * The default delimiter for segments. (default: `'/'`)\\n */\\n delimiter?: string;\\n}\\n\\ntype TokenType =\\n | \\\"{\\\"\\n | \\\"}\\\"\\n | \\\"wildcard\\\"\\n | \\\"param\\\"\\n | \\\"char\\\"\\n | \\\"escape\\\"\\n | \\\"end\\\"\\n // Reserved for use or ambiguous due to past use.\\n | \\\"(\\\"\\n | \\\")\\\"\\n | \\\"[\\\"\\n | \\\"]\\\"\\n | \\\"+\\\"\\n | \\\"?\\\"\\n | \\\"!\\\";\\n\\n/**\\n * Tokenizer results.\\n */\\ninterface LexToken {\\n type: TokenType;\\n index: number;\\n value: string;\\n}\\n\\nconst SIMPLE_TOKENS: Record = {\\n // Groups.\\n \\\"{\\\": \\\"{\\\",\\n \\\"}\\\": \\\"}\\\",\\n // Reserved.\\n \\\"(\\\": \\\"(\\\",\\n \\\")\\\": \\\")\\\",\\n \\\"[\\\": \\\"[\\\",\\n \\\"]\\\": \\\"]\\\",\\n \\\"+\\\": \\\"+\\\",\\n \\\"?\\\": \\\"?\\\",\\n \\\"!\\\": \\\"!\\\",\\n};\\n\\n/**\\n * Escape text for stringify to path.\\n */\\nfunction escapeText(str: string) {\\n return str.replace(/[{}()\\\\[\\\\]+?!:*\\\\\\\\]/g, \\\"\\\\\\\\$&\\\");\\n}\\n\\n/**\\n * Escape a regular expression string.\\n */\\nfunction escape(str: string) {\\n return str.replace(/[.+*?^${}()[\\\\]|/\\\\\\\\]/g, \\\"\\\\\\\\$&\\\");\\n}\\n\\n/**\\n * Plain text.\\n */\\nexport interface Text {\\n type: \\\"text\\\";\\n value: string;\\n}\\n\\n/**\\n * A parameter designed to match arbitrary text within a segment.\\n */\\nexport interface Parameter {\\n type: \\\"param\\\";\\n name: string;\\n}\\n\\n/**\\n * A wildcard parameter designed to match multiple segments.\\n */\\nexport interface Wildcard {\\n type: \\\"wildcard\\\";\\n name: string;\\n}\\n\\n/**\\n * A set of possible tokens to expand when matching.\\n */\\nexport interface Group {\\n type: \\\"group\\\";\\n tokens: Token[];\\n}\\n\\n/**\\n * A token that corresponds with a regexp capture.\\n */\\nexport type Key = Parameter | Wildcard;\\n\\n/**\\n * A sequence of `path-to-regexp` keys that match capturing groups.\\n */\\nexport type Keys = Array;\\n\\n/**\\n * A sequence of path match characters.\\n */\\nexport type Token = Text | Parameter | Wildcard | Group;\\n\\n/**\\n * Tokenized path instance.\\n */\\nexport class TokenData {\\n constructor(\\n public readonly tokens: Token[],\\n public readonly originalPath?: string,\\n ) {}\\n}\\n\\n/**\\n * ParseError is thrown when there is an error processing the path.\\n */\\nexport class PathError extends TypeError {\\n constructor(\\n message: string,\\n public readonly originalPath: string | undefined,\\n ) {\\n let text = message;\\n if (originalPath) text += `: ${originalPath}`;\\n text += `; visit https://git.new/pathToRegexpError for info`;\\n super(text);\\n }\\n}\\n\\n/**\\n * Parse a string for the raw tokens.\\n */\\nexport function parse(str: string, options: ParseOptions = {}): TokenData {\\n const { encodePath = NOOP_VALUE } = options;\\n const chars = [...str];\\n const tokens: Array = [];\\n let index = 0;\\n let pos = 0;\\n\\n function name() {\\n let value = \\\"\\\";\\n\\n if (ID_START.test(chars[index])) {\\n do {\\n value += chars[index++];\\n } while (ID_CONTINUE.test(chars[index]));\\n } else if (chars[index] === '\\\"') {\\n let quoteStart = index;\\n\\n while (index++ < chars.length) {\\n if (chars[index] === '\\\"') {\\n index++;\\n quoteStart = 0;\\n break;\\n }\\n\\n // Increment over escape characters.\\n if (chars[index] === \\\"\\\\\\\\\\\") index++;\\n\\n value += chars[index];\\n }\\n\\n if (quoteStart) {\\n throw new PathError(`Unterminated quote at index ${quoteStart}`, str);\\n }\\n }\\n\\n if (!value) {\\n throw new PathError(`Missing parameter name at index ${index}`, str);\\n }\\n\\n return value;\\n }\\n\\n while (index < chars.length) {\\n const value = chars[index];\\n const type = SIMPLE_TOKENS[value];\\n\\n if (type) {\\n tokens.push({ type, index: index++, value });\\n } else if (value === \\\"\\\\\\\\\\\") {\\n tokens.push({ type: \\\"escape\\\", index: index++, value: chars[index++] });\\n } else if (value === \\\":\\\") {\\n tokens.push({ type: \\\"param\\\", index: index++, value: name() });\\n } else if (value === \\\"*\\\") {\\n tokens.push({ type: \\\"wildcard\\\", index: index++, value: name() });\\n } else {\\n tokens.push({ type: \\\"char\\\", index: index++, value });\\n }\\n }\\n\\n tokens.push({ type: \\\"end\\\", index, value: \\\"\\\" });\\n\\n function consumeUntil(endType: TokenType): Token[] {\\n const output: Token[] = [];\\n\\n while (true) {\\n const token = tokens[pos++];\\n if (token.type === endType) break;\\n\\n if (token.type === \\\"char\\\" || token.type === \\\"escape\\\") {\\n let path = token.value;\\n let cur = tokens[pos];\\n\\n while (cur.type === \\\"char\\\" || cur.type === \\\"escape\\\") {\\n path += cur.value;\\n cur = tokens[++pos];\\n }\\n\\n output.push({\\n type: \\\"text\\\",\\n value: encodePath(path),\\n });\\n continue;\\n }\\n\\n if (token.type === \\\"param\\\" || token.type === \\\"wildcard\\\") {\\n output.push({\\n type: token.type,\\n name: token.value,\\n });\\n continue;\\n }\\n\\n if (token.type === \\\"{\\\") {\\n output.push({\\n type: \\\"group\\\",\\n tokens: consumeUntil(\\\"}\\\"),\\n });\\n continue;\\n }\\n\\n throw new PathError(\\n `Unexpected ${token.type} at index ${token.index}, expected ${endType}`,\\n str,\\n );\\n }\\n\\n return output;\\n }\\n\\n return new TokenData(consumeUntil(\\\"end\\\"), str);\\n}\\n\\n/**\\n * Compile a string to a template function for the path.\\n */\\nexport function compile

(\\n path: Path,\\n options: CompileOptions & ParseOptions = {},\\n) {\\n const { encode = encodeURIComponent, delimiter = DEFAULT_DELIMITER } =\\n options;\\n const data = typeof path === \\\"object\\\" ? path : parse(path, options);\\n const fn = tokensToFunction(data.tokens, delimiter, encode);\\n\\n return function path(params: P = {} as P) {\\n const [path, ...missing] = fn(params);\\n if (missing.length) {\\n throw new TypeError(`Missing parameters: ${missing.join(\\\", \\\")}`);\\n }\\n return path;\\n };\\n}\\n\\nexport type ParamData = Partial>;\\nexport type PathFunction

= (data?: P) => string;\\n\\nfunction tokensToFunction(\\n tokens: Token[],\\n delimiter: string,\\n encode: Encode | false,\\n) {\\n const encoders = tokens.map((token) =>\\n tokenToFunction(token, delimiter, encode),\\n );\\n\\n return (data: ParamData) => {\\n const result: string[] = [\\\"\\\"];\\n\\n for (const encoder of encoders) {\\n const [value, ...extras] = encoder(data);\\n result[0] += value;\\n result.push(...extras);\\n }\\n\\n return result;\\n };\\n}\\n\\n/**\\n * Convert a single token into a path building function.\\n */\\nfunction tokenToFunction(\\n token: Token,\\n delimiter: string,\\n encode: Encode | false,\\n): (data: ParamData) => string[] {\\n if (token.type === \\\"text\\\") return () => [token.value];\\n\\n if (token.type === \\\"group\\\") {\\n const fn = tokensToFunction(token.tokens, delimiter, encode);\\n\\n return (data) => {\\n const [value, ...missing] = fn(data);\\n if (!missing.length) return [value];\\n return [\\\"\\\"];\\n };\\n }\\n\\n const encodeValue = encode || NOOP_VALUE;\\n\\n if (token.type === \\\"wildcard\\\" && encode !== false) {\\n return (data) => {\\n const value = data[token.name];\\n if (value == null) return [\\\"\\\", token.name];\\n\\n if (!Array.isArray(value) || value.length === 0) {\\n throw new TypeError(`Expected \\\"${token.name}\\\" to be a non-empty array`);\\n }\\n\\n return [\\n value\\n .map((value, index) => {\\n if (typeof value !== \\\"string\\\") {\\n throw new TypeError(\\n `Expected \\\"${token.name}/${index}\\\" to be a string`,\\n );\\n }\\n\\n return encodeValue(value);\\n })\\n .join(delimiter),\\n ];\\n };\\n }\\n\\n return (data) => {\\n const value = data[token.name];\\n if (value == null) return [\\\"\\\", token.name];\\n\\n if (typeof value !== \\\"string\\\") {\\n throw new TypeError(`Expected \\\"${token.name}\\\" to be a string`);\\n }\\n\\n return [encodeValue(value)];\\n };\\n}\\n\\n/**\\n * A match result contains data about the path match.\\n */\\nexport interface MatchResult

{\\n path: string;\\n params: P;\\n}\\n\\n/**\\n * A match is either `false` (no match) or a match result.\\n */\\nexport type Match

= false | MatchResult

;\\n\\n/**\\n * The match function takes a string and returns whether it matched the path.\\n */\\nexport type MatchFunction

= (path: string) => Match

;\\n\\n/**\\n * Supported path types.\\n */\\nexport type Path = string | TokenData;\\n\\n/**\\n * Transform a path into a match function.\\n */\\nexport function match

(\\n path: Path | Path[],\\n options: MatchOptions & ParseOptions = {},\\n): MatchFunction

{\\n const { decode = decodeURIComponent, delimiter = DEFAULT_DELIMITER } =\\n options;\\n const { regexp, keys } = pathToRegexp(path, options);\\n\\n const decoders = keys.map((key) => {\\n if (decode === false) return NOOP_VALUE;\\n if (key.type === \\\"param\\\") return decode;\\n return (value: string) => value.split(delimiter).map(decode);\\n });\\n\\n return function match(input: string) {\\n const m = regexp.exec(input);\\n if (!m) return false;\\n\\n const path = m[0];\\n const params = Object.create(null);\\n\\n for (let i = 1; i < m.length; i++) {\\n if (m[i] === undefined) continue;\\n\\n const key = keys[i - 1];\\n const decoder = decoders[i - 1];\\n params[key.name] = decoder(m[i]);\\n }\\n\\n return { path, params };\\n };\\n}\\n\\nexport function pathToRegexp(\\n path: Path | Path[],\\n options: PathToRegexpOptions & ParseOptions = {},\\n) {\\n const {\\n delimiter = DEFAULT_DELIMITER,\\n end = true,\\n sensitive = false,\\n trailing = true,\\n } = options;\\n const keys: Keys = [];\\n const flags = sensitive ? \\\"\\\" : \\\"i\\\";\\n const sources: string[] = [];\\n\\n for (const input of pathsToArray(path, [])) {\\n const data = typeof input === \\\"object\\\" ? input : parse(input, options);\\n for (const tokens of flatten(data.tokens, 0, [])) {\\n sources.push(toRegExpSource(tokens, delimiter, keys, data.originalPath));\\n }\\n }\\n\\n let pattern = `^(?:${sources.join(\\\"|\\\")})`;\\n if (trailing) pattern += `(?:${escape(delimiter)}$)?`;\\n pattern += end ? \\\"$\\\" : `(?=${escape(delimiter)}|$)`;\\n\\n const regexp = new RegExp(pattern, flags);\\n return { regexp, keys };\\n}\\n\\n/**\\n * Convert a path or array of paths into a flat array.\\n */\\nfunction pathsToArray(paths: Path | Path[], init: Path[]): Path[] {\\n if (Array.isArray(paths)) {\\n for (const p of paths) pathsToArray(p, init);\\n } else {\\n init.push(paths);\\n }\\n return init;\\n}\\n\\n/**\\n * Flattened token set.\\n */\\ntype FlatToken = Text | Parameter | Wildcard;\\n\\n/**\\n * Generate a flat list of sequence tokens from the given tokens.\\n */\\nfunction* flatten(\\n tokens: Token[],\\n index: number,\\n init: FlatToken[],\\n): Generator {\\n if (index === tokens.length) {\\n return yield init;\\n }\\n\\n const token = tokens[index];\\n\\n if (token.type === \\\"group\\\") {\\n for (const seq of flatten(token.tokens, 0, init.slice())) {\\n yield* flatten(tokens, index + 1, seq);\\n }\\n } else {\\n init.push(token);\\n }\\n\\n yield* flatten(tokens, index + 1, init);\\n}\\n\\n/**\\n * Transform a flat sequence of tokens into a regular expression.\\n */\\nfunction toRegExpSource(\\n tokens: FlatToken[],\\n delimiter: string,\\n keys: Keys,\\n originalPath: string | undefined,\\n): string {\\n let result = \\\"\\\";\\n let backtrack = \\\"\\\";\\n let isSafeSegmentParam = true;\\n\\n for (const token of tokens) {\\n if (token.type === \\\"text\\\") {\\n result += escape(token.value);\\n backtrack += token.value;\\n isSafeSegmentParam ||= token.value.includes(delimiter);\\n continue;\\n }\\n\\n if (token.type === \\\"param\\\" || token.type === \\\"wildcard\\\") {\\n if (!isSafeSegmentParam && !backtrack) {\\n throw new PathError(\\n `Missing text before \\\"${token.name}\\\" ${token.type}`,\\n originalPath,\\n );\\n }\\n\\n if (token.type === \\\"param\\\") {\\n result += `(${negate(delimiter, isSafeSegmentParam ? \\\"\\\" : backtrack)}+)`;\\n } else {\\n result += `([\\\\\\\\s\\\\\\\\S]+)`;\\n }\\n\\n keys.push(token);\\n backtrack = \\\"\\\";\\n isSafeSegmentParam = false;\\n continue;\\n }\\n }\\n\\n return result;\\n}\\n\\n/**\\n * Block backtracking on previous text and ignore delimiter string.\\n */\\nfunction negate(delimiter: string, backtrack: string): string {\\n if (backtrack.length < 2) {\\n if (delimiter.length < 2) return `[^${escape(delimiter + backtrack)}]`;\\n return `(?:(?!${escape(delimiter)})[^${escape(backtrack)}])`;\\n }\\n if (delimiter.length < 2) {\\n return `(?:(?!${escape(backtrack)})[^${escape(delimiter)}])`;\\n }\\n return `(?:(?!${escape(backtrack)}|${escape(delimiter)})[\\\\\\\\s\\\\\\\\S])`;\\n}\\n\\n/**\\n * Stringify an array of tokens into a path string.\\n */\\nfunction stringifyTokens(tokens: Token[]): string {\\n let value = \\\"\\\";\\n let i = 0;\\n\\n function name(value: string) {\\n const isSafe = isNameSafe(value) && isNextNameSafe(tokens[i]);\\n return isSafe ? value : JSON.stringify(value);\\n }\\n\\n while (i < tokens.length) {\\n const token = tokens[i++];\\n\\n if (token.type === \\\"text\\\") {\\n value += escapeText(token.value);\\n continue;\\n }\\n\\n if (token.type === \\\"group\\\") {\\n value += `{${stringifyTokens(token.tokens)}}`;\\n continue;\\n }\\n\\n if (token.type === \\\"param\\\") {\\n value += `:${name(token.name)}`;\\n continue;\\n }\\n\\n if (token.type === \\\"wildcard\\\") {\\n value += `*${name(token.name)}`;\\n continue;\\n }\\n\\n throw new TypeError(`Unknown token type: ${(token as any).type}`);\\n }\\n\\n return value;\\n}\\n\\n/**\\n * Stringify token data into a path string.\\n */\\nexport function stringify(data: TokenData): string {\\n return stringifyTokens(data.tokens);\\n}\\n\\n/**\\n * Validate the parameter name contains valid ID characters.\\n */\\nfunction isNameSafe(name: string): boolean {\\n const [first, ...rest] = name;\\n return ID_START.test(first) && rest.every((char) => ID_CONTINUE.test(char));\\n}\\n\\n/**\\n * Validate the next token does not interfere with the current param name.\\n */\\nfunction isNextNameSafe(token: Token | undefined): boolean {\\n if (token && token.type === \\\"text\\\") return !ID_CONTINUE.test(token.value[0]);\\n return true;\\n}\\n\",\"'use strict'\\n\\n// Note: this is the semver.org version of the spec that it implements\\n// Not necessarily the package version of this code.\\nconst SEMVER_SPEC_VERSION = '2.0.0'\\n\\nconst MAX_LENGTH = 256\\nconst MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER ||\\n/* istanbul ignore next */ 9007199254740991\\n\\n// Max safe segment length for coercion.\\nconst MAX_SAFE_COMPONENT_LENGTH = 16\\n\\n// Max safe length for a build identifier. The max length minus 6 characters for\\n// the shortest version with a build 0.0.0+BUILD.\\nconst MAX_SAFE_BUILD_LENGTH = MAX_LENGTH - 6\\n\\nconst RELEASE_TYPES = [\\n 'major',\\n 'premajor',\\n 'minor',\\n 'preminor',\\n 'patch',\\n 'prepatch',\\n 'prerelease',\\n]\\n\\nmodule.exports = {\\n MAX_LENGTH,\\n MAX_SAFE_COMPONENT_LENGTH,\\n MAX_SAFE_BUILD_LENGTH,\\n MAX_SAFE_INTEGER,\\n RELEASE_TYPES,\\n SEMVER_SPEC_VERSION,\\n FLAG_INCLUDE_PRERELEASE: 0b001,\\n FLAG_LOOSE: 0b010,\\n}\\n\",\"'use strict'\\n\\nconst debug = (\\n typeof process === 'object' &&\\n process.env &&\\n process.env.NODE_DEBUG &&\\n /\\\\bsemver\\\\b/i.test(process.env.NODE_DEBUG)\\n) ? (...args) => console.error('SEMVER', ...args)\\n : () => {}\\n\\nmodule.exports = debug\\n\",\"'use strict'\\n\\nconst {\\n MAX_SAFE_COMPONENT_LENGTH,\\n MAX_SAFE_BUILD_LENGTH,\\n MAX_LENGTH,\\n} = require('./constants')\\nconst debug = require('./debug')\\nexports = module.exports = {}\\n\\n// The actual regexps go on exports.re\\nconst re = exports.re = []\\nconst safeRe = exports.safeRe = []\\nconst src = exports.src = []\\nconst safeSrc = exports.safeSrc = []\\nconst t = exports.t = {}\\nlet R = 0\\n\\nconst LETTERDASHNUMBER = '[a-zA-Z0-9-]'\\n\\n// Replace some greedy regex tokens to prevent regex dos issues. These regex are\\n// used internally via the safeRe object since all inputs in this library get\\n// normalized first to trim and collapse all extra whitespace. The original\\n// regexes are exported for userland consumption and lower level usage. A\\n// future breaking change could export the safer regex only with a note that\\n// all input should have extra whitespace removed.\\nconst safeRegexReplacements = [\\n ['\\\\\\\\s', 1],\\n ['\\\\\\\\d', MAX_LENGTH],\\n [LETTERDASHNUMBER, MAX_SAFE_BUILD_LENGTH],\\n]\\n\\nconst makeSafeRegex = (value) => {\\n for (const [token, max] of safeRegexReplacements) {\\n value = value\\n .split(`${token}*`).join(`${token}{0,${max}}`)\\n .split(`${token}+`).join(`${token}{1,${max}}`)\\n }\\n return value\\n}\\n\\nconst createToken = (name, value, isGlobal) => {\\n const safe = makeSafeRegex(value)\\n const index = R++\\n debug(name, index, value)\\n t[name] = index\\n src[index] = value\\n safeSrc[index] = safe\\n re[index] = new RegExp(value, isGlobal ? 'g' : undefined)\\n safeRe[index] = new RegExp(safe, isGlobal ? 'g' : undefined)\\n}\\n\\n// The following Regular Expressions can be used for tokenizing,\\n// validating, and parsing SemVer version strings.\\n\\n// ## Numeric Identifier\\n// A single `0`, or a non-zero digit followed by zero or more digits.\\n\\ncreateToken('NUMERICIDENTIFIER', '0|[1-9]\\\\\\\\d*')\\ncreateToken('NUMERICIDENTIFIERLOOSE', '\\\\\\\\d+')\\n\\n// ## Non-numeric Identifier\\n// Zero or more digits, followed by a letter or hyphen, and then zero or\\n// more letters, digits, or hyphens.\\n\\ncreateToken('NONNUMERICIDENTIFIER', `\\\\\\\\d*[a-zA-Z-]${LETTERDASHNUMBER}*`)\\n\\n// ## Main Version\\n// Three dot-separated numeric identifiers.\\n\\ncreateToken('MAINVERSION', `(${src[t.NUMERICIDENTIFIER]})\\\\\\\\.` +\\n `(${src[t.NUMERICIDENTIFIER]})\\\\\\\\.` +\\n `(${src[t.NUMERICIDENTIFIER]})`)\\n\\ncreateToken('MAINVERSIONLOOSE', `(${src[t.NUMERICIDENTIFIERLOOSE]})\\\\\\\\.` +\\n `(${src[t.NUMERICIDENTIFIERLOOSE]})\\\\\\\\.` +\\n `(${src[t.NUMERICIDENTIFIERLOOSE]})`)\\n\\n// ## Pre-release Version Identifier\\n// A numeric identifier, or a non-numeric identifier.\\n// Non-numberic identifiers include numberic identifiers but can be longer.\\n// Therefore non-numberic identifiers must go first.\\n\\ncreateToken('PRERELEASEIDENTIFIER', `(?:${src[t.NONNUMERICIDENTIFIER]\\n}|${src[t.NUMERICIDENTIFIER]})`)\\n\\ncreateToken('PRERELEASEIDENTIFIERLOOSE', `(?:${src[t.NONNUMERICIDENTIFIER]\\n}|${src[t.NUMERICIDENTIFIERLOOSE]})`)\\n\\n// ## Pre-release Version\\n// Hyphen, followed by one or more dot-separated pre-release version\\n// identifiers.\\n\\ncreateToken('PRERELEASE', `(?:-(${src[t.PRERELEASEIDENTIFIER]\\n}(?:\\\\\\\\.${src[t.PRERELEASEIDENTIFIER]})*))`)\\n\\ncreateToken('PRERELEASELOOSE', `(?:-?(${src[t.PRERELEASEIDENTIFIERLOOSE]\\n}(?:\\\\\\\\.${src[t.PRERELEASEIDENTIFIERLOOSE]})*))`)\\n\\n// ## Build Metadata Identifier\\n// Any combination of digits, letters, or hyphens.\\n\\ncreateToken('BUILDIDENTIFIER', `${LETTERDASHNUMBER}+`)\\n\\n// ## Build Metadata\\n// Plus sign, followed by one or more period-separated build metadata\\n// identifiers.\\n\\ncreateToken('BUILD', `(?:\\\\\\\\+(${src[t.BUILDIDENTIFIER]\\n}(?:\\\\\\\\.${src[t.BUILDIDENTIFIER]})*))`)\\n\\n// ## Full Version String\\n// A main version, followed optionally by a pre-release version and\\n// build metadata.\\n\\n// Note that the only major, minor, patch, and pre-release sections of\\n// the version string are capturing groups. The build metadata is not a\\n// capturing group, because it should not ever be used in version\\n// comparison.\\n\\ncreateToken('FULLPLAIN', `v?${src[t.MAINVERSION]\\n}${src[t.PRERELEASE]}?${\\n src[t.BUILD]}?`)\\n\\ncreateToken('FULL', `^${src[t.FULLPLAIN]}$`)\\n\\n// like full, but allows v1.2.3 and =1.2.3, which people do sometimes.\\n// also, 1.0.0alpha1 (prerelease without the hyphen) which is pretty\\n// common in the npm registry.\\ncreateToken('LOOSEPLAIN', `[v=\\\\\\\\s]*${src[t.MAINVERSIONLOOSE]\\n}${src[t.PRERELEASELOOSE]}?${\\n src[t.BUILD]}?`)\\n\\ncreateToken('LOOSE', `^${src[t.LOOSEPLAIN]}$`)\\n\\ncreateToken('GTLT', '((?:<|>)?=?)')\\n\\n// Something like \\\"2.*\\\" or \\\"1.2.x\\\".\\n// Note that \\\"x.x\\\" is a valid xRange identifer, meaning \\\"any version\\\"\\n// Only the first item is strictly required.\\ncreateToken('XRANGEIDENTIFIERLOOSE', `${src[t.NUMERICIDENTIFIERLOOSE]}|x|X|\\\\\\\\*`)\\ncreateToken('XRANGEIDENTIFIER', `${src[t.NUMERICIDENTIFIER]}|x|X|\\\\\\\\*`)\\n\\ncreateToken('XRANGEPLAIN', `[v=\\\\\\\\s]*(${src[t.XRANGEIDENTIFIER]})` +\\n `(?:\\\\\\\\.(${src[t.XRANGEIDENTIFIER]})` +\\n `(?:\\\\\\\\.(${src[t.XRANGEIDENTIFIER]})` +\\n `(?:${src[t.PRERELEASE]})?${\\n src[t.BUILD]}?` +\\n `)?)?`)\\n\\ncreateToken('XRANGEPLAINLOOSE', `[v=\\\\\\\\s]*(${src[t.XRANGEIDENTIFIERLOOSE]})` +\\n `(?:\\\\\\\\.(${src[t.XRANGEIDENTIFIERLOOSE]})` +\\n `(?:\\\\\\\\.(${src[t.XRANGEIDENTIFIERLOOSE]})` +\\n `(?:${src[t.PRERELEASELOOSE]})?${\\n src[t.BUILD]}?` +\\n `)?)?`)\\n\\ncreateToken('XRANGE', `^${src[t.GTLT]}\\\\\\\\s*${src[t.XRANGEPLAIN]}$`)\\ncreateToken('XRANGELOOSE', `^${src[t.GTLT]}\\\\\\\\s*${src[t.XRANGEPLAINLOOSE]}$`)\\n\\n// Coercion.\\n// Extract anything that could conceivably be a part of a valid semver\\ncreateToken('COERCEPLAIN', `${'(^|[^\\\\\\\\d])' +\\n '(\\\\\\\\d{1,'}${MAX_SAFE_COMPONENT_LENGTH}})` +\\n `(?:\\\\\\\\.(\\\\\\\\d{1,${MAX_SAFE_COMPONENT_LENGTH}}))?` +\\n `(?:\\\\\\\\.(\\\\\\\\d{1,${MAX_SAFE_COMPONENT_LENGTH}}))?`)\\ncreateToken('COERCE', `${src[t.COERCEPLAIN]}(?:$|[^\\\\\\\\d])`)\\ncreateToken('COERCEFULL', src[t.COERCEPLAIN] +\\n `(?:${src[t.PRERELEASE]})?` +\\n `(?:${src[t.BUILD]})?` +\\n `(?:$|[^\\\\\\\\d])`)\\ncreateToken('COERCERTL', src[t.COERCE], true)\\ncreateToken('COERCERTLFULL', src[t.COERCEFULL], true)\\n\\n// Tilde ranges.\\n// Meaning is \\\"reasonably at or greater than\\\"\\ncreateToken('LONETILDE', '(?:~>?)')\\n\\ncreateToken('TILDETRIM', `(\\\\\\\\s*)${src[t.LONETILDE]}\\\\\\\\s+`, true)\\nexports.tildeTrimReplace = '$1~'\\n\\ncreateToken('TILDE', `^${src[t.LONETILDE]}${src[t.XRANGEPLAIN]}$`)\\ncreateToken('TILDELOOSE', `^${src[t.LONETILDE]}${src[t.XRANGEPLAINLOOSE]}$`)\\n\\n// Caret ranges.\\n// Meaning is \\\"at least and backwards compatible with\\\"\\ncreateToken('LONECARET', '(?:\\\\\\\\^)')\\n\\ncreateToken('CARETTRIM', `(\\\\\\\\s*)${src[t.LONECARET]}\\\\\\\\s+`, true)\\nexports.caretTrimReplace = '$1^'\\n\\ncreateToken('CARET', `^${src[t.LONECARET]}${src[t.XRANGEPLAIN]}$`)\\ncreateToken('CARETLOOSE', `^${src[t.LONECARET]}${src[t.XRANGEPLAINLOOSE]}$`)\\n\\n// A simple gt/lt/eq thing, or just \\\"\\\" to indicate \\\"any version\\\"\\ncreateToken('COMPARATORLOOSE', `^${src[t.GTLT]}\\\\\\\\s*(${src[t.LOOSEPLAIN]})$|^$`)\\ncreateToken('COMPARATOR', `^${src[t.GTLT]}\\\\\\\\s*(${src[t.FULLPLAIN]})$|^$`)\\n\\n// An expression to strip any whitespace between the gtlt and the thing\\n// it modifies, so that `> 1.2.3` ==> `>1.2.3`\\ncreateToken('COMPARATORTRIM', `(\\\\\\\\s*)${src[t.GTLT]\\n}\\\\\\\\s*(${src[t.LOOSEPLAIN]}|${src[t.XRANGEPLAIN]})`, true)\\nexports.comparatorTrimReplace = '$1$2$3'\\n\\n// Something like `1.2.3 - 1.2.4`\\n// Note that these all use the loose form, because they'll be\\n// checked against either the strict or loose comparator form\\n// later.\\ncreateToken('HYPHENRANGE', `^\\\\\\\\s*(${src[t.XRANGEPLAIN]})` +\\n `\\\\\\\\s+-\\\\\\\\s+` +\\n `(${src[t.XRANGEPLAIN]})` +\\n `\\\\\\\\s*$`)\\n\\ncreateToken('HYPHENRANGELOOSE', `^\\\\\\\\s*(${src[t.XRANGEPLAINLOOSE]})` +\\n `\\\\\\\\s+-\\\\\\\\s+` +\\n `(${src[t.XRANGEPLAINLOOSE]})` +\\n `\\\\\\\\s*$`)\\n\\n// Star ranges basically just allow anything at all.\\ncreateToken('STAR', '(<|>)?=?\\\\\\\\s*\\\\\\\\*')\\n// >=0.0.0 is like a star\\ncreateToken('GTE0', '^\\\\\\\\s*>=\\\\\\\\s*0\\\\\\\\.0\\\\\\\\.0\\\\\\\\s*$')\\ncreateToken('GTE0PRE', '^\\\\\\\\s*>=\\\\\\\\s*0\\\\\\\\.0\\\\\\\\.0-0\\\\\\\\s*$')\\n\",\"'use strict'\\n\\n// parse out just the options we care about\\nconst looseOption = Object.freeze({ loose: true })\\nconst emptyOpts = Object.freeze({ })\\nconst parseOptions = options => {\\n if (!options) {\\n return emptyOpts\\n }\\n\\n if (typeof options !== 'object') {\\n return looseOption\\n }\\n\\n return options\\n}\\nmodule.exports = parseOptions\\n\",\"'use strict'\\n\\nconst numeric = /^[0-9]+$/\\nconst compareIdentifiers = (a, b) => {\\n if (typeof a === 'number' && typeof b === 'number') {\\n return a === b ? 0 : a < b ? -1 : 1\\n }\\n\\n const anum = numeric.test(a)\\n const bnum = numeric.test(b)\\n\\n if (anum && bnum) {\\n a = +a\\n b = +b\\n }\\n\\n return a === b ? 0\\n : (anum && !bnum) ? -1\\n : (bnum && !anum) ? 1\\n : a < b ? -1\\n : 1\\n}\\n\\nconst rcompareIdentifiers = (a, b) => compareIdentifiers(b, a)\\n\\nmodule.exports = {\\n compareIdentifiers,\\n rcompareIdentifiers,\\n}\\n\",\"'use strict'\\n\\nconst debug = require('../internal/debug')\\nconst { MAX_LENGTH, MAX_SAFE_INTEGER } = require('../internal/constants')\\nconst { safeRe: re, t } = require('../internal/re')\\n\\nconst parseOptions = require('../internal/parse-options')\\nconst { compareIdentifiers } = require('../internal/identifiers')\\nclass SemVer {\\n constructor (version, options) {\\n options = parseOptions(options)\\n\\n if (version instanceof SemVer) {\\n if (version.loose === !!options.loose &&\\n version.includePrerelease === !!options.includePrerelease) {\\n return version\\n } else {\\n version = version.version\\n }\\n } else if (typeof version !== 'string') {\\n throw new TypeError(`Invalid version. Must be a string. Got type \\\"${typeof version}\\\".`)\\n }\\n\\n if (version.length > MAX_LENGTH) {\\n throw new TypeError(\\n `version is longer than ${MAX_LENGTH} characters`\\n )\\n }\\n\\n debug('SemVer', version, options)\\n this.options = options\\n this.loose = !!options.loose\\n // this isn't actually relevant for versions, but keep it so that we\\n // don't run into trouble passing this.options around.\\n this.includePrerelease = !!options.includePrerelease\\n\\n const m = version.trim().match(options.loose ? re[t.LOOSE] : re[t.FULL])\\n\\n if (!m) {\\n throw new TypeError(`Invalid Version: ${version}`)\\n }\\n\\n this.raw = version\\n\\n // these are actually numbers\\n this.major = +m[1]\\n this.minor = +m[2]\\n this.patch = +m[3]\\n\\n if (this.major > MAX_SAFE_INTEGER || this.major < 0) {\\n throw new TypeError('Invalid major version')\\n }\\n\\n if (this.minor > MAX_SAFE_INTEGER || this.minor < 0) {\\n throw new TypeError('Invalid minor version')\\n }\\n\\n if (this.patch > MAX_SAFE_INTEGER || this.patch < 0) {\\n throw new TypeError('Invalid patch version')\\n }\\n\\n // numberify any prerelease numeric ids\\n if (!m[4]) {\\n this.prerelease = []\\n } else {\\n this.prerelease = m[4].split('.').map((id) => {\\n if (/^[0-9]+$/.test(id)) {\\n const num = +id\\n if (num >= 0 && num < MAX_SAFE_INTEGER) {\\n return num\\n }\\n }\\n return id\\n })\\n }\\n\\n this.build = m[5] ? m[5].split('.') : []\\n this.format()\\n }\\n\\n format () {\\n this.version = `${this.major}.${this.minor}.${this.patch}`\\n if (this.prerelease.length) {\\n this.version += `-${this.prerelease.join('.')}`\\n }\\n return this.version\\n }\\n\\n toString () {\\n return this.version\\n }\\n\\n compare (other) {\\n debug('SemVer.compare', this.version, this.options, other)\\n if (!(other instanceof SemVer)) {\\n if (typeof other === 'string' && other === this.version) {\\n return 0\\n }\\n other = new SemVer(other, this.options)\\n }\\n\\n if (other.version === this.version) {\\n return 0\\n }\\n\\n return this.compareMain(other) || this.comparePre(other)\\n }\\n\\n compareMain (other) {\\n if (!(other instanceof SemVer)) {\\n other = new SemVer(other, this.options)\\n }\\n\\n if (this.major < other.major) {\\n return -1\\n }\\n if (this.major > other.major) {\\n return 1\\n }\\n if (this.minor < other.minor) {\\n return -1\\n }\\n if (this.minor > other.minor) {\\n return 1\\n }\\n if (this.patch < other.patch) {\\n return -1\\n }\\n if (this.patch > other.patch) {\\n return 1\\n }\\n return 0\\n }\\n\\n comparePre (other) {\\n if (!(other instanceof SemVer)) {\\n other = new SemVer(other, this.options)\\n }\\n\\n // NOT having a prerelease is > having one\\n if (this.prerelease.length && !other.prerelease.length) {\\n return -1\\n } else if (!this.prerelease.length && other.prerelease.length) {\\n return 1\\n } else if (!this.prerelease.length && !other.prerelease.length) {\\n return 0\\n }\\n\\n let i = 0\\n do {\\n const a = this.prerelease[i]\\n const b = other.prerelease[i]\\n debug('prerelease compare', i, a, b)\\n if (a === undefined && b === undefined) {\\n return 0\\n } else if (b === undefined) {\\n return 1\\n } else if (a === undefined) {\\n return -1\\n } else if (a === b) {\\n continue\\n } else {\\n return compareIdentifiers(a, b)\\n }\\n } while (++i)\\n }\\n\\n compareBuild (other) {\\n if (!(other instanceof SemVer)) {\\n other = new SemVer(other, this.options)\\n }\\n\\n let i = 0\\n do {\\n const a = this.build[i]\\n const b = other.build[i]\\n debug('build compare', i, a, b)\\n if (a === undefined && b === undefined) {\\n return 0\\n } else if (b === undefined) {\\n return 1\\n } else if (a === undefined) {\\n return -1\\n } else if (a === b) {\\n continue\\n } else {\\n return compareIdentifiers(a, b)\\n }\\n } while (++i)\\n }\\n\\n // preminor will bump the version up to the next minor release, and immediately\\n // down to pre-release. premajor and prepatch work the same way.\\n inc (release, identifier, identifierBase) {\\n if (release.startsWith('pre')) {\\n if (!identifier && identifierBase === false) {\\n throw new Error('invalid increment argument: identifier is empty')\\n }\\n // Avoid an invalid semver results\\n if (identifier) {\\n const match = `-${identifier}`.match(this.options.loose ? re[t.PRERELEASELOOSE] : re[t.PRERELEASE])\\n if (!match || match[1] !== identifier) {\\n throw new Error(`invalid identifier: ${identifier}`)\\n }\\n }\\n }\\n\\n switch (release) {\\n case 'premajor':\\n this.prerelease.length = 0\\n this.patch = 0\\n this.minor = 0\\n this.major++\\n this.inc('pre', identifier, identifierBase)\\n break\\n case 'preminor':\\n this.prerelease.length = 0\\n this.patch = 0\\n this.minor++\\n this.inc('pre', identifier, identifierBase)\\n break\\n case 'prepatch':\\n // If this is already a prerelease, it will bump to the next version\\n // drop any prereleases that might already exist, since they are not\\n // relevant at this point.\\n this.prerelease.length = 0\\n this.inc('patch', identifier, identifierBase)\\n this.inc('pre', identifier, identifierBase)\\n break\\n // If the input is a non-prerelease version, this acts the same as\\n // prepatch.\\n case 'prerelease':\\n if (this.prerelease.length === 0) {\\n this.inc('patch', identifier, identifierBase)\\n }\\n this.inc('pre', identifier, identifierBase)\\n break\\n case 'release':\\n if (this.prerelease.length === 0) {\\n throw new Error(`version ${this.raw} is not a prerelease`)\\n }\\n this.prerelease.length = 0\\n break\\n\\n case 'major':\\n // If this is a pre-major version, bump up to the same major version.\\n // Otherwise increment major.\\n // 1.0.0-5 bumps to 1.0.0\\n // 1.1.0 bumps to 2.0.0\\n if (\\n this.minor !== 0 ||\\n this.patch !== 0 ||\\n this.prerelease.length === 0\\n ) {\\n this.major++\\n }\\n this.minor = 0\\n this.patch = 0\\n this.prerelease = []\\n break\\n case 'minor':\\n // If this is a pre-minor version, bump up to the same minor version.\\n // Otherwise increment minor.\\n // 1.2.0-5 bumps to 1.2.0\\n // 1.2.1 bumps to 1.3.0\\n if (this.patch !== 0 || this.prerelease.length === 0) {\\n this.minor++\\n }\\n this.patch = 0\\n this.prerelease = []\\n break\\n case 'patch':\\n // If this is not a pre-release version, it will increment the patch.\\n // If it is a pre-release it will bump up to the same patch version.\\n // 1.2.0-5 patches to 1.2.0\\n // 1.2.0 patches to 1.2.1\\n if (this.prerelease.length === 0) {\\n this.patch++\\n }\\n this.prerelease = []\\n break\\n // This probably shouldn't be used publicly.\\n // 1.0.0 'pre' would become 1.0.0-0 which is the wrong direction.\\n case 'pre': {\\n const base = Number(identifierBase) ? 1 : 0\\n\\n if (this.prerelease.length === 0) {\\n this.prerelease = [base]\\n } else {\\n let i = this.prerelease.length\\n while (--i >= 0) {\\n if (typeof this.prerelease[i] === 'number') {\\n this.prerelease[i]++\\n i = -2\\n }\\n }\\n if (i === -1) {\\n // didn't increment anything\\n if (identifier === this.prerelease.join('.') && identifierBase === false) {\\n throw new Error('invalid increment argument: identifier already exists')\\n }\\n this.prerelease.push(base)\\n }\\n }\\n if (identifier) {\\n // 1.2.0-beta.1 bumps to 1.2.0-beta.2,\\n // 1.2.0-beta.fooblz or 1.2.0-beta bumps to 1.2.0-beta.0\\n let prerelease = [identifier, base]\\n if (identifierBase === false) {\\n prerelease = [identifier]\\n }\\n if (compareIdentifiers(this.prerelease[0], identifier) === 0) {\\n if (isNaN(this.prerelease[1])) {\\n this.prerelease = prerelease\\n }\\n } else {\\n this.prerelease = prerelease\\n }\\n }\\n break\\n }\\n default:\\n throw new Error(`invalid increment argument: ${release}`)\\n }\\n this.raw = this.format()\\n if (this.build.length) {\\n this.raw += `+${this.build.join('.')}`\\n }\\n return this\\n }\\n}\\n\\nmodule.exports = SemVer\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst parse = (version, options, throwErrors = false) => {\\n if (version instanceof SemVer) {\\n return version\\n }\\n try {\\n return new SemVer(version, options)\\n } catch (er) {\\n if (!throwErrors) {\\n return null\\n }\\n throw er\\n }\\n}\\n\\nmodule.exports = parse\\n\",\"'use strict'\\n\\nconst parse = require('./parse')\\nconst valid = (version, options) => {\\n const v = parse(version, options)\\n return v ? v.version : null\\n}\\nmodule.exports = valid\\n\",\"'use strict'\\n\\nconst parse = require('./parse')\\nconst clean = (version, options) => {\\n const s = parse(version.trim().replace(/^[=v]+/, ''), options)\\n return s ? s.version : null\\n}\\nmodule.exports = clean\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\n\\nconst inc = (version, release, options, identifier, identifierBase) => {\\n if (typeof (options) === 'string') {\\n identifierBase = identifier\\n identifier = options\\n options = undefined\\n }\\n\\n try {\\n return new SemVer(\\n version instanceof SemVer ? version.version : version,\\n options\\n ).inc(release, identifier, identifierBase).version\\n } catch (er) {\\n return null\\n }\\n}\\nmodule.exports = inc\\n\",\"'use strict'\\n\\nconst parse = require('./parse.js')\\n\\nconst diff = (version1, version2) => {\\n const v1 = parse(version1, null, true)\\n const v2 = parse(version2, null, true)\\n const comparison = v1.compare(v2)\\n\\n if (comparison === 0) {\\n return null\\n }\\n\\n const v1Higher = comparison > 0\\n const highVersion = v1Higher ? v1 : v2\\n const lowVersion = v1Higher ? v2 : v1\\n const highHasPre = !!highVersion.prerelease.length\\n const lowHasPre = !!lowVersion.prerelease.length\\n\\n if (lowHasPre && !highHasPre) {\\n // Going from prerelease -> no prerelease requires some special casing\\n\\n // If the low version has only a major, then it will always be a major\\n // Some examples:\\n // 1.0.0-1 -> 1.0.0\\n // 1.0.0-1 -> 1.1.1\\n // 1.0.0-1 -> 2.0.0\\n if (!lowVersion.patch && !lowVersion.minor) {\\n return 'major'\\n }\\n\\n // If the main part has no difference\\n if (lowVersion.compareMain(highVersion) === 0) {\\n if (lowVersion.minor && !lowVersion.patch) {\\n return 'minor'\\n }\\n return 'patch'\\n }\\n }\\n\\n // add the `pre` prefix if we are going to a prerelease version\\n const prefix = highHasPre ? 'pre' : ''\\n\\n if (v1.major !== v2.major) {\\n return prefix + 'major'\\n }\\n\\n if (v1.minor !== v2.minor) {\\n return prefix + 'minor'\\n }\\n\\n if (v1.patch !== v2.patch) {\\n return prefix + 'patch'\\n }\\n\\n // high and low are preleases\\n return 'prerelease'\\n}\\n\\nmodule.exports = diff\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst major = (a, loose) => new SemVer(a, loose).major\\nmodule.exports = major\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst minor = (a, loose) => new SemVer(a, loose).minor\\nmodule.exports = minor\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst patch = (a, loose) => new SemVer(a, loose).patch\\nmodule.exports = patch\\n\",\"'use strict'\\n\\nconst parse = require('./parse')\\nconst prerelease = (version, options) => {\\n const parsed = parse(version, options)\\n return (parsed && parsed.prerelease.length) ? parsed.prerelease : null\\n}\\nmodule.exports = prerelease\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst compare = (a, b, loose) =>\\n new SemVer(a, loose).compare(new SemVer(b, loose))\\n\\nmodule.exports = compare\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst rcompare = (a, b, loose) => compare(b, a, loose)\\nmodule.exports = rcompare\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst compareLoose = (a, b) => compare(a, b, true)\\nmodule.exports = compareLoose\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst compareBuild = (a, b, loose) => {\\n const versionA = new SemVer(a, loose)\\n const versionB = new SemVer(b, loose)\\n return versionA.compare(versionB) || versionA.compareBuild(versionB)\\n}\\nmodule.exports = compareBuild\\n\",\"'use strict'\\n\\nconst compareBuild = require('./compare-build')\\nconst sort = (list, loose) => list.sort((a, b) => compareBuild(a, b, loose))\\nmodule.exports = sort\\n\",\"'use strict'\\n\\nconst compareBuild = require('./compare-build')\\nconst rsort = (list, loose) => list.sort((a, b) => compareBuild(b, a, loose))\\nmodule.exports = rsort\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst gt = (a, b, loose) => compare(a, b, loose) > 0\\nmodule.exports = gt\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst lt = (a, b, loose) => compare(a, b, loose) < 0\\nmodule.exports = lt\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst eq = (a, b, loose) => compare(a, b, loose) === 0\\nmodule.exports = eq\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst neq = (a, b, loose) => compare(a, b, loose) !== 0\\nmodule.exports = neq\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst gte = (a, b, loose) => compare(a, b, loose) >= 0\\nmodule.exports = gte\\n\",\"'use strict'\\n\\nconst compare = require('./compare')\\nconst lte = (a, b, loose) => compare(a, b, loose) <= 0\\nmodule.exports = lte\\n\",\"'use strict'\\n\\nconst eq = require('./eq')\\nconst neq = require('./neq')\\nconst gt = require('./gt')\\nconst gte = require('./gte')\\nconst lt = require('./lt')\\nconst lte = require('./lte')\\n\\nconst cmp = (a, op, b, loose) => {\\n switch (op) {\\n case '===':\\n if (typeof a === 'object') {\\n a = a.version\\n }\\n if (typeof b === 'object') {\\n b = b.version\\n }\\n return a === b\\n\\n case '!==':\\n if (typeof a === 'object') {\\n a = a.version\\n }\\n if (typeof b === 'object') {\\n b = b.version\\n }\\n return a !== b\\n\\n case '':\\n case '=':\\n case '==':\\n return eq(a, b, loose)\\n\\n case '!=':\\n return neq(a, b, loose)\\n\\n case '>':\\n return gt(a, b, loose)\\n\\n case '>=':\\n return gte(a, b, loose)\\n\\n case '<':\\n return lt(a, b, loose)\\n\\n case '<=':\\n return lte(a, b, loose)\\n\\n default:\\n throw new TypeError(`Invalid operator: ${op}`)\\n }\\n}\\nmodule.exports = cmp\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst parse = require('./parse')\\nconst { safeRe: re, t } = require('../internal/re')\\n\\nconst coerce = (version, options) => {\\n if (version instanceof SemVer) {\\n return version\\n }\\n\\n if (typeof version === 'number') {\\n version = String(version)\\n }\\n\\n if (typeof version !== 'string') {\\n return null\\n }\\n\\n options = options || {}\\n\\n let match = null\\n if (!options.rtl) {\\n match = version.match(options.includePrerelease ? re[t.COERCEFULL] : re[t.COERCE])\\n } else {\\n // Find the right-most coercible string that does not share\\n // a terminus with a more left-ward coercible string.\\n // Eg, '1.2.3.4' wants to coerce '2.3.4', not '3.4' or '4'\\n // With includePrerelease option set, '1.2.3.4-rc' wants to coerce '2.3.4-rc', not '2.3.4'\\n //\\n // Walk through the string checking with a /g regexp\\n // Manually set the index so as to pick up overlapping matches.\\n // Stop when we get a match that ends at the string end, since no\\n // coercible string can be more right-ward without the same terminus.\\n const coerceRtlRegex = options.includePrerelease ? re[t.COERCERTLFULL] : re[t.COERCERTL]\\n let next\\n while ((next = coerceRtlRegex.exec(version)) &&\\n (!match || match.index + match[0].length !== version.length)\\n ) {\\n if (!match ||\\n next.index + next[0].length !== match.index + match[0].length) {\\n match = next\\n }\\n coerceRtlRegex.lastIndex = next.index + next[1].length + next[2].length\\n }\\n // leave it in a clean state\\n coerceRtlRegex.lastIndex = -1\\n }\\n\\n if (match === null) {\\n return null\\n }\\n\\n const major = match[2]\\n const minor = match[3] || '0'\\n const patch = match[4] || '0'\\n const prerelease = options.includePrerelease && match[5] ? `-${match[5]}` : ''\\n const build = options.includePrerelease && match[6] ? `+${match[6]}` : ''\\n\\n return parse(`${major}.${minor}.${patch}${prerelease}${build}`, options)\\n}\\nmodule.exports = coerce\\n\",\"'use strict'\\n\\nclass LRUCache {\\n constructor () {\\n this.max = 1000\\n this.map = new Map()\\n }\\n\\n get (key) {\\n const value = this.map.get(key)\\n if (value === undefined) {\\n return undefined\\n } else {\\n // Remove the key from the map and add it to the end\\n this.map.delete(key)\\n this.map.set(key, value)\\n return value\\n }\\n }\\n\\n delete (key) {\\n return this.map.delete(key)\\n }\\n\\n set (key, value) {\\n const deleted = this.delete(key)\\n\\n if (!deleted && value !== undefined) {\\n // If cache is full, delete the least recently used item\\n if (this.map.size >= this.max) {\\n const firstKey = this.map.keys().next().value\\n this.delete(firstKey)\\n }\\n\\n this.map.set(key, value)\\n }\\n\\n return this\\n }\\n}\\n\\nmodule.exports = LRUCache\\n\",\"'use strict'\\n\\nconst SPACE_CHARACTERS = /\\\\s+/g\\n\\n// hoisted class for cyclic dependency\\nclass Range {\\n constructor (range, options) {\\n options = parseOptions(options)\\n\\n if (range instanceof Range) {\\n if (\\n range.loose === !!options.loose &&\\n range.includePrerelease === !!options.includePrerelease\\n ) {\\n return range\\n } else {\\n return new Range(range.raw, options)\\n }\\n }\\n\\n if (range instanceof Comparator) {\\n // just put it in the set and return\\n this.raw = range.value\\n this.set = [[range]]\\n this.formatted = undefined\\n return this\\n }\\n\\n this.options = options\\n this.loose = !!options.loose\\n this.includePrerelease = !!options.includePrerelease\\n\\n // First reduce all whitespace as much as possible so we do not have to rely\\n // on potentially slow regexes like \\\\s*. This is then stored and used for\\n // future error messages as well.\\n this.raw = range.trim().replace(SPACE_CHARACTERS, ' ')\\n\\n // First, split on ||\\n this.set = this.raw\\n .split('||')\\n // map the range to a 2d array of comparators\\n .map(r => this.parseRange(r.trim()))\\n // throw out any comparator lists that are empty\\n // this generally means that it was not a valid range, which is allowed\\n // in loose mode, but will still throw if the WHOLE range is invalid.\\n .filter(c => c.length)\\n\\n if (!this.set.length) {\\n throw new TypeError(`Invalid SemVer Range: ${this.raw}`)\\n }\\n\\n // if we have any that are not the null set, throw out null sets.\\n if (this.set.length > 1) {\\n // keep the first one, in case they're all null sets\\n const first = this.set[0]\\n this.set = this.set.filter(c => !isNullSet(c[0]))\\n if (this.set.length === 0) {\\n this.set = [first]\\n } else if (this.set.length > 1) {\\n // if we have any that are *, then the range is just *\\n for (const c of this.set) {\\n if (c.length === 1 && isAny(c[0])) {\\n this.set = [c]\\n break\\n }\\n }\\n }\\n }\\n\\n this.formatted = undefined\\n }\\n\\n get range () {\\n if (this.formatted === undefined) {\\n this.formatted = ''\\n for (let i = 0; i < this.set.length; i++) {\\n if (i > 0) {\\n this.formatted += '||'\\n }\\n const comps = this.set[i]\\n for (let k = 0; k < comps.length; k++) {\\n if (k > 0) {\\n this.formatted += ' '\\n }\\n this.formatted += comps[k].toString().trim()\\n }\\n }\\n }\\n return this.formatted\\n }\\n\\n format () {\\n return this.range\\n }\\n\\n toString () {\\n return this.range\\n }\\n\\n parseRange (range) {\\n // memoize range parsing for performance.\\n // this is a very hot path, and fully deterministic.\\n const memoOpts =\\n (this.options.includePrerelease && FLAG_INCLUDE_PRERELEASE) |\\n (this.options.loose && FLAG_LOOSE)\\n const memoKey = memoOpts + ':' + range\\n const cached = cache.get(memoKey)\\n if (cached) {\\n return cached\\n }\\n\\n const loose = this.options.loose\\n // `1.2.3 - 1.2.4` => `>=1.2.3 <=1.2.4`\\n const hr = loose ? re[t.HYPHENRANGELOOSE] : re[t.HYPHENRANGE]\\n range = range.replace(hr, hyphenReplace(this.options.includePrerelease))\\n debug('hyphen replace', range)\\n\\n // `> 1.2.3 < 1.2.5` => `>1.2.3 <1.2.5`\\n range = range.replace(re[t.COMPARATORTRIM], comparatorTrimReplace)\\n debug('comparator trim', range)\\n\\n // `~ 1.2.3` => `~1.2.3`\\n range = range.replace(re[t.TILDETRIM], tildeTrimReplace)\\n debug('tilde trim', range)\\n\\n // `^ 1.2.3` => `^1.2.3`\\n range = range.replace(re[t.CARETTRIM], caretTrimReplace)\\n debug('caret trim', range)\\n\\n // At this point, the range is completely trimmed and\\n // ready to be split into comparators.\\n\\n let rangeList = range\\n .split(' ')\\n .map(comp => parseComparator(comp, this.options))\\n .join(' ')\\n .split(/\\\\s+/)\\n // >=0.0.0 is equivalent to *\\n .map(comp => replaceGTE0(comp, this.options))\\n\\n if (loose) {\\n // in loose mode, throw out any that are not valid comparators\\n rangeList = rangeList.filter(comp => {\\n debug('loose invalid filter', comp, this.options)\\n return !!comp.match(re[t.COMPARATORLOOSE])\\n })\\n }\\n debug('range list', rangeList)\\n\\n // if any comparators are the null set, then replace with JUST null set\\n // if more than one comparator, remove any * comparators\\n // also, don't include the same comparator more than once\\n const rangeMap = new Map()\\n const comparators = rangeList.map(comp => new Comparator(comp, this.options))\\n for (const comp of comparators) {\\n if (isNullSet(comp)) {\\n return [comp]\\n }\\n rangeMap.set(comp.value, comp)\\n }\\n if (rangeMap.size > 1 && rangeMap.has('')) {\\n rangeMap.delete('')\\n }\\n\\n const result = [...rangeMap.values()]\\n cache.set(memoKey, result)\\n return result\\n }\\n\\n intersects (range, options) {\\n if (!(range instanceof Range)) {\\n throw new TypeError('a Range is required')\\n }\\n\\n return this.set.some((thisComparators) => {\\n return (\\n isSatisfiable(thisComparators, options) &&\\n range.set.some((rangeComparators) => {\\n return (\\n isSatisfiable(rangeComparators, options) &&\\n thisComparators.every((thisComparator) => {\\n return rangeComparators.every((rangeComparator) => {\\n return thisComparator.intersects(rangeComparator, options)\\n })\\n })\\n )\\n })\\n )\\n })\\n }\\n\\n // if ANY of the sets match ALL of its comparators, then pass\\n test (version) {\\n if (!version) {\\n return false\\n }\\n\\n if (typeof version === 'string') {\\n try {\\n version = new SemVer(version, this.options)\\n } catch (er) {\\n return false\\n }\\n }\\n\\n for (let i = 0; i < this.set.length; i++) {\\n if (testSet(this.set[i], version, this.options)) {\\n return true\\n }\\n }\\n return false\\n }\\n}\\n\\nmodule.exports = Range\\n\\nconst LRU = require('../internal/lrucache')\\nconst cache = new LRU()\\n\\nconst parseOptions = require('../internal/parse-options')\\nconst Comparator = require('./comparator')\\nconst debug = require('../internal/debug')\\nconst SemVer = require('./semver')\\nconst {\\n safeRe: re,\\n t,\\n comparatorTrimReplace,\\n tildeTrimReplace,\\n caretTrimReplace,\\n} = require('../internal/re')\\nconst { FLAG_INCLUDE_PRERELEASE, FLAG_LOOSE } = require('../internal/constants')\\n\\nconst isNullSet = c => c.value === '<0.0.0-0'\\nconst isAny = c => c.value === ''\\n\\n// take a set of comparators and determine whether there\\n// exists a version which can satisfy it\\nconst isSatisfiable = (comparators, options) => {\\n let result = true\\n const remainingComparators = comparators.slice()\\n let testComparator = remainingComparators.pop()\\n\\n while (result && remainingComparators.length) {\\n result = remainingComparators.every((otherComparator) => {\\n return testComparator.intersects(otherComparator, options)\\n })\\n\\n testComparator = remainingComparators.pop()\\n }\\n\\n return result\\n}\\n\\n// comprised of xranges, tildes, stars, and gtlt's at this point.\\n// already replaced the hyphen ranges\\n// turn into a set of JUST comparators.\\nconst parseComparator = (comp, options) => {\\n comp = comp.replace(re[t.BUILD], '')\\n debug('comp', comp, options)\\n comp = replaceCarets(comp, options)\\n debug('caret', comp)\\n comp = replaceTildes(comp, options)\\n debug('tildes', comp)\\n comp = replaceXRanges(comp, options)\\n debug('xrange', comp)\\n comp = replaceStars(comp, options)\\n debug('stars', comp)\\n return comp\\n}\\n\\nconst isX = id => !id || id.toLowerCase() === 'x' || id === '*'\\n\\n// ~, ~> --> * (any, kinda silly)\\n// ~2, ~2.x, ~2.x.x, ~>2, ~>2.x ~>2.x.x --> >=2.0.0 <3.0.0-0\\n// ~2.0, ~2.0.x, ~>2.0, ~>2.0.x --> >=2.0.0 <2.1.0-0\\n// ~1.2, ~1.2.x, ~>1.2, ~>1.2.x --> >=1.2.0 <1.3.0-0\\n// ~1.2.3, ~>1.2.3 --> >=1.2.3 <1.3.0-0\\n// ~1.2.0, ~>1.2.0 --> >=1.2.0 <1.3.0-0\\n// ~0.0.1 --> >=0.0.1 <0.1.0-0\\nconst replaceTildes = (comp, options) => {\\n return comp\\n .trim()\\n .split(/\\\\s+/)\\n .map((c) => replaceTilde(c, options))\\n .join(' ')\\n}\\n\\nconst replaceTilde = (comp, options) => {\\n const r = options.loose ? re[t.TILDELOOSE] : re[t.TILDE]\\n return comp.replace(r, (_, M, m, p, pr) => {\\n debug('tilde', comp, _, M, m, p, pr)\\n let ret\\n\\n if (isX(M)) {\\n ret = ''\\n } else if (isX(m)) {\\n ret = `>=${M}.0.0 <${+M + 1}.0.0-0`\\n } else if (isX(p)) {\\n // ~1.2 == >=1.2.0 <1.3.0-0\\n ret = `>=${M}.${m}.0 <${M}.${+m + 1}.0-0`\\n } else if (pr) {\\n debug('replaceTilde pr', pr)\\n ret = `>=${M}.${m}.${p}-${pr\\n } <${M}.${+m + 1}.0-0`\\n } else {\\n // ~1.2.3 == >=1.2.3 <1.3.0-0\\n ret = `>=${M}.${m}.${p\\n } <${M}.${+m + 1}.0-0`\\n }\\n\\n debug('tilde return', ret)\\n return ret\\n })\\n}\\n\\n// ^ --> * (any, kinda silly)\\n// ^2, ^2.x, ^2.x.x --> >=2.0.0 <3.0.0-0\\n// ^2.0, ^2.0.x --> >=2.0.0 <3.0.0-0\\n// ^1.2, ^1.2.x --> >=1.2.0 <2.0.0-0\\n// ^1.2.3 --> >=1.2.3 <2.0.0-0\\n// ^1.2.0 --> >=1.2.0 <2.0.0-0\\n// ^0.0.1 --> >=0.0.1 <0.0.2-0\\n// ^0.1.0 --> >=0.1.0 <0.2.0-0\\nconst replaceCarets = (comp, options) => {\\n return comp\\n .trim()\\n .split(/\\\\s+/)\\n .map((c) => replaceCaret(c, options))\\n .join(' ')\\n}\\n\\nconst replaceCaret = (comp, options) => {\\n debug('caret', comp, options)\\n const r = options.loose ? re[t.CARETLOOSE] : re[t.CARET]\\n const z = options.includePrerelease ? '-0' : ''\\n return comp.replace(r, (_, M, m, p, pr) => {\\n debug('caret', comp, _, M, m, p, pr)\\n let ret\\n\\n if (isX(M)) {\\n ret = ''\\n } else if (isX(m)) {\\n ret = `>=${M}.0.0${z} <${+M + 1}.0.0-0`\\n } else if (isX(p)) {\\n if (M === '0') {\\n ret = `>=${M}.${m}.0${z} <${M}.${+m + 1}.0-0`\\n } else {\\n ret = `>=${M}.${m}.0${z} <${+M + 1}.0.0-0`\\n }\\n } else if (pr) {\\n debug('replaceCaret pr', pr)\\n if (M === '0') {\\n if (m === '0') {\\n ret = `>=${M}.${m}.${p}-${pr\\n } <${M}.${m}.${+p + 1}-0`\\n } else {\\n ret = `>=${M}.${m}.${p}-${pr\\n } <${M}.${+m + 1}.0-0`\\n }\\n } else {\\n ret = `>=${M}.${m}.${p}-${pr\\n } <${+M + 1}.0.0-0`\\n }\\n } else {\\n debug('no pr')\\n if (M === '0') {\\n if (m === '0') {\\n ret = `>=${M}.${m}.${p\\n }${z} <${M}.${m}.${+p + 1}-0`\\n } else {\\n ret = `>=${M}.${m}.${p\\n }${z} <${M}.${+m + 1}.0-0`\\n }\\n } else {\\n ret = `>=${M}.${m}.${p\\n } <${+M + 1}.0.0-0`\\n }\\n }\\n\\n debug('caret return', ret)\\n return ret\\n })\\n}\\n\\nconst replaceXRanges = (comp, options) => {\\n debug('replaceXRanges', comp, options)\\n return comp\\n .split(/\\\\s+/)\\n .map((c) => replaceXRange(c, options))\\n .join(' ')\\n}\\n\\nconst replaceXRange = (comp, options) => {\\n comp = comp.trim()\\n const r = options.loose ? re[t.XRANGELOOSE] : re[t.XRANGE]\\n return comp.replace(r, (ret, gtlt, M, m, p, pr) => {\\n debug('xRange', comp, ret, gtlt, M, m, p, pr)\\n const xM = isX(M)\\n const xm = xM || isX(m)\\n const xp = xm || isX(p)\\n const anyX = xp\\n\\n if (gtlt === '=' && anyX) {\\n gtlt = ''\\n }\\n\\n // if we're including prereleases in the match, then we need\\n // to fix this to -0, the lowest possible prerelease value\\n pr = options.includePrerelease ? '-0' : ''\\n\\n if (xM) {\\n if (gtlt === '>' || gtlt === '<') {\\n // nothing is allowed\\n ret = '<0.0.0-0'\\n } else {\\n // nothing is forbidden\\n ret = '*'\\n }\\n } else if (gtlt && anyX) {\\n // we know patch is an x, because we have any x at all.\\n // replace X with 0\\n if (xm) {\\n m = 0\\n }\\n p = 0\\n\\n if (gtlt === '>') {\\n // >1 => >=2.0.0\\n // >1.2 => >=1.3.0\\n gtlt = '>='\\n if (xm) {\\n M = +M + 1\\n m = 0\\n p = 0\\n } else {\\n m = +m + 1\\n p = 0\\n }\\n } else if (gtlt === '<=') {\\n // <=0.7.x is actually <0.8.0, since any 0.7.x should\\n // pass. Similarly, <=7.x is actually <8.0.0, etc.\\n gtlt = '<'\\n if (xm) {\\n M = +M + 1\\n } else {\\n m = +m + 1\\n }\\n }\\n\\n if (gtlt === '<') {\\n pr = '-0'\\n }\\n\\n ret = `${gtlt + M}.${m}.${p}${pr}`\\n } else if (xm) {\\n ret = `>=${M}.0.0${pr} <${+M + 1}.0.0-0`\\n } else if (xp) {\\n ret = `>=${M}.${m}.0${pr\\n } <${M}.${+m + 1}.0-0`\\n }\\n\\n debug('xRange return', ret)\\n\\n return ret\\n })\\n}\\n\\n// Because * is AND-ed with everything else in the comparator,\\n// and '' means \\\"any version\\\", just remove the *s entirely.\\nconst replaceStars = (comp, options) => {\\n debug('replaceStars', comp, options)\\n // Looseness is ignored here. star is always as loose as it gets!\\n return comp\\n .trim()\\n .replace(re[t.STAR], '')\\n}\\n\\nconst replaceGTE0 = (comp, options) => {\\n debug('replaceGTE0', comp, options)\\n return comp\\n .trim()\\n .replace(re[options.includePrerelease ? t.GTE0PRE : t.GTE0], '')\\n}\\n\\n// This function is passed to string.replace(re[t.HYPHENRANGE])\\n// M, m, patch, prerelease, build\\n// 1.2 - 3.4.5 => >=1.2.0 <=3.4.5\\n// 1.2.3 - 3.4 => >=1.2.0 <3.5.0-0 Any 3.4.x will do\\n// 1.2 - 3.4 => >=1.2.0 <3.5.0-0\\n// TODO build?\\nconst hyphenReplace = incPr => ($0,\\n from, fM, fm, fp, fpr, fb,\\n to, tM, tm, tp, tpr) => {\\n if (isX(fM)) {\\n from = ''\\n } else if (isX(fm)) {\\n from = `>=${fM}.0.0${incPr ? '-0' : ''}`\\n } else if (isX(fp)) {\\n from = `>=${fM}.${fm}.0${incPr ? '-0' : ''}`\\n } else if (fpr) {\\n from = `>=${from}`\\n } else {\\n from = `>=${from}${incPr ? '-0' : ''}`\\n }\\n\\n if (isX(tM)) {\\n to = ''\\n } else if (isX(tm)) {\\n to = `<${+tM + 1}.0.0-0`\\n } else if (isX(tp)) {\\n to = `<${tM}.${+tm + 1}.0-0`\\n } else if (tpr) {\\n to = `<=${tM}.${tm}.${tp}-${tpr}`\\n } else if (incPr) {\\n to = `<${tM}.${tm}.${+tp + 1}-0`\\n } else {\\n to = `<=${to}`\\n }\\n\\n return `${from} ${to}`.trim()\\n}\\n\\nconst testSet = (set, version, options) => {\\n for (let i = 0; i < set.length; i++) {\\n if (!set[i].test(version)) {\\n return false\\n }\\n }\\n\\n if (version.prerelease.length && !options.includePrerelease) {\\n // Find the set of versions that are allowed to have prereleases\\n // For example, ^1.2.3-pr.1 desugars to >=1.2.3-pr.1 <2.0.0\\n // That should allow `1.2.3-pr.2` to pass.\\n // However, `1.2.4-alpha.notready` should NOT be allowed,\\n // even though it's within the range set by the comparators.\\n for (let i = 0; i < set.length; i++) {\\n debug(set[i].semver)\\n if (set[i].semver === Comparator.ANY) {\\n continue\\n }\\n\\n if (set[i].semver.prerelease.length > 0) {\\n const allowed = set[i].semver\\n if (allowed.major === version.major &&\\n allowed.minor === version.minor &&\\n allowed.patch === version.patch) {\\n return true\\n }\\n }\\n }\\n\\n // Version has a -pre, but it's not one of the ones we like.\\n return false\\n }\\n\\n return true\\n}\\n\",\"'use strict'\\n\\nconst ANY = Symbol('SemVer ANY')\\n// hoisted class for cyclic dependency\\nclass Comparator {\\n static get ANY () {\\n return ANY\\n }\\n\\n constructor (comp, options) {\\n options = parseOptions(options)\\n\\n if (comp instanceof Comparator) {\\n if (comp.loose === !!options.loose) {\\n return comp\\n } else {\\n comp = comp.value\\n }\\n }\\n\\n comp = comp.trim().split(/\\\\s+/).join(' ')\\n debug('comparator', comp, options)\\n this.options = options\\n this.loose = !!options.loose\\n this.parse(comp)\\n\\n if (this.semver === ANY) {\\n this.value = ''\\n } else {\\n this.value = this.operator + this.semver.version\\n }\\n\\n debug('comp', this)\\n }\\n\\n parse (comp) {\\n const r = this.options.loose ? re[t.COMPARATORLOOSE] : re[t.COMPARATOR]\\n const m = comp.match(r)\\n\\n if (!m) {\\n throw new TypeError(`Invalid comparator: ${comp}`)\\n }\\n\\n this.operator = m[1] !== undefined ? m[1] : ''\\n if (this.operator === '=') {\\n this.operator = ''\\n }\\n\\n // if it literally is just '>' or '' then allow anything.\\n if (!m[2]) {\\n this.semver = ANY\\n } else {\\n this.semver = new SemVer(m[2], this.options.loose)\\n }\\n }\\n\\n toString () {\\n return this.value\\n }\\n\\n test (version) {\\n debug('Comparator.test', version, this.options.loose)\\n\\n if (this.semver === ANY || version === ANY) {\\n return true\\n }\\n\\n if (typeof version === 'string') {\\n try {\\n version = new SemVer(version, this.options)\\n } catch (er) {\\n return false\\n }\\n }\\n\\n return cmp(version, this.operator, this.semver, this.options)\\n }\\n\\n intersects (comp, options) {\\n if (!(comp instanceof Comparator)) {\\n throw new TypeError('a Comparator is required')\\n }\\n\\n if (this.operator === '') {\\n if (this.value === '') {\\n return true\\n }\\n return new Range(comp.value, options).test(this.value)\\n } else if (comp.operator === '') {\\n if (comp.value === '') {\\n return true\\n }\\n return new Range(this.value, options).test(comp.semver)\\n }\\n\\n options = parseOptions(options)\\n\\n // Special cases where nothing can possibly be lower\\n if (options.includePrerelease &&\\n (this.value === '<0.0.0-0' || comp.value === '<0.0.0-0')) {\\n return false\\n }\\n if (!options.includePrerelease &&\\n (this.value.startsWith('<0.0.0') || comp.value.startsWith('<0.0.0'))) {\\n return false\\n }\\n\\n // Same direction increasing (> or >=)\\n if (this.operator.startsWith('>') && comp.operator.startsWith('>')) {\\n return true\\n }\\n // Same direction decreasing (< or <=)\\n if (this.operator.startsWith('<') && comp.operator.startsWith('<')) {\\n return true\\n }\\n // same SemVer and both sides are inclusive (<= or >=)\\n if (\\n (this.semver.version === comp.semver.version) &&\\n this.operator.includes('=') && comp.operator.includes('=')) {\\n return true\\n }\\n // opposite directions less than\\n if (cmp(this.semver, '<', comp.semver, options) &&\\n this.operator.startsWith('>') && comp.operator.startsWith('<')) {\\n return true\\n }\\n // opposite directions greater than\\n if (cmp(this.semver, '>', comp.semver, options) &&\\n this.operator.startsWith('<') && comp.operator.startsWith('>')) {\\n return true\\n }\\n return false\\n }\\n}\\n\\nmodule.exports = Comparator\\n\\nconst parseOptions = require('../internal/parse-options')\\nconst { safeRe: re, t } = require('../internal/re')\\nconst cmp = require('../functions/cmp')\\nconst debug = require('../internal/debug')\\nconst SemVer = require('./semver')\\nconst Range = require('./range')\\n\",\"'use strict'\\n\\nconst Range = require('../classes/range')\\nconst satisfies = (version, range, options) => {\\n try {\\n range = new Range(range, options)\\n } catch (er) {\\n return false\\n }\\n return range.test(version)\\n}\\nmodule.exports = satisfies\\n\",\"'use strict'\\n\\nconst Range = require('../classes/range')\\n\\n// Mostly just for testing and legacy API reasons\\nconst toComparators = (range, options) =>\\n new Range(range, options).set\\n .map(comp => comp.map(c => c.value).join(' ').trim().split(' '))\\n\\nmodule.exports = toComparators\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst Range = require('../classes/range')\\n\\nconst maxSatisfying = (versions, range, options) => {\\n let max = null\\n let maxSV = null\\n let rangeObj = null\\n try {\\n rangeObj = new Range(range, options)\\n } catch (er) {\\n return null\\n }\\n versions.forEach((v) => {\\n if (rangeObj.test(v)) {\\n // satisfies(v, range, options)\\n if (!max || maxSV.compare(v) === -1) {\\n // compare(max, v, true)\\n max = v\\n maxSV = new SemVer(max, options)\\n }\\n }\\n })\\n return max\\n}\\nmodule.exports = maxSatisfying\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst Range = require('../classes/range')\\nconst minSatisfying = (versions, range, options) => {\\n let min = null\\n let minSV = null\\n let rangeObj = null\\n try {\\n rangeObj = new Range(range, options)\\n } catch (er) {\\n return null\\n }\\n versions.forEach((v) => {\\n if (rangeObj.test(v)) {\\n // satisfies(v, range, options)\\n if (!min || minSV.compare(v) === 1) {\\n // compare(min, v, true)\\n min = v\\n minSV = new SemVer(min, options)\\n }\\n }\\n })\\n return min\\n}\\nmodule.exports = minSatisfying\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst Range = require('../classes/range')\\nconst gt = require('../functions/gt')\\n\\nconst minVersion = (range, loose) => {\\n range = new Range(range, loose)\\n\\n let minver = new SemVer('0.0.0')\\n if (range.test(minver)) {\\n return minver\\n }\\n\\n minver = new SemVer('0.0.0-0')\\n if (range.test(minver)) {\\n return minver\\n }\\n\\n minver = null\\n for (let i = 0; i < range.set.length; ++i) {\\n const comparators = range.set[i]\\n\\n let setMin = null\\n comparators.forEach((comparator) => {\\n // Clone to avoid manipulating the comparator's semver object.\\n const compver = new SemVer(comparator.semver.version)\\n switch (comparator.operator) {\\n case '>':\\n if (compver.prerelease.length === 0) {\\n compver.patch++\\n } else {\\n compver.prerelease.push(0)\\n }\\n compver.raw = compver.format()\\n /* fallthrough */\\n case '':\\n case '>=':\\n if (!setMin || gt(compver, setMin)) {\\n setMin = compver\\n }\\n break\\n case '<':\\n case '<=':\\n /* Ignore maximum versions */\\n break\\n /* istanbul ignore next */\\n default:\\n throw new Error(`Unexpected operation: ${comparator.operator}`)\\n }\\n })\\n if (setMin && (!minver || gt(minver, setMin))) {\\n minver = setMin\\n }\\n }\\n\\n if (minver && range.test(minver)) {\\n return minver\\n }\\n\\n return null\\n}\\nmodule.exports = minVersion\\n\",\"'use strict'\\n\\nconst Range = require('../classes/range')\\nconst validRange = (range, options) => {\\n try {\\n // Return '*' instead of '' so that truthiness works.\\n // This will throw if it's invalid anyway\\n return new Range(range, options).range || '*'\\n } catch (er) {\\n return null\\n }\\n}\\nmodule.exports = validRange\\n\",\"'use strict'\\n\\nconst SemVer = require('../classes/semver')\\nconst Comparator = require('../classes/comparator')\\nconst { ANY } = Comparator\\nconst Range = require('../classes/range')\\nconst satisfies = require('../functions/satisfies')\\nconst gt = require('../functions/gt')\\nconst lt = require('../functions/lt')\\nconst lte = require('../functions/lte')\\nconst gte = require('../functions/gte')\\n\\nconst outside = (version, range, hilo, options) => {\\n version = new SemVer(version, options)\\n range = new Range(range, options)\\n\\n let gtfn, ltefn, ltfn, comp, ecomp\\n switch (hilo) {\\n case '>':\\n gtfn = gt\\n ltefn = lte\\n ltfn = lt\\n comp = '>'\\n ecomp = '>='\\n break\\n case '<':\\n gtfn = lt\\n ltefn = gte\\n ltfn = gt\\n comp = '<'\\n ecomp = '<='\\n break\\n default:\\n throw new TypeError('Must provide a hilo val of \\\"<\\\" or \\\">\\\"')\\n }\\n\\n // If it satisfies the range it is not outside\\n if (satisfies(version, range, options)) {\\n return false\\n }\\n\\n // From now on, variable terms are as if we're in \\\"gtr\\\" mode.\\n // but note that everything is flipped for the \\\"ltr\\\" function.\\n\\n for (let i = 0; i < range.set.length; ++i) {\\n const comparators = range.set[i]\\n\\n let high = null\\n let low = null\\n\\n comparators.forEach((comparator) => {\\n if (comparator.semver === ANY) {\\n comparator = new Comparator('>=0.0.0')\\n }\\n high = high || comparator\\n low = low || comparator\\n if (gtfn(comparator.semver, high.semver, options)) {\\n high = comparator\\n } else if (ltfn(comparator.semver, low.semver, options)) {\\n low = comparator\\n }\\n })\\n\\n // If the edge version comparator has a operator then our version\\n // isn't outside it\\n if (high.operator === comp || high.operator === ecomp) {\\n return false\\n }\\n\\n // If the lowest version comparator has an operator and our version\\n // is less than it then it isn't higher than the range\\n if ((!low.operator || low.operator === comp) &&\\n ltefn(version, low.semver)) {\\n return false\\n } else if (low.operator === ecomp && ltfn(version, low.semver)) {\\n return false\\n }\\n }\\n return true\\n}\\n\\nmodule.exports = outside\\n\",\"'use strict'\\n\\n// Determine if version is greater than all the versions possible in the range.\\nconst outside = require('./outside')\\nconst gtr = (version, range, options) => outside(version, range, '>', options)\\nmodule.exports = gtr\\n\",\"'use strict'\\n\\nconst outside = require('./outside')\\n// Determine if version is less than all the versions possible in the range\\nconst ltr = (version, range, options) => outside(version, range, '<', options)\\nmodule.exports = ltr\\n\",\"'use strict'\\n\\nconst Range = require('../classes/range')\\nconst intersects = (r1, r2, options) => {\\n r1 = new Range(r1, options)\\n r2 = new Range(r2, options)\\n return r1.intersects(r2, options)\\n}\\nmodule.exports = intersects\\n\",\"'use strict'\\n\\n// given a set of versions and a range, create a \\\"simplified\\\" range\\n// that includes the same versions that the original range does\\n// If the original range is shorter than the simplified one, return that.\\nconst satisfies = require('../functions/satisfies.js')\\nconst compare = require('../functions/compare.js')\\nmodule.exports = (versions, range, options) => {\\n const set = []\\n let first = null\\n let prev = null\\n const v = versions.sort((a, b) => compare(a, b, options))\\n for (const version of v) {\\n const included = satisfies(version, range, options)\\n if (included) {\\n prev = version\\n if (!first) {\\n first = version\\n }\\n } else {\\n if (prev) {\\n set.push([first, prev])\\n }\\n prev = null\\n first = null\\n }\\n }\\n if (first) {\\n set.push([first, null])\\n }\\n\\n const ranges = []\\n for (const [min, max] of set) {\\n if (min === max) {\\n ranges.push(min)\\n } else if (!max && min === v[0]) {\\n ranges.push('*')\\n } else if (!max) {\\n ranges.push(`>=${min}`)\\n } else if (min === v[0]) {\\n ranges.push(`<=${max}`)\\n } else {\\n ranges.push(`${min} - ${max}`)\\n }\\n }\\n const simplified = ranges.join(' || ')\\n const original = typeof range.raw === 'string' ? range.raw : String(range)\\n return simplified.length < original.length ? simplified : range\\n}\\n\",\"'use strict'\\n\\nconst Range = require('../classes/range.js')\\nconst Comparator = require('../classes/comparator.js')\\nconst { ANY } = Comparator\\nconst satisfies = require('../functions/satisfies.js')\\nconst compare = require('../functions/compare.js')\\n\\n// Complex range `r1 || r2 || ...` is a subset of `R1 || R2 || ...` iff:\\n// - Every simple range `r1, r2, ...` is a null set, OR\\n// - Every simple range `r1, r2, ...` which is not a null set is a subset of\\n// some `R1, R2, ...`\\n//\\n// Simple range `c1 c2 ...` is a subset of simple range `C1 C2 ...` iff:\\n// - If c is only the ANY comparator\\n// - If C is only the ANY comparator, return true\\n// - Else if in prerelease mode, return false\\n// - else replace c with `[>=0.0.0]`\\n// - If C is only the ANY comparator\\n// - if in prerelease mode, return true\\n// - else replace C with `[>=0.0.0]`\\n// - Let EQ be the set of = comparators in c\\n// - If EQ is more than one, return true (null set)\\n// - Let GT be the highest > or >= comparator in c\\n// - Let LT be the lowest < or <= comparator in c\\n// - If GT and LT, and GT.semver > LT.semver, return true (null set)\\n// - If any C is a = range, and GT or LT are set, return false\\n// - If EQ\\n// - If GT, and EQ does not satisfy GT, return true (null set)\\n// - If LT, and EQ does not satisfy LT, return true (null set)\\n// - If EQ satisfies every C, return true\\n// - Else return false\\n// - If GT\\n// - If GT.semver is lower than any > or >= comp in C, return false\\n// - If GT is >=, and GT.semver does not satisfy every C, return false\\n// - If GT.semver has a prerelease, and not in prerelease mode\\n// - If no C has a prerelease and the GT.semver tuple, return false\\n// - If LT\\n// - If LT.semver is greater than any < or <= comp in C, return false\\n// - If LT is <=, and LT.semver does not satisfy every C, return false\\n// - If GT.semver has a prerelease, and not in prerelease mode\\n// - If no C has a prerelease and the LT.semver tuple, return false\\n// - Else return true\\n\\nconst subset = (sub, dom, options = {}) => {\\n if (sub === dom) {\\n return true\\n }\\n\\n sub = new Range(sub, options)\\n dom = new Range(dom, options)\\n let sawNonNull = false\\n\\n OUTER: for (const simpleSub of sub.set) {\\n for (const simpleDom of dom.set) {\\n const isSub = simpleSubset(simpleSub, simpleDom, options)\\n sawNonNull = sawNonNull || isSub !== null\\n if (isSub) {\\n continue OUTER\\n }\\n }\\n // the null set is a subset of everything, but null simple ranges in\\n // a complex range should be ignored. so if we saw a non-null range,\\n // then we know this isn't a subset, but if EVERY simple range was null,\\n // then it is a subset.\\n if (sawNonNull) {\\n return false\\n }\\n }\\n return true\\n}\\n\\nconst minimumVersionWithPreRelease = [new Comparator('>=0.0.0-0')]\\nconst minimumVersion = [new Comparator('>=0.0.0')]\\n\\nconst simpleSubset = (sub, dom, options) => {\\n if (sub === dom) {\\n return true\\n }\\n\\n if (sub.length === 1 && sub[0].semver === ANY) {\\n if (dom.length === 1 && dom[0].semver === ANY) {\\n return true\\n } else if (options.includePrerelease) {\\n sub = minimumVersionWithPreRelease\\n } else {\\n sub = minimumVersion\\n }\\n }\\n\\n if (dom.length === 1 && dom[0].semver === ANY) {\\n if (options.includePrerelease) {\\n return true\\n } else {\\n dom = minimumVersion\\n }\\n }\\n\\n const eqSet = new Set()\\n let gt, lt\\n for (const c of sub) {\\n if (c.operator === '>' || c.operator === '>=') {\\n gt = higherGT(gt, c, options)\\n } else if (c.operator === '<' || c.operator === '<=') {\\n lt = lowerLT(lt, c, options)\\n } else {\\n eqSet.add(c.semver)\\n }\\n }\\n\\n if (eqSet.size > 1) {\\n return null\\n }\\n\\n let gtltComp\\n if (gt && lt) {\\n gtltComp = compare(gt.semver, lt.semver, options)\\n if (gtltComp > 0) {\\n return null\\n } else if (gtltComp === 0 && (gt.operator !== '>=' || lt.operator !== '<=')) {\\n return null\\n }\\n }\\n\\n // will iterate one or zero times\\n for (const eq of eqSet) {\\n if (gt && !satisfies(eq, String(gt), options)) {\\n return null\\n }\\n\\n if (lt && !satisfies(eq, String(lt), options)) {\\n return null\\n }\\n\\n for (const c of dom) {\\n if (!satisfies(eq, String(c), options)) {\\n return false\\n }\\n }\\n\\n return true\\n }\\n\\n let higher, lower\\n let hasDomLT, hasDomGT\\n // if the subset has a prerelease, we need a comparator in the superset\\n // with the same tuple and a prerelease, or it's not a subset\\n let needDomLTPre = lt &&\\n !options.includePrerelease &&\\n lt.semver.prerelease.length ? lt.semver : false\\n let needDomGTPre = gt &&\\n !options.includePrerelease &&\\n gt.semver.prerelease.length ? gt.semver : false\\n // exception: <1.2.3-0 is the same as <1.2.3\\n if (needDomLTPre && needDomLTPre.prerelease.length === 1 &&\\n lt.operator === '<' && needDomLTPre.prerelease[0] === 0) {\\n needDomLTPre = false\\n }\\n\\n for (const c of dom) {\\n hasDomGT = hasDomGT || c.operator === '>' || c.operator === '>='\\n hasDomLT = hasDomLT || c.operator === '<' || c.operator === '<='\\n if (gt) {\\n if (needDomGTPre) {\\n if (c.semver.prerelease && c.semver.prerelease.length &&\\n c.semver.major === needDomGTPre.major &&\\n c.semver.minor === needDomGTPre.minor &&\\n c.semver.patch === needDomGTPre.patch) {\\n needDomGTPre = false\\n }\\n }\\n if (c.operator === '>' || c.operator === '>=') {\\n higher = higherGT(gt, c, options)\\n if (higher === c && higher !== gt) {\\n return false\\n }\\n } else if (gt.operator === '>=' && !satisfies(gt.semver, String(c), options)) {\\n return false\\n }\\n }\\n if (lt) {\\n if (needDomLTPre) {\\n if (c.semver.prerelease && c.semver.prerelease.length &&\\n c.semver.major === needDomLTPre.major &&\\n c.semver.minor === needDomLTPre.minor &&\\n c.semver.patch === needDomLTPre.patch) {\\n needDomLTPre = false\\n }\\n }\\n if (c.operator === '<' || c.operator === '<=') {\\n lower = lowerLT(lt, c, options)\\n if (lower === c && lower !== lt) {\\n return false\\n }\\n } else if (lt.operator === '<=' && !satisfies(lt.semver, String(c), options)) {\\n return false\\n }\\n }\\n if (!c.operator && (lt || gt) && gtltComp !== 0) {\\n return false\\n }\\n }\\n\\n // if there was a < or >, and nothing in the dom, then must be false\\n // UNLESS it was limited by another range in the other direction.\\n // Eg, >1.0.0 <1.0.1 is still a subset of <2.0.0\\n if (gt && hasDomLT && !lt && gtltComp !== 0) {\\n return false\\n }\\n\\n if (lt && hasDomGT && !gt && gtltComp !== 0) {\\n return false\\n }\\n\\n // we needed a prerelease range in a specific tuple, but didn't get one\\n // then this isn't a subset. eg >=1.2.3-pre is not a subset of >=1.0.0,\\n // because it includes prereleases in the 1.2.3 tuple\\n if (needDomGTPre || needDomLTPre) {\\n return false\\n }\\n\\n return true\\n}\\n\\n// >=1.2.3 is lower than >1.2.3\\nconst higherGT = (a, b, options) => {\\n if (!a) {\\n return b\\n }\\n const comp = compare(a.semver, b.semver, options)\\n return comp > 0 ? a\\n : comp < 0 ? b\\n : b.operator === '>' && a.operator === '>=' ? b\\n : a\\n}\\n\\n// <=1.2.3 is higher than <1.2.3\\nconst lowerLT = (a, b, options) => {\\n if (!a) {\\n return b\\n }\\n const comp = compare(a.semver, b.semver, options)\\n return comp < 0 ? a\\n : comp > 0 ? b\\n : b.operator === '<' && a.operator === '<=' ? b\\n : a\\n}\\n\\nmodule.exports = subset\\n\",\"'use strict'\\n\\n// just pre-load all the stuff that index.js lazily exports\\nconst internalRe = require('./internal/re')\\nconst constants = require('./internal/constants')\\nconst SemVer = require('./classes/semver')\\nconst identifiers = require('./internal/identifiers')\\nconst parse = require('./functions/parse')\\nconst valid = require('./functions/valid')\\nconst clean = require('./functions/clean')\\nconst inc = require('./functions/inc')\\nconst diff = require('./functions/diff')\\nconst major = require('./functions/major')\\nconst minor = require('./functions/minor')\\nconst patch = require('./functions/patch')\\nconst prerelease = require('./functions/prerelease')\\nconst compare = require('./functions/compare')\\nconst rcompare = require('./functions/rcompare')\\nconst compareLoose = require('./functions/compare-loose')\\nconst compareBuild = require('./functions/compare-build')\\nconst sort = require('./functions/sort')\\nconst rsort = require('./functions/rsort')\\nconst gt = require('./functions/gt')\\nconst lt = require('./functions/lt')\\nconst eq = require('./functions/eq')\\nconst neq = require('./functions/neq')\\nconst gte = require('./functions/gte')\\nconst lte = require('./functions/lte')\\nconst cmp = require('./functions/cmp')\\nconst coerce = require('./functions/coerce')\\nconst Comparator = require('./classes/comparator')\\nconst Range = require('./classes/range')\\nconst satisfies = require('./functions/satisfies')\\nconst toComparators = require('./ranges/to-comparators')\\nconst maxSatisfying = require('./ranges/max-satisfying')\\nconst minSatisfying = require('./ranges/min-satisfying')\\nconst minVersion = require('./ranges/min-version')\\nconst validRange = require('./ranges/valid')\\nconst outside = require('./ranges/outside')\\nconst gtr = require('./ranges/gtr')\\nconst ltr = require('./ranges/ltr')\\nconst intersects = require('./ranges/intersects')\\nconst simplifyRange = require('./ranges/simplify')\\nconst subset = require('./ranges/subset')\\nmodule.exports = {\\n parse,\\n valid,\\n clean,\\n inc,\\n diff,\\n major,\\n minor,\\n patch,\\n prerelease,\\n compare,\\n rcompare,\\n compareLoose,\\n compareBuild,\\n sort,\\n rsort,\\n gt,\\n lt,\\n eq,\\n neq,\\n gte,\\n lte,\\n cmp,\\n coerce,\\n Comparator,\\n Range,\\n satisfies,\\n toComparators,\\n maxSatisfying,\\n minSatisfying,\\n minVersion,\\n validRange,\\n outside,\\n gtr,\\n ltr,\\n intersects,\\n simplifyRange,\\n subset,\\n SemVer,\\n re: internalRe.re,\\n src: internalRe.src,\\n tokens: internalRe.t,\\n SEMVER_SPEC_VERSION: constants.SEMVER_SPEC_VERSION,\\n RELEASE_TYPES: constants.RELEASE_TYPES,\\n compareIdentifiers: identifiers.compareIdentifiers,\\n rcompareIdentifiers: identifiers.rcompareIdentifiers,\\n}\\n\",\"/*! crc32.js (C) 2014-present SheetJS -- http://sheetjs.com */\\n/* vim: set ts=2: */\\n/*exported CRC32 */\\nvar CRC32;\\n(function (factory) {\\n\\t/*jshint ignore:start */\\n\\t/*eslint-disable */\\n\\tif(typeof DO_NOT_EXPORT_CRC === 'undefined') {\\n\\t\\tif('object' === typeof exports) {\\n\\t\\t\\tfactory(exports);\\n\\t\\t} else if ('function' === typeof define && define.amd) {\\n\\t\\t\\tdefine(function () {\\n\\t\\t\\t\\tvar module = {};\\n\\t\\t\\t\\tfactory(module);\\n\\t\\t\\t\\treturn module;\\n\\t\\t\\t});\\n\\t\\t} else {\\n\\t\\t\\tfactory(CRC32 = {});\\n\\t\\t}\\n\\t} else {\\n\\t\\tfactory(CRC32 = {});\\n\\t}\\n\\t/*eslint-enable */\\n\\t/*jshint ignore:end */\\n}(function(CRC32) {\\nCRC32.version = '1.2.2';\\n/*global Int32Array */\\nfunction signed_crc_table() {\\n\\tvar c = 0, table = new Array(256);\\n\\n\\tfor(var n =0; n != 256; ++n){\\n\\t\\tc = n;\\n\\t\\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\\n\\t\\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\\n\\t\\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\\n\\t\\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\\n\\t\\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\\n\\t\\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\\n\\t\\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\\n\\t\\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\\n\\t\\ttable[n] = c;\\n\\t}\\n\\n\\treturn typeof Int32Array !== 'undefined' ? new Int32Array(table) : table;\\n}\\n\\nvar T0 = signed_crc_table();\\nfunction slice_by_16_tables(T) {\\n\\tvar c = 0, v = 0, n = 0, table = typeof Int32Array !== 'undefined' ? new Int32Array(4096) : new Array(4096) ;\\n\\n\\tfor(n = 0; n != 256; ++n) table[n] = T[n];\\n\\tfor(n = 0; n != 256; ++n) {\\n\\t\\tv = T[n];\\n\\t\\tfor(c = 256 + n; c < 4096; c += 256) v = table[c] = (v >>> 8) ^ T[v & 0xFF];\\n\\t}\\n\\tvar out = [];\\n\\tfor(n = 1; n != 16; ++n) out[n - 1] = typeof Int32Array !== 'undefined' ? table.subarray(n * 256, n * 256 + 256) : table.slice(n * 256, n * 256 + 256);\\n\\treturn out;\\n}\\nvar TT = slice_by_16_tables(T0);\\nvar T1 = TT[0], T2 = TT[1], T3 = TT[2], T4 = TT[3], T5 = TT[4];\\nvar T6 = TT[5], T7 = TT[6], T8 = TT[7], T9 = TT[8], Ta = TT[9];\\nvar Tb = TT[10], Tc = TT[11], Td = TT[12], Te = TT[13], Tf = TT[14];\\nfunction crc32_bstr(bstr, seed) {\\n\\tvar C = seed ^ -1;\\n\\tfor(var i = 0, L = bstr.length; i < L;) C = (C>>>8) ^ T0[(C^bstr.charCodeAt(i++))&0xFF];\\n\\treturn ~C;\\n}\\n\\nfunction crc32_buf(B, seed) {\\n\\tvar C = seed ^ -1, L = B.length - 15, i = 0;\\n\\tfor(; i < L;) C =\\n\\t\\tTf[B[i++] ^ (C & 255)] ^\\n\\t\\tTe[B[i++] ^ ((C >> 8) & 255)] ^\\n\\t\\tTd[B[i++] ^ ((C >> 16) & 255)] ^\\n\\t\\tTc[B[i++] ^ (C >>> 24)] ^\\n\\t\\tTb[B[i++]] ^ Ta[B[i++]] ^ T9[B[i++]] ^ T8[B[i++]] ^\\n\\t\\tT7[B[i++]] ^ T6[B[i++]] ^ T5[B[i++]] ^ T4[B[i++]] ^\\n\\t\\tT3[B[i++]] ^ T2[B[i++]] ^ T1[B[i++]] ^ T0[B[i++]];\\n\\tL += 15;\\n\\twhile(i < L) C = (C>>>8) ^ T0[(C^B[i++])&0xFF];\\n\\treturn ~C;\\n}\\n\\nfunction crc32_str(str, seed) {\\n\\tvar C = seed ^ -1;\\n\\tfor(var i = 0, L = str.length, c = 0, d = 0; i < L;) {\\n\\t\\tc = str.charCodeAt(i++);\\n\\t\\tif(c < 0x80) {\\n\\t\\t\\tC = (C>>>8) ^ T0[(C^c)&0xFF];\\n\\t\\t} else if(c < 0x800) {\\n\\t\\t\\tC = (C>>>8) ^ T0[(C ^ (192|((c>>6)&31)))&0xFF];\\n\\t\\t\\tC = (C>>>8) ^ T0[(C ^ (128|(c&63)))&0xFF];\\n\\t\\t} else if(c >= 0xD800 && c < 0xE000) {\\n\\t\\t\\tc = (c&1023)+64; d = str.charCodeAt(i++)&1023;\\n\\t\\t\\tC = (C>>>8) ^ T0[(C ^ (240|((c>>8)&7)))&0xFF];\\n\\t\\t\\tC = (C>>>8) ^ T0[(C ^ (128|((c>>2)&63)))&0xFF];\\n\\t\\t\\tC = (C>>>8) ^ T0[(C ^ (128|((d>>6)&15)|((c&3)<<4)))&0xFF];\\n\\t\\t\\tC = (C>>>8) ^ T0[(C ^ (128|(d&63)))&0xFF];\\n\\t\\t} else {\\n\\t\\t\\tC = (C>>>8) ^ T0[(C ^ (224|((c>>12)&15)))&0xFF];\\n\\t\\t\\tC = (C>>>8) ^ T0[(C ^ (128|((c>>6)&63)))&0xFF];\\n\\t\\t\\tC = (C>>>8) ^ T0[(C ^ (128|(c&63)))&0xFF];\\n\\t\\t}\\n\\t}\\n\\treturn ~C;\\n}\\nCRC32.table = T0;\\n// $FlowIgnore\\nCRC32.bstr = crc32_bstr;\\n// $FlowIgnore\\nCRC32.buf = crc32_buf;\\n// $FlowIgnore\\nCRC32.str = crc32_str;\\n}));\\n\",\"import { toByteArray, fromByteArray } from 'base64-js';\\nimport { inflateSync } from 'fflate';\\nimport deepEqual from 'fast-deep-equal';\\nimport stableStringify from 'fast-json-stable-stringify';\\nimport he from 'he';\\nimport jsonLogic from 'json-logic-js';\\nimport LinkifyIt from 'linkify-it';\\nimport MarkdownIt from 'markdown-it';\\nimport { sha256 } from '@noble/hashes/sha256';\\nimport { bytesToHex } from '@noble/hashes/utils';\\nimport { match as pathMatch } from 'path-to-regexp';\\nimport semver from 'semver';\\nimport TinyQueue from 'tinyqueue';\\nimport CRC32 from 'crc-32';\\n\\nlet summary;\\ntry {\\n const metadataText = Host.v2.document.get('pack/metadata.json');\\n const ruleText = Host.v2.document.get('rules/findings.json');\\n const compressedAttachment = Host.v2.document.get('pack/attachment.deflated');\\n const payload = Host.v2.document.get('bytes/payload');\\n const extraPayload = Host.v2.document.get('bytes/flagship-extra');\\n\\n const metadata = JSON.parse(metadataText);\\n const docPaths = metadata.links ?? ['docs/a.md', 'docs/b.md'];\\n const docs = docPaths.map((docPath) => ({\\n docPath,\\n text: Host.v2.document.get(docPath),\\n }));\\n const markdown = new MarkdownIt({ linkify: true });\\n const linkify = new LinkifyIt();\\n const markdownSource = docs.map((doc) => doc.text).join('\\\\n');\\n const markdownTokens = markdown.parse(markdownSource, {});\\n const linkMatches = docs\\n .flatMap((doc) => linkify.match(doc.text) ?? [])\\n .map((item) => item.url);\\n\\n const releaseChecks = (metadata.requires ?? []).map((range) =>\\n semver.satisfies(metadata.release, range),\\n );\\n const rules = JSON.parse(ruleText);\\n const findingInput = {\\n linkCount: linkMatches.length,\\n releaseOk: releaseChecks.every(Boolean),\\n };\\n const ruleInputStable = deepEqual(\\n findingInput,\\n JSON.parse(stableStringify(findingInput)),\\n );\\n const rulePasses = Boolean(jsonLogic.apply(rules, findingInput));\\n\\n const queue = new TinyQueue([], (left, right) => left.priority - right.priority);\\n for (const link of linkMatches) {\\n queue.push({ link, priority: link.length });\\n }\\n const orderedLinks = [];\\n while (queue.length > 0) {\\n orderedLinks.push(queue.pop().link);\\n }\\n\\n const decompressed = inflateSync(compressedAttachment);\\n const attachmentRoundTrip = toByteArray(fromByteArray(decompressed));\\n const mergedBinary = new Uint8Array(\\n attachmentRoundTrip.length + payload.length + extraPayload.length,\\n );\\n mergedBinary.set(attachmentRoundTrip, 0);\\n mergedBinary.set(payload, attachmentRoundTrip.length);\\n mergedBinary.set(extraPayload, attachmentRoundTrip.length + payload.length);\\n const digestHex = bytesToHex(sha256(mergedBinary));\\n const crc32 = (CRC32.buf(mergedBinary) >>> 0)\\n .toString(16)\\n .padStart(8, '0');\\n\\n const decodedEntities = he.decode('<b>safe</b>');\\n const versionCapture = pathMatch('/document/:id/version/:version')(\\n '/document/42/version/1.2.3',\\n );\\n const orderedFindings = [\\n { id: 'links', value: linkMatches.length },\\n { id: 'rules', value: Number(rulePasses) },\\n { id: 'tokens', value: markdownTokens.length },\\n ].sort((left, right) => left.id.localeCompare(right.id));\\n\\n Promise.resolve('scheduled').then(() => undefined);\\n queueMicrotask(() => undefined);\\n\\n for (const doc of docs) {\\n Host.v2.emit({\\n type: 'knowledge-pack-doc',\\n docPath: doc.docPath,\\n length: doc.text.length,\\n });\\n }\\n\\n summary = {\\n status: 'ok',\\n packId: metadata.packId,\\n release: metadata.release,\\n checks: releaseChecks,\\n docTokenCount: markdownTokens.length,\\n linkCount: linkMatches.length,\\n uniqueLinks: [...new Set(orderedLinks)],\\n binary: {\\n byteLength: mergedBinary.length,\\n digestHex,\\n crc32,\\n },\\n decodedEntities,\\n versionCapture,\\n findings: orderedFindings,\\n ruleInputStable,\\n rulePasses,\\n };\\n} catch (error) {\\n summary = {\\n status: 'error',\\n message: String(error instanceof Error ? error.message : error),\\n };\\n}\\n\\nHost.v2.emit({\\n type: 'knowledge-pack-summary',\\n summaryHash: bytesToHex(\\n sha256(\\n toByteArray(\\n fromByteArray(\\n new Uint8Array([\\n ...Host.v2.document.get('bytes/payload'),\\n ...Host.v2.document.get('bytes/flagship-extra'),\\n ]),\\n ),\\n ),\\n ),\\n ),\\n status: summary.status,\\n});\\n\\nexport default summary;\\n\",\"// DEFLATE is a complex format; to read this code, you should probably check the RFC first:\\n// https://tools.ietf.org/html/rfc1951\\n// You may also wish to take a look at the guide I made about this program:\\n// https://gist.github.com/101arrowz/253f31eb5abc3d9275ab943003ffecad\\n// Some of the following code is similar to that of UZIP.js:\\n// https://github.com/photopea/UZIP.js\\n// However, the vast majority of the codebase has diverged from UZIP.js to increase performance and reduce bundle size.\\n// Sometimes 0 will appear where -1 would be more appropriate. This is because using a uint\\n// is better for memory in most engines (I *think*).\\nvar ch2 = {};\\nvar wk = (function (c, id, msg, transfer, cb) {\\n var w = new Worker(ch2[id] || (ch2[id] = URL.createObjectURL(new Blob([\\n c + ';addEventListener(\\\"error\\\",function(e){e=e.error;postMessage({$e$:[e.message,e.code,e.stack]})})'\\n ], { type: 'text/javascript' }))));\\n w.onmessage = function (e) {\\n var d = e.data, ed = d.$e$;\\n if (ed) {\\n var err = new Error(ed[0]);\\n err['code'] = ed[1];\\n err.stack = ed[2];\\n cb(err, null);\\n }\\n else\\n cb(null, d);\\n };\\n w.postMessage(msg, transfer);\\n return w;\\n});\\n\\n// aliases for shorter compressed code (most minifers don't do this)\\nvar u8 = Uint8Array, u16 = Uint16Array, i32 = Int32Array;\\n// fixed length extra bits\\nvar fleb = new u8([0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4, 5, 5, 5, 5, 0, /* unused */ 0, 0, /* impossible */ 0]);\\n// fixed distance extra bits\\nvar fdeb = new u8([0, 0, 0, 0, 1, 1, 2, 2, 3, 3, 4, 4, 5, 5, 6, 6, 7, 7, 8, 8, 9, 9, 10, 10, 11, 11, 12, 12, 13, 13, /* unused */ 0, 0]);\\n// code length index map\\nvar clim = new u8([16, 17, 18, 0, 8, 7, 9, 6, 10, 5, 11, 4, 12, 3, 13, 2, 14, 1, 15]);\\n// get base, reverse index map from extra bits\\nvar freb = function (eb, start) {\\n var b = new u16(31);\\n for (var i = 0; i < 31; ++i) {\\n b[i] = start += 1 << eb[i - 1];\\n }\\n // numbers here are at max 18 bits\\n var r = new i32(b[30]);\\n for (var i = 1; i < 30; ++i) {\\n for (var j = b[i]; j < b[i + 1]; ++j) {\\n r[j] = ((j - b[i]) << 5) | i;\\n }\\n }\\n return { b: b, r: r };\\n};\\nvar _a = freb(fleb, 2), fl = _a.b, revfl = _a.r;\\n// we can ignore the fact that the other numbers are wrong; they never happen anyway\\nfl[28] = 258, revfl[258] = 28;\\nvar _b = freb(fdeb, 0), fd = _b.b, revfd = _b.r;\\n// map of value to reverse (assuming 16 bits)\\nvar rev = new u16(32768);\\nfor (var i = 0; i < 32768; ++i) {\\n // reverse table algorithm from SO\\n var x = ((i & 0xAAAA) >> 1) | ((i & 0x5555) << 1);\\n x = ((x & 0xCCCC) >> 2) | ((x & 0x3333) << 2);\\n x = ((x & 0xF0F0) >> 4) | ((x & 0x0F0F) << 4);\\n rev[i] = (((x & 0xFF00) >> 8) | ((x & 0x00FF) << 8)) >> 1;\\n}\\n// create huffman tree from u8 \\\"map\\\": index -> code length for code index\\n// mb (max bits) must be at most 15\\n// TODO: optimize/split up?\\nvar hMap = (function (cd, mb, r) {\\n var s = cd.length;\\n // index\\n var i = 0;\\n // u16 \\\"map\\\": index -> # of codes with bit length = index\\n var l = new u16(mb);\\n // length of cd must be 288 (total # of codes)\\n for (; i < s; ++i) {\\n if (cd[i])\\n ++l[cd[i] - 1];\\n }\\n // u16 \\\"map\\\": index -> minimum code for bit length = index\\n var le = new u16(mb);\\n for (i = 1; i < mb; ++i) {\\n le[i] = (le[i - 1] + l[i - 1]) << 1;\\n }\\n var co;\\n if (r) {\\n // u16 \\\"map\\\": index -> number of actual bits, symbol for code\\n co = new u16(1 << mb);\\n // bits to remove for reverser\\n var rvb = 15 - mb;\\n for (i = 0; i < s; ++i) {\\n // ignore 0 lengths\\n if (cd[i]) {\\n // num encoding both symbol and bits read\\n var sv = (i << 4) | cd[i];\\n // free bits\\n var r_1 = mb - cd[i];\\n // start value\\n var v = le[cd[i] - 1]++ << r_1;\\n // m is end value\\n for (var m = v | ((1 << r_1) - 1); v <= m; ++v) {\\n // every 16 bit value starting with the code yields the same result\\n co[rev[v] >> rvb] = sv;\\n }\\n }\\n }\\n }\\n else {\\n co = new u16(s);\\n for (i = 0; i < s; ++i) {\\n if (cd[i]) {\\n co[i] = rev[le[cd[i] - 1]++] >> (15 - cd[i]);\\n }\\n }\\n }\\n return co;\\n});\\n// fixed length tree\\nvar flt = new u8(288);\\nfor (var i = 0; i < 144; ++i)\\n flt[i] = 8;\\nfor (var i = 144; i < 256; ++i)\\n flt[i] = 9;\\nfor (var i = 256; i < 280; ++i)\\n flt[i] = 7;\\nfor (var i = 280; i < 288; ++i)\\n flt[i] = 8;\\n// fixed distance tree\\nvar fdt = new u8(32);\\nfor (var i = 0; i < 32; ++i)\\n fdt[i] = 5;\\n// fixed length map\\nvar flm = /*#__PURE__*/ hMap(flt, 9, 0), flrm = /*#__PURE__*/ hMap(flt, 9, 1);\\n// fixed distance map\\nvar fdm = /*#__PURE__*/ hMap(fdt, 5, 0), fdrm = /*#__PURE__*/ hMap(fdt, 5, 1);\\n// find max of array\\nvar max = function (a) {\\n var m = a[0];\\n for (var i = 1; i < a.length; ++i) {\\n if (a[i] > m)\\n m = a[i];\\n }\\n return m;\\n};\\n// read d, starting at bit p and mask with m\\nvar bits = function (d, p, m) {\\n var o = (p / 8) | 0;\\n return ((d[o] | (d[o + 1] << 8)) >> (p & 7)) & m;\\n};\\n// read d, starting at bit p continuing for at least 16 bits\\nvar bits16 = function (d, p) {\\n var o = (p / 8) | 0;\\n return ((d[o] | (d[o + 1] << 8) | (d[o + 2] << 16)) >> (p & 7));\\n};\\n// get end of byte\\nvar shft = function (p) { return ((p + 7) / 8) | 0; };\\n// typed array slice - allows garbage collector to free original reference,\\n// while being more compatible than .slice\\nvar slc = function (v, s, e) {\\n if (s == null || s < 0)\\n s = 0;\\n if (e == null || e > v.length)\\n e = v.length;\\n // can't use .constructor in case user-supplied\\n return new u8(v.subarray(s, e));\\n};\\n/**\\n * Codes for errors generated within this library\\n */\\nexport var FlateErrorCode = {\\n UnexpectedEOF: 0,\\n InvalidBlockType: 1,\\n InvalidLengthLiteral: 2,\\n InvalidDistance: 3,\\n StreamFinished: 4,\\n NoStreamHandler: 5,\\n InvalidHeader: 6,\\n NoCallback: 7,\\n InvalidUTF8: 8,\\n ExtraFieldTooLong: 9,\\n InvalidDate: 10,\\n FilenameTooLong: 11,\\n StreamFinishing: 12,\\n InvalidZipData: 13,\\n UnknownCompressionMethod: 14\\n};\\n// error codes\\nvar ec = [\\n 'unexpected EOF',\\n 'invalid block type',\\n 'invalid length/literal',\\n 'invalid distance',\\n 'stream finished',\\n 'no stream handler',\\n ,\\n 'no callback',\\n 'invalid UTF-8 data',\\n 'extra field too long',\\n 'date not in range 1980-2099',\\n 'filename too long',\\n 'stream finishing',\\n 'invalid zip data'\\n // determined by unknown compression method\\n];\\n;\\nvar err = function (ind, msg, nt) {\\n var e = new Error(msg || ec[ind]);\\n e.code = ind;\\n if (Error.captureStackTrace)\\n Error.captureStackTrace(e, err);\\n if (!nt)\\n throw e;\\n return e;\\n};\\n// expands raw DEFLATE data\\nvar inflt = function (dat, st, buf, dict) {\\n // source length dict length\\n var sl = dat.length, dl = dict ? dict.length : 0;\\n if (!sl || st.f && !st.l)\\n return buf || new u8(0);\\n var noBuf = !buf;\\n // have to estimate size\\n var resize = noBuf || st.i != 2;\\n // no state\\n var noSt = st.i;\\n // Assumes roughly 33% compression ratio average\\n if (noBuf)\\n buf = new u8(sl * 3);\\n // ensure buffer can fit at least l elements\\n var cbuf = function (l) {\\n var bl = buf.length;\\n // need to increase size to fit\\n if (l > bl) {\\n // Double or set to necessary, whichever is greater\\n var nbuf = new u8(Math.max(bl * 2, l));\\n nbuf.set(buf);\\n buf = nbuf;\\n }\\n };\\n // last chunk bitpos bytes\\n var final = st.f || 0, pos = st.p || 0, bt = st.b || 0, lm = st.l, dm = st.d, lbt = st.m, dbt = st.n;\\n // total bits\\n var tbts = sl * 8;\\n do {\\n if (!lm) {\\n // BFINAL - this is only 1 when last chunk is next\\n final = bits(dat, pos, 1);\\n // type: 0 = no compression, 1 = fixed huffman, 2 = dynamic huffman\\n var type = bits(dat, pos + 1, 3);\\n pos += 3;\\n if (!type) {\\n // go to end of byte boundary\\n var s = shft(pos) + 4, l = dat[s - 4] | (dat[s - 3] << 8), t = s + l;\\n if (t > sl) {\\n if (noSt)\\n err(0);\\n break;\\n }\\n // ensure size\\n if (resize)\\n cbuf(bt + l);\\n // Copy over uncompressed data\\n buf.set(dat.subarray(s, t), bt);\\n // Get new bitpos, update byte count\\n st.b = bt += l, st.p = pos = t * 8, st.f = final;\\n continue;\\n }\\n else if (type == 1)\\n lm = flrm, dm = fdrm, lbt = 9, dbt = 5;\\n else if (type == 2) {\\n // literal lengths\\n var hLit = bits(dat, pos, 31) + 257, hcLen = bits(dat, pos + 10, 15) + 4;\\n var tl = hLit + bits(dat, pos + 5, 31) + 1;\\n pos += 14;\\n // length+distance tree\\n var ldt = new u8(tl);\\n // code length tree\\n var clt = new u8(19);\\n for (var i = 0; i < hcLen; ++i) {\\n // use index map to get real code\\n clt[clim[i]] = bits(dat, pos + i * 3, 7);\\n }\\n pos += hcLen * 3;\\n // code lengths bits\\n var clb = max(clt), clbmsk = (1 << clb) - 1;\\n // code lengths map\\n var clm = hMap(clt, clb, 1);\\n for (var i = 0; i < tl;) {\\n var r = clm[bits(dat, pos, clbmsk)];\\n // bits read\\n pos += r & 15;\\n // symbol\\n var s = r >> 4;\\n // code length to copy\\n if (s < 16) {\\n ldt[i++] = s;\\n }\\n else {\\n // copy count\\n var c = 0, n = 0;\\n if (s == 16)\\n n = 3 + bits(dat, pos, 3), pos += 2, c = ldt[i - 1];\\n else if (s == 17)\\n n = 3 + bits(dat, pos, 7), pos += 3;\\n else if (s == 18)\\n n = 11 + bits(dat, pos, 127), pos += 7;\\n while (n--)\\n ldt[i++] = c;\\n }\\n }\\n // length tree distance tree\\n var lt = ldt.subarray(0, hLit), dt = ldt.subarray(hLit);\\n // max length bits\\n lbt = max(lt);\\n // max dist bits\\n dbt = max(dt);\\n lm = hMap(lt, lbt, 1);\\n dm = hMap(dt, dbt, 1);\\n }\\n else\\n err(1);\\n if (pos > tbts) {\\n if (noSt)\\n err(0);\\n break;\\n }\\n }\\n // Make sure the buffer can hold this + the largest possible addition\\n // Maximum chunk size (practically, theoretically infinite) is 2^17\\n if (resize)\\n cbuf(bt + 131072);\\n var lms = (1 << lbt) - 1, dms = (1 << dbt) - 1;\\n var lpos = pos;\\n for (;; lpos = pos) {\\n // bits read, code\\n var c = lm[bits16(dat, pos) & lms], sym = c >> 4;\\n pos += c & 15;\\n if (pos > tbts) {\\n if (noSt)\\n err(0);\\n break;\\n }\\n if (!c)\\n err(2);\\n if (sym < 256)\\n buf[bt++] = sym;\\n else if (sym == 256) {\\n lpos = pos, lm = null;\\n break;\\n }\\n else {\\n var add = sym - 254;\\n // no extra bits needed if less\\n if (sym > 264) {\\n // index\\n var i = sym - 257, b = fleb[i];\\n add = bits(dat, pos, (1 << b) - 1) + fl[i];\\n pos += b;\\n }\\n // dist\\n var d = dm[bits16(dat, pos) & dms], dsym = d >> 4;\\n if (!d)\\n err(3);\\n pos += d & 15;\\n var dt = fd[dsym];\\n if (dsym > 3) {\\n var b = fdeb[dsym];\\n dt += bits16(dat, pos) & (1 << b) - 1, pos += b;\\n }\\n if (pos > tbts) {\\n if (noSt)\\n err(0);\\n break;\\n }\\n if (resize)\\n cbuf(bt + 131072);\\n var end = bt + add;\\n if (bt < dt) {\\n var shift = dl - dt, dend = Math.min(dt, end);\\n if (shift + bt < 0)\\n err(3);\\n for (; bt < dend; ++bt)\\n buf[bt] = dict[shift + bt];\\n }\\n for (; bt < end; ++bt)\\n buf[bt] = buf[bt - dt];\\n }\\n }\\n st.l = lm, st.p = lpos, st.b = bt, st.f = final;\\n if (lm)\\n final = 1, st.m = lbt, st.d = dm, st.n = dbt;\\n } while (!final);\\n // don't reallocate for streams or user buffers\\n return bt != buf.length && noBuf ? slc(buf, 0, bt) : buf.subarray(0, bt);\\n};\\n// starting at p, write the minimum number of bits that can hold v to d\\nvar wbits = function (d, p, v) {\\n v <<= p & 7;\\n var o = (p / 8) | 0;\\n d[o] |= v;\\n d[o + 1] |= v >> 8;\\n};\\n// starting at p, write the minimum number of bits (>8) that can hold v to d\\nvar wbits16 = function (d, p, v) {\\n v <<= p & 7;\\n var o = (p / 8) | 0;\\n d[o] |= v;\\n d[o + 1] |= v >> 8;\\n d[o + 2] |= v >> 16;\\n};\\n// creates code lengths from a frequency table\\nvar hTree = function (d, mb) {\\n // Need extra info to make a tree\\n var t = [];\\n for (var i = 0; i < d.length; ++i) {\\n if (d[i])\\n t.push({ s: i, f: d[i] });\\n }\\n var s = t.length;\\n var t2 = t.slice();\\n if (!s)\\n return { t: et, l: 0 };\\n if (s == 1) {\\n var v = new u8(t[0].s + 1);\\n v[t[0].s] = 1;\\n return { t: v, l: 1 };\\n }\\n t.sort(function (a, b) { return a.f - b.f; });\\n // after i2 reaches last ind, will be stopped\\n // freq must be greater than largest possible number of symbols\\n t.push({ s: -1, f: 25001 });\\n var l = t[0], r = t[1], i0 = 0, i1 = 1, i2 = 2;\\n t[0] = { s: -1, f: l.f + r.f, l: l, r: r };\\n // efficient algorithm from UZIP.js\\n // i0 is lookbehind, i2 is lookahead - after processing two low-freq\\n // symbols that combined have high freq, will start processing i2 (high-freq,\\n // non-composite) symbols instead\\n // see https://reddit.com/r/photopea/comments/ikekht/uzipjs_questions/\\n while (i1 != s - 1) {\\n l = t[t[i0].f < t[i2].f ? i0++ : i2++];\\n r = t[i0 != i1 && t[i0].f < t[i2].f ? i0++ : i2++];\\n t[i1++] = { s: -1, f: l.f + r.f, l: l, r: r };\\n }\\n var maxSym = t2[0].s;\\n for (var i = 1; i < s; ++i) {\\n if (t2[i].s > maxSym)\\n maxSym = t2[i].s;\\n }\\n // code lengths\\n var tr = new u16(maxSym + 1);\\n // max bits in tree\\n var mbt = ln(t[i1 - 1], tr, 0);\\n if (mbt > mb) {\\n // more algorithms from UZIP.js\\n // TODO: find out how this code works (debt)\\n // ind debt\\n var i = 0, dt = 0;\\n // left cost\\n var lft = mbt - mb, cst = 1 << lft;\\n t2.sort(function (a, b) { return tr[b.s] - tr[a.s] || a.f - b.f; });\\n for (; i < s; ++i) {\\n var i2_1 = t2[i].s;\\n if (tr[i2_1] > mb) {\\n dt += cst - (1 << (mbt - tr[i2_1]));\\n tr[i2_1] = mb;\\n }\\n else\\n break;\\n }\\n dt >>= lft;\\n while (dt > 0) {\\n var i2_2 = t2[i].s;\\n if (tr[i2_2] < mb)\\n dt -= 1 << (mb - tr[i2_2]++ - 1);\\n else\\n ++i;\\n }\\n for (; i >= 0 && dt; --i) {\\n var i2_3 = t2[i].s;\\n if (tr[i2_3] == mb) {\\n --tr[i2_3];\\n ++dt;\\n }\\n }\\n mbt = mb;\\n }\\n return { t: new u8(tr), l: mbt };\\n};\\n// get the max length and assign length codes\\nvar ln = function (n, l, d) {\\n return n.s == -1\\n ? Math.max(ln(n.l, l, d + 1), ln(n.r, l, d + 1))\\n : (l[n.s] = d);\\n};\\n// length codes generation\\nvar lc = function (c) {\\n var s = c.length;\\n // Note that the semicolon was intentional\\n while (s && !c[--s])\\n ;\\n var cl = new u16(++s);\\n // ind num streak\\n var cli = 0, cln = c[0], cls = 1;\\n var w = function (v) { cl[cli++] = v; };\\n for (var i = 1; i <= s; ++i) {\\n if (c[i] == cln && i != s)\\n ++cls;\\n else {\\n if (!cln && cls > 2) {\\n for (; cls > 138; cls -= 138)\\n w(32754);\\n if (cls > 2) {\\n w(cls > 10 ? ((cls - 11) << 5) | 28690 : ((cls - 3) << 5) | 12305);\\n cls = 0;\\n }\\n }\\n else if (cls > 3) {\\n w(cln), --cls;\\n for (; cls > 6; cls -= 6)\\n w(8304);\\n if (cls > 2)\\n w(((cls - 3) << 5) | 8208), cls = 0;\\n }\\n while (cls--)\\n w(cln);\\n cls = 1;\\n cln = c[i];\\n }\\n }\\n return { c: cl.subarray(0, cli), n: s };\\n};\\n// calculate the length of output from tree, code lengths\\nvar clen = function (cf, cl) {\\n var l = 0;\\n for (var i = 0; i < cl.length; ++i)\\n l += cf[i] * cl[i];\\n return l;\\n};\\n// writes a fixed block\\n// returns the new bit pos\\nvar wfblk = function (out, pos, dat) {\\n // no need to write 00 as type: TypedArray defaults to 0\\n var s = dat.length;\\n var o = shft(pos + 2);\\n out[o] = s & 255;\\n out[o + 1] = s >> 8;\\n out[o + 2] = out[o] ^ 255;\\n out[o + 3] = out[o + 1] ^ 255;\\n for (var i = 0; i < s; ++i)\\n out[o + i + 4] = dat[i];\\n return (o + 4 + s) * 8;\\n};\\n// writes a block\\nvar wblk = function (dat, out, final, syms, lf, df, eb, li, bs, bl, p) {\\n wbits(out, p++, final);\\n ++lf[256];\\n var _a = hTree(lf, 15), dlt = _a.t, mlb = _a.l;\\n var _b = hTree(df, 15), ddt = _b.t, mdb = _b.l;\\n var _c = lc(dlt), lclt = _c.c, nlc = _c.n;\\n var _d = lc(ddt), lcdt = _d.c, ndc = _d.n;\\n var lcfreq = new u16(19);\\n for (var i = 0; i < lclt.length; ++i)\\n ++lcfreq[lclt[i] & 31];\\n for (var i = 0; i < lcdt.length; ++i)\\n ++lcfreq[lcdt[i] & 31];\\n var _e = hTree(lcfreq, 7), lct = _e.t, mlcb = _e.l;\\n var nlcc = 19;\\n for (; nlcc > 4 && !lct[clim[nlcc - 1]]; --nlcc)\\n ;\\n var flen = (bl + 5) << 3;\\n var ftlen = clen(lf, flt) + clen(df, fdt) + eb;\\n var dtlen = clen(lf, dlt) + clen(df, ddt) + eb + 14 + 3 * nlcc + clen(lcfreq, lct) + 2 * lcfreq[16] + 3 * lcfreq[17] + 7 * lcfreq[18];\\n if (bs >= 0 && flen <= ftlen && flen <= dtlen)\\n return wfblk(out, p, dat.subarray(bs, bs + bl));\\n var lm, ll, dm, dl;\\n wbits(out, p, 1 + (dtlen < ftlen)), p += 2;\\n if (dtlen < ftlen) {\\n lm = hMap(dlt, mlb, 0), ll = dlt, dm = hMap(ddt, mdb, 0), dl = ddt;\\n var llm = hMap(lct, mlcb, 0);\\n wbits(out, p, nlc - 257);\\n wbits(out, p + 5, ndc - 1);\\n wbits(out, p + 10, nlcc - 4);\\n p += 14;\\n for (var i = 0; i < nlcc; ++i)\\n wbits(out, p + 3 * i, lct[clim[i]]);\\n p += 3 * nlcc;\\n var lcts = [lclt, lcdt];\\n for (var it = 0; it < 2; ++it) {\\n var clct = lcts[it];\\n for (var i = 0; i < clct.length; ++i) {\\n var len = clct[i] & 31;\\n wbits(out, p, llm[len]), p += lct[len];\\n if (len > 15)\\n wbits(out, p, (clct[i] >> 5) & 127), p += clct[i] >> 12;\\n }\\n }\\n }\\n else {\\n lm = flm, ll = flt, dm = fdm, dl = fdt;\\n }\\n for (var i = 0; i < li; ++i) {\\n var sym = syms[i];\\n if (sym > 255) {\\n var len = (sym >> 18) & 31;\\n wbits16(out, p, lm[len + 257]), p += ll[len + 257];\\n if (len > 7)\\n wbits(out, p, (sym >> 23) & 31), p += fleb[len];\\n var dst = sym & 31;\\n wbits16(out, p, dm[dst]), p += dl[dst];\\n if (dst > 3)\\n wbits16(out, p, (sym >> 5) & 8191), p += fdeb[dst];\\n }\\n else {\\n wbits16(out, p, lm[sym]), p += ll[sym];\\n }\\n }\\n wbits16(out, p, lm[256]);\\n return p + ll[256];\\n};\\n// deflate options (nice << 13) | chain\\nvar deo = /*#__PURE__*/ new i32([65540, 131080, 131088, 131104, 262176, 1048704, 1048832, 2114560, 2117632]);\\n// empty\\nvar et = /*#__PURE__*/ new u8(0);\\n// compresses data into a raw DEFLATE buffer\\nvar dflt = function (dat, lvl, plvl, pre, post, st) {\\n var s = st.z || dat.length;\\n var o = new u8(pre + s + 5 * (1 + Math.ceil(s / 7000)) + post);\\n // writing to this writes to the output buffer\\n var w = o.subarray(pre, o.length - post);\\n var lst = st.l;\\n var pos = (st.r || 0) & 7;\\n if (lvl) {\\n if (pos)\\n w[0] = st.r >> 3;\\n var opt = deo[lvl - 1];\\n var n = opt >> 13, c = opt & 8191;\\n var msk_1 = (1 << plvl) - 1;\\n // prev 2-byte val map curr 2-byte val map\\n var prev = st.p || new u16(32768), head = st.h || new u16(msk_1 + 1);\\n var bs1_1 = Math.ceil(plvl / 3), bs2_1 = 2 * bs1_1;\\n var hsh = function (i) { return (dat[i] ^ (dat[i + 1] << bs1_1) ^ (dat[i + 2] << bs2_1)) & msk_1; };\\n // 24576 is an arbitrary number of maximum symbols per block\\n // 424 buffer for last block\\n var syms = new i32(25000);\\n // length/literal freq distance freq\\n var lf = new u16(288), df = new u16(32);\\n // l/lcnt exbits index l/lind waitdx blkpos\\n var lc_1 = 0, eb = 0, i = st.i || 0, li = 0, wi = st.w || 0, bs = 0;\\n for (; i + 2 < s; ++i) {\\n // hash value\\n var hv = hsh(i);\\n // index mod 32768 previous index mod\\n var imod = i & 32767, pimod = head[hv];\\n prev[imod] = pimod;\\n head[hv] = imod;\\n // We always should modify head and prev, but only add symbols if\\n // this data is not yet processed (\\\"wait\\\" for wait index)\\n if (wi <= i) {\\n // bytes remaining\\n var rem = s - i;\\n if ((lc_1 > 7000 || li > 24576) && (rem > 423 || !lst)) {\\n pos = wblk(dat, w, 0, syms, lf, df, eb, li, bs, i - bs, pos);\\n li = lc_1 = eb = 0, bs = i;\\n for (var j = 0; j < 286; ++j)\\n lf[j] = 0;\\n for (var j = 0; j < 30; ++j)\\n df[j] = 0;\\n }\\n // len dist chain\\n var l = 2, d = 0, ch_1 = c, dif = imod - pimod & 32767;\\n if (rem > 2 && hv == hsh(i - dif)) {\\n var maxn = Math.min(n, rem) - 1;\\n var maxd = Math.min(32767, i);\\n // max possible length\\n // not capped at dif because decompressors implement \\\"rolling\\\" index population\\n var ml = Math.min(258, rem);\\n while (dif <= maxd && --ch_1 && imod != pimod) {\\n if (dat[i + l] == dat[i + l - dif]) {\\n var nl = 0;\\n for (; nl < ml && dat[i + nl] == dat[i + nl - dif]; ++nl)\\n ;\\n if (nl > l) {\\n l = nl, d = dif;\\n // break out early when we reach \\\"nice\\\" (we are satisfied enough)\\n if (nl > maxn)\\n break;\\n // now, find the rarest 2-byte sequence within this\\n // length of literals and search for that instead.\\n // Much faster than just using the start\\n var mmd = Math.min(dif, nl - 2);\\n var md = 0;\\n for (var j = 0; j < mmd; ++j) {\\n var ti = i - dif + j & 32767;\\n var pti = prev[ti];\\n var cd = ti - pti & 32767;\\n if (cd > md)\\n md = cd, pimod = ti;\\n }\\n }\\n }\\n // check the previous match\\n imod = pimod, pimod = prev[imod];\\n dif += imod - pimod & 32767;\\n }\\n }\\n // d will be nonzero only when a match was found\\n if (d) {\\n // store both dist and len data in one int32\\n // Make sure this is recognized as a len/dist with 28th bit (2^28)\\n syms[li++] = 268435456 | (revfl[l] << 18) | revfd[d];\\n var lin = revfl[l] & 31, din = revfd[d] & 31;\\n eb += fleb[lin] + fdeb[din];\\n ++lf[257 + lin];\\n ++df[din];\\n wi = i + l;\\n ++lc_1;\\n }\\n else {\\n syms[li++] = dat[i];\\n ++lf[dat[i]];\\n }\\n }\\n }\\n for (i = Math.max(i, wi); i < s; ++i) {\\n syms[li++] = dat[i];\\n ++lf[dat[i]];\\n }\\n pos = wblk(dat, w, lst, syms, lf, df, eb, li, bs, i - bs, pos);\\n if (!lst) {\\n st.r = (pos & 7) | w[(pos / 8) | 0] << 3;\\n // shft(pos) now 1 less if pos & 7 != 0\\n pos -= 7;\\n st.h = head, st.p = prev, st.i = i, st.w = wi;\\n }\\n }\\n else {\\n for (var i = st.w || 0; i < s + lst; i += 65535) {\\n // end\\n var e = i + 65535;\\n if (e >= s) {\\n // write final block\\n w[(pos / 8) | 0] = lst;\\n e = s;\\n }\\n pos = wfblk(w, pos + 1, dat.subarray(i, e));\\n }\\n st.i = s;\\n }\\n return slc(o, 0, pre + shft(pos) + post);\\n};\\n// CRC32 table\\nvar crct = /*#__PURE__*/ (function () {\\n var t = new Int32Array(256);\\n for (var i = 0; i < 256; ++i) {\\n var c = i, k = 9;\\n while (--k)\\n c = ((c & 1) && -306674912) ^ (c >>> 1);\\n t[i] = c;\\n }\\n return t;\\n})();\\n// CRC32\\nvar crc = function () {\\n var c = -1;\\n return {\\n p: function (d) {\\n // closures have awful performance\\n var cr = c;\\n for (var i = 0; i < d.length; ++i)\\n cr = crct[(cr & 255) ^ d[i]] ^ (cr >>> 8);\\n c = cr;\\n },\\n d: function () { return ~c; }\\n };\\n};\\n// Adler32\\nvar adler = function () {\\n var a = 1, b = 0;\\n return {\\n p: function (d) {\\n // closures have awful performance\\n var n = a, m = b;\\n var l = d.length | 0;\\n for (var i = 0; i != l;) {\\n var e = Math.min(i + 2655, l);\\n for (; i < e; ++i)\\n m += n += d[i];\\n n = (n & 65535) + 15 * (n >> 16), m = (m & 65535) + 15 * (m >> 16);\\n }\\n a = n, b = m;\\n },\\n d: function () {\\n a %= 65521, b %= 65521;\\n return (a & 255) << 24 | (a & 0xFF00) << 8 | (b & 255) << 8 | (b >> 8);\\n }\\n };\\n};\\n;\\n// deflate with opts\\nvar dopt = function (dat, opt, pre, post, st) {\\n if (!st) {\\n st = { l: 1 };\\n if (opt.dictionary) {\\n var dict = opt.dictionary.subarray(-32768);\\n var newDat = new u8(dict.length + dat.length);\\n newDat.set(dict);\\n newDat.set(dat, dict.length);\\n dat = newDat;\\n st.w = dict.length;\\n }\\n }\\n return dflt(dat, opt.level == null ? 6 : opt.level, opt.mem == null ? (st.l ? Math.ceil(Math.max(8, Math.min(13, Math.log(dat.length))) * 1.5) : 20) : (12 + opt.mem), pre, post, st);\\n};\\n// Walmart object spread\\nvar mrg = function (a, b) {\\n var o = {};\\n for (var k in a)\\n o[k] = a[k];\\n for (var k in b)\\n o[k] = b[k];\\n return o;\\n};\\n// worker clone\\n// This is possibly the craziest part of the entire codebase, despite how simple it may seem.\\n// The only parameter to this function is a closure that returns an array of variables outside of the function scope.\\n// We're going to try to figure out the variable names used in the closure as strings because that is crucial for workerization.\\n// We will return an object mapping of true variable name to value (basically, the current scope as a JS object).\\n// The reason we can't just use the original variable names is minifiers mangling the toplevel scope.\\n// This took me three weeks to figure out how to do.\\nvar wcln = function (fn, fnStr, td) {\\n var dt = fn();\\n var st = fn.toString();\\n var ks = st.slice(st.indexOf('[') + 1, st.lastIndexOf(']')).replace(/\\\\s+/g, '').split(',');\\n for (var i = 0; i < dt.length; ++i) {\\n var v = dt[i], k = ks[i];\\n if (typeof v == 'function') {\\n fnStr += ';' + k + '=';\\n var st_1 = v.toString();\\n if (v.prototype) {\\n // for global objects\\n if (st_1.indexOf('[native code]') != -1) {\\n var spInd = st_1.indexOf(' ', 8) + 1;\\n fnStr += st_1.slice(spInd, st_1.indexOf('(', spInd));\\n }\\n else {\\n fnStr += st_1;\\n for (var t in v.prototype)\\n fnStr += ';' + k + '.prototype.' + t + '=' + v.prototype[t].toString();\\n }\\n }\\n else\\n fnStr += st_1;\\n }\\n else\\n td[k] = v;\\n }\\n return fnStr;\\n};\\nvar ch = [];\\n// clone bufs\\nvar cbfs = function (v) {\\n var tl = [];\\n for (var k in v) {\\n if (v[k].buffer) {\\n tl.push((v[k] = new v[k].constructor(v[k])).buffer);\\n }\\n }\\n return tl;\\n};\\n// use a worker to execute code\\nvar wrkr = function (fns, init, id, cb) {\\n if (!ch[id]) {\\n var fnStr = '', td_1 = {}, m = fns.length - 1;\\n for (var i = 0; i < m; ++i)\\n fnStr = wcln(fns[i], fnStr, td_1);\\n ch[id] = { c: wcln(fns[m], fnStr, td_1), e: td_1 };\\n }\\n var td = mrg({}, ch[id].e);\\n return wk(ch[id].c + ';onmessage=function(e){for(var k in e.data)self[k]=e.data[k];onmessage=' + init.toString() + '}', id, td, cbfs(td), cb);\\n};\\n// base async inflate fn\\nvar bInflt = function () { return [u8, u16, i32, fleb, fdeb, clim, fl, fd, flrm, fdrm, rev, ec, hMap, max, bits, bits16, shft, slc, err, inflt, inflateSync, pbf, gopt]; };\\nvar bDflt = function () { return [u8, u16, i32, fleb, fdeb, clim, revfl, revfd, flm, flt, fdm, fdt, rev, deo, et, hMap, wbits, wbits16, hTree, ln, lc, clen, wfblk, wblk, shft, slc, dflt, dopt, deflateSync, pbf]; };\\n// gzip extra\\nvar gze = function () { return [gzh, gzhl, wbytes, crc, crct]; };\\n// gunzip extra\\nvar guze = function () { return [gzs, gzl]; };\\n// zlib extra\\nvar zle = function () { return [zlh, wbytes, adler]; };\\n// unzlib extra\\nvar zule = function () { return [zls]; };\\n// post buf\\nvar pbf = function (msg) { return postMessage(msg, [msg.buffer]); };\\n// get opts\\nvar gopt = function (o) { return o && {\\n out: o.size && new u8(o.size),\\n dictionary: o.dictionary\\n}; };\\n// async helper\\nvar cbify = function (dat, opts, fns, init, id, cb) {\\n var w = wrkr(fns, init, id, function (err, dat) {\\n w.terminate();\\n cb(err, dat);\\n });\\n w.postMessage([dat, opts], opts.consume ? [dat.buffer] : []);\\n return function () { w.terminate(); };\\n};\\n// auto stream\\nvar astrm = function (strm) {\\n strm.ondata = function (dat, final) { return postMessage([dat, final], [dat.buffer]); };\\n return function (ev) {\\n if (ev.data.length) {\\n strm.push(ev.data[0], ev.data[1]);\\n postMessage([ev.data[0].length]);\\n }\\n else\\n strm.flush();\\n };\\n};\\n// async stream attach\\nvar astrmify = function (fns, strm, opts, init, id, flush, ext) {\\n var t;\\n var w = wrkr(fns, init, id, function (err, dat) {\\n if (err)\\n w.terminate(), strm.ondata.call(strm, err);\\n else if (!Array.isArray(dat))\\n ext(dat);\\n else if (dat.length == 1) {\\n strm.queuedSize -= dat[0];\\n if (strm.ondrain)\\n strm.ondrain(dat[0]);\\n }\\n else {\\n if (dat[1])\\n w.terminate();\\n strm.ondata.call(strm, err, dat[0], dat[1]);\\n }\\n });\\n w.postMessage(opts);\\n strm.queuedSize = 0;\\n strm.push = function (d, f) {\\n if (!strm.ondata)\\n err(5);\\n if (t)\\n strm.ondata(err(4, 0, 1), null, !!f);\\n strm.queuedSize += d.length;\\n w.postMessage([d, t = f], [d.buffer]);\\n };\\n strm.terminate = function () { w.terminate(); };\\n if (flush) {\\n strm.flush = function () { w.postMessage([]); };\\n }\\n};\\n// read 2 bytes\\nvar b2 = function (d, b) { return d[b] | (d[b + 1] << 8); };\\n// read 4 bytes\\nvar b4 = function (d, b) { return (d[b] | (d[b + 1] << 8) | (d[b + 2] << 16) | (d[b + 3] << 24)) >>> 0; };\\nvar b8 = function (d, b) { return b4(d, b) + (b4(d, b + 4) * 4294967296); };\\n// write bytes\\nvar wbytes = function (d, b, v) {\\n for (; v; ++b)\\n d[b] = v, v >>>= 8;\\n};\\n// gzip header\\nvar gzh = function (c, o) {\\n var fn = o.filename;\\n c[0] = 31, c[1] = 139, c[2] = 8, c[8] = o.level < 2 ? 4 : o.level == 9 ? 2 : 0, c[9] = 3; // assume Unix\\n if (o.mtime != 0)\\n wbytes(c, 4, Math.floor(new Date(o.mtime || Date.now()) / 1000));\\n if (fn) {\\n c[3] = 8;\\n for (var i = 0; i <= fn.length; ++i)\\n c[i + 10] = fn.charCodeAt(i);\\n }\\n};\\n// gzip footer: -8 to -4 = CRC, -4 to -0 is length\\n// gzip start\\nvar gzs = function (d) {\\n if (d[0] != 31 || d[1] != 139 || d[2] != 8)\\n err(6, 'invalid gzip data');\\n var flg = d[3];\\n var st = 10;\\n if (flg & 4)\\n st += (d[10] | d[11] << 8) + 2;\\n for (var zs = (flg >> 3 & 1) + (flg >> 4 & 1); zs > 0; zs -= !d[st++])\\n ;\\n return st + (flg & 2);\\n};\\n// gzip length\\nvar gzl = function (d) {\\n var l = d.length;\\n return (d[l - 4] | d[l - 3] << 8 | d[l - 2] << 16 | d[l - 1] << 24) >>> 0;\\n};\\n// gzip header length\\nvar gzhl = function (o) { return 10 + (o.filename ? o.filename.length + 1 : 0); };\\n// zlib header\\nvar zlh = function (c, o) {\\n var lv = o.level, fl = lv == 0 ? 0 : lv < 6 ? 1 : lv == 9 ? 3 : 2;\\n c[0] = 120, c[1] = (fl << 6) | (o.dictionary && 32);\\n c[1] |= 31 - ((c[0] << 8) | c[1]) % 31;\\n if (o.dictionary) {\\n var h = adler();\\n h.p(o.dictionary);\\n wbytes(c, 2, h.d());\\n }\\n};\\n// zlib start\\nvar zls = function (d, dict) {\\n if ((d[0] & 15) != 8 || (d[0] >> 4) > 7 || ((d[0] << 8 | d[1]) % 31))\\n err(6, 'invalid zlib data');\\n if ((d[1] >> 5 & 1) == +!dict)\\n err(6, 'invalid zlib data: ' + (d[1] & 32 ? 'need' : 'unexpected') + ' dictionary');\\n return (d[1] >> 3 & 4) + 2;\\n};\\nfunction StrmOpt(opts, cb) {\\n if (typeof opts == 'function')\\n cb = opts, opts = {};\\n this.ondata = cb;\\n return opts;\\n}\\n/**\\n * Streaming DEFLATE compression\\n */\\nvar Deflate = /*#__PURE__*/ (function () {\\n function Deflate(opts, cb) {\\n if (typeof opts == 'function')\\n cb = opts, opts = {};\\n this.ondata = cb;\\n this.o = opts || {};\\n this.s = { l: 0, i: 32768, w: 32768, z: 32768 };\\n // Buffer length must always be 0 mod 32768 for index calculations to be correct when modifying head and prev\\n // 98304 = 32768 (lookback) + 65536 (common chunk size)\\n this.b = new u8(98304);\\n if (this.o.dictionary) {\\n var dict = this.o.dictionary.subarray(-32768);\\n this.b.set(dict, 32768 - dict.length);\\n this.s.i = 32768 - dict.length;\\n }\\n }\\n Deflate.prototype.p = function (c, f) {\\n this.ondata(dopt(c, this.o, 0, 0, this.s), f);\\n };\\n /**\\n * Pushes a chunk to be deflated\\n * @param chunk The chunk to push\\n * @param final Whether this is the last chunk\\n */\\n Deflate.prototype.push = function (chunk, final) {\\n if (!this.ondata)\\n err(5);\\n if (this.s.l)\\n err(4);\\n var endLen = chunk.length + this.s.z;\\n if (endLen > this.b.length) {\\n if (endLen > 2 * this.b.length - 32768) {\\n var newBuf = new u8(endLen & -32768);\\n newBuf.set(this.b.subarray(0, this.s.z));\\n this.b = newBuf;\\n }\\n var split = this.b.length - this.s.z;\\n this.b.set(chunk.subarray(0, split), this.s.z);\\n this.s.z = this.b.length;\\n this.p(this.b, false);\\n this.b.set(this.b.subarray(-32768));\\n this.b.set(chunk.subarray(split), 32768);\\n this.s.z = chunk.length - split + 32768;\\n this.s.i = 32766, this.s.w = 32768;\\n }\\n else {\\n this.b.set(chunk, this.s.z);\\n this.s.z += chunk.length;\\n }\\n this.s.l = final & 1;\\n if (this.s.z > this.s.w + 8191 || final) {\\n this.p(this.b, final || false);\\n this.s.w = this.s.i, this.s.i -= 2;\\n }\\n };\\n /**\\n * Flushes buffered uncompressed data. Useful to immediately retrieve the\\n * deflated output for small inputs.\\n */\\n Deflate.prototype.flush = function () {\\n if (!this.ondata)\\n err(5);\\n if (this.s.l)\\n err(4);\\n this.p(this.b, false);\\n this.s.w = this.s.i, this.s.i -= 2;\\n };\\n return Deflate;\\n}());\\nexport { Deflate };\\n/**\\n * Asynchronous streaming DEFLATE compression\\n */\\nvar AsyncDeflate = /*#__PURE__*/ (function () {\\n function AsyncDeflate(opts, cb) {\\n astrmify([\\n bDflt,\\n function () { return [astrm, Deflate]; }\\n ], this, StrmOpt.call(this, opts, cb), function (ev) {\\n var strm = new Deflate(ev.data);\\n onmessage = astrm(strm);\\n }, 6, 1);\\n }\\n return AsyncDeflate;\\n}());\\nexport { AsyncDeflate };\\nexport function deflate(data, opts, cb) {\\n if (!cb)\\n cb = opts, opts = {};\\n if (typeof cb != 'function')\\n err(7);\\n return cbify(data, opts, [\\n bDflt,\\n ], function (ev) { return pbf(deflateSync(ev.data[0], ev.data[1])); }, 0, cb);\\n}\\n/**\\n * Compresses data with DEFLATE without any wrapper\\n * @param data The data to compress\\n * @param opts The compression options\\n * @returns The deflated version of the data\\n */\\nexport function deflateSync(data, opts) {\\n return dopt(data, opts || {}, 0, 0);\\n}\\n/**\\n * Streaming DEFLATE decompression\\n */\\nvar Inflate = /*#__PURE__*/ (function () {\\n function Inflate(opts, cb) {\\n // no StrmOpt here to avoid adding to workerizer\\n if (typeof opts == 'function')\\n cb = opts, opts = {};\\n this.ondata = cb;\\n var dict = opts && opts.dictionary && opts.dictionary.subarray(-32768);\\n this.s = { i: 0, b: dict ? dict.length : 0 };\\n this.o = new u8(32768);\\n this.p = new u8(0);\\n if (dict)\\n this.o.set(dict);\\n }\\n Inflate.prototype.e = function (c) {\\n if (!this.ondata)\\n err(5);\\n if (this.d)\\n err(4);\\n if (!this.p.length)\\n this.p = c;\\n else if (c.length) {\\n var n = new u8(this.p.length + c.length);\\n n.set(this.p), n.set(c, this.p.length), this.p = n;\\n }\\n };\\n Inflate.prototype.c = function (final) {\\n this.s.i = +(this.d = final || false);\\n var bts = this.s.b;\\n var dt = inflt(this.p, this.s, this.o);\\n this.ondata(slc(dt, bts, this.s.b), this.d);\\n this.o = slc(dt, this.s.b - 32768), this.s.b = this.o.length;\\n this.p = slc(this.p, (this.s.p / 8) | 0), this.s.p &= 7;\\n };\\n /**\\n * Pushes a chunk to be inflated\\n * @param chunk The chunk to push\\n * @param final Whether this is the final chunk\\n */\\n Inflate.prototype.push = function (chunk, final) {\\n this.e(chunk), this.c(final);\\n };\\n return Inflate;\\n}());\\nexport { Inflate };\\n/**\\n * Asynchronous streaming DEFLATE decompression\\n */\\nvar AsyncInflate = /*#__PURE__*/ (function () {\\n function AsyncInflate(opts, cb) {\\n astrmify([\\n bInflt,\\n function () { return [astrm, Inflate]; }\\n ], this, StrmOpt.call(this, opts, cb), function (ev) {\\n var strm = new Inflate(ev.data);\\n onmessage = astrm(strm);\\n }, 7, 0);\\n }\\n return AsyncInflate;\\n}());\\nexport { AsyncInflate };\\nexport function inflate(data, opts, cb) {\\n if (!cb)\\n cb = opts, opts = {};\\n if (typeof cb != 'function')\\n err(7);\\n return cbify(data, opts, [\\n bInflt\\n ], function (ev) { return pbf(inflateSync(ev.data[0], gopt(ev.data[1]))); }, 1, cb);\\n}\\n/**\\n * Expands DEFLATE data with no wrapper\\n * @param data The data to decompress\\n * @param opts The decompression options\\n * @returns The decompressed version of the data\\n */\\nexport function inflateSync(data, opts) {\\n return inflt(data, { i: 2 }, opts && opts.out, opts && opts.dictionary);\\n}\\n// before you yell at me for not just using extends, my reason is that TS inheritance is hard to workerize.\\n/**\\n * Streaming GZIP compression\\n */\\nvar Gzip = /*#__PURE__*/ (function () {\\n function Gzip(opts, cb) {\\n this.c = crc();\\n this.l = 0;\\n this.v = 1;\\n Deflate.call(this, opts, cb);\\n }\\n /**\\n * Pushes a chunk to be GZIPped\\n * @param chunk The chunk to push\\n * @param final Whether this is the last chunk\\n */\\n Gzip.prototype.push = function (chunk, final) {\\n this.c.p(chunk);\\n this.l += chunk.length;\\n Deflate.prototype.push.call(this, chunk, final);\\n };\\n Gzip.prototype.p = function (c, f) {\\n var raw = dopt(c, this.o, this.v && gzhl(this.o), f && 8, this.s);\\n if (this.v)\\n gzh(raw, this.o), this.v = 0;\\n if (f)\\n wbytes(raw, raw.length - 8, this.c.d()), wbytes(raw, raw.length - 4, this.l);\\n this.ondata(raw, f);\\n };\\n /**\\n * Flushes buffered uncompressed data. Useful to immediately retrieve the\\n * GZIPped output for small inputs.\\n */\\n Gzip.prototype.flush = function () {\\n Deflate.prototype.flush.call(this);\\n };\\n return Gzip;\\n}());\\nexport { Gzip };\\n/**\\n * Asynchronous streaming GZIP compression\\n */\\nvar AsyncGzip = /*#__PURE__*/ (function () {\\n function AsyncGzip(opts, cb) {\\n astrmify([\\n bDflt,\\n gze,\\n function () { return [astrm, Deflate, Gzip]; }\\n ], this, StrmOpt.call(this, opts, cb), function (ev) {\\n var strm = new Gzip(ev.data);\\n onmessage = astrm(strm);\\n }, 8, 1);\\n }\\n return AsyncGzip;\\n}());\\nexport { AsyncGzip };\\nexport function gzip(data, opts, cb) {\\n if (!cb)\\n cb = opts, opts = {};\\n if (typeof cb != 'function')\\n err(7);\\n return cbify(data, opts, [\\n bDflt,\\n gze,\\n function () { return [gzipSync]; }\\n ], function (ev) { return pbf(gzipSync(ev.data[0], ev.data[1])); }, 2, cb);\\n}\\n/**\\n * Compresses data with GZIP\\n * @param data The data to compress\\n * @param opts The compression options\\n * @returns The gzipped version of the data\\n */\\nexport function gzipSync(data, opts) {\\n if (!opts)\\n opts = {};\\n var c = crc(), l = data.length;\\n c.p(data);\\n var d = dopt(data, opts, gzhl(opts), 8), s = d.length;\\n return gzh(d, opts), wbytes(d, s - 8, c.d()), wbytes(d, s - 4, l), d;\\n}\\n/**\\n * Streaming single or multi-member GZIP decompression\\n */\\nvar Gunzip = /*#__PURE__*/ (function () {\\n function Gunzip(opts, cb) {\\n this.v = 1;\\n this.r = 0;\\n Inflate.call(this, opts, cb);\\n }\\n /**\\n * Pushes a chunk to be GUNZIPped\\n * @param chunk The chunk to push\\n * @param final Whether this is the last chunk\\n */\\n Gunzip.prototype.push = function (chunk, final) {\\n Inflate.prototype.e.call(this, chunk);\\n this.r += chunk.length;\\n if (this.v) {\\n var p = this.p.subarray(this.v - 1);\\n var s = p.length > 3 ? gzs(p) : 4;\\n if (s > p.length) {\\n if (!final)\\n return;\\n }\\n else if (this.v > 1 && this.onmember) {\\n this.onmember(this.r - p.length);\\n }\\n this.p = p.subarray(s), this.v = 0;\\n }\\n // necessary to prevent TS from using the closure value\\n // This allows for workerization to function correctly\\n Inflate.prototype.c.call(this, final);\\n // process concatenated GZIP\\n if (this.s.f && !this.s.l && !final) {\\n this.v = shft(this.s.p) + 9;\\n this.s = { i: 0 };\\n this.o = new u8(0);\\n this.push(new u8(0), final);\\n }\\n };\\n return Gunzip;\\n}());\\nexport { Gunzip };\\n/**\\n * Asynchronous streaming single or multi-member GZIP decompression\\n */\\nvar AsyncGunzip = /*#__PURE__*/ (function () {\\n function AsyncGunzip(opts, cb) {\\n var _this = this;\\n astrmify([\\n bInflt,\\n guze,\\n function () { return [astrm, Inflate, Gunzip]; }\\n ], this, StrmOpt.call(this, opts, cb), function (ev) {\\n var strm = new Gunzip(ev.data);\\n strm.onmember = function (offset) { return postMessage(offset); };\\n onmessage = astrm(strm);\\n }, 9, 0, function (offset) { return _this.onmember && _this.onmember(offset); });\\n }\\n return AsyncGunzip;\\n}());\\nexport { AsyncGunzip };\\nexport function gunzip(data, opts, cb) {\\n if (!cb)\\n cb = opts, opts = {};\\n if (typeof cb != 'function')\\n err(7);\\n return cbify(data, opts, [\\n bInflt,\\n guze,\\n function () { return [gunzipSync]; }\\n ], function (ev) { return pbf(gunzipSync(ev.data[0], ev.data[1])); }, 3, cb);\\n}\\n/**\\n * Expands GZIP data\\n * @param data The data to decompress\\n * @param opts The decompression options\\n * @returns The decompressed version of the data\\n */\\nexport function gunzipSync(data, opts) {\\n var st = gzs(data);\\n if (st + 8 > data.length)\\n err(6, 'invalid gzip data');\\n return inflt(data.subarray(st, -8), { i: 2 }, opts && opts.out || new u8(gzl(data)), opts && opts.dictionary);\\n}\\n/**\\n * Streaming Zlib compression\\n */\\nvar Zlib = /*#__PURE__*/ (function () {\\n function Zlib(opts, cb) {\\n this.c = adler();\\n this.v = 1;\\n Deflate.call(this, opts, cb);\\n }\\n /**\\n * Pushes a chunk to be zlibbed\\n * @param chunk The chunk to push\\n * @param final Whether this is the last chunk\\n */\\n Zlib.prototype.push = function (chunk, final) {\\n this.c.p(chunk);\\n Deflate.prototype.push.call(this, chunk, final);\\n };\\n Zlib.prototype.p = function (c, f) {\\n var raw = dopt(c, this.o, this.v && (this.o.dictionary ? 6 : 2), f && 4, this.s);\\n if (this.v)\\n zlh(raw, this.o), this.v = 0;\\n if (f)\\n wbytes(raw, raw.length - 4, this.c.d());\\n this.ondata(raw, f);\\n };\\n /**\\n * Flushes buffered uncompressed data. Useful to immediately retrieve the\\n * zlibbed output for small inputs.\\n */\\n Zlib.prototype.flush = function () {\\n Deflate.prototype.flush.call(this);\\n };\\n return Zlib;\\n}());\\nexport { Zlib };\\n/**\\n * Asynchronous streaming Zlib compression\\n */\\nvar AsyncZlib = /*#__PURE__*/ (function () {\\n function AsyncZlib(opts, cb) {\\n astrmify([\\n bDflt,\\n zle,\\n function () { return [astrm, Deflate, Zlib]; }\\n ], this, StrmOpt.call(this, opts, cb), function (ev) {\\n var strm = new Zlib(ev.data);\\n onmessage = astrm(strm);\\n }, 10, 1);\\n }\\n return AsyncZlib;\\n}());\\nexport { AsyncZlib };\\nexport function zlib(data, opts, cb) {\\n if (!cb)\\n cb = opts, opts = {};\\n if (typeof cb != 'function')\\n err(7);\\n return cbify(data, opts, [\\n bDflt,\\n zle,\\n function () { return [zlibSync]; }\\n ], function (ev) { return pbf(zlibSync(ev.data[0], ev.data[1])); }, 4, cb);\\n}\\n/**\\n * Compress data with Zlib\\n * @param data The data to compress\\n * @param opts The compression options\\n * @returns The zlib-compressed version of the data\\n */\\nexport function zlibSync(data, opts) {\\n if (!opts)\\n opts = {};\\n var a = adler();\\n a.p(data);\\n var d = dopt(data, opts, opts.dictionary ? 6 : 2, 4);\\n return zlh(d, opts), wbytes(d, d.length - 4, a.d()), d;\\n}\\n/**\\n * Streaming Zlib decompression\\n */\\nvar Unzlib = /*#__PURE__*/ (function () {\\n function Unzlib(opts, cb) {\\n Inflate.call(this, opts, cb);\\n this.v = opts && opts.dictionary ? 2 : 1;\\n }\\n /**\\n * Pushes a chunk to be unzlibbed\\n * @param chunk The chunk to push\\n * @param final Whether this is the last chunk\\n */\\n Unzlib.prototype.push = function (chunk, final) {\\n Inflate.prototype.e.call(this, chunk);\\n if (this.v) {\\n if (this.p.length < 6 && !final)\\n return;\\n this.p = this.p.subarray(zls(this.p, this.v - 1)), this.v = 0;\\n }\\n if (final) {\\n if (this.p.length < 4)\\n err(6, 'invalid zlib data');\\n this.p = this.p.subarray(0, -4);\\n }\\n // necessary to prevent TS from using the closure value\\n // This allows for workerization to function correctly\\n Inflate.prototype.c.call(this, final);\\n };\\n return Unzlib;\\n}());\\nexport { Unzlib };\\n/**\\n * Asynchronous streaming Zlib decompression\\n */\\nvar AsyncUnzlib = /*#__PURE__*/ (function () {\\n function AsyncUnzlib(opts, cb) {\\n astrmify([\\n bInflt,\\n zule,\\n function () { return [astrm, Inflate, Unzlib]; }\\n ], this, StrmOpt.call(this, opts, cb), function (ev) {\\n var strm = new Unzlib(ev.data);\\n onmessage = astrm(strm);\\n }, 11, 0);\\n }\\n return AsyncUnzlib;\\n}());\\nexport { AsyncUnzlib };\\nexport function unzlib(data, opts, cb) {\\n if (!cb)\\n cb = opts, opts = {};\\n if (typeof cb != 'function')\\n err(7);\\n return cbify(data, opts, [\\n bInflt,\\n zule,\\n function () { return [unzlibSync]; }\\n ], function (ev) { return pbf(unzlibSync(ev.data[0], gopt(ev.data[1]))); }, 5, cb);\\n}\\n/**\\n * Expands Zlib data\\n * @param data The data to decompress\\n * @param opts The decompression options\\n * @returns The decompressed version of the data\\n */\\nexport function unzlibSync(data, opts) {\\n return inflt(data.subarray(zls(data, opts && opts.dictionary), -4), { i: 2 }, opts && opts.out, opts && opts.dictionary);\\n}\\n// Default algorithm for compression (used because having a known output size allows faster decompression)\\nexport { gzip as compress, AsyncGzip as AsyncCompress };\\nexport { gzipSync as compressSync, Gzip as Compress };\\n/**\\n * Streaming GZIP, Zlib, or raw DEFLATE decompression\\n */\\nvar Decompress = /*#__PURE__*/ (function () {\\n function Decompress(opts, cb) {\\n this.o = StrmOpt.call(this, opts, cb) || {};\\n this.G = Gunzip;\\n this.I = Inflate;\\n this.Z = Unzlib;\\n }\\n // init substream\\n // overriden by AsyncDecompress\\n Decompress.prototype.i = function () {\\n var _this = this;\\n this.s.ondata = function (dat, final) {\\n _this.ondata(dat, final);\\n };\\n };\\n /**\\n * Pushes a chunk to be decompressed\\n * @param chunk The chunk to push\\n * @param final Whether this is the last chunk\\n */\\n Decompress.prototype.push = function (chunk, final) {\\n if (!this.ondata)\\n err(5);\\n if (!this.s) {\\n if (this.p && this.p.length) {\\n var n = new u8(this.p.length + chunk.length);\\n n.set(this.p), n.set(chunk, this.p.length);\\n }\\n else\\n this.p = chunk;\\n if (this.p.length > 2) {\\n this.s = (this.p[0] == 31 && this.p[1] == 139 && this.p[2] == 8)\\n ? new this.G(this.o)\\n : ((this.p[0] & 15) != 8 || (this.p[0] >> 4) > 7 || ((this.p[0] << 8 | this.p[1]) % 31))\\n ? new this.I(this.o)\\n : new this.Z(this.o);\\n this.i();\\n this.s.push(this.p, final);\\n this.p = null;\\n }\\n }\\n else\\n this.s.push(chunk, final);\\n };\\n return Decompress;\\n}());\\nexport { Decompress };\\n/**\\n * Asynchronous streaming GZIP, Zlib, or raw DEFLATE decompression\\n */\\nvar AsyncDecompress = /*#__PURE__*/ (function () {\\n function AsyncDecompress(opts, cb) {\\n Decompress.call(this, opts, cb);\\n this.queuedSize = 0;\\n this.G = AsyncGunzip;\\n this.I = AsyncInflate;\\n this.Z = AsyncUnzlib;\\n }\\n AsyncDecompress.prototype.i = function () {\\n var _this = this;\\n this.s.ondata = function (err, dat, final) {\\n _this.ondata(err, dat, final);\\n };\\n this.s.ondrain = function (size) {\\n _this.queuedSize -= size;\\n if (_this.ondrain)\\n _this.ondrain(size);\\n };\\n };\\n /**\\n * Pushes a chunk to be decompressed\\n * @param chunk The chunk to push\\n * @param final Whether this is the last chunk\\n */\\n AsyncDecompress.prototype.push = function (chunk, final) {\\n this.queuedSize += chunk.length;\\n Decompress.prototype.push.call(this, chunk, final);\\n };\\n return AsyncDecompress;\\n}());\\nexport { AsyncDecompress };\\nexport function decompress(data, opts, cb) {\\n if (!cb)\\n cb = opts, opts = {};\\n if (typeof cb != 'function')\\n err(7);\\n return (data[0] == 31 && data[1] == 139 && data[2] == 8)\\n ? gunzip(data, opts, cb)\\n : ((data[0] & 15) != 8 || (data[0] >> 4) > 7 || ((data[0] << 8 | data[1]) % 31))\\n ? inflate(data, opts, cb)\\n : unzlib(data, opts, cb);\\n}\\n/**\\n * Expands compressed GZIP, Zlib, or raw DEFLATE data, automatically detecting the format\\n * @param data The data to decompress\\n * @param opts The decompression options\\n * @returns The decompressed version of the data\\n */\\nexport function decompressSync(data, opts) {\\n return (data[0] == 31 && data[1] == 139 && data[2] == 8)\\n ? gunzipSync(data, opts)\\n : ((data[0] & 15) != 8 || (data[0] >> 4) > 7 || ((data[0] << 8 | data[1]) % 31))\\n ? inflateSync(data, opts)\\n : unzlibSync(data, opts);\\n}\\n// flatten a directory structure\\nvar fltn = function (d, p, t, o) {\\n for (var k in d) {\\n var val = d[k], n = p + k, op = o;\\n if (Array.isArray(val))\\n op = mrg(o, val[1]), val = val[0];\\n if (val instanceof u8)\\n t[n] = [val, op];\\n else {\\n t[n += '/'] = [new u8(0), op];\\n fltn(val, n, t, o);\\n }\\n }\\n};\\n// text encoder\\nvar te = typeof TextEncoder != 'undefined' && /*#__PURE__*/ new TextEncoder();\\n// text decoder\\nvar td = typeof TextDecoder != 'undefined' && /*#__PURE__*/ new TextDecoder();\\n// text decoder stream\\nvar tds = 0;\\ntry {\\n td.decode(et, { stream: true });\\n tds = 1;\\n}\\ncatch (e) { }\\n// decode UTF8\\nvar dutf8 = function (d) {\\n for (var r = '', i = 0;;) {\\n var c = d[i++];\\n var eb = (c > 127) + (c > 223) + (c > 239);\\n if (i + eb > d.length)\\n return { s: r, r: slc(d, i - 1) };\\n if (!eb)\\n r += String.fromCharCode(c);\\n else if (eb == 3) {\\n c = ((c & 15) << 18 | (d[i++] & 63) << 12 | (d[i++] & 63) << 6 | (d[i++] & 63)) - 65536,\\n r += String.fromCharCode(55296 | (c >> 10), 56320 | (c & 1023));\\n }\\n else if (eb & 1)\\n r += String.fromCharCode((c & 31) << 6 | (d[i++] & 63));\\n else\\n r += String.fromCharCode((c & 15) << 12 | (d[i++] & 63) << 6 | (d[i++] & 63));\\n }\\n};\\n/**\\n * Streaming UTF-8 decoding\\n */\\nvar DecodeUTF8 = /*#__PURE__*/ (function () {\\n /**\\n * Creates a UTF-8 decoding stream\\n * @param cb The callback to call whenever data is decoded\\n */\\n function DecodeUTF8(cb) {\\n this.ondata = cb;\\n if (tds)\\n this.t = new TextDecoder();\\n else\\n this.p = et;\\n }\\n /**\\n * Pushes a chunk to be decoded from UTF-8 binary\\n * @param chunk The chunk to push\\n * @param final Whether this is the last chunk\\n */\\n DecodeUTF8.prototype.push = function (chunk, final) {\\n if (!this.ondata)\\n err(5);\\n final = !!final;\\n if (this.t) {\\n this.ondata(this.t.decode(chunk, { stream: true }), final);\\n if (final) {\\n if (this.t.decode().length)\\n err(8);\\n this.t = null;\\n }\\n return;\\n }\\n if (!this.p)\\n err(4);\\n var dat = new u8(this.p.length + chunk.length);\\n dat.set(this.p);\\n dat.set(chunk, this.p.length);\\n var _a = dutf8(dat), s = _a.s, r = _a.r;\\n if (final) {\\n if (r.length)\\n err(8);\\n this.p = null;\\n }\\n else\\n this.p = r;\\n this.ondata(s, final);\\n };\\n return DecodeUTF8;\\n}());\\nexport { DecodeUTF8 };\\n/**\\n * Streaming UTF-8 encoding\\n */\\nvar EncodeUTF8 = /*#__PURE__*/ (function () {\\n /**\\n * Creates a UTF-8 decoding stream\\n * @param cb The callback to call whenever data is encoded\\n */\\n function EncodeUTF8(cb) {\\n this.ondata = cb;\\n }\\n /**\\n * Pushes a chunk to be encoded to UTF-8\\n * @param chunk The string data to push\\n * @param final Whether this is the last chunk\\n */\\n EncodeUTF8.prototype.push = function (chunk, final) {\\n if (!this.ondata)\\n err(5);\\n if (this.d)\\n err(4);\\n this.ondata(strToU8(chunk), this.d = final || false);\\n };\\n return EncodeUTF8;\\n}());\\nexport { EncodeUTF8 };\\n/**\\n * Converts a string into a Uint8Array for use with compression/decompression methods\\n * @param str The string to encode\\n * @param latin1 Whether or not to interpret the data as Latin-1. This should\\n * not need to be true unless decoding a binary string.\\n * @returns The string encoded in UTF-8/Latin-1 binary\\n */\\nexport function strToU8(str, latin1) {\\n if (latin1) {\\n var ar_1 = new u8(str.length);\\n for (var i = 0; i < str.length; ++i)\\n ar_1[i] = str.charCodeAt(i);\\n return ar_1;\\n }\\n if (te)\\n return te.encode(str);\\n var l = str.length;\\n var ar = new u8(str.length + (str.length >> 1));\\n var ai = 0;\\n var w = function (v) { ar[ai++] = v; };\\n for (var i = 0; i < l; ++i) {\\n if (ai + 5 > ar.length) {\\n var n = new u8(ai + 8 + ((l - i) << 1));\\n n.set(ar);\\n ar = n;\\n }\\n var c = str.charCodeAt(i);\\n if (c < 128 || latin1)\\n w(c);\\n else if (c < 2048)\\n w(192 | (c >> 6)), w(128 | (c & 63));\\n else if (c > 55295 && c < 57344)\\n c = 65536 + (c & 1023 << 10) | (str.charCodeAt(++i) & 1023),\\n w(240 | (c >> 18)), w(128 | ((c >> 12) & 63)), w(128 | ((c >> 6) & 63)), w(128 | (c & 63));\\n else\\n w(224 | (c >> 12)), w(128 | ((c >> 6) & 63)), w(128 | (c & 63));\\n }\\n return slc(ar, 0, ai);\\n}\\n/**\\n * Converts a Uint8Array to a string\\n * @param dat The data to decode to string\\n * @param latin1 Whether or not to interpret the data as Latin-1. This should\\n * not need to be true unless encoding to binary string.\\n * @returns The original UTF-8/Latin-1 string\\n */\\nexport function strFromU8(dat, latin1) {\\n if (latin1) {\\n var r = '';\\n for (var i = 0; i < dat.length; i += 16384)\\n r += String.fromCharCode.apply(null, dat.subarray(i, i + 16384));\\n return r;\\n }\\n else if (td) {\\n return td.decode(dat);\\n }\\n else {\\n var _a = dutf8(dat), s = _a.s, r = _a.r;\\n if (r.length)\\n err(8);\\n return s;\\n }\\n}\\n;\\n// deflate bit flag\\nvar dbf = function (l) { return l == 1 ? 3 : l < 6 ? 2 : l == 9 ? 1 : 0; };\\n// skip local zip header\\nvar slzh = function (d, b) { return b + 30 + b2(d, b + 26) + b2(d, b + 28); };\\n// read zip header\\nvar zh = function (d, b, z) {\\n var fnl = b2(d, b + 28), fn = strFromU8(d.subarray(b + 46, b + 46 + fnl), !(b2(d, b + 8) & 2048)), es = b + 46 + fnl, bs = b4(d, b + 20);\\n var _a = z && bs == 4294967295 ? z64e(d, es) : [bs, b4(d, b + 24), b4(d, b + 42)], sc = _a[0], su = _a[1], off = _a[2];\\n return [b2(d, b + 10), sc, su, fn, es + b2(d, b + 30) + b2(d, b + 32), off];\\n};\\n// read zip64 extra field\\nvar z64e = function (d, b) {\\n for (; b2(d, b) != 1; b += 4 + b2(d, b + 2))\\n ;\\n return [b8(d, b + 12), b8(d, b + 4), b8(d, b + 20)];\\n};\\n// extra field length\\nvar exfl = function (ex) {\\n var le = 0;\\n if (ex) {\\n for (var k in ex) {\\n var l = ex[k].length;\\n if (l > 65535)\\n err(9);\\n le += l + 4;\\n }\\n }\\n return le;\\n};\\n// write zip header\\nvar wzh = function (d, b, f, fn, u, c, ce, co) {\\n var fl = fn.length, ex = f.extra, col = co && co.length;\\n var exl = exfl(ex);\\n wbytes(d, b, ce != null ? 0x2014B50 : 0x4034B50), b += 4;\\n if (ce != null)\\n d[b++] = 20, d[b++] = f.os;\\n d[b] = 20, b += 2; // spec compliance? what's that?\\n d[b++] = (f.flag << 1) | (c < 0 && 8), d[b++] = u && 8;\\n d[b++] = f.compression & 255, d[b++] = f.compression >> 8;\\n var dt = new Date(f.mtime == null ? Date.now() : f.mtime), y = dt.getFullYear() - 1980;\\n if (y < 0 || y > 119)\\n err(10);\\n wbytes(d, b, (y << 25) | ((dt.getMonth() + 1) << 21) | (dt.getDate() << 16) | (dt.getHours() << 11) | (dt.getMinutes() << 5) | (dt.getSeconds() >> 1)), b += 4;\\n if (c != -1) {\\n wbytes(d, b, f.crc);\\n wbytes(d, b + 4, c < 0 ? -c - 2 : c);\\n wbytes(d, b + 8, f.size);\\n }\\n wbytes(d, b + 12, fl);\\n wbytes(d, b + 14, exl), b += 16;\\n if (ce != null) {\\n wbytes(d, b, col);\\n wbytes(d, b + 6, f.attrs);\\n wbytes(d, b + 10, ce), b += 14;\\n }\\n d.set(fn, b);\\n b += fl;\\n if (exl) {\\n for (var k in ex) {\\n var exf = ex[k], l = exf.length;\\n wbytes(d, b, +k);\\n wbytes(d, b + 2, l);\\n d.set(exf, b + 4), b += 4 + l;\\n }\\n }\\n if (col)\\n d.set(co, b), b += col;\\n return b;\\n};\\n// write zip footer (end of central directory)\\nvar wzf = function (o, b, c, d, e) {\\n wbytes(o, b, 0x6054B50); // skip disk\\n wbytes(o, b + 8, c);\\n wbytes(o, b + 10, c);\\n wbytes(o, b + 12, d);\\n wbytes(o, b + 16, e);\\n};\\n/**\\n * A pass-through stream to keep data uncompressed in a ZIP archive.\\n */\\nvar ZipPassThrough = /*#__PURE__*/ (function () {\\n /**\\n * Creates a pass-through stream that can be added to ZIP archives\\n * @param filename The filename to associate with this data stream\\n */\\n function ZipPassThrough(filename) {\\n this.filename = filename;\\n this.c = crc();\\n this.size = 0;\\n this.compression = 0;\\n }\\n /**\\n * Processes a chunk and pushes to the output stream. You can override this\\n * method in a subclass for custom behavior, but by default this passes\\n * the data through. You must call this.ondata(err, chunk, final) at some\\n * point in this method.\\n * @param chunk The chunk to process\\n * @param final Whether this is the last chunk\\n */\\n ZipPassThrough.prototype.process = function (chunk, final) {\\n this.ondata(null, chunk, final);\\n };\\n /**\\n * Pushes a chunk to be added. If you are subclassing this with a custom\\n * compression algorithm, note that you must push data from the source\\n * file only, pre-compression.\\n * @param chunk The chunk to push\\n * @param final Whether this is the last chunk\\n */\\n ZipPassThrough.prototype.push = function (chunk, final) {\\n if (!this.ondata)\\n err(5);\\n this.c.p(chunk);\\n this.size += chunk.length;\\n if (final)\\n this.crc = this.c.d();\\n this.process(chunk, final || false);\\n };\\n return ZipPassThrough;\\n}());\\nexport { ZipPassThrough };\\n// I don't extend because TypeScript extension adds 1kB of runtime bloat\\n/**\\n * Streaming DEFLATE compression for ZIP archives. Prefer using AsyncZipDeflate\\n * for better performance\\n */\\nvar ZipDeflate = /*#__PURE__*/ (function () {\\n /**\\n * Creates a DEFLATE stream that can be added to ZIP archives\\n * @param filename The filename to associate with this data stream\\n * @param opts The compression options\\n */\\n function ZipDeflate(filename, opts) {\\n var _this = this;\\n if (!opts)\\n opts = {};\\n ZipPassThrough.call(this, filename);\\n this.d = new Deflate(opts, function (dat, final) {\\n _this.ondata(null, dat, final);\\n });\\n this.compression = 8;\\n this.flag = dbf(opts.level);\\n }\\n ZipDeflate.prototype.process = function (chunk, final) {\\n try {\\n this.d.push(chunk, final);\\n }\\n catch (e) {\\n this.ondata(e, null, final);\\n }\\n };\\n /**\\n * Pushes a chunk to be deflated\\n * @param chunk The chunk to push\\n * @param final Whether this is the last chunk\\n */\\n ZipDeflate.prototype.push = function (chunk, final) {\\n ZipPassThrough.prototype.push.call(this, chunk, final);\\n };\\n return ZipDeflate;\\n}());\\nexport { ZipDeflate };\\n/**\\n * Asynchronous streaming DEFLATE compression for ZIP archives\\n */\\nvar AsyncZipDeflate = /*#__PURE__*/ (function () {\\n /**\\n * Creates an asynchronous DEFLATE stream that can be added to ZIP archives\\n * @param filename The filename to associate with this data stream\\n * @param opts The compression options\\n */\\n function AsyncZipDeflate(filename, opts) {\\n var _this = this;\\n if (!opts)\\n opts = {};\\n ZipPassThrough.call(this, filename);\\n this.d = new AsyncDeflate(opts, function (err, dat, final) {\\n _this.ondata(err, dat, final);\\n });\\n this.compression = 8;\\n this.flag = dbf(opts.level);\\n this.terminate = this.d.terminate;\\n }\\n AsyncZipDeflate.prototype.process = function (chunk, final) {\\n this.d.push(chunk, final);\\n };\\n /**\\n * Pushes a chunk to be deflated\\n * @param chunk The chunk to push\\n * @param final Whether this is the last chunk\\n */\\n AsyncZipDeflate.prototype.push = function (chunk, final) {\\n ZipPassThrough.prototype.push.call(this, chunk, final);\\n };\\n return AsyncZipDeflate;\\n}());\\nexport { AsyncZipDeflate };\\n// TODO: Better tree shaking\\n/**\\n * A zippable archive to which files can incrementally be added\\n */\\nvar Zip = /*#__PURE__*/ (function () {\\n /**\\n * Creates an empty ZIP archive to which files can be added\\n * @param cb The callback to call whenever data for the generated ZIP archive\\n * is available\\n */\\n function Zip(cb) {\\n this.ondata = cb;\\n this.u = [];\\n this.d = 1;\\n }\\n /**\\n * Adds a file to the ZIP archive\\n * @param file The file stream to add\\n */\\n Zip.prototype.add = function (file) {\\n var _this = this;\\n if (!this.ondata)\\n err(5);\\n // finishing or finished\\n if (this.d & 2)\\n this.ondata(err(4 + (this.d & 1) * 8, 0, 1), null, false);\\n else {\\n var f = strToU8(file.filename), fl_1 = f.length;\\n var com = file.comment, o = com && strToU8(com);\\n var u = fl_1 != file.filename.length || (o && (com.length != o.length));\\n var hl_1 = fl_1 + exfl(file.extra) + 30;\\n if (fl_1 > 65535)\\n this.ondata(err(11, 0, 1), null, false);\\n var header = new u8(hl_1);\\n wzh(header, 0, file, f, u, -1);\\n var chks_1 = [header];\\n var pAll_1 = function () {\\n for (var _i = 0, chks_2 = chks_1; _i < chks_2.length; _i++) {\\n var chk = chks_2[_i];\\n _this.ondata(null, chk, false);\\n }\\n chks_1 = [];\\n };\\n var tr_1 = this.d;\\n this.d = 0;\\n var ind_1 = this.u.length;\\n var uf_1 = mrg(file, {\\n f: f,\\n u: u,\\n o: o,\\n t: function () {\\n if (file.terminate)\\n file.terminate();\\n },\\n r: function () {\\n pAll_1();\\n if (tr_1) {\\n var nxt = _this.u[ind_1 + 1];\\n if (nxt)\\n nxt.r();\\n else\\n _this.d = 1;\\n }\\n tr_1 = 1;\\n }\\n });\\n var cl_1 = 0;\\n file.ondata = function (err, dat, final) {\\n if (err) {\\n _this.ondata(err, dat, final);\\n _this.terminate();\\n }\\n else {\\n cl_1 += dat.length;\\n chks_1.push(dat);\\n if (final) {\\n var dd = new u8(16);\\n wbytes(dd, 0, 0x8074B50);\\n wbytes(dd, 4, file.crc);\\n wbytes(dd, 8, cl_1);\\n wbytes(dd, 12, file.size);\\n chks_1.push(dd);\\n uf_1.c = cl_1, uf_1.b = hl_1 + cl_1 + 16, uf_1.crc = file.crc, uf_1.size = file.size;\\n if (tr_1)\\n uf_1.r();\\n tr_1 = 1;\\n }\\n else if (tr_1)\\n pAll_1();\\n }\\n };\\n this.u.push(uf_1);\\n }\\n };\\n /**\\n * Ends the process of adding files and prepares to emit the final chunks.\\n * This *must* be called after adding all desired files for the resulting\\n * ZIP file to work properly.\\n */\\n Zip.prototype.end = function () {\\n var _this = this;\\n if (this.d & 2) {\\n this.ondata(err(4 + (this.d & 1) * 8, 0, 1), null, true);\\n return;\\n }\\n if (this.d)\\n this.e();\\n else\\n this.u.push({\\n r: function () {\\n if (!(_this.d & 1))\\n return;\\n _this.u.splice(-1, 1);\\n _this.e();\\n },\\n t: function () { }\\n });\\n this.d = 3;\\n };\\n Zip.prototype.e = function () {\\n var bt = 0, l = 0, tl = 0;\\n for (var _i = 0, _a = this.u; _i < _a.length; _i++) {\\n var f = _a[_i];\\n tl += 46 + f.f.length + exfl(f.extra) + (f.o ? f.o.length : 0);\\n }\\n var out = new u8(tl + 22);\\n for (var _b = 0, _c = this.u; _b < _c.length; _b++) {\\n var f = _c[_b];\\n wzh(out, bt, f, f.f, f.u, -f.c - 2, l, f.o);\\n bt += 46 + f.f.length + exfl(f.extra) + (f.o ? f.o.length : 0), l += f.b;\\n }\\n wzf(out, bt, this.u.length, tl, l);\\n this.ondata(null, out, true);\\n this.d = 2;\\n };\\n /**\\n * A method to terminate any internal workers used by the stream. Subsequent\\n * calls to add() will fail.\\n */\\n Zip.prototype.terminate = function () {\\n for (var _i = 0, _a = this.u; _i < _a.length; _i++) {\\n var f = _a[_i];\\n f.t();\\n }\\n this.d = 2;\\n };\\n return Zip;\\n}());\\nexport { Zip };\\nexport function zip(data, opts, cb) {\\n if (!cb)\\n cb = opts, opts = {};\\n if (typeof cb != 'function')\\n err(7);\\n var r = {};\\n fltn(data, '', r, opts);\\n var k = Object.keys(r);\\n var lft = k.length, o = 0, tot = 0;\\n var slft = lft, files = new Array(lft);\\n var term = [];\\n var tAll = function () {\\n for (var i = 0; i < term.length; ++i)\\n term[i]();\\n };\\n var cbd = function (a, b) {\\n mt(function () { cb(a, b); });\\n };\\n mt(function () { cbd = cb; });\\n var cbf = function () {\\n var out = new u8(tot + 22), oe = o, cdl = tot - o;\\n tot = 0;\\n for (var i = 0; i < slft; ++i) {\\n var f = files[i];\\n try {\\n var l = f.c.length;\\n wzh(out, tot, f, f.f, f.u, l);\\n var badd = 30 + f.f.length + exfl(f.extra);\\n var loc = tot + badd;\\n out.set(f.c, loc);\\n wzh(out, o, f, f.f, f.u, l, tot, f.m), o += 16 + badd + (f.m ? f.m.length : 0), tot = loc + l;\\n }\\n catch (e) {\\n return cbd(e, null);\\n }\\n }\\n wzf(out, o, files.length, cdl, oe);\\n cbd(null, out);\\n };\\n if (!lft)\\n cbf();\\n var _loop_1 = function (i) {\\n var fn = k[i];\\n var _a = r[fn], file = _a[0], p = _a[1];\\n var c = crc(), size = file.length;\\n c.p(file);\\n var f = strToU8(fn), s = f.length;\\n var com = p.comment, m = com && strToU8(com), ms = m && m.length;\\n var exl = exfl(p.extra);\\n var compression = p.level == 0 ? 0 : 8;\\n var cbl = function (e, d) {\\n if (e) {\\n tAll();\\n cbd(e, null);\\n }\\n else {\\n var l = d.length;\\n files[i] = mrg(p, {\\n size: size,\\n crc: c.d(),\\n c: d,\\n f: f,\\n m: m,\\n u: s != fn.length || (m && (com.length != ms)),\\n compression: compression\\n });\\n o += 30 + s + exl + l;\\n tot += 76 + 2 * (s + exl) + (ms || 0) + l;\\n if (!--lft)\\n cbf();\\n }\\n };\\n if (s > 65535)\\n cbl(err(11, 0, 1), null);\\n if (!compression)\\n cbl(null, file);\\n else if (size < 160000) {\\n try {\\n cbl(null, deflateSync(file, p));\\n }\\n catch (e) {\\n cbl(e, null);\\n }\\n }\\n else\\n term.push(deflate(file, p, cbl));\\n };\\n // Cannot use lft because it can decrease\\n for (var i = 0; i < slft; ++i) {\\n _loop_1(i);\\n }\\n return tAll;\\n}\\n/**\\n * Synchronously creates a ZIP file. Prefer using `zip` for better performance\\n * with more than one file.\\n * @param data The directory structure for the ZIP archive\\n * @param opts The main options, merged with per-file options\\n * @returns The generated ZIP archive\\n */\\nexport function zipSync(data, opts) {\\n if (!opts)\\n opts = {};\\n var r = {};\\n var files = [];\\n fltn(data, '', r, opts);\\n var o = 0;\\n var tot = 0;\\n for (var fn in r) {\\n var _a = r[fn], file = _a[0], p = _a[1];\\n var compression = p.level == 0 ? 0 : 8;\\n var f = strToU8(fn), s = f.length;\\n var com = p.comment, m = com && strToU8(com), ms = m && m.length;\\n var exl = exfl(p.extra);\\n if (s > 65535)\\n err(11);\\n var d = compression ? deflateSync(file, p) : file, l = d.length;\\n var c = crc();\\n c.p(file);\\n files.push(mrg(p, {\\n size: file.length,\\n crc: c.d(),\\n c: d,\\n f: f,\\n m: m,\\n u: s != fn.length || (m && (com.length != ms)),\\n o: o,\\n compression: compression\\n }));\\n o += 30 + s + exl + l;\\n tot += 76 + 2 * (s + exl) + (ms || 0) + l;\\n }\\n var out = new u8(tot + 22), oe = o, cdl = tot - o;\\n for (var i = 0; i < files.length; ++i) {\\n var f = files[i];\\n wzh(out, f.o, f, f.f, f.u, f.c.length);\\n var badd = 30 + f.f.length + exfl(f.extra);\\n out.set(f.c, f.o + badd);\\n wzh(out, o, f, f.f, f.u, f.c.length, f.o, f.m), o += 16 + badd + (f.m ? f.m.length : 0);\\n }\\n wzf(out, o, files.length, cdl, oe);\\n return out;\\n}\\n/**\\n * Streaming pass-through decompression for ZIP archives\\n */\\nvar UnzipPassThrough = /*#__PURE__*/ (function () {\\n function UnzipPassThrough() {\\n }\\n UnzipPassThrough.prototype.push = function (data, final) {\\n this.ondata(null, data, final);\\n };\\n UnzipPassThrough.compression = 0;\\n return UnzipPassThrough;\\n}());\\nexport { UnzipPassThrough };\\n/**\\n * Streaming DEFLATE decompression for ZIP archives. Prefer AsyncZipInflate for\\n * better performance.\\n */\\nvar UnzipInflate = /*#__PURE__*/ (function () {\\n /**\\n * Creates a DEFLATE decompression that can be used in ZIP archives\\n */\\n function UnzipInflate() {\\n var _this = this;\\n this.i = new Inflate(function (dat, final) {\\n _this.ondata(null, dat, final);\\n });\\n }\\n UnzipInflate.prototype.push = function (data, final) {\\n try {\\n this.i.push(data, final);\\n }\\n catch (e) {\\n this.ondata(e, null, final);\\n }\\n };\\n UnzipInflate.compression = 8;\\n return UnzipInflate;\\n}());\\nexport { UnzipInflate };\\n/**\\n * Asynchronous streaming DEFLATE decompression for ZIP archives\\n */\\nvar AsyncUnzipInflate = /*#__PURE__*/ (function () {\\n /**\\n * Creates a DEFLATE decompression that can be used in ZIP archives\\n */\\n function AsyncUnzipInflate(_, sz) {\\n var _this = this;\\n if (sz < 320000) {\\n this.i = new Inflate(function (dat, final) {\\n _this.ondata(null, dat, final);\\n });\\n }\\n else {\\n this.i = new AsyncInflate(function (err, dat, final) {\\n _this.ondata(err, dat, final);\\n });\\n this.terminate = this.i.terminate;\\n }\\n }\\n AsyncUnzipInflate.prototype.push = function (data, final) {\\n if (this.i.terminate)\\n data = slc(data, 0);\\n this.i.push(data, final);\\n };\\n AsyncUnzipInflate.compression = 8;\\n return AsyncUnzipInflate;\\n}());\\nexport { AsyncUnzipInflate };\\n/**\\n * A ZIP archive decompression stream that emits files as they are discovered\\n */\\nvar Unzip = /*#__PURE__*/ (function () {\\n /**\\n * Creates a ZIP decompression stream\\n * @param cb The callback to call whenever a file in the ZIP archive is found\\n */\\n function Unzip(cb) {\\n this.onfile = cb;\\n this.k = [];\\n this.o = {\\n 0: UnzipPassThrough\\n };\\n this.p = et;\\n }\\n /**\\n * Pushes a chunk to be unzipped\\n * @param chunk The chunk to push\\n * @param final Whether this is the last chunk\\n */\\n Unzip.prototype.push = function (chunk, final) {\\n var _this = this;\\n if (!this.onfile)\\n err(5);\\n if (!this.p)\\n err(4);\\n if (this.c > 0) {\\n var len = Math.min(this.c, chunk.length);\\n var toAdd = chunk.subarray(0, len);\\n this.c -= len;\\n if (this.d)\\n this.d.push(toAdd, !this.c);\\n else\\n this.k[0].push(toAdd);\\n chunk = chunk.subarray(len);\\n if (chunk.length)\\n return this.push(chunk, final);\\n }\\n else {\\n var f = 0, i = 0, is = void 0, buf = void 0;\\n if (!this.p.length)\\n buf = chunk;\\n else if (!chunk.length)\\n buf = this.p;\\n else {\\n buf = new u8(this.p.length + chunk.length);\\n buf.set(this.p), buf.set(chunk, this.p.length);\\n }\\n var l = buf.length, oc = this.c, add = oc && this.d;\\n var _loop_2 = function () {\\n var _a;\\n var sig = b4(buf, i);\\n if (sig == 0x4034B50) {\\n f = 1, is = i;\\n this_1.d = null;\\n this_1.c = 0;\\n var bf = b2(buf, i + 6), cmp_1 = b2(buf, i + 8), u = bf & 2048, dd = bf & 8, fnl = b2(buf, i + 26), es = b2(buf, i + 28);\\n if (l > i + 30 + fnl + es) {\\n var chks_3 = [];\\n this_1.k.unshift(chks_3);\\n f = 2;\\n var sc_1 = b4(buf, i + 18), su_1 = b4(buf, i + 22);\\n var fn_1 = strFromU8(buf.subarray(i + 30, i += 30 + fnl), !u);\\n if (sc_1 == 4294967295) {\\n _a = dd ? [-2] : z64e(buf, i), sc_1 = _a[0], su_1 = _a[1];\\n }\\n else if (dd)\\n sc_1 = -1;\\n i += es;\\n this_1.c = sc_1;\\n var d_1;\\n var file_1 = {\\n name: fn_1,\\n compression: cmp_1,\\n start: function () {\\n if (!file_1.ondata)\\n err(5);\\n if (!sc_1)\\n file_1.ondata(null, et, true);\\n else {\\n var ctr = _this.o[cmp_1];\\n if (!ctr)\\n file_1.ondata(err(14, 'unknown compression type ' + cmp_1, 1), null, false);\\n d_1 = sc_1 < 0 ? new ctr(fn_1) : new ctr(fn_1, sc_1, su_1);\\n d_1.ondata = function (err, dat, final) { file_1.ondata(err, dat, final); };\\n for (var _i = 0, chks_4 = chks_3; _i < chks_4.length; _i++) {\\n var dat = chks_4[_i];\\n d_1.push(dat, false);\\n }\\n if (_this.k[0] == chks_3 && _this.c)\\n _this.d = d_1;\\n else\\n d_1.push(et, true);\\n }\\n },\\n terminate: function () {\\n if (d_1 && d_1.terminate)\\n d_1.terminate();\\n }\\n };\\n if (sc_1 >= 0)\\n file_1.size = sc_1, file_1.originalSize = su_1;\\n this_1.onfile(file_1);\\n }\\n return \\\"break\\\";\\n }\\n else if (oc) {\\n if (sig == 0x8074B50) {\\n is = i += 12 + (oc == -2 && 8), f = 3, this_1.c = 0;\\n return \\\"break\\\";\\n }\\n else if (sig == 0x2014B50) {\\n is = i -= 4, f = 3, this_1.c = 0;\\n return \\\"break\\\";\\n }\\n }\\n };\\n var this_1 = this;\\n for (; i < l - 4; ++i) {\\n var state_1 = _loop_2();\\n if (state_1 === \\\"break\\\")\\n break;\\n }\\n this.p = et;\\n if (oc < 0) {\\n var dat = f ? buf.subarray(0, is - 12 - (oc == -2 && 8) - (b4(buf, is - 16) == 0x8074B50 && 4)) : buf.subarray(0, i);\\n if (add)\\n add.push(dat, !!f);\\n else\\n this.k[+(f == 2)].push(dat);\\n }\\n if (f & 2)\\n return this.push(buf.subarray(i), final);\\n this.p = buf.subarray(i);\\n }\\n if (final) {\\n if (this.c)\\n err(13);\\n this.p = null;\\n }\\n };\\n /**\\n * Registers a decoder with the stream, allowing for files compressed with\\n * the compression type provided to be expanded correctly\\n * @param decoder The decoder constructor\\n */\\n Unzip.prototype.register = function (decoder) {\\n this.o[decoder.compression] = decoder;\\n };\\n return Unzip;\\n}());\\nexport { Unzip };\\nvar mt = typeof queueMicrotask == 'function' ? queueMicrotask : typeof setTimeout == 'function' ? setTimeout : function (fn) { fn(); };\\nexport function unzip(data, opts, cb) {\\n if (!cb)\\n cb = opts, opts = {};\\n if (typeof cb != 'function')\\n err(7);\\n var term = [];\\n var tAll = function () {\\n for (var i = 0; i < term.length; ++i)\\n term[i]();\\n };\\n var files = {};\\n var cbd = function (a, b) {\\n mt(function () { cb(a, b); });\\n };\\n mt(function () { cbd = cb; });\\n var e = data.length - 22;\\n for (; b4(data, e) != 0x6054B50; --e) {\\n if (!e || data.length - e > 65558) {\\n cbd(err(13, 0, 1), null);\\n return tAll;\\n }\\n }\\n ;\\n var lft = b2(data, e + 8);\\n if (lft) {\\n var c = lft;\\n var o = b4(data, e + 16);\\n var z = o == 4294967295 || c == 65535;\\n if (z) {\\n var ze = b4(data, e - 12);\\n z = b4(data, ze) == 0x6064B50;\\n if (z) {\\n c = lft = b4(data, ze + 32);\\n o = b4(data, ze + 48);\\n }\\n }\\n var fltr = opts && opts.filter;\\n var _loop_3 = function (i) {\\n var _a = zh(data, o, z), c_1 = _a[0], sc = _a[1], su = _a[2], fn = _a[3], no = _a[4], off = _a[5], b = slzh(data, off);\\n o = no;\\n var cbl = function (e, d) {\\n if (e) {\\n tAll();\\n cbd(e, null);\\n }\\n else {\\n if (d)\\n files[fn] = d;\\n if (!--lft)\\n cbd(null, files);\\n }\\n };\\n if (!fltr || fltr({\\n name: fn,\\n size: sc,\\n originalSize: su,\\n compression: c_1\\n })) {\\n if (!c_1)\\n cbl(null, slc(data, b, b + sc));\\n else if (c_1 == 8) {\\n var infl = data.subarray(b, b + sc);\\n // Synchronously decompress under 512KB, or barely-compressed data\\n if (su < 524288 || sc > 0.8 * su) {\\n try {\\n cbl(null, inflateSync(infl, { out: new u8(su) }));\\n }\\n catch (e) {\\n cbl(e, null);\\n }\\n }\\n else\\n term.push(inflate(infl, { size: su }, cbl));\\n }\\n else\\n cbl(err(14, 'unknown compression type ' + c_1, 1), null);\\n }\\n else\\n cbl(null, null);\\n };\\n for (var i = 0; i < c; ++i) {\\n _loop_3(i);\\n }\\n }\\n else\\n cbd(null, {});\\n return tAll;\\n}\\n/**\\n * Synchronously decompresses a ZIP archive. Prefer using `unzip` for better\\n * performance with more than one file.\\n * @param data The raw compressed ZIP file\\n * @param opts The ZIP extraction options\\n * @returns The decompressed files\\n */\\nexport function unzipSync(data, opts) {\\n var files = {};\\n var e = data.length - 22;\\n for (; b4(data, e) != 0x6054B50; --e) {\\n if (!e || data.length - e > 65558)\\n err(13);\\n }\\n ;\\n var c = b2(data, e + 8);\\n if (!c)\\n return {};\\n var o = b4(data, e + 16);\\n var z = o == 4294967295 || c == 65535;\\n if (z) {\\n var ze = b4(data, e - 12);\\n z = b4(data, ze) == 0x6064B50;\\n if (z) {\\n c = b4(data, ze + 32);\\n o = b4(data, ze + 48);\\n }\\n }\\n var fltr = opts && opts.filter;\\n for (var i = 0; i < c; ++i) {\\n var _a = zh(data, o, z), c_2 = _a[0], sc = _a[1], su = _a[2], fn = _a[3], no = _a[4], off = _a[5], b = slzh(data, off);\\n o = no;\\n if (!fltr || fltr({\\n name: fn,\\n size: sc,\\n originalSize: su,\\n compression: c_2\\n })) {\\n if (!c_2)\\n files[fn] = slc(data, b, b + sc);\\n else if (c_2 == 8)\\n files[fn] = inflateSync(data.subarray(b, b + sc), { out: new u8(su) });\\n else\\n err(14, 'unknown compression type ' + c_2);\\n }\\n }\\n return files;\\n}\\n\",\"import Any from './properties/Any/regex.mjs';\\nimport Cc from './categories/Cc/regex.mjs';\\nimport Cf from './categories/Cf/regex.mjs';\\nimport P from './categories/P/regex.mjs';\\nimport S from './categories/S/regex.mjs';\\nimport Z from './categories/Z/regex.mjs';\\n\\nexport { Any, Cc, Cf, P, S, Z };\\n\",\"export default /[\\\\0-\\\\uD7FF\\\\uE000-\\\\uFFFF]|[\\\\uD800-\\\\uDBFF][\\\\uDC00-\\\\uDFFF]|[\\\\uD800-\\\\uDBFF](?![\\\\uDC00-\\\\uDFFF])|(?:[^\\\\uD800-\\\\uDBFF]|^)[\\\\uDC00-\\\\uDFFF]/\",\"export default /[\\\\0-\\\\x1F\\\\x7F-\\\\x9F]/\",\"export default /[\\\\xAD\\\\u0600-\\\\u0605\\\\u061C\\\\u06DD\\\\u070F\\\\u0890\\\\u0891\\\\u08E2\\\\u180E\\\\u200B-\\\\u200F\\\\u202A-\\\\u202E\\\\u2060-\\\\u2064\\\\u2066-\\\\u206F\\\\uFEFF\\\\uFFF9-\\\\uFFFB]|\\\\uD804[\\\\uDCBD\\\\uDCCD]|\\\\uD80D[\\\\uDC30-\\\\uDC3F]|\\\\uD82F[\\\\uDCA0-\\\\uDCA3]|\\\\uD834[\\\\uDD73-\\\\uDD7A]|\\\\uDB40[\\\\uDC01\\\\uDC20-\\\\uDC7F]/\",\"export default /[!-#%-\\\\*,-\\\\/:;\\\\?@\\\\[-\\\\]_\\\\{\\\\}\\\\xA1\\\\xA7\\\\xAB\\\\xB6\\\\xB7\\\\xBB\\\\xBF\\\\u037E\\\\u0387\\\\u055A-\\\\u055F\\\\u0589\\\\u058A\\\\u05BE\\\\u05C0\\\\u05C3\\\\u05C6\\\\u05F3\\\\u05F4\\\\u0609\\\\u060A\\\\u060C\\\\u060D\\\\u061B\\\\u061D-\\\\u061F\\\\u066A-\\\\u066D\\\\u06D4\\\\u0700-\\\\u070D\\\\u07F7-\\\\u07F9\\\\u0830-\\\\u083E\\\\u085E\\\\u0964\\\\u0965\\\\u0970\\\\u09FD\\\\u0A76\\\\u0AF0\\\\u0C77\\\\u0C84\\\\u0DF4\\\\u0E4F\\\\u0E5A\\\\u0E5B\\\\u0F04-\\\\u0F12\\\\u0F14\\\\u0F3A-\\\\u0F3D\\\\u0F85\\\\u0FD0-\\\\u0FD4\\\\u0FD9\\\\u0FDA\\\\u104A-\\\\u104F\\\\u10FB\\\\u1360-\\\\u1368\\\\u1400\\\\u166E\\\\u169B\\\\u169C\\\\u16EB-\\\\u16ED\\\\u1735\\\\u1736\\\\u17D4-\\\\u17D6\\\\u17D8-\\\\u17DA\\\\u1800-\\\\u180A\\\\u1944\\\\u1945\\\\u1A1E\\\\u1A1F\\\\u1AA0-\\\\u1AA6\\\\u1AA8-\\\\u1AAD\\\\u1B5A-\\\\u1B60\\\\u1B7D\\\\u1B7E\\\\u1BFC-\\\\u1BFF\\\\u1C3B-\\\\u1C3F\\\\u1C7E\\\\u1C7F\\\\u1CC0-\\\\u1CC7\\\\u1CD3\\\\u2010-\\\\u2027\\\\u2030-\\\\u2043\\\\u2045-\\\\u2051\\\\u2053-\\\\u205E\\\\u207D\\\\u207E\\\\u208D\\\\u208E\\\\u2308-\\\\u230B\\\\u2329\\\\u232A\\\\u2768-\\\\u2775\\\\u27C5\\\\u27C6\\\\u27E6-\\\\u27EF\\\\u2983-\\\\u2998\\\\u29D8-\\\\u29DB\\\\u29FC\\\\u29FD\\\\u2CF9-\\\\u2CFC\\\\u2CFE\\\\u2CFF\\\\u2D70\\\\u2E00-\\\\u2E2E\\\\u2E30-\\\\u2E4F\\\\u2E52-\\\\u2E5D\\\\u3001-\\\\u3003\\\\u3008-\\\\u3011\\\\u3014-\\\\u301F\\\\u3030\\\\u303D\\\\u30A0\\\\u30FB\\\\uA4FE\\\\uA4FF\\\\uA60D-\\\\uA60F\\\\uA673\\\\uA67E\\\\uA6F2-\\\\uA6F7\\\\uA874-\\\\uA877\\\\uA8CE\\\\uA8CF\\\\uA8F8-\\\\uA8FA\\\\uA8FC\\\\uA92E\\\\uA92F\\\\uA95F\\\\uA9C1-\\\\uA9CD\\\\uA9DE\\\\uA9DF\\\\uAA5C-\\\\uAA5F\\\\uAADE\\\\uAADF\\\\uAAF0\\\\uAAF1\\\\uABEB\\\\uFD3E\\\\uFD3F\\\\uFE10-\\\\uFE19\\\\uFE30-\\\\uFE52\\\\uFE54-\\\\uFE61\\\\uFE63\\\\uFE68\\\\uFE6A\\\\uFE6B\\\\uFF01-\\\\uFF03\\\\uFF05-\\\\uFF0A\\\\uFF0C-\\\\uFF0F\\\\uFF1A\\\\uFF1B\\\\uFF1F\\\\uFF20\\\\uFF3B-\\\\uFF3D\\\\uFF3F\\\\uFF5B\\\\uFF5D\\\\uFF5F-\\\\uFF65]|\\\\uD800[\\\\uDD00-\\\\uDD02\\\\uDF9F\\\\uDFD0]|\\\\uD801\\\\uDD6F|\\\\uD802[\\\\uDC57\\\\uDD1F\\\\uDD3F\\\\uDE50-\\\\uDE58\\\\uDE7F\\\\uDEF0-\\\\uDEF6\\\\uDF39-\\\\uDF3F\\\\uDF99-\\\\uDF9C]|\\\\uD803[\\\\uDEAD\\\\uDF55-\\\\uDF59\\\\uDF86-\\\\uDF89]|\\\\uD804[\\\\uDC47-\\\\uDC4D\\\\uDCBB\\\\uDCBC\\\\uDCBE-\\\\uDCC1\\\\uDD40-\\\\uDD43\\\\uDD74\\\\uDD75\\\\uDDC5-\\\\uDDC8\\\\uDDCD\\\\uDDDB\\\\uDDDD-\\\\uDDDF\\\\uDE38-\\\\uDE3D\\\\uDEA9]|\\\\uD805[\\\\uDC4B-\\\\uDC4F\\\\uDC5A\\\\uDC5B\\\\uDC5D\\\\uDCC6\\\\uDDC1-\\\\uDDD7\\\\uDE41-\\\\uDE43\\\\uDE60-\\\\uDE6C\\\\uDEB9\\\\uDF3C-\\\\uDF3E]|\\\\uD806[\\\\uDC3B\\\\uDD44-\\\\uDD46\\\\uDDE2\\\\uDE3F-\\\\uDE46\\\\uDE9A-\\\\uDE9C\\\\uDE9E-\\\\uDEA2\\\\uDF00-\\\\uDF09]|\\\\uD807[\\\\uDC41-\\\\uDC45\\\\uDC70\\\\uDC71\\\\uDEF7\\\\uDEF8\\\\uDF43-\\\\uDF4F\\\\uDFFF]|\\\\uD809[\\\\uDC70-\\\\uDC74]|\\\\uD80B[\\\\uDFF1\\\\uDFF2]|\\\\uD81A[\\\\uDE6E\\\\uDE6F\\\\uDEF5\\\\uDF37-\\\\uDF3B\\\\uDF44]|\\\\uD81B[\\\\uDE97-\\\\uDE9A\\\\uDFE2]|\\\\uD82F\\\\uDC9F|\\\\uD836[\\\\uDE87-\\\\uDE8B]|\\\\uD83A[\\\\uDD5E\\\\uDD5F]/\",\"export default /[\\\\$\\\\+<->\\\\^`\\\\|~\\\\xA2-\\\\xA6\\\\xA8\\\\xA9\\\\xAC\\\\xAE-\\\\xB1\\\\xB4\\\\xB8\\\\xD7\\\\xF7\\\\u02C2-\\\\u02C5\\\\u02D2-\\\\u02DF\\\\u02E5-\\\\u02EB\\\\u02ED\\\\u02EF-\\\\u02FF\\\\u0375\\\\u0384\\\\u0385\\\\u03F6\\\\u0482\\\\u058D-\\\\u058F\\\\u0606-\\\\u0608\\\\u060B\\\\u060E\\\\u060F\\\\u06DE\\\\u06E9\\\\u06FD\\\\u06FE\\\\u07F6\\\\u07FE\\\\u07FF\\\\u0888\\\\u09F2\\\\u09F3\\\\u09FA\\\\u09FB\\\\u0AF1\\\\u0B70\\\\u0BF3-\\\\u0BFA\\\\u0C7F\\\\u0D4F\\\\u0D79\\\\u0E3F\\\\u0F01-\\\\u0F03\\\\u0F13\\\\u0F15-\\\\u0F17\\\\u0F1A-\\\\u0F1F\\\\u0F34\\\\u0F36\\\\u0F38\\\\u0FBE-\\\\u0FC5\\\\u0FC7-\\\\u0FCC\\\\u0FCE\\\\u0FCF\\\\u0FD5-\\\\u0FD8\\\\u109E\\\\u109F\\\\u1390-\\\\u1399\\\\u166D\\\\u17DB\\\\u1940\\\\u19DE-\\\\u19FF\\\\u1B61-\\\\u1B6A\\\\u1B74-\\\\u1B7C\\\\u1FBD\\\\u1FBF-\\\\u1FC1\\\\u1FCD-\\\\u1FCF\\\\u1FDD-\\\\u1FDF\\\\u1FED-\\\\u1FEF\\\\u1FFD\\\\u1FFE\\\\u2044\\\\u2052\\\\u207A-\\\\u207C\\\\u208A-\\\\u208C\\\\u20A0-\\\\u20C0\\\\u2100\\\\u2101\\\\u2103-\\\\u2106\\\\u2108\\\\u2109\\\\u2114\\\\u2116-\\\\u2118\\\\u211E-\\\\u2123\\\\u2125\\\\u2127\\\\u2129\\\\u212E\\\\u213A\\\\u213B\\\\u2140-\\\\u2144\\\\u214A-\\\\u214D\\\\u214F\\\\u218A\\\\u218B\\\\u2190-\\\\u2307\\\\u230C-\\\\u2328\\\\u232B-\\\\u2426\\\\u2440-\\\\u244A\\\\u249C-\\\\u24E9\\\\u2500-\\\\u2767\\\\u2794-\\\\u27C4\\\\u27C7-\\\\u27E5\\\\u27F0-\\\\u2982\\\\u2999-\\\\u29D7\\\\u29DC-\\\\u29FB\\\\u29FE-\\\\u2B73\\\\u2B76-\\\\u2B95\\\\u2B97-\\\\u2BFF\\\\u2CE5-\\\\u2CEA\\\\u2E50\\\\u2E51\\\\u2E80-\\\\u2E99\\\\u2E9B-\\\\u2EF3\\\\u2F00-\\\\u2FD5\\\\u2FF0-\\\\u2FFF\\\\u3004\\\\u3012\\\\u3013\\\\u3020\\\\u3036\\\\u3037\\\\u303E\\\\u303F\\\\u309B\\\\u309C\\\\u3190\\\\u3191\\\\u3196-\\\\u319F\\\\u31C0-\\\\u31E3\\\\u31EF\\\\u3200-\\\\u321E\\\\u322A-\\\\u3247\\\\u3250\\\\u3260-\\\\u327F\\\\u328A-\\\\u32B0\\\\u32C0-\\\\u33FF\\\\u4DC0-\\\\u4DFF\\\\uA490-\\\\uA4C6\\\\uA700-\\\\uA716\\\\uA720\\\\uA721\\\\uA789\\\\uA78A\\\\uA828-\\\\uA82B\\\\uA836-\\\\uA839\\\\uAA77-\\\\uAA79\\\\uAB5B\\\\uAB6A\\\\uAB6B\\\\uFB29\\\\uFBB2-\\\\uFBC2\\\\uFD40-\\\\uFD4F\\\\uFDCF\\\\uFDFC-\\\\uFDFF\\\\uFE62\\\\uFE64-\\\\uFE66\\\\uFE69\\\\uFF04\\\\uFF0B\\\\uFF1C-\\\\uFF1E\\\\uFF3E\\\\uFF40\\\\uFF5C\\\\uFF5E\\\\uFFE0-\\\\uFFE6\\\\uFFE8-\\\\uFFEE\\\\uFFFC\\\\uFFFD]|\\\\uD800[\\\\uDD37-\\\\uDD3F\\\\uDD79-\\\\uDD89\\\\uDD8C-\\\\uDD8E\\\\uDD90-\\\\uDD9C\\\\uDDA0\\\\uDDD0-\\\\uDDFC]|\\\\uD802[\\\\uDC77\\\\uDC78\\\\uDEC8]|\\\\uD805\\\\uDF3F|\\\\uD807[\\\\uDFD5-\\\\uDFF1]|\\\\uD81A[\\\\uDF3C-\\\\uDF3F\\\\uDF45]|\\\\uD82F\\\\uDC9C|\\\\uD833[\\\\uDF50-\\\\uDFC3]|\\\\uD834[\\\\uDC00-\\\\uDCF5\\\\uDD00-\\\\uDD26\\\\uDD29-\\\\uDD64\\\\uDD6A-\\\\uDD6C\\\\uDD83\\\\uDD84\\\\uDD8C-\\\\uDDA9\\\\uDDAE-\\\\uDDEA\\\\uDE00-\\\\uDE41\\\\uDE45\\\\uDF00-\\\\uDF56]|\\\\uD835[\\\\uDEC1\\\\uDEDB\\\\uDEFB\\\\uDF15\\\\uDF35\\\\uDF4F\\\\uDF6F\\\\uDF89\\\\uDFA9\\\\uDFC3]|\\\\uD836[\\\\uDC00-\\\\uDDFF\\\\uDE37-\\\\uDE3A\\\\uDE6D-\\\\uDE74\\\\uDE76-\\\\uDE83\\\\uDE85\\\\uDE86]|\\\\uD838[\\\\uDD4F\\\\uDEFF]|\\\\uD83B[\\\\uDCAC\\\\uDCB0\\\\uDD2E\\\\uDEF0\\\\uDEF1]|\\\\uD83C[\\\\uDC00-\\\\uDC2B\\\\uDC30-\\\\uDC93\\\\uDCA0-\\\\uDCAE\\\\uDCB1-\\\\uDCBF\\\\uDCC1-\\\\uDCCF\\\\uDCD1-\\\\uDCF5\\\\uDD0D-\\\\uDDAD\\\\uDDE6-\\\\uDE02\\\\uDE10-\\\\uDE3B\\\\uDE40-\\\\uDE48\\\\uDE50\\\\uDE51\\\\uDE60-\\\\uDE65\\\\uDF00-\\\\uDFFF]|\\\\uD83D[\\\\uDC00-\\\\uDED7\\\\uDEDC-\\\\uDEEC\\\\uDEF0-\\\\uDEFC\\\\uDF00-\\\\uDF76\\\\uDF7B-\\\\uDFD9\\\\uDFE0-\\\\uDFEB\\\\uDFF0]|\\\\uD83E[\\\\uDC00-\\\\uDC0B\\\\uDC10-\\\\uDC47\\\\uDC50-\\\\uDC59\\\\uDC60-\\\\uDC87\\\\uDC90-\\\\uDCAD\\\\uDCB0\\\\uDCB1\\\\uDD00-\\\\uDE53\\\\uDE60-\\\\uDE6D\\\\uDE70-\\\\uDE7C\\\\uDE80-\\\\uDE88\\\\uDE90-\\\\uDEBD\\\\uDEBF-\\\\uDEC5\\\\uDECE-\\\\uDEDB\\\\uDEE0-\\\\uDEE8\\\\uDEF0-\\\\uDEF8\\\\uDF00-\\\\uDF92\\\\uDF94-\\\\uDFCA]/\",\"export default /[ \\\\xA0\\\\u1680\\\\u2000-\\\\u200A\\\\u2028\\\\u2029\\\\u202F\\\\u205F\\\\u3000]/\",\"import { Any, Cc, Z, P } from 'uc.micro'\\n\\nexport default function (opts) {\\n const re = {}\\n opts = opts || {}\\n\\n re.src_Any = Any.source\\n re.src_Cc = Cc.source\\n re.src_Z = Z.source\\n re.src_P = P.source\\n\\n // \\\\p{\\\\Z\\\\P\\\\Cc\\\\CF} (white spaces + control + format + punctuation)\\n re.src_ZPCc = [re.src_Z, re.src_P, re.src_Cc].join('|')\\n\\n // \\\\p{\\\\Z\\\\Cc} (white spaces + control)\\n re.src_ZCc = [re.src_Z, re.src_Cc].join('|')\\n\\n // Experimental. List of chars, completely prohibited in links\\n // because can separate it from other part of text\\n const text_separators = '[><\\\\uff5c]'\\n\\n // All possible word characters (everything without punctuation, spaces & controls)\\n // Defined via punctuation & spaces to save space\\n // Should be something like \\\\p{\\\\L\\\\N\\\\S\\\\M} (\\\\w but without `_`)\\n re.src_pseudo_letter = '(?:(?!' + text_separators + '|' + re.src_ZPCc + ')' + re.src_Any + ')'\\n // The same as abothe but without [0-9]\\n // var src_pseudo_letter_non_d = '(?:(?![0-9]|' + src_ZPCc + ')' + src_Any + ')';\\n\\n re.src_ip4 =\\n\\n '(?:(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\\\\\\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)'\\n\\n // Prohibit any of \\\"@/[]()\\\" in user/pass to avoid wrong domain fetch.\\n re.src_auth = '(?:(?:(?!' + re.src_ZCc + '|[@/\\\\\\\\[\\\\\\\\]()]).)+@)?'\\n\\n re.src_port =\\n\\n '(?::(?:6(?:[0-4]\\\\\\\\d{3}|5(?:[0-4]\\\\\\\\d{2}|5(?:[0-2]\\\\\\\\d|3[0-5])))|[1-5]?\\\\\\\\d{1,4}))?'\\n\\n re.src_host_terminator =\\n\\n '(?=$|' + text_separators + '|' + re.src_ZPCc + ')' +\\n '(?!' + (opts['---'] ? '-(?!--)|' : '-|') + '_|:\\\\\\\\d|\\\\\\\\.-|\\\\\\\\.(?!$|' + re.src_ZPCc + '))'\\n\\n re.src_path =\\n\\n '(?:' +\\n '[/?#]' +\\n '(?:' +\\n '(?!' + re.src_ZCc + '|' + text_separators + '|[()[\\\\\\\\]{}.,\\\"\\\\'?!\\\\\\\\-;]).|' +\\n '\\\\\\\\[(?:(?!' + re.src_ZCc + '|\\\\\\\\]).)*\\\\\\\\]|' +\\n '\\\\\\\\((?:(?!' + re.src_ZCc + '|[)]).)*\\\\\\\\)|' +\\n '\\\\\\\\{(?:(?!' + re.src_ZCc + '|[}]).)*\\\\\\\\}|' +\\n '\\\\\\\\\\\"(?:(?!' + re.src_ZCc + '|[\\\"]).)+\\\\\\\\\\\"|' +\\n \\\"\\\\\\\\'(?:(?!\\\" + re.src_ZCc + \\\"|[']).)+\\\\\\\\'|\\\" +\\n\\n // allow `I'm_king` if no pair found\\n \\\"\\\\\\\\'(?=\\\" + re.src_pseudo_letter + '|[-])|' +\\n\\n // google has many dots in \\\"google search\\\" links (#66, #81).\\n // github has ... in commit range links,\\n // Restrict to\\n // - english\\n // - percent-encoded\\n // - parts of file path\\n // - params separator\\n // until more examples found.\\n '\\\\\\\\.{2,}[a-zA-Z0-9%/&]|' +\\n\\n '\\\\\\\\.(?!' + re.src_ZCc + '|[.]|$)|' +\\n (opts['---']\\n ? '\\\\\\\\-(?!--(?:[^-]|$))(?:-*)|' // `---` => long dash, terminate\\n : '\\\\\\\\-+|'\\n ) +\\n // allow `,,,` in paths\\n ',(?!' + re.src_ZCc + '|$)|' +\\n\\n // allow `;` if not followed by space-like char\\n ';(?!' + re.src_ZCc + '|$)|' +\\n\\n // allow `!!!` in paths, but not at the end\\n '\\\\\\\\!+(?!' + re.src_ZCc + '|[!]|$)|' +\\n\\n '\\\\\\\\?(?!' + re.src_ZCc + '|[?]|$)' +\\n ')+' +\\n '|\\\\\\\\/' +\\n ')?'\\n\\n // Allow anything in markdown spec, forbid quote (\\\") at the first position\\n // because emails enclosed in quotes are far more common\\n re.src_email_name =\\n\\n '[\\\\\\\\-;:&=\\\\\\\\+\\\\\\\\$,\\\\\\\\.a-zA-Z0-9_][\\\\\\\\-;:&=\\\\\\\\+\\\\\\\\$,\\\\\\\\\\\"\\\\\\\\.a-zA-Z0-9_]*'\\n\\n re.src_xn =\\n\\n 'xn--[a-z0-9\\\\\\\\-]{1,59}'\\n\\n // More to read about domain names\\n // http://serverfault.com/questions/638260/\\n\\n re.src_domain_root =\\n\\n // Allow letters & digits (http://test1)\\n '(?:' +\\n re.src_xn +\\n '|' +\\n re.src_pseudo_letter + '{1,63}' +\\n ')'\\n\\n re.src_domain =\\n\\n '(?:' +\\n re.src_xn +\\n '|' +\\n '(?:' + re.src_pseudo_letter + ')' +\\n '|' +\\n '(?:' + re.src_pseudo_letter + '(?:-|' + re.src_pseudo_letter + '){0,61}' + re.src_pseudo_letter + ')' +\\n ')'\\n\\n re.src_host =\\n\\n '(?:' +\\n // Don't need IP check, because digits are already allowed in normal domain names\\n // src_ip4 +\\n // '|' +\\n '(?:(?:(?:' + re.src_domain + ')\\\\\\\\.)*' + re.src_domain/* _root */ + ')' +\\n ')'\\n\\n re.tpl_host_fuzzy =\\n\\n '(?:' +\\n re.src_ip4 +\\n '|' +\\n '(?:(?:(?:' + re.src_domain + ')\\\\\\\\.)+(?:%TLDS%))' +\\n ')'\\n\\n re.tpl_host_no_ip_fuzzy =\\n\\n '(?:(?:(?:' + re.src_domain + ')\\\\\\\\.)+(?:%TLDS%))'\\n\\n re.src_host_strict =\\n\\n re.src_host + re.src_host_terminator\\n\\n re.tpl_host_fuzzy_strict =\\n\\n re.tpl_host_fuzzy + re.src_host_terminator\\n\\n re.src_host_port_strict =\\n\\n re.src_host + re.src_port + re.src_host_terminator\\n\\n re.tpl_host_port_fuzzy_strict =\\n\\n re.tpl_host_fuzzy + re.src_port + re.src_host_terminator\\n\\n re.tpl_host_port_no_ip_fuzzy_strict =\\n\\n re.tpl_host_no_ip_fuzzy + re.src_port + re.src_host_terminator\\n\\n //\\n // Main rules\\n //\\n\\n // Rude test fuzzy links by host, for quick deny\\n re.tpl_host_fuzzy_test =\\n\\n 'localhost|www\\\\\\\\.|\\\\\\\\.\\\\\\\\d{1,3}\\\\\\\\.|(?:\\\\\\\\.(?:%TLDS%)(?:' + re.src_ZPCc + '|>|$))'\\n\\n re.tpl_email_fuzzy =\\n\\n '(^|' + text_separators + '|\\\"|\\\\\\\\(|' + re.src_ZCc + ')' +\\n '(' + re.src_email_name + '@' + re.tpl_host_fuzzy_strict + ')'\\n\\n re.tpl_link_fuzzy =\\n // Fuzzy link can't be prepended with .:/\\\\- and non punctuation.\\n // but can start with > (markdown blockquote)\\n '(^|(?![.:/\\\\\\\\-_@])(?:[$+<=>^`|\\\\uff5c]|' + re.src_ZPCc + '))' +\\n '((?![$+<=>^`|\\\\uff5c])' + re.tpl_host_port_fuzzy_strict + re.src_path + ')'\\n\\n re.tpl_link_no_ip_fuzzy =\\n // Fuzzy link can't be prepended with .:/\\\\- and non punctuation.\\n // but can start with > (markdown blockquote)\\n '(^|(?![.:/\\\\\\\\-_@])(?:[$+<=>^`|\\\\uff5c]|' + re.src_ZPCc + '))' +\\n '((?![$+<=>^`|\\\\uff5c])' + re.tpl_host_port_no_ip_fuzzy_strict + re.src_path + ')'\\n\\n return re\\n}\\n\",\"import reFactory from './lib/re.mjs'\\n\\n//\\n// Helpers\\n//\\n\\n// Merge objects\\n//\\nfunction assign (obj /* from1, from2, from3, ... */) {\\n const sources = Array.prototype.slice.call(arguments, 1)\\n\\n sources.forEach(function (source) {\\n if (!source) { return }\\n\\n Object.keys(source).forEach(function (key) {\\n obj[key] = source[key]\\n })\\n })\\n\\n return obj\\n}\\n\\nfunction _class (obj) { return Object.prototype.toString.call(obj) }\\nfunction isString (obj) { return _class(obj) === '[object String]' }\\nfunction isObject (obj) { return _class(obj) === '[object Object]' }\\nfunction isRegExp (obj) { return _class(obj) === '[object RegExp]' }\\nfunction isFunction (obj) { return _class(obj) === '[object Function]' }\\n\\nfunction escapeRE (str) { return str.replace(/[.?*+^$[\\\\]\\\\\\\\(){}|-]/g, '\\\\\\\\$&') }\\n\\n//\\n\\nconst defaultOptions = {\\n fuzzyLink: true,\\n fuzzyEmail: true,\\n fuzzyIP: false\\n}\\n\\nfunction isOptionsObj (obj) {\\n return Object.keys(obj || {}).reduce(function (acc, k) {\\n /* eslint-disable-next-line no-prototype-builtins */\\n return acc || defaultOptions.hasOwnProperty(k)\\n }, false)\\n}\\n\\nconst defaultSchemas = {\\n 'http:': {\\n validate: function (text, pos, self) {\\n const tail = text.slice(pos)\\n\\n if (!self.re.http) {\\n // compile lazily, because \\\"host\\\"-containing variables can change on tlds update.\\n self.re.http = new RegExp(\\n '^\\\\\\\\/\\\\\\\\/' + self.re.src_auth + self.re.src_host_port_strict + self.re.src_path, 'i'\\n )\\n }\\n if (self.re.http.test(tail)) {\\n return tail.match(self.re.http)[0].length\\n }\\n return 0\\n }\\n },\\n 'https:': 'http:',\\n 'ftp:': 'http:',\\n '//': {\\n validate: function (text, pos, self) {\\n const tail = text.slice(pos)\\n\\n if (!self.re.no_http) {\\n // compile lazily, because \\\"host\\\"-containing variables can change on tlds update.\\n self.re.no_http = new RegExp(\\n '^' +\\n self.re.src_auth +\\n // Don't allow single-level domains, because of false positives like '//test'\\n // with code comments\\n '(?:localhost|(?:(?:' + self.re.src_domain + ')\\\\\\\\.)+' + self.re.src_domain_root + ')' +\\n self.re.src_port +\\n self.re.src_host_terminator +\\n self.re.src_path,\\n\\n 'i'\\n )\\n }\\n\\n if (self.re.no_http.test(tail)) {\\n // should not be `://` & `///`, that protects from errors in protocol name\\n if (pos >= 3 && text[pos - 3] === ':') { return 0 }\\n if (pos >= 3 && text[pos - 3] === '/') { return 0 }\\n return tail.match(self.re.no_http)[0].length\\n }\\n return 0\\n }\\n },\\n 'mailto:': {\\n validate: function (text, pos, self) {\\n const tail = text.slice(pos)\\n\\n if (!self.re.mailto) {\\n self.re.mailto = new RegExp(\\n '^' + self.re.src_email_name + '@' + self.re.src_host_strict, 'i'\\n )\\n }\\n if (self.re.mailto.test(tail)) {\\n return tail.match(self.re.mailto)[0].length\\n }\\n return 0\\n }\\n }\\n}\\n\\n// RE pattern for 2-character tlds (autogenerated by ./support/tlds_2char_gen.js)\\n/* eslint-disable-next-line max-len */\\nconst tlds_2ch_src_re = 'a[cdefgilmnoqrstuwxz]|b[abdefghijmnorstvwyz]|c[acdfghiklmnoruvwxyz]|d[ejkmoz]|e[cegrstu]|f[ijkmor]|g[abdefghilmnpqrstuwy]|h[kmnrtu]|i[delmnoqrst]|j[emop]|k[eghimnprwyz]|l[abcikrstuvy]|m[acdeghklmnopqrstuvwxyz]|n[acefgilopruz]|om|p[aefghklmnrstwy]|qa|r[eosuw]|s[abcdeghijklmnortuvxyz]|t[cdfghjklmnortvwz]|u[agksyz]|v[aceginu]|w[fs]|y[et]|z[amw]'\\n\\n// DON'T try to make PRs with changes. Extend TLDs with LinkifyIt.tlds() instead\\nconst tlds_default = 'biz|com|edu|gov|net|org|pro|web|xxx|aero|asia|coop|info|museum|name|shop|рф'.split('|')\\n\\nfunction resetScanCache (self) {\\n self.__index__ = -1\\n self.__text_cache__ = ''\\n}\\n\\nfunction createValidator (re) {\\n return function (text, pos) {\\n const tail = text.slice(pos)\\n\\n if (re.test(tail)) {\\n return tail.match(re)[0].length\\n }\\n return 0\\n }\\n}\\n\\nfunction createNormalizer () {\\n return function (match, self) {\\n self.normalize(match)\\n }\\n}\\n\\n// Schemas compiler. Build regexps.\\n//\\nfunction compile (self) {\\n // Load & clone RE patterns.\\n const re = self.re = reFactory(self.__opts__)\\n\\n // Define dynamic patterns\\n const tlds = self.__tlds__.slice()\\n\\n self.onCompile()\\n\\n if (!self.__tlds_replaced__) {\\n tlds.push(tlds_2ch_src_re)\\n }\\n tlds.push(re.src_xn)\\n\\n re.src_tlds = tlds.join('|')\\n\\n function untpl (tpl) { return tpl.replace('%TLDS%', re.src_tlds) }\\n\\n re.email_fuzzy = RegExp(untpl(re.tpl_email_fuzzy), 'i')\\n re.link_fuzzy = RegExp(untpl(re.tpl_link_fuzzy), 'i')\\n re.link_no_ip_fuzzy = RegExp(untpl(re.tpl_link_no_ip_fuzzy), 'i')\\n re.host_fuzzy_test = RegExp(untpl(re.tpl_host_fuzzy_test), 'i')\\n\\n //\\n // Compile each schema\\n //\\n\\n const aliases = []\\n\\n self.__compiled__ = {} // Reset compiled data\\n\\n function schemaError (name, val) {\\n throw new Error('(LinkifyIt) Invalid schema \\\"' + name + '\\\": ' + val)\\n }\\n\\n Object.keys(self.__schemas__).forEach(function (name) {\\n const val = self.__schemas__[name]\\n\\n // skip disabled methods\\n if (val === null) { return }\\n\\n const compiled = { validate: null, link: null }\\n\\n self.__compiled__[name] = compiled\\n\\n if (isObject(val)) {\\n if (isRegExp(val.validate)) {\\n compiled.validate = createValidator(val.validate)\\n } else if (isFunction(val.validate)) {\\n compiled.validate = val.validate\\n } else {\\n schemaError(name, val)\\n }\\n\\n if (isFunction(val.normalize)) {\\n compiled.normalize = val.normalize\\n } else if (!val.normalize) {\\n compiled.normalize = createNormalizer()\\n } else {\\n schemaError(name, val)\\n }\\n\\n return\\n }\\n\\n if (isString(val)) {\\n aliases.push(name)\\n return\\n }\\n\\n schemaError(name, val)\\n })\\n\\n //\\n // Compile postponed aliases\\n //\\n\\n aliases.forEach(function (alias) {\\n if (!self.__compiled__[self.__schemas__[alias]]) {\\n // Silently fail on missed schemas to avoid errons on disable.\\n // schemaError(alias, self.__schemas__[alias]);\\n return\\n }\\n\\n self.__compiled__[alias].validate =\\n self.__compiled__[self.__schemas__[alias]].validate\\n self.__compiled__[alias].normalize =\\n self.__compiled__[self.__schemas__[alias]].normalize\\n })\\n\\n //\\n // Fake record for guessed links\\n //\\n self.__compiled__[''] = { validate: null, normalize: createNormalizer() }\\n\\n //\\n // Build schema condition\\n //\\n const slist = Object.keys(self.__compiled__)\\n .filter(function (name) {\\n // Filter disabled & fake schemas\\n return name.length > 0 && self.__compiled__[name]\\n })\\n .map(escapeRE)\\n .join('|')\\n // (?!_) cause 1.5x slowdown\\n self.re.schema_test = RegExp('(^|(?!_)(?:[><\\\\uff5c]|' + re.src_ZPCc + '))(' + slist + ')', 'i')\\n self.re.schema_search = RegExp('(^|(?!_)(?:[><\\\\uff5c]|' + re.src_ZPCc + '))(' + slist + ')', 'ig')\\n self.re.schema_at_start = RegExp('^' + self.re.schema_search.source, 'i')\\n\\n self.re.pretest = RegExp(\\n '(' + self.re.schema_test.source + ')|(' + self.re.host_fuzzy_test.source + ')|@',\\n 'i'\\n )\\n\\n //\\n // Cleanup\\n //\\n\\n resetScanCache(self)\\n}\\n\\n/**\\n * class Match\\n *\\n * Match result. Single element of array, returned by [[LinkifyIt#match]]\\n **/\\nfunction Match (self, shift) {\\n const start = self.__index__\\n const end = self.__last_index__\\n const text = self.__text_cache__.slice(start, end)\\n\\n /**\\n * Match#schema -> String\\n *\\n * Prefix (protocol) for matched string.\\n **/\\n this.schema = self.__schema__.toLowerCase()\\n /**\\n * Match#index -> Number\\n *\\n * First position of matched string.\\n **/\\n this.index = start + shift\\n /**\\n * Match#lastIndex -> Number\\n *\\n * Next position after matched string.\\n **/\\n this.lastIndex = end + shift\\n /**\\n * Match#raw -> String\\n *\\n * Matched string.\\n **/\\n this.raw = text\\n /**\\n * Match#text -> String\\n *\\n * Notmalized text of matched string.\\n **/\\n this.text = text\\n /**\\n * Match#url -> String\\n *\\n * Normalized url of matched string.\\n **/\\n this.url = text\\n}\\n\\nfunction createMatch (self, shift) {\\n const match = new Match(self, shift)\\n\\n self.__compiled__[match.schema].normalize(match, self)\\n\\n return match\\n}\\n\\n/**\\n * class LinkifyIt\\n **/\\n\\n/**\\n * new LinkifyIt(schemas, options)\\n * - schemas (Object): Optional. Additional schemas to validate (prefix/validator)\\n * - options (Object): { fuzzyLink|fuzzyEmail|fuzzyIP: true|false }\\n *\\n * Creates new linkifier instance with optional additional schemas.\\n * Can be called without `new` keyword for convenience.\\n *\\n * By default understands:\\n *\\n * - `http(s)://...` , `ftp://...`, `mailto:...` & `//...` links\\n * - \\\"fuzzy\\\" links and emails (example.com, foo@bar.com).\\n *\\n * `schemas` is an object, where each key/value describes protocol/rule:\\n *\\n * - __key__ - link prefix (usually, protocol name with `:` at the end, `skype:`\\n * for example). `linkify-it` makes shure that prefix is not preceeded with\\n * alphanumeric char and symbols. Only whitespaces and punctuation allowed.\\n * - __value__ - rule to check tail after link prefix\\n * - _String_ - just alias to existing rule\\n * - _Object_\\n * - _validate_ - validator function (should return matched length on success),\\n * or `RegExp`.\\n * - _normalize_ - optional function to normalize text & url of matched result\\n * (for example, for @twitter mentions).\\n *\\n * `options`:\\n *\\n * - __fuzzyLink__ - recognige URL-s without `http(s):` prefix. Default `true`.\\n * - __fuzzyIP__ - allow IPs in fuzzy links above. Can conflict with some texts\\n * like version numbers. Default `false`.\\n * - __fuzzyEmail__ - recognize emails without `mailto:` prefix.\\n *\\n **/\\nfunction LinkifyIt (schemas, options) {\\n if (!(this instanceof LinkifyIt)) {\\n return new LinkifyIt(schemas, options)\\n }\\n\\n if (!options) {\\n if (isOptionsObj(schemas)) {\\n options = schemas\\n schemas = {}\\n }\\n }\\n\\n this.__opts__ = assign({}, defaultOptions, options)\\n\\n // Cache last tested result. Used to skip repeating steps on next `match` call.\\n this.__index__ = -1\\n this.__last_index__ = -1 // Next scan position\\n this.__schema__ = ''\\n this.__text_cache__ = ''\\n\\n this.__schemas__ = assign({}, defaultSchemas, schemas)\\n this.__compiled__ = {}\\n\\n this.__tlds__ = tlds_default\\n this.__tlds_replaced__ = false\\n\\n this.re = {}\\n\\n compile(this)\\n}\\n\\n/** chainable\\n * LinkifyIt#add(schema, definition)\\n * - schema (String): rule name (fixed pattern prefix)\\n * - definition (String|RegExp|Object): schema definition\\n *\\n * Add new rule definition. See constructor description for details.\\n **/\\nLinkifyIt.prototype.add = function add (schema, definition) {\\n this.__schemas__[schema] = definition\\n compile(this)\\n return this\\n}\\n\\n/** chainable\\n * LinkifyIt#set(options)\\n * - options (Object): { fuzzyLink|fuzzyEmail|fuzzyIP: true|false }\\n *\\n * Set recognition options for links without schema.\\n **/\\nLinkifyIt.prototype.set = function set (options) {\\n this.__opts__ = assign(this.__opts__, options)\\n return this\\n}\\n\\n/**\\n * LinkifyIt#test(text) -> Boolean\\n *\\n * Searches linkifiable pattern and returns `true` on success or `false` on fail.\\n **/\\nLinkifyIt.prototype.test = function test (text) {\\n // Reset scan cache\\n this.__text_cache__ = text\\n this.__index__ = -1\\n\\n if (!text.length) { return false }\\n\\n let m, ml, me, len, shift, next, re, tld_pos, at_pos\\n\\n // try to scan for link with schema - that's the most simple rule\\n if (this.re.schema_test.test(text)) {\\n re = this.re.schema_search\\n re.lastIndex = 0\\n while ((m = re.exec(text)) !== null) {\\n len = this.testSchemaAt(text, m[2], re.lastIndex)\\n if (len) {\\n this.__schema__ = m[2]\\n this.__index__ = m.index + m[1].length\\n this.__last_index__ = m.index + m[0].length + len\\n break\\n }\\n }\\n }\\n\\n if (this.__opts__.fuzzyLink && this.__compiled__['http:']) {\\n // guess schemaless links\\n tld_pos = text.search(this.re.host_fuzzy_test)\\n if (tld_pos >= 0) {\\n // if tld is located after found link - no need to check fuzzy pattern\\n if (this.__index__ < 0 || tld_pos < this.__index__) {\\n if ((ml = text.match(this.__opts__.fuzzyIP ? this.re.link_fuzzy : this.re.link_no_ip_fuzzy)) !== null) {\\n shift = ml.index + ml[1].length\\n\\n if (this.__index__ < 0 || shift < this.__index__) {\\n this.__schema__ = ''\\n this.__index__ = shift\\n this.__last_index__ = ml.index + ml[0].length\\n }\\n }\\n }\\n }\\n }\\n\\n if (this.__opts__.fuzzyEmail && this.__compiled__['mailto:']) {\\n // guess schemaless emails\\n at_pos = text.indexOf('@')\\n if (at_pos >= 0) {\\n // We can't skip this check, because this cases are possible:\\n // 192.168.1.1@gmail.com, my.in@example.com\\n if ((me = text.match(this.re.email_fuzzy)) !== null) {\\n shift = me.index + me[1].length\\n next = me.index + me[0].length\\n\\n if (this.__index__ < 0 || shift < this.__index__ ||\\n (shift === this.__index__ && next > this.__last_index__)) {\\n this.__schema__ = 'mailto:'\\n this.__index__ = shift\\n this.__last_index__ = next\\n }\\n }\\n }\\n }\\n\\n return this.__index__ >= 0\\n}\\n\\n/**\\n * LinkifyIt#pretest(text) -> Boolean\\n *\\n * Very quick check, that can give false positives. Returns true if link MAY BE\\n * can exists. Can be used for speed optimization, when you need to check that\\n * link NOT exists.\\n **/\\nLinkifyIt.prototype.pretest = function pretest (text) {\\n return this.re.pretest.test(text)\\n}\\n\\n/**\\n * LinkifyIt#testSchemaAt(text, name, position) -> Number\\n * - text (String): text to scan\\n * - name (String): rule (schema) name\\n * - position (Number): text offset to check from\\n *\\n * Similar to [[LinkifyIt#test]] but checks only specific protocol tail exactly\\n * at given position. Returns length of found pattern (0 on fail).\\n **/\\nLinkifyIt.prototype.testSchemaAt = function testSchemaAt (text, schema, pos) {\\n // If not supported schema check requested - terminate\\n if (!this.__compiled__[schema.toLowerCase()]) {\\n return 0\\n }\\n return this.__compiled__[schema.toLowerCase()].validate(text, pos, this)\\n}\\n\\n/**\\n * LinkifyIt#match(text) -> Array|null\\n *\\n * Returns array of found link descriptions or `null` on fail. We strongly\\n * recommend to use [[LinkifyIt#test]] first, for best speed.\\n *\\n * ##### Result match description\\n *\\n * - __schema__ - link schema, can be empty for fuzzy links, or `//` for\\n * protocol-neutral links.\\n * - __index__ - offset of matched text\\n * - __lastIndex__ - index of next char after mathch end\\n * - __raw__ - matched text\\n * - __text__ - normalized text\\n * - __url__ - link, generated from matched text\\n **/\\nLinkifyIt.prototype.match = function match (text) {\\n const result = []\\n let shift = 0\\n\\n // Try to take previous element from cache, if .test() called before\\n if (this.__index__ >= 0 && this.__text_cache__ === text) {\\n result.push(createMatch(this, shift))\\n shift = this.__last_index__\\n }\\n\\n // Cut head if cache was used\\n let tail = shift ? text.slice(shift) : text\\n\\n // Scan string until end reached\\n while (this.test(tail)) {\\n result.push(createMatch(this, shift))\\n\\n tail = tail.slice(this.__last_index__)\\n shift += this.__last_index__\\n }\\n\\n if (result.length) {\\n return result\\n }\\n\\n return null\\n}\\n\\n/**\\n * LinkifyIt#matchAtStart(text) -> Match|null\\n *\\n * Returns fully-formed (not fuzzy) link if it starts at the beginning\\n * of the string, and null otherwise.\\n **/\\nLinkifyIt.prototype.matchAtStart = function matchAtStart (text) {\\n // Reset scan cache\\n this.__text_cache__ = text\\n this.__index__ = -1\\n\\n if (!text.length) return null\\n\\n const m = this.re.schema_at_start.exec(text)\\n if (!m) return null\\n\\n const len = this.testSchemaAt(text, m[2], m[0].length)\\n if (!len) return null\\n\\n this.__schema__ = m[2]\\n this.__index__ = m.index + m[1].length\\n this.__last_index__ = m.index + m[0].length + len\\n\\n return createMatch(this, 0)\\n}\\n\\n/** chainable\\n * LinkifyIt#tlds(list [, keepOld]) -> this\\n * - list (Array): list of tlds\\n * - keepOld (Boolean): merge with current list if `true` (`false` by default)\\n *\\n * Load (or merge) new tlds list. Those are user for fuzzy links (without prefix)\\n * to avoid false positives. By default this algorythm used:\\n *\\n * - hostname with any 2-letter root zones are ok.\\n * - biz|com|edu|gov|net|org|pro|web|xxx|aero|asia|coop|info|museum|name|shop|рф\\n * are ok.\\n * - encoded (`xn--...`) root zones are ok.\\n *\\n * If list is replaced, then exact match for 2-chars root zones will be checked.\\n **/\\nLinkifyIt.prototype.tlds = function tlds (list, keepOld) {\\n list = Array.isArray(list) ? list : [list]\\n\\n if (!keepOld) {\\n this.__tlds__ = list.slice()\\n this.__tlds_replaced__ = true\\n compile(this)\\n return this\\n }\\n\\n this.__tlds__ = this.__tlds__.concat(list)\\n .sort()\\n .filter(function (el, idx, arr) {\\n return el !== arr[idx - 1]\\n })\\n .reverse()\\n\\n compile(this)\\n return this\\n}\\n\\n/**\\n * LinkifyIt#normalize(match)\\n *\\n * Default normalizer (if schema does not define it's own).\\n **/\\nLinkifyIt.prototype.normalize = function normalize (match) {\\n // Do minimal possible changes by default. Need to collect feedback prior\\n // to move forward https://github.com/markdown-it/linkify-it/issues/1\\n\\n if (!match.schema) { match.url = 'http://' + match.url }\\n\\n if (match.schema === 'mailto:' && !/^mailto:/i.test(match.url)) {\\n match.url = 'mailto:' + match.url\\n }\\n}\\n\\n/**\\n * LinkifyIt#onCompile()\\n *\\n * Override to modify basic RegExp-s.\\n **/\\nLinkifyIt.prototype.onCompile = function onCompile () {\\n}\\n\\nexport default LinkifyIt\\n\",\"// Utilities\\n//\\n\\nimport * as mdurl from 'mdurl'\\nimport * as ucmicro from 'uc.micro'\\nimport { decodeHTML } from 'entities'\\n\\nfunction _class (obj) { return Object.prototype.toString.call(obj) }\\n\\nfunction isString (obj) { return _class(obj) === '[object String]' }\\n\\nconst _hasOwnProperty = Object.prototype.hasOwnProperty\\n\\nfunction has (object, key) {\\n return _hasOwnProperty.call(object, key)\\n}\\n\\n// Merge objects\\n//\\nfunction assign (obj /* from1, from2, from3, ... */) {\\n const sources = Array.prototype.slice.call(arguments, 1)\\n\\n sources.forEach(function (source) {\\n if (!source) { return }\\n\\n if (typeof source !== 'object') {\\n throw new TypeError(source + 'must be object')\\n }\\n\\n Object.keys(source).forEach(function (key) {\\n obj[key] = source[key]\\n })\\n })\\n\\n return obj\\n}\\n\\n// Remove element from array and put another array at those position.\\n// Useful for some operations with tokens\\nfunction arrayReplaceAt (src, pos, newElements) {\\n return [].concat(src.slice(0, pos), newElements, src.slice(pos + 1))\\n}\\n\\nfunction isValidEntityCode (c) {\\n /* eslint no-bitwise:0 */\\n // broken sequence\\n if (c >= 0xD800 && c <= 0xDFFF) { return false }\\n // never used\\n if (c >= 0xFDD0 && c <= 0xFDEF) { return false }\\n if ((c & 0xFFFF) === 0xFFFF || (c & 0xFFFF) === 0xFFFE) { return false }\\n // control codes\\n if (c >= 0x00 && c <= 0x08) { return false }\\n if (c === 0x0B) { return false }\\n if (c >= 0x0E && c <= 0x1F) { return false }\\n if (c >= 0x7F && c <= 0x9F) { return false }\\n // out of range\\n if (c > 0x10FFFF) { return false }\\n return true\\n}\\n\\nfunction fromCodePoint (c) {\\n /* eslint no-bitwise:0 */\\n if (c > 0xffff) {\\n c -= 0x10000\\n const surrogate1 = 0xd800 + (c >> 10)\\n const surrogate2 = 0xdc00 + (c & 0x3ff)\\n\\n return String.fromCharCode(surrogate1, surrogate2)\\n }\\n return String.fromCharCode(c)\\n}\\n\\nconst UNESCAPE_MD_RE = /\\\\\\\\([!\\\"#$%&'()*+,\\\\-./:;<=>?@[\\\\\\\\\\\\]^_`{|}~])/g\\nconst ENTITY_RE = /&([a-z#][a-z0-9]{1,31});/gi\\nconst UNESCAPE_ALL_RE = new RegExp(UNESCAPE_MD_RE.source + '|' + ENTITY_RE.source, 'gi')\\n\\nconst DIGITAL_ENTITY_TEST_RE = /^#((?:x[a-f0-9]{1,8}|[0-9]{1,8}))$/i\\n\\nfunction replaceEntityPattern (match, name) {\\n if (name.charCodeAt(0) === 0x23/* # */ && DIGITAL_ENTITY_TEST_RE.test(name)) {\\n const code = name[1].toLowerCase() === 'x'\\n ? parseInt(name.slice(2), 16)\\n : parseInt(name.slice(1), 10)\\n\\n if (isValidEntityCode(code)) {\\n return fromCodePoint(code)\\n }\\n\\n return match\\n }\\n\\n const decoded = decodeHTML(match)\\n if (decoded !== match) {\\n return decoded\\n }\\n\\n return match\\n}\\n\\n/* function replaceEntities(str) {\\n if (str.indexOf('&') < 0) { return str; }\\n\\n return str.replace(ENTITY_RE, replaceEntityPattern);\\n} */\\n\\nfunction unescapeMd (str) {\\n if (str.indexOf('\\\\\\\\') < 0) { return str }\\n return str.replace(UNESCAPE_MD_RE, '$1')\\n}\\n\\nfunction unescapeAll (str) {\\n if (str.indexOf('\\\\\\\\') < 0 && str.indexOf('&') < 0) { return str }\\n\\n return str.replace(UNESCAPE_ALL_RE, function (match, escaped, entity) {\\n if (escaped) { return escaped }\\n return replaceEntityPattern(match, entity)\\n })\\n}\\n\\nconst HTML_ESCAPE_TEST_RE = /[&<>\\\"]/\\nconst HTML_ESCAPE_REPLACE_RE = /[&<>\\\"]/g\\nconst HTML_REPLACEMENTS = {\\n '&': '&',\\n '<': '<',\\n '>': '>',\\n '\\\"': '"'\\n}\\n\\nfunction replaceUnsafeChar (ch) {\\n return HTML_REPLACEMENTS[ch]\\n}\\n\\nfunction escapeHtml (str) {\\n if (HTML_ESCAPE_TEST_RE.test(str)) {\\n return str.replace(HTML_ESCAPE_REPLACE_RE, replaceUnsafeChar)\\n }\\n return str\\n}\\n\\nconst REGEXP_ESCAPE_RE = /[.?*+^$[\\\\]\\\\\\\\(){}|-]/g\\n\\nfunction escapeRE (str) {\\n return str.replace(REGEXP_ESCAPE_RE, '\\\\\\\\$&')\\n}\\n\\nfunction isSpace (code) {\\n switch (code) {\\n case 0x09:\\n case 0x20:\\n return true\\n }\\n return false\\n}\\n\\n// Zs (unicode class) || [\\\\t\\\\f\\\\v\\\\r\\\\n]\\nfunction isWhiteSpace (code) {\\n if (code >= 0x2000 && code <= 0x200A) { return true }\\n switch (code) {\\n case 0x09: // \\\\t\\n case 0x0A: // \\\\n\\n case 0x0B: // \\\\v\\n case 0x0C: // \\\\f\\n case 0x0D: // \\\\r\\n case 0x20:\\n case 0xA0:\\n case 0x1680:\\n case 0x202F:\\n case 0x205F:\\n case 0x3000:\\n return true\\n }\\n return false\\n}\\n\\n/* eslint-disable max-len */\\n\\n// Currently without astral characters support.\\nfunction isPunctChar (ch) {\\n return ucmicro.P.test(ch) || ucmicro.S.test(ch)\\n}\\n\\n// Markdown ASCII punctuation characters.\\n//\\n// !, \\\", #, $, %, &, ', (, ), *, +, ,, -, ., /, :, ;, <, =, >, ?, @, [, \\\\, ], ^, _, `, {, |, }, or ~\\n// http://spec.commonmark.org/0.15/#ascii-punctuation-character\\n//\\n// Don't confuse with unicode punctuation !!! It lacks some chars in ascii range.\\n//\\nfunction isMdAsciiPunct (ch) {\\n switch (ch) {\\n case 0x21/* ! */:\\n case 0x22/* \\\" */:\\n case 0x23/* # */:\\n case 0x24/* $ */:\\n case 0x25/* % */:\\n case 0x26/* & */:\\n case 0x27/* ' */:\\n case 0x28/* ( */:\\n case 0x29/* ) */:\\n case 0x2A/* * */:\\n case 0x2B/* + */:\\n case 0x2C/* , */:\\n case 0x2D/* - */:\\n case 0x2E/* . */:\\n case 0x2F/* / */:\\n case 0x3A/* : */:\\n case 0x3B/* ; */:\\n case 0x3C/* < */:\\n case 0x3D/* = */:\\n case 0x3E/* > */:\\n case 0x3F/* ? */:\\n case 0x40/* @ */:\\n case 0x5B/* [ */:\\n case 0x5C/* \\\\ */:\\n case 0x5D/* ] */:\\n case 0x5E/* ^ */:\\n case 0x5F/* _ */:\\n case 0x60/* ` */:\\n case 0x7B/* { */:\\n case 0x7C/* | */:\\n case 0x7D/* } */:\\n case 0x7E/* ~ */:\\n return true\\n default:\\n return false\\n }\\n}\\n\\n// Hepler to unify [reference labels].\\n//\\nfunction normalizeReference (str) {\\n // Trim and collapse whitespace\\n //\\n str = str.trim().replace(/\\\\s+/g, ' ')\\n\\n // In node v10 'ẞ'.toLowerCase() === 'Ṿ', which is presumed to be a bug\\n // fixed in v12 (couldn't find any details).\\n //\\n // So treat this one as a special case\\n // (remove this when node v10 is no longer supported).\\n //\\n if ('ẞ'.toLowerCase() === 'Ṿ') {\\n str = str.replace(/ẞ/g, 'ß')\\n }\\n\\n // .toLowerCase().toUpperCase() should get rid of all differences\\n // between letter variants.\\n //\\n // Simple .toLowerCase() doesn't normalize 125 code points correctly,\\n // and .toUpperCase doesn't normalize 6 of them (list of exceptions:\\n // İ, ϴ, ẞ, Ω, K, Å - those are already uppercased, but have differently\\n // uppercased versions).\\n //\\n // Here's an example showing how it happens. Lets take greek letter omega:\\n // uppercase U+0398 (Θ), U+03f4 (ϴ) and lowercase U+03b8 (θ), U+03d1 (ϑ)\\n //\\n // Unicode entries:\\n // 0398;GREEK CAPITAL LETTER THETA;Lu;0;L;;;;;N;;;;03B8;\\n // 03B8;GREEK SMALL LETTER THETA;Ll;0;L;;;;;N;;;0398;;0398\\n // 03D1;GREEK THETA SYMBOL;Ll;0;L; 03B8;;;;N;GREEK SMALL LETTER SCRIPT THETA;;0398;;0398\\n // 03F4;GREEK CAPITAL THETA SYMBOL;Lu;0;L; 0398;;;;N;;;;03B8;\\n //\\n // Case-insensitive comparison should treat all of them as equivalent.\\n //\\n // But .toLowerCase() doesn't change ϑ (it's already lowercase),\\n // and .toUpperCase() doesn't change ϴ (already uppercase).\\n //\\n // Applying first lower then upper case normalizes any character:\\n // '\\\\u0398\\\\u03f4\\\\u03b8\\\\u03d1'.toLowerCase().toUpperCase() === '\\\\u0398\\\\u0398\\\\u0398\\\\u0398'\\n //\\n // Note: this is equivalent to unicode case folding; unicode normalization\\n // is a different step that is not required here.\\n //\\n // Final result should be uppercased, because it's later stored in an object\\n // (this avoid a conflict with Object.prototype members,\\n // most notably, `__proto__`)\\n //\\n return str.toLowerCase().toUpperCase()\\n}\\n\\n// Re-export libraries commonly used in both markdown-it and its plugins,\\n// so plugins won't have to depend on them explicitly, which reduces their\\n// bundled size (e.g. a browser build).\\n//\\nconst lib = { mdurl, ucmicro }\\n\\nexport {\\n lib,\\n assign,\\n isString,\\n has,\\n unescapeMd,\\n unescapeAll,\\n isValidEntityCode,\\n fromCodePoint,\\n escapeHtml,\\n arrayReplaceAt,\\n isSpace,\\n isWhiteSpace,\\n isMdAsciiPunct,\\n isPunctChar,\\n escapeRE,\\n normalizeReference\\n}\\n\",\"import decode from './lib/decode.mjs'\\nimport encode from './lib/encode.mjs'\\nimport format from './lib/format.mjs'\\nimport parse from './lib/parse.mjs'\\n\\nexport {\\n decode,\\n encode,\\n format,\\n parse\\n}\\n\",\"/* eslint-disable no-bitwise */\\n\\nconst decodeCache = {}\\n\\nfunction getDecodeCache (exclude) {\\n let cache = decodeCache[exclude]\\n if (cache) { return cache }\\n\\n cache = decodeCache[exclude] = []\\n\\n for (let i = 0; i < 128; i++) {\\n const ch = String.fromCharCode(i)\\n cache.push(ch)\\n }\\n\\n for (let i = 0; i < exclude.length; i++) {\\n const ch = exclude.charCodeAt(i)\\n cache[ch] = '%' + ('0' + ch.toString(16).toUpperCase()).slice(-2)\\n }\\n\\n return cache\\n}\\n\\n// Decode percent-encoded string.\\n//\\nfunction decode (string, exclude) {\\n if (typeof exclude !== 'string') {\\n exclude = decode.defaultChars\\n }\\n\\n const cache = getDecodeCache(exclude)\\n\\n return string.replace(/(%[a-f0-9]{2})+/gi, function (seq) {\\n let result = ''\\n\\n for (let i = 0, l = seq.length; i < l; i += 3) {\\n const b1 = parseInt(seq.slice(i + 1, i + 3), 16)\\n\\n if (b1 < 0x80) {\\n result += cache[b1]\\n continue\\n }\\n\\n if ((b1 & 0xE0) === 0xC0 && (i + 3 < l)) {\\n // 110xxxxx 10xxxxxx\\n const b2 = parseInt(seq.slice(i + 4, i + 6), 16)\\n\\n if ((b2 & 0xC0) === 0x80) {\\n const chr = ((b1 << 6) & 0x7C0) | (b2 & 0x3F)\\n\\n if (chr < 0x80) {\\n result += '\\\\ufffd\\\\ufffd'\\n } else {\\n result += String.fromCharCode(chr)\\n }\\n\\n i += 3\\n continue\\n }\\n }\\n\\n if ((b1 & 0xF0) === 0xE0 && (i + 6 < l)) {\\n // 1110xxxx 10xxxxxx 10xxxxxx\\n const b2 = parseInt(seq.slice(i + 4, i + 6), 16)\\n const b3 = parseInt(seq.slice(i + 7, i + 9), 16)\\n\\n if ((b2 & 0xC0) === 0x80 && (b3 & 0xC0) === 0x80) {\\n const chr = ((b1 << 12) & 0xF000) | ((b2 << 6) & 0xFC0) | (b3 & 0x3F)\\n\\n if (chr < 0x800 || (chr >= 0xD800 && chr <= 0xDFFF)) {\\n result += '\\\\ufffd\\\\ufffd\\\\ufffd'\\n } else {\\n result += String.fromCharCode(chr)\\n }\\n\\n i += 6\\n continue\\n }\\n }\\n\\n if ((b1 & 0xF8) === 0xF0 && (i + 9 < l)) {\\n // 111110xx 10xxxxxx 10xxxxxx 10xxxxxx\\n const b2 = parseInt(seq.slice(i + 4, i + 6), 16)\\n const b3 = parseInt(seq.slice(i + 7, i + 9), 16)\\n const b4 = parseInt(seq.slice(i + 10, i + 12), 16)\\n\\n if ((b2 & 0xC0) === 0x80 && (b3 & 0xC0) === 0x80 && (b4 & 0xC0) === 0x80) {\\n let chr = ((b1 << 18) & 0x1C0000) | ((b2 << 12) & 0x3F000) | ((b3 << 6) & 0xFC0) | (b4 & 0x3F)\\n\\n if (chr < 0x10000 || chr > 0x10FFFF) {\\n result += '\\\\ufffd\\\\ufffd\\\\ufffd\\\\ufffd'\\n } else {\\n chr -= 0x10000\\n result += String.fromCharCode(0xD800 + (chr >> 10), 0xDC00 + (chr & 0x3FF))\\n }\\n\\n i += 9\\n continue\\n }\\n }\\n\\n result += '\\\\ufffd'\\n }\\n\\n return result\\n })\\n}\\n\\ndecode.defaultChars = ';/?:@&=+$,#'\\ndecode.componentChars = ''\\n\\nexport default decode\\n\",\"const encodeCache = {}\\n\\n// Create a lookup array where anything but characters in `chars` string\\n// and alphanumeric chars is percent-encoded.\\n//\\nfunction getEncodeCache (exclude) {\\n let cache = encodeCache[exclude]\\n if (cache) { return cache }\\n\\n cache = encodeCache[exclude] = []\\n\\n for (let i = 0; i < 128; i++) {\\n const ch = String.fromCharCode(i)\\n\\n if (/^[0-9a-z]$/i.test(ch)) {\\n // always allow unencoded alphanumeric characters\\n cache.push(ch)\\n } else {\\n cache.push('%' + ('0' + i.toString(16).toUpperCase()).slice(-2))\\n }\\n }\\n\\n for (let i = 0; i < exclude.length; i++) {\\n cache[exclude.charCodeAt(i)] = exclude[i]\\n }\\n\\n return cache\\n}\\n\\n// Encode unsafe characters with percent-encoding, skipping already\\n// encoded sequences.\\n//\\n// - string - string to encode\\n// - exclude - list of characters to ignore (in addition to a-zA-Z0-9)\\n// - keepEscaped - don't encode '%' in a correct escape sequence (default: true)\\n//\\nfunction encode (string, exclude, keepEscaped) {\\n if (typeof exclude !== 'string') {\\n // encode(string, keepEscaped)\\n keepEscaped = exclude\\n exclude = encode.defaultChars\\n }\\n\\n if (typeof keepEscaped === 'undefined') {\\n keepEscaped = true\\n }\\n\\n const cache = getEncodeCache(exclude)\\n let result = ''\\n\\n for (let i = 0, l = string.length; i < l; i++) {\\n const code = string.charCodeAt(i)\\n\\n if (keepEscaped && code === 0x25 /* % */ && i + 2 < l) {\\n if (/^[0-9a-f]{2}$/i.test(string.slice(i + 1, i + 3))) {\\n result += string.slice(i, i + 3)\\n i += 2\\n continue\\n }\\n }\\n\\n if (code < 128) {\\n result += cache[code]\\n continue\\n }\\n\\n if (code >= 0xD800 && code <= 0xDFFF) {\\n if (code >= 0xD800 && code <= 0xDBFF && i + 1 < l) {\\n const nextCode = string.charCodeAt(i + 1)\\n if (nextCode >= 0xDC00 && nextCode <= 0xDFFF) {\\n result += encodeURIComponent(string[i] + string[i + 1])\\n i++\\n continue\\n }\\n }\\n result += '%EF%BF%BD'\\n continue\\n }\\n\\n result += encodeURIComponent(string[i])\\n }\\n\\n return result\\n}\\n\\nencode.defaultChars = \\\";/?:@&=+$,-_.!~*'()#\\\"\\nencode.componentChars = \\\"-_.!~*'()\\\"\\n\\nexport default encode\\n\",\"export default function format (url) {\\n let result = ''\\n\\n result += url.protocol || ''\\n result += url.slashes ? '//' : ''\\n result += url.auth ? url.auth + '@' : ''\\n\\n if (url.hostname && url.hostname.indexOf(':') !== -1) {\\n // ipv6 address\\n result += '[' + url.hostname + ']'\\n } else {\\n result += url.hostname || ''\\n }\\n\\n result += url.port ? ':' + url.port : ''\\n result += url.pathname || ''\\n result += url.search || ''\\n result += url.hash || ''\\n\\n return result\\n};\\n\",\"// Copyright Joyent, Inc. and other Node contributors.\\n//\\n// Permission is hereby granted, free of charge, to any person obtaining a\\n// copy of this software and associated documentation files (the\\n// \\\"Software\\\"), to deal in the Software without restriction, including\\n// without limitation the rights to use, copy, modify, merge, publish,\\n// distribute, sublicense, and/or sell copies of the Software, and to permit\\n// persons to whom the Software is furnished to do so, subject to the\\n// following conditions:\\n//\\n// The above copyright notice and this permission notice shall be included\\n// in all copies or substantial portions of the Software.\\n//\\n// THE SOFTWARE IS PROVIDED \\\"AS IS\\\", WITHOUT WARRANTY OF ANY KIND, EXPRESS\\n// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\\n// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN\\n// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,\\n// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR\\n// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE\\n// USE OR OTHER DEALINGS IN THE SOFTWARE.\\n\\n//\\n// Changes from joyent/node:\\n//\\n// 1. No leading slash in paths,\\n// e.g. in `url.parse('http://foo?bar')` pathname is ``, not `/`\\n//\\n// 2. Backslashes are not replaced with slashes,\\n// so `http:\\\\\\\\example.org\\\\` is treated like a relative path\\n//\\n// 3. Trailing colon is treated like a part of the path,\\n// i.e. in `http://example.org:foo` pathname is `:foo`\\n//\\n// 4. Nothing is URL-encoded in the resulting object,\\n// (in joyent/node some chars in auth and paths are encoded)\\n//\\n// 5. `url.parse()` does not have `parseQueryString` argument\\n//\\n// 6. Removed extraneous result properties: `host`, `path`, `query`, etc.,\\n// which can be constructed using other parts of the url.\\n//\\n\\nfunction Url () {\\n this.protocol = null\\n this.slashes = null\\n this.auth = null\\n this.port = null\\n this.hostname = null\\n this.hash = null\\n this.search = null\\n this.pathname = null\\n}\\n\\n// Reference: RFC 3986, RFC 1808, RFC 2396\\n\\n// define these here so at least they only have to be\\n// compiled once on the first module load.\\nconst protocolPattern = /^([a-z0-9.+-]+:)/i\\nconst portPattern = /:[0-9]*$/\\n\\n// Special case for a simple path URL\\n/* eslint-disable-next-line no-useless-escape */\\nconst simplePathPattern = /^(\\\\/\\\\/?(?!\\\\/)[^\\\\?\\\\s]*)(\\\\?[^\\\\s]*)?$/\\n\\n// RFC 2396: characters reserved for delimiting URLs.\\n// We actually just auto-escape these.\\nconst delims = ['<', '>', '\\\"', '`', ' ', '\\\\r', '\\\\n', '\\\\t']\\n\\n// RFC 2396: characters not allowed for various reasons.\\nconst unwise = ['{', '}', '|', '\\\\\\\\', '^', '`'].concat(delims)\\n\\n// Allowed by RFCs, but cause of XSS attacks. Always escape these.\\nconst autoEscape = ['\\\\''].concat(unwise)\\n// Characters that are never ever allowed in a hostname.\\n// Note that any invalid chars are also handled, but these\\n// are the ones that are *expected* to be seen, so we fast-path\\n// them.\\nconst nonHostChars = ['%', '/', '?', ';', '#'].concat(autoEscape)\\nconst hostEndingChars = ['/', '?', '#']\\nconst hostnameMaxLen = 255\\nconst hostnamePartPattern = /^[+a-z0-9A-Z_-]{0,63}$/\\nconst hostnamePartStart = /^([+a-z0-9A-Z_-]{0,63})(.*)$/\\n// protocols that can allow \\\"unsafe\\\" and \\\"unwise\\\" chars.\\n// protocols that never have a hostname.\\nconst hostlessProtocol = {\\n javascript: true,\\n 'javascript:': true\\n}\\n// protocols that always contain a // bit.\\nconst slashedProtocol = {\\n http: true,\\n https: true,\\n ftp: true,\\n gopher: true,\\n file: true,\\n 'http:': true,\\n 'https:': true,\\n 'ftp:': true,\\n 'gopher:': true,\\n 'file:': true\\n}\\n\\nfunction urlParse (url, slashesDenoteHost) {\\n if (url && url instanceof Url) return url\\n\\n const u = new Url()\\n u.parse(url, slashesDenoteHost)\\n return u\\n}\\n\\nUrl.prototype.parse = function (url, slashesDenoteHost) {\\n let lowerProto, hec, slashes\\n let rest = url\\n\\n // trim before proceeding.\\n // This is to support parse stuff like \\\" http://foo.com \\\\n\\\"\\n rest = rest.trim()\\n\\n if (!slashesDenoteHost && url.split('#').length === 1) {\\n // Try fast path regexp\\n const simplePath = simplePathPattern.exec(rest)\\n if (simplePath) {\\n this.pathname = simplePath[1]\\n if (simplePath[2]) {\\n this.search = simplePath[2]\\n }\\n return this\\n }\\n }\\n\\n let proto = protocolPattern.exec(rest)\\n if (proto) {\\n proto = proto[0]\\n lowerProto = proto.toLowerCase()\\n this.protocol = proto\\n rest = rest.substr(proto.length)\\n }\\n\\n // figure out if it's got a host\\n // user@server is *always* interpreted as a hostname, and url\\n // resolution will treat //foo/bar as host=foo,path=bar because that's\\n // how the browser resolves relative URLs.\\n /* eslint-disable-next-line no-useless-escape */\\n if (slashesDenoteHost || proto || rest.match(/^\\\\/\\\\/[^@\\\\/]+@[^@\\\\/]+/)) {\\n slashes = rest.substr(0, 2) === '//'\\n if (slashes && !(proto && hostlessProtocol[proto])) {\\n rest = rest.substr(2)\\n this.slashes = true\\n }\\n }\\n\\n if (!hostlessProtocol[proto] &&\\n (slashes || (proto && !slashedProtocol[proto]))) {\\n // there's a hostname.\\n // the first instance of /, ?, ;, or # ends the host.\\n //\\n // If there is an @ in the hostname, then non-host chars *are* allowed\\n // to the left of the last @ sign, unless some host-ending character\\n // comes *before* the @-sign.\\n // URLs are obnoxious.\\n //\\n // ex:\\n // http://a@b@c/ => user:a@b host:c\\n // http://a@b?@c => user:a host:c path:/?@c\\n\\n // v0.12 TODO(isaacs): This is not quite how Chrome does things.\\n // Review our test case against browsers more comprehensively.\\n\\n // find the first instance of any hostEndingChars\\n let hostEnd = -1\\n for (let i = 0; i < hostEndingChars.length; i++) {\\n hec = rest.indexOf(hostEndingChars[i])\\n if (hec !== -1 && (hostEnd === -1 || hec < hostEnd)) {\\n hostEnd = hec\\n }\\n }\\n\\n // at this point, either we have an explicit point where the\\n // auth portion cannot go past, or the last @ char is the decider.\\n let auth, atSign\\n if (hostEnd === -1) {\\n // atSign can be anywhere.\\n atSign = rest.lastIndexOf('@')\\n } else {\\n // atSign must be in auth portion.\\n // http://a@b/c@d => host:b auth:a path:/c@d\\n atSign = rest.lastIndexOf('@', hostEnd)\\n }\\n\\n // Now we have a portion which is definitely the auth.\\n // Pull that off.\\n if (atSign !== -1) {\\n auth = rest.slice(0, atSign)\\n rest = rest.slice(atSign + 1)\\n this.auth = auth\\n }\\n\\n // the host is the remaining to the left of the first non-host char\\n hostEnd = -1\\n for (let i = 0; i < nonHostChars.length; i++) {\\n hec = rest.indexOf(nonHostChars[i])\\n if (hec !== -1 && (hostEnd === -1 || hec < hostEnd)) {\\n hostEnd = hec\\n }\\n }\\n // if we still have not hit it, then the entire thing is a host.\\n if (hostEnd === -1) {\\n hostEnd = rest.length\\n }\\n\\n if (rest[hostEnd - 1] === ':') { hostEnd-- }\\n const host = rest.slice(0, hostEnd)\\n rest = rest.slice(hostEnd)\\n\\n // pull out port.\\n this.parseHost(host)\\n\\n // we've indicated that there is a hostname,\\n // so even if it's empty, it has to be present.\\n this.hostname = this.hostname || ''\\n\\n // if hostname begins with [ and ends with ]\\n // assume that it's an IPv6 address.\\n const ipv6Hostname = this.hostname[0] === '[' &&\\n this.hostname[this.hostname.length - 1] === ']'\\n\\n // validate a little.\\n if (!ipv6Hostname) {\\n const hostparts = this.hostname.split(/\\\\./)\\n for (let i = 0, l = hostparts.length; i < l; i++) {\\n const part = hostparts[i]\\n if (!part) { continue }\\n if (!part.match(hostnamePartPattern)) {\\n let newpart = ''\\n for (let j = 0, k = part.length; j < k; j++) {\\n if (part.charCodeAt(j) > 127) {\\n // we replace non-ASCII char with a temporary placeholder\\n // we need this to make sure size of hostname is not\\n // broken by replacing non-ASCII by nothing\\n newpart += 'x'\\n } else {\\n newpart += part[j]\\n }\\n }\\n // we test again with ASCII char only\\n if (!newpart.match(hostnamePartPattern)) {\\n const validParts = hostparts.slice(0, i)\\n const notHost = hostparts.slice(i + 1)\\n const bit = part.match(hostnamePartStart)\\n if (bit) {\\n validParts.push(bit[1])\\n notHost.unshift(bit[2])\\n }\\n if (notHost.length) {\\n rest = notHost.join('.') + rest\\n }\\n this.hostname = validParts.join('.')\\n break\\n }\\n }\\n }\\n }\\n\\n if (this.hostname.length > hostnameMaxLen) {\\n this.hostname = ''\\n }\\n\\n // strip [ and ] from the hostname\\n // the host field still retains them, though\\n if (ipv6Hostname) {\\n this.hostname = this.hostname.substr(1, this.hostname.length - 2)\\n }\\n }\\n\\n // chop off from the tail first.\\n const hash = rest.indexOf('#')\\n if (hash !== -1) {\\n // got a fragment string.\\n this.hash = rest.substr(hash)\\n rest = rest.slice(0, hash)\\n }\\n const qm = rest.indexOf('?')\\n if (qm !== -1) {\\n this.search = rest.substr(qm)\\n rest = rest.slice(0, qm)\\n }\\n if (rest) { this.pathname = rest }\\n if (slashedProtocol[lowerProto] &&\\n this.hostname && !this.pathname) {\\n this.pathname = ''\\n }\\n\\n return this\\n}\\n\\nUrl.prototype.parseHost = function (host) {\\n let port = portPattern.exec(host)\\n if (port) {\\n port = port[0]\\n if (port !== ':') {\\n this.port = port.substr(1)\\n }\\n host = host.substr(0, host.length - port.length)\\n }\\n if (host) { this.hostname = host }\\n}\\n\\nexport default urlParse\\n\",null,null,null,null,null,null,null,\"// Just a shortcut for bulk export\\n\\nimport parseLinkLabel from './parse_link_label.mjs'\\nimport parseLinkDestination from './parse_link_destination.mjs'\\nimport parseLinkTitle from './parse_link_title.mjs'\\n\\nexport {\\n parseLinkLabel,\\n parseLinkDestination,\\n parseLinkTitle\\n}\\n\",\"// Parse link label\\n//\\n// this function assumes that first character (\\\"[\\\") already matches;\\n// returns the end of the label\\n//\\n\\nexport default function parseLinkLabel (state, start, disableNested) {\\n let level, found, marker, prevPos\\n\\n const max = state.posMax\\n const oldPos = state.pos\\n\\n state.pos = start + 1\\n level = 1\\n\\n while (state.pos < max) {\\n marker = state.src.charCodeAt(state.pos)\\n if (marker === 0x5D /* ] */) {\\n level--\\n if (level === 0) {\\n found = true\\n break\\n }\\n }\\n\\n prevPos = state.pos\\n state.md.inline.skipToken(state)\\n if (marker === 0x5B /* [ */) {\\n if (prevPos === state.pos - 1) {\\n // increase level if we find text `[`, which is not a part of any token\\n level++\\n } else if (disableNested) {\\n state.pos = oldPos\\n return -1\\n }\\n }\\n }\\n\\n let labelEnd = -1\\n\\n if (found) {\\n labelEnd = state.pos\\n }\\n\\n // restore old state\\n state.pos = oldPos\\n\\n return labelEnd\\n}\\n\",\"// Parse link destination\\n//\\n\\nimport { unescapeAll } from '../common/utils.mjs'\\n\\nexport default function parseLinkDestination (str, start, max) {\\n let code\\n let pos = start\\n\\n const result = {\\n ok: false,\\n pos: 0,\\n str: ''\\n }\\n\\n if (str.charCodeAt(pos) === 0x3C /* < */) {\\n pos++\\n while (pos < max) {\\n code = str.charCodeAt(pos)\\n if (code === 0x0A /* \\\\n */) { return result }\\n if (code === 0x3C /* < */) { return result }\\n if (code === 0x3E /* > */) {\\n result.pos = pos + 1\\n result.str = unescapeAll(str.slice(start + 1, pos))\\n result.ok = true\\n return result\\n }\\n if (code === 0x5C /* \\\\ */ && pos + 1 < max) {\\n pos += 2\\n continue\\n }\\n\\n pos++\\n }\\n\\n // no closing '>'\\n return result\\n }\\n\\n // this should be ... } else { ... branch\\n\\n let level = 0\\n while (pos < max) {\\n code = str.charCodeAt(pos)\\n\\n if (code === 0x20) { break }\\n\\n // ascii control characters\\n if (code < 0x20 || code === 0x7F) { break }\\n\\n if (code === 0x5C /* \\\\ */ && pos + 1 < max) {\\n if (str.charCodeAt(pos + 1) === 0x20) { break }\\n pos += 2\\n continue\\n }\\n\\n if (code === 0x28 /* ( */) {\\n level++\\n if (level > 32) { return result }\\n }\\n\\n if (code === 0x29 /* ) */) {\\n if (level === 0) { break }\\n level--\\n }\\n\\n pos++\\n }\\n\\n if (start === pos) { return result }\\n if (level !== 0) { return result }\\n\\n result.str = unescapeAll(str.slice(start, pos))\\n result.pos = pos\\n result.ok = true\\n return result\\n}\\n\",\"// Parse link title\\n//\\n\\nimport { unescapeAll } from '../common/utils.mjs'\\n\\n// Parse link title within `str` in [start, max] range,\\n// or continue previous parsing if `prev_state` is defined (equal to result of last execution).\\n//\\nexport default function parseLinkTitle (str, start, max, prev_state) {\\n let code\\n let pos = start\\n\\n const state = {\\n // if `true`, this is a valid link title\\n ok: false,\\n // if `true`, this link can be continued on the next line\\n can_continue: false,\\n // if `ok`, it's the position of the first character after the closing marker\\n pos: 0,\\n // if `ok`, it's the unescaped title\\n str: '',\\n // expected closing marker character code\\n marker: 0\\n }\\n\\n if (prev_state) {\\n // this is a continuation of a previous parseLinkTitle call on the next line,\\n // used in reference links only\\n state.str = prev_state.str\\n state.marker = prev_state.marker\\n } else {\\n if (pos >= max) { return state }\\n\\n let marker = str.charCodeAt(pos)\\n if (marker !== 0x22 /* \\\" */ && marker !== 0x27 /* ' */ && marker !== 0x28 /* ( */) { return state }\\n\\n start++\\n pos++\\n\\n // if opening marker is \\\"(\\\", switch it to closing marker \\\")\\\"\\n if (marker === 0x28) { marker = 0x29 }\\n\\n state.marker = marker\\n }\\n\\n while (pos < max) {\\n code = str.charCodeAt(pos)\\n if (code === state.marker) {\\n state.pos = pos + 1\\n state.str += unescapeAll(str.slice(start, pos))\\n state.ok = true\\n return state\\n } else if (code === 0x28 /* ( */ && state.marker === 0x29 /* ) */) {\\n return state\\n } else if (code === 0x5C /* \\\\ */ && pos + 1 < max) {\\n pos++\\n }\\n\\n pos++\\n }\\n\\n // no closing marker found, but this link title may continue on the next line (for references)\\n state.can_continue = true\\n state.str += unescapeAll(str.slice(start, pos))\\n return state\\n}\\n\",\"/**\\n * class Renderer\\n *\\n * Generates HTML from parsed token stream. Each instance has independent\\n * copy of rules. Those can be rewritten with ease. Also, you can add new\\n * rules if you create plugin and adds new token types.\\n **/\\n\\nimport { assign, unescapeAll, escapeHtml } from './common/utils.mjs'\\n\\nconst default_rules = {}\\n\\ndefault_rules.code_inline = function (tokens, idx, options, env, slf) {\\n const token = tokens[idx]\\n\\n return '' +\\n escapeHtml(token.content) +\\n ''\\n}\\n\\ndefault_rules.code_block = function (tokens, idx, options, env, slf) {\\n const token = tokens[idx]\\n\\n return '' +\\n escapeHtml(tokens[idx].content) +\\n '\\\\n'\\n}\\n\\ndefault_rules.fence = function (tokens, idx, options, env, slf) {\\n const token = tokens[idx]\\n const info = token.info ? unescapeAll(token.info).trim() : ''\\n let langName = ''\\n let langAttrs = ''\\n\\n if (info) {\\n const arr = info.split(/(\\\\s+)/g)\\n langName = arr[0]\\n langAttrs = arr.slice(2).join('')\\n }\\n\\n let highlighted\\n if (options.highlight) {\\n highlighted = options.highlight(token.content, langName, langAttrs) || escapeHtml(token.content)\\n } else {\\n highlighted = escapeHtml(token.content)\\n }\\n\\n if (highlighted.indexOf('${highlighted}\\\\n`\\n }\\n\\n return `

${highlighted}
\\\\n`\\n}\\n\\ndefault_rules.image = function (tokens, idx, options, env, slf) {\\n const token = tokens[idx]\\n\\n // \\\"alt\\\" attr MUST be set, even if empty. Because it's mandatory and\\n // should be placed on proper position for tests.\\n //\\n // Replace content with actual value\\n\\n token.attrs[token.attrIndex('alt')][1] =\\n slf.renderInlineAsText(token.children, options, env)\\n\\n return slf.renderToken(tokens, idx, options)\\n}\\n\\ndefault_rules.hardbreak = function (tokens, idx, options /*, env */) {\\n return options.xhtmlOut ? '
\\\\n' : '
\\\\n'\\n}\\ndefault_rules.softbreak = function (tokens, idx, options /*, env */) {\\n return options.breaks ? (options.xhtmlOut ? '
\\\\n' : '
\\\\n') : '\\\\n'\\n}\\n\\ndefault_rules.text = function (tokens, idx /*, options, env */) {\\n return escapeHtml(tokens[idx].content)\\n}\\n\\ndefault_rules.html_block = function (tokens, idx /*, options, env */) {\\n return tokens[idx].content\\n}\\ndefault_rules.html_inline = function (tokens, idx /*, options, env */) {\\n return tokens[idx].content\\n}\\n\\n/**\\n * new Renderer()\\n *\\n * Creates new [[Renderer]] instance and fill [[Renderer#rules]] with defaults.\\n **/\\nfunction Renderer () {\\n /**\\n * Renderer#rules -> Object\\n *\\n * Contains render rules for tokens. Can be updated and extended.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n *\\n * md.renderer.rules.strong_open = function () { return ''; };\\n * md.renderer.rules.strong_close = function () { return ''; };\\n *\\n * var result = md.renderInline(...);\\n * ```\\n *\\n * Each rule is called as independent static function with fixed signature:\\n *\\n * ```javascript\\n * function my_token_render(tokens, idx, options, env, renderer) {\\n * // ...\\n * return renderedHTML;\\n * }\\n * ```\\n *\\n * See [source code](https://github.com/markdown-it/markdown-it/blob/master/lib/renderer.mjs)\\n * for more details and examples.\\n **/\\n this.rules = assign({}, default_rules)\\n}\\n\\n/**\\n * Renderer.renderAttrs(token) -> String\\n *\\n * Render token attributes to string.\\n **/\\nRenderer.prototype.renderAttrs = function renderAttrs (token) {\\n let i, l, result\\n\\n if (!token.attrs) { return '' }\\n\\n result = ''\\n\\n for (i = 0, l = token.attrs.length; i < l; i++) {\\n result += ' ' + escapeHtml(token.attrs[i][0]) + '=\\\"' + escapeHtml(token.attrs[i][1]) + '\\\"'\\n }\\n\\n return result\\n}\\n\\n/**\\n * Renderer.renderToken(tokens, idx, options) -> String\\n * - tokens (Array): list of tokens\\n * - idx (Numbed): token index to render\\n * - options (Object): params of parser instance\\n *\\n * Default token renderer. Can be overriden by custom function\\n * in [[Renderer#rules]].\\n **/\\nRenderer.prototype.renderToken = function renderToken (tokens, idx, options) {\\n const token = tokens[idx]\\n let result = ''\\n\\n // Tight list paragraphs\\n if (token.hidden) {\\n return ''\\n }\\n\\n // Insert a newline between hidden paragraph and subsequent opening\\n // block-level tag.\\n //\\n // For example, here we should insert a newline before blockquote:\\n // - a\\n // >\\n //\\n if (token.block && token.nesting !== -1 && idx && tokens[idx - 1].hidden) {\\n result += '\\\\n'\\n }\\n\\n // Add token name, e.g. ``.\\n //\\n needLf = false\\n }\\n }\\n }\\n }\\n\\n result += needLf ? '>\\\\n' : '>'\\n\\n return result\\n}\\n\\n/**\\n * Renderer.renderInline(tokens, options, env) -> String\\n * - tokens (Array): list on block tokens to render\\n * - options (Object): params of parser instance\\n * - env (Object): additional data from parsed input (references, for example)\\n *\\n * The same as [[Renderer.render]], but for single token of `inline` type.\\n **/\\nRenderer.prototype.renderInline = function (tokens, options, env) {\\n let result = ''\\n const rules = this.rules\\n\\n for (let i = 0, len = tokens.length; i < len; i++) {\\n const type = tokens[i].type\\n\\n if (typeof rules[type] !== 'undefined') {\\n result += rules[type](tokens, i, options, env, this)\\n } else {\\n result += this.renderToken(tokens, i, options)\\n }\\n }\\n\\n return result\\n}\\n\\n/** internal\\n * Renderer.renderInlineAsText(tokens, options, env) -> String\\n * - tokens (Array): list on block tokens to render\\n * - options (Object): params of parser instance\\n * - env (Object): additional data from parsed input (references, for example)\\n *\\n * Special kludge for image `alt` attributes to conform CommonMark spec.\\n * Don't try to use it! Spec requires to show `alt` content with stripped markup,\\n * instead of simple escaping.\\n **/\\nRenderer.prototype.renderInlineAsText = function (tokens, options, env) {\\n let result = ''\\n\\n for (let i = 0, len = tokens.length; i < len; i++) {\\n switch (tokens[i].type) {\\n case 'text':\\n result += tokens[i].content\\n break\\n case 'image':\\n result += this.renderInlineAsText(tokens[i].children, options, env)\\n break\\n case 'html_inline':\\n case 'html_block':\\n result += tokens[i].content\\n break\\n case 'softbreak':\\n case 'hardbreak':\\n result += '\\\\n'\\n break\\n default:\\n // all other tokens are skipped\\n }\\n }\\n\\n return result\\n}\\n\\n/**\\n * Renderer.render(tokens, options, env) -> String\\n * - tokens (Array): list on block tokens to render\\n * - options (Object): params of parser instance\\n * - env (Object): additional data from parsed input (references, for example)\\n *\\n * Takes token stream and generates HTML. Probably, you will never need to call\\n * this method directly.\\n **/\\nRenderer.prototype.render = function (tokens, options, env) {\\n let result = ''\\n const rules = this.rules\\n\\n for (let i = 0, len = tokens.length; i < len; i++) {\\n const type = tokens[i].type\\n\\n if (type === 'inline') {\\n result += this.renderInline(tokens[i].children, options, env)\\n } else if (typeof rules[type] !== 'undefined') {\\n result += rules[type](tokens, i, options, env, this)\\n } else {\\n result += this.renderToken(tokens, i, options, env)\\n }\\n }\\n\\n return result\\n}\\n\\nexport default Renderer\\n\",\"/**\\n * class Ruler\\n *\\n * Helper class, used by [[MarkdownIt#core]], [[MarkdownIt#block]] and\\n * [[MarkdownIt#inline]] to manage sequences of functions (rules):\\n *\\n * - keep rules in defined order\\n * - assign the name to each rule\\n * - enable/disable rules\\n * - add/replace rules\\n * - allow assign rules to additional named chains (in the same)\\n * - cacheing lists of active rules\\n *\\n * You will not need use this class directly until write plugins. For simple\\n * rules control use [[MarkdownIt.disable]], [[MarkdownIt.enable]] and\\n * [[MarkdownIt.use]].\\n **/\\n\\n/**\\n * new Ruler()\\n **/\\nfunction Ruler () {\\n // List of added rules. Each element is:\\n //\\n // {\\n // name: XXX,\\n // enabled: Boolean,\\n // fn: Function(),\\n // alt: [ name2, name3 ]\\n // }\\n //\\n this.__rules__ = []\\n\\n // Cached rule chains.\\n //\\n // First level - chain name, '' for default.\\n // Second level - diginal anchor for fast filtering by charcodes.\\n //\\n this.__cache__ = null\\n}\\n\\n// Helper methods, should not be used directly\\n\\n// Find rule index by name\\n//\\nRuler.prototype.__find__ = function (name) {\\n for (let i = 0; i < this.__rules__.length; i++) {\\n if (this.__rules__[i].name === name) {\\n return i\\n }\\n }\\n return -1\\n}\\n\\n// Build rules lookup cache\\n//\\nRuler.prototype.__compile__ = function () {\\n const self = this\\n const chains = ['']\\n\\n // collect unique names\\n self.__rules__.forEach(function (rule) {\\n if (!rule.enabled) { return }\\n\\n rule.alt.forEach(function (altName) {\\n if (chains.indexOf(altName) < 0) {\\n chains.push(altName)\\n }\\n })\\n })\\n\\n self.__cache__ = {}\\n\\n chains.forEach(function (chain) {\\n self.__cache__[chain] = []\\n self.__rules__.forEach(function (rule) {\\n if (!rule.enabled) { return }\\n\\n if (chain && rule.alt.indexOf(chain) < 0) { return }\\n\\n self.__cache__[chain].push(rule.fn)\\n })\\n })\\n}\\n\\n/**\\n * Ruler.at(name, fn [, options])\\n * - name (String): rule name to replace.\\n * - fn (Function): new rule function.\\n * - options (Object): new rule options (not mandatory).\\n *\\n * Replace rule by name with new function & options. Throws error if name not\\n * found.\\n *\\n * ##### Options:\\n *\\n * - __alt__ - array with names of \\\"alternate\\\" chains.\\n *\\n * ##### Example\\n *\\n * Replace existing typographer replacement rule with new one:\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n *\\n * md.core.ruler.at('replacements', function replace(state) {\\n * //...\\n * });\\n * ```\\n **/\\nRuler.prototype.at = function (name, fn, options) {\\n const index = this.__find__(name)\\n const opt = options || {}\\n\\n if (index === -1) { throw new Error('Parser rule not found: ' + name) }\\n\\n this.__rules__[index].fn = fn\\n this.__rules__[index].alt = opt.alt || []\\n this.__cache__ = null\\n}\\n\\n/**\\n * Ruler.before(beforeName, ruleName, fn [, options])\\n * - beforeName (String): new rule will be added before this one.\\n * - ruleName (String): name of added rule.\\n * - fn (Function): rule function.\\n * - options (Object): rule options (not mandatory).\\n *\\n * Add new rule to chain before one with given name. See also\\n * [[Ruler.after]], [[Ruler.push]].\\n *\\n * ##### Options:\\n *\\n * - __alt__ - array with names of \\\"alternate\\\" chains.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n *\\n * md.block.ruler.before('paragraph', 'my_rule', function replace(state) {\\n * //...\\n * });\\n * ```\\n **/\\nRuler.prototype.before = function (beforeName, ruleName, fn, options) {\\n const index = this.__find__(beforeName)\\n const opt = options || {}\\n\\n if (index === -1) { throw new Error('Parser rule not found: ' + beforeName) }\\n\\n this.__rules__.splice(index, 0, {\\n name: ruleName,\\n enabled: true,\\n fn,\\n alt: opt.alt || []\\n })\\n\\n this.__cache__ = null\\n}\\n\\n/**\\n * Ruler.after(afterName, ruleName, fn [, options])\\n * - afterName (String): new rule will be added after this one.\\n * - ruleName (String): name of added rule.\\n * - fn (Function): rule function.\\n * - options (Object): rule options (not mandatory).\\n *\\n * Add new rule to chain after one with given name. See also\\n * [[Ruler.before]], [[Ruler.push]].\\n *\\n * ##### Options:\\n *\\n * - __alt__ - array with names of \\\"alternate\\\" chains.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n *\\n * md.inline.ruler.after('text', 'my_rule', function replace(state) {\\n * //...\\n * });\\n * ```\\n **/\\nRuler.prototype.after = function (afterName, ruleName, fn, options) {\\n const index = this.__find__(afterName)\\n const opt = options || {}\\n\\n if (index === -1) { throw new Error('Parser rule not found: ' + afterName) }\\n\\n this.__rules__.splice(index + 1, 0, {\\n name: ruleName,\\n enabled: true,\\n fn,\\n alt: opt.alt || []\\n })\\n\\n this.__cache__ = null\\n}\\n\\n/**\\n * Ruler.push(ruleName, fn [, options])\\n * - ruleName (String): name of added rule.\\n * - fn (Function): rule function.\\n * - options (Object): rule options (not mandatory).\\n *\\n * Push new rule to the end of chain. See also\\n * [[Ruler.before]], [[Ruler.after]].\\n *\\n * ##### Options:\\n *\\n * - __alt__ - array with names of \\\"alternate\\\" chains.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n *\\n * md.core.ruler.push('my_rule', function replace(state) {\\n * //...\\n * });\\n * ```\\n **/\\nRuler.prototype.push = function (ruleName, fn, options) {\\n const opt = options || {}\\n\\n this.__rules__.push({\\n name: ruleName,\\n enabled: true,\\n fn,\\n alt: opt.alt || []\\n })\\n\\n this.__cache__ = null\\n}\\n\\n/**\\n * Ruler.enable(list [, ignoreInvalid]) -> Array\\n * - list (String|Array): list of rule names to enable.\\n * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found.\\n *\\n * Enable rules with given names. If any rule name not found - throw Error.\\n * Errors can be disabled by second param.\\n *\\n * Returns list of found rule names (if no exception happened).\\n *\\n * See also [[Ruler.disable]], [[Ruler.enableOnly]].\\n **/\\nRuler.prototype.enable = function (list, ignoreInvalid) {\\n if (!Array.isArray(list)) { list = [list] }\\n\\n const result = []\\n\\n // Search by name and enable\\n list.forEach(function (name) {\\n const idx = this.__find__(name)\\n\\n if (idx < 0) {\\n if (ignoreInvalid) { return }\\n throw new Error('Rules manager: invalid rule name ' + name)\\n }\\n this.__rules__[idx].enabled = true\\n result.push(name)\\n }, this)\\n\\n this.__cache__ = null\\n return result\\n}\\n\\n/**\\n * Ruler.enableOnly(list [, ignoreInvalid])\\n * - list (String|Array): list of rule names to enable (whitelist).\\n * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found.\\n *\\n * Enable rules with given names, and disable everything else. If any rule name\\n * not found - throw Error. Errors can be disabled by second param.\\n *\\n * See also [[Ruler.disable]], [[Ruler.enable]].\\n **/\\nRuler.prototype.enableOnly = function (list, ignoreInvalid) {\\n if (!Array.isArray(list)) { list = [list] }\\n\\n this.__rules__.forEach(function (rule) { rule.enabled = false })\\n\\n this.enable(list, ignoreInvalid)\\n}\\n\\n/**\\n * Ruler.disable(list [, ignoreInvalid]) -> Array\\n * - list (String|Array): list of rule names to disable.\\n * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found.\\n *\\n * Disable rules with given names. If any rule name not found - throw Error.\\n * Errors can be disabled by second param.\\n *\\n * Returns list of found rule names (if no exception happened).\\n *\\n * See also [[Ruler.enable]], [[Ruler.enableOnly]].\\n **/\\nRuler.prototype.disable = function (list, ignoreInvalid) {\\n if (!Array.isArray(list)) { list = [list] }\\n\\n const result = []\\n\\n // Search by name and disable\\n list.forEach(function (name) {\\n const idx = this.__find__(name)\\n\\n if (idx < 0) {\\n if (ignoreInvalid) { return }\\n throw new Error('Rules manager: invalid rule name ' + name)\\n }\\n this.__rules__[idx].enabled = false\\n result.push(name)\\n }, this)\\n\\n this.__cache__ = null\\n return result\\n}\\n\\n/**\\n * Ruler.getRules(chainName) -> Array\\n *\\n * Return array of active functions (rules) for given chain name. It analyzes\\n * rules configuration, compiles caches if not exists and returns result.\\n *\\n * Default chain name is `''` (empty string). It can't be skipped. That's\\n * done intentionally, to keep signature monomorphic for high speed.\\n **/\\nRuler.prototype.getRules = function (chainName) {\\n if (this.__cache__ === null) {\\n this.__compile__()\\n }\\n\\n // Chain can be empty, if rules disabled. But we still have to return Array.\\n return this.__cache__[chainName] || []\\n}\\n\\nexport default Ruler\\n\",\"// Token class\\n\\n/**\\n * class Token\\n **/\\n\\n/**\\n * new Token(type, tag, nesting)\\n *\\n * Create new token and fill passed properties.\\n **/\\nfunction Token (type, tag, nesting) {\\n /**\\n * Token#type -> String\\n *\\n * Type of the token (string, e.g. \\\"paragraph_open\\\")\\n **/\\n this.type = type\\n\\n /**\\n * Token#tag -> String\\n *\\n * html tag name, e.g. \\\"p\\\"\\n **/\\n this.tag = tag\\n\\n /**\\n * Token#attrs -> Array\\n *\\n * Html attributes. Format: `[ [ name1, value1 ], [ name2, value2 ] ]`\\n **/\\n this.attrs = null\\n\\n /**\\n * Token#map -> Array\\n *\\n * Source map info. Format: `[ line_begin, line_end ]`\\n **/\\n this.map = null\\n\\n /**\\n * Token#nesting -> Number\\n *\\n * Level change (number in {-1, 0, 1} set), where:\\n *\\n * - `1` means the tag is opening\\n * - `0` means the tag is self-closing\\n * - `-1` means the tag is closing\\n **/\\n this.nesting = nesting\\n\\n /**\\n * Token#level -> Number\\n *\\n * nesting level, the same as `state.level`\\n **/\\n this.level = 0\\n\\n /**\\n * Token#children -> Array\\n *\\n * An array of child nodes (inline and img tokens)\\n **/\\n this.children = null\\n\\n /**\\n * Token#content -> String\\n *\\n * In a case of self-closing tag (code, html, fence, etc.),\\n * it has contents of this tag.\\n **/\\n this.content = ''\\n\\n /**\\n * Token#markup -> String\\n *\\n * '*' or '_' for emphasis, fence string for fence, etc.\\n **/\\n this.markup = ''\\n\\n /**\\n * Token#info -> String\\n *\\n * Additional information:\\n *\\n * - Info string for \\\"fence\\\" tokens\\n * - The value \\\"auto\\\" for autolink \\\"link_open\\\" and \\\"link_close\\\" tokens\\n * - The string value of the item marker for ordered-list \\\"list_item_open\\\" tokens\\n **/\\n this.info = ''\\n\\n /**\\n * Token#meta -> Object\\n *\\n * A place for plugins to store an arbitrary data\\n **/\\n this.meta = null\\n\\n /**\\n * Token#block -> Boolean\\n *\\n * True for block-level tokens, false for inline tokens.\\n * Used in renderer to calculate line breaks\\n **/\\n this.block = false\\n\\n /**\\n * Token#hidden -> Boolean\\n *\\n * If it's true, ignore this element when rendering. Used for tight lists\\n * to hide paragraphs.\\n **/\\n this.hidden = false\\n}\\n\\n/**\\n * Token.attrIndex(name) -> Number\\n *\\n * Search attribute index by name.\\n **/\\nToken.prototype.attrIndex = function attrIndex (name) {\\n if (!this.attrs) { return -1 }\\n\\n const attrs = this.attrs\\n\\n for (let i = 0, len = attrs.length; i < len; i++) {\\n if (attrs[i][0] === name) { return i }\\n }\\n return -1\\n}\\n\\n/**\\n * Token.attrPush(attrData)\\n *\\n * Add `[ name, value ]` attribute to list. Init attrs if necessary\\n **/\\nToken.prototype.attrPush = function attrPush (attrData) {\\n if (this.attrs) {\\n this.attrs.push(attrData)\\n } else {\\n this.attrs = [attrData]\\n }\\n}\\n\\n/**\\n * Token.attrSet(name, value)\\n *\\n * Set `name` attribute to `value`. Override old value if exists.\\n **/\\nToken.prototype.attrSet = function attrSet (name, value) {\\n const idx = this.attrIndex(name)\\n const attrData = [name, value]\\n\\n if (idx < 0) {\\n this.attrPush(attrData)\\n } else {\\n this.attrs[idx] = attrData\\n }\\n}\\n\\n/**\\n * Token.attrGet(name)\\n *\\n * Get the value of attribute `name`, or null if it does not exist.\\n **/\\nToken.prototype.attrGet = function attrGet (name) {\\n const idx = this.attrIndex(name)\\n let value = null\\n if (idx >= 0) {\\n value = this.attrs[idx][1]\\n }\\n return value\\n}\\n\\n/**\\n * Token.attrJoin(name, value)\\n *\\n * Join value to existing attribute via space. Or create new attribute if not\\n * exists. Useful to operate with token classes.\\n **/\\nToken.prototype.attrJoin = function attrJoin (name, value) {\\n const idx = this.attrIndex(name)\\n\\n if (idx < 0) {\\n this.attrPush([name, value])\\n } else {\\n this.attrs[idx][1] = this.attrs[idx][1] + ' ' + value\\n }\\n}\\n\\nexport default Token\\n\",\"// Core state object\\n//\\n\\nimport Token from '../token.mjs'\\n\\nfunction StateCore (src, md, env) {\\n this.src = src\\n this.env = env\\n this.tokens = []\\n this.inlineMode = false\\n this.md = md // link to parser instance\\n}\\n\\n// re-export Token class to use in core rules\\nStateCore.prototype.Token = Token\\n\\nexport default StateCore\\n\",\"// Normalize input string\\n\\n// https://spec.commonmark.org/0.29/#line-ending\\nconst NEWLINES_RE = /\\\\r\\\\n?|\\\\n/g\\nconst NULL_RE = /\\\\0/g\\n\\nexport default function normalize (state) {\\n let str\\n\\n // Normalize newlines\\n str = state.src.replace(NEWLINES_RE, '\\\\n')\\n\\n // Replace NULL characters\\n str = str.replace(NULL_RE, '\\\\uFFFD')\\n\\n state.src = str\\n}\\n\",\"export default function block (state) {\\n let token\\n\\n if (state.inlineMode) {\\n token = new state.Token('inline', '', 0)\\n token.content = state.src\\n token.map = [0, 1]\\n token.children = []\\n state.tokens.push(token)\\n } else {\\n state.md.block.parse(state.src, state.md, state.env, state.tokens)\\n }\\n}\\n\",\"export default function inline (state) {\\n const tokens = state.tokens\\n\\n // Parse inlines\\n for (let i = 0, l = tokens.length; i < l; i++) {\\n const tok = tokens[i]\\n if (tok.type === 'inline') {\\n state.md.inline.parse(tok.content, state.md, state.env, tok.children)\\n }\\n }\\n}\\n\",\"// Replace link-like texts with link nodes.\\n//\\n// Currently restricted by `md.validateLink()` to http/https/ftp\\n//\\n\\nimport { arrayReplaceAt } from '../common/utils.mjs'\\n\\nfunction isLinkOpen (str) {\\n return /^\\\\s]/i.test(str)\\n}\\nfunction isLinkClose (str) {\\n return /^<\\\\/a\\\\s*>/i.test(str)\\n}\\n\\nexport default function linkify (state) {\\n const blockTokens = state.tokens\\n\\n if (!state.md.options.linkify) { return }\\n\\n for (let j = 0, l = blockTokens.length; j < l; j++) {\\n if (blockTokens[j].type !== 'inline' ||\\n !state.md.linkify.pretest(blockTokens[j].content)) {\\n continue\\n }\\n\\n let tokens = blockTokens[j].children\\n\\n let htmlLinkLevel = 0\\n\\n // We scan from the end, to keep position when new tags added.\\n // Use reversed logic in links start/end match\\n for (let i = tokens.length - 1; i >= 0; i--) {\\n const currentToken = tokens[i]\\n\\n // Skip content of markdown links\\n if (currentToken.type === 'link_close') {\\n i--\\n while (tokens[i].level !== currentToken.level && tokens[i].type !== 'link_open') {\\n i--\\n }\\n continue\\n }\\n\\n // Skip content of html tag links\\n if (currentToken.type === 'html_inline') {\\n if (isLinkOpen(currentToken.content) && htmlLinkLevel > 0) {\\n htmlLinkLevel--\\n }\\n if (isLinkClose(currentToken.content)) {\\n htmlLinkLevel++\\n }\\n }\\n if (htmlLinkLevel > 0) { continue }\\n\\n if (currentToken.type === 'text' && state.md.linkify.test(currentToken.content)) {\\n const text = currentToken.content\\n let links = state.md.linkify.match(text)\\n\\n // Now split string to nodes\\n const nodes = []\\n let level = currentToken.level\\n let lastPos = 0\\n\\n // forbid escape sequence at the start of the string,\\n // this avoids http\\\\://example.com/ from being linkified as\\n // http:
//example.com/\\n if (links.length > 0 &&\\n links[0].index === 0 &&\\n i > 0 &&\\n tokens[i - 1].type === 'text_special') {\\n links = links.slice(1)\\n }\\n\\n for (let ln = 0; ln < links.length; ln++) {\\n const url = links[ln].url\\n const fullUrl = state.md.normalizeLink(url)\\n if (!state.md.validateLink(fullUrl)) { continue }\\n\\n let urlText = links[ln].text\\n\\n // Linkifier might send raw hostnames like \\\"example.com\\\", where url\\n // starts with domain name. So we prepend http:// in those cases,\\n // and remove it afterwards.\\n //\\n if (!links[ln].schema) {\\n urlText = state.md.normalizeLinkText('http://' + urlText).replace(/^http:\\\\/\\\\//, '')\\n } else if (links[ln].schema === 'mailto:' && !/^mailto:/i.test(urlText)) {\\n urlText = state.md.normalizeLinkText('mailto:' + urlText).replace(/^mailto:/, '')\\n } else {\\n urlText = state.md.normalizeLinkText(urlText)\\n }\\n\\n const pos = links[ln].index\\n\\n if (pos > lastPos) {\\n const token = new state.Token('text', '', 0)\\n token.content = text.slice(lastPos, pos)\\n token.level = level\\n nodes.push(token)\\n }\\n\\n const token_o = new state.Token('link_open', 'a', 1)\\n token_o.attrs = [['href', fullUrl]]\\n token_o.level = level++\\n token_o.markup = 'linkify'\\n token_o.info = 'auto'\\n nodes.push(token_o)\\n\\n const token_t = new state.Token('text', '', 0)\\n token_t.content = urlText\\n token_t.level = level\\n nodes.push(token_t)\\n\\n const token_c = new state.Token('link_close', 'a', -1)\\n token_c.level = --level\\n token_c.markup = 'linkify'\\n token_c.info = 'auto'\\n nodes.push(token_c)\\n\\n lastPos = links[ln].lastIndex\\n }\\n if (lastPos < text.length) {\\n const token = new state.Token('text', '', 0)\\n token.content = text.slice(lastPos)\\n token.level = level\\n nodes.push(token)\\n }\\n\\n // replace current node\\n blockTokens[j].children = tokens = arrayReplaceAt(tokens, i, nodes)\\n }\\n }\\n }\\n}\\n\",\"// Simple typographic replacements\\n//\\n// (c) (C) → ©\\n// (tm) (TM) → ™\\n// (r) (R) → ®\\n// +- → ±\\n// ... → … (also ?.... → ?.., !.... → !..)\\n// ???????? → ???, !!!!! → !!!, `,,` → `,`\\n// -- → –, --- → —\\n//\\n\\n// TODO:\\n// - fractionals 1/2, 1/4, 3/4 -> ½, ¼, ¾\\n// - multiplications 2 x 4 -> 2 × 4\\n\\nconst RARE_RE = /\\\\+-|\\\\.\\\\.|\\\\?\\\\?\\\\?\\\\?|!!!!|,,|--/\\n\\n// Workaround for phantomjs - need regex without /g flag,\\n// or root check will fail every second time\\nconst SCOPED_ABBR_TEST_RE = /\\\\((c|tm|r)\\\\)/i\\n\\nconst SCOPED_ABBR_RE = /\\\\((c|tm|r)\\\\)/ig\\nconst SCOPED_ABBR = {\\n c: '©',\\n r: '®',\\n tm: '™'\\n}\\n\\nfunction replaceFn (match, name) {\\n return SCOPED_ABBR[name.toLowerCase()]\\n}\\n\\nfunction replace_scoped (inlineTokens) {\\n let inside_autolink = 0\\n\\n for (let i = inlineTokens.length - 1; i >= 0; i--) {\\n const token = inlineTokens[i]\\n\\n if (token.type === 'text' && !inside_autolink) {\\n token.content = token.content.replace(SCOPED_ABBR_RE, replaceFn)\\n }\\n\\n if (token.type === 'link_open' && token.info === 'auto') {\\n inside_autolink--\\n }\\n\\n if (token.type === 'link_close' && token.info === 'auto') {\\n inside_autolink++\\n }\\n }\\n}\\n\\nfunction replace_rare (inlineTokens) {\\n let inside_autolink = 0\\n\\n for (let i = inlineTokens.length - 1; i >= 0; i--) {\\n const token = inlineTokens[i]\\n\\n if (token.type === 'text' && !inside_autolink) {\\n if (RARE_RE.test(token.content)) {\\n token.content = token.content\\n .replace(/\\\\+-/g, '±')\\n // .., ..., ....... -> …\\n // but ?..... & !..... -> ?.. & !..\\n .replace(/\\\\.{2,}/g, '…').replace(/([?!])…/g, '$1..')\\n .replace(/([?!]){4,}/g, '$1$1$1').replace(/,{2,}/g, ',')\\n // em-dash\\n .replace(/(^|[^-])---(?=[^-]|$)/mg, '$1\\\\u2014')\\n // en-dash\\n .replace(/(^|\\\\s)--(?=\\\\s|$)/mg, '$1\\\\u2013')\\n .replace(/(^|[^-\\\\s])--(?=[^-\\\\s]|$)/mg, '$1\\\\u2013')\\n }\\n }\\n\\n if (token.type === 'link_open' && token.info === 'auto') {\\n inside_autolink--\\n }\\n\\n if (token.type === 'link_close' && token.info === 'auto') {\\n inside_autolink++\\n }\\n }\\n}\\n\\nexport default function replace (state) {\\n let blkIdx\\n\\n if (!state.md.options.typographer) { return }\\n\\n for (blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) {\\n if (state.tokens[blkIdx].type !== 'inline') { continue }\\n\\n if (SCOPED_ABBR_TEST_RE.test(state.tokens[blkIdx].content)) {\\n replace_scoped(state.tokens[blkIdx].children)\\n }\\n\\n if (RARE_RE.test(state.tokens[blkIdx].content)) {\\n replace_rare(state.tokens[blkIdx].children)\\n }\\n }\\n}\\n\",\"// Convert straight quotation marks to typographic ones\\n//\\n\\nimport { isWhiteSpace, isPunctChar, isMdAsciiPunct } from '../common/utils.mjs'\\n\\nconst QUOTE_TEST_RE = /['\\\"]/\\nconst QUOTE_RE = /['\\\"]/g\\nconst APOSTROPHE = '\\\\u2019' /* ’ */\\n\\nfunction replaceAt (str, index, ch) {\\n return str.slice(0, index) + ch + str.slice(index + 1)\\n}\\n\\nfunction process_inlines (tokens, state) {\\n let j\\n\\n const stack = []\\n\\n for (let i = 0; i < tokens.length; i++) {\\n const token = tokens[i]\\n\\n const thisLevel = tokens[i].level\\n\\n for (j = stack.length - 1; j >= 0; j--) {\\n if (stack[j].level <= thisLevel) { break }\\n }\\n stack.length = j + 1\\n\\n if (token.type !== 'text') { continue }\\n\\n let text = token.content\\n let pos = 0\\n let max = text.length\\n\\n /* eslint no-labels:0,block-scoped-var:0 */\\n OUTER:\\n while (pos < max) {\\n QUOTE_RE.lastIndex = pos\\n const t = QUOTE_RE.exec(text)\\n if (!t) { break }\\n\\n let canOpen = true\\n let canClose = true\\n pos = t.index + 1\\n const isSingle = (t[0] === \\\"'\\\")\\n\\n // Find previous character,\\n // default to space if it's the beginning of the line\\n //\\n let lastChar = 0x20\\n\\n if (t.index - 1 >= 0) {\\n lastChar = text.charCodeAt(t.index - 1)\\n } else {\\n for (j = i - 1; j >= 0; j--) {\\n if (tokens[j].type === 'softbreak' || tokens[j].type === 'hardbreak') break // lastChar defaults to 0x20\\n if (!tokens[j].content) continue // should skip all tokens except 'text', 'html_inline' or 'code_inline'\\n\\n lastChar = tokens[j].content.charCodeAt(tokens[j].content.length - 1)\\n break\\n }\\n }\\n\\n // Find next character,\\n // default to space if it's the end of the line\\n //\\n let nextChar = 0x20\\n\\n if (pos < max) {\\n nextChar = text.charCodeAt(pos)\\n } else {\\n for (j = i + 1; j < tokens.length; j++) {\\n if (tokens[j].type === 'softbreak' || tokens[j].type === 'hardbreak') break // nextChar defaults to 0x20\\n if (!tokens[j].content) continue // should skip all tokens except 'text', 'html_inline' or 'code_inline'\\n\\n nextChar = tokens[j].content.charCodeAt(0)\\n break\\n }\\n }\\n\\n const isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar))\\n const isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar))\\n\\n const isLastWhiteSpace = isWhiteSpace(lastChar)\\n const isNextWhiteSpace = isWhiteSpace(nextChar)\\n\\n if (isNextWhiteSpace) {\\n canOpen = false\\n } else if (isNextPunctChar) {\\n if (!(isLastWhiteSpace || isLastPunctChar)) {\\n canOpen = false\\n }\\n }\\n\\n if (isLastWhiteSpace) {\\n canClose = false\\n } else if (isLastPunctChar) {\\n if (!(isNextWhiteSpace || isNextPunctChar)) {\\n canClose = false\\n }\\n }\\n\\n if (nextChar === 0x22 /* \\\" */ && t[0] === '\\\"') {\\n if (lastChar >= 0x30 /* 0 */ && lastChar <= 0x39 /* 9 */) {\\n // special case: 1\\\"\\\" - count first quote as an inch\\n canClose = canOpen = false\\n }\\n }\\n\\n if (canOpen && canClose) {\\n // Replace quotes in the middle of punctuation sequence, but not\\n // in the middle of the words, i.e.:\\n //\\n // 1. foo \\\" bar \\\" baz - not replaced\\n // 2. foo-\\\"-bar-\\\"-baz - replaced\\n // 3. foo\\\"bar\\\"baz - not replaced\\n //\\n canOpen = isLastPunctChar\\n canClose = isNextPunctChar\\n }\\n\\n if (!canOpen && !canClose) {\\n // middle of word\\n if (isSingle) {\\n token.content = replaceAt(token.content, t.index, APOSTROPHE)\\n }\\n continue\\n }\\n\\n if (canClose) {\\n // this could be a closing quote, rewind the stack to get a match\\n for (j = stack.length - 1; j >= 0; j--) {\\n let item = stack[j]\\n if (stack[j].level < thisLevel) { break }\\n if (item.single === isSingle && stack[j].level === thisLevel) {\\n item = stack[j]\\n\\n let openQuote\\n let closeQuote\\n if (isSingle) {\\n openQuote = state.md.options.quotes[2]\\n closeQuote = state.md.options.quotes[3]\\n } else {\\n openQuote = state.md.options.quotes[0]\\n closeQuote = state.md.options.quotes[1]\\n }\\n\\n // replace token.content *before* tokens[item.token].content,\\n // because, if they are pointing at the same token, replaceAt\\n // could mess up indices when quote length != 1\\n token.content = replaceAt(token.content, t.index, closeQuote)\\n tokens[item.token].content = replaceAt(\\n tokens[item.token].content, item.pos, openQuote)\\n\\n pos += closeQuote.length - 1\\n if (item.token === i) { pos += openQuote.length - 1 }\\n\\n text = token.content\\n max = text.length\\n\\n stack.length = j\\n continue OUTER\\n }\\n }\\n }\\n\\n if (canOpen) {\\n stack.push({\\n token: i,\\n pos: t.index,\\n single: isSingle,\\n level: thisLevel\\n })\\n } else if (canClose && isSingle) {\\n token.content = replaceAt(token.content, t.index, APOSTROPHE)\\n }\\n }\\n }\\n}\\n\\nexport default function smartquotes (state) {\\n /* eslint max-depth:0 */\\n if (!state.md.options.typographer) { return }\\n\\n for (let blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) {\\n if (state.tokens[blkIdx].type !== 'inline' ||\\n !QUOTE_TEST_RE.test(state.tokens[blkIdx].content)) {\\n continue\\n }\\n\\n process_inlines(state.tokens[blkIdx].children, state)\\n }\\n}\\n\",\"// Join raw text tokens with the rest of the text\\n//\\n// This is set as a separate rule to provide an opportunity for plugins\\n// to run text replacements after text join, but before escape join.\\n//\\n// For example, `\\\\:)` shouldn't be replaced with an emoji.\\n//\\n\\nexport default function text_join (state) {\\n let curr, last\\n const blockTokens = state.tokens\\n const l = blockTokens.length\\n\\n for (let j = 0; j < l; j++) {\\n if (blockTokens[j].type !== 'inline') continue\\n\\n const tokens = blockTokens[j].children\\n const max = tokens.length\\n\\n for (curr = 0; curr < max; curr++) {\\n if (tokens[curr].type === 'text_special') {\\n tokens[curr].type = 'text'\\n }\\n }\\n\\n for (curr = last = 0; curr < max; curr++) {\\n if (tokens[curr].type === 'text' &&\\n curr + 1 < max &&\\n tokens[curr + 1].type === 'text') {\\n // collapse two adjacent text nodes\\n tokens[curr + 1].content = tokens[curr].content + tokens[curr + 1].content\\n } else {\\n if (curr !== last) { tokens[last] = tokens[curr] }\\n\\n last++\\n }\\n }\\n\\n if (curr !== last) {\\n tokens.length = last\\n }\\n }\\n}\\n\",\"/** internal\\n * class Core\\n *\\n * Top-level rules executor. Glues block/inline parsers and does intermediate\\n * transformations.\\n **/\\n\\nimport Ruler from './ruler.mjs'\\nimport StateCore from './rules_core/state_core.mjs'\\n\\nimport r_normalize from './rules_core/normalize.mjs'\\nimport r_block from './rules_core/block.mjs'\\nimport r_inline from './rules_core/inline.mjs'\\nimport r_linkify from './rules_core/linkify.mjs'\\nimport r_replacements from './rules_core/replacements.mjs'\\nimport r_smartquotes from './rules_core/smartquotes.mjs'\\nimport r_text_join from './rules_core/text_join.mjs'\\n\\nconst _rules = [\\n ['normalize', r_normalize],\\n ['block', r_block],\\n ['inline', r_inline],\\n ['linkify', r_linkify],\\n ['replacements', r_replacements],\\n ['smartquotes', r_smartquotes],\\n // `text_join` finds `text_special` tokens (for escape sequences)\\n // and joins them with the rest of the text\\n ['text_join', r_text_join]\\n]\\n\\n/**\\n * new Core()\\n **/\\nfunction Core () {\\n /**\\n * Core#ruler -> Ruler\\n *\\n * [[Ruler]] instance. Keep configuration of core rules.\\n **/\\n this.ruler = new Ruler()\\n\\n for (let i = 0; i < _rules.length; i++) {\\n this.ruler.push(_rules[i][0], _rules[i][1])\\n }\\n}\\n\\n/**\\n * Core.process(state)\\n *\\n * Executes core chain rules.\\n **/\\nCore.prototype.process = function (state) {\\n const rules = this.ruler.getRules('')\\n\\n for (let i = 0, l = rules.length; i < l; i++) {\\n rules[i](state)\\n }\\n}\\n\\nCore.prototype.State = StateCore\\n\\nexport default Core\\n\",\"// Parser state class\\n\\nimport Token from '../token.mjs'\\nimport { isSpace } from '../common/utils.mjs'\\n\\nfunction StateBlock (src, md, env, tokens) {\\n this.src = src\\n\\n // link to parser instance\\n this.md = md\\n\\n this.env = env\\n\\n //\\n // Internal state vartiables\\n //\\n\\n this.tokens = tokens\\n\\n this.bMarks = [] // line begin offsets for fast jumps\\n this.eMarks = [] // line end offsets for fast jumps\\n this.tShift = [] // offsets of the first non-space characters (tabs not expanded)\\n this.sCount = [] // indents for each line (tabs expanded)\\n\\n // An amount of virtual spaces (tabs expanded) between beginning\\n // of each line (bMarks) and real beginning of that line.\\n //\\n // It exists only as a hack because blockquotes override bMarks\\n // losing information in the process.\\n //\\n // It's used only when expanding tabs, you can think about it as\\n // an initial tab length, e.g. bsCount=21 applied to string `\\\\t123`\\n // means first tab should be expanded to 4-21%4 === 3 spaces.\\n //\\n this.bsCount = []\\n\\n // block parser variables\\n\\n // required block content indent (for example, if we are\\n // inside a list, it would be positioned after list marker)\\n this.blkIndent = 0\\n this.line = 0 // line index in src\\n this.lineMax = 0 // lines count\\n this.tight = false // loose/tight mode for lists\\n this.ddIndent = -1 // indent of the current dd block (-1 if there isn't any)\\n this.listIndent = -1 // indent of the current list block (-1 if there isn't any)\\n\\n // can be 'blockquote', 'list', 'root', 'paragraph' or 'reference'\\n // used in lists to determine if they interrupt a paragraph\\n this.parentType = 'root'\\n\\n this.level = 0\\n\\n // Create caches\\n // Generate markers.\\n const s = this.src\\n\\n for (let start = 0, pos = 0, indent = 0, offset = 0, len = s.length, indent_found = false; pos < len; pos++) {\\n const ch = s.charCodeAt(pos)\\n\\n if (!indent_found) {\\n if (isSpace(ch)) {\\n indent++\\n\\n if (ch === 0x09) {\\n offset += 4 - offset % 4\\n } else {\\n offset++\\n }\\n continue\\n } else {\\n indent_found = true\\n }\\n }\\n\\n if (ch === 0x0A || pos === len - 1) {\\n if (ch !== 0x0A) { pos++ }\\n this.bMarks.push(start)\\n this.eMarks.push(pos)\\n this.tShift.push(indent)\\n this.sCount.push(offset)\\n this.bsCount.push(0)\\n\\n indent_found = false\\n indent = 0\\n offset = 0\\n start = pos + 1\\n }\\n }\\n\\n // Push fake entry to simplify cache bounds checks\\n this.bMarks.push(s.length)\\n this.eMarks.push(s.length)\\n this.tShift.push(0)\\n this.sCount.push(0)\\n this.bsCount.push(0)\\n\\n this.lineMax = this.bMarks.length - 1 // don't count last fake line\\n}\\n\\n// Push new token to \\\"stream\\\".\\n//\\nStateBlock.prototype.push = function (type, tag, nesting) {\\n const token = new Token(type, tag, nesting)\\n token.block = true\\n\\n if (nesting < 0) this.level-- // closing tag\\n token.level = this.level\\n if (nesting > 0) this.level++ // opening tag\\n\\n this.tokens.push(token)\\n return token\\n}\\n\\nStateBlock.prototype.isEmpty = function isEmpty (line) {\\n return this.bMarks[line] + this.tShift[line] >= this.eMarks[line]\\n}\\n\\nStateBlock.prototype.skipEmptyLines = function skipEmptyLines (from) {\\n for (let max = this.lineMax; from < max; from++) {\\n if (this.bMarks[from] + this.tShift[from] < this.eMarks[from]) {\\n break\\n }\\n }\\n return from\\n}\\n\\n// Skip spaces from given position.\\nStateBlock.prototype.skipSpaces = function skipSpaces (pos) {\\n for (let max = this.src.length; pos < max; pos++) {\\n const ch = this.src.charCodeAt(pos)\\n if (!isSpace(ch)) { break }\\n }\\n return pos\\n}\\n\\n// Skip spaces from given position in reverse.\\nStateBlock.prototype.skipSpacesBack = function skipSpacesBack (pos, min) {\\n if (pos <= min) { return pos }\\n\\n while (pos > min) {\\n if (!isSpace(this.src.charCodeAt(--pos))) { return pos + 1 }\\n }\\n return pos\\n}\\n\\n// Skip char codes from given position\\nStateBlock.prototype.skipChars = function skipChars (pos, code) {\\n for (let max = this.src.length; pos < max; pos++) {\\n if (this.src.charCodeAt(pos) !== code) { break }\\n }\\n return pos\\n}\\n\\n// Skip char codes reverse from given position - 1\\nStateBlock.prototype.skipCharsBack = function skipCharsBack (pos, code, min) {\\n if (pos <= min) { return pos }\\n\\n while (pos > min) {\\n if (code !== this.src.charCodeAt(--pos)) { return pos + 1 }\\n }\\n return pos\\n}\\n\\n// cut lines range from source.\\nStateBlock.prototype.getLines = function getLines (begin, end, indent, keepLastLF) {\\n if (begin >= end) {\\n return ''\\n }\\n\\n const queue = new Array(end - begin)\\n\\n for (let i = 0, line = begin; line < end; line++, i++) {\\n let lineIndent = 0\\n const lineStart = this.bMarks[line]\\n let first = lineStart\\n let last\\n\\n if (line + 1 < end || keepLastLF) {\\n // No need for bounds check because we have fake entry on tail.\\n last = this.eMarks[line] + 1\\n } else {\\n last = this.eMarks[line]\\n }\\n\\n while (first < last && lineIndent < indent) {\\n const ch = this.src.charCodeAt(first)\\n\\n if (isSpace(ch)) {\\n if (ch === 0x09) {\\n lineIndent += 4 - (lineIndent + this.bsCount[line]) % 4\\n } else {\\n lineIndent++\\n }\\n } else if (first - lineStart < this.tShift[line]) {\\n // patched tShift masked characters to look like spaces (blockquotes, list markers)\\n lineIndent++\\n } else {\\n break\\n }\\n\\n first++\\n }\\n\\n if (lineIndent > indent) {\\n // partially expanding tabs in code blocks, e.g '\\\\t\\\\tfoobar'\\n // with indent=2 becomes ' \\\\tfoobar'\\n queue[i] = new Array(lineIndent - indent + 1).join(' ') + this.src.slice(first, last)\\n } else {\\n queue[i] = this.src.slice(first, last)\\n }\\n }\\n\\n return queue.join('')\\n}\\n\\n// re-export Token class to use in block rules\\nStateBlock.prototype.Token = Token\\n\\nexport default StateBlock\\n\",\"// GFM table, https://github.github.com/gfm/#tables-extension-\\n\\nimport { isSpace } from '../common/utils.mjs'\\n\\n// Limit the amount of empty autocompleted cells in a table,\\n// see https://github.com/markdown-it/markdown-it/issues/1000,\\n//\\n// Both pulldown-cmark and commonmark-hs limit the number of cells this way to ~200k.\\n// We set it to 65k, which can expand user input by a factor of x370\\n// (256x256 square is 1.8kB expanded into 650kB).\\nconst MAX_AUTOCOMPLETED_CELLS = 0x10000\\n\\nfunction getLine (state, line) {\\n const pos = state.bMarks[line] + state.tShift[line]\\n const max = state.eMarks[line]\\n\\n return state.src.slice(pos, max)\\n}\\n\\nfunction escapedSplit (str) {\\n const result = []\\n const max = str.length\\n\\n let pos = 0\\n let ch = str.charCodeAt(pos)\\n let isEscaped = false\\n let lastPos = 0\\n let current = ''\\n\\n while (pos < max) {\\n if (ch === 0x7c/* | */) {\\n if (!isEscaped) {\\n // pipe separating cells, '|'\\n result.push(current + str.substring(lastPos, pos))\\n current = ''\\n lastPos = pos + 1\\n } else {\\n // escaped pipe, '\\\\|'\\n current += str.substring(lastPos, pos - 1)\\n lastPos = pos\\n }\\n }\\n\\n isEscaped = (ch === 0x5c/* \\\\ */)\\n pos++\\n\\n ch = str.charCodeAt(pos)\\n }\\n\\n result.push(current + str.substring(lastPos))\\n\\n return result\\n}\\n\\nexport default function table (state, startLine, endLine, silent) {\\n // should have at least two lines\\n if (startLine + 2 > endLine) { return false }\\n\\n let nextLine = startLine + 1\\n\\n if (state.sCount[nextLine] < state.blkIndent) { return false }\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[nextLine] - state.blkIndent >= 4) { return false }\\n\\n // first character of the second line should be '|', '-', ':',\\n // and no other characters are allowed but spaces;\\n // basically, this is the equivalent of /^[-:|][-:|\\\\s]*$/ regexp\\n\\n let pos = state.bMarks[nextLine] + state.tShift[nextLine]\\n if (pos >= state.eMarks[nextLine]) { return false }\\n\\n const firstCh = state.src.charCodeAt(pos++)\\n if (firstCh !== 0x7C/* | */ && firstCh !== 0x2D/* - */ && firstCh !== 0x3A/* : */) { return false }\\n\\n if (pos >= state.eMarks[nextLine]) { return false }\\n\\n const secondCh = state.src.charCodeAt(pos++)\\n if (secondCh !== 0x7C/* | */ && secondCh !== 0x2D/* - */ && secondCh !== 0x3A/* : */ && !isSpace(secondCh)) {\\n return false\\n }\\n\\n // if first character is '-', then second character must not be a space\\n // (due to parsing ambiguity with list)\\n if (firstCh === 0x2D/* - */ && isSpace(secondCh)) { return false }\\n\\n while (pos < state.eMarks[nextLine]) {\\n const ch = state.src.charCodeAt(pos)\\n\\n if (ch !== 0x7C/* | */ && ch !== 0x2D/* - */ && ch !== 0x3A/* : */ && !isSpace(ch)) { return false }\\n\\n pos++\\n }\\n\\n let lineText = getLine(state, startLine + 1)\\n let columns = lineText.split('|')\\n const aligns = []\\n for (let i = 0; i < columns.length; i++) {\\n const t = columns[i].trim()\\n if (!t) {\\n // allow empty columns before and after table, but not in between columns;\\n // e.g. allow ` |---| `, disallow ` ---||--- `\\n if (i === 0 || i === columns.length - 1) {\\n continue\\n } else {\\n return false\\n }\\n }\\n\\n if (!/^:?-+:?$/.test(t)) { return false }\\n if (t.charCodeAt(t.length - 1) === 0x3A/* : */) {\\n aligns.push(t.charCodeAt(0) === 0x3A/* : */ ? 'center' : 'right')\\n } else if (t.charCodeAt(0) === 0x3A/* : */) {\\n aligns.push('left')\\n } else {\\n aligns.push('')\\n }\\n }\\n\\n lineText = getLine(state, startLine).trim()\\n if (lineText.indexOf('|') === -1) { return false }\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n columns = escapedSplit(lineText)\\n if (columns.length && columns[0] === '') columns.shift()\\n if (columns.length && columns[columns.length - 1] === '') columns.pop()\\n\\n // header row will define an amount of columns in the entire table,\\n // and align row should be exactly the same (the rest of the rows can differ)\\n const columnCount = columns.length\\n if (columnCount === 0 || columnCount !== aligns.length) { return false }\\n\\n if (silent) { return true }\\n\\n const oldParentType = state.parentType\\n state.parentType = 'table'\\n\\n // use 'blockquote' lists for termination because it's\\n // the most similar to tables\\n const terminatorRules = state.md.block.ruler.getRules('blockquote')\\n\\n const token_to = state.push('table_open', 'table', 1)\\n const tableLines = [startLine, 0]\\n token_to.map = tableLines\\n\\n const token_tho = state.push('thead_open', 'thead', 1)\\n token_tho.map = [startLine, startLine + 1]\\n\\n const token_htro = state.push('tr_open', 'tr', 1)\\n token_htro.map = [startLine, startLine + 1]\\n\\n for (let i = 0; i < columns.length; i++) {\\n const token_ho = state.push('th_open', 'th', 1)\\n if (aligns[i]) {\\n token_ho.attrs = [['style', 'text-align:' + aligns[i]]]\\n }\\n\\n const token_il = state.push('inline', '', 0)\\n token_il.content = columns[i].trim()\\n token_il.children = []\\n\\n state.push('th_close', 'th', -1)\\n }\\n\\n state.push('tr_close', 'tr', -1)\\n state.push('thead_close', 'thead', -1)\\n\\n let tbodyLines\\n let autocompletedCells = 0\\n\\n for (nextLine = startLine + 2; nextLine < endLine; nextLine++) {\\n if (state.sCount[nextLine] < state.blkIndent) { break }\\n\\n let terminate = false\\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\\n if (terminatorRules[i](state, nextLine, endLine, true)) {\\n terminate = true\\n break\\n }\\n }\\n\\n if (terminate) { break }\\n lineText = getLine(state, nextLine).trim()\\n if (!lineText) { break }\\n if (state.sCount[nextLine] - state.blkIndent >= 4) { break }\\n columns = escapedSplit(lineText)\\n if (columns.length && columns[0] === '') columns.shift()\\n if (columns.length && columns[columns.length - 1] === '') columns.pop()\\n\\n // note: autocomplete count can be negative if user specifies more columns than header,\\n // but that does not affect intended use (which is limiting expansion)\\n autocompletedCells += columnCount - columns.length\\n if (autocompletedCells > MAX_AUTOCOMPLETED_CELLS) { break }\\n\\n if (nextLine === startLine + 2) {\\n const token_tbo = state.push('tbody_open', 'tbody', 1)\\n token_tbo.map = tbodyLines = [startLine + 2, 0]\\n }\\n\\n const token_tro = state.push('tr_open', 'tr', 1)\\n token_tro.map = [nextLine, nextLine + 1]\\n\\n for (let i = 0; i < columnCount; i++) {\\n const token_tdo = state.push('td_open', 'td', 1)\\n if (aligns[i]) {\\n token_tdo.attrs = [['style', 'text-align:' + aligns[i]]]\\n }\\n\\n const token_il = state.push('inline', '', 0)\\n token_il.content = columns[i] ? columns[i].trim() : ''\\n token_il.children = []\\n\\n state.push('td_close', 'td', -1)\\n }\\n state.push('tr_close', 'tr', -1)\\n }\\n\\n if (tbodyLines) {\\n state.push('tbody_close', 'tbody', -1)\\n tbodyLines[1] = nextLine\\n }\\n\\n state.push('table_close', 'table', -1)\\n tableLines[1] = nextLine\\n\\n state.parentType = oldParentType\\n state.line = nextLine\\n return true\\n}\\n\",\"// Code block (4 spaces padded)\\n\\nexport default function code (state, startLine, endLine/*, silent */) {\\n if (state.sCount[startLine] - state.blkIndent < 4) { return false }\\n\\n let nextLine = startLine + 1\\n let last = nextLine\\n\\n while (nextLine < endLine) {\\n if (state.isEmpty(nextLine)) {\\n nextLine++\\n continue\\n }\\n\\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\\n nextLine++\\n last = nextLine\\n continue\\n }\\n break\\n }\\n\\n state.line = last\\n\\n const token = state.push('code_block', 'code', 0)\\n token.content = state.getLines(startLine, last, 4 + state.blkIndent, false) + '\\\\n'\\n token.map = [startLine, state.line]\\n\\n return true\\n}\\n\",\"// fences (``` lang, ~~~ lang)\\n\\nexport default function fence (state, startLine, endLine, silent) {\\n let pos = state.bMarks[startLine] + state.tShift[startLine]\\n let max = state.eMarks[startLine]\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n\\n if (pos + 3 > max) { return false }\\n\\n const marker = state.src.charCodeAt(pos)\\n\\n if (marker !== 0x7E/* ~ */ && marker !== 0x60 /* ` */) {\\n return false\\n }\\n\\n // scan marker length\\n let mem = pos\\n pos = state.skipChars(pos, marker)\\n\\n let len = pos - mem\\n\\n if (len < 3) { return false }\\n\\n const markup = state.src.slice(mem, pos)\\n const params = state.src.slice(pos, max)\\n\\n if (marker === 0x60 /* ` */) {\\n if (params.indexOf(String.fromCharCode(marker)) >= 0) {\\n return false\\n }\\n }\\n\\n // Since start is found, we can report success here in validation mode\\n if (silent) { return true }\\n\\n // search end of block\\n let nextLine = startLine\\n let haveEndMarker = false\\n\\n for (;;) {\\n nextLine++\\n if (nextLine >= endLine) {\\n // unclosed block should be autoclosed by end of document.\\n // also block seems to be autoclosed by end of parent\\n break\\n }\\n\\n pos = mem = state.bMarks[nextLine] + state.tShift[nextLine]\\n max = state.eMarks[nextLine]\\n\\n if (pos < max && state.sCount[nextLine] < state.blkIndent) {\\n // non-empty line with negative indent should stop the list:\\n // - ```\\n // test\\n break\\n }\\n\\n if (state.src.charCodeAt(pos) !== marker) { continue }\\n\\n if (state.sCount[nextLine] - state.blkIndent >= 4) {\\n // closing fence should be indented less than 4 spaces\\n continue\\n }\\n\\n pos = state.skipChars(pos, marker)\\n\\n // closing code fence must be at least as long as the opening one\\n if (pos - mem < len) { continue }\\n\\n // make sure tail has spaces only\\n pos = state.skipSpaces(pos)\\n\\n if (pos < max) { continue }\\n\\n haveEndMarker = true\\n // found!\\n break\\n }\\n\\n // If a fence has heading spaces, they should be removed from its inner block\\n len = state.sCount[startLine]\\n\\n state.line = nextLine + (haveEndMarker ? 1 : 0)\\n\\n const token = state.push('fence', 'code', 0)\\n token.info = params\\n token.content = state.getLines(startLine + 1, nextLine, len, true)\\n token.markup = markup\\n token.map = [startLine, state.line]\\n\\n return true\\n}\\n\",\"// Block quotes\\n\\nimport { isSpace } from '../common/utils.mjs'\\n\\nexport default function blockquote (state, startLine, endLine, silent) {\\n let pos = state.bMarks[startLine] + state.tShift[startLine]\\n let max = state.eMarks[startLine]\\n\\n const oldLineMax = state.lineMax\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n\\n // check the block quote marker\\n if (state.src.charCodeAt(pos) !== 0x3E/* > */) { return false }\\n\\n // we know that it's going to be a valid blockquote,\\n // so no point trying to find the end of it in silent mode\\n if (silent) { return true }\\n\\n const oldBMarks = []\\n const oldBSCount = []\\n const oldSCount = []\\n const oldTShift = []\\n\\n const terminatorRules = state.md.block.ruler.getRules('blockquote')\\n\\n const oldParentType = state.parentType\\n state.parentType = 'blockquote'\\n let lastLineEmpty = false\\n let nextLine\\n\\n // Search the end of the block\\n //\\n // Block ends with either:\\n // 1. an empty line outside:\\n // ```\\n // > test\\n //\\n // ```\\n // 2. an empty line inside:\\n // ```\\n // >\\n // test\\n // ```\\n // 3. another tag:\\n // ```\\n // > test\\n // - - -\\n // ```\\n for (nextLine = startLine; nextLine < endLine; nextLine++) {\\n // check if it's outdented, i.e. it's inside list item and indented\\n // less than said list item:\\n //\\n // ```\\n // 1. anything\\n // > current blockquote\\n // 2. checking this line\\n // ```\\n const isOutdented = state.sCount[nextLine] < state.blkIndent\\n\\n pos = state.bMarks[nextLine] + state.tShift[nextLine]\\n max = state.eMarks[nextLine]\\n\\n if (pos >= max) {\\n // Case 1: line is not inside the blockquote, and this line is empty.\\n break\\n }\\n\\n if (state.src.charCodeAt(pos++) === 0x3E/* > */ && !isOutdented) {\\n // This line is inside the blockquote.\\n\\n // set offset past spaces and \\\">\\\"\\n let initial = state.sCount[nextLine] + 1\\n let spaceAfterMarker\\n let adjustTab\\n\\n // skip one optional space after '>'\\n if (state.src.charCodeAt(pos) === 0x20 /* space */) {\\n // ' > test '\\n // ^ -- position start of line here:\\n pos++\\n initial++\\n adjustTab = false\\n spaceAfterMarker = true\\n } else if (state.src.charCodeAt(pos) === 0x09 /* tab */) {\\n spaceAfterMarker = true\\n\\n if ((state.bsCount[nextLine] + initial) % 4 === 3) {\\n // ' >\\\\t test '\\n // ^ -- position start of line here (tab has width===1)\\n pos++\\n initial++\\n adjustTab = false\\n } else {\\n // ' >\\\\t test '\\n // ^ -- position start of line here + shift bsCount slightly\\n // to make extra space appear\\n adjustTab = true\\n }\\n } else {\\n spaceAfterMarker = false\\n }\\n\\n let offset = initial\\n oldBMarks.push(state.bMarks[nextLine])\\n state.bMarks[nextLine] = pos\\n\\n while (pos < max) {\\n const ch = state.src.charCodeAt(pos)\\n\\n if (isSpace(ch)) {\\n if (ch === 0x09) {\\n offset += 4 - (offset + state.bsCount[nextLine] + (adjustTab ? 1 : 0)) % 4\\n } else {\\n offset++\\n }\\n } else {\\n break\\n }\\n\\n pos++\\n }\\n\\n lastLineEmpty = pos >= max\\n\\n oldBSCount.push(state.bsCount[nextLine])\\n state.bsCount[nextLine] = state.sCount[nextLine] + 1 + (spaceAfterMarker ? 1 : 0)\\n\\n oldSCount.push(state.sCount[nextLine])\\n state.sCount[nextLine] = offset - initial\\n\\n oldTShift.push(state.tShift[nextLine])\\n state.tShift[nextLine] = pos - state.bMarks[nextLine]\\n continue\\n }\\n\\n // Case 2: line is not inside the blockquote, and the last line was empty.\\n if (lastLineEmpty) { break }\\n\\n // Case 3: another tag found.\\n let terminate = false\\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\\n if (terminatorRules[i](state, nextLine, endLine, true)) {\\n terminate = true\\n break\\n }\\n }\\n\\n if (terminate) {\\n // Quirk to enforce \\\"hard termination mode\\\" for paragraphs;\\n // normally if you call `tokenize(state, startLine, nextLine)`,\\n // paragraphs will look below nextLine for paragraph continuation,\\n // but if blockquote is terminated by another tag, they shouldn't\\n state.lineMax = nextLine\\n\\n if (state.blkIndent !== 0) {\\n // state.blkIndent was non-zero, we now set it to zero,\\n // so we need to re-calculate all offsets to appear as\\n // if indent wasn't changed\\n oldBMarks.push(state.bMarks[nextLine])\\n oldBSCount.push(state.bsCount[nextLine])\\n oldTShift.push(state.tShift[nextLine])\\n oldSCount.push(state.sCount[nextLine])\\n state.sCount[nextLine] -= state.blkIndent\\n }\\n\\n break\\n }\\n\\n oldBMarks.push(state.bMarks[nextLine])\\n oldBSCount.push(state.bsCount[nextLine])\\n oldTShift.push(state.tShift[nextLine])\\n oldSCount.push(state.sCount[nextLine])\\n\\n // A negative indentation means that this is a paragraph continuation\\n //\\n state.sCount[nextLine] = -1\\n }\\n\\n const oldIndent = state.blkIndent\\n state.blkIndent = 0\\n\\n const token_o = state.push('blockquote_open', 'blockquote', 1)\\n token_o.markup = '>'\\n const lines = [startLine, 0]\\n token_o.map = lines\\n\\n state.md.block.tokenize(state, startLine, nextLine)\\n\\n const token_c = state.push('blockquote_close', 'blockquote', -1)\\n token_c.markup = '>'\\n\\n state.lineMax = oldLineMax\\n state.parentType = oldParentType\\n lines[1] = state.line\\n\\n // Restore original tShift; this might not be necessary since the parser\\n // has already been here, but just to make sure we can do that.\\n for (let i = 0; i < oldTShift.length; i++) {\\n state.bMarks[i + startLine] = oldBMarks[i]\\n state.tShift[i + startLine] = oldTShift[i]\\n state.sCount[i + startLine] = oldSCount[i]\\n state.bsCount[i + startLine] = oldBSCount[i]\\n }\\n state.blkIndent = oldIndent\\n\\n return true\\n}\\n\",\"// Horizontal rule\\n\\nimport { isSpace } from '../common/utils.mjs'\\n\\nexport default function hr (state, startLine, endLine, silent) {\\n const max = state.eMarks[startLine]\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n\\n let pos = state.bMarks[startLine] + state.tShift[startLine]\\n const marker = state.src.charCodeAt(pos++)\\n\\n // Check hr marker\\n if (marker !== 0x2A/* * */ &&\\n marker !== 0x2D/* - */ &&\\n marker !== 0x5F/* _ */) {\\n return false\\n }\\n\\n // markers can be mixed with spaces, but there should be at least 3 of them\\n\\n let cnt = 1\\n while (pos < max) {\\n const ch = state.src.charCodeAt(pos++)\\n if (ch !== marker && !isSpace(ch)) { return false }\\n if (ch === marker) { cnt++ }\\n }\\n\\n if (cnt < 3) { return false }\\n\\n if (silent) { return true }\\n\\n state.line = startLine + 1\\n\\n const token = state.push('hr', 'hr', 0)\\n token.map = [startLine, state.line]\\n token.markup = Array(cnt + 1).join(String.fromCharCode(marker))\\n\\n return true\\n}\\n\",\"// Lists\\n\\nimport { isSpace } from '../common/utils.mjs'\\n\\n// Search `[-+*][\\\\n ]`, returns next pos after marker on success\\n// or -1 on fail.\\nfunction skipBulletListMarker (state, startLine) {\\n const max = state.eMarks[startLine]\\n let pos = state.bMarks[startLine] + state.tShift[startLine]\\n\\n const marker = state.src.charCodeAt(pos++)\\n // Check bullet\\n if (marker !== 0x2A/* * */ &&\\n marker !== 0x2D/* - */ &&\\n marker !== 0x2B/* + */) {\\n return -1\\n }\\n\\n if (pos < max) {\\n const ch = state.src.charCodeAt(pos)\\n\\n if (!isSpace(ch)) {\\n // \\\" -test \\\" - is not a list item\\n return -1\\n }\\n }\\n\\n return pos\\n}\\n\\n// Search `\\\\d+[.)][\\\\n ]`, returns next pos after marker on success\\n// or -1 on fail.\\nfunction skipOrderedListMarker (state, startLine) {\\n const start = state.bMarks[startLine] + state.tShift[startLine]\\n const max = state.eMarks[startLine]\\n let pos = start\\n\\n // List marker should have at least 2 chars (digit + dot)\\n if (pos + 1 >= max) { return -1 }\\n\\n let ch = state.src.charCodeAt(pos++)\\n\\n if (ch < 0x30/* 0 */ || ch > 0x39/* 9 */) { return -1 }\\n\\n for (;;) {\\n // EOL -> fail\\n if (pos >= max) { return -1 }\\n\\n ch = state.src.charCodeAt(pos++)\\n\\n if (ch >= 0x30/* 0 */ && ch <= 0x39/* 9 */) {\\n // List marker should have no more than 9 digits\\n // (prevents integer overflow in browsers)\\n if (pos - start >= 10) { return -1 }\\n\\n continue\\n }\\n\\n // found valid marker\\n if (ch === 0x29/* ) */ || ch === 0x2e/* . */) {\\n break\\n }\\n\\n return -1\\n }\\n\\n if (pos < max) {\\n ch = state.src.charCodeAt(pos)\\n\\n if (!isSpace(ch)) {\\n // \\\" 1.test \\\" - is not a list item\\n return -1\\n }\\n }\\n return pos\\n}\\n\\nfunction markTightParagraphs (state, idx) {\\n const level = state.level + 2\\n\\n for (let i = idx + 2, l = state.tokens.length - 2; i < l; i++) {\\n if (state.tokens[i].level === level && state.tokens[i].type === 'paragraph_open') {\\n state.tokens[i + 2].hidden = true\\n state.tokens[i].hidden = true\\n i += 2\\n }\\n }\\n}\\n\\nexport default function list (state, startLine, endLine, silent) {\\n let max, pos, start, token\\n let nextLine = startLine\\n let tight = true\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[nextLine] - state.blkIndent >= 4) { return false }\\n\\n // Special case:\\n // - item 1\\n // - item 2\\n // - item 3\\n // - item 4\\n // - this one is a paragraph continuation\\n if (state.listIndent >= 0 &&\\n state.sCount[nextLine] - state.listIndent >= 4 &&\\n state.sCount[nextLine] < state.blkIndent) {\\n return false\\n }\\n\\n let isTerminatingParagraph = false\\n\\n // limit conditions when list can interrupt\\n // a paragraph (validation mode only)\\n if (silent && state.parentType === 'paragraph') {\\n // Next list item should still terminate previous list item;\\n //\\n // This code can fail if plugins use blkIndent as well as lists,\\n // but I hope the spec gets fixed long before that happens.\\n //\\n if (state.sCount[nextLine] >= state.blkIndent) {\\n isTerminatingParagraph = true\\n }\\n }\\n\\n // Detect list type and position after marker\\n let isOrdered\\n let markerValue\\n let posAfterMarker\\n if ((posAfterMarker = skipOrderedListMarker(state, nextLine)) >= 0) {\\n isOrdered = true\\n start = state.bMarks[nextLine] + state.tShift[nextLine]\\n markerValue = Number(state.src.slice(start, posAfterMarker - 1))\\n\\n // If we're starting a new ordered list right after\\n // a paragraph, it should start with 1.\\n if (isTerminatingParagraph && markerValue !== 1) return false\\n } else if ((posAfterMarker = skipBulletListMarker(state, nextLine)) >= 0) {\\n isOrdered = false\\n } else {\\n return false\\n }\\n\\n // If we're starting a new unordered list right after\\n // a paragraph, first line should not be empty.\\n if (isTerminatingParagraph) {\\n if (state.skipSpaces(posAfterMarker) >= state.eMarks[nextLine]) return false\\n }\\n\\n // For validation mode we can terminate immediately\\n if (silent) { return true }\\n\\n // We should terminate list on style change. Remember first one to compare.\\n const markerCharCode = state.src.charCodeAt(posAfterMarker - 1)\\n\\n // Start list\\n const listTokIdx = state.tokens.length\\n\\n if (isOrdered) {\\n token = state.push('ordered_list_open', 'ol', 1)\\n if (markerValue !== 1) {\\n token.attrs = [['start', markerValue]]\\n }\\n } else {\\n token = state.push('bullet_list_open', 'ul', 1)\\n }\\n\\n const listLines = [nextLine, 0]\\n token.map = listLines\\n token.markup = String.fromCharCode(markerCharCode)\\n\\n //\\n // Iterate list items\\n //\\n\\n let prevEmptyEnd = false\\n const terminatorRules = state.md.block.ruler.getRules('list')\\n\\n const oldParentType = state.parentType\\n state.parentType = 'list'\\n\\n while (nextLine < endLine) {\\n pos = posAfterMarker\\n max = state.eMarks[nextLine]\\n\\n const initial = state.sCount[nextLine] + posAfterMarker - (state.bMarks[nextLine] + state.tShift[nextLine])\\n let offset = initial\\n\\n while (pos < max) {\\n const ch = state.src.charCodeAt(pos)\\n\\n if (ch === 0x09) {\\n offset += 4 - (offset + state.bsCount[nextLine]) % 4\\n } else if (ch === 0x20) {\\n offset++\\n } else {\\n break\\n }\\n\\n pos++\\n }\\n\\n const contentStart = pos\\n let indentAfterMarker\\n\\n if (contentStart >= max) {\\n // trimming space in \\\"- \\\\n 3\\\" case, indent is 1 here\\n indentAfterMarker = 1\\n } else {\\n indentAfterMarker = offset - initial\\n }\\n\\n // If we have more than 4 spaces, the indent is 1\\n // (the rest is just indented code block)\\n if (indentAfterMarker > 4) { indentAfterMarker = 1 }\\n\\n // \\\" - test\\\"\\n // ^^^^^ - calculating total length of this thing\\n const indent = initial + indentAfterMarker\\n\\n // Run subparser & write tokens\\n token = state.push('list_item_open', 'li', 1)\\n token.markup = String.fromCharCode(markerCharCode)\\n const itemLines = [nextLine, 0]\\n token.map = itemLines\\n if (isOrdered) {\\n token.info = state.src.slice(start, posAfterMarker - 1)\\n }\\n\\n // change current state, then restore it after parser subcall\\n const oldTight = state.tight\\n const oldTShift = state.tShift[nextLine]\\n const oldSCount = state.sCount[nextLine]\\n\\n // - example list\\n // ^ listIndent position will be here\\n // ^ blkIndent position will be here\\n //\\n const oldListIndent = state.listIndent\\n state.listIndent = state.blkIndent\\n state.blkIndent = indent\\n\\n state.tight = true\\n state.tShift[nextLine] = contentStart - state.bMarks[nextLine]\\n state.sCount[nextLine] = offset\\n\\n if (contentStart >= max && state.isEmpty(nextLine + 1)) {\\n // workaround for this case\\n // (list item is empty, list terminates before \\\"foo\\\"):\\n // ~~~~~~~~\\n // -\\n //\\n // foo\\n // ~~~~~~~~\\n state.line = Math.min(state.line + 2, endLine)\\n } else {\\n state.md.block.tokenize(state, nextLine, endLine, true)\\n }\\n\\n // If any of list item is tight, mark list as tight\\n if (!state.tight || prevEmptyEnd) {\\n tight = false\\n }\\n // Item become loose if finish with empty line,\\n // but we should filter last element, because it means list finish\\n prevEmptyEnd = (state.line - nextLine) > 1 && state.isEmpty(state.line - 1)\\n\\n state.blkIndent = state.listIndent\\n state.listIndent = oldListIndent\\n state.tShift[nextLine] = oldTShift\\n state.sCount[nextLine] = oldSCount\\n state.tight = oldTight\\n\\n token = state.push('list_item_close', 'li', -1)\\n token.markup = String.fromCharCode(markerCharCode)\\n\\n nextLine = state.line\\n itemLines[1] = nextLine\\n\\n if (nextLine >= endLine) { break }\\n\\n //\\n // Try to check if list is terminated or continued.\\n //\\n if (state.sCount[nextLine] < state.blkIndent) { break }\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[nextLine] - state.blkIndent >= 4) { break }\\n\\n // fail if terminating block found\\n let terminate = false\\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\\n if (terminatorRules[i](state, nextLine, endLine, true)) {\\n terminate = true\\n break\\n }\\n }\\n if (terminate) { break }\\n\\n // fail if list has another type\\n if (isOrdered) {\\n posAfterMarker = skipOrderedListMarker(state, nextLine)\\n if (posAfterMarker < 0) { break }\\n start = state.bMarks[nextLine] + state.tShift[nextLine]\\n } else {\\n posAfterMarker = skipBulletListMarker(state, nextLine)\\n if (posAfterMarker < 0) { break }\\n }\\n\\n if (markerCharCode !== state.src.charCodeAt(posAfterMarker - 1)) { break }\\n }\\n\\n // Finalize list\\n if (isOrdered) {\\n token = state.push('ordered_list_close', 'ol', -1)\\n } else {\\n token = state.push('bullet_list_close', 'ul', -1)\\n }\\n token.markup = String.fromCharCode(markerCharCode)\\n\\n listLines[1] = nextLine\\n state.line = nextLine\\n\\n state.parentType = oldParentType\\n\\n // mark paragraphs tight if needed\\n if (tight) {\\n markTightParagraphs(state, listTokIdx)\\n }\\n\\n return true\\n}\\n\",\"import { isSpace, normalizeReference } from '../common/utils.mjs'\\n\\nexport default function reference (state, startLine, _endLine, silent) {\\n let pos = state.bMarks[startLine] + state.tShift[startLine]\\n let max = state.eMarks[startLine]\\n let nextLine = startLine + 1\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n\\n if (state.src.charCodeAt(pos) !== 0x5B/* [ */) { return false }\\n\\n function getNextLine (nextLine) {\\n const endLine = state.lineMax\\n\\n if (nextLine >= endLine || state.isEmpty(nextLine)) {\\n // empty line or end of input\\n return null\\n }\\n\\n let isContinuation = false\\n\\n // this would be a code block normally, but after paragraph\\n // it's considered a lazy continuation regardless of what's there\\n if (state.sCount[nextLine] - state.blkIndent > 3) { isContinuation = true }\\n\\n // quirk for blockquotes, this line should already be checked by that rule\\n if (state.sCount[nextLine] < 0) { isContinuation = true }\\n\\n if (!isContinuation) {\\n const terminatorRules = state.md.block.ruler.getRules('reference')\\n const oldParentType = state.parentType\\n state.parentType = 'reference'\\n\\n // Some tags can terminate paragraph without empty line.\\n let terminate = false\\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\\n if (terminatorRules[i](state, nextLine, endLine, true)) {\\n terminate = true\\n break\\n }\\n }\\n\\n state.parentType = oldParentType\\n if (terminate) {\\n // terminated by another block\\n return null\\n }\\n }\\n\\n const pos = state.bMarks[nextLine] + state.tShift[nextLine]\\n const max = state.eMarks[nextLine]\\n\\n // max + 1 explicitly includes the newline\\n return state.src.slice(pos, max + 1)\\n }\\n\\n let str = state.src.slice(pos, max + 1)\\n\\n max = str.length\\n let labelEnd = -1\\n\\n for (pos = 1; pos < max; pos++) {\\n const ch = str.charCodeAt(pos)\\n if (ch === 0x5B /* [ */) {\\n return false\\n } else if (ch === 0x5D /* ] */) {\\n labelEnd = pos\\n break\\n } else if (ch === 0x0A /* \\\\n */) {\\n const lineContent = getNextLine(nextLine)\\n if (lineContent !== null) {\\n str += lineContent\\n max = str.length\\n nextLine++\\n }\\n } else if (ch === 0x5C /* \\\\ */) {\\n pos++\\n if (pos < max && str.charCodeAt(pos) === 0x0A) {\\n const lineContent = getNextLine(nextLine)\\n if (lineContent !== null) {\\n str += lineContent\\n max = str.length\\n nextLine++\\n }\\n }\\n }\\n }\\n\\n if (labelEnd < 0 || str.charCodeAt(labelEnd + 1) !== 0x3A/* : */) { return false }\\n\\n // [label]: destination 'title'\\n // ^^^ skip optional whitespace here\\n for (pos = labelEnd + 2; pos < max; pos++) {\\n const ch = str.charCodeAt(pos)\\n if (ch === 0x0A) {\\n const lineContent = getNextLine(nextLine)\\n if (lineContent !== null) {\\n str += lineContent\\n max = str.length\\n nextLine++\\n }\\n } else if (isSpace(ch)) {\\n /* eslint no-empty:0 */\\n } else {\\n break\\n }\\n }\\n\\n // [label]: destination 'title'\\n // ^^^^^^^^^^^ parse this\\n const destRes = state.md.helpers.parseLinkDestination(str, pos, max)\\n if (!destRes.ok) { return false }\\n\\n const href = state.md.normalizeLink(destRes.str)\\n if (!state.md.validateLink(href)) { return false }\\n\\n pos = destRes.pos\\n\\n // save cursor state, we could require to rollback later\\n const destEndPos = pos\\n const destEndLineNo = nextLine\\n\\n // [label]: destination 'title'\\n // ^^^ skipping those spaces\\n const start = pos\\n for (; pos < max; pos++) {\\n const ch = str.charCodeAt(pos)\\n if (ch === 0x0A) {\\n const lineContent = getNextLine(nextLine)\\n if (lineContent !== null) {\\n str += lineContent\\n max = str.length\\n nextLine++\\n }\\n } else if (isSpace(ch)) {\\n /* eslint no-empty:0 */\\n } else {\\n break\\n }\\n }\\n\\n // [label]: destination 'title'\\n // ^^^^^^^ parse this\\n let titleRes = state.md.helpers.parseLinkTitle(str, pos, max)\\n while (titleRes.can_continue) {\\n const lineContent = getNextLine(nextLine)\\n if (lineContent === null) break\\n str += lineContent\\n pos = max\\n max = str.length\\n nextLine++\\n titleRes = state.md.helpers.parseLinkTitle(str, pos, max, titleRes)\\n }\\n let title\\n\\n if (pos < max && start !== pos && titleRes.ok) {\\n title = titleRes.str\\n pos = titleRes.pos\\n } else {\\n title = ''\\n pos = destEndPos\\n nextLine = destEndLineNo\\n }\\n\\n // skip trailing spaces until the rest of the line\\n while (pos < max) {\\n const ch = str.charCodeAt(pos)\\n if (!isSpace(ch)) { break }\\n pos++\\n }\\n\\n if (pos < max && str.charCodeAt(pos) !== 0x0A) {\\n if (title) {\\n // garbage at the end of the line after title,\\n // but it could still be a valid reference if we roll back\\n title = ''\\n pos = destEndPos\\n nextLine = destEndLineNo\\n while (pos < max) {\\n const ch = str.charCodeAt(pos)\\n if (!isSpace(ch)) { break }\\n pos++\\n }\\n }\\n }\\n\\n if (pos < max && str.charCodeAt(pos) !== 0x0A) {\\n // garbage at the end of the line\\n return false\\n }\\n\\n const label = normalizeReference(str.slice(1, labelEnd))\\n if (!label) {\\n // CommonMark 0.20 disallows empty labels\\n return false\\n }\\n\\n // Reference can not terminate anything. This check is for safety only.\\n /* istanbul ignore if */\\n if (silent) { return true }\\n\\n if (typeof state.env.references === 'undefined') {\\n state.env.references = {}\\n }\\n if (typeof state.env.references[label] === 'undefined') {\\n state.env.references[label] = { title, href }\\n }\\n\\n state.line = nextLine\\n return true\\n}\\n\",\"// List of valid html blocks names, according to commonmark spec\\n// https://spec.commonmark.org/0.30/#html-blocks\\n\\nexport default [\\n 'address',\\n 'article',\\n 'aside',\\n 'base',\\n 'basefont',\\n 'blockquote',\\n 'body',\\n 'caption',\\n 'center',\\n 'col',\\n 'colgroup',\\n 'dd',\\n 'details',\\n 'dialog',\\n 'dir',\\n 'div',\\n 'dl',\\n 'dt',\\n 'fieldset',\\n 'figcaption',\\n 'figure',\\n 'footer',\\n 'form',\\n 'frame',\\n 'frameset',\\n 'h1',\\n 'h2',\\n 'h3',\\n 'h4',\\n 'h5',\\n 'h6',\\n 'head',\\n 'header',\\n 'hr',\\n 'html',\\n 'iframe',\\n 'legend',\\n 'li',\\n 'link',\\n 'main',\\n 'menu',\\n 'menuitem',\\n 'nav',\\n 'noframes',\\n 'ol',\\n 'optgroup',\\n 'option',\\n 'p',\\n 'param',\\n 'search',\\n 'section',\\n 'summary',\\n 'table',\\n 'tbody',\\n 'td',\\n 'tfoot',\\n 'th',\\n 'thead',\\n 'title',\\n 'tr',\\n 'track',\\n 'ul'\\n]\\n\",\"// Regexps to match html elements\\n\\nconst attr_name = '[a-zA-Z_:][a-zA-Z0-9:._-]*'\\n\\nconst unquoted = '[^\\\"\\\\'=<>`\\\\\\\\x00-\\\\\\\\x20]+'\\nconst single_quoted = \\\"'[^']*'\\\"\\nconst double_quoted = '\\\"[^\\\"]*\\\"'\\n\\nconst attr_value = '(?:' + unquoted + '|' + single_quoted + '|' + double_quoted + ')'\\n\\nconst attribute = '(?:\\\\\\\\s+' + attr_name + '(?:\\\\\\\\s*=\\\\\\\\s*' + attr_value + ')?)'\\n\\nconst open_tag = '<[A-Za-z][A-Za-z0-9\\\\\\\\-]*' + attribute + '*\\\\\\\\s*\\\\\\\\/?>'\\n\\nconst close_tag = '<\\\\\\\\/[A-Za-z][A-Za-z0-9\\\\\\\\-]*\\\\\\\\s*>'\\nconst comment = ''\\nconst processing = '<[?][\\\\\\\\s\\\\\\\\S]*?[?]>'\\nconst declaration = ']*>'\\nconst cdata = ''\\n\\nconst HTML_TAG_RE = new RegExp('^(?:' + open_tag + '|' + close_tag + '|' + comment +\\n '|' + processing + '|' + declaration + '|' + cdata + ')')\\nconst HTML_OPEN_CLOSE_TAG_RE = new RegExp('^(?:' + open_tag + '|' + close_tag + ')')\\n\\nexport { HTML_TAG_RE, HTML_OPEN_CLOSE_TAG_RE }\\n\",\"// HTML block\\n\\nimport block_names from '../common/html_blocks.mjs'\\nimport { HTML_OPEN_CLOSE_TAG_RE } from '../common/html_re.mjs'\\n\\n// An array of opening and corresponding closing sequences for html tags,\\n// last argument defines whether it can terminate a paragraph or not\\n//\\nconst HTML_SEQUENCES = [\\n [/^<(script|pre|style|textarea)(?=(\\\\s|>|$))/i, /<\\\\/(script|pre|style|textarea)>/i, true],\\n [/^/, true],\\n [/^<\\\\?/, /\\\\?>/, true],\\n [/^/, true],\\n [/^/, true],\\n [new RegExp('^|$))', 'i'), /^$/, true],\\n [new RegExp(HTML_OPEN_CLOSE_TAG_RE.source + '\\\\\\\\s*$'), /^$/, false]\\n]\\n\\nexport default function html_block (state, startLine, endLine, silent) {\\n let pos = state.bMarks[startLine] + state.tShift[startLine]\\n let max = state.eMarks[startLine]\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n\\n if (!state.md.options.html) { return false }\\n\\n if (state.src.charCodeAt(pos) !== 0x3C/* < */) { return false }\\n\\n let lineText = state.src.slice(pos, max)\\n\\n let i = 0\\n for (; i < HTML_SEQUENCES.length; i++) {\\n if (HTML_SEQUENCES[i][0].test(lineText)) { break }\\n }\\n if (i === HTML_SEQUENCES.length) { return false }\\n\\n if (silent) {\\n // true if this sequence can be a terminator, false otherwise\\n return HTML_SEQUENCES[i][2]\\n }\\n\\n let nextLine = startLine + 1\\n\\n // If we are here - we detected HTML block.\\n // Let's roll down till block end.\\n if (!HTML_SEQUENCES[i][1].test(lineText)) {\\n for (; nextLine < endLine; nextLine++) {\\n if (state.sCount[nextLine] < state.blkIndent) { break }\\n\\n pos = state.bMarks[nextLine] + state.tShift[nextLine]\\n max = state.eMarks[nextLine]\\n lineText = state.src.slice(pos, max)\\n\\n if (HTML_SEQUENCES[i][1].test(lineText)) {\\n if (lineText.length !== 0) { nextLine++ }\\n break\\n }\\n }\\n }\\n\\n state.line = nextLine\\n\\n const token = state.push('html_block', '', 0)\\n token.map = [startLine, nextLine]\\n token.content = state.getLines(startLine, nextLine, state.blkIndent, true)\\n\\n return true\\n}\\n\",\"// heading (#, ##, ...)\\n\\nimport { isSpace } from '../common/utils.mjs'\\n\\nexport default function heading (state, startLine, endLine, silent) {\\n let pos = state.bMarks[startLine] + state.tShift[startLine]\\n let max = state.eMarks[startLine]\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n\\n let ch = state.src.charCodeAt(pos)\\n\\n if (ch !== 0x23/* # */ || pos >= max) { return false }\\n\\n // count heading level\\n let level = 1\\n ch = state.src.charCodeAt(++pos)\\n while (ch === 0x23/* # */ && pos < max && level <= 6) {\\n level++\\n ch = state.src.charCodeAt(++pos)\\n }\\n\\n if (level > 6 || (pos < max && !isSpace(ch))) { return false }\\n\\n if (silent) { return true }\\n\\n // Let's cut tails like ' ### ' from the end of string\\n\\n max = state.skipSpacesBack(max, pos)\\n const tmp = state.skipCharsBack(max, 0x23, pos) // #\\n if (tmp > pos && isSpace(state.src.charCodeAt(tmp - 1))) {\\n max = tmp\\n }\\n\\n state.line = startLine + 1\\n\\n const token_o = state.push('heading_open', 'h' + String(level), 1)\\n token_o.markup = '########'.slice(0, level)\\n token_o.map = [startLine, state.line]\\n\\n const token_i = state.push('inline', '', 0)\\n token_i.content = state.src.slice(pos, max).trim()\\n token_i.map = [startLine, state.line]\\n token_i.children = []\\n\\n const token_c = state.push('heading_close', 'h' + String(level), -1)\\n token_c.markup = '########'.slice(0, level)\\n\\n return true\\n}\\n\",\"// lheading (---, ===)\\n\\nexport default function lheading (state, startLine, endLine/*, silent */) {\\n const terminatorRules = state.md.block.ruler.getRules('paragraph')\\n\\n // if it's indented more than 3 spaces, it should be a code block\\n if (state.sCount[startLine] - state.blkIndent >= 4) { return false }\\n\\n const oldParentType = state.parentType\\n state.parentType = 'paragraph' // use paragraph to match terminatorRules\\n\\n // jump line-by-line until empty one or EOF\\n let level = 0\\n let marker\\n let nextLine = startLine + 1\\n\\n for (; nextLine < endLine && !state.isEmpty(nextLine); nextLine++) {\\n // this would be a code block normally, but after paragraph\\n // it's considered a lazy continuation regardless of what's there\\n if (state.sCount[nextLine] - state.blkIndent > 3) { continue }\\n\\n //\\n // Check for underline in setext header\\n //\\n if (state.sCount[nextLine] >= state.blkIndent) {\\n let pos = state.bMarks[nextLine] + state.tShift[nextLine]\\n const max = state.eMarks[nextLine]\\n\\n if (pos < max) {\\n marker = state.src.charCodeAt(pos)\\n\\n if (marker === 0x2D/* - */ || marker === 0x3D/* = */) {\\n pos = state.skipChars(pos, marker)\\n pos = state.skipSpaces(pos)\\n\\n if (pos >= max) {\\n level = (marker === 0x3D/* = */ ? 1 : 2)\\n break\\n }\\n }\\n }\\n }\\n\\n // quirk for blockquotes, this line should already be checked by that rule\\n if (state.sCount[nextLine] < 0) { continue }\\n\\n // Some tags can terminate paragraph without empty line.\\n let terminate = false\\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\\n if (terminatorRules[i](state, nextLine, endLine, true)) {\\n terminate = true\\n break\\n }\\n }\\n if (terminate) { break }\\n }\\n\\n if (!level) {\\n // Didn't find valid underline\\n return false\\n }\\n\\n const content = state.getLines(startLine, nextLine, state.blkIndent, false).trim()\\n\\n state.line = nextLine + 1\\n\\n const token_o = state.push('heading_open', 'h' + String(level), 1)\\n token_o.markup = String.fromCharCode(marker)\\n token_o.map = [startLine, state.line]\\n\\n const token_i = state.push('inline', '', 0)\\n token_i.content = content\\n token_i.map = [startLine, state.line - 1]\\n token_i.children = []\\n\\n const token_c = state.push('heading_close', 'h' + String(level), -1)\\n token_c.markup = String.fromCharCode(marker)\\n\\n state.parentType = oldParentType\\n\\n return true\\n}\\n\",\"// Paragraph\\n\\nexport default function paragraph (state, startLine, endLine) {\\n const terminatorRules = state.md.block.ruler.getRules('paragraph')\\n const oldParentType = state.parentType\\n let nextLine = startLine + 1\\n state.parentType = 'paragraph'\\n\\n // jump line-by-line until empty one or EOF\\n for (; nextLine < endLine && !state.isEmpty(nextLine); nextLine++) {\\n // this would be a code block normally, but after paragraph\\n // it's considered a lazy continuation regardless of what's there\\n if (state.sCount[nextLine] - state.blkIndent > 3) { continue }\\n\\n // quirk for blockquotes, this line should already be checked by that rule\\n if (state.sCount[nextLine] < 0) { continue }\\n\\n // Some tags can terminate paragraph without empty line.\\n let terminate = false\\n for (let i = 0, l = terminatorRules.length; i < l; i++) {\\n if (terminatorRules[i](state, nextLine, endLine, true)) {\\n terminate = true\\n break\\n }\\n }\\n if (terminate) { break }\\n }\\n\\n const content = state.getLines(startLine, nextLine, state.blkIndent, false).trim()\\n\\n state.line = nextLine\\n\\n const token_o = state.push('paragraph_open', 'p', 1)\\n token_o.map = [startLine, state.line]\\n\\n const token_i = state.push('inline', '', 0)\\n token_i.content = content\\n token_i.map = [startLine, state.line]\\n token_i.children = []\\n\\n state.push('paragraph_close', 'p', -1)\\n\\n state.parentType = oldParentType\\n\\n return true\\n}\\n\",\"/** internal\\n * class ParserBlock\\n *\\n * Block-level tokenizer.\\n **/\\n\\nimport Ruler from './ruler.mjs'\\nimport StateBlock from './rules_block/state_block.mjs'\\n\\nimport r_table from './rules_block/table.mjs'\\nimport r_code from './rules_block/code.mjs'\\nimport r_fence from './rules_block/fence.mjs'\\nimport r_blockquote from './rules_block/blockquote.mjs'\\nimport r_hr from './rules_block/hr.mjs'\\nimport r_list from './rules_block/list.mjs'\\nimport r_reference from './rules_block/reference.mjs'\\nimport r_html_block from './rules_block/html_block.mjs'\\nimport r_heading from './rules_block/heading.mjs'\\nimport r_lheading from './rules_block/lheading.mjs'\\nimport r_paragraph from './rules_block/paragraph.mjs'\\n\\nconst _rules = [\\n // First 2 params - rule name & source. Secondary array - list of rules,\\n // which can be terminated by this one.\\n ['table', r_table, ['paragraph', 'reference']],\\n ['code', r_code],\\n ['fence', r_fence, ['paragraph', 'reference', 'blockquote', 'list']],\\n ['blockquote', r_blockquote, ['paragraph', 'reference', 'blockquote', 'list']],\\n ['hr', r_hr, ['paragraph', 'reference', 'blockquote', 'list']],\\n ['list', r_list, ['paragraph', 'reference', 'blockquote']],\\n ['reference', r_reference],\\n ['html_block', r_html_block, ['paragraph', 'reference', 'blockquote']],\\n ['heading', r_heading, ['paragraph', 'reference', 'blockquote']],\\n ['lheading', r_lheading],\\n ['paragraph', r_paragraph]\\n]\\n\\n/**\\n * new ParserBlock()\\n **/\\nfunction ParserBlock () {\\n /**\\n * ParserBlock#ruler -> Ruler\\n *\\n * [[Ruler]] instance. Keep configuration of block rules.\\n **/\\n this.ruler = new Ruler()\\n\\n for (let i = 0; i < _rules.length; i++) {\\n this.ruler.push(_rules[i][0], _rules[i][1], { alt: (_rules[i][2] || []).slice() })\\n }\\n}\\n\\n// Generate tokens for input range\\n//\\nParserBlock.prototype.tokenize = function (state, startLine, endLine) {\\n const rules = this.ruler.getRules('')\\n const len = rules.length\\n const maxNesting = state.md.options.maxNesting\\n let line = startLine\\n let hasEmptyLines = false\\n\\n while (line < endLine) {\\n state.line = line = state.skipEmptyLines(line)\\n if (line >= endLine) { break }\\n\\n // Termination condition for nested calls.\\n // Nested calls currently used for blockquotes & lists\\n if (state.sCount[line] < state.blkIndent) { break }\\n\\n // If nesting level exceeded - skip tail to the end. That's not ordinary\\n // situation and we should not care about content.\\n if (state.level >= maxNesting) {\\n state.line = endLine\\n break\\n }\\n\\n // Try all possible rules.\\n // On success, rule should:\\n //\\n // - update `state.line`\\n // - update `state.tokens`\\n // - return true\\n const prevLine = state.line\\n let ok = false\\n\\n for (let i = 0; i < len; i++) {\\n ok = rules[i](state, line, endLine, false)\\n if (ok) {\\n if (prevLine >= state.line) {\\n throw new Error(\\\"block rule didn't increment state.line\\\")\\n }\\n break\\n }\\n }\\n\\n // this can only happen if user disables paragraph rule\\n if (!ok) throw new Error('none of the block rules matched')\\n\\n // set state.tight if we had an empty line before current tag\\n // i.e. latest empty line should not count\\n state.tight = !hasEmptyLines\\n\\n // paragraph might \\\"eat\\\" one newline after it in nested lists\\n if (state.isEmpty(state.line - 1)) {\\n hasEmptyLines = true\\n }\\n\\n line = state.line\\n\\n if (line < endLine && state.isEmpty(line)) {\\n hasEmptyLines = true\\n line++\\n state.line = line\\n }\\n }\\n}\\n\\n/**\\n * ParserBlock.parse(str, md, env, outTokens)\\n *\\n * Process input string and push block tokens into `outTokens`\\n **/\\nParserBlock.prototype.parse = function (src, md, env, outTokens) {\\n if (!src) { return }\\n\\n const state = new this.State(src, md, env, outTokens)\\n\\n this.tokenize(state, state.line, state.lineMax)\\n}\\n\\nParserBlock.prototype.State = StateBlock\\n\\nexport default ParserBlock\\n\",\"// Inline parser state\\n\\nimport Token from '../token.mjs'\\nimport { isWhiteSpace, isPunctChar, isMdAsciiPunct } from '../common/utils.mjs'\\n\\nfunction StateInline (src, md, env, outTokens) {\\n this.src = src\\n this.env = env\\n this.md = md\\n this.tokens = outTokens\\n this.tokens_meta = Array(outTokens.length)\\n\\n this.pos = 0\\n this.posMax = this.src.length\\n this.level = 0\\n this.pending = ''\\n this.pendingLevel = 0\\n\\n // Stores { start: end } pairs. Useful for backtrack\\n // optimization of pairs parse (emphasis, strikes).\\n this.cache = {}\\n\\n // List of emphasis-like delimiters for current tag\\n this.delimiters = []\\n\\n // Stack of delimiter lists for upper level tags\\n this._prev_delimiters = []\\n\\n // backtick length => last seen position\\n this.backticks = {}\\n this.backticksScanned = false\\n\\n // Counter used to disable inline linkify-it execution\\n // inside and markdown links\\n this.linkLevel = 0\\n}\\n\\n// Flush pending text\\n//\\nStateInline.prototype.pushPending = function () {\\n const token = new Token('text', '', 0)\\n token.content = this.pending\\n token.level = this.pendingLevel\\n this.tokens.push(token)\\n this.pending = ''\\n return token\\n}\\n\\n// Push new token to \\\"stream\\\".\\n// If pending text exists - flush it as text token\\n//\\nStateInline.prototype.push = function (type, tag, nesting) {\\n if (this.pending) {\\n this.pushPending()\\n }\\n\\n const token = new Token(type, tag, nesting)\\n let token_meta = null\\n\\n if (nesting < 0) {\\n // closing tag\\n this.level--\\n this.delimiters = this._prev_delimiters.pop()\\n }\\n\\n token.level = this.level\\n\\n if (nesting > 0) {\\n // opening tag\\n this.level++\\n this._prev_delimiters.push(this.delimiters)\\n this.delimiters = []\\n token_meta = { delimiters: this.delimiters }\\n }\\n\\n this.pendingLevel = this.level\\n this.tokens.push(token)\\n this.tokens_meta.push(token_meta)\\n return token\\n}\\n\\n// Scan a sequence of emphasis-like markers, and determine whether\\n// it can start an emphasis sequence or end an emphasis sequence.\\n//\\n// - start - position to scan from (it should point at a valid marker);\\n// - canSplitWord - determine if these markers can be found inside a word\\n//\\nStateInline.prototype.scanDelims = function (start, canSplitWord) {\\n const max = this.posMax\\n const marker = this.src.charCodeAt(start)\\n\\n // treat beginning of the line as a whitespace\\n const lastChar = start > 0 ? this.src.charCodeAt(start - 1) : 0x20\\n\\n let pos = start\\n while (pos < max && this.src.charCodeAt(pos) === marker) { pos++ }\\n\\n const count = pos - start\\n\\n // treat end of the line as a whitespace\\n const nextChar = pos < max ? this.src.charCodeAt(pos) : 0x20\\n\\n const isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar))\\n const isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar))\\n\\n const isLastWhiteSpace = isWhiteSpace(lastChar)\\n const isNextWhiteSpace = isWhiteSpace(nextChar)\\n\\n const left_flanking =\\n !isNextWhiteSpace && (!isNextPunctChar || isLastWhiteSpace || isLastPunctChar)\\n const right_flanking =\\n !isLastWhiteSpace && (!isLastPunctChar || isNextWhiteSpace || isNextPunctChar)\\n\\n const can_open = left_flanking && (canSplitWord || !right_flanking || isLastPunctChar)\\n const can_close = right_flanking && (canSplitWord || !left_flanking || isNextPunctChar)\\n\\n return { can_open, can_close, length: count }\\n}\\n\\n// re-export Token class to use in block rules\\nStateInline.prototype.Token = Token\\n\\nexport default StateInline\\n\",\"// Skip text characters for text token, place those to pending buffer\\n// and increment current pos\\n\\n// Rule to skip pure text\\n// '{}$%@~+=:' reserved for extentions\\n\\n// !, \\\", #, $, %, &, ', (, ), *, +, ,, -, ., /, :, ;, <, =, >, ?, @, [, \\\\, ], ^, _, `, {, |, }, or ~\\n\\n// !!!! Don't confuse with \\\"Markdown ASCII Punctuation\\\" chars\\n// http://spec.commonmark.org/0.15/#ascii-punctuation-character\\nfunction isTerminatorChar (ch) {\\n switch (ch) {\\n case 0x0A/* \\\\n */:\\n case 0x21/* ! */:\\n case 0x23/* # */:\\n case 0x24/* $ */:\\n case 0x25/* % */:\\n case 0x26/* & */:\\n case 0x2A/* * */:\\n case 0x2B/* + */:\\n case 0x2D/* - */:\\n case 0x3A/* : */:\\n case 0x3C/* < */:\\n case 0x3D/* = */:\\n case 0x3E/* > */:\\n case 0x40/* @ */:\\n case 0x5B/* [ */:\\n case 0x5C/* \\\\ */:\\n case 0x5D/* ] */:\\n case 0x5E/* ^ */:\\n case 0x5F/* _ */:\\n case 0x60/* ` */:\\n case 0x7B/* { */:\\n case 0x7D/* } */:\\n case 0x7E/* ~ */:\\n return true\\n default:\\n return false\\n }\\n}\\n\\nexport default function text (state, silent) {\\n let pos = state.pos\\n\\n while (pos < state.posMax && !isTerminatorChar(state.src.charCodeAt(pos))) {\\n pos++\\n }\\n\\n if (pos === state.pos) { return false }\\n\\n if (!silent) { state.pending += state.src.slice(state.pos, pos) }\\n\\n state.pos = pos\\n\\n return true\\n}\\n\\n// Alternative implementation, for memory.\\n//\\n// It costs 10% of performance, but allows extend terminators list, if place it\\n// to `ParserInline` property. Probably, will switch to it sometime, such\\n// flexibility required.\\n\\n/*\\nvar TERMINATOR_RE = /[\\\\n!#$%&*+\\\\-:<=>@[\\\\\\\\\\\\]^_`{}~]/;\\n\\nmodule.exports = function text(state, silent) {\\n var pos = state.pos,\\n idx = state.src.slice(pos).search(TERMINATOR_RE);\\n\\n // first char is terminator -> empty text\\n if (idx === 0) { return false; }\\n\\n // no terminator -> text till end of string\\n if (idx < 0) {\\n if (!silent) { state.pending += state.src.slice(pos); }\\n state.pos = state.src.length;\\n return true;\\n }\\n\\n if (!silent) { state.pending += state.src.slice(pos, pos + idx); }\\n\\n state.pos += idx;\\n\\n return true;\\n}; */\\n\",\"// Process links like https://example.org/\\n\\n// RFC3986: scheme = ALPHA *( ALPHA / DIGIT / \\\"+\\\" / \\\"-\\\" / \\\".\\\" )\\nconst SCHEME_RE = /(?:^|[^a-z0-9.+-])([a-z][a-z0-9.+-]*)$/i\\n\\nexport default function linkify (state, silent) {\\n if (!state.md.options.linkify) return false\\n if (state.linkLevel > 0) return false\\n\\n const pos = state.pos\\n const max = state.posMax\\n\\n if (pos + 3 > max) return false\\n if (state.src.charCodeAt(pos) !== 0x3A/* : */) return false\\n if (state.src.charCodeAt(pos + 1) !== 0x2F/* / */) return false\\n if (state.src.charCodeAt(pos + 2) !== 0x2F/* / */) return false\\n\\n const match = state.pending.match(SCHEME_RE)\\n if (!match) return false\\n\\n const proto = match[1]\\n\\n const link = state.md.linkify.matchAtStart(state.src.slice(pos - proto.length))\\n if (!link) return false\\n\\n let url = link.url\\n\\n // invalid link, but still detected by linkify somehow;\\n // need to check to prevent infinite loop below\\n if (url.length <= proto.length) return false\\n\\n // disallow '*' at the end of the link (conflicts with emphasis)\\n // do manual backsearch to avoid perf issues with regex /\\\\*+$/ on \\\"****...****a\\\".\\n let urlEnd = url.length\\n while (urlEnd > 0 && url.charCodeAt(urlEnd - 1) === 0x2A/* * */) {\\n urlEnd--\\n }\\n if (urlEnd !== url.length) {\\n url = url.slice(0, urlEnd)\\n }\\n\\n const fullUrl = state.md.normalizeLink(url)\\n if (!state.md.validateLink(fullUrl)) return false\\n\\n if (!silent) {\\n state.pending = state.pending.slice(0, -proto.length)\\n\\n const token_o = state.push('link_open', 'a', 1)\\n token_o.attrs = [['href', fullUrl]]\\n token_o.markup = 'linkify'\\n token_o.info = 'auto'\\n\\n const token_t = state.push('text', '', 0)\\n token_t.content = state.md.normalizeLinkText(url)\\n\\n const token_c = state.push('link_close', 'a', -1)\\n token_c.markup = 'linkify'\\n token_c.info = 'auto'\\n }\\n\\n state.pos += url.length - proto.length\\n return true\\n}\\n\",\"// Proceess '\\\\n'\\n\\nimport { isSpace } from '../common/utils.mjs'\\n\\nexport default function newline (state, silent) {\\n let pos = state.pos\\n\\n if (state.src.charCodeAt(pos) !== 0x0A/* \\\\n */) { return false }\\n\\n const pmax = state.pending.length - 1\\n const max = state.posMax\\n\\n // ' \\\\n' -> hardbreak\\n // Lookup in pending chars is bad practice! Don't copy to other rules!\\n // Pending string is stored in concat mode, indexed lookups will cause\\n // convertion to flat mode.\\n if (!silent) {\\n if (pmax >= 0 && state.pending.charCodeAt(pmax) === 0x20) {\\n if (pmax >= 1 && state.pending.charCodeAt(pmax - 1) === 0x20) {\\n // Find whitespaces tail of pending chars.\\n let ws = pmax - 1\\n while (ws >= 1 && state.pending.charCodeAt(ws - 1) === 0x20) ws--\\n\\n state.pending = state.pending.slice(0, ws)\\n state.push('hardbreak', 'br', 0)\\n } else {\\n state.pending = state.pending.slice(0, -1)\\n state.push('softbreak', 'br', 0)\\n }\\n } else {\\n state.push('softbreak', 'br', 0)\\n }\\n }\\n\\n pos++\\n\\n // skip heading spaces for next line\\n while (pos < max && isSpace(state.src.charCodeAt(pos))) { pos++ }\\n\\n state.pos = pos\\n return true\\n}\\n\",\"// Process escaped chars and hardbreaks\\n\\nimport { isSpace } from '../common/utils.mjs'\\n\\nconst ESCAPED = []\\n\\nfor (let i = 0; i < 256; i++) { ESCAPED.push(0) }\\n\\n'\\\\\\\\!\\\"#$%&\\\\'()*+,./:;<=>?@[]^_`{|}~-'\\n .split('').forEach(function (ch) { ESCAPED[ch.charCodeAt(0)] = 1 })\\n\\nexport default function escape (state, silent) {\\n let pos = state.pos\\n const max = state.posMax\\n\\n if (state.src.charCodeAt(pos) !== 0x5C/* \\\\ */) return false\\n pos++\\n\\n // '\\\\' at the end of the inline block\\n if (pos >= max) return false\\n\\n let ch1 = state.src.charCodeAt(pos)\\n\\n if (ch1 === 0x0A) {\\n if (!silent) {\\n state.push('hardbreak', 'br', 0)\\n }\\n\\n pos++\\n // skip leading whitespaces from next line\\n while (pos < max) {\\n ch1 = state.src.charCodeAt(pos)\\n if (!isSpace(ch1)) break\\n pos++\\n }\\n\\n state.pos = pos\\n return true\\n }\\n\\n let escapedStr = state.src[pos]\\n\\n if (ch1 >= 0xD800 && ch1 <= 0xDBFF && pos + 1 < max) {\\n const ch2 = state.src.charCodeAt(pos + 1)\\n\\n if (ch2 >= 0xDC00 && ch2 <= 0xDFFF) {\\n escapedStr += state.src[pos + 1]\\n pos++\\n }\\n }\\n\\n const origStr = '\\\\\\\\' + escapedStr\\n\\n if (!silent) {\\n const token = state.push('text_special', '', 0)\\n\\n if (ch1 < 256 && ESCAPED[ch1] !== 0) {\\n token.content = escapedStr\\n } else {\\n token.content = origStr\\n }\\n\\n token.markup = origStr\\n token.info = 'escape'\\n }\\n\\n state.pos = pos + 1\\n return true\\n}\\n\",\"// Parse backticks\\n\\nexport default function backtick (state, silent) {\\n let pos = state.pos\\n const ch = state.src.charCodeAt(pos)\\n\\n if (ch !== 0x60/* ` */) { return false }\\n\\n const start = pos\\n pos++\\n const max = state.posMax\\n\\n // scan marker length\\n while (pos < max && state.src.charCodeAt(pos) === 0x60/* ` */) { pos++ }\\n\\n const marker = state.src.slice(start, pos)\\n const openerLength = marker.length\\n\\n if (state.backticksScanned && (state.backticks[openerLength] || 0) <= start) {\\n if (!silent) state.pending += marker\\n state.pos += openerLength\\n return true\\n }\\n\\n let matchEnd = pos\\n let matchStart\\n\\n // Nothing found in the cache, scan until the end of the line (or until marker is found)\\n while ((matchStart = state.src.indexOf('`', matchEnd)) !== -1) {\\n matchEnd = matchStart + 1\\n\\n // scan marker length\\n while (matchEnd < max && state.src.charCodeAt(matchEnd) === 0x60/* ` */) { matchEnd++ }\\n\\n const closerLength = matchEnd - matchStart\\n\\n if (closerLength === openerLength) {\\n // Found matching closer length.\\n if (!silent) {\\n const token = state.push('code_inline', 'code', 0)\\n token.markup = marker\\n token.content = state.src.slice(pos, matchStart)\\n .replace(/\\\\n/g, ' ')\\n .replace(/^ (.+) $/, '$1')\\n }\\n state.pos = matchEnd\\n return true\\n }\\n\\n // Some different length found, put it in cache as upper limit of where closer can be found\\n state.backticks[closerLength] = matchStart\\n }\\n\\n // Scanned through the end, didn't find anything\\n state.backticksScanned = true\\n\\n if (!silent) state.pending += marker\\n state.pos += openerLength\\n return true\\n}\\n\",\"// ~~strike through~~\\n//\\n\\n// Insert each marker as a separate text token, and add it to delimiter list\\n//\\nfunction strikethrough_tokenize (state, silent) {\\n const start = state.pos\\n const marker = state.src.charCodeAt(start)\\n\\n if (silent) { return false }\\n\\n if (marker !== 0x7E/* ~ */) { return false }\\n\\n const scanned = state.scanDelims(state.pos, true)\\n let len = scanned.length\\n const ch = String.fromCharCode(marker)\\n\\n if (len < 2) { return false }\\n\\n let token\\n\\n if (len % 2) {\\n token = state.push('text', '', 0)\\n token.content = ch\\n len--\\n }\\n\\n for (let i = 0; i < len; i += 2) {\\n token = state.push('text', '', 0)\\n token.content = ch + ch\\n\\n state.delimiters.push({\\n marker,\\n length: 0, // disable \\\"rule of 3\\\" length checks meant for emphasis\\n token: state.tokens.length - 1,\\n end: -1,\\n open: scanned.can_open,\\n close: scanned.can_close\\n })\\n }\\n\\n state.pos += scanned.length\\n\\n return true\\n}\\n\\nfunction postProcess (state, delimiters) {\\n let token\\n const loneMarkers = []\\n const max = delimiters.length\\n\\n for (let i = 0; i < max; i++) {\\n const startDelim = delimiters[i]\\n\\n if (startDelim.marker !== 0x7E/* ~ */) {\\n continue\\n }\\n\\n if (startDelim.end === -1) {\\n continue\\n }\\n\\n const endDelim = delimiters[startDelim.end]\\n\\n token = state.tokens[startDelim.token]\\n token.type = 's_open'\\n token.tag = 's'\\n token.nesting = 1\\n token.markup = '~~'\\n token.content = ''\\n\\n token = state.tokens[endDelim.token]\\n token.type = 's_close'\\n token.tag = 's'\\n token.nesting = -1\\n token.markup = '~~'\\n token.content = ''\\n\\n if (state.tokens[endDelim.token - 1].type === 'text' &&\\n state.tokens[endDelim.token - 1].content === '~') {\\n loneMarkers.push(endDelim.token - 1)\\n }\\n }\\n\\n // If a marker sequence has an odd number of characters, it's splitted\\n // like this: `~~~~~` -> `~` + `~~` + `~~`, leaving one marker at the\\n // start of the sequence.\\n //\\n // So, we have to move all those markers after subsequent s_close tags.\\n //\\n while (loneMarkers.length) {\\n const i = loneMarkers.pop()\\n let j = i + 1\\n\\n while (j < state.tokens.length && state.tokens[j].type === 's_close') {\\n j++\\n }\\n\\n j--\\n\\n if (i !== j) {\\n token = state.tokens[j]\\n state.tokens[j] = state.tokens[i]\\n state.tokens[i] = token\\n }\\n }\\n}\\n\\n// Walk through delimiter list and replace text tokens with tags\\n//\\nfunction strikethrough_postProcess (state) {\\n const tokens_meta = state.tokens_meta\\n const max = state.tokens_meta.length\\n\\n postProcess(state, state.delimiters)\\n\\n for (let curr = 0; curr < max; curr++) {\\n if (tokens_meta[curr] && tokens_meta[curr].delimiters) {\\n postProcess(state, tokens_meta[curr].delimiters)\\n }\\n }\\n}\\n\\nexport default {\\n tokenize: strikethrough_tokenize,\\n postProcess: strikethrough_postProcess\\n}\\n\",\"// Process *this* and _that_\\n//\\n\\n// Insert each marker as a separate text token, and add it to delimiter list\\n//\\nfunction emphasis_tokenize (state, silent) {\\n const start = state.pos\\n const marker = state.src.charCodeAt(start)\\n\\n if (silent) { return false }\\n\\n if (marker !== 0x5F /* _ */ && marker !== 0x2A /* * */) { return false }\\n\\n const scanned = state.scanDelims(state.pos, marker === 0x2A)\\n\\n for (let i = 0; i < scanned.length; i++) {\\n const token = state.push('text', '', 0)\\n token.content = String.fromCharCode(marker)\\n\\n state.delimiters.push({\\n // Char code of the starting marker (number).\\n //\\n marker,\\n\\n // Total length of these series of delimiters.\\n //\\n length: scanned.length,\\n\\n // A position of the token this delimiter corresponds to.\\n //\\n token: state.tokens.length - 1,\\n\\n // If this delimiter is matched as a valid opener, `end` will be\\n // equal to its position, otherwise it's `-1`.\\n //\\n end: -1,\\n\\n // Boolean flags that determine if this delimiter could open or close\\n // an emphasis.\\n //\\n open: scanned.can_open,\\n close: scanned.can_close\\n })\\n }\\n\\n state.pos += scanned.length\\n\\n return true\\n}\\n\\nfunction postProcess (state, delimiters) {\\n const max = delimiters.length\\n\\n for (let i = max - 1; i >= 0; i--) {\\n const startDelim = delimiters[i]\\n\\n if (startDelim.marker !== 0x5F/* _ */ && startDelim.marker !== 0x2A/* * */) {\\n continue\\n }\\n\\n // Process only opening markers\\n if (startDelim.end === -1) {\\n continue\\n }\\n\\n const endDelim = delimiters[startDelim.end]\\n\\n // If the previous delimiter has the same marker and is adjacent to this one,\\n // merge those into one strong delimiter.\\n //\\n // `whatever` -> `whatever`\\n //\\n const isStrong = i > 0 &&\\n delimiters[i - 1].end === startDelim.end + 1 &&\\n // check that first two markers match and adjacent\\n delimiters[i - 1].marker === startDelim.marker &&\\n delimiters[i - 1].token === startDelim.token - 1 &&\\n // check that last two markers are adjacent (we can safely assume they match)\\n delimiters[startDelim.end + 1].token === endDelim.token + 1\\n\\n const ch = String.fromCharCode(startDelim.marker)\\n\\n const token_o = state.tokens[startDelim.token]\\n token_o.type = isStrong ? 'strong_open' : 'em_open'\\n token_o.tag = isStrong ? 'strong' : 'em'\\n token_o.nesting = 1\\n token_o.markup = isStrong ? ch + ch : ch\\n token_o.content = ''\\n\\n const token_c = state.tokens[endDelim.token]\\n token_c.type = isStrong ? 'strong_close' : 'em_close'\\n token_c.tag = isStrong ? 'strong' : 'em'\\n token_c.nesting = -1\\n token_c.markup = isStrong ? ch + ch : ch\\n token_c.content = ''\\n\\n if (isStrong) {\\n state.tokens[delimiters[i - 1].token].content = ''\\n state.tokens[delimiters[startDelim.end + 1].token].content = ''\\n i--\\n }\\n }\\n}\\n\\n// Walk through delimiter list and replace text tokens with tags\\n//\\nfunction emphasis_post_process (state) {\\n const tokens_meta = state.tokens_meta\\n const max = state.tokens_meta.length\\n\\n postProcess(state, state.delimiters)\\n\\n for (let curr = 0; curr < max; curr++) {\\n if (tokens_meta[curr] && tokens_meta[curr].delimiters) {\\n postProcess(state, tokens_meta[curr].delimiters)\\n }\\n }\\n}\\n\\nexport default {\\n tokenize: emphasis_tokenize,\\n postProcess: emphasis_post_process\\n}\\n\",\"// Process [link]( \\\"stuff\\\")\\n\\nimport { normalizeReference, isSpace } from '../common/utils.mjs'\\n\\nexport default function link (state, silent) {\\n let code, label, res, ref\\n let href = ''\\n let title = ''\\n let start = state.pos\\n let parseReference = true\\n\\n if (state.src.charCodeAt(state.pos) !== 0x5B/* [ */) { return false }\\n\\n const oldPos = state.pos\\n const max = state.posMax\\n const labelStart = state.pos + 1\\n const labelEnd = state.md.helpers.parseLinkLabel(state, state.pos, true)\\n\\n // parser failed to find ']', so it's not a valid link\\n if (labelEnd < 0) { return false }\\n\\n let pos = labelEnd + 1\\n if (pos < max && state.src.charCodeAt(pos) === 0x28/* ( */) {\\n //\\n // Inline link\\n //\\n\\n // might have found a valid shortcut link, disable reference parsing\\n parseReference = false\\n\\n // [link]( \\\"title\\\" )\\n // ^^ skipping these spaces\\n pos++\\n for (; pos < max; pos++) {\\n code = state.src.charCodeAt(pos)\\n if (!isSpace(code) && code !== 0x0A) { break }\\n }\\n if (pos >= max) { return false }\\n\\n // [link]( \\\"title\\\" )\\n // ^^^^^^ parsing link destination\\n start = pos\\n res = state.md.helpers.parseLinkDestination(state.src, pos, state.posMax)\\n if (res.ok) {\\n href = state.md.normalizeLink(res.str)\\n if (state.md.validateLink(href)) {\\n pos = res.pos\\n } else {\\n href = ''\\n }\\n\\n // [link]( \\\"title\\\" )\\n // ^^ skipping these spaces\\n start = pos\\n for (; pos < max; pos++) {\\n code = state.src.charCodeAt(pos)\\n if (!isSpace(code) && code !== 0x0A) { break }\\n }\\n\\n // [link]( \\\"title\\\" )\\n // ^^^^^^^ parsing link title\\n res = state.md.helpers.parseLinkTitle(state.src, pos, state.posMax)\\n if (pos < max && start !== pos && res.ok) {\\n title = res.str\\n pos = res.pos\\n\\n // [link]( \\\"title\\\" )\\n // ^^ skipping these spaces\\n for (; pos < max; pos++) {\\n code = state.src.charCodeAt(pos)\\n if (!isSpace(code) && code !== 0x0A) { break }\\n }\\n }\\n }\\n\\n if (pos >= max || state.src.charCodeAt(pos) !== 0x29/* ) */) {\\n // parsing a valid shortcut link failed, fallback to reference\\n parseReference = true\\n }\\n pos++\\n }\\n\\n if (parseReference) {\\n //\\n // Link reference\\n //\\n if (typeof state.env.references === 'undefined') { return false }\\n\\n if (pos < max && state.src.charCodeAt(pos) === 0x5B/* [ */) {\\n start = pos + 1\\n pos = state.md.helpers.parseLinkLabel(state, pos)\\n if (pos >= 0) {\\n label = state.src.slice(start, pos++)\\n } else {\\n pos = labelEnd + 1\\n }\\n } else {\\n pos = labelEnd + 1\\n }\\n\\n // covers label === '' and label === undefined\\n // (collapsed reference link and shortcut reference link respectively)\\n if (!label) { label = state.src.slice(labelStart, labelEnd) }\\n\\n ref = state.env.references[normalizeReference(label)]\\n if (!ref) {\\n state.pos = oldPos\\n return false\\n }\\n href = ref.href\\n title = ref.title\\n }\\n\\n //\\n // We found the end of the link, and know for a fact it's a valid link;\\n // so all that's left to do is to call tokenizer.\\n //\\n if (!silent) {\\n state.pos = labelStart\\n state.posMax = labelEnd\\n\\n const token_o = state.push('link_open', 'a', 1)\\n const attrs = [['href', href]]\\n token_o.attrs = attrs\\n if (title) {\\n attrs.push(['title', title])\\n }\\n\\n state.linkLevel++\\n state.md.inline.tokenize(state)\\n state.linkLevel--\\n\\n state.push('link_close', 'a', -1)\\n }\\n\\n state.pos = pos\\n state.posMax = max\\n return true\\n}\\n\",\"// Process ![image]( \\\"title\\\")\\n\\nimport { normalizeReference, isSpace } from '../common/utils.mjs'\\n\\nexport default function image (state, silent) {\\n let code, content, label, pos, ref, res, title, start\\n let href = ''\\n const oldPos = state.pos\\n const max = state.posMax\\n\\n if (state.src.charCodeAt(state.pos) !== 0x21/* ! */) { return false }\\n if (state.src.charCodeAt(state.pos + 1) !== 0x5B/* [ */) { return false }\\n\\n const labelStart = state.pos + 2\\n const labelEnd = state.md.helpers.parseLinkLabel(state, state.pos + 1, false)\\n\\n // parser failed to find ']', so it's not a valid link\\n if (labelEnd < 0) { return false }\\n\\n pos = labelEnd + 1\\n if (pos < max && state.src.charCodeAt(pos) === 0x28/* ( */) {\\n //\\n // Inline link\\n //\\n\\n // [link]( \\\"title\\\" )\\n // ^^ skipping these spaces\\n pos++\\n for (; pos < max; pos++) {\\n code = state.src.charCodeAt(pos)\\n if (!isSpace(code) && code !== 0x0A) { break }\\n }\\n if (pos >= max) { return false }\\n\\n // [link]( \\\"title\\\" )\\n // ^^^^^^ parsing link destination\\n start = pos\\n res = state.md.helpers.parseLinkDestination(state.src, pos, state.posMax)\\n if (res.ok) {\\n href = state.md.normalizeLink(res.str)\\n if (state.md.validateLink(href)) {\\n pos = res.pos\\n } else {\\n href = ''\\n }\\n }\\n\\n // [link]( \\\"title\\\" )\\n // ^^ skipping these spaces\\n start = pos\\n for (; pos < max; pos++) {\\n code = state.src.charCodeAt(pos)\\n if (!isSpace(code) && code !== 0x0A) { break }\\n }\\n\\n // [link]( \\\"title\\\" )\\n // ^^^^^^^ parsing link title\\n res = state.md.helpers.parseLinkTitle(state.src, pos, state.posMax)\\n if (pos < max && start !== pos && res.ok) {\\n title = res.str\\n pos = res.pos\\n\\n // [link]( \\\"title\\\" )\\n // ^^ skipping these spaces\\n for (; pos < max; pos++) {\\n code = state.src.charCodeAt(pos)\\n if (!isSpace(code) && code !== 0x0A) { break }\\n }\\n } else {\\n title = ''\\n }\\n\\n if (pos >= max || state.src.charCodeAt(pos) !== 0x29/* ) */) {\\n state.pos = oldPos\\n return false\\n }\\n pos++\\n } else {\\n //\\n // Link reference\\n //\\n if (typeof state.env.references === 'undefined') { return false }\\n\\n if (pos < max && state.src.charCodeAt(pos) === 0x5B/* [ */) {\\n start = pos + 1\\n pos = state.md.helpers.parseLinkLabel(state, pos)\\n if (pos >= 0) {\\n label = state.src.slice(start, pos++)\\n } else {\\n pos = labelEnd + 1\\n }\\n } else {\\n pos = labelEnd + 1\\n }\\n\\n // covers label === '' and label === undefined\\n // (collapsed reference link and shortcut reference link respectively)\\n if (!label) { label = state.src.slice(labelStart, labelEnd) }\\n\\n ref = state.env.references[normalizeReference(label)]\\n if (!ref) {\\n state.pos = oldPos\\n return false\\n }\\n href = ref.href\\n title = ref.title\\n }\\n\\n //\\n // We found the end of the link, and know for a fact it's a valid link;\\n // so all that's left to do is to call tokenizer.\\n //\\n if (!silent) {\\n content = state.src.slice(labelStart, labelEnd)\\n\\n const tokens = []\\n state.md.inline.parse(\\n content,\\n state.md,\\n state.env,\\n tokens\\n )\\n\\n const token = state.push('image', 'img', 0)\\n const attrs = [['src', href], ['alt', '']]\\n token.attrs = attrs\\n token.children = tokens\\n token.content = content\\n\\n if (title) {\\n attrs.push(['title', title])\\n }\\n }\\n\\n state.pos = pos\\n state.posMax = max\\n return true\\n}\\n\",\"// Process autolinks ''\\n\\n/* eslint max-len:0 */\\nconst EMAIL_RE = /^([a-zA-Z0-9.!#$%&'*+/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\\\\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*)$/\\n/* eslint-disable-next-line no-control-regex */\\nconst AUTOLINK_RE = /^([a-zA-Z][a-zA-Z0-9+.-]{1,31}):([^<>\\\\x00-\\\\x20]*)$/\\n\\nexport default function autolink (state, silent) {\\n let pos = state.pos\\n\\n if (state.src.charCodeAt(pos) !== 0x3C/* < */) { return false }\\n\\n const start = state.pos\\n const max = state.posMax\\n\\n for (;;) {\\n if (++pos >= max) return false\\n\\n const ch = state.src.charCodeAt(pos)\\n\\n if (ch === 0x3C /* < */) return false\\n if (ch === 0x3E /* > */) break\\n }\\n\\n const url = state.src.slice(start + 1, pos)\\n\\n if (AUTOLINK_RE.test(url)) {\\n const fullUrl = state.md.normalizeLink(url)\\n if (!state.md.validateLink(fullUrl)) { return false }\\n\\n if (!silent) {\\n const token_o = state.push('link_open', 'a', 1)\\n token_o.attrs = [['href', fullUrl]]\\n token_o.markup = 'autolink'\\n token_o.info = 'auto'\\n\\n const token_t = state.push('text', '', 0)\\n token_t.content = state.md.normalizeLinkText(url)\\n\\n const token_c = state.push('link_close', 'a', -1)\\n token_c.markup = 'autolink'\\n token_c.info = 'auto'\\n }\\n\\n state.pos += url.length + 2\\n return true\\n }\\n\\n if (EMAIL_RE.test(url)) {\\n const fullUrl = state.md.normalizeLink('mailto:' + url)\\n if (!state.md.validateLink(fullUrl)) { return false }\\n\\n if (!silent) {\\n const token_o = state.push('link_open', 'a', 1)\\n token_o.attrs = [['href', fullUrl]]\\n token_o.markup = 'autolink'\\n token_o.info = 'auto'\\n\\n const token_t = state.push('text', '', 0)\\n token_t.content = state.md.normalizeLinkText(url)\\n\\n const token_c = state.push('link_close', 'a', -1)\\n token_c.markup = 'autolink'\\n token_c.info = 'auto'\\n }\\n\\n state.pos += url.length + 2\\n return true\\n }\\n\\n return false\\n}\\n\",\"// Process html tags\\n\\nimport { HTML_TAG_RE } from '../common/html_re.mjs'\\n\\nfunction isLinkOpen (str) {\\n return /^\\\\s]/i.test(str)\\n}\\nfunction isLinkClose (str) {\\n return /^<\\\\/a\\\\s*>/i.test(str)\\n}\\n\\nfunction isLetter (ch) {\\n /* eslint no-bitwise:0 */\\n const lc = ch | 0x20 // to lower case\\n return (lc >= 0x61/* a */) && (lc <= 0x7a/* z */)\\n}\\n\\nexport default function html_inline (state, silent) {\\n if (!state.md.options.html) { return false }\\n\\n // Check start\\n const max = state.posMax\\n const pos = state.pos\\n if (state.src.charCodeAt(pos) !== 0x3C/* < */ ||\\n pos + 2 >= max) {\\n return false\\n }\\n\\n // Quick fail on second char\\n const ch = state.src.charCodeAt(pos + 1)\\n if (ch !== 0x21/* ! */ &&\\n ch !== 0x3F/* ? */ &&\\n ch !== 0x2F/* / */ &&\\n !isLetter(ch)) {\\n return false\\n }\\n\\n const match = state.src.slice(pos).match(HTML_TAG_RE)\\n if (!match) { return false }\\n\\n if (!silent) {\\n const token = state.push('html_inline', '', 0)\\n token.content = match[0]\\n\\n if (isLinkOpen(token.content)) state.linkLevel++\\n if (isLinkClose(token.content)) state.linkLevel--\\n }\\n state.pos += match[0].length\\n return true\\n}\\n\",\"// Process html entity - {, ¯, ", ...\\n\\nimport { decodeHTML } from 'entities'\\nimport { isValidEntityCode, fromCodePoint } from '../common/utils.mjs'\\n\\nconst DIGITAL_RE = /^&#((?:x[a-f0-9]{1,6}|[0-9]{1,7}));/i\\nconst NAMED_RE = /^&([a-z][a-z0-9]{1,31});/i\\n\\nexport default function entity (state, silent) {\\n const pos = state.pos\\n const max = state.posMax\\n\\n if (state.src.charCodeAt(pos) !== 0x26/* & */) return false\\n\\n if (pos + 1 >= max) return false\\n\\n const ch = state.src.charCodeAt(pos + 1)\\n\\n if (ch === 0x23 /* # */) {\\n const match = state.src.slice(pos).match(DIGITAL_RE)\\n if (match) {\\n if (!silent) {\\n const code = match[1][0].toLowerCase() === 'x' ? parseInt(match[1].slice(1), 16) : parseInt(match[1], 10)\\n\\n const token = state.push('text_special', '', 0)\\n token.content = isValidEntityCode(code) ? fromCodePoint(code) : fromCodePoint(0xFFFD)\\n token.markup = match[0]\\n token.info = 'entity'\\n }\\n state.pos += match[0].length\\n return true\\n }\\n } else {\\n const match = state.src.slice(pos).match(NAMED_RE)\\n if (match) {\\n const decoded = decodeHTML(match[0])\\n if (decoded !== match[0]) {\\n if (!silent) {\\n const token = state.push('text_special', '', 0)\\n token.content = decoded\\n token.markup = match[0]\\n token.info = 'entity'\\n }\\n state.pos += match[0].length\\n return true\\n }\\n }\\n }\\n\\n return false\\n}\\n\",\"// For each opening emphasis-like marker find a matching closing one\\n//\\n\\nfunction processDelimiters (delimiters) {\\n const openersBottom = {}\\n const max = delimiters.length\\n\\n if (!max) return\\n\\n // headerIdx is the first delimiter of the current (where closer is) delimiter run\\n let headerIdx = 0\\n let lastTokenIdx = -2 // needs any value lower than -1\\n const jumps = []\\n\\n for (let closerIdx = 0; closerIdx < max; closerIdx++) {\\n const closer = delimiters[closerIdx]\\n\\n jumps.push(0)\\n\\n // markers belong to same delimiter run if:\\n // - they have adjacent tokens\\n // - AND markers are the same\\n //\\n if (delimiters[headerIdx].marker !== closer.marker || lastTokenIdx !== closer.token - 1) {\\n headerIdx = closerIdx\\n }\\n\\n lastTokenIdx = closer.token\\n\\n // Length is only used for emphasis-specific \\\"rule of 3\\\",\\n // if it's not defined (in strikethrough or 3rd party plugins),\\n // we can default it to 0 to disable those checks.\\n //\\n closer.length = closer.length || 0\\n\\n if (!closer.close) continue\\n\\n // Previously calculated lower bounds (previous fails)\\n // for each marker, each delimiter length modulo 3,\\n // and for whether this closer can be an opener;\\n // https://github.com/commonmark/cmark/commit/34250e12ccebdc6372b8b49c44fab57c72443460\\n /* eslint-disable-next-line no-prototype-builtins */\\n if (!openersBottom.hasOwnProperty(closer.marker)) {\\n openersBottom[closer.marker] = [-1, -1, -1, -1, -1, -1]\\n }\\n\\n const minOpenerIdx = openersBottom[closer.marker][(closer.open ? 3 : 0) + (closer.length % 3)]\\n\\n let openerIdx = headerIdx - jumps[headerIdx] - 1\\n\\n let newMinOpenerIdx = openerIdx\\n\\n for (; openerIdx > minOpenerIdx; openerIdx -= jumps[openerIdx] + 1) {\\n const opener = delimiters[openerIdx]\\n\\n if (opener.marker !== closer.marker) continue\\n\\n if (opener.open && opener.end < 0) {\\n let isOddMatch = false\\n\\n // from spec:\\n //\\n // If one of the delimiters can both open and close emphasis, then the\\n // sum of the lengths of the delimiter runs containing the opening and\\n // closing delimiters must not be a multiple of 3 unless both lengths\\n // are multiples of 3.\\n //\\n if (opener.close || closer.open) {\\n if ((opener.length + closer.length) % 3 === 0) {\\n if (opener.length % 3 !== 0 || closer.length % 3 !== 0) {\\n isOddMatch = true\\n }\\n }\\n }\\n\\n if (!isOddMatch) {\\n // If previous delimiter cannot be an opener, we can safely skip\\n // the entire sequence in future checks. This is required to make\\n // sure algorithm has linear complexity (see *_*_*_*_*_... case).\\n //\\n const lastJump = openerIdx > 0 && !delimiters[openerIdx - 1].open\\n ? jumps[openerIdx - 1] + 1\\n : 0\\n\\n jumps[closerIdx] = closerIdx - openerIdx + lastJump\\n jumps[openerIdx] = lastJump\\n\\n closer.open = false\\n opener.end = closerIdx\\n opener.close = false\\n newMinOpenerIdx = -1\\n // treat next token as start of run,\\n // it optimizes skips in **<...>**a**<...>** pathological case\\n lastTokenIdx = -2\\n break\\n }\\n }\\n }\\n\\n if (newMinOpenerIdx !== -1) {\\n // If match for this delimiter run failed, we want to set lower bound for\\n // future lookups. This is required to make sure algorithm has linear\\n // complexity.\\n //\\n // See details here:\\n // https://github.com/commonmark/cmark/issues/178#issuecomment-270417442\\n //\\n openersBottom[closer.marker][(closer.open ? 3 : 0) + ((closer.length || 0) % 3)] = newMinOpenerIdx\\n }\\n }\\n}\\n\\nexport default function link_pairs (state) {\\n const tokens_meta = state.tokens_meta\\n const max = state.tokens_meta.length\\n\\n processDelimiters(state.delimiters)\\n\\n for (let curr = 0; curr < max; curr++) {\\n if (tokens_meta[curr] && tokens_meta[curr].delimiters) {\\n processDelimiters(tokens_meta[curr].delimiters)\\n }\\n }\\n}\\n\",\"// Clean up tokens after emphasis and strikethrough postprocessing:\\n// merge adjacent text nodes into one and re-calculate all token levels\\n//\\n// This is necessary because initially emphasis delimiter markers (*, _, ~)\\n// are treated as their own separate text tokens. Then emphasis rule either\\n// leaves them as text (needed to merge with adjacent text) or turns them\\n// into opening/closing tags (which messes up levels inside).\\n//\\n\\nexport default function fragments_join (state) {\\n let curr, last\\n let level = 0\\n const tokens = state.tokens\\n const max = state.tokens.length\\n\\n for (curr = last = 0; curr < max; curr++) {\\n // re-calculate levels after emphasis/strikethrough turns some text nodes\\n // into opening/closing tags\\n if (tokens[curr].nesting < 0) level-- // closing tag\\n tokens[curr].level = level\\n if (tokens[curr].nesting > 0) level++ // opening tag\\n\\n if (tokens[curr].type === 'text' &&\\n curr + 1 < max &&\\n tokens[curr + 1].type === 'text') {\\n // collapse two adjacent text nodes\\n tokens[curr + 1].content = tokens[curr].content + tokens[curr + 1].content\\n } else {\\n if (curr !== last) { tokens[last] = tokens[curr] }\\n\\n last++\\n }\\n }\\n\\n if (curr !== last) {\\n tokens.length = last\\n }\\n}\\n\",\"/** internal\\n * class ParserInline\\n *\\n * Tokenizes paragraph content.\\n **/\\n\\nimport Ruler from './ruler.mjs'\\nimport StateInline from './rules_inline/state_inline.mjs'\\n\\nimport r_text from './rules_inline/text.mjs'\\nimport r_linkify from './rules_inline/linkify.mjs'\\nimport r_newline from './rules_inline/newline.mjs'\\nimport r_escape from './rules_inline/escape.mjs'\\nimport r_backticks from './rules_inline/backticks.mjs'\\nimport r_strikethrough from './rules_inline/strikethrough.mjs'\\nimport r_emphasis from './rules_inline/emphasis.mjs'\\nimport r_link from './rules_inline/link.mjs'\\nimport r_image from './rules_inline/image.mjs'\\nimport r_autolink from './rules_inline/autolink.mjs'\\nimport r_html_inline from './rules_inline/html_inline.mjs'\\nimport r_entity from './rules_inline/entity.mjs'\\n\\nimport r_balance_pairs from './rules_inline/balance_pairs.mjs'\\nimport r_fragments_join from './rules_inline/fragments_join.mjs'\\n\\n// Parser rules\\n\\nconst _rules = [\\n ['text', r_text],\\n ['linkify', r_linkify],\\n ['newline', r_newline],\\n ['escape', r_escape],\\n ['backticks', r_backticks],\\n ['strikethrough', r_strikethrough.tokenize],\\n ['emphasis', r_emphasis.tokenize],\\n ['link', r_link],\\n ['image', r_image],\\n ['autolink', r_autolink],\\n ['html_inline', r_html_inline],\\n ['entity', r_entity]\\n]\\n\\n// `rule2` ruleset was created specifically for emphasis/strikethrough\\n// post-processing and may be changed in the future.\\n//\\n// Don't use this for anything except pairs (plugins working with `balance_pairs`).\\n//\\nconst _rules2 = [\\n ['balance_pairs', r_balance_pairs],\\n ['strikethrough', r_strikethrough.postProcess],\\n ['emphasis', r_emphasis.postProcess],\\n // rules for pairs separate '**' into its own text tokens, which may be left unused,\\n // rule below merges unused segments back with the rest of the text\\n ['fragments_join', r_fragments_join]\\n]\\n\\n/**\\n * new ParserInline()\\n **/\\nfunction ParserInline () {\\n /**\\n * ParserInline#ruler -> Ruler\\n *\\n * [[Ruler]] instance. Keep configuration of inline rules.\\n **/\\n this.ruler = new Ruler()\\n\\n for (let i = 0; i < _rules.length; i++) {\\n this.ruler.push(_rules[i][0], _rules[i][1])\\n }\\n\\n /**\\n * ParserInline#ruler2 -> Ruler\\n *\\n * [[Ruler]] instance. Second ruler used for post-processing\\n * (e.g. in emphasis-like rules).\\n **/\\n this.ruler2 = new Ruler()\\n\\n for (let i = 0; i < _rules2.length; i++) {\\n this.ruler2.push(_rules2[i][0], _rules2[i][1])\\n }\\n}\\n\\n// Skip single token by running all rules in validation mode;\\n// returns `true` if any rule reported success\\n//\\nParserInline.prototype.skipToken = function (state) {\\n const pos = state.pos\\n const rules = this.ruler.getRules('')\\n const len = rules.length\\n const maxNesting = state.md.options.maxNesting\\n const cache = state.cache\\n\\n if (typeof cache[pos] !== 'undefined') {\\n state.pos = cache[pos]\\n return\\n }\\n\\n let ok = false\\n\\n if (state.level < maxNesting) {\\n for (let i = 0; i < len; i++) {\\n // Increment state.level and decrement it later to limit recursion.\\n // It's harmless to do here, because no tokens are created. But ideally,\\n // we'd need a separate private state variable for this purpose.\\n //\\n state.level++\\n ok = rules[i](state, true)\\n state.level--\\n\\n if (ok) {\\n if (pos >= state.pos) { throw new Error(\\\"inline rule didn't increment state.pos\\\") }\\n break\\n }\\n }\\n } else {\\n // Too much nesting, just skip until the end of the paragraph.\\n //\\n // NOTE: this will cause links to behave incorrectly in the following case,\\n // when an amount of `[` is exactly equal to `maxNesting + 1`:\\n //\\n // [[[[[[[[[[[[[[[[[[[[[foo]()\\n //\\n // TODO: remove this workaround when CM standard will allow nested links\\n // (we can replace it by preventing links from being parsed in\\n // validation mode)\\n //\\n state.pos = state.posMax\\n }\\n\\n if (!ok) { state.pos++ }\\n cache[pos] = state.pos\\n}\\n\\n// Generate tokens for input range\\n//\\nParserInline.prototype.tokenize = function (state) {\\n const rules = this.ruler.getRules('')\\n const len = rules.length\\n const end = state.posMax\\n const maxNesting = state.md.options.maxNesting\\n\\n while (state.pos < end) {\\n // Try all possible rules.\\n // On success, rule should:\\n //\\n // - update `state.pos`\\n // - update `state.tokens`\\n // - return true\\n const prevPos = state.pos\\n let ok = false\\n\\n if (state.level < maxNesting) {\\n for (let i = 0; i < len; i++) {\\n ok = rules[i](state, false)\\n if (ok) {\\n if (prevPos >= state.pos) { throw new Error(\\\"inline rule didn't increment state.pos\\\") }\\n break\\n }\\n }\\n }\\n\\n if (ok) {\\n if (state.pos >= end) { break }\\n continue\\n }\\n\\n state.pending += state.src[state.pos++]\\n }\\n\\n if (state.pending) {\\n state.pushPending()\\n }\\n}\\n\\n/**\\n * ParserInline.parse(str, md, env, outTokens)\\n *\\n * Process input string and push inline tokens into `outTokens`\\n **/\\nParserInline.prototype.parse = function (str, md, env, outTokens) {\\n const state = new this.State(str, md, env, outTokens)\\n\\n this.tokenize(state)\\n\\n const rules = this.ruler2.getRules('')\\n const len = rules.length\\n\\n for (let i = 0; i < len; i++) {\\n rules[i](state)\\n }\\n}\\n\\nParserInline.prototype.State = StateInline\\n\\nexport default ParserInline\\n\",\"'use strict';\\n\\n/** Highest positive signed 32-bit float value */\\nconst maxInt = 2147483647; // aka. 0x7FFFFFFF or 2^31-1\\n\\n/** Bootstring parameters */\\nconst base = 36;\\nconst tMin = 1;\\nconst tMax = 26;\\nconst skew = 38;\\nconst damp = 700;\\nconst initialBias = 72;\\nconst initialN = 128; // 0x80\\nconst delimiter = '-'; // '\\\\x2D'\\n\\n/** Regular expressions */\\nconst regexPunycode = /^xn--/;\\nconst regexNonASCII = /[^\\\\0-\\\\x7F]/; // Note: U+007F DEL is excluded too.\\nconst regexSeparators = /[\\\\x2E\\\\u3002\\\\uFF0E\\\\uFF61]/g; // RFC 3490 separators\\n\\n/** Error messages */\\nconst errors = {\\n\\t'overflow': 'Overflow: input needs wider integers to process',\\n\\t'not-basic': 'Illegal input >= 0x80 (not a basic code point)',\\n\\t'invalid-input': 'Invalid input'\\n};\\n\\n/** Convenience shortcuts */\\nconst baseMinusTMin = base - tMin;\\nconst floor = Math.floor;\\nconst stringFromCharCode = String.fromCharCode;\\n\\n/*--------------------------------------------------------------------------*/\\n\\n/**\\n * A generic error utility function.\\n * @private\\n * @param {String} type The error type.\\n * @returns {Error} Throws a `RangeError` with the applicable error message.\\n */\\nfunction error(type) {\\n\\tthrow new RangeError(errors[type]);\\n}\\n\\n/**\\n * A generic `Array#map` utility function.\\n * @private\\n * @param {Array} array The array to iterate over.\\n * @param {Function} callback The function that gets called for every array\\n * item.\\n * @returns {Array} A new array of values returned by the callback function.\\n */\\nfunction map(array, callback) {\\n\\tconst result = [];\\n\\tlet length = array.length;\\n\\twhile (length--) {\\n\\t\\tresult[length] = callback(array[length]);\\n\\t}\\n\\treturn result;\\n}\\n\\n/**\\n * A simple `Array#map`-like wrapper to work with domain name strings or email\\n * addresses.\\n * @private\\n * @param {String} domain The domain name or email address.\\n * @param {Function} callback The function that gets called for every\\n * character.\\n * @returns {String} A new string of characters returned by the callback\\n * function.\\n */\\nfunction mapDomain(domain, callback) {\\n\\tconst parts = domain.split('@');\\n\\tlet result = '';\\n\\tif (parts.length > 1) {\\n\\t\\t// In email addresses, only the domain name should be punycoded. Leave\\n\\t\\t// the local part (i.e. everything up to `@`) intact.\\n\\t\\tresult = parts[0] + '@';\\n\\t\\tdomain = parts[1];\\n\\t}\\n\\t// Avoid `split(regex)` for IE8 compatibility. See #17.\\n\\tdomain = domain.replace(regexSeparators, '\\\\x2E');\\n\\tconst labels = domain.split('.');\\n\\tconst encoded = map(labels, callback).join('.');\\n\\treturn result + encoded;\\n}\\n\\n/**\\n * Creates an array containing the numeric code points of each Unicode\\n * character in the string. While JavaScript uses UCS-2 internally,\\n * this function will convert a pair of surrogate halves (each of which\\n * UCS-2 exposes as separate characters) into a single code point,\\n * matching UTF-16.\\n * @see `punycode.ucs2.encode`\\n * @see \\n * @memberOf punycode.ucs2\\n * @name decode\\n * @param {String} string The Unicode input string (UCS-2).\\n * @returns {Array} The new array of code points.\\n */\\nfunction ucs2decode(string) {\\n\\tconst output = [];\\n\\tlet counter = 0;\\n\\tconst length = string.length;\\n\\twhile (counter < length) {\\n\\t\\tconst value = string.charCodeAt(counter++);\\n\\t\\tif (value >= 0xD800 && value <= 0xDBFF && counter < length) {\\n\\t\\t\\t// It's a high surrogate, and there is a next character.\\n\\t\\t\\tconst extra = string.charCodeAt(counter++);\\n\\t\\t\\tif ((extra & 0xFC00) == 0xDC00) { // Low surrogate.\\n\\t\\t\\t\\toutput.push(((value & 0x3FF) << 10) + (extra & 0x3FF) + 0x10000);\\n\\t\\t\\t} else {\\n\\t\\t\\t\\t// It's an unmatched surrogate; only append this code unit, in case the\\n\\t\\t\\t\\t// next code unit is the high surrogate of a surrogate pair.\\n\\t\\t\\t\\toutput.push(value);\\n\\t\\t\\t\\tcounter--;\\n\\t\\t\\t}\\n\\t\\t} else {\\n\\t\\t\\toutput.push(value);\\n\\t\\t}\\n\\t}\\n\\treturn output;\\n}\\n\\n/**\\n * Creates a string based on an array of numeric code points.\\n * @see `punycode.ucs2.decode`\\n * @memberOf punycode.ucs2\\n * @name encode\\n * @param {Array} codePoints The array of numeric code points.\\n * @returns {String} The new Unicode string (UCS-2).\\n */\\nconst ucs2encode = codePoints => String.fromCodePoint(...codePoints);\\n\\n/**\\n * Converts a basic code point into a digit/integer.\\n * @see `digitToBasic()`\\n * @private\\n * @param {Number} codePoint The basic numeric code point value.\\n * @returns {Number} The numeric value of a basic code point (for use in\\n * representing integers) in the range `0` to `base - 1`, or `base` if\\n * the code point does not represent a value.\\n */\\nconst basicToDigit = function(codePoint) {\\n\\tif (codePoint >= 0x30 && codePoint < 0x3A) {\\n\\t\\treturn 26 + (codePoint - 0x30);\\n\\t}\\n\\tif (codePoint >= 0x41 && codePoint < 0x5B) {\\n\\t\\treturn codePoint - 0x41;\\n\\t}\\n\\tif (codePoint >= 0x61 && codePoint < 0x7B) {\\n\\t\\treturn codePoint - 0x61;\\n\\t}\\n\\treturn base;\\n};\\n\\n/**\\n * Converts a digit/integer into a basic code point.\\n * @see `basicToDigit()`\\n * @private\\n * @param {Number} digit The numeric value of a basic code point.\\n * @returns {Number} The basic code point whose value (when used for\\n * representing integers) is `digit`, which needs to be in the range\\n * `0` to `base - 1`. If `flag` is non-zero, the uppercase form is\\n * used; else, the lowercase form is used. The behavior is undefined\\n * if `flag` is non-zero and `digit` has no uppercase form.\\n */\\nconst digitToBasic = function(digit, flag) {\\n\\t// 0..25 map to ASCII a..z or A..Z\\n\\t// 26..35 map to ASCII 0..9\\n\\treturn digit + 22 + 75 * (digit < 26) - ((flag != 0) << 5);\\n};\\n\\n/**\\n * Bias adaptation function as per section 3.4 of RFC 3492.\\n * https://tools.ietf.org/html/rfc3492#section-3.4\\n * @private\\n */\\nconst adapt = function(delta, numPoints, firstTime) {\\n\\tlet k = 0;\\n\\tdelta = firstTime ? floor(delta / damp) : delta >> 1;\\n\\tdelta += floor(delta / numPoints);\\n\\tfor (/* no initialization */; delta > baseMinusTMin * tMax >> 1; k += base) {\\n\\t\\tdelta = floor(delta / baseMinusTMin);\\n\\t}\\n\\treturn floor(k + (baseMinusTMin + 1) * delta / (delta + skew));\\n};\\n\\n/**\\n * Converts a Punycode string of ASCII-only symbols to a string of Unicode\\n * symbols.\\n * @memberOf punycode\\n * @param {String} input The Punycode string of ASCII-only symbols.\\n * @returns {String} The resulting string of Unicode symbols.\\n */\\nconst decode = function(input) {\\n\\t// Don't use UCS-2.\\n\\tconst output = [];\\n\\tconst inputLength = input.length;\\n\\tlet i = 0;\\n\\tlet n = initialN;\\n\\tlet bias = initialBias;\\n\\n\\t// Handle the basic code points: let `basic` be the number of input code\\n\\t// points before the last delimiter, or `0` if there is none, then copy\\n\\t// the first basic code points to the output.\\n\\n\\tlet basic = input.lastIndexOf(delimiter);\\n\\tif (basic < 0) {\\n\\t\\tbasic = 0;\\n\\t}\\n\\n\\tfor (let j = 0; j < basic; ++j) {\\n\\t\\t// if it's not a basic code point\\n\\t\\tif (input.charCodeAt(j) >= 0x80) {\\n\\t\\t\\terror('not-basic');\\n\\t\\t}\\n\\t\\toutput.push(input.charCodeAt(j));\\n\\t}\\n\\n\\t// Main decoding loop: start just after the last delimiter if any basic code\\n\\t// points were copied; start at the beginning otherwise.\\n\\n\\tfor (let index = basic > 0 ? basic + 1 : 0; index < inputLength; /* no final expression */) {\\n\\n\\t\\t// `index` is the index of the next character to be consumed.\\n\\t\\t// Decode a generalized variable-length integer into `delta`,\\n\\t\\t// which gets added to `i`. The overflow checking is easier\\n\\t\\t// if we increase `i` as we go, then subtract off its starting\\n\\t\\t// value at the end to obtain `delta`.\\n\\t\\tconst oldi = i;\\n\\t\\tfor (let w = 1, k = base; /* no condition */; k += base) {\\n\\n\\t\\t\\tif (index >= inputLength) {\\n\\t\\t\\t\\terror('invalid-input');\\n\\t\\t\\t}\\n\\n\\t\\t\\tconst digit = basicToDigit(input.charCodeAt(index++));\\n\\n\\t\\t\\tif (digit >= base) {\\n\\t\\t\\t\\terror('invalid-input');\\n\\t\\t\\t}\\n\\t\\t\\tif (digit > floor((maxInt - i) / w)) {\\n\\t\\t\\t\\terror('overflow');\\n\\t\\t\\t}\\n\\n\\t\\t\\ti += digit * w;\\n\\t\\t\\tconst t = k <= bias ? tMin : (k >= bias + tMax ? tMax : k - bias);\\n\\n\\t\\t\\tif (digit < t) {\\n\\t\\t\\t\\tbreak;\\n\\t\\t\\t}\\n\\n\\t\\t\\tconst baseMinusT = base - t;\\n\\t\\t\\tif (w > floor(maxInt / baseMinusT)) {\\n\\t\\t\\t\\terror('overflow');\\n\\t\\t\\t}\\n\\n\\t\\t\\tw *= baseMinusT;\\n\\n\\t\\t}\\n\\n\\t\\tconst out = output.length + 1;\\n\\t\\tbias = adapt(i - oldi, out, oldi == 0);\\n\\n\\t\\t// `i` was supposed to wrap around from `out` to `0`,\\n\\t\\t// incrementing `n` each time, so we'll fix that now:\\n\\t\\tif (floor(i / out) > maxInt - n) {\\n\\t\\t\\terror('overflow');\\n\\t\\t}\\n\\n\\t\\tn += floor(i / out);\\n\\t\\ti %= out;\\n\\n\\t\\t// Insert `n` at position `i` of the output.\\n\\t\\toutput.splice(i++, 0, n);\\n\\n\\t}\\n\\n\\treturn String.fromCodePoint(...output);\\n};\\n\\n/**\\n * Converts a string of Unicode symbols (e.g. a domain name label) to a\\n * Punycode string of ASCII-only symbols.\\n * @memberOf punycode\\n * @param {String} input The string of Unicode symbols.\\n * @returns {String} The resulting Punycode string of ASCII-only symbols.\\n */\\nconst encode = function(input) {\\n\\tconst output = [];\\n\\n\\t// Convert the input in UCS-2 to an array of Unicode code points.\\n\\tinput = ucs2decode(input);\\n\\n\\t// Cache the length.\\n\\tconst inputLength = input.length;\\n\\n\\t// Initialize the state.\\n\\tlet n = initialN;\\n\\tlet delta = 0;\\n\\tlet bias = initialBias;\\n\\n\\t// Handle the basic code points.\\n\\tfor (const currentValue of input) {\\n\\t\\tif (currentValue < 0x80) {\\n\\t\\t\\toutput.push(stringFromCharCode(currentValue));\\n\\t\\t}\\n\\t}\\n\\n\\tconst basicLength = output.length;\\n\\tlet handledCPCount = basicLength;\\n\\n\\t// `handledCPCount` is the number of code points that have been handled;\\n\\t// `basicLength` is the number of basic code points.\\n\\n\\t// Finish the basic string with a delimiter unless it's empty.\\n\\tif (basicLength) {\\n\\t\\toutput.push(delimiter);\\n\\t}\\n\\n\\t// Main encoding loop:\\n\\twhile (handledCPCount < inputLength) {\\n\\n\\t\\t// All non-basic code points < n have been handled already. Find the next\\n\\t\\t// larger one:\\n\\t\\tlet m = maxInt;\\n\\t\\tfor (const currentValue of input) {\\n\\t\\t\\tif (currentValue >= n && currentValue < m) {\\n\\t\\t\\t\\tm = currentValue;\\n\\t\\t\\t}\\n\\t\\t}\\n\\n\\t\\t// Increase `delta` enough to advance the decoder's state to ,\\n\\t\\t// but guard against overflow.\\n\\t\\tconst handledCPCountPlusOne = handledCPCount + 1;\\n\\t\\tif (m - n > floor((maxInt - delta) / handledCPCountPlusOne)) {\\n\\t\\t\\terror('overflow');\\n\\t\\t}\\n\\n\\t\\tdelta += (m - n) * handledCPCountPlusOne;\\n\\t\\tn = m;\\n\\n\\t\\tfor (const currentValue of input) {\\n\\t\\t\\tif (currentValue < n && ++delta > maxInt) {\\n\\t\\t\\t\\terror('overflow');\\n\\t\\t\\t}\\n\\t\\t\\tif (currentValue === n) {\\n\\t\\t\\t\\t// Represent delta as a generalized variable-length integer.\\n\\t\\t\\t\\tlet q = delta;\\n\\t\\t\\t\\tfor (let k = base; /* no condition */; k += base) {\\n\\t\\t\\t\\t\\tconst t = k <= bias ? tMin : (k >= bias + tMax ? tMax : k - bias);\\n\\t\\t\\t\\t\\tif (q < t) {\\n\\t\\t\\t\\t\\t\\tbreak;\\n\\t\\t\\t\\t\\t}\\n\\t\\t\\t\\t\\tconst qMinusT = q - t;\\n\\t\\t\\t\\t\\tconst baseMinusT = base - t;\\n\\t\\t\\t\\t\\toutput.push(\\n\\t\\t\\t\\t\\t\\tstringFromCharCode(digitToBasic(t + qMinusT % baseMinusT, 0))\\n\\t\\t\\t\\t\\t);\\n\\t\\t\\t\\t\\tq = floor(qMinusT / baseMinusT);\\n\\t\\t\\t\\t}\\n\\n\\t\\t\\t\\toutput.push(stringFromCharCode(digitToBasic(q, 0)));\\n\\t\\t\\t\\tbias = adapt(delta, handledCPCountPlusOne, handledCPCount === basicLength);\\n\\t\\t\\t\\tdelta = 0;\\n\\t\\t\\t\\t++handledCPCount;\\n\\t\\t\\t}\\n\\t\\t}\\n\\n\\t\\t++delta;\\n\\t\\t++n;\\n\\n\\t}\\n\\treturn output.join('');\\n};\\n\\n/**\\n * Converts a Punycode string representing a domain name or an email address\\n * to Unicode. Only the Punycoded parts of the input will be converted, i.e.\\n * it doesn't matter if you call it on a string that has already been\\n * converted to Unicode.\\n * @memberOf punycode\\n * @param {String} input The Punycoded domain name or email address to\\n * convert to Unicode.\\n * @returns {String} The Unicode representation of the given Punycode\\n * string.\\n */\\nconst toUnicode = function(input) {\\n\\treturn mapDomain(input, function(string) {\\n\\t\\treturn regexPunycode.test(string)\\n\\t\\t\\t? decode(string.slice(4).toLowerCase())\\n\\t\\t\\t: string;\\n\\t});\\n};\\n\\n/**\\n * Converts a Unicode string representing a domain name or an email address to\\n * Punycode. Only the non-ASCII parts of the domain name will be converted,\\n * i.e. it doesn't matter if you call it with a domain that's already in\\n * ASCII.\\n * @memberOf punycode\\n * @param {String} input The domain name or email address to convert, as a\\n * Unicode string.\\n * @returns {String} The Punycode representation of the given domain name or\\n * email address.\\n */\\nconst toASCII = function(input) {\\n\\treturn mapDomain(input, function(string) {\\n\\t\\treturn regexNonASCII.test(string)\\n\\t\\t\\t? 'xn--' + encode(string)\\n\\t\\t\\t: string;\\n\\t});\\n};\\n\\n/*--------------------------------------------------------------------------*/\\n\\n/** Define the public API */\\nconst punycode = {\\n\\t/**\\n\\t * A string representing the current Punycode.js version number.\\n\\t * @memberOf punycode\\n\\t * @type String\\n\\t */\\n\\t'version': '2.3.1',\\n\\t/**\\n\\t * An object of methods to convert from JavaScript's internal character\\n\\t * representation (UCS-2) to Unicode code points, and back.\\n\\t * @see \\n\\t * @memberOf punycode\\n\\t * @type Object\\n\\t */\\n\\t'ucs2': {\\n\\t\\t'decode': ucs2decode,\\n\\t\\t'encode': ucs2encode\\n\\t},\\n\\t'decode': decode,\\n\\t'encode': encode,\\n\\t'toASCII': toASCII,\\n\\t'toUnicode': toUnicode\\n};\\n\\nexport { ucs2decode, ucs2encode, decode, encode, toASCII, toUnicode };\\nexport default punycode;\\n\",\"// markdown-it default options\\n\\nexport default {\\n options: {\\n // Enable HTML tags in source\\n html: false,\\n\\n // Use '/' to close single tags (
)\\n xhtmlOut: false,\\n\\n // Convert '\\\\n' in paragraphs into
\\n breaks: false,\\n\\n // CSS language prefix for fenced blocks\\n langPrefix: 'language-',\\n\\n // autoconvert URL-like texts to links\\n linkify: false,\\n\\n // Enable some language-neutral replacements + quotes beautification\\n typographer: false,\\n\\n // Double + single quotes replacement pairs, when typographer enabled,\\n // and smartquotes on. Could be either a String or an Array.\\n //\\n // For example, you can use '«»„“' for Russian, '„“‚‘' for German,\\n // and ['«\\\\xA0', '\\\\xA0»', '‹\\\\xA0', '\\\\xA0›'] for French (including nbsp).\\n quotes: '\\\\u201c\\\\u201d\\\\u2018\\\\u2019', /* “”‘’ */\\n\\n // Highlighter function. Should return escaped HTML,\\n // or '' if the source string is not changed and should be escaped externaly.\\n // If result starts with )\\n xhtmlOut: false,\\n\\n // Convert '\\\\n' in paragraphs into
\\n breaks: false,\\n\\n // CSS language prefix for fenced blocks\\n langPrefix: 'language-',\\n\\n // autoconvert URL-like texts to links\\n linkify: false,\\n\\n // Enable some language-neutral replacements + quotes beautification\\n typographer: false,\\n\\n // Double + single quotes replacement pairs, when typographer enabled,\\n // and smartquotes on. Could be either a String or an Array.\\n //\\n // For example, you can use '«»„“' for Russian, '„“‚‘' for German,\\n // and ['«\\\\xA0', '\\\\xA0»', '‹\\\\xA0', '\\\\xA0›'] for French (including nbsp).\\n quotes: '\\\\u201c\\\\u201d\\\\u2018\\\\u2019', /* “”‘’ */\\n\\n // Highlighter function. Should return escaped HTML,\\n // or '' if the source string is not changed and should be escaped externaly.\\n // If result starts with )\\n xhtmlOut: true,\\n\\n // Convert '\\\\n' in paragraphs into
\\n breaks: false,\\n\\n // CSS language prefix for fenced blocks\\n langPrefix: 'language-',\\n\\n // autoconvert URL-like texts to links\\n linkify: false,\\n\\n // Enable some language-neutral replacements + quotes beautification\\n typographer: false,\\n\\n // Double + single quotes replacement pairs, when typographer enabled,\\n // and smartquotes on. Could be either a String or an Array.\\n //\\n // For example, you can use '«»„“' for Russian, '„“‚‘' for German,\\n // and ['«\\\\xA0', '\\\\xA0»', '‹\\\\xA0', '\\\\xA0›'] for French (including nbsp).\\n quotes: '\\\\u201c\\\\u201d\\\\u2018\\\\u2019', /* “”‘’ */\\n\\n // Highlighter function. Should return escaped HTML,\\n // or '' if the source string is not changed and should be escaped externaly.\\n // If result starts with = 0) {\\n try {\\n parsed.hostname = punycode.toASCII(parsed.hostname)\\n } catch (er) { /**/ }\\n }\\n }\\n\\n return mdurl.encode(mdurl.format(parsed))\\n}\\n\\nfunction normalizeLinkText (url) {\\n const parsed = mdurl.parse(url, true)\\n\\n if (parsed.hostname) {\\n // Encode hostnames in urls like:\\n // `http://host/`, `https://host/`, `mailto:user@host`, `//host/`\\n //\\n // We don't encode unknown schemas, because it's likely that we encode\\n // something we shouldn't (e.g. `skype:name` treated as `skype:host`)\\n //\\n if (!parsed.protocol || RECODE_HOSTNAME_FOR.indexOf(parsed.protocol) >= 0) {\\n try {\\n parsed.hostname = punycode.toUnicode(parsed.hostname)\\n } catch (er) { /**/ }\\n }\\n }\\n\\n // add '%' to exclude list because of https://github.com/markdown-it/markdown-it/issues/720\\n return mdurl.decode(mdurl.format(parsed), mdurl.decode.defaultChars + '%')\\n}\\n\\n/**\\n * class MarkdownIt\\n *\\n * Main parser/renderer class.\\n *\\n * ##### Usage\\n *\\n * ```javascript\\n * // node.js, \\\"classic\\\" way:\\n * var MarkdownIt = require('markdown-it'),\\n * md = new MarkdownIt();\\n * var result = md.render('# markdown-it rulezz!');\\n *\\n * // node.js, the same, but with sugar:\\n * var md = require('markdown-it')();\\n * var result = md.render('# markdown-it rulezz!');\\n *\\n * // browser without AMD, added to \\\"window\\\" on script load\\n * // Note, there are no dash.\\n * var md = window.markdownit();\\n * var result = md.render('# markdown-it rulezz!');\\n * ```\\n *\\n * Single line rendering, without paragraph wrap:\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n * var result = md.renderInline('__markdown-it__ rulezz!');\\n * ```\\n **/\\n\\n/**\\n * new MarkdownIt([presetName, options])\\n * - presetName (String): optional, `commonmark` / `zero`\\n * - options (Object)\\n *\\n * Creates parser instanse with given config. Can be called without `new`.\\n *\\n * ##### presetName\\n *\\n * MarkdownIt provides named presets as a convenience to quickly\\n * enable/disable active syntax rules and options for common use cases.\\n *\\n * - [\\\"commonmark\\\"](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/commonmark.mjs) -\\n * configures parser to strict [CommonMark](http://commonmark.org/) mode.\\n * - [default](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/default.mjs) -\\n * similar to GFM, used when no preset name given. Enables all available rules,\\n * but still without html, typographer & autolinker.\\n * - [\\\"zero\\\"](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/zero.mjs) -\\n * all rules disabled. Useful to quickly setup your config via `.enable()`.\\n * For example, when you need only `bold` and `italic` markup and nothing else.\\n *\\n * ##### options:\\n *\\n * - __html__ - `false`. Set `true` to enable HTML tags in source. Be careful!\\n * That's not safe! You may need external sanitizer to protect output from XSS.\\n * It's better to extend features via plugins, instead of enabling HTML.\\n * - __xhtmlOut__ - `false`. Set `true` to add '/' when closing single tags\\n * (`
`). This is needed only for full CommonMark compatibility. In real\\n * world you will need HTML output.\\n * - __breaks__ - `false`. Set `true` to convert `\\\\n` in paragraphs into `
`.\\n * - __langPrefix__ - `language-`. CSS language class prefix for fenced blocks.\\n * Can be useful for external highlighters.\\n * - __linkify__ - `false`. Set `true` to autoconvert URL-like text to links.\\n * - __typographer__ - `false`. Set `true` to enable [some language-neutral\\n * replacement](https://github.com/markdown-it/markdown-it/blob/master/lib/rules_core/replacements.mjs) +\\n * quotes beautification (smartquotes).\\n * - __quotes__ - `“”‘’`, String or Array. Double + single quotes replacement\\n * pairs, when typographer enabled and smartquotes on. For example, you can\\n * use `'«»„“'` for Russian, `'„“‚‘'` for German, and\\n * `['«\\\\xA0', '\\\\xA0»', '‹\\\\xA0', '\\\\xA0›']` for French (including nbsp).\\n * - __highlight__ - `null`. Highlighter function for fenced code blocks.\\n * Highlighter `function (str, lang)` should return escaped HTML. It can also\\n * return empty string if the source was not changed and should be escaped\\n * externaly. If result starts with ` or ``):\\n *\\n * ```javascript\\n * var hljs = require('highlight.js') // https://highlightjs.org/\\n *\\n * // Actual default values\\n * var md = require('markdown-it')({\\n * highlight: function (str, lang) {\\n * if (lang && hljs.getLanguage(lang)) {\\n * try {\\n * return '
' +\\n *                hljs.highlight(str, { language: lang, ignoreIllegals: true }).value +\\n *                '
';\\n * } catch (__) {}\\n * }\\n *\\n * return '
' + md.utils.escapeHtml(str) + '
';\\n * }\\n * });\\n * ```\\n *\\n **/\\nfunction MarkdownIt (presetName, options) {\\n if (!(this instanceof MarkdownIt)) {\\n return new MarkdownIt(presetName, options)\\n }\\n\\n if (!options) {\\n if (!utils.isString(presetName)) {\\n options = presetName || {}\\n presetName = 'default'\\n }\\n }\\n\\n /**\\n * MarkdownIt#inline -> ParserInline\\n *\\n * Instance of [[ParserInline]]. You may need it to add new rules when\\n * writing plugins. For simple rules control use [[MarkdownIt.disable]] and\\n * [[MarkdownIt.enable]].\\n **/\\n this.inline = new ParserInline()\\n\\n /**\\n * MarkdownIt#block -> ParserBlock\\n *\\n * Instance of [[ParserBlock]]. You may need it to add new rules when\\n * writing plugins. For simple rules control use [[MarkdownIt.disable]] and\\n * [[MarkdownIt.enable]].\\n **/\\n this.block = new ParserBlock()\\n\\n /**\\n * MarkdownIt#core -> Core\\n *\\n * Instance of [[Core]] chain executor. You may need it to add new rules when\\n * writing plugins. For simple rules control use [[MarkdownIt.disable]] and\\n * [[MarkdownIt.enable]].\\n **/\\n this.core = new ParserCore()\\n\\n /**\\n * MarkdownIt#renderer -> Renderer\\n *\\n * Instance of [[Renderer]]. Use it to modify output look. Or to add rendering\\n * rules for new token types, generated by plugins.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n *\\n * function myToken(tokens, idx, options, env, self) {\\n * //...\\n * return result;\\n * };\\n *\\n * md.renderer.rules['my_token'] = myToken\\n * ```\\n *\\n * See [[Renderer]] docs and [source code](https://github.com/markdown-it/markdown-it/blob/master/lib/renderer.mjs).\\n **/\\n this.renderer = new Renderer()\\n\\n /**\\n * MarkdownIt#linkify -> LinkifyIt\\n *\\n * [linkify-it](https://github.com/markdown-it/linkify-it) instance.\\n * Used by [linkify](https://github.com/markdown-it/markdown-it/blob/master/lib/rules_core/linkify.mjs)\\n * rule.\\n **/\\n this.linkify = new LinkifyIt()\\n\\n /**\\n * MarkdownIt#validateLink(url) -> Boolean\\n *\\n * Link validation function. CommonMark allows too much in links. By default\\n * we disable `javascript:`, `vbscript:`, `file:` schemas, and almost all `data:...` schemas\\n * except some embedded image types.\\n *\\n * You can change this behaviour:\\n *\\n * ```javascript\\n * var md = require('markdown-it')();\\n * // enable everything\\n * md.validateLink = function () { return true; }\\n * ```\\n **/\\n this.validateLink = validateLink\\n\\n /**\\n * MarkdownIt#normalizeLink(url) -> String\\n *\\n * Function used to encode link url to a machine-readable format,\\n * which includes url-encoding, punycode, etc.\\n **/\\n this.normalizeLink = normalizeLink\\n\\n /**\\n * MarkdownIt#normalizeLinkText(url) -> String\\n *\\n * Function used to decode link url to a human-readable format`\\n **/\\n this.normalizeLinkText = normalizeLinkText\\n\\n // Expose utils & helpers for easy acces from plugins\\n\\n /**\\n * MarkdownIt#utils -> utils\\n *\\n * Assorted utility functions, useful to write plugins. See details\\n * [here](https://github.com/markdown-it/markdown-it/blob/master/lib/common/utils.mjs).\\n **/\\n this.utils = utils\\n\\n /**\\n * MarkdownIt#helpers -> helpers\\n *\\n * Link components parser functions, useful to write plugins. See details\\n * [here](https://github.com/markdown-it/markdown-it/blob/master/lib/helpers).\\n **/\\n this.helpers = utils.assign({}, helpers)\\n\\n this.options = {}\\n this.configure(presetName)\\n\\n if (options) { this.set(options) }\\n}\\n\\n/** chainable\\n * MarkdownIt.set(options)\\n *\\n * Set parser options (in the same format as in constructor). Probably, you\\n * will never need it, but you can change options after constructor call.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var md = require('markdown-it')()\\n * .set({ html: true, breaks: true })\\n * .set({ typographer, true });\\n * ```\\n *\\n * __Note:__ To achieve the best possible performance, don't modify a\\n * `markdown-it` instance options on the fly. If you need multiple configurations\\n * it's best to create multiple instances and initialize each with separate\\n * config.\\n **/\\nMarkdownIt.prototype.set = function (options) {\\n utils.assign(this.options, options)\\n return this\\n}\\n\\n/** chainable, internal\\n * MarkdownIt.configure(presets)\\n *\\n * Batch load of all options and compenent settings. This is internal method,\\n * and you probably will not need it. But if you will - see available presets\\n * and data structure [here](https://github.com/markdown-it/markdown-it/tree/master/lib/presets)\\n *\\n * We strongly recommend to use presets instead of direct config loads. That\\n * will give better compatibility with next versions.\\n **/\\nMarkdownIt.prototype.configure = function (presets) {\\n const self = this\\n\\n if (utils.isString(presets)) {\\n const presetName = presets\\n presets = config[presetName]\\n if (!presets) { throw new Error('Wrong `markdown-it` preset \\\"' + presetName + '\\\", check name') }\\n }\\n\\n if (!presets) { throw new Error('Wrong `markdown-it` preset, can\\\\'t be empty') }\\n\\n if (presets.options) { self.set(presets.options) }\\n\\n if (presets.components) {\\n Object.keys(presets.components).forEach(function (name) {\\n if (presets.components[name].rules) {\\n self[name].ruler.enableOnly(presets.components[name].rules)\\n }\\n if (presets.components[name].rules2) {\\n self[name].ruler2.enableOnly(presets.components[name].rules2)\\n }\\n })\\n }\\n return this\\n}\\n\\n/** chainable\\n * MarkdownIt.enable(list, ignoreInvalid)\\n * - list (String|Array): rule name or list of rule names to enable\\n * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found.\\n *\\n * Enable list or rules. It will automatically find appropriate components,\\n * containing rules with given names. If rule not found, and `ignoreInvalid`\\n * not set - throws exception.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var md = require('markdown-it')()\\n * .enable(['sub', 'sup'])\\n * .disable('smartquotes');\\n * ```\\n **/\\nMarkdownIt.prototype.enable = function (list, ignoreInvalid) {\\n let result = []\\n\\n if (!Array.isArray(list)) { list = [list] }\\n\\n ['core', 'block', 'inline'].forEach(function (chain) {\\n result = result.concat(this[chain].ruler.enable(list, true))\\n }, this)\\n\\n result = result.concat(this.inline.ruler2.enable(list, true))\\n\\n const missed = list.filter(function (name) { return result.indexOf(name) < 0 })\\n\\n if (missed.length && !ignoreInvalid) {\\n throw new Error('MarkdownIt. Failed to enable unknown rule(s): ' + missed)\\n }\\n\\n return this\\n}\\n\\n/** chainable\\n * MarkdownIt.disable(list, ignoreInvalid)\\n * - list (String|Array): rule name or list of rule names to disable.\\n * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found.\\n *\\n * The same as [[MarkdownIt.enable]], but turn specified rules off.\\n **/\\nMarkdownIt.prototype.disable = function (list, ignoreInvalid) {\\n let result = []\\n\\n if (!Array.isArray(list)) { list = [list] }\\n\\n ['core', 'block', 'inline'].forEach(function (chain) {\\n result = result.concat(this[chain].ruler.disable(list, true))\\n }, this)\\n\\n result = result.concat(this.inline.ruler2.disable(list, true))\\n\\n const missed = list.filter(function (name) { return result.indexOf(name) < 0 })\\n\\n if (missed.length && !ignoreInvalid) {\\n throw new Error('MarkdownIt. Failed to disable unknown rule(s): ' + missed)\\n }\\n return this\\n}\\n\\n/** chainable\\n * MarkdownIt.use(plugin, params)\\n *\\n * Load specified plugin with given params into current parser instance.\\n * It's just a sugar to call `plugin(md, params)` with curring.\\n *\\n * ##### Example\\n *\\n * ```javascript\\n * var iterator = require('markdown-it-for-inline');\\n * var md = require('markdown-it')()\\n * .use(iterator, 'foo_replace', 'text', function (tokens, idx) {\\n * tokens[idx].content = tokens[idx].content.replace(/foo/g, 'bar');\\n * });\\n * ```\\n **/\\nMarkdownIt.prototype.use = function (plugin /*, params, ... */) {\\n const args = [this].concat(Array.prototype.slice.call(arguments, 1))\\n plugin.apply(plugin, args)\\n return this\\n}\\n\\n/** internal\\n * MarkdownIt.parse(src, env) -> Array\\n * - src (String): source string\\n * - env (Object): environment sandbox\\n *\\n * Parse input string and return list of block tokens (special token type\\n * \\\"inline\\\" will contain list of inline tokens). You should not call this\\n * method directly, until you write custom renderer (for example, to produce\\n * AST).\\n *\\n * `env` is used to pass data between \\\"distributed\\\" rules and return additional\\n * metadata like reference info, needed for the renderer. It also can be used to\\n * inject data in specific cases. Usually, you will be ok to pass `{}`,\\n * and then pass updated object to renderer.\\n **/\\nMarkdownIt.prototype.parse = function (src, env) {\\n if (typeof src !== 'string') {\\n throw new Error('Input data should be a String')\\n }\\n\\n const state = new this.core.State(src, this, env)\\n\\n this.core.process(state)\\n\\n return state.tokens\\n}\\n\\n/**\\n * MarkdownIt.render(src [, env]) -> String\\n * - src (String): source string\\n * - env (Object): environment sandbox\\n *\\n * Render markdown string into html. It does all magic for you :).\\n *\\n * `env` can be used to inject additional metadata (`{}` by default).\\n * But you will not need it with high probability. See also comment\\n * in [[MarkdownIt.parse]].\\n **/\\nMarkdownIt.prototype.render = function (src, env) {\\n env = env || {}\\n\\n return this.renderer.render(this.parse(src, env), this.options, env)\\n}\\n\\n/** internal\\n * MarkdownIt.parseInline(src, env) -> Array\\n * - src (String): source string\\n * - env (Object): environment sandbox\\n *\\n * The same as [[MarkdownIt.parse]] but skip all block rules. It returns the\\n * block tokens list with the single `inline` element, containing parsed inline\\n * tokens in `children` property. Also updates `env` object.\\n **/\\nMarkdownIt.prototype.parseInline = function (src, env) {\\n const state = new this.core.State(src, this, env)\\n\\n state.inlineMode = true\\n this.core.process(state)\\n\\n return state.tokens\\n}\\n\\n/**\\n * MarkdownIt.renderInline(src [, env]) -> String\\n * - src (String): source string\\n * - env (Object): environment sandbox\\n *\\n * Similar to [[MarkdownIt.render]] but for single paragraph content. Result\\n * will NOT be wrapped into `

` tags.\\n **/\\nMarkdownIt.prototype.renderInline = function (src, env) {\\n env = env || {}\\n\\n return this.renderer.render(this.parseInline(src, env), this.options, env)\\n}\\n\\nexport default MarkdownIt\\n\",\"/**\\n * Utilities for hex, bytes, CSPRNG.\\n * @module\\n */\\n/*! noble-hashes - MIT License (c) 2022 Paul Miller (paulmillr.com) */\\n\\n// We use WebCrypto aka globalThis.crypto, which exists in browsers and node.js 16+.\\n// node.js versions earlier than v19 don't declare it in global scope.\\n// For node.js, package.json#exports field mapping rewrites import\\n// from `crypto` to `cryptoNode`, which imports native module.\\n// Makes the utils un-importable in browsers without a bundler.\\n// Once node.js 18 is deprecated (2025-04-30), we can just drop the import.\\nimport { crypto } from '@noble/hashes/crypto';\\n\\n/** Checks if something is Uint8Array. Be careful: nodejs Buffer will return true. */\\nexport function isBytes(a: unknown): a is Uint8Array {\\n return a instanceof Uint8Array || (ArrayBuffer.isView(a) && a.constructor.name === 'Uint8Array');\\n}\\n\\n/** Asserts something is positive integer. */\\nexport function anumber(n: number): void {\\n if (!Number.isSafeInteger(n) || n < 0) throw new Error('positive integer expected, got ' + n);\\n}\\n\\n/** Asserts something is Uint8Array. */\\nexport function abytes(b: Uint8Array | undefined, ...lengths: number[]): void {\\n if (!isBytes(b)) throw new Error('Uint8Array expected');\\n if (lengths.length > 0 && !lengths.includes(b.length))\\n throw new Error('Uint8Array expected of length ' + lengths + ', got length=' + b.length);\\n}\\n\\n/** Asserts something is hash */\\nexport function ahash(h: IHash): void {\\n if (typeof h !== 'function' || typeof h.create !== 'function')\\n throw new Error('Hash should be wrapped by utils.createHasher');\\n anumber(h.outputLen);\\n anumber(h.blockLen);\\n}\\n\\n/** Asserts a hash instance has not been destroyed / finished */\\nexport function aexists(instance: any, checkFinished = true): void {\\n if (instance.destroyed) throw new Error('Hash instance has been destroyed');\\n if (checkFinished && instance.finished) throw new Error('Hash#digest() has already been called');\\n}\\n\\n/** Asserts output is properly-sized byte array */\\nexport function aoutput(out: any, instance: any): void {\\n abytes(out);\\n const min = instance.outputLen;\\n if (out.length < min) {\\n throw new Error('digestInto() expects output buffer of length at least ' + min);\\n }\\n}\\n\\n/** Generic type encompassing 8/16/32-byte arrays - but not 64-byte. */\\n// prettier-ignore\\nexport type TypedArray = Int8Array | Uint8ClampedArray | Uint8Array |\\n Uint16Array | Int16Array | Uint32Array | Int32Array;\\n\\n/** Cast u8 / u16 / u32 to u8. */\\nexport function u8(arr: TypedArray): Uint8Array {\\n return new Uint8Array(arr.buffer, arr.byteOffset, arr.byteLength);\\n}\\n\\n/** Cast u8 / u16 / u32 to u32. */\\nexport function u32(arr: TypedArray): Uint32Array {\\n return new Uint32Array(arr.buffer, arr.byteOffset, Math.floor(arr.byteLength / 4));\\n}\\n\\n/** Zeroize a byte array. Warning: JS provides no guarantees. */\\nexport function clean(...arrays: TypedArray[]): void {\\n for (let i = 0; i < arrays.length; i++) {\\n arrays[i].fill(0);\\n }\\n}\\n\\n/** Create DataView of an array for easy byte-level manipulation. */\\nexport function createView(arr: TypedArray): DataView {\\n return new DataView(arr.buffer, arr.byteOffset, arr.byteLength);\\n}\\n\\n/** The rotate right (circular right shift) operation for uint32 */\\nexport function rotr(word: number, shift: number): number {\\n return (word << (32 - shift)) | (word >>> shift);\\n}\\n\\n/** The rotate left (circular left shift) operation for uint32 */\\nexport function rotl(word: number, shift: number): number {\\n return (word << shift) | ((word >>> (32 - shift)) >>> 0);\\n}\\n\\n/** Is current platform little-endian? Most are. Big-Endian platform: IBM */\\nexport const isLE: boolean = /* @__PURE__ */ (() =>\\n new Uint8Array(new Uint32Array([0x11223344]).buffer)[0] === 0x44)();\\n\\n/** The byte swap operation for uint32 */\\nexport function byteSwap(word: number): number {\\n return (\\n ((word << 24) & 0xff000000) |\\n ((word << 8) & 0xff0000) |\\n ((word >>> 8) & 0xff00) |\\n ((word >>> 24) & 0xff)\\n );\\n}\\n/** Conditionally byte swap if on a big-endian platform */\\nexport const swap8IfBE: (n: number) => number = isLE\\n ? (n: number) => n\\n : (n: number) => byteSwap(n);\\n\\n/** @deprecated */\\nexport const byteSwapIfBE: typeof swap8IfBE = swap8IfBE;\\n/** In place byte swap for Uint32Array */\\nexport function byteSwap32(arr: Uint32Array): Uint32Array {\\n for (let i = 0; i < arr.length; i++) {\\n arr[i] = byteSwap(arr[i]);\\n }\\n return arr;\\n}\\n\\nexport const swap32IfBE: (u: Uint32Array) => Uint32Array = isLE\\n ? (u: Uint32Array) => u\\n : byteSwap32;\\n\\n// Built-in hex conversion https://caniuse.com/mdn-javascript_builtins_uint8array_fromhex\\nconst hasHexBuiltin: boolean = /* @__PURE__ */ (() =>\\n // @ts-ignore\\n typeof Uint8Array.from([]).toHex === 'function' && typeof Uint8Array.fromHex === 'function')();\\n\\n// Array where index 0xf0 (240) is mapped to string 'f0'\\nconst hexes = /* @__PURE__ */ Array.from({ length: 256 }, (_, i) =>\\n i.toString(16).padStart(2, '0')\\n);\\n\\n/**\\n * Convert byte array to hex string. Uses built-in function, when available.\\n * @example bytesToHex(Uint8Array.from([0xca, 0xfe, 0x01, 0x23])) // 'cafe0123'\\n */\\nexport function bytesToHex(bytes: Uint8Array): string {\\n abytes(bytes);\\n // @ts-ignore\\n if (hasHexBuiltin) return bytes.toHex();\\n // pre-caching improves the speed 6x\\n let hex = '';\\n for (let i = 0; i < bytes.length; i++) {\\n hex += hexes[bytes[i]];\\n }\\n return hex;\\n}\\n\\n// We use optimized technique to convert hex string to byte array\\nconst asciis = { _0: 48, _9: 57, A: 65, F: 70, a: 97, f: 102 } as const;\\nfunction asciiToBase16(ch: number): number | undefined {\\n if (ch >= asciis._0 && ch <= asciis._9) return ch - asciis._0; // '2' => 50-48\\n if (ch >= asciis.A && ch <= asciis.F) return ch - (asciis.A - 10); // 'B' => 66-(65-10)\\n if (ch >= asciis.a && ch <= asciis.f) return ch - (asciis.a - 10); // 'b' => 98-(97-10)\\n return;\\n}\\n\\n/**\\n * Convert hex string to byte array. Uses built-in function, when available.\\n * @example hexToBytes('cafe0123') // Uint8Array.from([0xca, 0xfe, 0x01, 0x23])\\n */\\nexport function hexToBytes(hex: string): Uint8Array {\\n if (typeof hex !== 'string') throw new Error('hex string expected, got ' + typeof hex);\\n // @ts-ignore\\n if (hasHexBuiltin) return Uint8Array.fromHex(hex);\\n const hl = hex.length;\\n const al = hl / 2;\\n if (hl % 2) throw new Error('hex string expected, got unpadded hex of length ' + hl);\\n const array = new Uint8Array(al);\\n for (let ai = 0, hi = 0; ai < al; ai++, hi += 2) {\\n const n1 = asciiToBase16(hex.charCodeAt(hi));\\n const n2 = asciiToBase16(hex.charCodeAt(hi + 1));\\n if (n1 === undefined || n2 === undefined) {\\n const char = hex[hi] + hex[hi + 1];\\n throw new Error('hex string expected, got non-hex character \\\"' + char + '\\\" at index ' + hi);\\n }\\n array[ai] = n1 * 16 + n2; // multiply first octet, e.g. 'a3' => 10*16+3 => 160 + 3 => 163\\n }\\n return array;\\n}\\n\\n/**\\n * There is no setImmediate in browser and setTimeout is slow.\\n * Call of async fn will return Promise, which will be fullfiled only on\\n * next scheduler queue processing step and this is exactly what we need.\\n */\\nexport const nextTick = async (): Promise => {};\\n\\n/** Returns control to thread each 'tick' ms to avoid blocking. */\\nexport async function asyncLoop(\\n iters: number,\\n tick: number,\\n cb: (i: number) => void\\n): Promise {\\n let ts = Date.now();\\n for (let i = 0; i < iters; i++) {\\n cb(i);\\n // Date.now() is not monotonic, so in case if clock goes backwards we return return control too\\n const diff = Date.now() - ts;\\n if (diff >= 0 && diff < tick) continue;\\n await nextTick();\\n ts += diff;\\n }\\n}\\n\\n// Global symbols, but ts doesn't see them: https://github.com/microsoft/TypeScript/issues/31535\\ndeclare const TextEncoder: any;\\ndeclare const TextDecoder: any;\\n\\n/**\\n * Converts string to bytes using UTF8 encoding.\\n * @example utf8ToBytes('abc') // Uint8Array.from([97, 98, 99])\\n */\\nexport function utf8ToBytes(str: string): Uint8Array {\\n if (typeof str !== 'string') throw new Error('string expected');\\n return new Uint8Array(new TextEncoder().encode(str)); // https://bugzil.la/1681809\\n}\\n\\n/**\\n * Converts bytes to string using UTF8 encoding.\\n * @example bytesToUtf8(Uint8Array.from([97, 98, 99])) // 'abc'\\n */\\nexport function bytesToUtf8(bytes: Uint8Array): string {\\n return new TextDecoder().decode(bytes);\\n}\\n\\n/** Accepted input of hash functions. Strings are converted to byte arrays. */\\nexport type Input = string | Uint8Array;\\n/**\\n * Normalizes (non-hex) string or Uint8Array to Uint8Array.\\n * Warning: when Uint8Array is passed, it would NOT get copied.\\n * Keep in mind for future mutable operations.\\n */\\nexport function toBytes(data: Input): Uint8Array {\\n if (typeof data === 'string') data = utf8ToBytes(data);\\n abytes(data);\\n return data;\\n}\\n\\n/** KDFs can accept string or Uint8Array for user convenience. */\\nexport type KDFInput = string | Uint8Array;\\n/**\\n * Helper for KDFs: consumes uint8array or string.\\n * When string is passed, does utf8 decoding, using TextDecoder.\\n */\\nexport function kdfInputToBytes(data: KDFInput): Uint8Array {\\n if (typeof data === 'string') data = utf8ToBytes(data);\\n abytes(data);\\n return data;\\n}\\n\\n/** Copies several Uint8Arrays into one. */\\nexport function concatBytes(...arrays: Uint8Array[]): Uint8Array {\\n let sum = 0;\\n for (let i = 0; i < arrays.length; i++) {\\n const a = arrays[i];\\n abytes(a);\\n sum += a.length;\\n }\\n const res = new Uint8Array(sum);\\n for (let i = 0, pad = 0; i < arrays.length; i++) {\\n const a = arrays[i];\\n res.set(a, pad);\\n pad += a.length;\\n }\\n return res;\\n}\\n\\ntype EmptyObj = {};\\nexport function checkOpts(\\n defaults: T1,\\n opts?: T2\\n): T1 & T2 {\\n if (opts !== undefined && {}.toString.call(opts) !== '[object Object]')\\n throw new Error('options should be object or undefined');\\n const merged = Object.assign(defaults, opts);\\n return merged as T1 & T2;\\n}\\n\\n/** Hash interface. */\\nexport type IHash = {\\n (data: Uint8Array): Uint8Array;\\n blockLen: number;\\n outputLen: number;\\n create: any;\\n};\\n\\n/** For runtime check if class implements interface */\\nexport abstract class Hash> {\\n abstract blockLen: number; // Bytes per block\\n abstract outputLen: number; // Bytes in output\\n abstract update(buf: Input): this;\\n // Writes digest into buf\\n abstract digestInto(buf: Uint8Array): void;\\n abstract digest(): Uint8Array;\\n /**\\n * Resets internal state. Makes Hash instance unusable.\\n * Reset is impossible for keyed hashes if key is consumed into state. If digest is not consumed\\n * by user, they will need to manually call `destroy()` when zeroing is necessary.\\n */\\n abstract destroy(): void;\\n /**\\n * Clones hash instance. Unsafe: doesn't check whether `to` is valid. Can be used as `clone()`\\n * when no options are passed.\\n * Reasons to use `_cloneInto` instead of clone: 1) performance 2) reuse instance => all internal\\n * buffers are overwritten => causes buffer overwrite which is used for digest in some cases.\\n * There are no guarantees for clean-up because it's impossible in JS.\\n */\\n abstract _cloneInto(to?: T): T;\\n // Safe version that clones internal state\\n abstract clone(): T;\\n}\\n\\n/**\\n * XOF: streaming API to read digest in chunks.\\n * Same as 'squeeze' in keccak/k12 and 'seek' in blake3, but more generic name.\\n * When hash used in XOF mode it is up to user to call '.destroy' afterwards, since we cannot\\n * destroy state, next call can require more bytes.\\n */\\nexport type HashXOF> = Hash & {\\n xof(bytes: number): Uint8Array; // Read 'bytes' bytes from digest stream\\n xofInto(buf: Uint8Array): Uint8Array; // read buf.length bytes from digest stream into buf\\n};\\n\\n/** Hash function */\\nexport type CHash = ReturnType;\\n/** Hash function with output */\\nexport type CHashO = ReturnType;\\n/** XOF with output */\\nexport type CHashXO = ReturnType;\\n\\n/** Wraps hash function, creating an interface on top of it */\\nexport function createHasher>(\\n hashCons: () => Hash\\n): {\\n (msg: Input): Uint8Array;\\n outputLen: number;\\n blockLen: number;\\n create(): Hash;\\n} {\\n const hashC = (msg: Input): Uint8Array => hashCons().update(toBytes(msg)).digest();\\n const tmp = hashCons();\\n hashC.outputLen = tmp.outputLen;\\n hashC.blockLen = tmp.blockLen;\\n hashC.create = () => hashCons();\\n return hashC;\\n}\\n\\nexport function createOptHasher, T extends Object>(\\n hashCons: (opts?: T) => Hash\\n): {\\n (msg: Input, opts?: T): Uint8Array;\\n outputLen: number;\\n blockLen: number;\\n create(opts?: T): Hash;\\n} {\\n const hashC = (msg: Input, opts?: T): Uint8Array => hashCons(opts).update(toBytes(msg)).digest();\\n const tmp = hashCons({} as T);\\n hashC.outputLen = tmp.outputLen;\\n hashC.blockLen = tmp.blockLen;\\n hashC.create = (opts?: T) => hashCons(opts);\\n return hashC;\\n}\\n\\nexport function createXOFer, T extends Object>(\\n hashCons: (opts?: T) => HashXOF\\n): {\\n (msg: Input, opts?: T): Uint8Array;\\n outputLen: number;\\n blockLen: number;\\n create(opts?: T): HashXOF;\\n} {\\n const hashC = (msg: Input, opts?: T): Uint8Array => hashCons(opts).update(toBytes(msg)).digest();\\n const tmp = hashCons({} as T);\\n hashC.outputLen = tmp.outputLen;\\n hashC.blockLen = tmp.blockLen;\\n hashC.create = (opts?: T) => hashCons(opts);\\n return hashC;\\n}\\nexport const wrapConstructor: typeof createHasher = createHasher;\\nexport const wrapConstructorWithOpts: typeof createOptHasher = createOptHasher;\\nexport const wrapXOFConstructorWithOpts: typeof createXOFer = createXOFer;\\n\\n/** Cryptographically secure PRNG. Uses internal OS-level `crypto.getRandomValues`. */\\nexport function randomBytes(bytesLength = 32): Uint8Array {\\n if (crypto && typeof crypto.getRandomValues === 'function') {\\n return crypto.getRandomValues(new Uint8Array(bytesLength));\\n }\\n // Legacy Node.js compatibility\\n if (crypto && typeof crypto.randomBytes === 'function') {\\n return Uint8Array.from(crypto.randomBytes(bytesLength));\\n }\\n throw new Error('crypto.getRandomValues must be defined');\\n}\\n\",\"/**\\n * Internal Merkle-Damgard hash utils.\\n * @module\\n */\\nimport { type Input, Hash, abytes, aexists, aoutput, clean, createView, toBytes } from './utils.ts';\\n\\n/** Polyfill for Safari 14. https://caniuse.com/mdn-javascript_builtins_dataview_setbiguint64 */\\nexport function setBigUint64(\\n view: DataView,\\n byteOffset: number,\\n value: bigint,\\n isLE: boolean\\n): void {\\n if (typeof view.setBigUint64 === 'function') return view.setBigUint64(byteOffset, value, isLE);\\n const _32n = BigInt(32);\\n const _u32_max = BigInt(0xffffffff);\\n const wh = Number((value >> _32n) & _u32_max);\\n const wl = Number(value & _u32_max);\\n const h = isLE ? 4 : 0;\\n const l = isLE ? 0 : 4;\\n view.setUint32(byteOffset + h, wh, isLE);\\n view.setUint32(byteOffset + l, wl, isLE);\\n}\\n\\n/** Choice: a ? b : c */\\nexport function Chi(a: number, b: number, c: number): number {\\n return (a & b) ^ (~a & c);\\n}\\n\\n/** Majority function, true if any two inputs is true. */\\nexport function Maj(a: number, b: number, c: number): number {\\n return (a & b) ^ (a & c) ^ (b & c);\\n}\\n\\n/**\\n * Merkle-Damgard hash construction base class.\\n * Could be used to create MD5, RIPEMD, SHA1, SHA2.\\n */\\nexport abstract class HashMD> extends Hash {\\n protected abstract process(buf: DataView, offset: number): void;\\n protected abstract get(): number[];\\n protected abstract set(...args: number[]): void;\\n abstract destroy(): void;\\n protected abstract roundClean(): void;\\n\\n readonly blockLen: number;\\n readonly outputLen: number;\\n readonly padOffset: number;\\n readonly isLE: boolean;\\n\\n // For partial updates less than block size\\n protected buffer: Uint8Array;\\n protected view: DataView;\\n protected finished = false;\\n protected length = 0;\\n protected pos = 0;\\n protected destroyed = false;\\n\\n constructor(blockLen: number, outputLen: number, padOffset: number, isLE: boolean) {\\n super();\\n this.blockLen = blockLen;\\n this.outputLen = outputLen;\\n this.padOffset = padOffset;\\n this.isLE = isLE;\\n this.buffer = new Uint8Array(blockLen);\\n this.view = createView(this.buffer);\\n }\\n update(data: Input): this {\\n aexists(this);\\n data = toBytes(data);\\n abytes(data);\\n const { view, buffer, blockLen } = this;\\n const len = data.length;\\n for (let pos = 0; pos < len; ) {\\n const take = Math.min(blockLen - this.pos, len - pos);\\n // Fast path: we have at least one block in input, cast it to view and process\\n if (take === blockLen) {\\n const dataView = createView(data);\\n for (; blockLen <= len - pos; pos += blockLen) this.process(dataView, pos);\\n continue;\\n }\\n buffer.set(data.subarray(pos, pos + take), this.pos);\\n this.pos += take;\\n pos += take;\\n if (this.pos === blockLen) {\\n this.process(view, 0);\\n this.pos = 0;\\n }\\n }\\n this.length += data.length;\\n this.roundClean();\\n return this;\\n }\\n digestInto(out: Uint8Array): void {\\n aexists(this);\\n aoutput(out, this);\\n this.finished = true;\\n // Padding\\n // We can avoid allocation of buffer for padding completely if it\\n // was previously not allocated here. But it won't change performance.\\n const { buffer, view, blockLen, isLE } = this;\\n let { pos } = this;\\n // append the bit '1' to the message\\n buffer[pos++] = 0b10000000;\\n clean(this.buffer.subarray(pos));\\n // we have less than padOffset left in buffer, so we cannot put length in\\n // current block, need process it and pad again\\n if (this.padOffset > blockLen - pos) {\\n this.process(view, 0);\\n pos = 0;\\n }\\n // Pad until full block byte with zeros\\n for (let i = pos; i < blockLen; i++) buffer[i] = 0;\\n // Note: sha512 requires length to be 128bit integer, but length in JS will overflow before that\\n // You need to write around 2 exabytes (u64_max / 8 / (1024**6)) for this to happen.\\n // So we just write lowest 64 bits of that value.\\n setBigUint64(view, blockLen - 8, BigInt(this.length * 8), isLE);\\n this.process(view, 0);\\n const oview = createView(out);\\n const len = this.outputLen;\\n // NOTE: we do division by 4 later, which should be fused in single op with modulo by JIT\\n if (len % 4) throw new Error('_sha2: outputLen should be aligned to 32bit');\\n const outLen = len / 4;\\n const state = this.get();\\n if (outLen > state.length) throw new Error('_sha2: outputLen bigger than state');\\n for (let i = 0; i < outLen; i++) oview.setUint32(4 * i, state[i], isLE);\\n }\\n digest(): Uint8Array {\\n const { buffer, outputLen } = this;\\n this.digestInto(buffer);\\n const res = buffer.slice(0, outputLen);\\n this.destroy();\\n return res;\\n }\\n _cloneInto(to?: T): T {\\n to ||= new (this.constructor as any)() as T;\\n to.set(...this.get());\\n const { blockLen, buffer, length, finished, destroyed, pos } = this;\\n to.destroyed = destroyed;\\n to.finished = finished;\\n to.length = length;\\n to.pos = pos;\\n if (length % blockLen) to.buffer.set(buffer);\\n return to;\\n }\\n clone(): T {\\n return this._cloneInto();\\n }\\n}\\n\\n/**\\n * Initial SHA-2 state: fractional parts of square roots of first 16 primes 2..53.\\n * Check out `test/misc/sha2-gen-iv.js` for recomputation guide.\\n */\\n\\n/** Initial SHA256 state. Bits 0..32 of frac part of sqrt of primes 2..19 */\\nexport const SHA256_IV: Uint32Array = /* @__PURE__ */ Uint32Array.from([\\n 0x6a09e667, 0xbb67ae85, 0x3c6ef372, 0xa54ff53a, 0x510e527f, 0x9b05688c, 0x1f83d9ab, 0x5be0cd19,\\n]);\\n\\n/** Initial SHA224 state. Bits 32..64 of frac part of sqrt of primes 23..53 */\\nexport const SHA224_IV: Uint32Array = /* @__PURE__ */ Uint32Array.from([\\n 0xc1059ed8, 0x367cd507, 0x3070dd17, 0xf70e5939, 0xffc00b31, 0x68581511, 0x64f98fa7, 0xbefa4fa4,\\n]);\\n\\n/** Initial SHA384 state. Bits 0..64 of frac part of sqrt of primes 23..53 */\\nexport const SHA384_IV: Uint32Array = /* @__PURE__ */ Uint32Array.from([\\n 0xcbbb9d5d, 0xc1059ed8, 0x629a292a, 0x367cd507, 0x9159015a, 0x3070dd17, 0x152fecd8, 0xf70e5939,\\n 0x67332667, 0xffc00b31, 0x8eb44a87, 0x68581511, 0xdb0c2e0d, 0x64f98fa7, 0x47b5481d, 0xbefa4fa4,\\n]);\\n\\n/** Initial SHA512 state. Bits 0..64 of frac part of sqrt of primes 2..19 */\\nexport const SHA512_IV: Uint32Array = /* @__PURE__ */ Uint32Array.from([\\n 0x6a09e667, 0xf3bcc908, 0xbb67ae85, 0x84caa73b, 0x3c6ef372, 0xfe94f82b, 0xa54ff53a, 0x5f1d36f1,\\n 0x510e527f, 0xade682d1, 0x9b05688c, 0x2b3e6c1f, 0x1f83d9ab, 0xfb41bd6b, 0x5be0cd19, 0x137e2179,\\n]);\\n\",\"/**\\n * SHA2 hash function. A.k.a. sha256, sha384, sha512, sha512_224, sha512_256.\\n * SHA256 is the fastest hash implementable in JS, even faster than Blake3.\\n * Check out [RFC 4634](https://datatracker.ietf.org/doc/html/rfc4634) and\\n * [FIPS 180-4](https://nvlpubs.nist.gov/nistpubs/FIPS/NIST.FIPS.180-4.pdf).\\n * @module\\n */\\nimport { Chi, HashMD, Maj, SHA224_IV, SHA256_IV, SHA384_IV, SHA512_IV } from './_md.ts';\\nimport * as u64 from './_u64.ts';\\nimport { type CHash, clean, createHasher, rotr } from './utils.ts';\\n\\n/**\\n * Round constants:\\n * First 32 bits of fractional parts of the cube roots of the first 64 primes 2..311)\\n */\\n// prettier-ignore\\nconst SHA256_K = /* @__PURE__ */ Uint32Array.from([\\n 0x428a2f98, 0x71374491, 0xb5c0fbcf, 0xe9b5dba5, 0x3956c25b, 0x59f111f1, 0x923f82a4, 0xab1c5ed5,\\n 0xd807aa98, 0x12835b01, 0x243185be, 0x550c7dc3, 0x72be5d74, 0x80deb1fe, 0x9bdc06a7, 0xc19bf174,\\n 0xe49b69c1, 0xefbe4786, 0x0fc19dc6, 0x240ca1cc, 0x2de92c6f, 0x4a7484aa, 0x5cb0a9dc, 0x76f988da,\\n 0x983e5152, 0xa831c66d, 0xb00327c8, 0xbf597fc7, 0xc6e00bf3, 0xd5a79147, 0x06ca6351, 0x14292967,\\n 0x27b70a85, 0x2e1b2138, 0x4d2c6dfc, 0x53380d13, 0x650a7354, 0x766a0abb, 0x81c2c92e, 0x92722c85,\\n 0xa2bfe8a1, 0xa81a664b, 0xc24b8b70, 0xc76c51a3, 0xd192e819, 0xd6990624, 0xf40e3585, 0x106aa070,\\n 0x19a4c116, 0x1e376c08, 0x2748774c, 0x34b0bcb5, 0x391c0cb3, 0x4ed8aa4a, 0x5b9cca4f, 0x682e6ff3,\\n 0x748f82ee, 0x78a5636f, 0x84c87814, 0x8cc70208, 0x90befffa, 0xa4506ceb, 0xbef9a3f7, 0xc67178f2\\n]);\\n\\n/** Reusable temporary buffer. \\\"W\\\" comes straight from spec. */\\nconst SHA256_W = /* @__PURE__ */ new Uint32Array(64);\\nexport class SHA256 extends HashMD {\\n // We cannot use array here since array allows indexing by variable\\n // which means optimizer/compiler cannot use registers.\\n protected A: number = SHA256_IV[0] | 0;\\n protected B: number = SHA256_IV[1] | 0;\\n protected C: number = SHA256_IV[2] | 0;\\n protected D: number = SHA256_IV[3] | 0;\\n protected E: number = SHA256_IV[4] | 0;\\n protected F: number = SHA256_IV[5] | 0;\\n protected G: number = SHA256_IV[6] | 0;\\n protected H: number = SHA256_IV[7] | 0;\\n\\n constructor(outputLen: number = 32) {\\n super(64, outputLen, 8, false);\\n }\\n protected get(): [number, number, number, number, number, number, number, number] {\\n const { A, B, C, D, E, F, G, H } = this;\\n return [A, B, C, D, E, F, G, H];\\n }\\n // prettier-ignore\\n protected set(\\n A: number, B: number, C: number, D: number, E: number, F: number, G: number, H: number\\n ): void {\\n this.A = A | 0;\\n this.B = B | 0;\\n this.C = C | 0;\\n this.D = D | 0;\\n this.E = E | 0;\\n this.F = F | 0;\\n this.G = G | 0;\\n this.H = H | 0;\\n }\\n protected process(view: DataView, offset: number): void {\\n // Extend the first 16 words into the remaining 48 words w[16..63] of the message schedule array\\n for (let i = 0; i < 16; i++, offset += 4) SHA256_W[i] = view.getUint32(offset, false);\\n for (let i = 16; i < 64; i++) {\\n const W15 = SHA256_W[i - 15];\\n const W2 = SHA256_W[i - 2];\\n const s0 = rotr(W15, 7) ^ rotr(W15, 18) ^ (W15 >>> 3);\\n const s1 = rotr(W2, 17) ^ rotr(W2, 19) ^ (W2 >>> 10);\\n SHA256_W[i] = (s1 + SHA256_W[i - 7] + s0 + SHA256_W[i - 16]) | 0;\\n }\\n // Compression function main loop, 64 rounds\\n let { A, B, C, D, E, F, G, H } = this;\\n for (let i = 0; i < 64; i++) {\\n const sigma1 = rotr(E, 6) ^ rotr(E, 11) ^ rotr(E, 25);\\n const T1 = (H + sigma1 + Chi(E, F, G) + SHA256_K[i] + SHA256_W[i]) | 0;\\n const sigma0 = rotr(A, 2) ^ rotr(A, 13) ^ rotr(A, 22);\\n const T2 = (sigma0 + Maj(A, B, C)) | 0;\\n H = G;\\n G = F;\\n F = E;\\n E = (D + T1) | 0;\\n D = C;\\n C = B;\\n B = A;\\n A = (T1 + T2) | 0;\\n }\\n // Add the compressed chunk to the current hash value\\n A = (A + this.A) | 0;\\n B = (B + this.B) | 0;\\n C = (C + this.C) | 0;\\n D = (D + this.D) | 0;\\n E = (E + this.E) | 0;\\n F = (F + this.F) | 0;\\n G = (G + this.G) | 0;\\n H = (H + this.H) | 0;\\n this.set(A, B, C, D, E, F, G, H);\\n }\\n protected roundClean(): void {\\n clean(SHA256_W);\\n }\\n destroy(): void {\\n this.set(0, 0, 0, 0, 0, 0, 0, 0);\\n clean(this.buffer);\\n }\\n}\\n\\nexport class SHA224 extends SHA256 {\\n protected A: number = SHA224_IV[0] | 0;\\n protected B: number = SHA224_IV[1] | 0;\\n protected C: number = SHA224_IV[2] | 0;\\n protected D: number = SHA224_IV[3] | 0;\\n protected E: number = SHA224_IV[4] | 0;\\n protected F: number = SHA224_IV[5] | 0;\\n protected G: number = SHA224_IV[6] | 0;\\n protected H: number = SHA224_IV[7] | 0;\\n constructor() {\\n super(28);\\n }\\n}\\n\\n// SHA2-512 is slower than sha256 in js because u64 operations are slow.\\n\\n// Round contants\\n// First 32 bits of the fractional parts of the cube roots of the first 80 primes 2..409\\n// prettier-ignore\\nconst K512 = /* @__PURE__ */ (() => u64.split([\\n '0x428a2f98d728ae22', '0x7137449123ef65cd', '0xb5c0fbcfec4d3b2f', '0xe9b5dba58189dbbc',\\n '0x3956c25bf348b538', '0x59f111f1b605d019', '0x923f82a4af194f9b', '0xab1c5ed5da6d8118',\\n '0xd807aa98a3030242', '0x12835b0145706fbe', '0x243185be4ee4b28c', '0x550c7dc3d5ffb4e2',\\n '0x72be5d74f27b896f', '0x80deb1fe3b1696b1', '0x9bdc06a725c71235', '0xc19bf174cf692694',\\n '0xe49b69c19ef14ad2', '0xefbe4786384f25e3', '0x0fc19dc68b8cd5b5', '0x240ca1cc77ac9c65',\\n '0x2de92c6f592b0275', '0x4a7484aa6ea6e483', '0x5cb0a9dcbd41fbd4', '0x76f988da831153b5',\\n '0x983e5152ee66dfab', '0xa831c66d2db43210', '0xb00327c898fb213f', '0xbf597fc7beef0ee4',\\n '0xc6e00bf33da88fc2', '0xd5a79147930aa725', '0x06ca6351e003826f', '0x142929670a0e6e70',\\n '0x27b70a8546d22ffc', '0x2e1b21385c26c926', '0x4d2c6dfc5ac42aed', '0x53380d139d95b3df',\\n '0x650a73548baf63de', '0x766a0abb3c77b2a8', '0x81c2c92e47edaee6', '0x92722c851482353b',\\n '0xa2bfe8a14cf10364', '0xa81a664bbc423001', '0xc24b8b70d0f89791', '0xc76c51a30654be30',\\n '0xd192e819d6ef5218', '0xd69906245565a910', '0xf40e35855771202a', '0x106aa07032bbd1b8',\\n '0x19a4c116b8d2d0c8', '0x1e376c085141ab53', '0x2748774cdf8eeb99', '0x34b0bcb5e19b48a8',\\n '0x391c0cb3c5c95a63', '0x4ed8aa4ae3418acb', '0x5b9cca4f7763e373', '0x682e6ff3d6b2b8a3',\\n '0x748f82ee5defb2fc', '0x78a5636f43172f60', '0x84c87814a1f0ab72', '0x8cc702081a6439ec',\\n '0x90befffa23631e28', '0xa4506cebde82bde9', '0xbef9a3f7b2c67915', '0xc67178f2e372532b',\\n '0xca273eceea26619c', '0xd186b8c721c0c207', '0xeada7dd6cde0eb1e', '0xf57d4f7fee6ed178',\\n '0x06f067aa72176fba', '0x0a637dc5a2c898a6', '0x113f9804bef90dae', '0x1b710b35131c471b',\\n '0x28db77f523047d84', '0x32caab7b40c72493', '0x3c9ebe0a15c9bebc', '0x431d67c49c100d4c',\\n '0x4cc5d4becb3e42b6', '0x597f299cfc657e2a', '0x5fcb6fab3ad6faec', '0x6c44198c4a475817'\\n].map(n => BigInt(n))))();\\nconst SHA512_Kh = /* @__PURE__ */ (() => K512[0])();\\nconst SHA512_Kl = /* @__PURE__ */ (() => K512[1])();\\n\\n// Reusable temporary buffers\\nconst SHA512_W_H = /* @__PURE__ */ new Uint32Array(80);\\nconst SHA512_W_L = /* @__PURE__ */ new Uint32Array(80);\\n\\nexport class SHA512 extends HashMD {\\n // We cannot use array here since array allows indexing by variable\\n // which means optimizer/compiler cannot use registers.\\n // h -- high 32 bits, l -- low 32 bits\\n protected Ah: number = SHA512_IV[0] | 0;\\n protected Al: number = SHA512_IV[1] | 0;\\n protected Bh: number = SHA512_IV[2] | 0;\\n protected Bl: number = SHA512_IV[3] | 0;\\n protected Ch: number = SHA512_IV[4] | 0;\\n protected Cl: number = SHA512_IV[5] | 0;\\n protected Dh: number = SHA512_IV[6] | 0;\\n protected Dl: number = SHA512_IV[7] | 0;\\n protected Eh: number = SHA512_IV[8] | 0;\\n protected El: number = SHA512_IV[9] | 0;\\n protected Fh: number = SHA512_IV[10] | 0;\\n protected Fl: number = SHA512_IV[11] | 0;\\n protected Gh: number = SHA512_IV[12] | 0;\\n protected Gl: number = SHA512_IV[13] | 0;\\n protected Hh: number = SHA512_IV[14] | 0;\\n protected Hl: number = SHA512_IV[15] | 0;\\n\\n constructor(outputLen: number = 64) {\\n super(128, outputLen, 16, false);\\n }\\n // prettier-ignore\\n protected get(): [\\n number, number, number, number, number, number, number, number,\\n number, number, number, number, number, number, number, number\\n ] {\\n const { Ah, Al, Bh, Bl, Ch, Cl, Dh, Dl, Eh, El, Fh, Fl, Gh, Gl, Hh, Hl } = this;\\n return [Ah, Al, Bh, Bl, Ch, Cl, Dh, Dl, Eh, El, Fh, Fl, Gh, Gl, Hh, Hl];\\n }\\n // prettier-ignore\\n protected set(\\n Ah: number, Al: number, Bh: number, Bl: number, Ch: number, Cl: number, Dh: number, Dl: number,\\n Eh: number, El: number, Fh: number, Fl: number, Gh: number, Gl: number, Hh: number, Hl: number\\n ): void {\\n this.Ah = Ah | 0;\\n this.Al = Al | 0;\\n this.Bh = Bh | 0;\\n this.Bl = Bl | 0;\\n this.Ch = Ch | 0;\\n this.Cl = Cl | 0;\\n this.Dh = Dh | 0;\\n this.Dl = Dl | 0;\\n this.Eh = Eh | 0;\\n this.El = El | 0;\\n this.Fh = Fh | 0;\\n this.Fl = Fl | 0;\\n this.Gh = Gh | 0;\\n this.Gl = Gl | 0;\\n this.Hh = Hh | 0;\\n this.Hl = Hl | 0;\\n }\\n protected process(view: DataView, offset: number): void {\\n // Extend the first 16 words into the remaining 64 words w[16..79] of the message schedule array\\n for (let i = 0; i < 16; i++, offset += 4) {\\n SHA512_W_H[i] = view.getUint32(offset);\\n SHA512_W_L[i] = view.getUint32((offset += 4));\\n }\\n for (let i = 16; i < 80; i++) {\\n // s0 := (w[i-15] rightrotate 1) xor (w[i-15] rightrotate 8) xor (w[i-15] rightshift 7)\\n const W15h = SHA512_W_H[i - 15] | 0;\\n const W15l = SHA512_W_L[i - 15] | 0;\\n const s0h = u64.rotrSH(W15h, W15l, 1) ^ u64.rotrSH(W15h, W15l, 8) ^ u64.shrSH(W15h, W15l, 7);\\n const s0l = u64.rotrSL(W15h, W15l, 1) ^ u64.rotrSL(W15h, W15l, 8) ^ u64.shrSL(W15h, W15l, 7);\\n // s1 := (w[i-2] rightrotate 19) xor (w[i-2] rightrotate 61) xor (w[i-2] rightshift 6)\\n const W2h = SHA512_W_H[i - 2] | 0;\\n const W2l = SHA512_W_L[i - 2] | 0;\\n const s1h = u64.rotrSH(W2h, W2l, 19) ^ u64.rotrBH(W2h, W2l, 61) ^ u64.shrSH(W2h, W2l, 6);\\n const s1l = u64.rotrSL(W2h, W2l, 19) ^ u64.rotrBL(W2h, W2l, 61) ^ u64.shrSL(W2h, W2l, 6);\\n // SHA256_W[i] = s0 + s1 + SHA256_W[i - 7] + SHA256_W[i - 16];\\n const SUMl = u64.add4L(s0l, s1l, SHA512_W_L[i - 7], SHA512_W_L[i - 16]);\\n const SUMh = u64.add4H(SUMl, s0h, s1h, SHA512_W_H[i - 7], SHA512_W_H[i - 16]);\\n SHA512_W_H[i] = SUMh | 0;\\n SHA512_W_L[i] = SUMl | 0;\\n }\\n let { Ah, Al, Bh, Bl, Ch, Cl, Dh, Dl, Eh, El, Fh, Fl, Gh, Gl, Hh, Hl } = this;\\n // Compression function main loop, 80 rounds\\n for (let i = 0; i < 80; i++) {\\n // S1 := (e rightrotate 14) xor (e rightrotate 18) xor (e rightrotate 41)\\n const sigma1h = u64.rotrSH(Eh, El, 14) ^ u64.rotrSH(Eh, El, 18) ^ u64.rotrBH(Eh, El, 41);\\n const sigma1l = u64.rotrSL(Eh, El, 14) ^ u64.rotrSL(Eh, El, 18) ^ u64.rotrBL(Eh, El, 41);\\n //const T1 = (H + sigma1 + Chi(E, F, G) + SHA256_K[i] + SHA256_W[i]) | 0;\\n const CHIh = (Eh & Fh) ^ (~Eh & Gh);\\n const CHIl = (El & Fl) ^ (~El & Gl);\\n // T1 = H + sigma1 + Chi(E, F, G) + SHA512_K[i] + SHA512_W[i]\\n // prettier-ignore\\n const T1ll = u64.add5L(Hl, sigma1l, CHIl, SHA512_Kl[i], SHA512_W_L[i]);\\n const T1h = u64.add5H(T1ll, Hh, sigma1h, CHIh, SHA512_Kh[i], SHA512_W_H[i]);\\n const T1l = T1ll | 0;\\n // S0 := (a rightrotate 28) xor (a rightrotate 34) xor (a rightrotate 39)\\n const sigma0h = u64.rotrSH(Ah, Al, 28) ^ u64.rotrBH(Ah, Al, 34) ^ u64.rotrBH(Ah, Al, 39);\\n const sigma0l = u64.rotrSL(Ah, Al, 28) ^ u64.rotrBL(Ah, Al, 34) ^ u64.rotrBL(Ah, Al, 39);\\n const MAJh = (Ah & Bh) ^ (Ah & Ch) ^ (Bh & Ch);\\n const MAJl = (Al & Bl) ^ (Al & Cl) ^ (Bl & Cl);\\n Hh = Gh | 0;\\n Hl = Gl | 0;\\n Gh = Fh | 0;\\n Gl = Fl | 0;\\n Fh = Eh | 0;\\n Fl = El | 0;\\n ({ h: Eh, l: El } = u64.add(Dh | 0, Dl | 0, T1h | 0, T1l | 0));\\n Dh = Ch | 0;\\n Dl = Cl | 0;\\n Ch = Bh | 0;\\n Cl = Bl | 0;\\n Bh = Ah | 0;\\n Bl = Al | 0;\\n const All = u64.add3L(T1l, sigma0l, MAJl);\\n Ah = u64.add3H(All, T1h, sigma0h, MAJh);\\n Al = All | 0;\\n }\\n // Add the compressed chunk to the current hash value\\n ({ h: Ah, l: Al } = u64.add(this.Ah | 0, this.Al | 0, Ah | 0, Al | 0));\\n ({ h: Bh, l: Bl } = u64.add(this.Bh | 0, this.Bl | 0, Bh | 0, Bl | 0));\\n ({ h: Ch, l: Cl } = u64.add(this.Ch | 0, this.Cl | 0, Ch | 0, Cl | 0));\\n ({ h: Dh, l: Dl } = u64.add(this.Dh | 0, this.Dl | 0, Dh | 0, Dl | 0));\\n ({ h: Eh, l: El } = u64.add(this.Eh | 0, this.El | 0, Eh | 0, El | 0));\\n ({ h: Fh, l: Fl } = u64.add(this.Fh | 0, this.Fl | 0, Fh | 0, Fl | 0));\\n ({ h: Gh, l: Gl } = u64.add(this.Gh | 0, this.Gl | 0, Gh | 0, Gl | 0));\\n ({ h: Hh, l: Hl } = u64.add(this.Hh | 0, this.Hl | 0, Hh | 0, Hl | 0));\\n this.set(Ah, Al, Bh, Bl, Ch, Cl, Dh, Dl, Eh, El, Fh, Fl, Gh, Gl, Hh, Hl);\\n }\\n protected roundClean(): void {\\n clean(SHA512_W_H, SHA512_W_L);\\n }\\n destroy(): void {\\n clean(this.buffer);\\n this.set(0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);\\n }\\n}\\n\\nexport class SHA384 extends SHA512 {\\n protected Ah: number = SHA384_IV[0] | 0;\\n protected Al: number = SHA384_IV[1] | 0;\\n protected Bh: number = SHA384_IV[2] | 0;\\n protected Bl: number = SHA384_IV[3] | 0;\\n protected Ch: number = SHA384_IV[4] | 0;\\n protected Cl: number = SHA384_IV[5] | 0;\\n protected Dh: number = SHA384_IV[6] | 0;\\n protected Dl: number = SHA384_IV[7] | 0;\\n protected Eh: number = SHA384_IV[8] | 0;\\n protected El: number = SHA384_IV[9] | 0;\\n protected Fh: number = SHA384_IV[10] | 0;\\n protected Fl: number = SHA384_IV[11] | 0;\\n protected Gh: number = SHA384_IV[12] | 0;\\n protected Gl: number = SHA384_IV[13] | 0;\\n protected Hh: number = SHA384_IV[14] | 0;\\n protected Hl: number = SHA384_IV[15] | 0;\\n\\n constructor() {\\n super(48);\\n }\\n}\\n\\n/**\\n * Truncated SHA512/256 and SHA512/224.\\n * SHA512_IV is XORed with 0xa5a5a5a5a5a5a5a5, then used as \\\"intermediary\\\" IV of SHA512/t.\\n * Then t hashes string to produce result IV.\\n * See `test/misc/sha2-gen-iv.js`.\\n */\\n\\n/** SHA512/224 IV */\\nconst T224_IV = /* @__PURE__ */ Uint32Array.from([\\n 0x8c3d37c8, 0x19544da2, 0x73e19966, 0x89dcd4d6, 0x1dfab7ae, 0x32ff9c82, 0x679dd514, 0x582f9fcf,\\n 0x0f6d2b69, 0x7bd44da8, 0x77e36f73, 0x04c48942, 0x3f9d85a8, 0x6a1d36c8, 0x1112e6ad, 0x91d692a1,\\n]);\\n\\n/** SHA512/256 IV */\\nconst T256_IV = /* @__PURE__ */ Uint32Array.from([\\n 0x22312194, 0xfc2bf72c, 0x9f555fa3, 0xc84c64c2, 0x2393b86b, 0x6f53b151, 0x96387719, 0x5940eabd,\\n 0x96283ee2, 0xa88effe3, 0xbe5e1e25, 0x53863992, 0x2b0199fc, 0x2c85b8aa, 0x0eb72ddc, 0x81c52ca2,\\n]);\\n\\nexport class SHA512_224 extends SHA512 {\\n protected Ah: number = T224_IV[0] | 0;\\n protected Al: number = T224_IV[1] | 0;\\n protected Bh: number = T224_IV[2] | 0;\\n protected Bl: number = T224_IV[3] | 0;\\n protected Ch: number = T224_IV[4] | 0;\\n protected Cl: number = T224_IV[5] | 0;\\n protected Dh: number = T224_IV[6] | 0;\\n protected Dl: number = T224_IV[7] | 0;\\n protected Eh: number = T224_IV[8] | 0;\\n protected El: number = T224_IV[9] | 0;\\n protected Fh: number = T224_IV[10] | 0;\\n protected Fl: number = T224_IV[11] | 0;\\n protected Gh: number = T224_IV[12] | 0;\\n protected Gl: number = T224_IV[13] | 0;\\n protected Hh: number = T224_IV[14] | 0;\\n protected Hl: number = T224_IV[15] | 0;\\n\\n constructor() {\\n super(28);\\n }\\n}\\n\\nexport class SHA512_256 extends SHA512 {\\n protected Ah: number = T256_IV[0] | 0;\\n protected Al: number = T256_IV[1] | 0;\\n protected Bh: number = T256_IV[2] | 0;\\n protected Bl: number = T256_IV[3] | 0;\\n protected Ch: number = T256_IV[4] | 0;\\n protected Cl: number = T256_IV[5] | 0;\\n protected Dh: number = T256_IV[6] | 0;\\n protected Dl: number = T256_IV[7] | 0;\\n protected Eh: number = T256_IV[8] | 0;\\n protected El: number = T256_IV[9] | 0;\\n protected Fh: number = T256_IV[10] | 0;\\n protected Fl: number = T256_IV[11] | 0;\\n protected Gh: number = T256_IV[12] | 0;\\n protected Gl: number = T256_IV[13] | 0;\\n protected Hh: number = T256_IV[14] | 0;\\n protected Hl: number = T256_IV[15] | 0;\\n\\n constructor() {\\n super(32);\\n }\\n}\\n\\n/**\\n * SHA2-256 hash function from RFC 4634.\\n *\\n * It is the fastest JS hash, even faster than Blake3.\\n * To break sha256 using birthday attack, attackers need to try 2^128 hashes.\\n * BTC network is doing 2^70 hashes/sec (2^95 hashes/year) as per 2025.\\n */\\nexport const sha256: CHash = /* @__PURE__ */ createHasher(() => new SHA256());\\n/** SHA2-224 hash function from RFC 4634 */\\nexport const sha224: CHash = /* @__PURE__ */ createHasher(() => new SHA224());\\n\\n/** SHA2-512 hash function from RFC 4634. */\\nexport const sha512: CHash = /* @__PURE__ */ createHasher(() => new SHA512());\\n/** SHA2-384 hash function from RFC 4634. */\\nexport const sha384: CHash = /* @__PURE__ */ createHasher(() => new SHA384());\\n\\n/**\\n * SHA2-512/256 \\\"truncated\\\" hash function, with improved resistance to length extension attacks.\\n * See the paper on [truncated SHA512](https://eprint.iacr.org/2010/548.pdf).\\n */\\nexport const sha512_256: CHash = /* @__PURE__ */ createHasher(() => new SHA512_256());\\n/**\\n * SHA2-512/224 \\\"truncated\\\" hash function, with improved resistance to length extension attacks.\\n * See the paper on [truncated SHA512](https://eprint.iacr.org/2010/548.pdf).\\n */\\nexport const sha512_224: CHash = /* @__PURE__ */ createHasher(() => new SHA512_224());\\n\",\"/**\\n * SHA2-256 a.k.a. sha256. In JS, it is the fastest hash, even faster than Blake3.\\n *\\n * To break sha256 using birthday attack, attackers need to try 2^128 hashes.\\n * BTC network is doing 2^70 hashes/sec (2^95 hashes/year) as per 2025.\\n *\\n * Check out [FIPS 180-4](https://nvlpubs.nist.gov/nistpubs/FIPS/NIST.FIPS.180-4.pdf).\\n * @module\\n * @deprecated\\n */\\nimport {\\n SHA224 as SHA224n,\\n sha224 as sha224n,\\n SHA256 as SHA256n,\\n sha256 as sha256n,\\n} from './sha2.ts';\\n/** @deprecated Use import from `noble/hashes/sha2` module */\\nexport const SHA256: typeof SHA256n = SHA256n;\\n/** @deprecated Use import from `noble/hashes/sha2` module */\\nexport const sha256: typeof sha256n = sha256n;\\n/** @deprecated Use import from `noble/hashes/sha2` module */\\nexport const SHA224: typeof SHA224n = SHA224n;\\n/** @deprecated Use import from `noble/hashes/sha2` module */\\nexport const sha224: typeof sha224n = sha224n;\\n\",\"\\nexport default class TinyQueue {\\n constructor(data = [], compare = (a, b) => (a < b ? -1 : a > b ? 1 : 0)) {\\n this.data = data;\\n this.length = this.data.length;\\n this.compare = compare;\\n\\n if (this.length > 0) {\\n for (let i = (this.length >> 1) - 1; i >= 0; i--) this._down(i);\\n }\\n }\\n\\n push(item) {\\n this.data.push(item);\\n this._up(this.length++);\\n }\\n\\n pop() {\\n if (this.length === 0) return undefined;\\n\\n const top = this.data[0];\\n const bottom = this.data.pop();\\n\\n if (--this.length > 0) {\\n this.data[0] = bottom;\\n this._down(0);\\n }\\n\\n return top;\\n }\\n\\n peek() {\\n return this.data[0];\\n }\\n\\n _up(pos) {\\n const {data, compare} = this;\\n const item = data[pos];\\n\\n while (pos > 0) {\\n const parent = (pos - 1) >> 1;\\n const current = data[parent];\\n if (compare(item, current) >= 0) break;\\n data[pos] = current;\\n pos = parent;\\n }\\n\\n data[pos] = item;\\n }\\n\\n _down(pos) {\\n const {data, compare} = this;\\n const halfLength = this.length >> 1;\\n const item = data[pos];\\n\\n while (pos < halfLength) {\\n let bestChild = (pos << 1) + 1; // initially it is the left child\\n const right = bestChild + 1;\\n\\n if (right < this.length && compare(data[right], data[bestChild]) < 0) {\\n bestChild = right;\\n }\\n if (compare(data[bestChild], item) >= 0) break;\\n\\n data[pos] = data[bestChild];\\n pos = bestChild;\\n }\\n\\n data[pos] = item;\\n }\\n}\\n\"],\"version\":3}", + "originMeta": { + "originalPath": "node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/_md.js", + "packageName": "@noble/hashes", + "packageVersion": "1.8.0", + "integrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562" + } + } + ], + "builderVersion": "deterministic-builder-v1", + "dependencyIntegrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562", + "diagnosticsMeta": { + "entryPath": "/workspace/apps/ecosystem-certifier/fixtures/flagship/knowledge-pack-entry.ts", + "modulePaths": [ + "./knowledge-pack-entry.js" + ] + }, + "graphHash": "f958784978f428dd5f0403b87b386190472ab2afc3fff78fff214da50aaf3699" + } + } + }, + "manifest": { + "abi_id": "Host.v2", + "abi_version": 2, + "functions": [ + { + "fn_id": 1, + "js_path": [ + "document", + "get" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 2, + "js_path": [ + "document", + "getCanonical" + ], + "effect": "READ", + "arity": 1, + "arg_schema": [ + { + "type": "string" + } + ], + "return_schema": { + "type": "dv" + }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [ + 2048 + ] + }, + "error_codes": [ + { + "code": "INVALID_PATH", + "tag": "host/invalid_path" + }, + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + }, + { + "code": "NOT_FOUND", + "tag": "host/not_found" + } + ] + }, + { + "fn_id": 3, + "js_path": [ + "emit" + ], + "effect": "EMIT", + "arity": 1, + "arg_schema": [ + { + "type": "dv" + } + ], + "return_schema": { + "type": "null" + }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [ + { + "code": "LIMIT_EXCEEDED", + "tag": "host/limit" + } + ] + } + ] + } + } + ] +} diff --git a/apps/bluequickjs-playground/public/generated/playground-oog-boundaries.json b/apps/bluequickjs-playground/public/generated/playground-oog-boundaries.json new file mode 100644 index 0000000..a619b43 --- /dev/null +++ b/apps/bluequickjs-playground/public/generated/playground-oog-boundaries.json @@ -0,0 +1,109 @@ +{ + "generatedAt": "current-worktree", + "metadata": { + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8 + }, + "boundaries": { + "example-basic-script": { + "firstSuccessGas": "74", + "lastFailureGas": "73", + "successGasUsed": "74", + "successGasRemaining": "0", + "failureGasUsed": "73", + "failureGasRemaining": "0", + "failureCode": "OOG", + "failureTag": "vm/out_of_gas" + }, + "example-module-pack": { + "firstSuccessGas": "145", + "lastFailureGas": "144", + "successGasUsed": "145", + "successGasRemaining": "0", + "failureGasUsed": "144", + "failureGasRemaining": "0", + "failureCode": "MODULE_EXPORT_MISSING", + "failureTag": "vm/module_pack" + }, + "example-library-reuse": { + "firstSuccessGas": "2070503", + "lastFailureGas": "2070502", + "successGasUsed": "2070503", + "successGasRemaining": "0", + "failureGasUsed": "2070502", + "failureGasRemaining": "0", + "failureCode": "MODULE_EXPORT_MISSING", + "failureTag": "vm/module_pack" + }, + "example-promises-async": { + "firstSuccessGas": "128", + "lastFailureGas": "127", + "successGasUsed": "128", + "successGasRemaining": "0", + "failureGasUsed": "127", + "failureGasRemaining": "0", + "failureCode": "OOG", + "failureTag": "vm/out_of_gas" + }, + "example-promises-library-host": { + "firstSuccessGas": "290", + "lastFailureGas": "289", + "successGasUsed": "290", + "successGasRemaining": "0", + "failureGasUsed": "289", + "failureGasRemaining": "0", + "failureCode": "MODULE_EVALUATION_ERROR", + "failureTag": "vm/module_pack" + }, + "example-binary-host-v2": { + "firstSuccessGas": "253", + "lastFailureGas": "252", + "successGasUsed": "253", + "successGasRemaining": "0", + "failureGasUsed": "252", + "failureGasRemaining": "0", + "failureCode": "OOG", + "failureTag": "vm/out_of_gas" + }, + "example-console-shim": { + "firstSuccessGas": "139", + "lastFailureGas": "138", + "successGasUsed": "139", + "successGasRemaining": "0", + "failureGasUsed": "138", + "failureGasRemaining": "0", + "failureCode": "OOG", + "failureTag": "vm/out_of_gas" + }, + "example-stable-sort": { + "firstSuccessGas": "1020", + "lastFailureGas": "1019", + "successGasUsed": "1020", + "successGasRemaining": "0", + "failureGasUsed": "1019", + "failureGasRemaining": "0", + "failureCode": "OOG", + "failureTag": "vm/out_of_gas" + }, + "example-kitchen-sink": { + "firstSuccessGas": "1390", + "lastFailureGas": "1389", + "successGasUsed": "1390", + "successGasRemaining": "0", + "failureGasUsed": "1389", + "failureGasRemaining": "0", + "failureCode": "MODULE_EVALUATION_ERROR", + "failureTag": "vm/module_pack" + }, + "example-max-gas-policy": { + "firstSuccessGas": "170099", + "lastFailureGas": "170098", + "successGasUsed": "170099", + "successGasRemaining": "0", + "failureGasUsed": "170098", + "failureGasRemaining": "0", + "failureCode": "OOG", + "failureTag": "vm/out_of_gas" + } + } +} diff --git a/apps/bluequickjs-playground/public/generated/playground-red-fixtures.json b/apps/bluequickjs-playground/public/generated/playground-red-fixtures.json new file mode 100644 index 0000000..1d16a3a --- /dev/null +++ b/apps/bluequickjs-playground/public/generated/playground-red-fixtures.json @@ -0,0 +1,170 @@ +{ + "generatedAt": "current-worktree", + "metadata": { + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8 + }, + "fixtures": [ + { + "id": "red-diff-timers", + "title": "diff package timer references are deterministically rejected", + "kind": "negative", + "executionProfile": "compat-general-v1", + "failureStage": "builder_reject", + "errorCode": null, + "errorTag": null, + "certified": true, + "docsLinks": [ + { + "label": "Workload certification", + "href": "/docs/workload-certification.md" + }, + { + "label": "Compatibility report", + "href": "/docs/ecosystem-compatibility-report.md" + }, + { + "label": "Unsupported features and why", + "href": "/docs/unsupported-features-and-why.md" + } + ], + "diagnostics": [ + { + "filePath": "./diff-entry.js", + "ruleId": "timers_disabled", + "message": "forbidden API used: setTimeout" + } + ], + "runtimeArtifact": null, + "reportSource": "ecosystem-certifier:red-diff-timers" + }, + { + "id": "red-dynamic-import", + "title": "dynamic import must be rejected at build stage", + "kind": "negative", + "executionProfile": "compat-general-v1", + "failureStage": "builder_reject", + "errorCode": null, + "errorTag": null, + "certified": true, + "docsLinks": [ + { + "label": "Workload certification", + "href": "/docs/workload-certification.md" + }, + { + "label": "Compatibility report", + "href": "/docs/ecosystem-compatibility-report.md" + }, + { + "label": "Unsupported features and why", + "href": "/docs/unsupported-features-and-why.md" + } + ], + "diagnostics": [ + { + "filePath": "./dynamic-import-entry.js", + "ruleId": "dynamic_import_disabled", + "message": "dynamic import() is disabled in deterministic mode" + } + ], + "runtimeArtifact": null, + "reportSource": "ecosystem-certifier:red-dynamic-import" + }, + { + "id": "red-proxy", + "title": "Proxy usage must be rejected at build stage", + "kind": "negative", + "executionProfile": "compat-general-v1", + "failureStage": "builder_reject", + "errorCode": null, + "errorTag": null, + "certified": true, + "docsLinks": [ + { + "label": "Workload certification", + "href": "/docs/workload-certification.md" + }, + { + "label": "Compatibility report", + "href": "/docs/ecosystem-compatibility-report.md" + }, + { + "label": "Unsupported features and why", + "href": "/docs/unsupported-features-and-why.md" + } + ], + "diagnostics": [ + { + "filePath": "./proxy-entry.js", + "ruleId": "proxy_disabled", + "message": "forbidden API used: Proxy" + } + ], + "runtimeArtifact": null, + "reportSource": "ecosystem-certifier:red-proxy" + }, + { + "id": "red-function-constructor", + "title": "Function constructor must fail deterministically in module-pack flow", + "kind": "negative", + "executionProfile": "compat-general-v1", + "failureStage": "artifact_validation", + "errorCode": "MODULE_EXPORT_MISSING", + "errorTag": "vm/module_pack", + "certified": true, + "docsLinks": [ + { + "label": "Workload certification", + "href": "/docs/workload-certification.md" + }, + { + "label": "Compatibility report", + "href": "/docs/ecosystem-compatibility-report.md" + }, + { + "label": "Unsupported features and why", + "href": "/docs/unsupported-features-and-why.md" + } + ], + "diagnostics": [], + "runtimeArtifact": { + "version": 2, + "abiId": "Host.v1", + "abiVersion": 1, + "abiManifestHash": "e23b0b2ee169900bbde7aff78e6ce20fead1715c60f8a8e3106d9959450a3d34", + "engineBuildHash": "f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea", + "gasVersion": 8, + "executionProfile": "compat-general-v1", + "sourceKind": "module-pack", + "source": { + "modulePack": { + "version": 1, + "entrySpecifier": "./function-constructor-entry.js", + "entryExport": "default", + "modules": [ + { + "specifier": "./function-constructor-entry.js", + "source": "// apps/ecosystem-certifier/fixtures/negative/function-constructor-entry.ts\nvar make = new Function(\"return 41 + 1;\");\nvar function_constructor_entry_default = make();\nexport {\n function_constructor_entry_default as default\n};\n", + "sourceMap": "{\"mappings\":\";AAAA,IAAM,OAAO,IAAI,SAAS,gBAAgB;AAE1C,IAAO,qCAAQ,KAAK;\",\"names\":[],\"sources\":[\"../apps/ecosystem-certifier/fixtures/negative/function-constructor-entry.ts\"],\"sourcesContent\":[\"const make = new Function('return 41 + 1;');\\n\\nexport default make();\\n\"],\"version\":3}", + "originMeta": { + "originalPath": "apps/ecosystem-certifier/fixtures/negative/function-constructor-entry.ts" + } + } + ], + "builderVersion": "deterministic-builder-v1", + "dependencyIntegrity": "483aad47a5ae3669a320d313a6ce1be9be705b5c52775cba1b4f45d1fada0562", + "diagnosticsMeta": { + "entryPath": "/workspace/apps/ecosystem-certifier/fixtures/negative/function-constructor-entry.ts", + "modulePaths": [ + "./function-constructor-entry.js" + ] + }, + "graphHash": "540034aad543c614a540b986b8c391e620261b8046c00edede6484f37461f21b" + } + } + }, + "reportSource": "ecosystem-certifier:red-function-constructor" + } + ] +} diff --git a/apps/bluequickjs-playground/scripts/dev.sh b/apps/bluequickjs-playground/scripts/dev.sh new file mode 100644 index 0000000..15daeac --- /dev/null +++ b/apps/bluequickjs-playground/scripts/dev.sh @@ -0,0 +1,19 @@ +#!/usr/bin/env bash +set -euo pipefail + +SCRIPT_DIR="$(cd -- "$(dirname -- "${BASH_SOURCE[0]}")" && pwd)" +REPO_ROOT="$(cd -- "${SCRIPT_DIR}/../../.." && pwd)" + +cd "${REPO_ROOT}" + +if [ ! -f "tools/emsdk/emsdk_env.sh" ]; then + echo "Missing tools/emsdk/emsdk_env.sh" + echo "Run: bash tools/scripts/setup-emsdk.sh" + exit 1 +fi + +bash tools/scripts/ensure-quickjs-submodule.sh +source tools/emsdk/emsdk_env.sh +pnpm nx build bluequickjs-playground +node apps/bluequickjs-playground/scripts/generate-playground-data.mjs +exec pnpm vite --host --port 4325 --config apps/bluequickjs-playground/vite.config.mts diff --git a/apps/bluequickjs-playground/scripts/generate-playground-data.mjs b/apps/bluequickjs-playground/scripts/generate-playground-data.mjs new file mode 100644 index 0000000..750f283 --- /dev/null +++ b/apps/bluequickjs-playground/scripts/generate-playground-data.mjs @@ -0,0 +1,960 @@ +#!/usr/bin/env node + +import { createHash } from 'node:crypto'; +import { spawnSync } from 'node:child_process'; +import { existsSync } from 'node:fs'; +import { mkdir, readFile, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { fileURLToPath } from 'node:url'; +import jiti from 'jiti'; + +const __dirname = path.dirname(fileURLToPath(import.meta.url)); +const repoRoot = path.resolve(__dirname, '..', '..', '..'); +const outDir = path.resolve( + repoRoot, + 'apps/bluequickjs-playground/public/generated', +); +const args = parseArgs(process.argv.slice(2)); + +await ensurePlaygroundBuildArtifacts(); + +const require = jiti(import.meta.url, { interopDefault: true }); + +const { + HOST_V1_HASH, + HOST_V1_MANIFEST, + HOST_V2_HASH, + HOST_V2_MANIFEST, +} = require('../../../libs/abi-manifest/src/index.ts'); +const { + buildDeterministicModulePack, + DeterministicBuilderError, +} = require('../../../libs/deterministic-builder/src/index.ts'); +const { encodeDv2 } = require('../../../libs/dv/src/index.ts'); +const { evaluate } = require('../../../libs/quickjs-runtime/src/index.ts'); +const { + loadQuickjsWasmBinary, + loadQuickjsWasmMetadata, +} = require('../../../libs/quickjs-wasm/src/index.ts'); +const { + EXAMPLE_CORPUS, + DETERMINISM_INPUT, + createDeterminismHost, + serializeHostTape, +} = require('../../../libs/test-harness/src/index.ts'); +const { + CERTIFIER_FIXTURES, + manifestForFixture, +} = require('../../../apps/ecosystem-certifier/src/shared/fixtures.ts'); +const { + createCertificationHost, +} = require('../../../apps/ecosystem-certifier/src/shared/host.ts'); + +const CERTIFICATION_INPUT = { + event: { type: 'ecosystem-certifier' }, + eventCanonical: { type: 'ecosystem-certifier' }, + steps: [], + currentContract: { id: 'ecosystem-certifier' }, + currentContractCanonical: { id: { value: 'ecosystem-certifier' } }, +}; + +const HOST_PRESET_SUMMARIES = { + determinism: { + label: 'Determinism fixture host', + description: + 'Provides stable Host.v1/Host.v2 document responses plus deterministic emit tape capture.', + documents: [ + 'path/to/doc', + 'path/to/canonical', + 'path/to/first', + 'path/to/second', + 'path/to/third', + 'bytes/payload', + ], + }, + certification: { + label: 'Certification host', + description: + 'Provides the ecosystem-certifier text and binary documents used for workload certification.', + documents: [ + 'pack/metadata.json', + 'pack/metadata.yaml', + 'docs/a.md', + 'docs/b.md', + 'docs/c.md', + 'docs/d.md', + 'bytes/payload', + 'bytes/flagship-extra', + 'pack/attachment.deflated', + ], + }, +}; + +const SELECTED_GREEN_FIXTURE_IDS = [ + 'green-semver', + 'green-base64', + 'green-markdown-it', + 'green-noble-sha', +]; + +const SELECTED_RED_FIXTURE_IDS = [ + 'red-diff-timers', + 'red-dynamic-import', + 'red-proxy', + 'red-function-constructor', +]; + +const metadata = await loadQuickjsWasmMetadata(); +const wasmBinary = await loadQuickjsWasmBinary('wasm32', 'release', metadata); +const engineBuildHash = + metadata.variants?.wasm32?.release?.engineBuildHash ?? + metadata.engineBuildHash ?? + null; +const gasVersion = metadata.gasVersion ?? null; +const generatedAt = 'current-worktree'; + +const runnableExamples = await buildExampleEntries(); +const selectedGreenFixtures = await buildGreenFixtures(); +const flagshipFixture = await buildFlagshipFixture(); +const redFixtures = await buildRedFixtures(); +const oogBoundaries = await buildOogBoundaries(runnableExamples); + +const examplesPayload = { + generatedAt, + metadata: { + engineBuildHash, + gasVersion, + wasmVariant: 'wasm32', + wasmBuildType: 'release', + }, + examples: [ + ...runnableExamples.galleryEntries, + ...selectedGreenFixtures.galleryEntries, + flagshipFixture.galleryEntry, + ], +}; + +const evidencePayload = { + generatedAt, + metadata: { + engineBuildHash, + gasVersion, + }, + evidence: { + ...runnableExamples.evidenceById, + ...selectedGreenFixtures.evidenceById, + ...flagshipFixture.evidenceById, + }, +}; + +const oogPayload = { + generatedAt, + metadata: { + engineBuildHash, + gasVersion, + }, + boundaries: oogBoundaries, +}; + +const redPayload = { + generatedAt, + metadata: { + engineBuildHash, + gasVersion, + }, + fixtures: redFixtures, +}; + +const outputs = new Map([ + ['playground-examples.json', `${JSON.stringify(examplesPayload, null, 2)}\n`], + ['playground-evidence.json', `${JSON.stringify(evidencePayload, null, 2)}\n`], + [ + 'playground-oog-boundaries.json', + `${JSON.stringify(oogPayload, null, 2)}\n`, + ], + ['playground-red-fixtures.json', `${JSON.stringify(redPayload, null, 2)}\n`], +]); + +await mkdir(outDir, { recursive: true }); + +if (args.check) { + const mismatches = []; + for (const [filename, expected] of outputs) { + const targetPath = path.join(outDir, filename); + let current = null; + try { + current = await readFile(targetPath, 'utf8'); + } catch { + current = null; + } + if (current !== expected) { + mismatches.push(filename); + } + } + + process.stdout.write( + `${JSON.stringify( + { + status: mismatches.length === 0 ? 'ok' : 'stale', + outDir: path.relative(repoRoot, outDir), + checkedFiles: [...outputs.keys()], + mismatches, + }, + null, + 2, + )}\n`, + ); + + if (mismatches.length > 0) { + process.exitCode = 1; + } +} else { + for (const [filename, contents] of outputs) { + await writeFile(path.join(outDir, filename), contents, 'utf8'); + } + + process.stdout.write( + `${JSON.stringify( + { + status: 'generated', + outDir: path.relative(repoRoot, outDir), + files: [...outputs.keys()], + }, + null, + 2, + )}\n`, + ); +} + +async function buildExampleEntries() { + const galleryEntries = []; + const evidenceById = {}; + + for (const entry of EXAMPLE_CORPUS) { + const built = await buildCorpusEntry(entry); + galleryEntries.push(built.galleryEntry); + evidenceById[built.galleryEntry.id] = built.evidence; + } + + return { galleryEntries, evidenceById }; +} + +async function buildCorpusEntry(entry) { + const id = `example-${entry.slug}`; + const docsLinks = docsLinksForExample(entry.slug); + const gasLimit = gasLimitForExample(entry.slug); + const sourcePaths = entry.sourcePaths; + const sourceText = await readPrimarySource(sourcePaths[0]); + const profile = Array.isArray(entry.profile) + ? entry.profile[0] + : entry.profile; + + let program; + let manifest; + const hostPreset = 'determinism'; + let description = exampleDescription(entry.slug); + + switch (entry.slug) { + case 'basic-script': + case 'promises-async': + case 'console-shim': + case 'stable-sort': + case 'max-gas-policy': + program = createScriptProgram({ + code: await readPrimarySource(sourcePaths[0]), + profile, + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + }); + manifest = HOST_V1_MANIFEST; + break; + case 'binary-host-v2': + program = createScriptProgram({ + code: await readPrimarySource(sourcePaths[0]), + profile: 'compat-binary-v1', + abiId: 'Host.v2', + abiVersion: 2, + abiManifestHash: HOST_V2_HASH, + }); + manifest = HOST_V2_MANIFEST; + break; + case 'module-pack': + case 'promises-library-host': + case 'kitchen-sink': { + const built = await buildProgramArtifact({ + entryPath: sourcePaths[0], + profile, + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + }); + program = built.programArtifact; + manifest = HOST_V1_MANIFEST; + break; + } + case 'library-reuse': { + const built = await buildProgramArtifact({ + entryPath: 'libs/test-harness/fixtures/library-reuse/chess-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + }); + program = built.programArtifact; + manifest = HOST_V1_MANIFEST; + description += + ' The binary base64 companion source remains listed alongside the chess.js entry for comparison.'; + break; + } + default: + throw new Error(`unhandled example corpus slug: ${entry.slug}`); + } + + const execution = await evaluateWithPreset({ + id, + title: entry.title, + program, + manifest, + gasLimit, + hostPreset, + }); + + return { + galleryEntry: { + id, + title: entry.title, + kind: 'example', + badge: `Example ${entry.id}`, + description, + certified: true, + executionProfile: program.executionProfile, + sourceKind: program.sourceKind, + abiId: program.abiId, + gasLimit: gasLimit.toString(), + sourcePaths, + sourceText, + hostPreset, + hostSummary: HOST_PRESET_SUMMARIES[hostPreset], + docsLinks, + supportsOogSearch: true, + program, + manifest, + }, + evidence: { + ...execution.snapshot, + certified: true, + reportSource: `examples/${entry.id.toString().padStart(2, '0')}-${entry.slug}`, + fixtureCoverage: entry.coverage, + }, + }; +} + +async function buildGreenFixtures() { + const galleryEntries = []; + const evidenceById = {}; + + for (const fixtureId of SELECTED_GREEN_FIXTURE_IDS) { + const fixture = CERTIFIER_FIXTURES.find((item) => item.id === fixtureId); + if (!fixture) { + throw new Error(`unknown selected green fixture: ${fixtureId}`); + } + + const built = await buildProgramArtifact({ + entryPath: fixture.entryPath, + profile: fixture.profile, + abiId: fixture.abiId, + abiVersion: fixture.abiVersion, + abiManifestHash: fixture.abiManifestHash, + }); + const manifest = manifestForFixture(fixture); + const execution = await evaluateWithPreset({ + id: fixture.id, + title: fixture.title, + program: built.programArtifact, + manifest, + gasLimit: fixture.gasLimit, + hostPreset: 'certification', + }); + + galleryEntries.push({ + id: fixture.id, + title: fixture.title, + kind: 'ecosystem-green', + badge: 'Green ecosystem fixture', + description: fixtureDescription(fixture.id), + certified: true, + executionProfile: built.programArtifact.executionProfile, + sourceKind: built.programArtifact.sourceKind, + abiId: built.programArtifact.abiId, + gasLimit: fixture.gasLimit.toString(), + sourcePaths: [fixture.entryPath], + sourceText: await readPrimarySource(fixture.entryPath), + hostPreset: 'certification', + hostSummary: HOST_PRESET_SUMMARIES.certification, + docsLinks: docsLinksForFixture(fixture.id), + supportsOogSearch: false, + program: built.programArtifact, + manifest, + }); + + evidenceById[fixture.id] = { + ...execution.snapshot, + certified: true, + reportSource: `ecosystem-certifier:${fixture.id}`, + fixtureCoverage: [ + { suite: 'ecosystem-certifier', fixtureName: fixture.id }, + ], + }; + } + + return { galleryEntries, evidenceById }; +} + +async function buildFlagshipFixture() { + const fixture = CERTIFIER_FIXTURES.find( + (item) => item.id === 'flagship-knowledge-pack', + ); + if (!fixture) { + throw new Error('flagship fixture not found'); + } + + const built = await buildProgramArtifact({ + entryPath: fixture.entryPath, + profile: fixture.profile, + abiId: fixture.abiId, + abiVersion: fixture.abiVersion, + abiManifestHash: fixture.abiManifestHash, + }); + const manifest = manifestForFixture(fixture); + const execution = await evaluateWithPreset({ + id: fixture.id, + title: fixture.title, + program: built.programArtifact, + manifest, + gasLimit: fixture.gasLimit, + hostPreset: 'certification', + }); + + return { + galleryEntry: { + id: fixture.id, + title: fixture.title, + kind: 'flagship', + badge: 'Flagship workload', + description: + 'A browsable flagship deterministic workload that mixes static imports, Promise jobs, text and binary host data, and certification-ready evidence.', + certified: true, + executionProfile: built.programArtifact.executionProfile, + sourceKind: built.programArtifact.sourceKind, + abiId: built.programArtifact.abiId, + gasLimit: fixture.gasLimit.toString(), + sourcePaths: [fixture.entryPath], + sourceText: await readPrimarySource(fixture.entryPath), + hostPreset: 'certification', + hostSummary: HOST_PRESET_SUMMARIES.certification, + docsLinks: docsLinksForFixture(fixture.id), + supportsOogSearch: false, + program: built.programArtifact, + manifest, + }, + evidenceById: { + [fixture.id]: { + ...execution.snapshot, + certified: true, + reportSource: `ecosystem-certifier:${fixture.id}`, + fixtureCoverage: [ + { suite: 'ecosystem-certifier', fixtureName: fixture.id }, + ], + }, + }, + }; +} + +async function buildRedFixtures() { + const fixtures = []; + + for (const fixtureId of SELECTED_RED_FIXTURE_IDS) { + const fixture = CERTIFIER_FIXTURES.find((item) => item.id === fixtureId); + if (!fixture) { + throw new Error(`unknown selected red fixture: ${fixtureId}`); + } + + try { + const built = await buildProgramArtifact({ + entryPath: fixture.entryPath, + profile: fixture.profile, + abiId: fixture.abiId, + abiVersion: fixture.abiVersion, + abiManifestHash: fixture.abiManifestHash, + }); + const manifest = manifestForFixture(fixture); + const execution = await evaluateWithPreset({ + id: fixture.id, + title: fixture.title, + program: built.programArtifact, + manifest, + gasLimit: fixture.gasLimit, + hostPreset: 'certification', + }); + + fixtures.push({ + id: fixture.id, + title: fixture.title, + kind: fixture.kind, + executionProfile: fixture.profile, + failureStage: execution.snapshot.stage, + errorCode: execution.snapshot.errorCode, + errorTag: execution.snapshot.errorTag, + certified: true, + docsLinks: docsLinksForFixture(fixture.id), + diagnostics: [], + runtimeArtifact: built.programArtifact, + reportSource: `ecosystem-certifier:${fixture.id}`, + }); + } catch (error) { + if (!(error instanceof DeterministicBuilderError)) { + throw error; + } + + fixtures.push({ + id: fixture.id, + title: fixture.title, + kind: fixture.kind, + executionProfile: fixture.profile, + failureStage: 'builder_reject', + errorCode: null, + errorTag: null, + certified: true, + docsLinks: docsLinksForFixture(fixture.id), + diagnostics: error.diagnostics, + runtimeArtifact: null, + reportSource: `ecosystem-certifier:${fixture.id}`, + }); + } + } + + return fixtures; +} + +async function buildOogBoundaries(runnableExamples) { + const boundaries = {}; + + for (const example of runnableExamples.galleryEntries) { + const boundary = await findOogBoundary({ + program: example.program, + manifest: example.manifest, + gasLimit: BigInt(example.gasLimit), + hostPreset: example.hostPreset, + }); + boundaries[example.id] = boundary; + } + + return boundaries; +} + +async function findOogBoundary({ program, manifest, gasLimit, hostPreset }) { + const successful = await evaluateWithPreset({ + id: 'boundary', + title: 'boundary', + program, + manifest, + gasLimit, + hostPreset, + }); + let upperGas = BigInt(successful.snapshot.gasUsed); + let upperResult = await runRawEvaluate({ + program, + manifest, + gasLimit: upperGas, + hostPreset, + }); + + while (!upperResult.ok) { + upperGas *= 2n; + upperResult = await runRawEvaluate({ + program, + manifest, + gasLimit: upperGas, + hostPreset, + }); + } + + let lowerGas = 0n; + let lowerResult = await runRawEvaluate({ + program, + manifest, + gasLimit: lowerGas, + hostPreset, + }); + + while (lowerGas + 1n < upperGas) { + const mid = (lowerGas + upperGas) >> 1n; + const current = await runRawEvaluate({ + program, + manifest, + gasLimit: mid, + hostPreset, + }); + if (current.ok) { + upperGas = mid; + upperResult = current; + } else { + lowerGas = mid; + lowerResult = current; + } + } + + return { + firstSuccessGas: upperGas.toString(), + lastFailureGas: lowerGas.toString(), + successGasUsed: upperResult.gasUsed.toString(), + successGasRemaining: upperResult.gasRemaining.toString(), + failureGasUsed: lowerResult.gasUsed.toString(), + failureGasRemaining: lowerResult.gasRemaining.toString(), + failureCode: lowerResult.ok ? null : lowerResult.error.code, + failureTag: + !lowerResult.ok && 'tag' in lowerResult.error + ? lowerResult.error.tag + : null, + }; +} + +async function evaluateWithPreset({ + id, + title, + program, + manifest, + gasLimit, + hostPreset, +}) { + const result = await runRawEvaluate({ + program, + manifest, + gasLimit, + hostPreset, + }); + + const snapshot = await snapshotFromResult(result); + return { id, title, snapshot }; +} + +async function runRawEvaluate({ program, manifest, gasLimit, hostPreset }) { + const host = createHostPreset(hostPreset); + return evaluate({ + program, + input: + hostPreset === 'certification' ? CERTIFICATION_INPUT : DETERMINISM_INPUT, + gasLimit, + manifest, + handlers: host.handlers, + tape: { capacity: 128 }, + metadata, + wasmBinary, + releaseMode: true, + expectedExecutionProfile: program.executionProfile, + }); +} + +async function snapshotFromResult(result) { + const tape = result.tape ?? []; + const tapeHash = + tape.length === 0 ? null : sha256Hex(serializeHostTape(tape)); + + if (result.ok) { + return { + stage: 'success', + resultHash: sha256Hex(encodeDv2(result.value)), + errorCode: null, + errorTag: null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash, + tapeLength: tape.length, + }; + } + + return { + stage: normalizeFailureStage(result.error.kind), + resultHash: null, + errorCode: result.error.code, + errorTag: 'tag' in result.error ? result.error.tag : null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash, + tapeLength: tape.length, + }; +} + +function normalizeFailureStage(kind) { + if (kind === 'module-pack') { + return 'artifact_validation'; + } + if (kind === 'execution-surface-mismatch') { + return 'pin_enforcement'; + } + return 'runtime_error'; +} + +function createHostPreset(hostPreset) { + return hostPreset === 'certification' + ? createCertificationHost() + : createDeterminismHost(); +} + +function createScriptProgram({ + code, + profile, + abiId, + abiVersion, + abiManifestHash, +}) { + return { + version: 2, + abiId, + abiVersion, + abiManifestHash, + executionProfile: profile, + sourceKind: 'script', + source: { code }, + ...(engineBuildHash ? { engineBuildHash } : {}), + ...(gasVersion !== null ? { gasVersion } : {}), + }; +} + +async function buildProgramArtifact({ + entryPath, + profile, + abiId, + abiVersion, + abiManifestHash, +}) { + const built = await buildDeterministicModulePack({ + absWorkingDir: repoRoot, + entryPath, + profile, + emitProgramArtifact: true, + abiId, + abiVersion, + abiManifestHash, + ...(engineBuildHash ? { engineBuildHash } : {}), + ...(gasVersion !== null ? { gasVersion } : {}), + }); + + if (!built.programArtifact) { + throw new Error( + `builder did not return ProgramArtifact.v2 for ${entryPath}`, + ); + } + + return built; +} + +function docsLinksForExample(slug) { + const base = [ + { label: 'Learn path', href: '/docs/learn/README.md' }, + { label: 'Examples corpus', href: '/examples/README.md' }, + ]; + + switch (slug) { + case 'module-pack': + return [ + ...base, + { + label: 'Module packs', + href: '/docs/learn/03-module-packs-and-imports.md', + }, + ]; + case 'promises-async': + case 'promises-library-host': + return [ + ...base, + { + label: 'Promises and microtasks', + href: '/docs/learn/04-promises-async-and-microtasks.md', + }, + ]; + case 'binary-host-v2': + return [ + ...base, + { + label: 'Binary mode and Host.v2', + href: '/docs/learn/05-binary-and-host-v2.md', + }, + ]; + case 'max-gas-policy': + return [ + ...base, + { + label: 'Gas and OOG', + href: '/docs/learn/06-gas-oog-and-max-gas-policies.md', + }, + ]; + default: + return base; + } +} + +function docsLinksForFixture(fixtureId) { + const base = [ + { + label: 'Workload certification', + href: '/docs/workload-certification.md', + }, + { + label: 'Compatibility report', + href: '/docs/ecosystem-compatibility-report.md', + }, + ]; + + if (fixtureId.startsWith('red-')) { + return [ + ...base, + { + label: 'Unsupported features and why', + href: '/docs/unsupported-features-and-why.md', + }, + ]; + } + + if (fixtureId === 'flagship-knowledge-pack') { + return [ + ...base, + { + label: 'Architecture overview', + href: '/docs/architecture-overview.md', + }, + ]; + } + + return base; +} + +function exampleDescription(slug) { + return { + 'basic-script': 'Smallest possible deterministic script-mode example.', + 'module-pack': + 'Static ESM module-pack example with a deterministic graph hash.', + 'library-reuse': + 'Real library reuse through a deterministic module-pack instead of runtime imports.', + 'promises-async': + 'Promise job draining under an explicitly compatible profile.', + 'promises-library-host': + 'Imported module code plus Promise jobs plus host interaction.', + 'binary-host-v2': + 'Typed-array and bytes boundary example using Host.v2 and DV2.', + 'console-shim': 'Deterministic console shimming routed through host tape.', + 'stable-sort': + 'Compatibility profile example showing deterministic stable sort.', + 'kitchen-sink': + 'Composite example mixing modules, Promise jobs, host calls, and stable sort.', + 'max-gas-policy': + 'Shows how exact OOG boundaries are part of the release contract.', + }[slug]; +} + +function fixtureDescription(fixtureId) { + return { + 'green-semver': + 'Semver constraint evaluation from the certified green ecosystem corpus.', + 'green-base64': + 'Binary roundtrip coverage from the certified green ecosystem corpus.', + 'green-markdown-it': + 'A larger parser-oriented compatibility fixture running under deterministic constraints.', + 'green-noble-sha': + 'A binary-heavy crypto-style fixture showing deterministic digest behavior.', + }[fixtureId]; +} + +function gasLimitForExample(slug) { + return { + 'basic-script': 1_000_000n, + 'module-pack': 50_000n, + 'library-reuse': 5_000_000n, + 'promises-async': 50_000n, + 'promises-library-host': 100_000n, + 'binary-host-v2': 50_000n, + 'console-shim': 50_000n, + 'stable-sort': 100_000n, + 'kitchen-sink': 200_000n, + 'max-gas-policy': 1_000_000n, + }[slug]; +} + +async function readPrimarySource(relativePath) { + return readFile(path.join(repoRoot, relativePath), 'utf8'); +} + +function sha256Hex(input) { + const bytes = + typeof input === 'string' ? new TextEncoder().encode(input) : input; + return createHash('sha256').update(bytes).digest('hex'); +} + +function parseArgs(argv) { + return { + check: argv.includes('--check'), + }; +} + +async function ensurePlaygroundBuildArtifacts() { + const requiredFiles = [ + 'libs/dv/dist/index.js', + 'libs/abi-manifest/dist/index.js', + 'libs/quickjs-runtime/dist/index.js', + 'libs/quickjs-wasm/dist/index.js', + 'libs/test-harness/dist/index.js', + 'libs/deterministic-builder/dist/index.js', + ].map((relativePath) => path.join(repoRoot, relativePath)); + + if (requiredFiles.every((targetPath) => existsSync(targetPath))) { + return; + } + + const emsdkEnvPath = path.join(repoRoot, 'tools/emsdk/emsdk_env.sh'); + if (!existsSync(emsdkEnvPath)) { + throw new Error( + [ + 'Playground generation needs built workspace libraries and the pinned Emscripten toolchain.', + 'Missing tools/emsdk/emsdk_env.sh.', + 'Run:', + ' bash tools/scripts/setup-emsdk.sh', + ' source tools/emsdk/emsdk_env.sh', + ' pnpm nx build bluequickjs-playground', + 'or use:', + ' bash apps/bluequickjs-playground/scripts/dev.sh', + ].join('\n'), + ); + } + + const buildCommand = + 'source tools/emsdk/emsdk_env.sh && pnpm nx build bluequickjs-playground'; + process.stderr.write( + [ + 'bluequickjs-playground: built workspace outputs were not found.', + 'Bootstrapping them now with:', + ` ${buildCommand}`, + '', + ].join('\n'), + ); + + const result = spawnSync('bash', ['-lc', buildCommand], { + cwd: repoRoot, + stdio: 'inherit', + env: process.env, + }); + + if (result.status !== 0) { + throw new Error( + [ + 'Automatic playground bootstrap build failed.', + 'If tools/scripts/setup-emsdk.sh was interrupted, rerun it because the install is idempotent.', + 'Then run:', + ' source tools/emsdk/emsdk_env.sh', + ' pnpm nx build bluequickjs-playground', + ' node apps/bluequickjs-playground/scripts/generate-playground-data.mjs', + ].join('\n'), + ); + } +} diff --git a/apps/bluequickjs-playground/src/app/format.spec.ts b/apps/bluequickjs-playground/src/app/format.spec.ts new file mode 100644 index 0000000..830701c --- /dev/null +++ b/apps/bluequickjs-playground/src/app/format.spec.ts @@ -0,0 +1,31 @@ +import { + formatGas, + formatStage, + shortenHash, + slugToLabel, + toPrettyJson, +} from './format.js'; + +describe('playground format helpers', () => { + it('formats gas values with grouping', () => { + expect(formatGas('1000000')).toBe('1,000,000'); + expect(formatGas(74n)).toBe('74'); + }); + + it('shortens hashes for UI display', () => { + expect(shortenHash('a'.repeat(64), 6)).toBe('aaaaaa…aaaaaa'); + expect(shortenHash(null)).toBe('—'); + }); + + it('formats failure stages for labels', () => { + expect(formatStage('artifact_validation')).toBe('artifact validation'); + }); + + it('converts slugs into labels', () => { + expect(slugToLabel('ecosystem-green')).toBe('Ecosystem Green'); + }); + + it('pretty prints json content', () => { + expect(toPrettyJson({ ok: true })).toContain('"ok": true'); + }); +}); diff --git a/apps/bluequickjs-playground/src/app/format.ts b/apps/bluequickjs-playground/src/app/format.ts new file mode 100644 index 0000000..cd93f5e --- /dev/null +++ b/apps/bluequickjs-playground/src/app/format.ts @@ -0,0 +1,29 @@ +export function formatGas(value: string | bigint): string { + const raw = typeof value === 'bigint' ? value.toString() : value; + return Number(raw).toLocaleString('en-US'); +} + +export function shortenHash(value: string | null, size = 8): string { + if (!value) { + return '—'; + } + if (value.length <= size * 2) { + return value; + } + return `${value.slice(0, size)}…${value.slice(-size)}`; +} + +export function toPrettyJson(value: unknown): string { + return `${JSON.stringify(value, null, 2)}\n`; +} + +export function formatStage(stage: string): string { + return stage.replace(/[-_]/g, ' '); +} + +export function slugToLabel(value: string): string { + return value + .split(/[-_]/g) + .map((part) => part.charAt(0).toUpperCase() + part.slice(1)) + .join(' '); +} diff --git a/apps/bluequickjs-playground/src/app/monaco.ts b/apps/bluequickjs-playground/src/app/monaco.ts new file mode 100644 index 0000000..1aeb2dc --- /dev/null +++ b/apps/bluequickjs-playground/src/app/monaco.ts @@ -0,0 +1,14 @@ +import editorWorker from 'monaco-editor/esm/vs/editor/editor.worker?worker'; +import jsonWorker from 'monaco-editor/esm/vs/language/json/json.worker?worker'; +import * as monaco from 'monaco-editor/esm/vs/editor/editor.api'; + +self.MonacoEnvironment = { + getWorker(_: unknown, label: string) { + if (label === 'json') { + return new jsonWorker(); + } + return new editorWorker(); + }, +}; + +export { monaco }; diff --git a/apps/bluequickjs-playground/src/app/playground-app.ts b/apps/bluequickjs-playground/src/app/playground-app.ts new file mode 100644 index 0000000..136134c --- /dev/null +++ b/apps/bluequickjs-playground/src/app/playground-app.ts @@ -0,0 +1,962 @@ +import { isKnownExecutionProfile } from '@blue-quickjs/execution-profiles'; +import { monaco } from './monaco.js'; +import { formatGas, shortenHash, slugToLabel, toPrettyJson } from './format.js'; +import { + compareAgainstEvidence, + createScriptArtifact, + defaultManifestForArtifact, + findOogBoundary, + loadPlaygroundData, + parseArtifactJson, + runArtifact, +} from './runtime.js'; +import { + getInitialExample, + getProfileSummary, + groupExamples, +} from './state.js'; +import type { + GalleryEntry, + HostPresetId, + LoadedPlaygroundData, + OogBoundaryRecord, + PlaygroundRunResult, + RedFixtureRecord, +} from './types.js'; + +type Selection = { type: 'gallery'; id: string } | { type: 'red'; id: string }; + +export class PlaygroundApp { + private data: LoadedPlaygroundData | null = null; + + private selection: Selection | null = null; + + private mode: 'gallery' | 'script' | 'artifact' = 'gallery'; + + private runResult: PlaygroundRunResult | null = null; + + private activeTab: 'result' | 'evidence' | 'host' | 'metadata' | 'help' = + 'result'; + + private hostPreset: HostPresetId = 'determinism'; + + private editor: monaco.editor.IStandaloneCodeEditor | null = null; + + private boundaryOverride: OogBoundaryRecord | null = null; + + private scriptProfile = 'baseline-v1'; + + private artifactJson = ''; + + private readonly root: HTMLElement; + + constructor(root: HTMLElement) { + this.root = root; + } + + async init(): Promise { + this.root.innerHTML = + '

Loading BlueQuickjs Playground…
'; + this.data = await loadPlaygroundData(); + const initial = getInitialExample(this.data); + this.selection = { type: 'gallery', id: initial.id }; + this.hostPreset = initial.hostPreset; + this.renderShell(); + this.renderLists(); + this.syncSelectionToSurface(); + this.bindEvents(); + this.createEditor(); + this.updateEditorForMode(); + this.updatePanels(); + } + + private renderShell(): void { + this.root.innerHTML = ` +
+
+
+ +
+

web.blue visual language

+

BlueQuickjs Playground

+
+
+

+ Explore deterministic JavaScript execution with the same wasm32 engine + and evidence model used by the release process. Consensus-safe scope is + explicitly wasm-node vs wasm-browser; native remains + diagnostic-only. +

+
+ Consensus-safe: wasm32 only + Exact gas + exact OOG + Generated evidence-backed examples +
+
+ +
+ + +
+
+
+
+

+

+
+
+ + +
+
+
+
+ + +
+
+
+ +
+
+
+

Run output

+

Result bytes, gas, host tape, evidence match status, and release pins.

+
+
+ Idle + No run yet +
+
+
+
+ + + + + +
+
+
+
+
+
+ `; + } + + private bindEvents(): void { + this.root + .querySelectorAll('[data-mode]') + .forEach((button) => { + button.addEventListener('click', () => { + this.mode = button.dataset.mode as typeof this.mode; + this.updateEditorForMode(); + this.updateControls(); + this.updatePanels(); + }); + }); + + this.root + .querySelector('[data-profile]') + ?.addEventListener('change', (event) => { + const next = (event.currentTarget as HTMLSelectElement).value; + if (isKnownExecutionProfile(next)) { + this.scriptProfile = next; + this.updateControls(); + } + }); + + this.root + .querySelector('[data-gas-limit]') + ?.addEventListener('change', () => this.updatePanels()); + + this.root + .querySelector('[data-host-preset]') + ?.addEventListener('change', (event) => { + this.hostPreset = (event.currentTarget as HTMLSelectElement) + .value as HostPresetId; + this.updatePanels(); + }); + + this.root + .querySelectorAll('[data-gas-preset]') + .forEach((button) => { + button.addEventListener('click', () => { + const input = + this.root.querySelector('[data-gas-limit]'); + if (input && button.dataset.gasPreset) { + input.value = button.dataset.gasPreset; + } + }); + }); + + this.root + .querySelector('[data-run]') + ?.addEventListener('click', () => void this.runCurrentSelection()); + this.root + .querySelector('[data-find-oog]') + ?.addEventListener('click', () => void this.findBoundary()); + this.root + .querySelector('[data-export-artifact]') + ?.addEventListener('click', () => this.exportArtifact()); + this.root + .querySelector('[data-export-evidence]') + ?.addEventListener('click', () => this.exportEvidence()); + + this.root + .querySelectorAll('[data-tab]') + .forEach((button) => { + button.addEventListener('click', () => { + this.activeTab = button.dataset.tab as typeof this.activeTab; + this.updatePanels(); + }); + }); + } + + private createEditor(): void { + const mount = this.root.querySelector('[data-editor]'); + if (!mount) { + return; + } + this.editor = monaco.editor.create(mount, { + value: '', + language: 'javascript', + automaticLayout: true, + minimap: { enabled: false }, + fontFamily: 'Roboto Mono, monospace', + fontSize: 14, + lineHeight: 20, + scrollBeyondLastLine: false, + roundedSelection: true, + readOnly: true, + theme: 'vs', + padding: { top: 16, bottom: 16 }, + }); + } + + private renderLists(): void { + if (!this.data) { + return; + } + + const grouped = groupExamples(this.data.examples.examples); + const groupsMount = this.root.querySelector( + '[data-gallery-groups]', + ); + const redMount = this.root.querySelector('[data-red-list]'); + + if (groupsMount) { + groupsMount.innerHTML = Object.entries(grouped) + .map( + ([key, entries]) => ` + + `, + ) + .join(''); + + groupsMount + .querySelectorAll('[data-gallery-id]') + .forEach((button) => { + button.addEventListener('click', () => { + const galleryId = button.dataset.galleryId; + if (!galleryId) { + return; + } + this.selection = { type: 'gallery', id: galleryId }; + this.mode = 'gallery'; + this.boundaryOverride = null; + this.runResult = null; + const current = this.currentGalleryEntry(); + if (current) { + this.hostPreset = current.hostPreset; + } + this.updateEditorForMode(); + this.updateControls(); + this.updatePanels(); + }); + }); + } + + if (redMount) { + redMount.innerHTML = this.data.red.fixtures + .map( + (fixture) => ` + + `, + ) + .join(''); + + redMount + .querySelectorAll('[data-red-id]') + .forEach((button) => { + button.addEventListener('click', () => { + const redId = button.dataset.redId; + if (!redId) { + return; + } + this.selection = { type: 'red', id: redId }; + this.mode = 'gallery'; + this.boundaryOverride = null; + this.runResult = null; + this.hostPreset = 'certification'; + this.updateEditorForMode(); + this.updateControls(); + this.updatePanels(); + }); + }); + } + } + + private currentGalleryEntry(): GalleryEntry | null { + if (!this.data || !this.selection || this.selection.type !== 'gallery') { + return null; + } + return ( + this.data.examples.examples.find( + (entry) => entry.id === this.selection?.id, + ) ?? null + ); + } + + private currentRedFixture(): RedFixtureRecord | null { + if (!this.data || !this.selection || this.selection.type !== 'red') { + return null; + } + return ( + this.data.red.fixtures.find((entry) => entry.id === this.selection?.id) ?? + null + ); + } + + private updateEditorForMode(): void { + if (!this.editor || !this.data) { + return; + } + + const selection = this.currentGalleryEntry(); + const redFixture = this.currentRedFixture(); + const modeLabel = this.root.querySelector( + '[data-editor-mode-label]', + ); + const sourcePaths = this.root.querySelector( + '[data-editor-source-paths]', + ); + + if (this.mode === 'script') { + const seed = selection?.sourceText ?? 'export default (() => 1 + 2)();\n'; + this.editor.updateOptions({ readOnly: false }); + this.editor.setValue(seed); + const model = this.editor.getModel(); + if (model) { + monaco.editor.setModelLanguage(model, 'javascript'); + } + if (modeLabel) modeLabel.textContent = 'Script mode'; + if (sourcePaths) sourcePaths.textContent = 'Editable JavaScript snippet'; + return; + } + + if (this.mode === 'artifact') { + if (!this.artifactJson) { + this.artifactJson = toPrettyJson( + selection?.program ?? + redFixture?.runtimeArtifact ?? + createScriptArtifact( + 'export default (() => 1 + 2)();\n', + this.scriptProfile as GalleryEntry['executionProfile'], + this.data.examples.metadata, + ), + ); + } + this.editor.updateOptions({ readOnly: false }); + this.editor.setValue(this.artifactJson); + const model = this.editor.getModel(); + if (model) { + monaco.editor.setModelLanguage(model, 'json'); + } + if (modeLabel) modeLabel.textContent = 'Artifact JSON import mode'; + if (sourcePaths) + sourcePaths.textContent = 'Paste or edit ProgramArtifact.v2 JSON'; + return; + } + + this.editor.updateOptions({ readOnly: true }); + if (selection) { + this.editor.setValue(selection.sourceText); + const model = this.editor.getModel(); + if (model) { + monaco.editor.setModelLanguage( + model, + selection.sourcePaths[0]?.endsWith('.ts') + ? 'typescript' + : 'javascript', + ); + } + if (modeLabel) modeLabel.textContent = 'Certified gallery source'; + if (sourcePaths) + sourcePaths.textContent = selection.sourcePaths.join(' · '); + } else if (redFixture) { + const payload = redFixture.runtimeArtifact ?? { + diagnostics: redFixture.diagnostics, + failureStage: redFixture.failureStage, + }; + this.editor.setValue(toPrettyJson(payload)); + const model = this.editor.getModel(); + if (model) { + monaco.editor.setModelLanguage(model, 'json'); + } + if (modeLabel) modeLabel.textContent = 'Deterministic failure fixture'; + if (sourcePaths) sourcePaths.textContent = redFixture.reportSource; + } + } + + private updateControls(): void { + const selection = this.currentGalleryEntry(); + const redFixture = this.currentRedFixture(); + const profileSelect = + this.root.querySelector('[data-profile]'); + const gasInput = + this.root.querySelector('[data-gas-limit]'); + const hostPreset = + this.root.querySelector('[data-host-preset]'); + const profileHelp = this.root.querySelector( + '[data-profile-help]', + ); + const runButton = this.root.querySelector('[data-run]'); + const oogButton = + this.root.querySelector('[data-find-oog]'); + + if (selection) { + if (gasInput) gasInput.value = selection.gasLimit; + if (hostPreset) hostPreset.value = this.hostPreset; + } + if (redFixture && gasInput) { + gasInput.value = '1000000'; + } + + if (profileSelect) { + profileSelect.value = + this.mode === 'script' + ? this.scriptProfile + : (selection?.executionProfile ?? 'baseline-v1'); + profileSelect.disabled = this.mode !== 'script'; + } + + if (profileHelp) { + profileHelp.textContent = getProfileSummary( + (this.mode === 'script' + ? this.scriptProfile + : (selection?.executionProfile ?? 'baseline-v1')) as never, + ); + } + + if (runButton) { + runButton.disabled = + this.mode === 'gallery' && + redFixture !== null && + redFixture.runtimeArtifact === null; + } + + if (oogButton) { + oogButton.disabled = + this.mode === 'gallery' + ? selection === null || !selection.supportsOogSearch + : false; + } + + this.root + .querySelectorAll('[data-mode]') + .forEach((button) => { + button.dataset.active = String(button.dataset.mode === this.mode); + }); + this.root + .querySelectorAll('[data-tab]') + .forEach((button) => { + button.dataset.active = String(button.dataset.tab === this.activeTab); + }); + } + + private syncSelectionToSurface(): void { + const selection = this.currentGalleryEntry(); + const redFixture = this.currentRedFixture(); + const title = this.root.querySelector( + '[data-selection-title]', + ); + const description = this.root.querySelector( + '[data-selection-description]', + ); + const badge = this.root.querySelector( + '[data-selection-badge]', + ); + const cert = this.root.querySelector('[data-selection-cert]'); + const meta = this.root.querySelector('[data-selection-meta]'); + + if (selection) { + if (title) title.textContent = selection.title; + if (description) description.textContent = selection.description; + if (badge) badge.textContent = selection.badge; + if (cert) + cert.textContent = selection.certified + ? 'Consensus-certified evidence' + : 'Uncertified'; + if (meta) { + meta.innerHTML = ` + ${selection.executionProfile} + ${selection.sourceKind} + ${selection.abiId} + ${selection.hostSummary.label} + `; + } + return; + } + + if (redFixture) { + if (title) title.textContent = redFixture.title; + if (description) { + description.textContent = + redFixture.runtimeArtifact === null + ? 'Builder rejection fixture that teaches why unsupported code never reaches runtime.' + : 'Runtime-level deterministic failure fixture with a stable failure stage.'; + } + if (badge) badge.textContent = 'Red deterministic failure'; + if (cert) cert.textContent = 'Certified deterministic rejection'; + if (meta) { + meta.innerHTML = ` + ${redFixture.executionProfile} + ${redFixture.failureStage} + ${redFixture.reportSource} + `; + } + } + } + + private updatePanels(): void { + this.syncSelectionToSurface(); + this.updateControls(); + this.renderMetrics(); + this.renderTabPanel(); + } + + private renderMetrics(): void { + const mount = this.root.querySelector('[data-metrics-grid]'); + const runStatus = this.root.querySelector('[data-run-status]'); + const evidenceStatus = this.root.querySelector( + '[data-evidence-status]', + ); + if (!mount) { + return; + } + + if (!this.runResult) { + mount.innerHTML = ` +
+ Awaiting run + Choose an example, script, or artifact JSON and press Run. +
+ `; + if (runStatus) runStatus.textContent = 'Idle'; + if (evidenceStatus) evidenceStatus.textContent = 'No run yet'; + return; + } + + const currentId = + this.selection?.type === 'gallery' || this.selection?.type === 'red' + ? this.selection.id + : null; + const evidence = + currentId && this.data + ? this.data.evidence.evidence[currentId] + : undefined; + const match = compareAgainstEvidence(this.runResult, evidence); + if (runStatus) + runStatus.textContent = this.runResult.ok ? 'Success' : 'Failure'; + if (evidenceStatus) { + evidenceStatus.textContent = !match.available + ? 'No certified evidence' + : match.matches + ? 'Matches certified snapshot' + : 'Differs from certified snapshot'; + } + + mount.innerHTML = [ + metricCard('Stage', this.runResult.snapshot.stage), + metricCard('Gas used', formatGas(this.runResult.snapshot.gasUsed)), + metricCard( + 'Gas remaining', + formatGas(this.runResult.snapshot.gasRemaining), + ), + metricCard('Tape length', String(this.runResult.snapshot.tapeLength)), + metricCard( + 'Result hash', + shortenHash(this.runResult.snapshot.resultHash), + ), + metricCard('Tape hash', shortenHash(this.runResult.snapshot.tapeHash)), + metricCard( + 'engineBuildHash', + shortenHash(this.runResult.runtimeMetadata.engineBuildHash), + ), + metricCard( + 'gasVersion', + this.runResult.runtimeMetadata.gasVersion?.toString() ?? '—', + ), + ].join(''); + } + + private renderTabPanel(): void { + const mount = this.root.querySelector('[data-tab-panel]'); + if (!mount || !this.data) { + return; + } + + const selection = this.currentGalleryEntry(); + const redFixture = this.currentRedFixture(); + const evidenceKey = + this.selection?.type === 'gallery' || this.selection?.type === 'red' + ? this.selection.id + : ''; + const evidence = this.data.evidence.evidence[evidenceKey]; + const boundary = + this.boundaryOverride ?? + (evidenceKey ? this.data.oog.boundaries[evidenceKey] : undefined); + + if (this.activeTab === 'help') { + const links = selection?.docsLinks ?? redFixture?.docsLinks ?? []; + mount.innerHTML = ` +
+ `; + return; + } + + if (this.activeTab === 'metadata') { + const runtimeMetadata = this.runResult?.runtimeMetadata; + mount.innerHTML = ` +
+
${toPrettyJson({
+            selection: selection ??
+              redFixture ?? {
+                mode: this.mode,
+                scriptProfile: this.scriptProfile,
+              },
+            runtimeMetadata,
+            certifiedBoundary: boundary ?? null,
+          })}
+
+ `; + return; + } + + if (this.activeTab === 'host') { + mount.innerHTML = ` +
+

${ + selection?.hostSummary.description ?? + 'Host activity is captured through wrapped mock handlers plus tape hashes.' + }

+
${toPrettyJson(this.runResult?.hostEvents ?? [])}
+
+ `; + return; + } + + if (this.activeTab === 'evidence') { + if (redFixture) { + mount.innerHTML = ` +
+

Red fixtures teach deterministic failures instead of hiding them.

+
${toPrettyJson({
+              failureStage: redFixture.failureStage,
+              errorCode: redFixture.errorCode,
+              errorTag: redFixture.errorTag,
+              diagnostics: redFixture.diagnostics,
+            })}
+
+ `; + return; + } + + const comparison = this.runResult + ? compareAgainstEvidence(this.runResult, evidence) + : null; + mount.innerHTML = ` +
+
${toPrettyJson({
+            certifiedEvidence: evidence ?? null,
+            currentRun: this.runResult?.snapshot ?? null,
+            comparison,
+            certifiedBoundary: boundary ?? null,
+          })}
+
+ `; + return; + } + + mount.innerHTML = ` +
+
${toPrettyJson({
+          ok: this.runResult?.ok ?? null,
+          snapshot: this.runResult?.snapshot ?? null,
+          value: this.runResult?.value ?? null,
+          errorMessage: this.runResult?.errorMessage ?? null,
+        })}
+
+ `; + } + + private async runCurrentSelection(): Promise { + if (!this.data) { + return; + } + + try { + let artifact; + let manifest; + const gasLimit = BigInt( + this.root.querySelector('[data-gas-limit]')?.value ?? + '1000000', + ); + const selection = this.currentGalleryEntry(); + const redFixture = this.currentRedFixture(); + + if (this.mode === 'script') { + artifact = createScriptArtifact( + this.editor?.getValue() ?? '', + this.scriptProfile as GalleryEntry['executionProfile'], + this.data.examples.metadata, + ); + manifest = defaultManifestForArtifact(artifact); + } else if (this.mode === 'artifact') { + this.artifactJson = this.editor?.getValue() ?? '{}'; + artifact = parseArtifactJson(this.artifactJson); + manifest = defaultManifestForArtifact(artifact); + } else if (selection) { + artifact = selection.program; + manifest = selection.manifest; + } else if (redFixture?.runtimeArtifact) { + artifact = redFixture.runtimeArtifact; + manifest = defaultManifestForArtifact(artifact); + } else { + return; + } + + this.runResult = await runArtifact({ + artifact, + manifest, + gasLimit, + hostPreset: this.hostPreset, + }); + this.activeTab = this.runResult.ok ? 'result' : 'evidence'; + this.updatePanels(); + } catch (error) { + this.runResult = { + ok: false, + snapshot: { + stage: 'artifact_validation', + resultHash: null, + errorCode: 'PROGRAM_ARTIFACT_INVALID', + errorTag: 'vm/module_pack', + gasUsed: '0', + gasRemaining: '0', + tapeHash: null, + tapeLength: 0, + }, + value: null, + errorMessage: error instanceof Error ? error.message : String(error), + hostEvents: [], + tape: [], + runtimeMetadata: { + engineBuildHash: this.data.examples.metadata.engineBuildHash, + gasVersion: this.data.examples.metadata.gasVersion, + executionProfile: this.scriptProfile, + sourceKind: 'script', + abiId: this.hostPreset === 'certification' ? 'Host.v2' : 'Host.v1', + moduleGraphHash: null, + }, + }; + this.activeTab = 'evidence'; + this.updatePanels(); + } + } + + private async findBoundary(): Promise { + if (!this.data) { + return; + } + + let artifact; + let manifest; + const initialGasLimit = BigInt( + this.root.querySelector('[data-gas-limit]')?.value ?? + '1000000', + ); + const selection = this.currentGalleryEntry(); + const redFixture = this.currentRedFixture(); + + if (this.mode === 'script') { + artifact = createScriptArtifact( + this.editor?.getValue() ?? '', + this.scriptProfile as GalleryEntry['executionProfile'], + this.data.examples.metadata, + ); + manifest = defaultManifestForArtifact(artifact); + } else if (this.mode === 'artifact') { + artifact = parseArtifactJson(this.editor?.getValue() ?? '{}'); + manifest = defaultManifestForArtifact(artifact); + } else if (selection) { + artifact = selection.program; + manifest = selection.manifest; + } else if (redFixture?.runtimeArtifact) { + artifact = redFixture.runtimeArtifact; + manifest = defaultManifestForArtifact(artifact); + } else { + return; + } + + this.boundaryOverride = await findOogBoundary({ + artifact, + manifest, + hostPreset: this.hostPreset, + initialGasLimit, + }); + this.activeTab = 'evidence'; + this.updatePanels(); + } + + private exportArtifact(): void { + if (!this.data) { + return; + } + const selection = this.currentGalleryEntry(); + const redFixture = this.currentRedFixture(); + let artifactContent = '{}\n'; + if (this.mode === 'artifact') { + artifactContent = this.editor?.getValue() ?? '{}\n'; + } else if (this.mode === 'script') { + artifactContent = toPrettyJson( + createScriptArtifact( + this.editor?.getValue() ?? '', + this.scriptProfile as GalleryEntry['executionProfile'], + this.data.examples.metadata, + ), + ); + } else if (selection) { + artifactContent = toPrettyJson(selection.program); + } else if (redFixture?.runtimeArtifact) { + artifactContent = toPrettyJson(redFixture.runtimeArtifact); + } + downloadFile('bluequickjs-artifact.json', artifactContent); + } + + private exportEvidence(): void { + const payload = toPrettyJson({ + selection: this.selection, + runResult: this.runResult, + boundary: this.boundaryOverride, + }); + downloadFile('bluequickjs-run-evidence.json', payload); + } +} + +function metricCard(label: string, value: string): string { + return ` +
+ ${label} + ${value} +
+ `; +} + +function downloadFile(filename: string, contents: string): void { + const blob = new Blob([contents], { type: 'application/json' }); + const url = URL.createObjectURL(blob); + const anchor = document.createElement('a'); + anchor.href = url; + anchor.download = filename; + anchor.click(); + URL.revokeObjectURL(url); +} diff --git a/apps/bluequickjs-playground/src/app/runtime.spec.ts b/apps/bluequickjs-playground/src/app/runtime.spec.ts new file mode 100644 index 0000000..c081fb5 --- /dev/null +++ b/apps/bluequickjs-playground/src/app/runtime.spec.ts @@ -0,0 +1,93 @@ +import { HOST_V1_HASH, HOST_V2_HASH } from '@blue-quickjs/abi-manifest'; +import { + compareAgainstEvidence, + createScriptArtifact, + defaultManifestForArtifact, + parseArtifactJson, +} from './runtime.js'; + +describe('playground runtime helpers', () => { + const metadata = { + engineBuildHash: 'a'.repeat(64), + gasVersion: 8, + wasmVariant: 'wasm32', + wasmBuildType: 'release', + }; + + it('creates baseline script artifacts against Host.v1', () => { + const artifact = createScriptArtifact( + '(() => 1)();', + 'baseline-v1', + metadata, + ); + expect(artifact.abiId).toBe('Host.v1'); + expect(artifact.abiManifestHash).toBe(HOST_V1_HASH); + expect(artifact.engineBuildHash).toBe(metadata.engineBuildHash); + }); + + it('creates binary script artifacts against Host.v2', () => { + const artifact = createScriptArtifact( + '(() => Host.v2.document.get("bytes/payload"))();', + 'compat-binary-v1', + metadata, + ); + expect(artifact.abiId).toBe('Host.v2'); + expect(artifact.abiManifestHash).toBe(HOST_V2_HASH); + expect(defaultManifestForArtifact(artifact).abi_id).toBe('Host.v2'); + }); + + it('parses artifact json through runtime validation', () => { + const artifact = createScriptArtifact( + '(() => 1)();', + 'baseline-v1', + metadata, + ); + expect(parseArtifactJson(JSON.stringify(artifact))).toEqual(artifact); + }); + + it('compares run snapshots against certified evidence', () => { + const result = compareAgainstEvidence( + { + ok: true, + snapshot: { + stage: 'success', + resultHash: 'a', + errorCode: null, + errorTag: null, + gasUsed: '10', + gasRemaining: '90', + tapeHash: null, + tapeLength: 0, + }, + value: 1, + errorMessage: null, + hostEvents: [], + tape: [], + runtimeMetadata: { + engineBuildHash: metadata.engineBuildHash, + gasVersion: 8, + executionProfile: 'baseline-v1', + sourceKind: 'script', + abiId: 'Host.v1', + moduleGraphHash: null, + }, + }, + { + stage: 'success', + resultHash: 'a', + errorCode: null, + errorTag: null, + gasUsed: '10', + gasRemaining: '90', + tapeHash: null, + tapeLength: 0, + certified: true, + reportSource: 'fixture', + fixtureCoverage: [], + }, + ); + + expect(result.matches).toBe(true); + expect(result.differences).toEqual([]); + }); +}); diff --git a/apps/bluequickjs-playground/src/app/runtime.ts b/apps/bluequickjs-playground/src/app/runtime.ts new file mode 100644 index 0000000..ad98819 --- /dev/null +++ b/apps/bluequickjs-playground/src/app/runtime.ts @@ -0,0 +1,488 @@ +import { + HOST_V1_HASH, + HOST_V1_MANIFEST, + HOST_V2_HASH, + HOST_V2_MANIFEST, + type AbiManifest, +} from '@blue-quickjs/abi-manifest'; +import { encodeDv2 } from '@blue-quickjs/dv'; +import type { + HostCallResult, + HostDispatcherHandlers, + ProgramArtifactV2, +} from '@blue-quickjs/quickjs-runtime'; +import { + evaluate, + validateProgramArtifactV2, +} from '@blue-quickjs/quickjs-runtime'; +import { + loadQuickjsWasmBinary, + loadQuickjsWasmMetadata, +} from '@blue-quickjs/quickjs-wasm'; +import { + DETERMINISM_INPUT, + createDeterminismHost, + serializeHostTape, +} from '@blue-quickjs/test-harness'; +import type { + EvidencePayload, + HostEvent, + HostPresetId, + LoadedPlaygroundData, + OogPayload, + PlaygroundRunResult, + RunSnapshot, +} from './types.js'; + +const CERTIFICATION_INPUT = { + event: { type: 'ecosystem-certifier' }, + eventCanonical: { type: 'ecosystem-certifier' }, + steps: [], + currentContract: { id: 'ecosystem-certifier' }, + currentContractCanonical: { id: { value: 'ecosystem-certifier' } }, +}; + +const CERT_TEXT_DOCUMENTS = new Map([ + [ + 'pack/metadata.json', + JSON.stringify( + { + packId: 'kp-2026-rc', + release: '1.2.3', + requires: ['>=1.2.0 <2.0.0', '^1.2.0'], + links: ['docs/a.md', 'docs/b.md', 'docs/c.md', 'docs/d.md'], + }, + null, + 2, + ), + ], + [ + 'pack/metadata.yaml', + [ + 'packId: kp-2026-rc', + 'release: 1.2.3', + 'requires:', + ' - ">=1.2.0 <2.0.0"', + ' - "^1.2.0"', + 'links:', + ' - docs/a.md', + ' - docs/b.md', + '', + ].join('\n'), + ], + ['docs/a.md', '# Alpha\n\nSee [Beta](docs/b.md).\n'], + ['docs/b.md', '# Beta\n\nBacklink to [Alpha](docs/a.md).\n'], + ['docs/c.md', '# Gamma\n\nCross-link to [Delta](docs/d.md).\n'], + ['docs/d.md', '# Delta\n\nBack to [Alpha](docs/a.md).\n'], + ['text/semver-case', '1.2.3'], +]); + +const CERT_BINARY_DOCUMENTS = new Map([ + [ + 'bytes/payload', + Uint8Array.from( + Array.from({ length: 64 }, (_, index) => (index * 17) % 251), + ), + ], + [ + 'bytes/flagship-extra', + Uint8Array.from( + Array.from({ length: 192 }, (_, index) => (index * 29 + 11) % 251), + ), + ], +]); + +let runtimeAssetsPromise: + | Promise<{ + metadata: Awaited>; + wasmBinary: Uint8Array; + }> + | undefined; + +export async function loadPlaygroundData(): Promise { + const [examples, evidence, oog, red] = await Promise.all([ + loadJson('/generated/playground-examples.json'), + loadJson('/generated/playground-evidence.json'), + loadJson('/generated/playground-oog-boundaries.json'), + loadJson('/generated/playground-red-fixtures.json'), + ]); + + return { + examples, + evidence, + oog, + red, + } as LoadedPlaygroundData; +} + +export async function getRuntimeAssets() { + if (!runtimeAssetsPromise) { + runtimeAssetsPromise = (async () => { + const metadata = await loadQuickjsWasmMetadata(); + const wasmBinary = await loadQuickjsWasmBinary( + 'wasm32', + 'release', + metadata, + ); + return { metadata, wasmBinary }; + })(); + } + return runtimeAssetsPromise; +} + +export async function runArtifact(options: { + artifact: ProgramArtifactV2; + manifest: AbiManifest; + gasLimit: bigint; + hostPreset: HostPresetId; +}): Promise { + const { metadata, wasmBinary } = await getRuntimeAssets(); + const host = createWrappedHost(options.hostPreset); + const result = await evaluate({ + program: options.artifact, + input: + options.hostPreset === 'certification' + ? CERTIFICATION_INPUT + : DETERMINISM_INPUT, + gasLimit: options.gasLimit, + manifest: options.manifest, + handlers: host.handlers, + tape: { capacity: 128 }, + metadata, + wasmBinary, + releaseMode: true, + expectedExecutionProfile: options.artifact.executionProfile, + }); + + return { + ok: result.ok, + snapshot: await toSnapshot(result), + value: result.ok ? result.value : null, + errorMessage: result.ok ? null : result.message, + hostEvents: host.events, + tape: result.tape ?? [], + runtimeMetadata: { + engineBuildHash: + metadata.variants?.wasm32?.release?.engineBuildHash ?? + metadata.engineBuildHash ?? + null, + gasVersion: metadata.gasVersion ?? null, + executionProfile: options.artifact.executionProfile, + sourceKind: options.artifact.sourceKind, + abiId: options.artifact.abiId, + moduleGraphHash: + options.artifact.sourceKind === 'module-pack' + ? options.artifact.source.modulePack.graphHash + : null, + }, + }; +} + +export async function findOogBoundary(options: { + artifact: ProgramArtifactV2; + manifest: AbiManifest; + hostPreset: HostPresetId; + initialGasLimit: bigint; +}): Promise { + let upperGas = options.initialGasLimit; + let upper = await runArtifact({ + artifact: options.artifact, + manifest: options.manifest, + gasLimit: upperGas, + hostPreset: options.hostPreset, + }); + + while (!upper.ok) { + upperGas *= 2n; + upper = await runArtifact({ + artifact: options.artifact, + manifest: options.manifest, + gasLimit: upperGas, + hostPreset: options.hostPreset, + }); + } + + let lowerGas = 0n; + let lower = await runArtifact({ + artifact: options.artifact, + manifest: options.manifest, + gasLimit: lowerGas, + hostPreset: options.hostPreset, + }); + + while (lowerGas + 1n < upperGas) { + const mid = (lowerGas + upperGas) >> 1n; + const current = await runArtifact({ + artifact: options.artifact, + manifest: options.manifest, + gasLimit: mid, + hostPreset: options.hostPreset, + }); + if (current.ok) { + upperGas = mid; + upper = current; + } else { + lowerGas = mid; + lower = current; + } + } + + return { + firstSuccessGas: upperGas.toString(), + lastFailureGas: lowerGas.toString(), + successGasUsed: upper.snapshot.gasUsed, + successGasRemaining: upper.snapshot.gasRemaining, + failureGasUsed: lower.snapshot.gasUsed, + failureGasRemaining: lower.snapshot.gasRemaining, + failureCode: lower.snapshot.errorCode, + failureTag: lower.snapshot.errorTag, + }; +} + +export function createScriptArtifact( + code: string, + profile: ProgramArtifactV2['executionProfile'], + metadata: LoadedPlaygroundData['examples']['metadata'], +): ProgramArtifactV2 { + const binary = profile === 'compat-binary-v1'; + return { + version: 2, + abiId: binary ? 'Host.v2' : 'Host.v1', + abiVersion: binary ? 2 : 1, + abiManifestHash: binary ? HOST_V2_HASH : HOST_V1_HASH, + ...(metadata.engineBuildHash + ? { engineBuildHash: metadata.engineBuildHash } + : {}), + ...(metadata.gasVersion !== null + ? { gasVersion: metadata.gasVersion } + : {}), + executionProfile: profile, + sourceKind: 'script', + source: { code }, + }; +} + +export function defaultManifestForArtifact( + artifact: ProgramArtifactV2, +): AbiManifest { + return artifact.abiId === 'Host.v2' ? HOST_V2_MANIFEST : HOST_V1_MANIFEST; +} + +export function parseArtifactJson(text: string): ProgramArtifactV2 { + return validateProgramArtifactV2(JSON.parse(text)); +} + +export function compareAgainstEvidence( + run: PlaygroundRunResult, + evidence: EvidencePayload['evidence'][string] | undefined, +) { + if (!evidence) { + return { + available: false, + matches: false, + differences: [], + }; + } + + const differences = [ + ['stage', run.snapshot.stage, evidence.stage], + ['resultHash', run.snapshot.resultHash, evidence.resultHash], + ['errorCode', run.snapshot.errorCode, evidence.errorCode], + ['errorTag', run.snapshot.errorTag, evidence.errorTag], + ['gasUsed', run.snapshot.gasUsed, evidence.gasUsed], + ['gasRemaining', run.snapshot.gasRemaining, evidence.gasRemaining], + ['tapeHash', run.snapshot.tapeHash, evidence.tapeHash], + ['tapeLength', run.snapshot.tapeLength, evidence.tapeLength], + ].filter(([, actual, expected]) => actual !== expected); + + return { + available: true, + matches: differences.length === 0, + differences, + }; +} + +function createWrappedHost(hostPreset: HostPresetId): { + handlers: HostDispatcherHandlers; + events: HostEvent[]; +} { + const base = + hostPreset === 'certification' + ? createInlineCertificationHost() + : createDeterminismHost(); + const events: HostEvent[] = []; + + return { + handlers: { + document: { + get: (docPath: string): HostCallResult => { + const result = base.handlers.document.get(docPath); + events.push({ + fn: 'document.get', + request: docPath, + response: previewHostResult(result), + units: result.units, + }); + return result; + }, + getCanonical: (docPath: string): HostCallResult => { + const result = base.handlers.document.getCanonical(docPath); + events.push({ + fn: 'document.getCanonical', + request: docPath, + response: previewHostResult(result), + units: result.units, + }); + return result; + }, + }, + emit: (value: unknown): HostCallResult => { + const result = base.handlers.emit(value); + events.push({ + fn: 'emit', + request: previewValue(value), + response: previewHostResult(result), + units: result.units, + }); + return result; + }, + }, + events, + }; +} + +function createInlineCertificationHost(): { + handlers: HostDispatcherHandlers; + emitted: unknown[]; +} { + const emitted: unknown[] = []; + return { + emitted, + handlers: { + document: { + get: (docPath: string): HostCallResult => { + const binaryDoc = CERT_BINARY_DOCUMENTS.get(docPath); + if (binaryDoc) { + return { ok: binaryDoc, units: 6 }; + } + const textDoc = CERT_TEXT_DOCUMENTS.get(docPath); + if (textDoc) { + return { ok: textDoc, units: 2 }; + } + return { + err: { code: 'NOT_FOUND', tag: 'host/not_found' }, + units: 1, + }; + }, + getCanonical: (docPath: string): HostCallResult => { + const textDoc = CERT_TEXT_DOCUMENTS.get(docPath); + if (textDoc) { + return { ok: textDoc, units: 2 }; + } + const binaryDoc = CERT_BINARY_DOCUMENTS.get(docPath); + if (binaryDoc) { + return { ok: binaryDoc, units: 6 }; + } + return { + err: { code: 'NOT_FOUND', tag: 'host/not_found' }, + units: 1, + }; + }, + }, + emit: (value: unknown): HostCallResult => { + emitted.push(value); + return { ok: null, units: 1 }; + }, + }, + }; +} + +function previewHostResult(result: HostCallResult): unknown { + if ('ok' in result) { + return { ok: previewValue(result.ok), units: result.units }; + } + return { err: result.err, units: result.units }; +} + +function previewValue(value: unknown): unknown { + if (value instanceof Uint8Array) { + return { + type: 'Uint8Array', + length: value.byteLength, + hexPreview: Array.from(value.slice(0, 16)) + .map((byte) => byte.toString(16).padStart(2, '0')) + .join(''), + }; + } + return value; +} + +async function toSnapshot( + result: Awaited>, +): Promise { + const tape = result.tape ?? []; + const tapeHash = + tape.length > 0 ? await sha256Hex(serializeHostTape(tape)) : null; + if (result.ok) { + return { + stage: 'success', + resultHash: await sha256Hex(encodeDv2(result.value)), + errorCode: null, + errorTag: null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash, + tapeLength: tape.length, + }; + } + return { + stage: normalizeFailureStage(result.error.kind), + resultHash: null, + errorCode: result.error.code, + errorTag: 'tag' in result.error ? result.error.tag : null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash, + tapeLength: tape.length, + }; +} + +function normalizeFailureStage(kind: string): RunSnapshot['stage'] { + if (kind === 'module-pack') { + return 'artifact_validation'; + } + if (kind === 'execution-surface-mismatch') { + return 'pin_enforcement'; + } + return 'runtime_error'; +} + +async function sha256Hex(input: Uint8Array | string): Promise { + const bytes = + typeof input === 'string' ? new TextEncoder().encode(input) : input; + const digest = await crypto.subtle.digest('SHA-256', toArrayBuffer(bytes)); + return Array.from(new Uint8Array(digest)) + .map((byte) => byte.toString(16).padStart(2, '0')) + .join(''); +} + +function toArrayBuffer(bytes: Uint8Array): ArrayBuffer { + if ( + bytes.byteOffset === 0 && + bytes.byteLength === bytes.buffer.byteLength && + bytes.buffer instanceof ArrayBuffer + ) { + return bytes.buffer; + } + return bytes.slice().buffer; +} + +async function loadJson(url: string): Promise { + const response = await fetch(url); + if (!response.ok) { + throw new Error( + `Failed to load ${url}: ${response.status} ${response.statusText}`, + ); + } + return response.json(); +} diff --git a/apps/bluequickjs-playground/src/app/state.spec.ts b/apps/bluequickjs-playground/src/app/state.spec.ts new file mode 100644 index 0000000..a676e98 --- /dev/null +++ b/apps/bluequickjs-playground/src/app/state.spec.ts @@ -0,0 +1,141 @@ +import { + getInitialExample, + getProfileSummary, + groupExamples, +} from './state.js'; +import type { LoadedPlaygroundData } from './types.js'; + +const DATA = { + examples: { + generatedAt: '2026-03-21T00:00:00.000Z', + metadata: { + engineBuildHash: 'a'.repeat(64), + gasVersion: 8, + wasmVariant: 'wasm32', + wasmBuildType: 'release', + }, + examples: [ + { + id: 'example-basic-script', + title: 'Basic deterministic script', + kind: 'example', + badge: 'Example 1', + description: 'Basic deterministic script', + certified: true, + executionProfile: 'baseline-v1', + sourceKind: 'script', + abiId: 'Host.v1', + gasLimit: '1000000', + sourcePaths: ['examples/01-basic-script/program.js'], + sourceText: '(() => 1)();', + hostPreset: 'determinism', + hostSummary: { + label: 'Determinism fixture host', + description: 'stable host', + documents: [], + }, + docsLinks: [], + supportsOogSearch: true, + program: { + version: 2, + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: 'b'.repeat(64), + engineBuildHash: 'a'.repeat(64), + gasVersion: 8, + executionProfile: 'baseline-v1', + sourceKind: 'script', + source: { code: '(() => 1)();' }, + }, + manifest: { + abi_id: 'Host.v1', + abi_version: 1, + funcs: [], + }, + }, + { + id: 'green-semver', + title: 'semver', + kind: 'ecosystem-green', + badge: 'Green ecosystem fixture', + description: 'semver fixture', + certified: true, + executionProfile: 'compat-general-v1', + sourceKind: 'module-pack', + abiId: 'Host.v1', + gasLimit: '1000000', + sourcePaths: [ + 'apps/ecosystem-certifier/fixtures/positive/semver-entry.ts', + ], + sourceText: 'export default 1;', + hostPreset: 'certification', + hostSummary: { + label: 'Certification host', + description: 'cert host', + documents: [], + }, + docsLinks: [], + supportsOogSearch: false, + program: { + version: 2, + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: 'b'.repeat(64), + engineBuildHash: 'a'.repeat(64), + gasVersion: 8, + executionProfile: 'compat-general-v1', + sourceKind: 'module-pack', + source: { + modulePack: { + version: 1, + entrySpecifier: './entry.js', + modules: [], + graphHash: 'c'.repeat(64), + builderVersion: 'deterministic-builder-v1', + dependencyIntegrity: 'd'.repeat(64), + }, + }, + }, + manifest: { + abi_id: 'Host.v1', + abi_version: 1, + funcs: [], + }, + }, + ], + }, + evidence: { + generatedAt: '', + metadata: { engineBuildHash: 'a'.repeat(64), gasVersion: 8 }, + evidence: {}, + }, + oog: { + generatedAt: '', + metadata: { engineBuildHash: 'a'.repeat(64), gasVersion: 8 }, + boundaries: {}, + }, + red: { + generatedAt: '', + metadata: { engineBuildHash: 'a'.repeat(64), gasVersion: 8 }, + fixtures: [], + }, +} satisfies LoadedPlaygroundData; + +describe('playground state helpers', () => { + it('returns the first example as initial selection', () => { + expect(getInitialExample(DATA).id).toBe('example-basic-script'); + }); + + it('groups gallery entries by kind', () => { + const groups = groupExamples(DATA.examples.examples); + expect(groups.example).toHaveLength(1); + expect(groups['ecosystem-green']).toHaveLength(1); + }); + + it('summarizes profile capabilities', () => { + expect(getProfileSummary('baseline-v1')).toContain( + 'Minimal consensus baseline', + ); + expect(getProfileSummary('compat-general-v1')).toContain('promiseJobs'); + }); +}); diff --git a/apps/bluequickjs-playground/src/app/state.ts b/apps/bluequickjs-playground/src/app/state.ts new file mode 100644 index 0000000..b484cb6 --- /dev/null +++ b/apps/bluequickjs-playground/src/app/state.ts @@ -0,0 +1,42 @@ +import { + getExecutionProfileCapabilities, + type PublicExecutionProfile, +} from '@blue-quickjs/execution-profiles'; +import type { + GalleryEntry, + LoadedPlaygroundData, + RedFixtureRecord, +} from './types.js'; + +export type RunMode = 'gallery' | 'script' | 'artifact'; + +export type ResultTab = 'result' | 'evidence' | 'host' | 'metadata' | 'help'; + +export function getInitialExample(data: LoadedPlaygroundData): GalleryEntry { + return data.examples.examples[0]; +} + +export function groupExamples( + entries: GalleryEntry[], +): Record { + return entries.reduce>((groups, entry) => { + const key = entry.kind; + groups[key] ??= []; + groups[key].push(entry); + return groups; + }, {}); +} + +export function getProfileSummary(profile: PublicExecutionProfile): string { + const capabilities = getExecutionProfileCapabilities(profile); + if (capabilities.length === 0) { + return 'Minimal consensus baseline with no Promise jobs or binary APIs.'; + } + return capabilities.join(', '); +} + +export function getRedFixtureMap( + redFixtures: RedFixtureRecord[], +): Map { + return new Map(redFixtures.map((fixture) => [fixture.id, fixture])); +} diff --git a/apps/bluequickjs-playground/src/app/types.ts b/apps/bluequickjs-playground/src/app/types.ts new file mode 100644 index 0000000..95da8f1 --- /dev/null +++ b/apps/bluequickjs-playground/src/app/types.ts @@ -0,0 +1,160 @@ +import type { AbiManifest } from '@blue-quickjs/abi-manifest'; +import type { ProgramArtifactV2 } from '@blue-quickjs/quickjs-runtime'; + +export type HostPresetId = 'determinism' | 'certification'; + +export interface DocsLink { + label: string; + href: string; +} + +export interface HostSummary { + label: string; + description: string; + documents: string[]; +} + +export interface GalleryEntry { + id: string; + title: string; + kind: 'example' | 'ecosystem-green' | 'flagship'; + badge: string; + description: string; + certified: boolean; + executionProfile: string; + sourceKind: ProgramArtifactV2['sourceKind']; + abiId: string; + gasLimit: string; + sourcePaths: string[]; + sourceText: string; + hostPreset: HostPresetId; + hostSummary: HostSummary; + docsLinks: DocsLink[]; + supportsOogSearch: boolean; + program: ProgramArtifactV2; + manifest: AbiManifest; +} + +export interface EvidenceRecord { + stage: string; + resultHash: string | null; + errorCode: string | null; + errorTag: string | null; + gasUsed: string; + gasRemaining: string; + tapeHash: string | null; + tapeLength: number; + certified: boolean; + reportSource: string; + fixtureCoverage: Array<{ suite: string; fixtureName: string }>; +} + +export interface OogBoundaryRecord { + firstSuccessGas: string; + lastFailureGas: string; + successGasUsed: string; + successGasRemaining: string; + failureGasUsed: string; + failureGasRemaining: string; + failureCode: string | null; + failureTag: string | null; +} + +export interface RedFixtureRecord { + id: string; + title: string; + kind: string; + executionProfile: string; + failureStage: string; + errorCode: string | null; + errorTag: string | null; + certified: boolean; + docsLinks: DocsLink[]; + diagnostics: Array<{ filePath: string; ruleId: string; message: string }>; + runtimeArtifact: ProgramArtifactV2 | null; + reportSource: string; +} + +export interface ExamplesPayload { + generatedAt: string; + metadata: { + engineBuildHash: string | null; + gasVersion: number | null; + wasmVariant: string; + wasmBuildType: string; + }; + examples: GalleryEntry[]; +} + +export interface EvidencePayload { + generatedAt: string; + metadata: { + engineBuildHash: string | null; + gasVersion: number | null; + }; + evidence: Record; +} + +export interface OogPayload { + generatedAt: string; + metadata: { + engineBuildHash: string | null; + gasVersion: number | null; + }; + boundaries: Record; +} + +export interface RedPayload { + generatedAt: string; + metadata: { + engineBuildHash: string | null; + gasVersion: number | null; + }; + fixtures: RedFixtureRecord[]; +} + +export interface LoadedPlaygroundData { + examples: ExamplesPayload; + evidence: EvidencePayload; + oog: OogPayload; + red: RedPayload; +} + +export interface RunSnapshot { + stage: + | 'success' + | 'artifact_validation' + | 'runtime_error' + | 'pin_enforcement'; + resultHash: string | null; + errorCode: string | null; + errorTag: string | null; + gasUsed: string; + gasRemaining: string; + tapeHash: string | null; + tapeLength: number; +} + +export interface HostEvent { + fn: 'document.get' | 'document.getCanonical' | 'emit'; + request: unknown; + response: unknown; + units: number; +} + +export interface PlaygroundRunResult { + ok: boolean; + snapshot: RunSnapshot; + value: unknown | null; + errorMessage: string | null; + hostEvents: HostEvent[]; + tape: unknown[]; + runtimeMetadata: { + engineBuildHash: string | null; + gasVersion: number | null; + executionProfile: string; + sourceKind: ProgramArtifactV2['sourceKind']; + abiId: string; + moduleGraphHash: string | null; + }; +} diff --git a/apps/bluequickjs-playground/src/design/theme.css b/apps/bluequickjs-playground/src/design/theme.css new file mode 100644 index 0000000..07e8b4e --- /dev/null +++ b/apps/bluequickjs-playground/src/design/theme.css @@ -0,0 +1,33 @@ +:root { + --bq-font-sans: 'Roboto', 'Inter', 'Helvetica Neue', Arial, sans-serif; + --bq-font-mono: 'Roboto Mono', 'SFMono-Regular', Consolas, monospace; + + --bq-color-canvas: #f4f7fb; + --bq-color-surface: #ffffff; + --bq-color-surface-muted: #f8fafc; + --bq-color-border: #d8e1ec; + --bq-color-border-strong: #c1cedc; + --bq-color-text: #14213d; + --bq-color-text-muted: #5c6b80; + --bq-color-accent: #1f6fff; + --bq-color-accent-soft: #e7f0ff; + --bq-color-success: #0f9f65; + --bq-color-warning: #b7791f; + --bq-color-danger: #d14343; + --bq-color-code-bg: #0f172a; + --bq-color-code-text: #e2e8f0; + + --bq-radius-xs: 10px; + --bq-radius-sm: 14px; + --bq-radius-md: 18px; + --bq-radius-pill: 999px; + + --bq-shadow-sm: 0 8px 24px rgba(20, 33, 61, 0.06); + --bq-shadow-md: 0 18px 48px rgba(20, 33, 61, 0.08); + + --bq-space-xs: 8px; + --bq-space-sm: 12px; + --bq-space-md: 16px; + --bq-space-lg: 24px; + --bq-space-xl: 32px; +} diff --git a/apps/bluequickjs-playground/src/design/tokens.ts b/apps/bluequickjs-playground/src/design/tokens.ts new file mode 100644 index 0000000..93a7c4e --- /dev/null +++ b/apps/bluequickjs-playground/src/design/tokens.ts @@ -0,0 +1,35 @@ +export const TOKENS = { + colors: { + canvas: '#f4f7fb', + surface: '#ffffff', + surfaceMuted: '#f8fafc', + border: '#d8e1ec', + borderStrong: '#c1cedc', + text: '#14213d', + textMuted: '#5c6b80', + accent: '#1f6fff', + accentSoft: '#e7f0ff', + success: '#0f9f65', + warning: '#b7791f', + danger: '#d14343', + codeBg: '#0f172a', + codeText: '#e2e8f0', + }, + radius: { + xs: '10px', + sm: '14px', + md: '18px', + pill: '999px', + }, + shadow: { + sm: '0 8px 24px rgba(20, 33, 61, 0.06)', + md: '0 18px 48px rgba(20, 33, 61, 0.08)', + }, + spacing: { + xs: '8px', + sm: '12px', + md: '16px', + lg: '24px', + xl: '32px', + }, +} as const; diff --git a/apps/bluequickjs-playground/src/main.ts b/apps/bluequickjs-playground/src/main.ts new file mode 100644 index 0000000..1419b1d --- /dev/null +++ b/apps/bluequickjs-playground/src/main.ts @@ -0,0 +1,11 @@ +import './styles.css'; +import { PlaygroundApp } from './app/playground-app.js'; + +const root = document.getElementById('app'); + +if (!root) { + throw new Error('Missing #app root for BlueQuickjs Playground'); +} + +const app = new PlaygroundApp(root); +void app.init(); diff --git a/apps/bluequickjs-playground/src/styles.css b/apps/bluequickjs-playground/src/styles.css new file mode 100644 index 0000000..78d9b91 --- /dev/null +++ b/apps/bluequickjs-playground/src/styles.css @@ -0,0 +1,421 @@ +@import url('https://fonts.googleapis.com/css2?family=Roboto:wght@300;400;500;700&family=Roboto+Mono:wght@400;500&display=swap'); +@import './design/theme.css'; + +* { + box-sizing: border-box; +} + +html, +body { + margin: 0; + min-height: 100%; + background: var(--bq-color-canvas); + color: var(--bq-color-text); + font-family: var(--bq-font-sans); +} + +body { + min-height: 100vh; +} + +a { + color: var(--bq-color-accent); +} + +button, +input, +select, +textarea { + font: inherit; +} + +#app { + min-height: 100vh; +} + +.bq-loading { + display: grid; + min-height: 100vh; + place-items: center; + color: var(--bq-color-text-muted); +} + +.bq-shell { + max-width: 1480px; + margin: 0 auto; + padding: var(--bq-space-xl); + display: grid; + gap: var(--bq-space-lg); +} + +.card { + background: var(--bq-color-surface); + border: 1px solid var(--bq-color-border); + border-radius: var(--bq-radius-md); + box-shadow: var(--bq-shadow-sm); +} + +.bq-hero { + padding: var(--bq-space-xl); + display: grid; + gap: var(--bq-space-md); +} + +.bq-brand { + display: flex; + align-items: center; + gap: var(--bq-space-md); +} + +.bq-logo { + width: 44px; + height: 44px; + border-radius: 14px; + display: grid; + place-items: center; + background: linear-gradient(135deg, var(--bq-color-accent), #2f8cff); + color: white; + font-weight: 700; + font-size: 22px; +} + +.eyebrow { + margin: 0; + font-size: 12px; + letter-spacing: 0.08em; + text-transform: uppercase; + color: var(--bq-color-text-muted); +} + +h1, +h2, +h3, +p { + margin: 0; +} + +h1 { + font-size: 36px; + line-height: 1.1; +} + +h2 { + font-size: 20px; + line-height: 1.2; +} + +h3 { + font-size: 15px; +} + +.lede, +.section-heading p, +.panel-note, +.field-help, +.gallery-item span, +.meta-strip, +.stack { + color: var(--bq-color-text-muted); +} + +.hero-chips, +.chip-row, +.preset-row, +.button-row, +.meta-strip, +.tab-row { + display: flex; + flex-wrap: wrap; + gap: var(--bq-space-sm); +} + +.chip { + display: inline-flex; + align-items: center; + min-height: 34px; + padding: 0 12px; + border-radius: var(--bq-radius-pill); + border: 1px solid var(--bq-color-border); + background: var(--bq-color-surface-muted); + color: var(--bq-color-text); + font-size: 13px; +} + +.chip.accent { + background: var(--bq-color-accent-soft); + border-color: #c6dafd; + color: var(--bq-color-accent); +} + +.chip.status { + font-weight: 600; +} + +.bq-layout { + display: grid; + grid-template-columns: minmax(320px, 380px) minmax(0, 1fr); + gap: var(--bq-space-lg); +} + +.bq-sidebar, +.bq-main { + display: grid; + gap: var(--bq-space-lg); +} + +.controls-card, +.gallery-card, +.editor-card, +.results-card { + padding: var(--bq-space-lg); +} + +.section-heading { + display: grid; + gap: 6px; + margin-bottom: var(--bq-space-md); +} + +.section-heading.inline { + display: flex; + justify-content: space-between; + align-items: flex-start; + gap: var(--bq-space-md); +} + +.section-heading.tight { + margin-bottom: var(--bq-space-sm); +} + +.segmented { + display: inline-flex; + padding: 4px; + border-radius: var(--bq-radius-pill); + border: 1px solid var(--bq-color-border); + background: var(--bq-color-surface-muted); +} + +.segmented-button, +.tab-button, +.ghost-button, +.primary-button, +.gallery-item { + border: 1px solid transparent; + border-radius: var(--bq-radius-sm); + cursor: pointer; + transition: + background 120ms ease, + border-color 120ms ease, + box-shadow 120ms ease, + transform 120ms ease; +} + +.segmented-button, +.tab-button { + background: transparent; + color: var(--bq-color-text-muted); + padding: 10px 14px; +} + +.segmented-button[data-active='true'], +.tab-button[data-active='true'] { + background: var(--bq-color-surface); + color: var(--bq-color-text); + border-color: var(--bq-color-border); + box-shadow: var(--bq-shadow-sm); +} + +.field { + display: grid; + gap: 8px; + margin-top: var(--bq-space-md); +} + +.field span { + font-size: 13px; + font-weight: 500; +} + +.field input, +.field select { + min-height: 44px; + border-radius: var(--bq-radius-sm); + border: 1px solid var(--bq-color-border); + background: var(--bq-color-surface); + padding: 0 14px; + color: var(--bq-color-text); +} + +.ghost-button, +.primary-button { + min-height: 42px; + padding: 0 14px; +} + +.ghost-button { + background: var(--bq-color-surface-muted); + border-color: var(--bq-color-border); + color: var(--bq-color-text); +} + +.primary-button { + background: linear-gradient(135deg, var(--bq-color-accent), #2f8cff); + color: white; +} + +.gallery-group { + display: grid; + gap: var(--bq-space-sm); + margin-bottom: var(--bq-space-md); +} + +.gallery-list { + display: grid; + gap: var(--bq-space-sm); +} + +.gallery-item { + width: 100%; + text-align: left; + padding: var(--bq-space-md); + background: var(--bq-color-surface-muted); + border-color: var(--bq-color-border); + display: grid; + gap: 6px; +} + +.gallery-item.danger { + border-color: #f3c5c5; + background: #fff7f7; +} + +.divider { + height: 1px; + background: var(--bq-color-border); + margin: var(--bq-space-md) 0; +} + +.editor-toolbar { + display: flex; + justify-content: space-between; + gap: var(--bq-space-md); + margin-bottom: var(--bq-space-md); +} + +.editor-frame { + overflow: hidden; + min-height: 520px; + border-radius: var(--bq-radius-md); + border: 1px solid var(--bq-color-border); +} + +.meta-strip { + margin-bottom: var(--bq-space-md); +} + +.meta-strip span { + background: var(--bq-color-surface-muted); + border: 1px solid var(--bq-color-border); + padding: 8px 12px; + border-radius: var(--bq-radius-pill); + font-size: 13px; +} + +.metrics-grid { + display: grid; + grid-template-columns: repeat(4, minmax(0, 1fr)); + gap: var(--bq-space-sm); + margin-bottom: var(--bq-space-md); +} + +.metric-card { + min-height: 90px; + padding: var(--bq-space-md); + border-radius: var(--bq-radius-sm); + border: 1px solid var(--bq-color-border); + background: var(--bq-color-surface-muted); + display: grid; + gap: 8px; +} + +.metric-card.empty { + grid-column: 1 / -1; +} + +.metric-label { + font-size: 12px; + text-transform: uppercase; + letter-spacing: 0.08em; + color: var(--bq-color-text-muted); +} + +.tab-row { + margin-bottom: var(--bq-space-md); +} + +.tab-panel pre { + margin: 0; + padding: var(--bq-space-md); + border-radius: var(--bq-radius-sm); + background: var(--bq-color-code-bg); + color: var(--bq-color-code-text); + font-family: var(--bq-font-mono); + font-size: 13px; + line-height: 1.5; + overflow: auto; + white-space: pre-wrap; + word-break: break-word; +} + +.stack { + display: grid; + gap: var(--bq-space-md); +} + +.link-list { + display: grid; + gap: var(--bq-space-sm); + padding-left: 18px; + margin: 0; +} + +button:hover, +select:hover, +input:hover { + border-color: var(--bq-color-border-strong); +} + +button:focus-visible, +select:focus-visible, +input:focus-visible { + outline: 3px solid rgba(31, 111, 255, 0.18); + outline-offset: 2px; +} + +@media (max-width: 1180px) { + .bq-layout { + grid-template-columns: 1fr; + } + + .metrics-grid { + grid-template-columns: repeat(2, minmax(0, 1fr)); + } +} + +@media (max-width: 760px) { + .bq-shell { + padding: var(--bq-space-md); + } + + .section-heading.inline { + flex-direction: column; + } + + .metrics-grid { + grid-template-columns: 1fr; + } + + .editor-frame { + min-height: 380px; + } +} diff --git a/apps/bluequickjs-playground/tests/playground.spec.ts b/apps/bluequickjs-playground/tests/playground.spec.ts new file mode 100644 index 0000000..1efaed1 --- /dev/null +++ b/apps/bluequickjs-playground/tests/playground.spec.ts @@ -0,0 +1,141 @@ +import { expect, test } from '@playwright/test'; + +async function selectGalleryItem( + page: import('@playwright/test').Page, + text: string, +) { + await page + .locator('button.gallery-item') + .filter({ hasText: text }) + .first() + .click(); +} + +test('renders the landing state', async ({ page, browserName }) => { + await page.goto('/'); + await expect( + page.getByRole('heading', { name: 'BlueQuickjs Playground' }), + ).toBeVisible(); + await expect(page.locator('[data-selection-title]')).toContainText( + 'Basic deterministic script', + ); + + if (browserName === 'chromium') { + await expect(page).toHaveScreenshot('playground-landing.png', { + fullPage: true, + }); + } +}); + +test('runs the baseline example and matches certified evidence', async ({ + page, + browserName, +}) => { + await page.goto('/'); + await page.getByRole('button', { name: 'Run current selection' }).click(); + + await expect(page.locator('[data-run-status]')).toContainText('Success'); + await expect(page.locator('[data-evidence-status]')).toContainText( + 'Matches certified snapshot', + ); + await expect(page.locator('[data-tab-panel]')).toContainText( + '"gasUsed": "74"', + ); + + if (browserName === 'chromium') { + await expect(page).toHaveScreenshot('playground-success.png', { + fullPage: true, + }); + } +}); + +test('runs promise and binary examples through their profile-gated flows', async ({ + page, + browserName, +}) => { + await page.goto('/'); + + await selectGalleryItem(page, 'Promises / async / microtasks'); + await page.getByRole('button', { name: 'Run current selection' }).click(); + await expect(page.locator('[data-run-status]')).toContainText('Success'); + await expect(page.locator('[data-evidence-status]')).toContainText( + 'Matches certified snapshot', + ); + + await selectGalleryItem(page, 'Binary / typed arrays / Host.v2 DV2'); + await page.getByRole('button', { name: 'Run current selection' }).click(); + await expect(page.locator('[data-run-status]')).toContainText('Success'); + await expect(page.locator('[data-evidence-status]')).toContainText( + 'Matches certified snapshot', + ); + + if (browserName === 'chromium') { + await expect(page).toHaveScreenshot('playground-binary.png', { + fullPage: true, + }); + } +}); + +test('shows deterministic failure messaging for red fixtures', async ({ + page, + browserName, +}) => { + await page.goto('/'); + await selectGalleryItem( + page, + 'dynamic import must be rejected at build stage', + ); + + await expect(page.locator('[data-selection-title]')).toContainText( + 'dynamic import must be rejected at build stage', + ); + await expect( + page.getByRole('button', { name: 'Run current selection' }), + ).toBeDisabled(); + await page.getByRole('button', { name: 'Determinism evidence' }).click(); + await expect(page.locator('[data-tab-panel]')).toContainText( + 'builder_reject', + ); + + if (browserName === 'chromium') { + await expect(page).toHaveScreenshot('playground-failure.png', { + fullPage: true, + }); + } +}); + +test('supports exact OOG boundary inspection and artifact-json roundtrips', async ({ + page, + browserName, +}) => { + await page.goto('/'); + await selectGalleryItem(page, 'Max-gas policy / OOG boundary'); + await page.getByRole('button', { name: 'Find OOG boundary' }).click(); + await page.getByRole('button', { name: 'Determinism evidence' }).click(); + await expect(page.locator('[data-tab-panel]')).toContainText( + '"firstSuccessGas": "170099"', + ); + await expect(page.locator('[data-tab-panel]')).toContainText( + '"lastFailureGas": "170098"', + ); + + if (browserName === 'chromium') { + await expect(page).toHaveScreenshot('playground-oog.png', { + fullPage: true, + }); + } + + await selectGalleryItem(page, 'Standard ESM module-pack'); + await page.getByRole('button', { name: 'Artifact JSON' }).click(); + await page.getByRole('button', { name: 'Run current selection' }).click(); + await expect(page.locator('[data-run-status]')).toContainText('Success'); + await expect(page.locator('[data-evidence-status]')).toContainText( + 'Matches certified snapshot', + ); + + const [download] = await Promise.all([ + page.waitForEvent('download'), + page.getByRole('button', { name: 'Export artifact' }).click(), + ]); + expect(download.suggestedFilename()).toContain('bluequickjs-artifact'); +}); diff --git a/apps/bluequickjs-playground/tests/playground.spec.ts-snapshots/playground-binary-chromium-linux.png b/apps/bluequickjs-playground/tests/playground.spec.ts-snapshots/playground-binary-chromium-linux.png new file mode 100644 index 0000000..970d77a Binary files /dev/null and b/apps/bluequickjs-playground/tests/playground.spec.ts-snapshots/playground-binary-chromium-linux.png differ diff --git a/apps/bluequickjs-playground/tests/playground.spec.ts-snapshots/playground-failure-chromium-linux.png b/apps/bluequickjs-playground/tests/playground.spec.ts-snapshots/playground-failure-chromium-linux.png new file mode 100644 index 0000000..cbc790e Binary files /dev/null and b/apps/bluequickjs-playground/tests/playground.spec.ts-snapshots/playground-failure-chromium-linux.png differ diff --git a/apps/bluequickjs-playground/tests/playground.spec.ts-snapshots/playground-landing-chromium-linux.png b/apps/bluequickjs-playground/tests/playground.spec.ts-snapshots/playground-landing-chromium-linux.png new file mode 100644 index 0000000..fdabf4c Binary files /dev/null and b/apps/bluequickjs-playground/tests/playground.spec.ts-snapshots/playground-landing-chromium-linux.png differ diff --git a/apps/bluequickjs-playground/tests/playground.spec.ts-snapshots/playground-oog-chromium-linux.png b/apps/bluequickjs-playground/tests/playground.spec.ts-snapshots/playground-oog-chromium-linux.png new file mode 100644 index 0000000..8f2d614 Binary files /dev/null and b/apps/bluequickjs-playground/tests/playground.spec.ts-snapshots/playground-oog-chromium-linux.png differ diff --git a/apps/bluequickjs-playground/tests/playground.spec.ts-snapshots/playground-success-chromium-linux.png b/apps/bluequickjs-playground/tests/playground.spec.ts-snapshots/playground-success-chromium-linux.png new file mode 100644 index 0000000..b64579f Binary files /dev/null and b/apps/bluequickjs-playground/tests/playground.spec.ts-snapshots/playground-success-chromium-linux.png differ diff --git a/apps/bluequickjs-playground/tsconfig.app.json b/apps/bluequickjs-playground/tsconfig.app.json new file mode 100644 index 0000000..c5a9d61 --- /dev/null +++ b/apps/bluequickjs-playground/tsconfig.app.json @@ -0,0 +1,58 @@ +{ + "extends": "../../tsconfig.base.json", + "compilerOptions": { + "outDir": "dist", + "lib": ["es2022", "dom", "dom.iterable"], + "types": ["node", "vite/client"], + "rootDir": "src", + "module": "esnext", + "moduleResolution": "bundler", + "tsBuildInfoFile": "dist/tsconfig.app.tsbuildinfo" + }, + "exclude": [ + "out-tsc", + "dist", + "src/**/*.spec.ts", + "src/**/*.test.ts", + "vite.config.ts", + "vite.config.mts", + "vitest.config.ts", + "vitest.config.mts", + "src/**/*.test.tsx", + "src/**/*.spec.tsx", + "src/**/*.test.js", + "src/**/*.spec.js", + "src/**/*.test.jsx", + "src/**/*.spec.jsx", + "eslint.config.js", + "eslint.config.cjs", + "eslint.config.mjs" + ], + "include": ["src/**/*.ts", "src/**/*.d.ts"], + "references": [ + { + "path": "../ecosystem-certifier/tsconfig.app.json" + }, + { + "path": "../../libs/test-harness/tsconfig.lib.json" + }, + { + "path": "../../libs/quickjs-wasm/tsconfig.lib.json" + }, + { + "path": "../../libs/quickjs-runtime/tsconfig.lib.json" + }, + { + "path": "../../libs/execution-profiles/tsconfig.lib.json" + }, + { + "path": "../../libs/dv/tsconfig.lib.json" + }, + { + "path": "../../libs/deterministic-builder/tsconfig.lib.json" + }, + { + "path": "../../libs/abi-manifest/tsconfig.lib.json" + } + ] +} diff --git a/apps/bluequickjs-playground/tsconfig.json b/apps/bluequickjs-playground/tsconfig.json new file mode 100644 index 0000000..63dbe35 --- /dev/null +++ b/apps/bluequickjs-playground/tsconfig.json @@ -0,0 +1,13 @@ +{ + "extends": "../../tsconfig.base.json", + "files": [], + "include": [], + "references": [ + { + "path": "./tsconfig.app.json" + }, + { + "path": "./tsconfig.spec.json" + } + ] +} diff --git a/apps/bluequickjs-playground/tsconfig.spec.json b/apps/bluequickjs-playground/tsconfig.spec.json new file mode 100644 index 0000000..feb6ad3 --- /dev/null +++ b/apps/bluequickjs-playground/tsconfig.spec.json @@ -0,0 +1,36 @@ +{ + "extends": "../../tsconfig.base.json", + "compilerOptions": { + "outDir": "./out-tsc/vitest", + "lib": ["es2022", "dom", "dom.iterable"], + "types": [ + "vitest/globals", + "vitest/importMeta", + "vite/client", + "node", + "vitest" + ], + "module": "esnext", + "moduleResolution": "bundler" + }, + "include": [ + "vite.config.ts", + "vite.config.mts", + "vitest.config.ts", + "vitest.config.mts", + "src/**/*.test.ts", + "src/**/*.spec.ts", + "src/**/*.test.tsx", + "src/**/*.spec.tsx", + "src/**/*.test.js", + "src/**/*.spec.js", + "src/**/*.test.jsx", + "src/**/*.spec.jsx", + "src/**/*.d.ts" + ], + "references": [ + { + "path": "./tsconfig.app.json" + } + ] +} diff --git a/apps/bluequickjs-playground/vite.config.mts b/apps/bluequickjs-playground/vite.config.mts new file mode 100644 index 0000000..eca94d9 --- /dev/null +++ b/apps/bluequickjs-playground/vite.config.mts @@ -0,0 +1,40 @@ +/// +import path from 'node:path'; +import { defineConfig } from 'vite'; + +export default defineConfig(() => ({ + root: import.meta.dirname, + cacheDir: '../../node_modules/.vite/apps/bluequickjs-playground', + server: { + port: 4325, + host: 'localhost', + fs: { + allow: [path.resolve(import.meta.dirname, '..', '..', '..')], + }, + }, + preview: { + port: 4325, + host: 'localhost', + }, + build: { + outDir: './dist', + emptyOutDir: true, + reportCompressedSize: true, + commonjsOptions: { + transformMixedEsModules: true, + }, + }, + test: { + name: 'bluequickjs-playground', + watch: false, + globals: true, + environment: 'jsdom', + include: ['src/**/*.{test,spec}.{js,mjs,cjs,ts,mts,cts,jsx,tsx}'], + exclude: ['tests/**'], + reporters: ['default'], + coverage: { + reportsDirectory: './test-output/vitest/coverage', + provider: 'v8' as const, + }, + }, +})); diff --git a/apps/ecosystem-certifier/README.md b/apps/ecosystem-certifier/README.md new file mode 100644 index 0000000..12064fe --- /dev/null +++ b/apps/ecosystem-certifier/README.md @@ -0,0 +1,29 @@ +# ecosystem-certifier + +Workload and ecosystem certification app for deterministic `blue-quickjs`. + +## What it runs + +- Flagship knowledge/compliance pack workload. +- Positive third-party compatibility fixtures. +- Negative deterministic-boundary fixtures. +- Node vs browser parity comparisons (result/error, gas, tape). + +## Commands + +- Unit tests: `pnpm nx test ecosystem-certifier` +- Browser e2e: `pnpm nx run ecosystem-certifier:e2e` +- Generate certification report: + `pnpm nx run ecosystem-certifier:certify -- --out-dir artifacts/workload-certification --browser chromium` +- Builder path-determinism check: + `node apps/ecosystem-certifier/scripts/check-builder-determinism.mjs` +- OOG boundary parity report: + `node apps/ecosystem-certifier/scripts/run-oog-boundary-certification.mjs --out-dir artifacts/workload-certification --browser chromium` +- Repeatability / soak report: + `node apps/ecosystem-certifier/scripts/run-repeatability-certification.mjs --out-dir artifacts/workload-certification --iterations 100 --flagship-iterations 40 --browser chromium` +- Seeded property corpus parity report: + `node apps/ecosystem-certifier/scripts/run-seeded-property-corpus.mjs --out-dir artifacts/workload-certification --seed-count 80 --browser chromium` +- Compatibility delta report: + `node apps/ecosystem-certifier/scripts/generate-compatibility-delta-report.mjs --current-dir artifacts/workload-certification --out-dir artifacts/workload-certification` +- Regenerate deterministic stress corpus: + `node apps/ecosystem-certifier/scripts/generate-stress-corpus.mjs` diff --git a/apps/ecosystem-certifier/fixtures/flagship/knowledge-pack-entry.ts b/apps/ecosystem-certifier/fixtures/flagship/knowledge-pack-entry.ts new file mode 100644 index 0000000..eee2b10 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/flagship/knowledge-pack-entry.ts @@ -0,0 +1,138 @@ +import { toByteArray, fromByteArray } from 'base64-js'; +import { inflateSync } from 'fflate'; +import deepEqual from 'fast-deep-equal'; +import stableStringify from 'fast-json-stable-stringify'; +import he from 'he'; +import jsonLogic from 'json-logic-js'; +import LinkifyIt from 'linkify-it'; +import MarkdownIt from 'markdown-it'; +import { sha256 } from '@noble/hashes/sha256'; +import { bytesToHex } from '@noble/hashes/utils'; +import { match as pathMatch } from 'path-to-regexp'; +import semver from 'semver'; +import TinyQueue from 'tinyqueue'; +import CRC32 from 'crc-32'; + +let summary; +try { + const metadataText = Host.v2.document.get('pack/metadata.json'); + const ruleText = Host.v2.document.get('rules/findings.json'); + const compressedAttachment = Host.v2.document.get('pack/attachment.deflated'); + const payload = Host.v2.document.get('bytes/payload'); + const extraPayload = Host.v2.document.get('bytes/flagship-extra'); + + const metadata = JSON.parse(metadataText); + const docPaths = metadata.links ?? ['docs/a.md', 'docs/b.md']; + const docs = docPaths.map((docPath) => ({ + docPath, + text: Host.v2.document.get(docPath), + })); + const markdown = new MarkdownIt({ linkify: true }); + const linkify = new LinkifyIt(); + const markdownSource = docs.map((doc) => doc.text).join('\n'); + const markdownTokens = markdown.parse(markdownSource, {}); + const linkMatches = docs + .flatMap((doc) => linkify.match(doc.text) ?? []) + .map((item) => item.url); + + const releaseChecks = (metadata.requires ?? []).map((range) => + semver.satisfies(metadata.release, range), + ); + const rules = JSON.parse(ruleText); + const findingInput = { + linkCount: linkMatches.length, + releaseOk: releaseChecks.every(Boolean), + }; + const ruleInputStable = deepEqual( + findingInput, + JSON.parse(stableStringify(findingInput)), + ); + const rulePasses = Boolean(jsonLogic.apply(rules, findingInput)); + + const queue = new TinyQueue([], (left, right) => left.priority - right.priority); + for (const link of linkMatches) { + queue.push({ link, priority: link.length }); + } + const orderedLinks = []; + while (queue.length > 0) { + orderedLinks.push(queue.pop().link); + } + + const decompressed = inflateSync(compressedAttachment); + const attachmentRoundTrip = toByteArray(fromByteArray(decompressed)); + const mergedBinary = new Uint8Array( + attachmentRoundTrip.length + payload.length + extraPayload.length, + ); + mergedBinary.set(attachmentRoundTrip, 0); + mergedBinary.set(payload, attachmentRoundTrip.length); + mergedBinary.set(extraPayload, attachmentRoundTrip.length + payload.length); + const digestHex = bytesToHex(sha256(mergedBinary)); + const crc32 = (CRC32.buf(mergedBinary) >>> 0) + .toString(16) + .padStart(8, '0'); + + const decodedEntities = he.decode('<b>safe</b>'); + const versionCapture = pathMatch('/document/:id/version/:version')( + '/document/42/version/1.2.3', + ); + const orderedFindings = [ + { id: 'links', value: linkMatches.length }, + { id: 'rules', value: Number(rulePasses) }, + { id: 'tokens', value: markdownTokens.length }, + ].sort((left, right) => left.id.localeCompare(right.id)); + + Promise.resolve('scheduled').then(() => undefined); + queueMicrotask(() => undefined); + + for (const doc of docs) { + Host.v2.emit({ + type: 'knowledge-pack-doc', + docPath: doc.docPath, + length: doc.text.length, + }); + } + + summary = { + status: 'ok', + packId: metadata.packId, + release: metadata.release, + checks: releaseChecks, + docTokenCount: markdownTokens.length, + linkCount: linkMatches.length, + uniqueLinks: [...new Set(orderedLinks)], + binary: { + byteLength: mergedBinary.length, + digestHex, + crc32, + }, + decodedEntities, + versionCapture, + findings: orderedFindings, + ruleInputStable, + rulePasses, + }; +} catch (error) { + summary = { + status: 'error', + message: String(error instanceof Error ? error.message : error), + }; +} + +Host.v2.emit({ + type: 'knowledge-pack-summary', + summaryHash: bytesToHex( + sha256( + toByteArray( + fromByteArray( + new Uint8Array([ + ...Host.v2.document.get('bytes/payload'), + ...Host.v2.document.get('bytes/flagship-extra'), + ]), + ), + ), + ), + ), + status: summary.status, +}); + +export default summary; diff --git a/apps/ecosystem-certifier/fixtures/negative/dynamic-import-entry.ts b/apps/ecosystem-certifier/fixtures/negative/dynamic-import-entry.ts new file mode 100644 index 0000000..68c949c --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/negative/dynamic-import-entry.ts @@ -0,0 +1,4 @@ +export default async () => { + const loaded = await import('./dynamic-local'); + return loaded.value; +}; diff --git a/apps/ecosystem-certifier/fixtures/negative/dynamic-local.ts b/apps/ecosystem-certifier/fixtures/negative/dynamic-local.ts new file mode 100644 index 0000000..5f45ec8 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/negative/dynamic-local.ts @@ -0,0 +1 @@ +export const value = 7; diff --git a/apps/ecosystem-certifier/fixtures/negative/function-constructor-entry.ts b/apps/ecosystem-certifier/fixtures/negative/function-constructor-entry.ts new file mode 100644 index 0000000..796ee22 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/negative/function-constructor-entry.ts @@ -0,0 +1,3 @@ +const make = new Function('return 41 + 1;'); + +export default make(); diff --git a/apps/ecosystem-certifier/fixtures/negative/graphlib-entry.ts b/apps/ecosystem-certifier/fixtures/negative/graphlib-entry.ts new file mode 100644 index 0000000..9a5f98f --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/negative/graphlib-entry.ts @@ -0,0 +1,8 @@ +import { Graph } from 'graphlib'; + +const graph = new Graph({ directed: true }); +graph.setNode('a'); +graph.setNode('b'); +graph.setEdge('a', 'b'); + +export default graph.edgeCount(); diff --git a/apps/ecosystem-certifier/fixtures/negative/math-random-entry.ts b/apps/ecosystem-certifier/fixtures/negative/math-random-entry.ts new file mode 100644 index 0000000..b6daef7 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/negative/math-random-entry.ts @@ -0,0 +1 @@ +export default Math.random(); diff --git a/apps/ecosystem-certifier/fixtures/negative/proxy-entry.ts b/apps/ecosystem-certifier/fixtures/negative/proxy-entry.ts new file mode 100644 index 0000000..900409d --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/negative/proxy-entry.ts @@ -0,0 +1,8 @@ +const target = { value: 1 }; +const proxy = new Proxy(target, { + get(obj, prop) { + return obj[prop]; + }, +}); + +export default proxy.value; diff --git a/apps/ecosystem-certifier/fixtures/positive/array-move-entry.ts b/apps/ecosystem-certifier/fixtures/positive/array-move-entry.ts new file mode 100644 index 0000000..b043416 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/array-move-entry.ts @@ -0,0 +1,9 @@ +import { arrayMoveImmutable } from 'array-move'; + +const values = ['wasm-node', 'chromium', 'firefox', 'webk-it']; +const reordered = arrayMoveImmutable(values, 3, 1); + +export default { + reordered, + original: values, +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/camelcase-entry.ts b/apps/ecosystem-certifier/fixtures/positive/camelcase-entry.ts new file mode 100644 index 0000000..f03d8db --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/camelcase-entry.ts @@ -0,0 +1,7 @@ +import camelCase from 'camelcase'; + +const samples = ['hello-world', 'blue_quickjs', 'deterministic vm']; + +export default { + values: samples.map((sample) => camelCase(sample)), +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/crc32-entry.ts b/apps/ecosystem-certifier/fixtures/positive/crc32-entry.ts new file mode 100644 index 0000000..574c3e0 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/crc32-entry.ts @@ -0,0 +1,9 @@ +import CRC32 from 'crc-32'; + +const value = Host.v1.document.get('text/markdown-case'); +const checksum = (CRC32.str(value) >>> 0).toString(16).padStart(8, '0'); + +export default { + checksum, + length: value.length, +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/decamelize-entry.ts b/apps/ecosystem-certifier/fixtures/positive/decamelize-entry.ts new file mode 100644 index 0000000..ace54aa --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/decamelize-entry.ts @@ -0,0 +1,7 @@ +import decamelize from 'decamelize'; + +const samples = ['deterministicRuntime', 'gasVersionPin', 'hostCallTape']; + +export default { + values: samples.map((sample) => decamelize(sample)), +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/deepmerge-entry.ts b/apps/ecosystem-certifier/fixtures/positive/deepmerge-entry.ts new file mode 100644 index 0000000..fe7df0f --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/deepmerge-entry.ts @@ -0,0 +1,16 @@ +import merge from 'deepmerge'; + +const left = { + release: { + consensus: true, + executors: ['wasm-node'], + }, +}; +const right = { + release: { + executors: ['wasm-browser'], + profiles: ['compat-general-v1'], + }, +}; + +export default merge(left, right); diff --git a/apps/ecosystem-certifier/fixtures/positive/diff-entry.ts b/apps/ecosystem-certifier/fixtures/positive/diff-entry.ts new file mode 100644 index 0000000..3b6447f --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/diff-entry.ts @@ -0,0 +1,11 @@ +import { diffLines } from 'diff'; + +const left = Host.v1.document.get('text/diff-left'); +const right = Host.v1.document.get('text/diff-right'); +const chunks = diffLines(left, right); + +export default { + chunkCount: chunks.length, + added: chunks.filter((chunk) => chunk.added).length, + removed: chunks.filter((chunk) => chunk.removed).length, +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/dijkstrajs-entry.ts b/apps/ecosystem-certifier/fixtures/positive/dijkstrajs-entry.ts new file mode 100644 index 0000000..b38fe34 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/dijkstrajs-entry.ts @@ -0,0 +1,13 @@ +import dijkstra from 'dijkstrajs'; + +const graph = { + start: { parse: 2, hash: 5 }, + parse: { graph: 1, hash: 2 }, + hash: { graph: 2, done: 3 }, + graph: { done: 1 }, + done: {}, +}; + +export default { + route: dijkstra.find_path(graph, 'start', 'done'), +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/escape-string-regexp-entry.ts b/apps/ecosystem-certifier/fixtures/positive/escape-string-regexp-entry.ts new file mode 100644 index 0000000..9e9e0c1 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/escape-string-regexp-entry.ts @@ -0,0 +1,7 @@ +import escapeStringRegexp from 'escape-string-regexp'; + +const raw = Host.v1.document.get('text/path-case'); + +export default { + escaped: escapeStringRegexp(raw), +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/fast-deep-equal-entry.ts b/apps/ecosystem-certifier/fixtures/positive/fast-deep-equal-entry.ts new file mode 100644 index 0000000..4cfb203 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/fast-deep-equal-entry.ts @@ -0,0 +1,12 @@ +import deepEqual from 'fast-deep-equal'; + +const left = { + id: 'deterministic', + values: [1, 2, 3], + nested: { ok: true }, +}; +const right = JSON.parse(JSON.stringify(left)); + +export default { + equal: deepEqual(left, right), +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/fast-json-stable-stringify-entry.ts b/apps/ecosystem-certifier/fixtures/positive/fast-json-stable-stringify-entry.ts new file mode 100644 index 0000000..c19b625 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/fast-json-stable-stringify-entry.ts @@ -0,0 +1,14 @@ +import stableStringify from 'fast-json-stable-stringify'; + +const payload = { + zebra: 1, + alpha: 2, + nested: { + gamma: 3, + beta: 4, + }, +}; + +export default { + serialized: stableStringify(payload), +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/fastest-levenshtein-entry.ts b/apps/ecosystem-certifier/fixtures/positive/fastest-levenshtein-entry.ts new file mode 100644 index 0000000..deacfdd --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/fastest-levenshtein-entry.ts @@ -0,0 +1,13 @@ +import { closest, distance } from 'fastest-levenshtein'; + +const dictionary = ['consensus', 'determinism', 'compatibility', 'gas-metering']; +const target = 'deterministic'; + +export default { + target, + closest: closest(target, dictionary), + distances: dictionary.map((entry) => ({ + entry, + value: distance(target, entry), + })), +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/fflate-entry.ts b/apps/ecosystem-certifier/fixtures/positive/fflate-entry.ts new file mode 100644 index 0000000..033b624 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/fflate-entry.ts @@ -0,0 +1,10 @@ +import { strToU8, zlibSync, unzlibSync } from 'fflate'; + +const text = Host.v1.document.get('text/markdown-case'); +const compressed = zlibSync(strToU8(text)); +const roundTrip = unzlibSync(compressed); + +export default { + compressedLength: compressed.length, + restoredLength: roundTrip.length, +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/he-entry.ts b/apps/ecosystem-certifier/fixtures/positive/he-entry.ts new file mode 100644 index 0000000..a39b4a4 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/he-entry.ts @@ -0,0 +1,8 @@ +import he from 'he'; + +const encoded = Host.v1.document.get('text/he-case'); + +export default { + encoded, + decoded: he.decode(encoded), +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/json-logic-entry.ts b/apps/ecosystem-certifier/fixtures/positive/json-logic-entry.ts new file mode 100644 index 0000000..3bbbb96 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/json-logic-entry.ts @@ -0,0 +1,14 @@ +import jsonLogic from 'json-logic-js'; + +const payload = JSON.parse(Host.v1.document.get('text/json-logic-case')); +const rule = { + and: [ + { '>': [{ var: 'score' }, { var: 'threshold' }] }, + { '<=': [{ var: 'threshold' }, 10] }, + ], +}; + +export default { + payload, + passes: Boolean(jsonLogic.apply(rule, payload)), +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/linkify-it-entry.ts b/apps/ecosystem-certifier/fixtures/positive/linkify-it-entry.ts new file mode 100644 index 0000000..f6e07e2 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/linkify-it-entry.ts @@ -0,0 +1,10 @@ +import LinkifyIt from 'linkify-it'; + +const parser = new LinkifyIt(); +const value = Host.v1.document.get('text/markdown-case'); +const links = parser.match(value) ?? []; + +export default { + linkCount: links.length, + urls: links.map((item) => item.url), +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/lodash-es-entry.ts b/apps/ecosystem-certifier/fixtures/positive/lodash-es-entry.ts new file mode 100644 index 0000000..042daea --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/lodash-es-entry.ts @@ -0,0 +1,11 @@ +import sortBy from 'lodash-es/sortBy.js'; + +const findings = [ + { id: 'b', score: 2 }, + { id: 'a', score: 1 }, + { id: 'c', score: 2 }, +]; + +export default { + orderedIds: sortBy(findings, ['score', 'id']).map((item) => item.id), +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/markdown-it-entry.ts b/apps/ecosystem-certifier/fixtures/positive/markdown-it-entry.ts new file mode 100644 index 0000000..e728a47 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/markdown-it-entry.ts @@ -0,0 +1,14 @@ +import MarkdownIt from 'markdown-it'; + +const md = new MarkdownIt({ + linkify: true, +}); +const source = Host.v1.document.get('text/markdown-case'); +const tokens = md.parse(source, {}); +const links = md.render(source).match(/ token.type), + tokenCount: tokens.length, + linkCount: links, +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/path-to-regexp-entry.ts b/apps/ecosystem-certifier/fixtures/positive/path-to-regexp-entry.ts new file mode 100644 index 0000000..9ab2954 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/path-to-regexp-entry.ts @@ -0,0 +1,10 @@ +import { match } from 'path-to-regexp'; + +const pattern = Host.v1.document.get('text/path-case'); +const matcher = match(pattern); +const matched = matcher('/document/42/version/1.2.3'); + +export default { + matched: Boolean(matched), + params: matched?.params ?? null, +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/query-string-entry.ts b/apps/ecosystem-certifier/fixtures/positive/query-string-entry.ts new file mode 100644 index 0000000..e33341c --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/query-string-entry.ts @@ -0,0 +1,10 @@ +import queryString from 'query-string'; + +const query = 'profile=compat-general-v1&gasVersion=8&checks=parity&checks=oog'; +const parsed = queryString.parse(query); +const stringified = queryString.stringify(parsed, { arrayFormat: 'none' }); + +export default { + parsed, + stringified, +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/semver-entry.ts b/apps/ecosystem-certifier/fixtures/positive/semver-entry.ts new file mode 100644 index 0000000..e9aed02 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/semver-entry.ts @@ -0,0 +1,10 @@ +import { satisfies, valid } from 'semver'; + +const version = Host.v1.document.get('text/semver-case'); +const ranges = ['>=1.2.0 <2.0.0', '^1.2.0', '~1.2.3']; + +export default { + version, + valid: valid(version) !== null, + checks: ranges.map((range) => ({ range, ok: satisfies(version, range) })), +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/sort-keys-entry.ts b/apps/ecosystem-certifier/fixtures/positive/sort-keys-entry.ts new file mode 100644 index 0000000..4f6b88e --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/sort-keys-entry.ts @@ -0,0 +1,13 @@ +import sortKeys from 'sort-keys'; + +const payload = { + zeta: 4, + alpha: 1, + gamma: 3, + beta: 2, +}; + +export default { + sorted: sortKeys(payload), + keys: Object.keys(sortKeys(payload)), +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/spark-md5-entry.ts b/apps/ecosystem-certifier/fixtures/positive/spark-md5-entry.ts new file mode 100644 index 0000000..b469d5b --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/spark-md5-entry.ts @@ -0,0 +1,8 @@ +import SparkMD5 from 'spark-md5'; + +const payload = Host.v1.document.get('text/markdown-case'); + +export default { + digest: SparkMD5.hash(payload), + digestPrefix: SparkMD5.hash(payload).slice(0, 8), +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/stress-corpus-entry.ts b/apps/ecosystem-certifier/fixtures/positive/stress-corpus-entry.ts new file mode 100644 index 0000000..df77be7 --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/stress-corpus-entry.ts @@ -0,0 +1,18 @@ +import { satisfies } from 'semver'; +import corpus from '../../src/shared/fixtures/stress-corpus.generated.json'; + +const firstDoc = corpus.markdownDocs[0]?.id ?? null; +const semverPasses = corpus.semverChecks.filter((entry) => + satisfies(entry.version, entry.range), +).length; +const sortedNumeric = [...corpus.numericWork].sort((left, right) => left - right); + +export default { + seed: corpus.seed, + docs: corpus.markdownDocs.length, + firstDoc, + semverPasses, + numericMin: sortedNumeric[0], + numericMax: sortedNumeric[sortedNumeric.length - 1], + numericMedian: sortedNumeric[Math.floor(sortedNumeric.length / 2)], +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/tinyqueue-entry.ts b/apps/ecosystem-certifier/fixtures/positive/tinyqueue-entry.ts new file mode 100644 index 0000000..2acc40d --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/tinyqueue-entry.ts @@ -0,0 +1,15 @@ +import TinyQueue from 'tinyqueue'; + +const queue = new TinyQueue([], (left, right) => left.priority - right.priority); +queue.push({ id: 'b', priority: 2 }); +queue.push({ id: 'a', priority: 1 }); +queue.push({ id: 'c', priority: 3 }); + +const ordered = []; +while (queue.length > 0) { + ordered.push(queue.pop().id); +} + +export default { + ordered, +}; diff --git a/apps/ecosystem-certifier/fixtures/positive/yaml-entry.ts b/apps/ecosystem-certifier/fixtures/positive/yaml-entry.ts new file mode 100644 index 0000000..13844ff --- /dev/null +++ b/apps/ecosystem-certifier/fixtures/positive/yaml-entry.ts @@ -0,0 +1,10 @@ +import { parse } from 'yaml'; + +const text = Host.v1.document.get('text/yaml-case'); +const parsed = parse(text) as { name: string; value: number }; + +export default { + keys: Object.keys(parsed).sort(), + name: parsed.name, + value: parsed.value, +}; diff --git a/apps/ecosystem-certifier/index.html b/apps/ecosystem-certifier/index.html new file mode 100644 index 0000000..48310ff --- /dev/null +++ b/apps/ecosystem-certifier/index.html @@ -0,0 +1,12 @@ + + + + + + Ecosystem Certifier + + +
Loading ecosystem certifier…
+ + + diff --git a/apps/ecosystem-certifier/package.json b/apps/ecosystem-certifier/package.json new file mode 100644 index 0000000..681cb55 --- /dev/null +++ b/apps/ecosystem-certifier/package.json @@ -0,0 +1,65 @@ +{ + "name": "@blue-quickjs/ecosystem-certifier", + "version": "0.0.1", + "private": true, + "type": "module", + "dependencies": { + "@blue-quickjs/abi-manifest": "workspace:*", + "@blue-quickjs/deterministic-builder": "workspace:*", + "@blue-quickjs/dv": "workspace:*", + "@blue-quickjs/quickjs-runtime": "workspace:*", + "@blue-quickjs/quickjs-wasm": "workspace:*", + "@blue-quickjs/test-harness": "workspace:*", + "@noble/hashes": "^1.8.0", + "array-move": "^4.0.0", + "base64-js": "^1.5.1", + "camelcase": "^9.0.0", + "chess.js": "^1.4.0", + "crc-32": "^1.2.2", + "decamelize": "^6.0.1", + "deepmerge": "^4.3.1", + "diff": "^8.0.2", + "dijkstrajs": "^1.0.3", + "escape-string-regexp": "^5.0.0", + "fast-deep-equal": "^3.1.3", + "fast-json-stable-stringify": "^2.1.0", + "fastest-levenshtein": "^1.0.16", + "fflate": "^0.8.2", + "graphlib": "^2.1.8", + "he": "^1.2.0", + "json-logic-js": "^2.0.5", + "linkify-it": "^5.0.0", + "lodash-es": "^4.17.21", + "markdown-it": "^14.1.0", + "path-to-regexp": "^8.2.0", + "query-string": "^9.3.1", + "semver": "^7.7.3", + "sort-keys": "^6.0.0", + "spark-md5": "^3.0.2", + "tinyqueue": "^3.0.0", + "tslib": "^2.3.0", + "yaml": "^2.8.2" + }, + "nx": { + "name": "ecosystem-certifier", + "targets": { + "e2e": { + "dependsOn": [ + "^build" + ], + "executor": "nx:run-commands", + "options": { + "command": "pnpm playwright test apps/ecosystem-certifier/tests --config apps/ecosystem-certifier/playwright.config.cts", + "cwd": "." + } + }, + "certify": { + "executor": "nx:run-commands", + "options": { + "command": "node apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs", + "cwd": "." + } + } + } + } +} diff --git a/apps/ecosystem-certifier/playwright.config.cts b/apps/ecosystem-certifier/playwright.config.cts new file mode 100644 index 0000000..f6ba331 --- /dev/null +++ b/apps/ecosystem-certifier/playwright.config.cts @@ -0,0 +1,20 @@ +import { defineConfig } from '@playwright/test'; + +const projectRoot = __dirname; + +export default defineConfig({ + testDir: './tests', + fullyParallel: false, + timeout: 120000, + use: { + headless: true, + baseURL: 'http://localhost:4310', + }, + webServer: { + command: 'pnpm vite --host --port 4310 --config vite.config.mts', + cwd: projectRoot, + url: 'http://localhost:4310', + reuseExistingServer: !process.env.CI, + timeout: 120000, + }, +}); diff --git a/apps/ecosystem-certifier/scripts/_certifier-eval-helpers.mjs b/apps/ecosystem-certifier/scripts/_certifier-eval-helpers.mjs new file mode 100644 index 0000000..1c31da8 --- /dev/null +++ b/apps/ecosystem-certifier/scripts/_certifier-eval-helpers.mjs @@ -0,0 +1,192 @@ +import { chromium, firefox, webkit } from '@playwright/test'; +import { createHash } from 'node:crypto'; +import path from 'node:path'; +import { fileURLToPath } from 'node:url'; +import { createServer } from 'vite'; +import jiti from 'jiti'; + +const __dirname = path.dirname(fileURLToPath(import.meta.url)); +export const repoRoot = path.resolve(__dirname, '..', '..', '..'); +export const appRoot = path.resolve(repoRoot, 'apps/ecosystem-certifier'); +const require = jiti(import.meta.url, { interopDefault: true }); + +const { buildDeterministicModulePack, DeterministicBuilderError } = require( + '../../../libs/deterministic-builder/src/index.ts', +); +const { evaluate } = require('../../../libs/quickjs-runtime/src/index.ts'); +const { encodeDv } = require('../../../libs/dv/src/index.ts'); +const { serializeHostTape } = require('../../../libs/test-harness/src/index.ts'); +const { + CERTIFIER_FIXTURES, + manifestForFixture, +} = require('../src/shared/fixtures.ts'); +const { createCertificationHost } = require('../src/shared/host.ts'); + +export async function buildRunnableCasesByIds(ids) { + const fixtures = CERTIFIER_FIXTURES.filter( + (fixture) => ids.includes(fixture.id) && fixture.expect.stage === 'success', + ); + const cases = []; + for (const fixture of fixtures) { + try { + const built = await buildDeterministicModulePack({ + absWorkingDir: repoRoot, + entryPath: fixture.entryPath, + profile: fixture.profile, + emitProgramArtifact: true, + abiId: fixture.abiId, + abiVersion: fixture.abiVersion, + abiManifestHash: fixture.abiManifestHash, + }); + if (!built.programArtifact) { + throw new Error(`missing ProgramArtifact.v2 for ${fixture.id}`); + } + cases.push({ + id: fixture.id, + title: fixture.title, + kind: fixture.kind, + gasLimit: fixture.gasLimit.toString(), + manifest: manifestForFixture(fixture), + program: built.programArtifact, + }); + } catch (error) { + if (error instanceof DeterministicBuilderError) { + throw new Error( + `fixture ${fixture.id} unexpectedly failed builder compatibility: ${JSON.stringify( + error.diagnostics, + )}`, + ); + } + throw error; + } + } + return cases; +} + +export async function evaluateCaseNode(certCase, gasLimit) { + const host = createCertificationHost(); + const result = await evaluate({ + program: certCase.program, + input: { + event: { type: 'ecosystem-certifier' }, + eventCanonical: { type: 'ecosystem-certifier' }, + steps: [], + currentContract: { id: 'ecosystem-certifier' }, + currentContractCanonical: { id: { value: 'ecosystem-certifier' } }, + }, + gasLimit: BigInt(gasLimit ?? certCase.gasLimit), + manifest: certCase.manifest, + handlers: host.handlers, + tape: { capacity: 128 }, + }); + return snapshotFromEvaluateResult(result); +} + +export async function launchBrowserCertifier( + baseUrlOverride, + browserName = 'chromium', +) { + const viteServer = await createServer({ + configFile: path.join(appRoot, 'vite.config.mts'), + server: { + host: '127.0.0.1', + port: 4310, + strictPort: true, + }, + clearScreen: false, + }); + await viteServer.listen(); + + const baseUrl = baseUrlOverride ?? 'http://127.0.0.1:4310'; + const browserType = resolveBrowserType(browserName); + const browser = await browserType.launch({ headless: true }); + const context = await browser.newContext({ baseURL: baseUrl }); + const page = await context.newPage(); + await page.goto('/'); + await page.waitForFunction( + () => typeof window.__ECOSYSTEM_CERT_RUN_CASE__ === 'function', + undefined, + { + timeout: 120000, + }, + ); + + return { + async evaluateCaseSnapshot(certCase, gasLimit) { + return page.evaluate( + async ({ certCasePayload, gasLimitValue }) => { + if (!window.__ECOSYSTEM_CERT_RUN_CASE__) { + throw new Error('window.__ECOSYSTEM_CERT_RUN_CASE__ unavailable'); + } + return window.__ECOSYSTEM_CERT_RUN_CASE__( + certCasePayload, + gasLimitValue, + ); + }, + { certCasePayload: certCase, gasLimitValue: gasLimit ?? certCase.gasLimit }, + ); + }, + async close() { + await context.close(); + await browser.close(); + await viteServer.close(); + }, + }; +} + +export function snapshotFromEvaluateResult(result) { + const tape = result.tape ?? []; + if (result.ok) { + return { + stage: 'success', + resultHash: sha256Hex(Buffer.from(encodeDv(result.value))), + errorCode: null, + errorTag: null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: + tape.length > 0 + ? sha256Hex(Buffer.from(serializeHostTape(tape))) + : null, + tapeLength: tape.length, + }; + } + return { + stage: normalizeFailureStage(result.error.kind), + resultHash: null, + errorCode: result.error.code, + errorTag: 'tag' in result.error ? result.error.tag : null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: + tape.length > 0 ? sha256Hex(Buffer.from(serializeHostTape(tape))) : null, + tapeLength: tape.length, + }; +} + +export function sha256Hex(input) { + return createHash('sha256').update(input).digest('hex'); +} + +function normalizeFailureStage(kind) { + if (kind === 'module-pack') { + return 'artifact_validation'; + } + if (kind === 'execution-surface-mismatch') { + return 'pin_enforcement'; + } + return 'runtime_error'; +} + +function resolveBrowserType(browserName) { + if (browserName === 'chromium') { + return chromium; + } + if (browserName === 'firefox') { + return firefox; + } + if (browserName === 'webkit') { + return webkit; + } + throw new Error(`unsupported browser: ${browserName}`); +} diff --git a/apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs b/apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs new file mode 100644 index 0000000..058c988 --- /dev/null +++ b/apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs @@ -0,0 +1,396 @@ +#!/usr/bin/env node + +import { chromium, firefox, webkit } from '@playwright/test'; +import { createHash } from 'node:crypto'; +import { mkdir, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { fileURLToPath } from 'node:url'; +import { createServer } from 'vite'; +import jiti from 'jiti'; + +const __dirname = path.dirname(fileURLToPath(import.meta.url)); +const repoRoot = path.resolve(__dirname, '..', '..', '..'); +const appRoot = path.resolve(repoRoot, 'apps/ecosystem-certifier'); +const require = jiti(import.meta.url, { interopDefault: true }); + +const { buildDeterministicModulePack, DeterministicBuilderError } = require( + '../../../libs/deterministic-builder/src/index.ts', +); +const { evaluate } = require('../../../libs/quickjs-runtime/src/index.ts'); +const { encodeDv } = require('../../../libs/dv/src/index.ts'); +const { serializeHostTape } = require('../../../libs/test-harness/src/index.ts'); +const { + CERTIFIER_FIXTURES, + manifestForFixture, +} = require('../src/shared/fixtures.ts'); +const { createCertificationHost } = require('../src/shared/host.ts'); + +const args = parseArgs(process.argv.slice(2)); +const now = new Date(); +const timestamp = now.toISOString().replace(/[:.]/g, '-'); +const outDir = path.resolve(repoRoot, args.outDir); +const jsonPath = path.join(outDir, `workload-certification-${timestamp}.json`); +const mdPath = path.join(outDir, `workload-certification-${timestamp}.md`); +const checksumPath = `${jsonPath}.sha256`; +const matrixPath = path.join(outDir, `compatibility-matrix-${timestamp}.json`); + +await mkdir(outDir, { recursive: true }); + +const nodeRecords = []; +const browserCases = []; + +for (const fixture of CERTIFIER_FIXTURES) { + const manifest = manifestForFixture(fixture); + const entry = { + id: fixture.id, + title: fixture.title, + kind: fixture.kind, + profile: fixture.profile, + expected: fixture.expect, + node: null, + browser: null, + builder: { + ok: false, + diagnostics: [], + graphHash: null, + }, + }; + + try { + const built = await buildDeterministicModulePack({ + absWorkingDir: repoRoot, + entryPath: fixture.entryPath, + profile: fixture.profile, + emitProgramArtifact: true, + abiId: fixture.abiId, + abiVersion: fixture.abiVersion, + abiManifestHash: fixture.abiManifestHash, + }); + entry.builder = { + ok: true, + diagnostics: built.compatibility.diagnostics, + graphHash: built.modulePack.graphHash, + }; + + if (!built.programArtifact) { + throw new Error(`builder did not return ProgramArtifact.v2 (${fixture.id})`); + } + + const host = createCertificationHost(); + const nodeResult = await evaluate({ + program: built.programArtifact, + input: { + event: { type: 'ecosystem-certifier' }, + eventCanonical: { type: 'ecosystem-certifier' }, + steps: [], + currentContract: { id: 'ecosystem-certifier' }, + currentContractCanonical: { id: { value: 'ecosystem-certifier' } }, + }, + gasLimit: fixture.gasLimit, + manifest, + handlers: host.handlers, + tape: { capacity: 64 }, + }); + + entry.node = snapshotFromEvaluateResult(nodeResult); + browserCases.push({ + id: fixture.id, + title: fixture.title, + kind: fixture.kind, + gasLimit: fixture.gasLimit.toString(), + manifest, + program: built.programArtifact, + }); + } catch (error) { + if (error instanceof DeterministicBuilderError) { + entry.node = { + stage: 'builder_reject', + resultHash: null, + errorCode: null, + errorTag: null, + gasUsed: '0', + gasRemaining: fixture.gasLimit.toString(), + tapeHash: null, + tapeLength: 0, + }; + entry.builder = { + ok: false, + diagnostics: error.diagnostics, + graphHash: null, + }; + } else { + throw error; + } + } + + nodeRecords.push(entry); +} + +const browserSnapshotsById = await runBrowserCases( + browserCases, + args.baseUrl, + args.browser, +); + +for (const record of nodeRecords) { + record.browser = browserSnapshotsById.get(record.id) ?? null; + record.match = determineFixtureMatch(record); +} + +const mismatches = nodeRecords.filter((record) => !record.match); +const positiveRecords = nodeRecords.filter((record) => record.kind === 'positive'); +const negativeRecords = nodeRecords.filter((record) => record.kind === 'negative'); +const flagshipRecords = nodeRecords.filter((record) => record.kind === 'flagship'); +const compatibilityMatrix = nodeRecords.map((record) => ({ + id: record.id, + title: record.title, + kind: record.kind, + profile: record.profile, + expectedStage: record.expected.stage, + nodeStage: record.node?.stage ?? null, + browserStage: record.browser?.stage ?? null, + match: record.match, + diagnostics: record.builder?.diagnostics ?? [], +})); +const report = { + generatedAt: now.toISOString(), + browser: args.browser, + summary: { + total: nodeRecords.length, + withBrowserRuns: browserCases.length, + mismatches: mismatches.length, + greenCount: positiveRecords.length, + redCount: negativeRecords.length, + flagshipCount: flagshipRecords.length, + }, + compatibilityMatrix, + records: nodeRecords, + signature: { + algorithm: 'sha256', + digest: sha256Hex(JSON.stringify(nodeRecords)), + }, +}; + +const reportText = `${JSON.stringify(report, null, 2)}\n`; +await writeFile(jsonPath, reportText, 'utf8'); +await writeFile( + checksumPath, + `${sha256Hex(reportText)} ${path.basename(jsonPath)}\n`, + 'utf8', +); +await writeFile(mdPath, renderMarkdownReport(report), 'utf8'); +await writeFile( + matrixPath, + `${JSON.stringify( + { + generatedAt: now.toISOString(), + summary: report.summary, + compatibilityMatrix, + }, + null, + 2, + )}\n`, + 'utf8', +); + +console.log( + JSON.stringify( + { + jsonPath, + mdPath, + checksumPath, + matrixPath, + mismatches: mismatches.length, + }, + null, + 2, + ), +); + +if (mismatches.length > 0) { + process.exitCode = 1; +} + +function snapshotFromEvaluateResult(result) { + const tape = result.tape ?? []; + if (result.ok) { + return { + stage: 'success', + resultHash: sha256Hex(Buffer.from(encodeDv(result.value))), + errorCode: null, + errorTag: null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: + tape.length > 0 + ? sha256Hex(Buffer.from(serializeHostTape(tape))) + : null, + tapeLength: tape.length, + }; + } + + return { + stage: normalizeFailureStage(result.error.kind), + resultHash: null, + errorCode: result.error.code, + errorTag: 'tag' in result.error ? result.error.tag : null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: + tape.length > 0 ? sha256Hex(Buffer.from(serializeHostTape(tape))) : null, + tapeLength: tape.length, + }; +} + +function normalizeFailureStage(kind) { + if (kind === 'module-pack') { + return 'artifact_validation'; + } + if (kind === 'execution-surface-mismatch') { + return 'pin_enforcement'; + } + return 'runtime_error'; +} + +async function runBrowserCases(cases, baseUrlOverride, browserName) { + if (cases.length === 0) { + return new Map(); + } + + const viteServer = await createServer({ + configFile: path.join(appRoot, 'vite.config.mts'), + server: { + host: '127.0.0.1', + port: 4310, + strictPort: true, + }, + clearScreen: false, + }); + await viteServer.listen(); + + const baseUrl = baseUrlOverride ?? 'http://127.0.0.1:4310'; + const browserType = resolveBrowserType(browserName); + const browser = await browserType.launch({ headless: true }); + const context = await browser.newContext({ baseURL: baseUrl }); + + try { + const page = await context.newPage(); + await page.addInitScript((payload) => { + window.__ECOSYSTEM_CERT_CASES__ = payload; + }, cases); + await page.goto('/'); + await page.waitForSelector('[data-runstate="done"]', { timeout: 120000 }); + + const records = await page.evaluate(() => window.__ECOSYSTEM_CERT_RESULTS__ ?? []); + return new Map(records.map((record) => [record.id, record.browser])); + } finally { + await context.close(); + await browser.close(); + await viteServer.close(); + } +} + +function determineFixtureMatch(record) { + const expected = record.expected; + const node = record.node; + const browser = record.browser; + + if (expected.stage === 'builder_reject') { + return node.stage === 'builder_reject' && browser === null; + } + + if (expected.stage === 'success') { + return ( + node.stage === 'success' && + browser !== null && + JSON.stringify(node) === JSON.stringify(browser) + ); + } + + if (expected.stage === 'runtime_error') { + if (node.stage !== 'runtime_error' || browser === null) { + return false; + } + if (expected.errorCode && node.errorCode !== expected.errorCode) { + return false; + } + if (expected.errorTag && node.errorTag !== expected.errorTag) { + return false; + } + return JSON.stringify(node) === JSON.stringify(browser); + } + + return node.stage === expected.stage; +} + +function renderMarkdownReport(report) { + const lines = [ + '# Workload Certification Report (Generated)', + '', + `Generated: ${report.generatedAt}`, + '', + `- Total fixtures: ${report.summary.total}`, + `- Browser-evaluated fixtures: ${report.summary.withBrowserRuns}`, + `- Mismatches: ${report.summary.mismatches}`, + `- Green fixtures: ${report.summary.greenCount}`, + `- Red fixtures: ${report.summary.redCount}`, + '', + '| Fixture | Kind | Expected stage | Node stage | Browser stage | Match |', + '| --- | --- | --- | --- | --- | --- |', + ]; + + for (const record of report.records) { + lines.push( + `| ${record.id} | ${record.kind} | ${record.expected.stage} | ${record.node?.stage ?? 'n/a'} | ${record.browser?.stage ?? 'n/a'} | ${record.match ? 'yes' : 'no'} |`, + ); + } + + return `${lines.join('\n')}\n`; +} + +function parseArgs(argv) { + let outDir = 'artifacts/workload-certification'; + let baseUrl = null; + let browser = 'chromium'; + for (let i = 0; i < argv.length; i += 1) { + const arg = argv[i]; + if (arg === '--') { + continue; + } + if (arg === '--out-dir') { + outDir = argv[i + 1] ?? outDir; + i += 1; + continue; + } + if (arg === '--base-url') { + baseUrl = argv[i + 1] ?? baseUrl; + i += 1; + continue; + } + if (arg === '--browser') { + browser = argv[i + 1] ?? browser; + i += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { outDir, baseUrl, browser }; +} + +function sha256Hex(input) { + return createHash('sha256').update(input).digest('hex'); +} + +function resolveBrowserType(browserName) { + if (browserName === 'chromium') { + return chromium; + } + if (browserName === 'firefox') { + return firefox; + } + if (browserName === 'webkit') { + return webkit; + } + throw new Error(`unsupported browser: ${browserName}`); +} diff --git a/apps/ecosystem-certifier/scripts/check-builder-determinism.mjs b/apps/ecosystem-certifier/scripts/check-builder-determinism.mjs new file mode 100644 index 0000000..fce709e --- /dev/null +++ b/apps/ecosystem-certifier/scripts/check-builder-determinism.mjs @@ -0,0 +1,120 @@ +#!/usr/bin/env node + +import { createHash } from 'node:crypto'; +import fs from 'node:fs'; +import path from 'node:path'; +import { mkdir, writeFile } from 'node:fs/promises'; +import jiti from 'jiti'; +import { fileURLToPath } from 'node:url'; + +const __dirname = path.dirname(fileURLToPath(import.meta.url)); +const repoRoot = path.resolve(__dirname, '..', '..', '..'); +const require = jiti(import.meta.url, { interopDefault: true }); +const { buildDeterministicModulePack } = require( + '../../../libs/deterministic-builder/src/index.ts', +); +const { HOST_V1_HASH } = require('../../../libs/abi-manifest/src/index.ts'); + +const args = parseArgs(process.argv.slice(2)); +const outDir = path.resolve(repoRoot, args.outDir); +await mkdir(outDir, { recursive: true }); + +const fixtureSource = [ + "const values = [3, 1, 2];", + 'values.sort((a, b) => a - b);', + "export default {", + ' values,', + " joined: values.join(',')", + '};', + '', +].join('\n'); + +const tmpRoot = path.join(repoRoot, 'tmp', 'workload-certifier'); +await mkdir(tmpRoot, { recursive: true }); +const dirA = fs.mkdtempSync(path.join(tmpRoot, 'builder-det-a-')); +const dirB = fs.mkdtempSync(path.join(tmpRoot, 'builder-det-b-')); +await writeFixture(dirA, fixtureSource); +await writeFixture(dirB, fixtureSource); + +const builtA = await buildDeterministicModulePack({ + absWorkingDir: dirA, + entryPath: 'entry.ts', + profile: 'compat-general-v1', + emitProgramArtifact: true, + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, +}); +const builtB = await buildDeterministicModulePack({ + absWorkingDir: dirB, + entryPath: 'entry.ts', + profile: 'compat-general-v1', + emitProgramArtifact: true, + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, +}); + +const canonicalA = canonicalHash(builtA.modulePack); +const canonicalB = canonicalHash(builtB.modulePack); +const report = { + generatedAt: new Date().toISOString(), + fixtures: [ + { + workingDir: dirA, + graphHash: builtA.modulePack.graphHash, + canonicalHash: canonicalA, + moduleCount: builtA.modulePack.modules.length, + }, + { + workingDir: dirB, + graphHash: builtB.modulePack.graphHash, + canonicalHash: canonicalB, + moduleCount: builtB.modulePack.modules.length, + }, + ], + checks: { + graphHashEqual: builtA.modulePack.graphHash === builtB.modulePack.graphHash, + canonicalHashEqual: canonicalA === canonicalB, + }, +}; + +const outputPath = path.join(outDir, 'builder-determinism-report.json'); +await writeFile(outputPath, `${JSON.stringify(report, null, 2)}\n`, 'utf8'); + +console.log(JSON.stringify({ outputPath, checks: report.checks }, null, 2)); + +if (!report.checks.graphHashEqual || !report.checks.canonicalHashEqual) { + process.exitCode = 1; +} + +async function writeFixture(targetDir, source) { + await writeFile(path.join(targetDir, 'entry.ts'), source, 'utf8'); +} + +function canonicalHash(modulePack) { + const payload = JSON.stringify({ + entrySpecifier: modulePack.entrySpecifier, + entryExport: modulePack.entryExport, + modules: modulePack.modules.map((module) => ({ + specifier: module.specifier, + source: module.source, + sourceMap: module.sourceMap ?? null, + })), + }); + return createHash('sha256').update(payload).digest('hex'); +} + +function parseArgs(argv) { + let outDir = 'artifacts/workload-certification'; + for (let i = 0; i < argv.length; i += 1) { + const arg = argv[i]; + if (arg === '--out-dir') { + outDir = argv[i + 1] ?? outDir; + i += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { outDir }; +} diff --git a/apps/ecosystem-certifier/scripts/generate-compatibility-delta-report.mjs b/apps/ecosystem-certifier/scripts/generate-compatibility-delta-report.mjs new file mode 100644 index 0000000..3ee3f90 --- /dev/null +++ b/apps/ecosystem-certifier/scripts/generate-compatibility-delta-report.mjs @@ -0,0 +1,204 @@ +#!/usr/bin/env node + +import { mkdir, readFile, readdir, stat, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { fileURLToPath } from 'node:url'; + +const __dirname = path.dirname(fileURLToPath(import.meta.url)); +const repoRoot = path.resolve(__dirname, '..', '..', '..'); +const args = parseArgs(process.argv.slice(2)); +const currentDir = path.resolve(repoRoot, args.currentDir); +const outDir = path.resolve(repoRoot, args.outDir); +const baselinePath = path.resolve(repoRoot, args.baselinePath); + +await mkdir(outDir, { recursive: true }); + +const baseline = JSON.parse(await readFile(baselinePath, 'utf8')); +const currentReportPath = + args.currentReport ?? + (await findNewestFile(currentDir, (entry) => + /^workload-certification-.*\.json$/.test(entry.name), + )); +const currentReport = JSON.parse(await readFile(currentReportPath, 'utf8')); + +const baselineFixtures = new Map( + baseline.fixtures.map((fixture) => [fixture.id, fixture]), +); +const currentFixturesRaw = + currentReport.compatibilityMatrix ?? + currentReport.records?.map((record) => ({ + id: record.id, + kind: record.kind, + expectedStage: record.expected?.stage ?? null, + nodeStage: record.node?.stage ?? null, + browserStage: record.browser?.stage ?? null, + profile: record.profile ?? null, + })) ?? + []; +const currentFixtures = new Map( + currentFixturesRaw.map((fixture) => [fixture.id, fixture]), +); + +const added = []; +const removed = []; +const stageChanges = []; +const profileCounts = new Map(); + +for (const [id, current] of currentFixtures.entries()) { + if (!baselineFixtures.has(id)) { + added.push({ + id, + kind: current.kind, + expectedStage: current.expectedStage, + profile: current.profile ?? null, + }); + } else { + const previous = baselineFixtures.get(id); + if (previous.expectedStage !== current.expectedStage) { + stageChanges.push({ + id, + kind: current.kind, + from: previous.expectedStage, + to: current.expectedStage, + }); + } + } + if (current.kind === 'positive') { + const profile = current.profile ?? 'unknown'; + profileCounts.set(profile, (profileCounts.get(profile) ?? 0) + 1); + } +} + +for (const [id, previous] of baselineFixtures.entries()) { + if (!currentFixtures.has(id)) { + removed.push({ + id, + kind: previous.kind, + expectedStage: previous.expectedStage, + }); + } +} + +const currentSummary = currentReport.summary ?? { + greenCount: currentFixturesRaw.filter((fixture) => fixture.kind === 'positive') + .length, + redCount: currentFixturesRaw.filter((fixture) => fixture.kind === 'negative') + .length, + flagshipCount: currentFixturesRaw.filter((fixture) => fixture.kind === 'flagship') + .length, +}; + +const delta = { + generatedAt: new Date().toISOString(), + baseline: { + release: baseline.release ?? 'unknown', + path: path.relative(repoRoot, baselinePath), + summary: baseline.summary ?? null, + }, + current: { + reportPath: path.relative(repoRoot, currentReportPath), + summary: currentSummary, + }, + deltas: { + greenDelta: + (currentSummary.greenCount ?? 0) - (baseline.summary?.greenCount ?? 0), + redDelta: (currentSummary.redCount ?? 0) - (baseline.summary?.redCount ?? 0), + flagshipDelta: + (currentSummary.flagshipCount ?? 0) - (baseline.summary?.flagshipCount ?? 0), + }, + added, + removed, + stageChanges, + positiveProfileCounts: Object.fromEntries( + [...profileCounts.entries()].sort((left, right) => + left[0].localeCompare(right[0]), + ), + ), +}; + +const outputPath = path.join(outDir, 'compatibility-delta-report.json'); +await writeFile(outputPath, `${JSON.stringify(delta, null, 2)}\n`, 'utf8'); + +process.stdout.write( + `${JSON.stringify( + { + outputPath: path.relative(repoRoot, outputPath), + greenDelta: delta.deltas.greenDelta, + addedCount: added.length, + removedCount: removed.length, + }, + null, + 2, + )}\n`, +); + +async function findNewestFile(rootDir, predicate) { + const files = await walk(rootDir); + let latest = null; + for (const filePath of files) { + const entry = { name: path.basename(filePath), path: filePath }; + if (!predicate(entry)) { + continue; + } + const fileStat = await stat(filePath); + if (!latest || fileStat.mtimeMs > latest.mtimeMs) { + latest = { filePath, mtimeMs: fileStat.mtimeMs }; + } + } + if (!latest) { + throw new Error(`no current report files found under ${rootDir}`); + } + return latest.filePath; +} + +async function walk(dirPath) { + const entries = await readdir(dirPath, { withFileTypes: true }); + const files = []; + for (const entry of entries) { + const fullPath = path.join(dirPath, entry.name); + if (entry.isDirectory()) { + files.push(...(await walk(fullPath))); + } else { + files.push(fullPath); + } + } + return files; +} + +function parseArgs(argv) { + const parsed = { + currentDir: 'artifacts/workload-certification', + outDir: 'artifacts/workload-certification', + baselinePath: 'docs/ecosystem-compatibility-baseline-0.4.1.json', + currentReport: null, + }; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--current-dir') { + parsed.currentDir = argv[index + 1] ?? parsed.currentDir; + index += 1; + continue; + } + if (arg === '--out-dir') { + parsed.outDir = argv[index + 1] ?? parsed.outDir; + index += 1; + continue; + } + if (arg === '--baseline-path') { + parsed.baselinePath = argv[index + 1] ?? parsed.baselinePath; + index += 1; + continue; + } + if (arg === '--current-report') { + parsed.currentReport = argv[index + 1] ?? parsed.currentReport; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return parsed; +} diff --git a/apps/ecosystem-certifier/scripts/generate-stress-corpus.mjs b/apps/ecosystem-certifier/scripts/generate-stress-corpus.mjs new file mode 100644 index 0000000..45baa90 --- /dev/null +++ b/apps/ecosystem-certifier/scripts/generate-stress-corpus.mjs @@ -0,0 +1,66 @@ +#!/usr/bin/env node + +import { mkdir, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import { fileURLToPath } from 'node:url'; + +const __dirname = path.dirname(fileURLToPath(import.meta.url)); +const outputPath = path.resolve( + __dirname, + '../src/shared/fixtures/stress-corpus.generated.json', +); +const seed = 0x6d2b79f5; + +const rng = createXorShift(seed); +const markdownDocs = []; +const semverChecks = []; +const numericWork = []; + +for (let i = 0; i < 32; i += 1) { + const id = `doc-${i.toString().padStart(2, '0')}`; + const links = [ + `https://example.com/${Math.floor(rng() * 5000)}`, + `https://example.org/${Math.floor(rng() * 5000)}`, + ]; + markdownDocs.push({ + id, + markdown: `# ${id}\n\nLink A: ${links[0]}\n\nLink B: ${links[1]}\n`, + }); +} + +for (let i = 0; i < 128; i += 1) { + const major = 1 + Math.floor(rng() * 3); + const minor = Math.floor(rng() * 10); + const patch = Math.floor(rng() * 20); + const version = `${major}.${minor}.${patch}`; + semverChecks.push({ + version, + range: `>=${major}.${Math.max(0, minor - 1)}.0 <${major + 1}.0.0`, + }); +} + +for (let i = 0; i < 256; i += 1) { + numericWork.push(Math.floor(rng() * 100_000)); +} + +const payload = { + version: 1, + seed, + markdownDocs, + semverChecks, + numericWork, +}; + +await mkdir(path.dirname(outputPath), { recursive: true }); +await writeFile(outputPath, `${JSON.stringify(payload, null, 2)}\n`, 'utf8'); +console.log(JSON.stringify({ outputPath, docs: markdownDocs.length }, null, 2)); + +function createXorShift(initialSeed) { + let state = initialSeed >>> 0; + return () => { + state ^= state << 13; + state ^= state >>> 17; + state ^= state << 5; + return (state >>> 0) / 0xffffffff; + }; +} diff --git a/apps/ecosystem-certifier/scripts/run-oog-boundary-certification.mjs b/apps/ecosystem-certifier/scripts/run-oog-boundary-certification.mjs new file mode 100644 index 0000000..23d8d33 --- /dev/null +++ b/apps/ecosystem-certifier/scripts/run-oog-boundary-certification.mjs @@ -0,0 +1,158 @@ +#!/usr/bin/env node + +import { mkdir, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { + buildRunnableCasesByIds, + launchBrowserCertifier, + evaluateCaseNode, + repoRoot, +} from './_certifier-eval-helpers.mjs'; + +const args = parseArgs(process.argv.slice(2)); +const outDir = path.resolve(repoRoot, args.outDir); +await mkdir(outDir, { recursive: true }); + +const fixtureIds = args.fixtureIds ?? [ + 'flagship-knowledge-pack', + 'green-chess', + 'green-semver', + 'green-markdown-it', + 'green-stress-corpus', +]; + +const cases = await buildRunnableCasesByIds(fixtureIds); +const browser = await launchBrowserCertifier(args.baseUrl, args.browser); +const boundaries = []; + +try { + for (const certCase of cases) { + const maxGas = BigInt(certCase.gasLimit); + const nodeBoundary = await searchBoundary({ + low: 1n, + high: maxGas, + runSuccess: async (gasLimit) => { + const snapshot = await evaluateCaseNode(certCase, gasLimit.toString()); + return snapshot.stage === 'success'; + }, + }); + + const browserBoundary = await searchBoundary({ + low: 1n, + high: maxGas, + runSuccess: async (gasLimit) => { + const snapshot = await browser.evaluateCaseSnapshot( + certCase, + gasLimit.toString(), + ); + return snapshot.stage === 'success'; + }, + }); + + boundaries.push({ + id: certCase.id, + title: certCase.title, + node: { + firstSuccessGas: nodeBoundary.firstSuccessGas.toString(), + lastFailureGas: nodeBoundary.lastFailureGas.toString(), + }, + browser: { + firstSuccessGas: browserBoundary.firstSuccessGas.toString(), + lastFailureGas: browserBoundary.lastFailureGas.toString(), + }, + parity: { + firstSuccessEqual: + nodeBoundary.firstSuccessGas.toString() === + browserBoundary.firstSuccessGas.toString(), + lastFailureEqual: + nodeBoundary.lastFailureGas.toString() === + browserBoundary.lastFailureGas.toString(), + }, + }); + } +} finally { + await browser.close(); +} + +const mismatchCount = boundaries.filter( + (entry) => !entry.parity.firstSuccessEqual || !entry.parity.lastFailureEqual, +).length; +const output = { + generatedAt: new Date().toISOString(), + browser: args.browser, + fixtureCount: boundaries.length, + mismatchCount, + boundaries, +}; +const outputPath = path.join(outDir, 'oog-boundaries.json'); +await writeFile(outputPath, `${JSON.stringify(output, null, 2)}\n`, 'utf8'); + +console.log(JSON.stringify({ outputPath, mismatchCount }, null, 2)); +if (mismatchCount > 0) { + process.exitCode = 1; +} + +async function searchBoundary({ low, high, runSuccess }) { + let left = low; + let right = high; + const highSuccess = await runSuccess(right); + if (!highSuccess) { + throw new Error( + `upper bound ${high.toString()} failed; increase gas limit in fixture`, + ); + } + + while (left + 1n < right) { + const mid = (left + right) / 2n; + const ok = await runSuccess(mid); + if (ok) { + right = mid; + } else { + left = mid; + } + } + + return { + lastFailureGas: left, + firstSuccessGas: right, + }; +} + +function parseArgs(argv) { + let outDir = 'artifacts/workload-certification'; + let baseUrl = null; + let fixtureIds = null; + let browser = 'chromium'; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--out-dir') { + outDir = argv[index + 1] ?? outDir; + index += 1; + continue; + } + if (arg === '--base-url') { + baseUrl = argv[index + 1] ?? baseUrl; + index += 1; + continue; + } + if (arg === '--fixtures') { + fixtureIds = (argv[index + 1] ?? '') + .split(',') + .map((value) => value.trim()) + .filter(Boolean); + index += 1; + continue; + } + if (arg === '--browser') { + browser = argv[index + 1] ?? browser; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { outDir, baseUrl, fixtureIds, browser }; +} diff --git a/apps/ecosystem-certifier/scripts/run-repeatability-certification.mjs b/apps/ecosystem-certifier/scripts/run-repeatability-certification.mjs new file mode 100644 index 0000000..eac8598 --- /dev/null +++ b/apps/ecosystem-certifier/scripts/run-repeatability-certification.mjs @@ -0,0 +1,156 @@ +#!/usr/bin/env node + +import { mkdir, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { + buildRunnableCasesByIds, + evaluateCaseNode, + launchBrowserCertifier, + repoRoot, +} from './_certifier-eval-helpers.mjs'; + +const args = parseArgs(process.argv.slice(2)); +const outDir = path.resolve(repoRoot, args.outDir); +await mkdir(outDir, { recursive: true }); + +const fixtures = args.fixtureIds ?? [ + 'flagship-knowledge-pack', + 'green-semver', + 'green-markdown-it', + 'green-stress-corpus', +]; +const runnableCases = await buildRunnableCasesByIds(fixtures); +const browser = await launchBrowserCertifier(args.baseUrl, args.browser); + +const records = []; +try { + for (const certCase of runnableCases) { + const iterations = + certCase.id === 'flagship-knowledge-pack' + ? args.flagshipIterations + : args.iterations; + + const nodeBaseline = await evaluateCaseNode(certCase, certCase.gasLimit); + const browserBaseline = await browser.evaluateCaseSnapshot( + certCase, + certCase.gasLimit, + ); + + let nodeDriftCount = 0; + let browserDriftCount = 0; + let crossParityDriftCount = + JSON.stringify(nodeBaseline) === JSON.stringify(browserBaseline) ? 0 : 1; + + for (let run = 1; run < iterations; run += 1) { + const nodeSnapshot = await evaluateCaseNode(certCase, certCase.gasLimit); + const browserSnapshot = await browser.evaluateCaseSnapshot( + certCase, + certCase.gasLimit, + ); + if (JSON.stringify(nodeSnapshot) !== JSON.stringify(nodeBaseline)) { + nodeDriftCount += 1; + } + if (JSON.stringify(browserSnapshot) !== JSON.stringify(browserBaseline)) { + browserDriftCount += 1; + } + if (JSON.stringify(nodeSnapshot) !== JSON.stringify(browserSnapshot)) { + crossParityDriftCount += 1; + } + } + + records.push({ + id: certCase.id, + title: certCase.title, + iterations, + baseline: { + node: nodeBaseline, + browser: browserBaseline, + }, + drift: { + nodeDriftCount, + browserDriftCount, + crossParityDriftCount, + }, + stable: + nodeDriftCount === 0 && + browserDriftCount === 0 && + crossParityDriftCount === 0, + }); + } +} finally { + await browser.close(); +} + +const unstableCount = records.filter((record) => !record.stable).length; +const output = { + generatedAt: new Date().toISOString(), + browser: args.browser, + fixtureCount: records.length, + unstableCount, + records, +}; +const outputPath = path.join(outDir, 'repeatability-report.json'); +await writeFile(outputPath, `${JSON.stringify(output, null, 2)}\n`, 'utf8'); + +console.log(JSON.stringify({ outputPath, unstableCount }, null, 2)); +if (unstableCount > 0) { + process.exitCode = 1; +} + +function parseArgs(argv) { + let outDir = 'artifacts/workload-certification'; + let baseUrl = null; + let iterations = 100; + let flagshipIterations = 40; + let fixtureIds = null; + let browser = 'chromium'; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--out-dir') { + outDir = argv[index + 1] ?? outDir; + index += 1; + continue; + } + if (arg === '--base-url') { + baseUrl = argv[index + 1] ?? baseUrl; + index += 1; + continue; + } + if (arg === '--iterations') { + iterations = Number(argv[index + 1] ?? iterations); + index += 1; + continue; + } + if (arg === '--flagship-iterations') { + flagshipIterations = Number(argv[index + 1] ?? flagshipIterations); + index += 1; + continue; + } + if (arg === '--fixtures') { + fixtureIds = (argv[index + 1] ?? '') + .split(',') + .map((value) => value.trim()) + .filter(Boolean); + index += 1; + continue; + } + if (arg === '--browser') { + browser = argv[index + 1] ?? browser; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { + outDir, + baseUrl, + iterations, + flagshipIterations, + fixtureIds, + browser, + }; +} diff --git a/apps/ecosystem-certifier/scripts/run-seeded-property-corpus.mjs b/apps/ecosystem-certifier/scripts/run-seeded-property-corpus.mjs new file mode 100644 index 0000000..7b61665 --- /dev/null +++ b/apps/ecosystem-certifier/scripts/run-seeded-property-corpus.mjs @@ -0,0 +1,167 @@ +#!/usr/bin/env node + +import { mkdir, readFile, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import jiti from 'jiti'; +import { + launchBrowserCertifier, + repoRoot, + snapshotFromEvaluateResult, +} from './_certifier-eval-helpers.mjs'; + +const require = jiti(import.meta.url, { interopDefault: true }); +const { HOST_V1_HASH, HOST_V1_MANIFEST } = require( + '../../../libs/abi-manifest/src/index.ts', +); +const { evaluate } = require('../../../libs/quickjs-runtime/src/index.ts'); +const { createCertificationHost } = require('../src/shared/host.ts'); + +const propertySeedConfigPath = path.resolve( + repoRoot, + 'apps/ecosystem-certifier/src/shared/fixtures/property-seed-config.json', +); +const defaultConfig = JSON.parse(await readFile(propertySeedConfigPath, 'utf8')); + +const args = parseArgs(process.argv.slice(2)); +const outDir = path.resolve(repoRoot, args.outDir); +await mkdir(outDir, { recursive: true }); + +const browser = await launchBrowserCertifier(args.baseUrl, args.browser); +const records = []; + +try { + for (let seed = args.seedStart; seed < args.seedStart + args.seedCount; seed += 1) { + const certCase = createSeededCase(seed, args.gasLimit); + const host = createCertificationHost(); + const nodeResult = await evaluate({ + program: certCase.program, + input: { + event: { type: 'ecosystem-certifier' }, + eventCanonical: { type: 'ecosystem-certifier' }, + steps: [], + currentContract: { id: 'ecosystem-certifier' }, + currentContractCanonical: { id: { value: 'ecosystem-certifier' } }, + }, + gasLimit: BigInt(certCase.gasLimit), + manifest: HOST_V1_MANIFEST, + handlers: host.handlers, + tape: { capacity: 16 }, + }); + const nodeSnapshot = snapshotFromEvaluateResult(nodeResult); + const browserSnapshot = await browser.evaluateCaseSnapshot( + certCase, + certCase.gasLimit, + ); + const match = JSON.stringify(nodeSnapshot) === JSON.stringify(browserSnapshot); + records.push({ + seed, + node: nodeSnapshot, + browser: browserSnapshot, + match, + }); + } +} finally { + await browser.close(); +} + +const mismatchCount = records.filter((record) => !record.match).length; +const output = { + generatedAt: new Date().toISOString(), + browser: args.browser, + seedStart: args.seedStart, + seedCount: args.seedCount, + mismatchCount, + records, +}; +const outputPath = path.join(outDir, 'seeded-property-corpus-report.json'); +await writeFile(outputPath, `${JSON.stringify(output, null, 2)}\n`, 'utf8'); + +console.log(JSON.stringify({ outputPath, mismatchCount }, null, 2)); +if (mismatchCount > 0) { + process.exitCode = 1; +} + +function createSeededCase(seed, gasLimit) { + const code = [ + `let x = ${seed} >>> 0;`, + 'function rnd() {', + ' x = ((x * 1664525) + 1013904223) >>> 0;', + ' return x;', + '}', + 'const values = [];', + 'for (let i = 0; i < 64; i += 1) values.push(rnd() % 10000);', + 'values.sort((a, b) => a - b);', + '({', + ` seed: ${seed},`, + ' sum: values.reduce((total, value) => total + value, 0),', + ' min: values[0],', + ' max: values[values.length - 1],', + ' checksum: values[3] ^ values[15] ^ values[31] ^ values[63],', + '});', + ].join('\n'); + + return { + id: `seed-${seed}`, + title: `seed-${seed}`, + kind: 'positive', + gasLimit: String(gasLimit), + manifest: HOST_V1_MANIFEST, + program: { + version: 2, + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + executionProfile: 'compat-general-v1', + sourceKind: 'script', + source: { code }, + }, + }; +} + +function parseArgs(argv) { + let outDir = 'artifacts/workload-certification'; + let baseUrl = null; + let seedStart = defaultConfig.seedStart; + let seedCount = defaultConfig.seedCount; + let gasLimit = defaultConfig.gasLimit; + let browser = 'chromium'; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--out-dir') { + outDir = argv[index + 1] ?? outDir; + index += 1; + continue; + } + if (arg === '--base-url') { + baseUrl = argv[index + 1] ?? baseUrl; + index += 1; + continue; + } + if (arg === '--seed-start') { + seedStart = Number(argv[index + 1] ?? seedStart); + index += 1; + continue; + } + if (arg === '--seed-count') { + seedCount = Number(argv[index + 1] ?? seedCount); + index += 1; + continue; + } + if (arg === '--gas-limit') { + gasLimit = Number(argv[index + 1] ?? gasLimit); + index += 1; + continue; + } + if (arg === '--browser') { + browser = argv[index + 1] ?? browser; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { outDir, baseUrl, seedStart, seedCount, gasLimit, browser }; +} diff --git a/apps/ecosystem-certifier/src/browser/certifier.ts b/apps/ecosystem-certifier/src/browser/certifier.ts new file mode 100644 index 0000000..bcb9c0e --- /dev/null +++ b/apps/ecosystem-certifier/src/browser/certifier.ts @@ -0,0 +1,172 @@ +import { encodeDv } from '@blue-quickjs/dv'; +import { + type HostTapeRecord, + evaluate, + type EvaluateResult, +} from '@blue-quickjs/quickjs-runtime'; +import { serializeHostTape } from '@blue-quickjs/test-harness'; +import { createCertificationHost } from '../shared/host.js'; +import type { + BrowserEvaluationCase, + FailureStage, + FixtureParityRecord, + FixtureSnapshot, +} from '../shared/types.js'; + +declare global { + interface Window { + __ECOSYSTEM_CERT_CASES__?: BrowserEvaluationCase[]; + __ECOSYSTEM_CERT_RESULTS__?: FixtureParityRecord[]; + __ECOSYSTEM_CERT_RUNSTATE__?: 'idle' | 'running' | 'done' | 'error'; + __ECOSYSTEM_CERT_RUN_CASE__?: ( + certCase: BrowserEvaluationCase, + gasLimit?: string, + ) => Promise; + } +} + +export async function runBrowserCertifier(): Promise { + renderShell(); + const runstate = document.querySelector('[data-runstate]'); + const resultEl = document.querySelector('[data-results]'); + + try { + const cases = window.__ECOSYSTEM_CERT_CASES__ ?? []; + window.__ECOSYSTEM_CERT_RUN_CASE__ = evaluateCaseInBrowser; + window.__ECOSYSTEM_CERT_RUNSTATE__ = 'running'; + if (runstate) { + runstate.dataset.runstate = 'running'; + runstate.textContent = `Running ${cases.length} cases…`; + } + + const records: FixtureParityRecord[] = []; + for (const certCase of cases) { + const snapshot = await evaluateCaseInBrowser(certCase, certCase.gasLimit); + records.push({ + id: certCase.id, + title: certCase.title, + kind: certCase.kind, + node: snapshot, + browser: snapshot, + match: true, + }); + } + + window.__ECOSYSTEM_CERT_RESULTS__ = records; + window.__ECOSYSTEM_CERT_RUNSTATE__ = 'done'; + if (runstate) { + runstate.dataset.runstate = 'done'; + runstate.textContent = 'Done'; + } + if (resultEl) { + resultEl.textContent = JSON.stringify(records, null, 2); + } + } catch (error) { + const message = error instanceof Error ? error.message : String(error); + window.__ECOSYSTEM_CERT_RESULTS__ = []; + window.__ECOSYSTEM_CERT_RUNSTATE__ = 'error'; + if (runstate) { + runstate.dataset.runstate = 'error'; + runstate.textContent = `Error: ${message}`; + } + if (resultEl) { + resultEl.textContent = message; + } + } +} + +function renderShell(): void { + const app = document.querySelector('[data-app]'); + if (!app) { + return; + } + app.innerHTML = ` +

Ecosystem Certifier (Browser Runner)

+

Idle

+
Waiting…
+ `; +} + +async function toSnapshot(result: EvaluateResult): Promise { + const tape = result.tape ?? []; + const tapeHash = await hashTape(tape); + if (result.ok) { + return { + stage: 'success', + resultHash: await hashDv(result.value), + errorCode: null, + errorTag: null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash, + tapeLength: tape.length, + }; + } + + return { + stage: normalizeFailureStage(result.error.kind), + resultHash: null, + errorCode: result.error.code, + errorTag: 'tag' in result.error ? result.error.tag : null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash, + tapeLength: tape.length, + }; +} + +async function evaluateCaseInBrowser( + certCase: BrowserEvaluationCase, + gasLimit?: string, +): Promise { + const host = createCertificationHost(); + const result = await evaluate({ + program: certCase.program, + input: { + event: { type: 'ecosystem-certifier' }, + eventCanonical: { type: 'ecosystem-certifier' }, + steps: [], + currentContract: { id: 'ecosystem-certifier' }, + currentContractCanonical: { id: { value: 'ecosystem-certifier' } }, + }, + gasLimit: BigInt(gasLimit ?? certCase.gasLimit), + manifest: certCase.manifest, + handlers: host.handlers, + tape: { capacity: 64 }, + }); + return toSnapshot(result); +} + +function normalizeFailureStage(kind: string): FailureStage { + if (kind === 'module-pack') { + return 'artifact_validation'; + } + if (kind === 'execution-surface-mismatch') { + return 'pin_enforcement'; + } + return 'runtime_error'; +} + +async function hashDv(value: unknown): Promise { + return sha256Hex(encodeDv(value)); +} + +async function hashTape(tape: HostTapeRecord[]): Promise { + if (tape.length === 0) { + return null; + } + return sha256Hex(new TextEncoder().encode(serializeHostTape(tape))); +} + +async function sha256Hex(data: Uint8Array): Promise { + const digest = await crypto.subtle.digest('SHA-256', toArrayBuffer(data)); + const bytes = new Uint8Array(digest); + return [...bytes].map((byte) => byte.toString(16).padStart(2, '0')).join(''); +} + +function toArrayBuffer(data: Uint8Array): ArrayBuffer { + if (data.byteOffset === 0 && data.byteLength === data.buffer.byteLength) { + return data.buffer as ArrayBuffer; + } + return data.slice().buffer; +} diff --git a/apps/ecosystem-certifier/src/main.ts b/apps/ecosystem-certifier/src/main.ts new file mode 100644 index 0000000..7600e16 --- /dev/null +++ b/apps/ecosystem-certifier/src/main.ts @@ -0,0 +1,3 @@ +import { runBrowserCertifier } from './browser/certifier.js'; + +void runBrowserCertifier(); diff --git a/apps/ecosystem-certifier/src/shared/builder-determinism.spec.ts b/apps/ecosystem-certifier/src/shared/builder-determinism.spec.ts new file mode 100644 index 0000000..fa36128 --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/builder-determinism.spec.ts @@ -0,0 +1,25 @@ +import { compareBuilderReports } from './builder-determinism.js'; + +describe('builder determinism helpers', () => { + it('detects hash mismatches between reports', () => { + const result = compareBuilderReports( + { + checks: { graphHashEqual: true, canonicalHashEqual: true }, + fixtures: [ + { graphHash: 'a', canonicalHash: 'b' }, + { graphHash: 'c', canonicalHash: 'd' }, + ], + }, + { + checks: { graphHashEqual: false, canonicalHashEqual: false }, + fixtures: [ + { graphHash: 'a', canonicalHash: 'x' }, + { graphHash: 'z', canonicalHash: 'd' }, + ], + }, + ); + + expect(result.graphHashMismatchCount).toBe(1); + expect(result.canonicalHashMismatchCount).toBe(1); + }); +}); diff --git a/apps/ecosystem-certifier/src/shared/builder-determinism.ts b/apps/ecosystem-certifier/src/shared/builder-determinism.ts new file mode 100644 index 0000000..63fccdd --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/builder-determinism.ts @@ -0,0 +1,43 @@ +export interface BuilderDeterminismFixture { + graphHash: string; + canonicalHash: string; +} + +export interface BuilderDeterminismReport { + checks: { + graphHashEqual: boolean; + canonicalHashEqual: boolean; + }; + fixtures: BuilderDeterminismFixture[]; +} + +export function compareBuilderReports( + baseline: BuilderDeterminismReport, + candidate: BuilderDeterminismReport, +): { graphHashMismatchCount: number; canonicalHashMismatchCount: number } { + let graphHashMismatchCount = 0; + let canonicalHashMismatchCount = 0; + + const fixtureCount = Math.min( + baseline.fixtures.length, + candidate.fixtures.length, + ); + for (let index = 0; index < fixtureCount; index += 1) { + if ( + baseline.fixtures[index].graphHash !== candidate.fixtures[index].graphHash + ) { + graphHashMismatchCount += 1; + } + if ( + baseline.fixtures[index].canonicalHash !== + candidate.fixtures[index].canonicalHash + ) { + canonicalHashMismatchCount += 1; + } + } + + return { + graphHashMismatchCount, + canonicalHashMismatchCount, + }; +} diff --git a/apps/ecosystem-certifier/src/shared/fixtures.spec.ts b/apps/ecosystem-certifier/src/shared/fixtures.spec.ts new file mode 100644 index 0000000..f61b245 --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/fixtures.spec.ts @@ -0,0 +1,15 @@ +import { CERTIFIER_FIXTURES } from './fixtures.js'; + +describe('ecosystem certifier fixture catalog', () => { + it('includes flagship, positive, and negative fixtures', () => { + const kinds = new Set(CERTIFIER_FIXTURES.map((fixture) => fixture.kind)); + expect(kinds.has('flagship')).toBe(true); + expect(kinds.has('positive')).toBe(true); + expect(kinds.has('negative')).toBe(true); + }); + + it('uses unique ids', () => { + const ids = CERTIFIER_FIXTURES.map((fixture) => fixture.id); + expect(new Set(ids).size).toBe(ids.length); + }); +}); diff --git a/apps/ecosystem-certifier/src/shared/fixtures.ts b/apps/ecosystem-certifier/src/shared/fixtures.ts new file mode 100644 index 0000000..2225149 --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/fixtures.ts @@ -0,0 +1,438 @@ +import { + HOST_V1_HASH, + HOST_V1_MANIFEST, + HOST_V2_HASH, + HOST_V2_MANIFEST, +} from '@blue-quickjs/abi-manifest'; +import type { AbiManifest } from '@blue-quickjs/abi-manifest'; +import type { BuildFixtureDefinition } from './types.js'; + +export const CERTIFIER_FIXTURES: BuildFixtureDefinition[] = [ + { + id: 'flagship-knowledge-pack', + title: 'Flagship knowledge/compliance pack processor', + kind: 'flagship', + entryPath: 'apps/ecosystem-certifier/fixtures/flagship/knowledge-pack-entry.ts', + profile: 'compat-binary-v1', + abiId: 'Host.v2', + abiVersion: 2, + abiManifestHash: HOST_V2_HASH, + gasLimit: 8_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-chess', + title: 'chess.js deterministic move legality', + kind: 'positive', + entryPath: 'libs/test-harness/fixtures/library-reuse/chess-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 5_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-base64', + title: 'base64-js deterministic roundtrip', + kind: 'positive', + entryPath: 'libs/test-harness/fixtures/library-reuse/binary-base64-entry.ts', + profile: 'compat-binary-v1', + abiId: 'Host.v2', + abiVersion: 2, + abiManifestHash: HOST_V2_HASH, + gasLimit: 5_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-noble-sha', + title: '@noble/hashes deterministic digest', + kind: 'positive', + entryPath: 'libs/test-harness/fixtures/library-reuse/binary-sha256-entry.ts', + profile: 'compat-binary-v1', + abiId: 'Host.v2', + abiVersion: 2, + abiManifestHash: HOST_V2_HASH, + gasLimit: 5_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-semver', + title: 'semver constraint evaluation', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/semver-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-he', + title: 'he deterministic HTML entity decode', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/he-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-path-to-regexp', + title: 'path-to-regexp deterministic path match', + kind: 'positive', + entryPath: + 'apps/ecosystem-certifier/fixtures/positive/path-to-regexp-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-fast-json-stable-stringify', + title: 'fast-json-stable-stringify canonical output', + kind: 'positive', + entryPath: + 'apps/ecosystem-certifier/fixtures/positive/fast-json-stable-stringify-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-json-logic-js', + title: 'json-logic-js deterministic rule application', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/json-logic-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-crc32', + title: 'crc-32 deterministic checksum calculation', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/crc32-entry.ts', + profile: 'compat-binary-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-tinyqueue', + title: 'tinyqueue deterministic priority ordering', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/tinyqueue-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-fflate', + title: 'fflate deterministic compression roundtrip', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/fflate-entry.ts', + profile: 'compat-binary-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 5_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-linkify-it', + title: 'linkify-it deterministic URL extraction', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/linkify-it-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-markdown-it', + title: 'markdown-it deterministic tokenization', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/markdown-it-entry.ts', + profile: 'compat-binary-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-escape-string-regexp', + title: 'escape-string-regexp deterministic escaping', + kind: 'positive', + entryPath: + 'apps/ecosystem-certifier/fixtures/positive/escape-string-regexp-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-fast-deep-equal', + title: 'fast-deep-equal deterministic structure comparison', + kind: 'positive', + entryPath: + 'apps/ecosystem-certifier/fixtures/positive/fast-deep-equal-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-stress-corpus', + title: 'seeded stress corpus deterministic summary', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/stress-corpus-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-camelcase', + title: 'camelcase deterministic normalization', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/camelcase-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-decamelize', + title: 'decamelize deterministic token splitting', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/decamelize-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-fastest-levenshtein', + title: 'fastest-levenshtein deterministic edit distance', + kind: 'positive', + entryPath: + 'apps/ecosystem-certifier/fixtures/positive/fastest-levenshtein-entry.ts', + profile: 'compat-binary-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-dijkstrajs', + title: 'dijkstrajs deterministic shortest path', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/dijkstrajs-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-spark-md5', + title: 'spark-md5 deterministic hash digest', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/spark-md5-entry.ts', + profile: 'compat-binary-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-query-string', + title: 'query-string deterministic parse/stringify', + kind: 'positive', + entryPath: + 'apps/ecosystem-certifier/fixtures/positive/query-string-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-deepmerge', + title: 'deepmerge deterministic object merge', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/deepmerge-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-sort-keys', + title: 'sort-keys deterministic object ordering', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/sort-keys-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'green-array-move', + title: 'array-move deterministic list reordering', + kind: 'positive', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/array-move-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'success' }, + }, + { + id: 'red-diff-timers', + title: 'diff package timer references are deterministically rejected', + kind: 'negative', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/diff-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'builder_reject' }, + }, + { + id: 'red-yaml-date', + title: 'yaml package date usage is deterministically rejected', + kind: 'negative', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/yaml-entry.ts', + profile: 'compat-binary-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'builder_reject' }, + }, + { + id: 'red-graphlib-proxy', + title: 'graphlib proxy usage is deterministically rejected', + kind: 'negative', + entryPath: 'apps/ecosystem-certifier/fixtures/negative/graphlib-entry.ts', + profile: 'compat-binary-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'builder_reject' }, + }, + { + id: 'red-dynamic-import', + title: 'dynamic import must be rejected at build stage', + kind: 'negative', + entryPath: 'apps/ecosystem-certifier/fixtures/negative/dynamic-import-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'builder_reject' }, + }, + { + id: 'red-proxy', + title: 'Proxy usage must be rejected at build stage', + kind: 'negative', + entryPath: 'apps/ecosystem-certifier/fixtures/negative/proxy-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'builder_reject' }, + }, + { + id: 'red-math-random', + title: 'Math.random usage must be rejected at build stage', + kind: 'negative', + entryPath: 'apps/ecosystem-certifier/fixtures/negative/math-random-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { stage: 'builder_reject' }, + }, + { + id: 'red-lodash-function-constructor', + title: 'lodash-es root detection hits Function constructor in runtime', + kind: 'negative', + entryPath: 'apps/ecosystem-certifier/fixtures/positive/lodash-es-entry.ts', + profile: 'compat-binary-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { + stage: 'artifact_validation', + errorCode: 'MODULE_EXPORT_MISSING', + errorTag: 'vm/module_pack', + }, + }, + { + id: 'red-function-constructor', + title: 'Function constructor must fail deterministically in module-pack flow', + kind: 'negative', + entryPath: + 'apps/ecosystem-certifier/fixtures/negative/function-constructor-entry.ts', + profile: 'compat-general-v1', + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + gasLimit: 1_000_000n, + expect: { + stage: 'artifact_validation', + errorCode: 'MODULE_EXPORT_MISSING', + errorTag: 'vm/module_pack', + }, + }, +]; + +export function manifestForFixture(fixture: BuildFixtureDefinition): AbiManifest { + return fixture.abiId === 'Host.v2' ? HOST_V2_MANIFEST : HOST_V1_MANIFEST; +} diff --git a/apps/ecosystem-certifier/src/shared/fixtures/compat-negative.ts b/apps/ecosystem-certifier/src/shared/fixtures/compat-negative.ts new file mode 100644 index 0000000..5bf5035 --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/fixtures/compat-negative.ts @@ -0,0 +1,5 @@ +import { CERTIFIER_FIXTURES } from '../fixtures.js'; + +export const NEGATIVE_COMPAT_FIXTURES = CERTIFIER_FIXTURES.filter( + (fixture) => fixture.kind === 'negative', +); diff --git a/apps/ecosystem-certifier/src/shared/fixtures/compat-positive.ts b/apps/ecosystem-certifier/src/shared/fixtures/compat-positive.ts new file mode 100644 index 0000000..8a53e02 --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/fixtures/compat-positive.ts @@ -0,0 +1,5 @@ +import { CERTIFIER_FIXTURES } from '../fixtures.js'; + +export const POSITIVE_COMPAT_FIXTURES = CERTIFIER_FIXTURES.filter( + (fixture) => fixture.kind === 'positive', +); diff --git a/apps/ecosystem-certifier/src/shared/fixtures/flagship-pack.ts b/apps/ecosystem-certifier/src/shared/fixtures/flagship-pack.ts new file mode 100644 index 0000000..e15c5cb --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/fixtures/flagship-pack.ts @@ -0,0 +1,7 @@ +import { CERTIFIER_FIXTURES } from '../fixtures.js'; + +export const FLAGSHIP_FIXTURE_IDS = ['flagship-knowledge-pack'] as const; + +export const FLAGSHIP_FIXTURES = CERTIFIER_FIXTURES.filter((fixture) => + FLAGSHIP_FIXTURE_IDS.includes(fixture.id as (typeof FLAGSHIP_FIXTURE_IDS)[number]), +); diff --git a/apps/ecosystem-certifier/src/shared/fixtures/property-seed-config.json b/apps/ecosystem-certifier/src/shared/fixtures/property-seed-config.json new file mode 100644 index 0000000..6631adb --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/fixtures/property-seed-config.json @@ -0,0 +1,5 @@ +{ + "seedStart": 1, + "seedCount": 80, + "gasLimit": 600000 +} diff --git a/apps/ecosystem-certifier/src/shared/fixtures/stress-corpus.generated.json b/apps/ecosystem-certifier/src/shared/fixtures/stress-corpus.generated.json new file mode 100644 index 0000000..10127fa --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/fixtures/stress-corpus.generated.json @@ -0,0 +1,906 @@ +{ + "version": 1, + "seed": 1831565813, + "markdownDocs": [ + { + "id": "doc-00", + "markdown": "# doc-00\n\nLink A: https://example.com/1263\n\nLink B: https://example.org/2849\n" + }, + { + "id": "doc-01", + "markdown": "# doc-01\n\nLink A: https://example.com/3048\n\nLink B: https://example.org/1981\n" + }, + { + "id": "doc-02", + "markdown": "# doc-02\n\nLink A: https://example.com/308\n\nLink B: https://example.org/1199\n" + }, + { + "id": "doc-03", + "markdown": "# doc-03\n\nLink A: https://example.com/4670\n\nLink B: https://example.org/2422\n" + }, + { + "id": "doc-04", + "markdown": "# doc-04\n\nLink A: https://example.com/4871\n\nLink B: https://example.org/268\n" + }, + { + "id": "doc-05", + "markdown": "# doc-05\n\nLink A: https://example.com/3122\n\nLink B: https://example.org/1237\n" + }, + { + "id": "doc-06", + "markdown": "# doc-06\n\nLink A: https://example.com/2945\n\nLink B: https://example.org/1419\n" + }, + { + "id": "doc-07", + "markdown": "# doc-07\n\nLink A: https://example.com/4503\n\nLink B: https://example.org/1560\n" + }, + { + "id": "doc-08", + "markdown": "# doc-08\n\nLink A: https://example.com/3780\n\nLink B: https://example.org/2057\n" + }, + { + "id": "doc-09", + "markdown": "# doc-09\n\nLink A: https://example.com/4650\n\nLink B: https://example.org/2696\n" + }, + { + "id": "doc-10", + "markdown": "# doc-10\n\nLink A: https://example.com/2844\n\nLink B: https://example.org/692\n" + }, + { + "id": "doc-11", + "markdown": "# doc-11\n\nLink A: https://example.com/3343\n\nLink B: https://example.org/3032\n" + }, + { + "id": "doc-12", + "markdown": "# doc-12\n\nLink A: https://example.com/4271\n\nLink B: https://example.org/2407\n" + }, + { + "id": "doc-13", + "markdown": "# doc-13\n\nLink A: https://example.com/2243\n\nLink B: https://example.org/1918\n" + }, + { + "id": "doc-14", + "markdown": "# doc-14\n\nLink A: https://example.com/2271\n\nLink B: https://example.org/2538\n" + }, + { + "id": "doc-15", + "markdown": "# doc-15\n\nLink A: https://example.com/3324\n\nLink B: https://example.org/1767\n" + }, + { + "id": "doc-16", + "markdown": "# doc-16\n\nLink A: https://example.com/3532\n\nLink B: https://example.org/2534\n" + }, + { + "id": "doc-17", + "markdown": "# doc-17\n\nLink A: https://example.com/4887\n\nLink B: https://example.org/651\n" + }, + { + "id": "doc-18", + "markdown": "# doc-18\n\nLink A: https://example.com/279\n\nLink B: https://example.org/555\n" + }, + { + "id": "doc-19", + "markdown": "# doc-19\n\nLink A: https://example.com/3411\n\nLink B: https://example.org/3593\n" + }, + { + "id": "doc-20", + "markdown": "# doc-20\n\nLink A: https://example.com/4237\n\nLink B: https://example.org/3182\n" + }, + { + "id": "doc-21", + "markdown": "# doc-21\n\nLink A: https://example.com/360\n\nLink B: https://example.org/2483\n" + }, + { + "id": "doc-22", + "markdown": "# doc-22\n\nLink A: https://example.com/307\n\nLink B: https://example.org/1260\n" + }, + { + "id": "doc-23", + "markdown": "# doc-23\n\nLink A: https://example.com/3394\n\nLink B: https://example.org/2456\n" + }, + { + "id": "doc-24", + "markdown": "# doc-24\n\nLink A: https://example.com/3304\n\nLink B: https://example.org/191\n" + }, + { + "id": "doc-25", + "markdown": "# doc-25\n\nLink A: https://example.com/1370\n\nLink B: https://example.org/675\n" + }, + { + "id": "doc-26", + "markdown": "# doc-26\n\nLink A: https://example.com/3934\n\nLink B: https://example.org/3646\n" + }, + { + "id": "doc-27", + "markdown": "# doc-27\n\nLink A: https://example.com/1102\n\nLink B: https://example.org/84\n" + }, + { + "id": "doc-28", + "markdown": "# doc-28\n\nLink A: https://example.com/2013\n\nLink B: https://example.org/1018\n" + }, + { + "id": "doc-29", + "markdown": "# doc-29\n\nLink A: https://example.com/2449\n\nLink B: https://example.org/2095\n" + }, + { + "id": "doc-30", + "markdown": "# doc-30\n\nLink A: https://example.com/4050\n\nLink B: https://example.org/1412\n" + }, + { + "id": "doc-31", + "markdown": "# doc-31\n\nLink A: https://example.com/4586\n\nLink B: https://example.org/2470\n" + } + ], + "semverChecks": [ + { + "version": "2.8.11", + "range": ">=2.7.0 <3.0.0" + }, + { + "version": "3.9.4", + "range": ">=3.8.0 <4.0.0" + }, + { + "version": "3.3.17", + "range": ">=3.2.0 <4.0.0" + }, + { + "version": "2.6.11", + "range": ">=2.5.0 <3.0.0" + }, + { + "version": "2.3.5", + "range": ">=2.2.0 <3.0.0" + }, + { + "version": "1.2.4", + "range": ">=1.1.0 <2.0.0" + }, + { + "version": "2.0.7", + "range": ">=2.0.0 <3.0.0" + }, + { + "version": "2.3.4", + "range": ">=2.2.0 <3.0.0" + }, + { + "version": "2.7.12", + "range": ">=2.6.0 <3.0.0" + }, + { + "version": "2.0.3", + "range": ">=2.0.0 <3.0.0" + }, + { + "version": "2.8.2", + "range": ">=2.7.0 <3.0.0" + }, + { + "version": "1.7.8", + "range": ">=1.6.0 <2.0.0" + }, + { + "version": "1.0.4", + "range": ">=1.0.0 <2.0.0" + }, + { + "version": "1.1.15", + "range": ">=1.0.0 <2.0.0" + }, + { + "version": "2.9.11", + "range": ">=2.8.0 <3.0.0" + }, + { + "version": "2.0.10", + "range": ">=2.0.0 <3.0.0" + }, + { + "version": "1.8.6", + "range": ">=1.7.0 <2.0.0" + }, + { + "version": "2.6.11", + "range": ">=2.5.0 <3.0.0" + }, + { + "version": "3.7.16", + "range": ">=3.6.0 <4.0.0" + }, + { + "version": "3.7.5", + "range": ">=3.6.0 <4.0.0" + }, + { + "version": "1.4.8", + "range": ">=1.3.0 <2.0.0" + }, + { + "version": "3.5.0", + "range": ">=3.4.0 <4.0.0" + }, + { + "version": "3.4.15", + "range": ">=3.3.0 <4.0.0" + }, + { + "version": "3.3.16", + "range": ">=3.2.0 <4.0.0" + }, + { + "version": "3.9.16", + "range": ">=3.8.0 <4.0.0" + }, + { + "version": "2.6.3", + "range": ">=2.5.0 <3.0.0" + }, + { + "version": "3.0.6", + "range": ">=3.0.0 <4.0.0" + }, + { + "version": "2.5.8", + "range": ">=2.4.0 <3.0.0" + }, + { + "version": "2.3.17", + "range": ">=2.2.0 <3.0.0" + }, + { + "version": "1.2.11", + "range": ">=1.1.0 <2.0.0" + }, + { + "version": "3.9.17", + "range": ">=3.8.0 <4.0.0" + }, + { + "version": "2.2.5", + "range": ">=2.1.0 <3.0.0" + }, + { + "version": "3.6.14", + "range": ">=3.5.0 <4.0.0" + }, + { + "version": "2.6.15", + "range": ">=2.5.0 <3.0.0" + }, + { + "version": "3.3.10", + "range": ">=3.2.0 <4.0.0" + }, + { + "version": "3.4.4", + "range": ">=3.3.0 <4.0.0" + }, + { + "version": "1.2.16", + "range": ">=1.1.0 <2.0.0" + }, + { + "version": "3.7.17", + "range": ">=3.6.0 <4.0.0" + }, + { + "version": "2.4.8", + "range": ">=2.3.0 <3.0.0" + }, + { + "version": "2.1.10", + "range": ">=2.0.0 <3.0.0" + }, + { + "version": "3.0.10", + "range": ">=3.0.0 <4.0.0" + }, + { + "version": "2.7.1", + "range": ">=2.6.0 <3.0.0" + }, + { + "version": "1.8.5", + "range": ">=1.7.0 <2.0.0" + }, + { + "version": "3.6.15", + "range": ">=3.5.0 <4.0.0" + }, + { + "version": "3.9.5", + "range": ">=3.8.0 <4.0.0" + }, + { + "version": "3.6.12", + "range": ">=3.5.0 <4.0.0" + }, + { + "version": "3.3.4", + "range": ">=3.2.0 <4.0.0" + }, + { + "version": "3.6.1", + "range": ">=3.5.0 <4.0.0" + }, + { + "version": "2.4.19", + "range": ">=2.3.0 <3.0.0" + }, + { + "version": "2.7.15", + "range": ">=2.6.0 <3.0.0" + }, + { + "version": "1.7.4", + "range": ">=1.6.0 <2.0.0" + }, + { + "version": "3.1.2", + "range": ">=3.0.0 <4.0.0" + }, + { + "version": "3.3.4", + "range": ">=3.2.0 <4.0.0" + }, + { + "version": "2.2.0", + "range": ">=2.1.0 <3.0.0" + }, + { + "version": "3.1.7", + "range": ">=3.0.0 <4.0.0" + }, + { + "version": "2.4.8", + "range": ">=2.3.0 <3.0.0" + }, + { + "version": "3.0.2", + "range": ">=3.0.0 <4.0.0" + }, + { + "version": "1.9.17", + "range": ">=1.8.0 <2.0.0" + }, + { + "version": "1.1.3", + "range": ">=1.0.0 <2.0.0" + }, + { + "version": "3.9.10", + "range": ">=3.8.0 <4.0.0" + }, + { + "version": "3.2.17", + "range": ">=3.1.0 <4.0.0" + }, + { + "version": "2.0.6", + "range": ">=2.0.0 <3.0.0" + }, + { + "version": "2.0.6", + "range": ">=2.0.0 <3.0.0" + }, + { + "version": "3.7.12", + "range": ">=3.6.0 <4.0.0" + }, + { + "version": "2.4.17", + "range": ">=2.3.0 <3.0.0" + }, + { + "version": "2.6.15", + "range": ">=2.5.0 <3.0.0" + }, + { + "version": "2.5.4", + "range": ">=2.4.0 <3.0.0" + }, + { + "version": "3.1.2", + "range": ">=3.0.0 <4.0.0" + }, + { + "version": "1.3.14", + "range": ">=1.2.0 <2.0.0" + }, + { + "version": "1.2.17", + "range": ">=1.1.0 <2.0.0" + }, + { + "version": "1.5.14", + "range": ">=1.4.0 <2.0.0" + }, + { + "version": "1.2.7", + "range": ">=1.1.0 <2.0.0" + }, + { + "version": "3.1.16", + "range": ">=3.0.0 <4.0.0" + }, + { + "version": "3.4.16", + "range": ">=3.3.0 <4.0.0" + }, + { + "version": "2.2.14", + "range": ">=2.1.0 <3.0.0" + }, + { + "version": "3.2.0", + "range": ">=3.1.0 <4.0.0" + }, + { + "version": "2.3.6", + "range": ">=2.2.0 <3.0.0" + }, + { + "version": "1.8.8", + "range": ">=1.7.0 <2.0.0" + }, + { + "version": "3.1.3", + "range": ">=3.0.0 <4.0.0" + }, + { + "version": "3.5.1", + "range": ">=3.4.0 <4.0.0" + }, + { + "version": "2.2.16", + "range": ">=2.1.0 <3.0.0" + }, + { + "version": "1.0.13", + "range": ">=1.0.0 <2.0.0" + }, + { + "version": "3.4.14", + "range": ">=3.3.0 <4.0.0" + }, + { + "version": "1.6.10", + "range": ">=1.5.0 <2.0.0" + }, + { + "version": "2.4.17", + "range": ">=2.3.0 <3.0.0" + }, + { + "version": "3.2.3", + "range": ">=3.1.0 <4.0.0" + }, + { + "version": "1.0.12", + "range": ">=1.0.0 <2.0.0" + }, + { + "version": "1.3.18", + "range": ">=1.2.0 <2.0.0" + }, + { + "version": "2.6.7", + "range": ">=2.5.0 <3.0.0" + }, + { + "version": "3.0.16", + "range": ">=3.0.0 <4.0.0" + }, + { + "version": "1.3.15", + "range": ">=1.2.0 <2.0.0" + }, + { + "version": "3.5.13", + "range": ">=3.4.0 <4.0.0" + }, + { + "version": "2.6.18", + "range": ">=2.5.0 <3.0.0" + }, + { + "version": "3.1.19", + "range": ">=3.0.0 <4.0.0" + }, + { + "version": "2.7.6", + "range": ">=2.6.0 <3.0.0" + }, + { + "version": "1.2.11", + "range": ">=1.1.0 <2.0.0" + }, + { + "version": "3.1.7", + "range": ">=3.0.0 <4.0.0" + }, + { + "version": "2.2.1", + "range": ">=2.1.0 <3.0.0" + }, + { + "version": "2.1.10", + "range": ">=2.0.0 <3.0.0" + }, + { + "version": "3.5.4", + "range": ">=3.4.0 <4.0.0" + }, + { + "version": "2.3.18", + "range": ">=2.2.0 <3.0.0" + }, + { + "version": "1.3.3", + "range": ">=1.2.0 <2.0.0" + }, + { + "version": "1.3.7", + "range": ">=1.2.0 <2.0.0" + }, + { + "version": "2.6.1", + "range": ">=2.5.0 <3.0.0" + }, + { + "version": "3.8.19", + "range": ">=3.7.0 <4.0.0" + }, + { + "version": "1.3.4", + "range": ">=1.2.0 <2.0.0" + }, + { + "version": "1.7.9", + "range": ">=1.6.0 <2.0.0" + }, + { + "version": "1.3.14", + "range": ">=1.2.0 <2.0.0" + }, + { + "version": "1.8.7", + "range": ">=1.7.0 <2.0.0" + }, + { + "version": "1.7.13", + "range": ">=1.6.0 <2.0.0" + }, + { + "version": "2.5.5", + "range": ">=2.4.0 <3.0.0" + }, + { + "version": "1.6.5", + "range": ">=1.5.0 <2.0.0" + }, + { + "version": "3.2.18", + "range": ">=3.1.0 <4.0.0" + }, + { + "version": "3.8.19", + "range": ">=3.7.0 <4.0.0" + }, + { + "version": "1.3.17", + "range": ">=1.2.0 <2.0.0" + }, + { + "version": "3.1.12", + "range": ">=3.0.0 <4.0.0" + }, + { + "version": "1.9.13", + "range": ">=1.8.0 <2.0.0" + }, + { + "version": "1.0.11", + "range": ">=1.0.0 <2.0.0" + }, + { + "version": "2.0.11", + "range": ">=2.0.0 <3.0.0" + }, + { + "version": "3.7.10", + "range": ">=3.6.0 <4.0.0" + }, + { + "version": "3.4.14", + "range": ">=3.3.0 <4.0.0" + }, + { + "version": "2.4.2", + "range": ">=2.3.0 <3.0.0" + }, + { + "version": "2.4.5", + "range": ">=2.3.0 <3.0.0" + }, + { + "version": "3.3.4", + "range": ">=3.2.0 <4.0.0" + }, + { + "version": "1.2.1", + "range": ">=1.1.0 <2.0.0" + }, + { + "version": "1.7.13", + "range": ">=1.6.0 <2.0.0" + }, + { + "version": "1.2.6", + "range": ">=1.1.0 <2.0.0" + }, + { + "version": "1.1.11", + "range": ">=1.0.0 <2.0.0" + } + ], + "numericWork": [ + 39309, + 60365, + 65130, + 42142, + 32870, + 19040, + 53421, + 73865, + 84996, + 77736, + 5585, + 43615, + 19396, + 75590, + 53132, + 68868, + 44246, + 1375, + 11879, + 45060, + 66024, + 22345, + 48441, + 63408, + 9616, + 92799, + 97113, + 97702, + 18434, + 88550, + 58302, + 55808, + 92846, + 41344, + 37284, + 83724, + 89336, + 86919, + 79987, + 56379, + 68293, + 53775, + 83343, + 92029, + 41088, + 85696, + 80202, + 6242, + 13100, + 27307, + 78277, + 30924, + 62257, + 79002, + 43045, + 81102, + 74109, + 26329, + 49762, + 47999, + 92846, + 7898, + 74703, + 58188, + 99053, + 74438, + 77158, + 94565, + 97089, + 3160, + 79508, + 84479, + 22151, + 49703, + 92816, + 13619, + 7078, + 75158, + 51663, + 37295, + 36944, + 56627, + 36479, + 25408, + 62494, + 73687, + 71676, + 49802, + 80373, + 42036, + 11314, + 97490, + 22764, + 33342, + 75380, + 67775, + 24169, + 1159, + 73385, + 45404, + 10892, + 1109, + 60139, + 20339, + 2304, + 51989, + 68625, + 39464, + 6910, + 11047, + 33819, + 31473, + 23110, + 17189, + 58967, + 9687, + 21284, + 40872, + 28039, + 84079, + 87651, + 86698, + 73074, + 98008, + 26761, + 29686, + 16970, + 30861, + 85869, + 39788, + 10523, + 45378, + 89050, + 3712, + 17703, + 1947, + 48827, + 6975, + 12574, + 66119, + 24832, + 24082, + 15427, + 54665, + 14107, + 48852, + 52152, + 25672, + 89553, + 29049, + 27585, + 71881, + 11712, + 36032, + 49294, + 77952, + 8880, + 95433, + 84607, + 34689, + 36712, + 76276, + 52491, + 93196, + 80984, + 88348, + 46222, + 99710, + 87258, + 22467, + 63078, + 17328, + 63799, + 45013, + 21209, + 78754, + 21924, + 55402, + 54574, + 20733, + 53934, + 72667, + 69174, + 30221, + 92183, + 78796, + 15769, + 26946, + 77650, + 13310, + 97718, + 63170, + 93201, + 32580, + 22618, + 33399, + 78012, + 69297, + 18456, + 21644, + 84949, + 68497, + 45990, + 60813, + 22737, + 66620, + 39826, + 33767, + 32347, + 57207, + 63391, + 90264, + 19988, + 55143, + 6202, + 74038, + 54329, + 64319, + 86702, + 98139, + 97628, + 65731, + 28850, + 68795, + 20438, + 88167, + 31627, + 46741, + 30131, + 85602, + 28717, + 74013, + 31003, + 32529, + 73656, + 87341, + 71866, + 23622, + 97014, + 5580, + 31513, + 55708, + 7357, + 15114, + 32040, + 31710, + 7200, + 48347, + 42327, + 65096, + 12526, + 58349, + 2143, + 76932, + 83642, + 34408 + ] +} diff --git a/apps/ecosystem-certifier/src/shared/hash.ts b/apps/ecosystem-certifier/src/shared/hash.ts new file mode 100644 index 0000000..60ac6e9 --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/hash.ts @@ -0,0 +1,21 @@ +import { createHash } from 'node:crypto'; +import { encodeDv } from '@blue-quickjs/dv'; +import { serializeHostTape } from '@blue-quickjs/test-harness'; +import type { HostTapeRecord } from '@blue-quickjs/quickjs-runtime'; + +export function sha256Hex(input: Uint8Array | string): string { + const bytes = + typeof input === 'string' ? new TextEncoder().encode(input) : input; + return createHash('sha256').update(bytes).digest('hex'); +} + +export function hashDv(value: unknown): string { + return sha256Hex(encodeDv(value)); +} + +export function hashTape(tape: HostTapeRecord[]): string | null { + if (tape.length === 0) { + return null; + } + return sha256Hex(serializeHostTape(tape)); +} diff --git a/apps/ecosystem-certifier/src/shared/host.ts b/apps/ecosystem-certifier/src/shared/host.ts new file mode 100644 index 0000000..7064dff --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/host.ts @@ -0,0 +1,164 @@ +import type { + HostDispatcherHandlers, + HostCallResult, +} from '@blue-quickjs/quickjs-runtime'; + +const TEXT_DOCUMENTS = new Map([ + [ + 'pack/metadata.json', + JSON.stringify( + { + packId: 'kp-2026-rc', + release: '1.2.3', + requires: ['>=1.2.0 <2.0.0', '^1.2.0'], + links: ['docs/a.md', 'docs/b.md', 'docs/c.md', 'docs/d.md'], + }, + null, + 2, + ), + ], + [ + 'pack/metadata.yaml', + [ + 'packId: kp-2026-rc', + 'release: 1.2.3', + 'requires:', + ' - ">=1.2.0 <2.0.0"', + ' - "^1.2.0"', + 'links:', + ' - docs/a.md', + ' - docs/b.md', + '', + ].join('\n'), + ], + [ + 'docs/a.md', + [ + '# Alpha', + '', + 'See [Beta](docs/b.md), [Gamma](docs/c.md), and https://example.com/path.', + '', + 'Encoded value: & deterministic.', + '', + 'Paragraph: Deterministic workloads should remain stable across', + 'wasm-node and wasm-browser executors.', + '', + ].join('\n'), + ], + [ + 'docs/b.md', + [ + '# Beta', + '', + 'Backlink to [Alpha](docs/a.md) and [Delta](docs/d.md).', + '', + 'Extra URL: https://example.net/release-notes.', + '', + ].join('\n'), + ], + [ + 'docs/c.md', + [ + '# Gamma', + '', + 'Cross-link to [Delta](docs/d.md).', + '', + 'Reference URL: https://example.org/matrix.', + '', + ].join('\n'), + ], + [ + 'docs/d.md', + [ + '# Delta', + '', + 'Back to [Alpha](docs/a.md) and [Beta](docs/b.md).', + '', + 'Reference URL: https://example.dev/consensus.', + '', + ].join('\n'), + ], + [ + 'rules/findings.json', + JSON.stringify( + { + and: [ + { '>=': [{ var: 'linkCount' }, 8] }, + { '==': [{ var: 'releaseOk' }, true] }, + ], + }, + null, + 2, + ), + ], + ['text/semver-case', '1.2.3'], + ['text/path-case', '/document/:id/version/:version'], + ['text/yaml-case', 'name: Blue\nvalue: 42\n'], + ['text/markdown-case', '# Heading\n\nA [link](https://example.com).\n'], + ['text/he-case', '<b>safe</b>'], + ['text/diff-left', 'alpha\nbeta\ngamma\n'], + ['text/diff-right', 'alpha\nbeta2\ngamma\n'], + ['text/json-logic-case', JSON.stringify({ score: 7, threshold: 5 })], +]); + +const BINARY_DOCUMENTS = new Map([ + [ + 'bytes/payload', + Uint8Array.from(Array.from({ length: 64 }, (_, index) => (index * 17) % 251)), + ], + [ + 'bytes/flagship-extra', + Uint8Array.from( + Array.from({ length: 192 }, (_, index) => ((index * 29) + 11) % 251), + ), + ], + [ + 'pack/attachment.deflated', + Uint8Array.from([ + 120, 156, 179, 73, 77, 206, 79, 73, 45, 86, 112, 46, 41, 202, 204, 75, + 87, 72, 206, 207, 43, 73, 45, 2, 0, 101, 57, 8, 181, + ]), + ], +]); + +export function createCertificationHost(): { + handlers: HostDispatcherHandlers; + emitted: unknown[]; +} { + const emitted: unknown[] = []; + + const handlers: HostDispatcherHandlers = { + document: { + get: (docPath: string): HostCallResult => { + if (BINARY_DOCUMENTS.has(docPath)) { + return { ok: BINARY_DOCUMENTS.get(docPath)!, units: 6 }; + } + if (TEXT_DOCUMENTS.has(docPath)) { + return { ok: TEXT_DOCUMENTS.get(docPath)!, units: 2 }; + } + return { + err: { code: 'NOT_FOUND', tag: 'host/not_found' }, + units: 1, + }; + }, + getCanonical: (docPath: string): HostCallResult => { + if (TEXT_DOCUMENTS.has(docPath)) { + return { ok: TEXT_DOCUMENTS.get(docPath)!, units: 2 }; + } + if (BINARY_DOCUMENTS.has(docPath)) { + return { ok: BINARY_DOCUMENTS.get(docPath)!, units: 6 }; + } + return { + err: { code: 'NOT_FOUND', tag: 'host/not_found' }, + units: 1, + }; + }, + }, + emit: (value: unknown) => { + emitted.push(value); + return { ok: null, units: 1 }; + }, + }; + + return { handlers, emitted }; +} diff --git a/apps/ecosystem-certifier/src/shared/oog-boundary.spec.ts b/apps/ecosystem-certifier/src/shared/oog-boundary.spec.ts new file mode 100644 index 0000000..9adbe5a --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/oog-boundary.spec.ts @@ -0,0 +1,22 @@ +import { compareBoundaries, searchOogBoundary } from './oog-boundary.js'; + +describe('OOG boundary search', () => { + it('finds exact boundary with binary search', async () => { + const boundary = await searchOogBoundary({ + low: 1n, + high: 200n, + runSuccess: async (gasLimit) => gasLimit >= 77n, + }); + expect(boundary.lastFailureGas).toBe(76n); + expect(boundary.firstSuccessGas).toBe(77n); + }); + + it('compares boundaries', () => { + const parity = compareBoundaries( + { lastFailureGas: 76n, firstSuccessGas: 77n }, + { lastFailureGas: 76n, firstSuccessGas: 77n }, + ); + expect(parity.firstSuccessEqual).toBe(true); + expect(parity.lastFailureEqual).toBe(true); + }); +}); diff --git a/apps/ecosystem-certifier/src/shared/oog-boundary.ts b/apps/ecosystem-certifier/src/shared/oog-boundary.ts new file mode 100644 index 0000000..affd64d --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/oog-boundary.ts @@ -0,0 +1,44 @@ +export interface OogBoundary { + lastFailureGas: bigint; + firstSuccessGas: bigint; +} + +export async function searchOogBoundary(options: { + low: bigint; + high: bigint; + runSuccess: (gasLimit: bigint) => Promise; +}): Promise { + let left = options.low; + let right = options.high; + const highSuccess = await options.runSuccess(right); + if (!highSuccess) { + throw new Error( + `upper gas bound ${right.toString()} did not succeed during OOG boundary search`, + ); + } + + while (left + 1n < right) { + const mid = (left + right) / 2n; + const success = await options.runSuccess(mid); + if (success) { + right = mid; + } else { + left = mid; + } + } + + return { + lastFailureGas: left, + firstSuccessGas: right, + }; +} + +export function compareBoundaries( + node: OogBoundary, + browser: OogBoundary, +): { firstSuccessEqual: boolean; lastFailureEqual: boolean } { + return { + firstSuccessEqual: node.firstSuccessGas === browser.firstSuccessGas, + lastFailureEqual: node.lastFailureGas === browser.lastFailureGas, + }; +} diff --git a/apps/ecosystem-certifier/src/shared/parity.spec.ts b/apps/ecosystem-certifier/src/shared/parity.spec.ts new file mode 100644 index 0000000..c2847d5 --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/parity.spec.ts @@ -0,0 +1,30 @@ +import type { FixtureSnapshot } from './types.js'; +import { compareSnapshots, isStrictParity } from './parity.js'; + +describe('parity helpers', () => { + const snapshot: FixtureSnapshot = { + stage: 'success', + resultHash: 'abc', + errorCode: null, + errorTag: null, + gasUsed: '10', + gasRemaining: '90', + tapeHash: 'def', + tapeLength: 1, + }; + + it('returns strict parity for equal snapshots', () => { + const parity = compareSnapshots(snapshot, { ...snapshot }); + expect(isStrictParity(parity)).toBe(true); + }); + + it('returns parity mismatch for different gas', () => { + const parity = compareSnapshots(snapshot, { + ...snapshot, + gasUsed: '11', + gasRemaining: '89', + }); + expect(isStrictParity(parity)).toBe(false); + expect(parity.gasUsedEqual).toBe(false); + }); +}); diff --git a/apps/ecosystem-certifier/src/shared/parity.ts b/apps/ecosystem-certifier/src/shared/parity.ts new file mode 100644 index 0000000..9ecab02 --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/parity.ts @@ -0,0 +1,54 @@ +import type { FixtureSnapshot } from './types.js'; + +export interface SnapshotParity { + stageEqual: boolean; + resultHashEqual: boolean; + errorCodeEqual: boolean; + errorTagEqual: boolean; + gasUsedEqual: boolean; + gasRemainingEqual: boolean; + tapeHashEqual: boolean; + tapeLengthEqual: boolean; +} + +export function compareSnapshots( + node: FixtureSnapshot, + browser: FixtureSnapshot | null, +): SnapshotParity { + if (!browser) { + return { + stageEqual: false, + resultHashEqual: false, + errorCodeEqual: false, + errorTagEqual: false, + gasUsedEqual: false, + gasRemainingEqual: false, + tapeHashEqual: false, + tapeLengthEqual: false, + }; + } + + return { + stageEqual: node.stage === browser.stage, + resultHashEqual: node.resultHash === browser.resultHash, + errorCodeEqual: node.errorCode === browser.errorCode, + errorTagEqual: node.errorTag === browser.errorTag, + gasUsedEqual: node.gasUsed === browser.gasUsed, + gasRemainingEqual: node.gasRemaining === browser.gasRemaining, + tapeHashEqual: node.tapeHash === browser.tapeHash, + tapeLengthEqual: node.tapeLength === browser.tapeLength, + }; +} + +export function isStrictParity(parity: SnapshotParity): boolean { + return ( + parity.stageEqual && + parity.resultHashEqual && + parity.errorCodeEqual && + parity.errorTagEqual && + parity.gasUsedEqual && + parity.gasRemainingEqual && + parity.tapeHashEqual && + parity.tapeLengthEqual + ); +} diff --git a/apps/ecosystem-certifier/src/shared/repeatability.spec.ts b/apps/ecosystem-certifier/src/shared/repeatability.spec.ts new file mode 100644 index 0000000..d5683a7 --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/repeatability.spec.ts @@ -0,0 +1,23 @@ +import type { FixtureSnapshot } from './types.js'; +import { runRepeatability } from './repeatability.js'; + +describe('repeatability helper', () => { + it('reports zero drift for stable snapshots', async () => { + const snapshot: FixtureSnapshot = { + stage: 'success', + resultHash: 'stable', + errorCode: null, + errorTag: null, + gasUsed: '10', + gasRemaining: '90', + tapeHash: null, + tapeLength: 0, + }; + const result = await runRepeatability({ + iterations: 5, + runSnapshot: async () => ({ ...snapshot }), + }); + expect(result.driftCount).toBe(0); + expect(result.totalRuns).toBe(5); + }); +}); diff --git a/apps/ecosystem-certifier/src/shared/repeatability.ts b/apps/ecosystem-certifier/src/shared/repeatability.ts new file mode 100644 index 0000000..9d9de8e --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/repeatability.ts @@ -0,0 +1,33 @@ +import type { FixtureSnapshot } from './types.js'; + +export interface RepeatabilityResult { + baseline: FixtureSnapshot; + driftCount: number; + totalRuns: number; +} + +export async function runRepeatability(options: { + iterations: number; + runSnapshot: () => Promise; +}): Promise { + if (options.iterations < 1) { + throw new Error('repeatability iterations must be >= 1'); + } + + const baseline = await options.runSnapshot(); + let driftCount = 0; + const baselineJson = JSON.stringify(baseline); + + for (let index = 1; index < options.iterations; index += 1) { + const snapshot = await options.runSnapshot(); + if (JSON.stringify(snapshot) !== baselineJson) { + driftCount += 1; + } + } + + return { + baseline, + driftCount, + totalRuns: options.iterations, + }; +} diff --git a/apps/ecosystem-certifier/src/shared/types.ts b/apps/ecosystem-certifier/src/shared/types.ts new file mode 100644 index 0000000..279935d --- /dev/null +++ b/apps/ecosystem-certifier/src/shared/types.ts @@ -0,0 +1,76 @@ +import type { AbiManifest } from '@blue-quickjs/abi-manifest'; +import type { ProgramArtifactV2 } from '@blue-quickjs/quickjs-runtime'; + +export type FixtureKind = 'flagship' | 'positive' | 'negative'; + +export type FailureStage = + | 'builder_reject' + | 'artifact_validation' + | 'runtime_error' + | 'pin_enforcement'; + +export interface BuildFixtureDefinition { + id: string; + title: string; + kind: FixtureKind; + entryPath: string; + profile: + | 'baseline-v1' + | 'compat-regexp-v1' + | 'compat-general-v1' + | 'compat-binary-v1'; + abiId: 'Host.v1' | 'Host.v2'; + abiVersion: 1 | 2; + abiManifestHash: string; + gasLimit: bigint; + expect: + | { + stage: 'success'; + } + | { + stage: FailureStage; + errorCode?: string; + errorTag?: string; + }; +} + +export interface BrowserEvaluationCase { + id: string; + title: string; + kind: FixtureKind; + gasLimit: string; + manifest: AbiManifest; + program: ProgramArtifactV2; +} + +export interface FixtureSnapshot { + stage: 'success' | FailureStage; + resultHash: string | null; + errorCode: string | null; + errorTag: string | null; + gasUsed: string; + gasRemaining: string; + tapeHash: string | null; + tapeLength: number; +} + +export interface FixtureParityRecord { + id: string; + title: string; + kind: FixtureKind; + node: FixtureSnapshot; + browser: FixtureSnapshot | null; + match: boolean; +} + +export interface CertificationReport { + generatedAt: string; + summary: { + total: number; + withBrowserRuns: number; + mismatches: number; + greenCount: number; + redCount: number; + }; + records: FixtureParityRecord[]; +} diff --git a/apps/ecosystem-certifier/src/typings.d.ts b/apps/ecosystem-certifier/src/typings.d.ts new file mode 100644 index 0000000..861dae0 --- /dev/null +++ b/apps/ecosystem-certifier/src/typings.d.ts @@ -0,0 +1,15 @@ +import type { BrowserEvaluationCase, FixtureParityRecord } from './shared/types.js'; + +declare global { + interface Window { + __ECOSYSTEM_CERT_CASES__?: BrowserEvaluationCase[]; + __ECOSYSTEM_CERT_RESULTS__?: FixtureParityRecord[]; + __ECOSYSTEM_CERT_RUNSTATE__?: 'idle' | 'running' | 'done' | 'error'; + __ECOSYSTEM_CERT_RUN_CASE__?: ( + certCase: BrowserEvaluationCase, + gasLimit?: string, + ) => Promise; + } +} + +export {}; diff --git a/apps/ecosystem-certifier/tests/builder-determinism.spec.ts b/apps/ecosystem-certifier/tests/builder-determinism.spec.ts new file mode 100644 index 0000000..bcfca52 --- /dev/null +++ b/apps/ecosystem-certifier/tests/builder-determinism.spec.ts @@ -0,0 +1,31 @@ +import { execFile } from 'node:child_process'; +import { readFile } from 'node:fs/promises'; +import path from 'node:path'; +import { promisify } from 'node:util'; +import { expect, test } from '@playwright/test'; +import type { BuilderDeterminismReport } from '../src/shared/builder-determinism.js'; + +const execFileAsync = promisify(execFile); + +test('builder path determinism script reports stable hashes', async () => { + const outDir = path.join( + process.cwd(), + 'artifacts', + 'workload-certification-test', + `builder-${Date.now()}`, + ); + await execFileAsync('node', [ + 'apps/ecosystem-certifier/scripts/check-builder-determinism.mjs', + '--out-dir', + outDir, + ]); + + const reportPath = path.join(outDir, 'builder-determinism-report.json'); + const report = JSON.parse( + await readFile(reportPath, 'utf8'), + ) as BuilderDeterminismReport; + + expect(report.checks.graphHashEqual).toBe(true); + expect(report.checks.canonicalHashEqual).toBe(true); + expect(report.fixtures).toHaveLength(2); +}); diff --git a/apps/ecosystem-certifier/tests/certifier.spec.ts b/apps/ecosystem-certifier/tests/certifier.spec.ts new file mode 100644 index 0000000..5899b79 --- /dev/null +++ b/apps/ecosystem-certifier/tests/certifier.spec.ts @@ -0,0 +1,38 @@ +import { HOST_V1_HASH, HOST_V1_MANIFEST } from '@blue-quickjs/abi-manifest'; +import { expect, test } from '@playwright/test'; + +test('browser certifier executes injected evaluation cases', async ({ page }) => { + const cases = [ + { + id: 'sample-script-case', + title: 'sample script', + kind: 'positive', + gasLimit: '100000', + manifest: HOST_V1_MANIFEST, + program: { + version: 2, + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + executionProfile: 'baseline-v1', + sourceKind: 'script', + source: { + code: '42', + }, + }, + }, + ]; + + await page.addInitScript((payload) => { + window.__ECOSYSTEM_CERT_CASES__ = payload; + }, cases); + + await page.goto('/'); + await page.waitForSelector('[data-runstate="done"]', { timeout: 60000 }); + + const results = await page.evaluate(() => window.__ECOSYSTEM_CERT_RESULTS__ ?? []); + expect(results).toHaveLength(1); + expect(results[0].id).toBe('sample-script-case'); + expect(results[0].browser.stage).toBe('success'); + expect(results[0].browser.errorCode).toBeNull(); +}); diff --git a/apps/ecosystem-certifier/tests/fixture-helpers.ts b/apps/ecosystem-certifier/tests/fixture-helpers.ts new file mode 100644 index 0000000..db8145d --- /dev/null +++ b/apps/ecosystem-certifier/tests/fixture-helpers.ts @@ -0,0 +1,144 @@ +import type { Page } from '@playwright/test'; +import { + type BuildDeterministicModulePackResult, + buildDeterministicModulePack, +} from '@blue-quickjs/deterministic-builder'; +import { evaluate } from '@blue-quickjs/quickjs-runtime'; +import { + type BrowserEvaluationCase, + type BuildFixtureDefinition, + type FailureStage, + type FixtureSnapshot, +} from '../src/shared/types.js'; +import { CERTIFIER_FIXTURES, manifestForFixture } from '../src/shared/fixtures.js'; +import { createCertificationHost } from '../src/shared/host.js'; +import { hashDv, hashTape } from '../src/shared/hash.js'; + +const INPUT = { + event: { type: 'ecosystem-certifier' }, + eventCanonical: { type: 'ecosystem-certifier' }, + steps: [], + currentContract: { id: 'ecosystem-certifier' }, + currentContractCanonical: { id: { value: 'ecosystem-certifier' } }, +}; + +export function getFixtureById(id: string): BuildFixtureDefinition { + const fixture = CERTIFIER_FIXTURES.find((item) => item.id === id); + if (!fixture) { + throw new Error(`fixture not found: ${id}`); + } + return fixture; +} + +export async function buildCaseByFixtureId( + id: string, +): Promise { + const fixture = getFixtureById(id); + const built = await buildDeterministicModulePack({ + absWorkingDir: process.cwd(), + entryPath: fixture.entryPath, + profile: fixture.profile, + emitProgramArtifact: true, + abiId: fixture.abiId, + abiVersion: fixture.abiVersion, + abiManifestHash: fixture.abiManifestHash, + }); + return toBrowserCase(fixture, built); +} + +export async function runNodeSnapshot( + certCase: BrowserEvaluationCase, + gasLimit?: string, +): Promise { + const host = createCertificationHost(); + const result = await evaluate({ + program: certCase.program, + input: INPUT, + gasLimit: BigInt(gasLimit ?? certCase.gasLimit), + manifest: certCase.manifest, + handlers: host.handlers, + tape: { capacity: 64 }, + }); + const tape = result.tape ?? []; + if (result.ok) { + return { + stage: 'success', + resultHash: hashDv(result.value), + errorCode: null, + errorTag: null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: hashTape(tape), + tapeLength: tape.length, + }; + } + return { + stage: normalizeFailureStage(result.error.kind), + resultHash: null, + errorCode: result.error.code, + errorTag: 'tag' in result.error ? result.error.tag : null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: hashTape(tape), + tapeLength: tape.length, + }; +} + +export async function runBrowserSnapshot( + page: Page, + certCase: BrowserEvaluationCase, + gasLimit?: string, +): Promise { + await ensureRunnerReady(page); + return page.evaluate( + async ({ certCasePayload, gasLimitValue }) => { + if (!window.__ECOSYSTEM_CERT_RUN_CASE__) { + throw new Error('window.__ECOSYSTEM_CERT_RUN_CASE__ is unavailable'); + } + return window.__ECOSYSTEM_CERT_RUN_CASE__( + certCasePayload, + gasLimitValue ?? certCasePayload.gasLimit, + ); + }, + { + certCasePayload: certCase, + gasLimitValue: gasLimit, + }, + ); +} + +async function ensureRunnerReady(page: Page): Promise { + await page.goto('/'); + await page.waitForFunction( + () => typeof window.__ECOSYSTEM_CERT_RUN_CASE__ === 'function', + undefined, + { timeout: 120000 }, + ); +} + +function toBrowserCase( + fixture: BuildFixtureDefinition, + built: BuildDeterministicModulePackResult, +): BrowserEvaluationCase { + if (!built.programArtifact) { + throw new Error(`missing ProgramArtifact.v2 for ${fixture.id}`); + } + return { + id: fixture.id, + title: fixture.title, + kind: fixture.kind, + gasLimit: fixture.gasLimit.toString(), + manifest: manifestForFixture(fixture), + program: built.programArtifact, + }; +} + +function normalizeFailureStage(kind: string): FailureStage { + if (kind === 'module-pack') { + return 'artifact_validation'; + } + if (kind === 'execution-surface-mismatch') { + return 'pin_enforcement'; + } + return 'runtime_error'; +} diff --git a/apps/ecosystem-certifier/tests/negative-determinism.spec.ts b/apps/ecosystem-certifier/tests/negative-determinism.spec.ts new file mode 100644 index 0000000..cc995c5 --- /dev/null +++ b/apps/ecosystem-certifier/tests/negative-determinism.spec.ts @@ -0,0 +1,49 @@ +import { expect, test } from '@playwright/test'; +import { + DeterministicBuilderError, + buildDeterministicModulePack, +} from '@blue-quickjs/deterministic-builder'; +import { HOST_V1_HASH } from '@blue-quickjs/abi-manifest'; +import { + buildCaseByFixtureId, + getFixtureById, + runBrowserSnapshot, + runNodeSnapshot, +} from './fixture-helpers.js'; + +test('function-constructor fixture fails deterministically in both environments', async ({ + page, +}) => { + const certCase = await buildCaseByFixtureId('red-function-constructor'); + const nodeSnapshot = await runNodeSnapshot(certCase); + const browserSnapshot = await runBrowserSnapshot(page, certCase); + + expect(nodeSnapshot.stage).toBe('artifact_validation'); + expect(nodeSnapshot.errorCode).toBe('MODULE_EXPORT_MISSING'); + expect(nodeSnapshot.errorTag).toBe('vm/module_pack'); + expect(browserSnapshot).toEqual(nodeSnapshot); +}); + +test('proxy fixture is rejected at build stage with deterministic rule', async () => { + const fixture = getFixtureById('red-proxy'); + let thrown: unknown = null; + try { + await buildDeterministicModulePack({ + absWorkingDir: process.cwd(), + entryPath: fixture.entryPath, + profile: fixture.profile, + emitProgramArtifact: true, + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + }); + } catch (error) { + thrown = error; + } + expect(thrown).toBeInstanceOf(DeterministicBuilderError); + if (thrown instanceof DeterministicBuilderError) { + expect(thrown.diagnostics.some((entry) => entry.ruleId === 'proxy_disabled')).toBe( + true, + ); + } +}); diff --git a/apps/ecosystem-certifier/tests/oog-boundary.spec.ts b/apps/ecosystem-certifier/tests/oog-boundary.spec.ts new file mode 100644 index 0000000..28e84ad --- /dev/null +++ b/apps/ecosystem-certifier/tests/oog-boundary.spec.ts @@ -0,0 +1,38 @@ +import { expect, test } from '@playwright/test'; +import { + compareBoundaries, + searchOogBoundary, +} from '../src/shared/oog-boundary.js'; +import { + buildCaseByFixtureId, + runBrowserSnapshot, + runNodeSnapshot, +} from './fixture-helpers.js'; + +test('node and browser share exact OOG boundary for semver fixture', async ({ + page, +}) => { + const certCase = await buildCaseByFixtureId('green-semver'); + const maxGas = BigInt(certCase.gasLimit); + + const nodeBoundary = await searchOogBoundary({ + low: 1n, + high: maxGas, + runSuccess: async (gasLimit) => { + const snapshot = await runNodeSnapshot(certCase, gasLimit.toString()); + return snapshot.stage === 'success'; + }, + }); + const browserBoundary = await searchOogBoundary({ + low: 1n, + high: maxGas, + runSuccess: async (gasLimit) => { + const snapshot = await runBrowserSnapshot(page, certCase, gasLimit.toString()); + return snapshot.stage === 'success'; + }, + }); + + const parity = compareBoundaries(nodeBoundary, browserBoundary); + expect(parity.firstSuccessEqual).toBe(true); + expect(parity.lastFailureEqual).toBe(true); +}); diff --git a/apps/ecosystem-certifier/tests/parity.spec.ts b/apps/ecosystem-certifier/tests/parity.spec.ts new file mode 100644 index 0000000..933f224 --- /dev/null +++ b/apps/ecosystem-certifier/tests/parity.spec.ts @@ -0,0 +1,19 @@ +import { expect, test } from '@playwright/test'; +import { compareSnapshots, isStrictParity } from '../src/shared/parity.js'; +import { + buildCaseByFixtureId, + runBrowserSnapshot, + runNodeSnapshot, +} from './fixture-helpers.js'; + +test('flagship fixture preserves strict node/browser parity snapshot', async ({ + page, +}) => { + const certCase = await buildCaseByFixtureId('flagship-knowledge-pack'); + const nodeSnapshot = await runNodeSnapshot(certCase); + const browserSnapshot = await runBrowserSnapshot(page, certCase); + const parity = compareSnapshots(nodeSnapshot, browserSnapshot); + + expect(isStrictParity(parity)).toBe(true); + expect(browserSnapshot).toEqual(nodeSnapshot); +}); diff --git a/apps/ecosystem-certifier/tests/repeatability.spec.ts b/apps/ecosystem-certifier/tests/repeatability.spec.ts new file mode 100644 index 0000000..23b6648 --- /dev/null +++ b/apps/ecosystem-certifier/tests/repeatability.spec.ts @@ -0,0 +1,26 @@ +import { expect, test } from '@playwright/test'; +import { runRepeatability } from '../src/shared/repeatability.js'; +import { + buildCaseByFixtureId, + runBrowserSnapshot, + runNodeSnapshot, +} from './fixture-helpers.js'; + +test('stress corpus snapshot is stable across repeated node/browser runs', async ({ + page, +}) => { + const certCase = await buildCaseByFixtureId('green-stress-corpus'); + + const nodeRepeatability = await runRepeatability({ + iterations: 8, + runSnapshot: async () => runNodeSnapshot(certCase), + }); + const browserRepeatability = await runRepeatability({ + iterations: 8, + runSnapshot: async () => runBrowserSnapshot(page, certCase), + }); + + expect(nodeRepeatability.driftCount).toBe(0); + expect(browserRepeatability.driftCount).toBe(0); + expect(browserRepeatability.baseline).toEqual(nodeRepeatability.baseline); +}); diff --git a/apps/ecosystem-certifier/tsconfig.app.json b/apps/ecosystem-certifier/tsconfig.app.json new file mode 100644 index 0000000..aa3d485 --- /dev/null +++ b/apps/ecosystem-certifier/tsconfig.app.json @@ -0,0 +1,29 @@ +{ + "extends": "./tsconfig.json", + "compilerOptions": { + "outDir": "dist/out-tsc", + "types": [] + }, + "include": ["src/**/*.ts"], + "exclude": ["src/**/*.spec.ts", "tests/**/*.ts"], + "references": [ + { + "path": "../../libs/test-harness/tsconfig.lib.json" + }, + { + "path": "../../libs/quickjs-wasm/tsconfig.lib.json" + }, + { + "path": "../../libs/quickjs-runtime/tsconfig.lib.json" + }, + { + "path": "../../libs/dv/tsconfig.lib.json" + }, + { + "path": "../../libs/deterministic-builder/tsconfig.lib.json" + }, + { + "path": "../../libs/abi-manifest/tsconfig.lib.json" + } + ] +} diff --git a/apps/ecosystem-certifier/tsconfig.json b/apps/ecosystem-certifier/tsconfig.json new file mode 100644 index 0000000..fe91c13 --- /dev/null +++ b/apps/ecosystem-certifier/tsconfig.json @@ -0,0 +1,18 @@ +{ + "extends": "../../tsconfig.base.json", + "compilerOptions": { + "types": [ + "node" + ] + }, + "files": [], + "include": [], + "references": [ + { + "path": "./tsconfig.app.json" + }, + { + "path": "./tsconfig.spec.json" + } + ] +} diff --git a/apps/ecosystem-certifier/tsconfig.spec.json b/apps/ecosystem-certifier/tsconfig.spec.json new file mode 100644 index 0000000..b961d92 --- /dev/null +++ b/apps/ecosystem-certifier/tsconfig.spec.json @@ -0,0 +1,14 @@ +{ + "extends": "./tsconfig.json", + "compilerOptions": { + "outDir": "dist/out-tsc-spec", + "types": [ + "vitest/globals", + "node" + ] + }, + "include": [ + "src/**/*.spec.ts", + "tests/**/*.ts" + ] +} diff --git a/apps/ecosystem-certifier/vite.config.mts b/apps/ecosystem-certifier/vite.config.mts new file mode 100644 index 0000000..f99ff0d --- /dev/null +++ b/apps/ecosystem-certifier/vite.config.mts @@ -0,0 +1,40 @@ +/// +import path from 'node:path'; +import { defineConfig } from 'vite'; + +export default defineConfig(() => ({ + root: import.meta.dirname, + cacheDir: '../../node_modules/.vite/apps/ecosystem-certifier', + server: { + port: 4310, + host: 'localhost', + fs: { + allow: [path.resolve(import.meta.dirname, '..', '..', '..')], + }, + }, + preview: { + port: 4310, + host: 'localhost', + }, + build: { + outDir: './dist', + emptyOutDir: true, + reportCompressedSize: true, + commonjsOptions: { + transformMixedEsModules: true, + }, + }, + test: { + name: 'ecosystem-certifier', + watch: false, + globals: true, + environment: 'node', + include: ['src/**/*.{test,spec}.{js,mjs,cjs,ts,mts,cts,jsx,tsx}'], + exclude: ['tests/**'], + reporters: ['default'], + coverage: { + reportsDirectory: './test-output/vitest/coverage', + provider: 'v8' as const, + }, + }, +})); diff --git a/apps/smoke-node/package.json b/apps/smoke-node/package.json index 8d44dd9..357b33e 100644 --- a/apps/smoke-node/package.json +++ b/apps/smoke-node/package.json @@ -36,5 +36,8 @@ "@blue-quickjs/quickjs-runtime": "workspace:*", "@blue-quickjs/test-harness": "workspace:*", "tslib": "^2.3.0" + }, + "devDependencies": { + "@blue-quickjs/deterministic-bundler": "workspace:*" } } diff --git a/apps/smoke-node/src/lib/binary-library-reuse.spec.ts b/apps/smoke-node/src/lib/binary-library-reuse.spec.ts new file mode 100644 index 0000000..a42b6b3 --- /dev/null +++ b/apps/smoke-node/src/lib/binary-library-reuse.spec.ts @@ -0,0 +1,46 @@ +import { bundleDeterministicProgram } from '@blue-quickjs/deterministic-bundler'; +import path from 'node:path'; +import { + BINARY_LIBRARY_FIXTURES, + BINARY_LIBRARY_GAS_LIMIT, + BINARY_LIBRARY_INPUT, + BINARY_LIBRARY_MANIFEST, + BINARY_LIBRARY_PROGRAM_BASE, + createDeterminismHost, +} from '@blue-quickjs/test-harness'; +import { evaluate } from '@blue-quickjs/quickjs-runtime'; + +describe('smoke-node binary library reuse', () => { + it('bundles binary-heavy npm packages and matches expected results', async () => { + const workspaceRoot = path.resolve(process.cwd(), '../..'); + + for (const fixture of BINARY_LIBRARY_FIXTURES) { + const bundled = await bundleDeterministicProgram({ + absWorkingDir: workspaceRoot, + entryPath: fixture.entryPath, + profile: 'compat-binary-v1', + }); + + const host = createDeterminismHost(); + const result = await evaluate({ + program: { + ...BINARY_LIBRARY_PROGRAM_BASE, + code: bundled.code, + }, + input: BINARY_LIBRARY_INPUT, + gasLimit: BINARY_LIBRARY_GAS_LIMIT, + manifest: BINARY_LIBRARY_MANIFEST, + handlers: host.handlers, + }); + + expect(result.ok).toBe(true); + if (!result.ok) { + throw new Error( + `${fixture.name} failed: ${result.error.code}: ${result.message}`, + ); + } + + expect(result.value).toEqual(fixture.expectedValue); + } + }); +}); diff --git a/apps/smoke-node/src/lib/chess-library-reuse.spec.ts b/apps/smoke-node/src/lib/chess-library-reuse.spec.ts new file mode 100644 index 0000000..1a621f4 --- /dev/null +++ b/apps/smoke-node/src/lib/chess-library-reuse.spec.ts @@ -0,0 +1,41 @@ +import { bundleDeterministicProgram } from '@blue-quickjs/deterministic-bundler'; +import path from 'node:path'; +import { + CHESS_E2E6_EXPECTED_LEGAL, + CHESS_LIBRARY_ENTRY_PATH, + CHESS_LIBRARY_GAS_LIMIT, + CHESS_LIBRARY_INPUT, + CHESS_LIBRARY_MANIFEST, + CHESS_LIBRARY_PROGRAM_BASE, + createDeterminismHost, +} from '@blue-quickjs/test-harness'; +import { evaluate } from '@blue-quickjs/quickjs-runtime'; + +describe('smoke-node chess.js reuse', () => { + it('bundles chess.js and checks e2e6 legality', async () => { + const workspaceRoot = path.resolve(process.cwd(), '../..'); + const bundled = await bundleDeterministicProgram({ + absWorkingDir: workspaceRoot, + entryPath: CHESS_LIBRARY_ENTRY_PATH, + profile: 'compat-general-v1', + }); + + const host = createDeterminismHost(); + const result = await evaluate({ + program: { + ...CHESS_LIBRARY_PROGRAM_BASE, + code: bundled.code, + }, + input: CHESS_LIBRARY_INPUT, + gasLimit: CHESS_LIBRARY_GAS_LIMIT, + manifest: CHESS_LIBRARY_MANIFEST, + handlers: host.handlers, + }); + + expect(result.ok).toBe(true); + if (!result.ok) { + throw new Error(result.message); + } + expect(result.value).toBe(CHESS_E2E6_EXPECTED_LEGAL); + }); +}); diff --git a/apps/smoke-node/src/lib/examples-corpus.spec.ts b/apps/smoke-node/src/lib/examples-corpus.spec.ts new file mode 100644 index 0000000..0e4e786 --- /dev/null +++ b/apps/smoke-node/src/lib/examples-corpus.spec.ts @@ -0,0 +1,54 @@ +import fs from 'node:fs'; +import path from 'node:path'; +import { fileURLToPath } from 'node:url'; +import { + BINARY_LIBRARY_FIXTURES, + DETERMINISM_FIXTURES, + EXAMPLE_CORPUS, + GAS_SAMPLE_FIXTURES, + MODULE_PACK_FIXTURES, +} from '@blue-quickjs/test-harness'; + +const currentDir = path.dirname(fileURLToPath(import.meta.url)); +const workspaceRoot = path.resolve(currentDir, '../../../..'); + +describe('examples corpus coverage', () => { + it('includes source files for all ten example categories', () => { + expect(EXAMPLE_CORPUS).toHaveLength(10); + const ids = new Set(EXAMPLE_CORPUS.map((entry) => entry.id)); + expect(ids.size).toBe(EXAMPLE_CORPUS.length); + + const sourcePaths = EXAMPLE_CORPUS.flatMap((entry) => entry.sourcePaths); + const missing = sourcePaths.filter( + (relativePath) => !fs.existsSync(path.join(workspaceRoot, relativePath)), + ); + + expect(missing).toEqual([]); + }); + + it('maps examples to existing fixture coverage', () => { + const fixtureSets = { + determinism: new Set(DETERMINISM_FIXTURES.map((fixture) => fixture.name)), + 'module-pack': new Set(MODULE_PACK_FIXTURES.map((fixture) => fixture.name)), + 'gas-sample': new Set(GAS_SAMPLE_FIXTURES.map((fixture) => fixture.name)), + 'gas-boundary': new Set(GAS_SAMPLE_FIXTURES.map((fixture) => fixture.name)), + 'binary-library': new Set( + BINARY_LIBRARY_FIXTURES.map((fixture) => fixture.name), + ), + 'chess-library': new Set(['chess-e2e6']), + } as const; + + const missingTargets: string[] = []; + for (const example of EXAMPLE_CORPUS) { + for (const target of example.coverage) { + if (!fixtureSets[target.suite].has(target.fixtureName)) { + missingTargets.push( + `${example.slug}:${target.suite}:${target.fixtureName}`, + ); + } + } + } + + expect(missingTargets).toEqual([]); + }); +}); diff --git a/apps/smoke-node/src/lib/module-pack-parity.spec.ts b/apps/smoke-node/src/lib/module-pack-parity.spec.ts new file mode 100644 index 0000000..30cff22 --- /dev/null +++ b/apps/smoke-node/src/lib/module-pack-parity.spec.ts @@ -0,0 +1,37 @@ +import { MODULE_PACK_FIXTURES } from '@blue-quickjs/test-harness'; +import { evaluate } from '@blue-quickjs/quickjs-runtime'; + +describe('smoke-node module-pack fixtures', () => { + it('executes module-pack fixtures with expected outcomes', async () => { + for (const fixture of MODULE_PACK_FIXTURES) { + const host = fixture.createHost(); + const result = await evaluate({ + program: fixture.program, + input: fixture.input, + gasLimit: fixture.gasLimit, + manifest: fixture.manifest, + handlers: host.handlers, + tape: { capacity: 16 }, + }); + + expect(result.ok).toBe(fixture.expected.ok); + + if (fixture.expected.ok) { + if (!result.ok) { + throw new Error( + `${fixture.name} expected success, got error ${result.error.code}`, + ); + } + expect(result.value).toEqual(fixture.expected.value); + } else { + if (result.ok) { + throw new Error(`${fixture.name} expected failure`); + } + expect(result.error.code).toBe(fixture.expected.errorCode); + expect('tag' in result.error ? result.error.tag : null).toBe( + fixture.expected.errorTag, + ); + } + } + }); +}); diff --git a/apps/smoke-node/tsconfig.lib.json b/apps/smoke-node/tsconfig.lib.json index c21c2fa..369217f 100644 --- a/apps/smoke-node/tsconfig.lib.json +++ b/apps/smoke-node/tsconfig.lib.json @@ -19,6 +19,9 @@ }, { "path": "../../libs/dv/tsconfig.lib.json" + }, + { + "path": "../../libs/deterministic-bundler/tsconfig.lib.json" } ], "exclude": [ diff --git a/apps/smoke-web/binary-library-reuse.html b/apps/smoke-web/binary-library-reuse.html new file mode 100644 index 0000000..cda1ead --- /dev/null +++ b/apps/smoke-web/binary-library-reuse.html @@ -0,0 +1,12 @@ + + + + + + Binary library reuse + + +
Loading binary library reuse fixture…
+ + + diff --git a/apps/smoke-web/chess-library-reuse.html b/apps/smoke-web/chess-library-reuse.html new file mode 100644 index 0000000..9db2f29 --- /dev/null +++ b/apps/smoke-web/chess-library-reuse.html @@ -0,0 +1,12 @@ + + + + + + Chess library reuse + + +
Loading chess library reuse fixture…
+ + + diff --git a/apps/smoke-web/module-pack-fixtures.html b/apps/smoke-web/module-pack-fixtures.html new file mode 100644 index 0000000..01f44ca --- /dev/null +++ b/apps/smoke-web/module-pack-fixtures.html @@ -0,0 +1,12 @@ + + + + + + Module-pack fixtures + + +
Loading module-pack fixtures…
+ + + diff --git a/apps/smoke-web/package.json b/apps/smoke-web/package.json index 24a5d08..1cbeb40 100644 --- a/apps/smoke-web/package.json +++ b/apps/smoke-web/package.json @@ -4,9 +4,10 @@ "type": "module", "private": true, "dependencies": { + "@blue-quickjs/deterministic-bundler": "workspace:*", "@blue-quickjs/dv": "workspace:*", - "@blue-quickjs/quickjs-wasm": "workspace:*", "@blue-quickjs/quickjs-runtime": "workspace:*", + "@blue-quickjs/quickjs-wasm": "workspace:*", "@blue-quickjs/test-harness": "workspace:*" }, "nx": { diff --git a/apps/smoke-web/src/app/gas-samples.element.ts b/apps/smoke-web/src/app/gas-samples.element.ts index 5fa6939..a583e64 100644 --- a/apps/smoke-web/src/app/gas-samples.element.ts +++ b/apps/smoke-web/src/app/gas-samples.element.ts @@ -45,13 +45,35 @@ interface FixtureResult { repeatSameContext?: RepeatSnapshot; } +interface BoundaryFixtureResult { + name: string; + firstSuccessGas: string; + lastFailureGas: string; + successGasUsed: string; + successGasRemaining: string; + failureGasUsed: string; + failureGasRemaining: string; + failureCode: string | null; + failureTag: string | null; +} + declare global { interface Window { __GAS_SAMPLE_RESULTS__?: FixtureResult[]; + __GAS_BOUNDARY_RESULTS__?: BoundaryFixtureResult[]; __GAS_SAMPLE_STATE__?: RunState; } } +const GAS_BOUNDARY_FIXTURE_NAMES = new Set([ + 'return-1', + 'loop-1k', + 'loop-10k', + 'string-concat', + 'object-alloc', + 'array-ops', +]); + export class GasSamplesElement extends HTMLElement { private isRunning = false; @@ -106,7 +128,13 @@ export class GasSamplesElement extends HTMLElement { }); } + const boundaryResults = await runBoundaryFixtureSearches( + metadata, + wasmBinary, + ); + window.__GAS_SAMPLE_RESULTS__ = results; + window.__GAS_BOUNDARY_RESULTS__ = boundaryResults; window.__GAS_SAMPLE_STATE__ = 'done'; this.renderResults(results); this.updateRunstate('done', 'Done'); @@ -222,6 +250,103 @@ function compareSnapshots( }; } +async function runBoundaryFixtureSearches( + metadata: Awaited>, + wasmBinary: Uint8Array, +): Promise { + const selected = GAS_SAMPLE_FIXTURES.filter((fixture) => + GAS_BOUNDARY_FIXTURE_NAMES.has(fixture.name), + ); + const results: BoundaryFixtureResult[] = []; + for (const fixture of selected) { + results.push(await findOutOfGasBoundary(fixture, metadata, wasmBinary)); + } + return results; +} + +async function findOutOfGasBoundary( + fixture: (typeof GAS_SAMPLE_FIXTURES)[number], + metadata: Awaited>, + wasmBinary: Uint8Array, +): Promise { + let upperGas = fixture.expected.gasUsed; + let upper = await runFixtureAtGasLimit( + fixture, + upperGas, + metadata, + wasmBinary, + ); + while (!upper.ok) { + upperGas *= 2n; + upper = await runFixtureAtGasLimit(fixture, upperGas, metadata, wasmBinary); + } + + let lowerGas = 0n; + let lower = await runFixtureAtGasLimit( + fixture, + lowerGas, + metadata, + wasmBinary, + ); + while (lowerGas + 1n < upperGas) { + const mid = (lowerGas + upperGas) >> 1n; + const current = await runFixtureAtGasLimit( + fixture, + mid, + metadata, + wasmBinary, + ); + if (current.ok) { + upperGas = mid; + upper = current; + } else { + lowerGas = mid; + lower = current; + } + } + + if (!upper.ok) { + throw new Error( + `boundary search failed for ${fixture.name}: no successful gas limit found`, + ); + } + if (lower.ok) { + throw new Error( + `boundary search failed for ${fixture.name}: expected failing gas limit`, + ); + } + + return { + name: fixture.name, + firstSuccessGas: upperGas.toString(), + lastFailureGas: lowerGas.toString(), + successGasUsed: upper.gasUsed.toString(), + successGasRemaining: upper.gasRemaining.toString(), + failureGasUsed: lower.gasUsed.toString(), + failureGasRemaining: lower.gasRemaining.toString(), + failureCode: lower.error.code, + failureTag: 'tag' in lower.error ? lower.error.tag : null, + }; +} + +async function runFixtureAtGasLimit( + fixture: (typeof GAS_SAMPLE_FIXTURES)[number], + gasLimit: bigint, + metadata: Awaited>, + wasmBinary: Uint8Array, +): Promise { + const host = fixture.createHost(); + return evaluate({ + program: fixture.program, + input: fixture.input, + gasLimit, + manifest: fixture.manifest, + handlers: host.handlers, + metadata, + wasmBinary, + }); +} + async function runRepeatSameContext( fixture: (typeof GAS_SAMPLE_FIXTURES)[number], metadata: Awaited>, diff --git a/apps/smoke-web/src/binary-library-reuse.ts b/apps/smoke-web/src/binary-library-reuse.ts new file mode 100644 index 0000000..c7456c0 --- /dev/null +++ b/apps/smoke-web/src/binary-library-reuse.ts @@ -0,0 +1,110 @@ +import { evaluate } from '@blue-quickjs/quickjs-runtime'; +import { + BINARY_LIBRARY_GAS_LIMIT, + BINARY_LIBRARY_INPUT, + BINARY_LIBRARY_MANIFEST, + BINARY_LIBRARY_PROGRAM_BASE, + createDeterminismHost, +} from '@blue-quickjs/test-harness'; + +type BinaryReuseResult = { + ok: boolean; + value: Record | null; + gasUsed: string; + gasRemaining: string; + errorCode: string | null; + errorTag: string | null; +}; + +declare global { + interface Window { + __BINARY_BUNDLED_CODE__?: string; + __BINARY_LIBRARY_REUSE_RESULT__?: BinaryReuseResult; + } +} + +renderShell(); +void run(); + +function renderShell(): void { + const app = document.querySelector('[data-app]'); + if (!app) { + return; + } + app.innerHTML = ` +

Binary package deterministic reuse

+

Execution profile: compat-binary-v1

+

Running…

+
waiting…
+ `; +} + +async function run(): Promise { + const runstate = document.querySelector('[data-runstate]'); + const resultEl = document.querySelector('[data-result]'); + + try { + const code = window.__BINARY_BUNDLED_CODE__; + if (typeof code !== 'string' || code.length === 0) { + throw new Error( + 'Missing bundled binary fixture code in window.__BINARY_BUNDLED_CODE__', + ); + } + + const host = createDeterminismHost(); + const result = await evaluate({ + program: { + ...BINARY_LIBRARY_PROGRAM_BASE, + code, + }, + input: BINARY_LIBRARY_INPUT, + gasLimit: BINARY_LIBRARY_GAS_LIMIT, + manifest: BINARY_LIBRARY_MANIFEST, + handlers: host.handlers, + }); + + const payload: BinaryReuseResult = result.ok + ? { + ok: true, + value: result.value as Record, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + errorCode: null, + errorTag: null, + } + : { + ok: false, + value: null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + errorCode: result.error.code, + errorTag: 'tag' in result.error ? result.error.tag : null, + }; + + window.__BINARY_LIBRARY_REUSE_RESULT__ = payload; + if (runstate) { + runstate.dataset.runstate = 'done'; + runstate.textContent = payload.ok ? 'Done' : 'Failed'; + } + if (resultEl) { + resultEl.textContent = JSON.stringify(payload, null, 2); + } + } catch (error) { + const message = error instanceof Error ? error.message : String(error); + window.__BINARY_LIBRARY_REUSE_RESULT__ = { + ok: false, + value: null, + gasUsed: '0', + gasRemaining: '0', + errorCode: 'BOOT_FAILURE', + errorTag: null, + }; + if (runstate) { + runstate.dataset.runstate = 'error'; + runstate.textContent = `Error: ${message}`; + } + if (resultEl) { + resultEl.textContent = message; + } + } +} diff --git a/apps/smoke-web/src/chess-library-reuse.ts b/apps/smoke-web/src/chess-library-reuse.ts new file mode 100644 index 0000000..7fa6294 --- /dev/null +++ b/apps/smoke-web/src/chess-library-reuse.ts @@ -0,0 +1,111 @@ +import { evaluate } from '@blue-quickjs/quickjs-runtime'; +import { + CHESS_E2E6_EXPECTED_LEGAL, + CHESS_LIBRARY_GAS_LIMIT, + CHESS_LIBRARY_INPUT, + CHESS_LIBRARY_MANIFEST, + CHESS_LIBRARY_PROGRAM_BASE, + createDeterminismHost, +} from '@blue-quickjs/test-harness'; + +type ChessReuseResult = { + ok: boolean; + value: boolean | null; + gasUsed: string; + gasRemaining: string; + errorCode: string | null; + errorTag: string | null; +}; + +declare global { + interface Window { + __CHESS_BUNDLED_CODE__?: string; + __CHESS_LIBRARY_REUSE_RESULT__?: ChessReuseResult; + } +} + +renderShell(); +void run(); + +function renderShell(): void { + const app = document.querySelector('[data-app]'); + if (!app) { + return; + } + app.innerHTML = ` +

Chess.js deterministic reuse

+

Expected e2e6 legal: ${String(CHESS_E2E6_EXPECTED_LEGAL)}

+

Running…

+
waiting…
+ `; +} + +async function run(): Promise { + const runstate = document.querySelector('[data-runstate]'); + const resultEl = document.querySelector('[data-result]'); + + try { + const code = window.__CHESS_BUNDLED_CODE__; + if (typeof code !== 'string' || code.length === 0) { + throw new Error( + 'Missing bundled chess code in window.__CHESS_BUNDLED_CODE__', + ); + } + + const host = createDeterminismHost(); + const result = await evaluate({ + program: { + ...CHESS_LIBRARY_PROGRAM_BASE, + code, + }, + input: CHESS_LIBRARY_INPUT, + gasLimit: CHESS_LIBRARY_GAS_LIMIT, + manifest: CHESS_LIBRARY_MANIFEST, + handlers: host.handlers, + }); + + const payload: ChessReuseResult = result.ok + ? { + ok: true, + value: result.value as boolean, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + errorCode: null, + errorTag: null, + } + : { + ok: false, + value: null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + errorCode: result.error.code, + errorTag: 'tag' in result.error ? result.error.tag : null, + }; + + window.__CHESS_LIBRARY_REUSE_RESULT__ = payload; + if (runstate) { + runstate.dataset.runstate = 'done'; + runstate.textContent = payload.ok ? 'Done' : 'Failed'; + } + if (resultEl) { + resultEl.textContent = JSON.stringify(payload, null, 2); + } + } catch (error) { + const message = error instanceof Error ? error.message : String(error); + window.__CHESS_LIBRARY_REUSE_RESULT__ = { + ok: false, + value: null, + gasUsed: '0', + gasRemaining: '0', + errorCode: 'BOOT_FAILURE', + errorTag: null, + }; + if (runstate) { + runstate.dataset.runstate = 'error'; + runstate.textContent = `Error: ${message}`; + } + if (resultEl) { + resultEl.textContent = message; + } + } +} diff --git a/apps/smoke-web/src/module-pack-fixtures.ts b/apps/smoke-web/src/module-pack-fixtures.ts new file mode 100644 index 0000000..f7ff9e0 --- /dev/null +++ b/apps/smoke-web/src/module-pack-fixtures.ts @@ -0,0 +1,103 @@ +import { evaluate } from '@blue-quickjs/quickjs-runtime'; +import { MODULE_PACK_FIXTURES } from '@blue-quickjs/test-harness'; +import { hashDv, hashTape } from './app/hash-utils.js'; + +type ModulePackFixtureSnapshot = { + ok: boolean; + valueHash: string | null; + errorCode: string | null; + errorTag: string | null; + gasUsed: string; + gasRemaining: string; + tapeHash: string | null; + tapeLength: number; +}; + +type ModulePackFixtureResult = { + name: string; + expectedOk: boolean; + actual: ModulePackFixtureSnapshot; +}; + +declare global { + interface Window { + __MODULE_PACK_FIXTURE_RESULTS__?: ModulePackFixtureResult[]; + } +} + +renderShell(); +void run(); + +function renderShell(): void { + const app = document.querySelector('[data-app]'); + if (!app) { + return; + } + app.innerHTML = ` +

Module-pack fixture parity

+

Running…

+
waiting…
+ `; +} + +async function run(): Promise { + const runstate = document.querySelector('[data-runstate]'); + const resultEl = document.querySelector('[data-result]'); + + try { + const results: ModulePackFixtureResult[] = []; + + for (const fixture of MODULE_PACK_FIXTURES) { + const host = fixture.createHost(); + const result = await evaluate({ + program: fixture.program, + input: fixture.input, + gasLimit: fixture.gasLimit, + manifest: fixture.manifest, + handlers: host.handlers, + tape: { capacity: 16 }, + }); + + const tape = result.tape ?? []; + const snapshot: ModulePackFixtureSnapshot = { + ok: result.ok, + valueHash: result.ok ? await hashDv(result.value) : null, + errorCode: result.ok ? null : result.error.code, + errorTag: result.ok + ? null + : 'tag' in result.error + ? result.error.tag + : null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: await hashTape(tape), + tapeLength: tape.length, + }; + + results.push({ + name: fixture.name, + expectedOk: fixture.expected.ok, + actual: snapshot, + }); + } + + window.__MODULE_PACK_FIXTURE_RESULTS__ = results; + if (runstate) { + runstate.dataset.runstate = 'done'; + runstate.textContent = 'Done'; + } + if (resultEl) { + resultEl.textContent = JSON.stringify(results, null, 2); + } + } catch (error) { + const message = error instanceof Error ? error.message : String(error); + window.__MODULE_PACK_FIXTURE_RESULTS__ = []; + if (runstate) { + runstate.dataset.runstate = 'error'; + runstate.textContent = `Error: ${message}`; + } + if (resultEl) { + resultEl.textContent = message; + } + } +} diff --git a/apps/smoke-web/tests/binary-library-reuse.spec.ts b/apps/smoke-web/tests/binary-library-reuse.spec.ts new file mode 100644 index 0000000..e389fe5 --- /dev/null +++ b/apps/smoke-web/tests/binary-library-reuse.spec.ts @@ -0,0 +1,89 @@ +import { bundleDeterministicProgram } from '@blue-quickjs/deterministic-bundler'; +import { evaluate } from '@blue-quickjs/quickjs-runtime'; +import { + BINARY_LIBRARY_FIXTURES, + BINARY_LIBRARY_GAS_LIMIT, + BINARY_LIBRARY_INPUT, + BINARY_LIBRARY_MANIFEST, + BINARY_LIBRARY_PROGRAM_BASE, + createDeterminismHost, +} from '@blue-quickjs/test-harness'; +import { expect, test } from '@playwright/test'; + +type BinaryReuseResult = { + ok: boolean; + value: Record | null; + gasUsed: string; + gasRemaining: string; + errorCode: string | null; + errorTag: string | null; +}; + +for (const fixture of BINARY_LIBRARY_FIXTURES) { + test(`browser matches node for ${fixture.name}`, async ({ page }) => { + const bundled = await bundleDeterministicProgram({ + absWorkingDir: process.cwd(), + entryPath: fixture.entryPath, + profile: 'compat-binary-v1', + }); + + const nodeResult = await runNodeFixture(bundled.code); + + await page.addInitScript((code) => { + ( + window as Window & { __BINARY_BUNDLED_CODE__?: string } + ).__BINARY_BUNDLED_CODE__ = code; + }, bundled.code); + + await page.goto('/binary-library-reuse.html'); + await page.waitForSelector('[data-runstate="done"]', { timeout: 30000 }); + + const browserResult = (await page.evaluate( + () => + ( + window as Window & { + __BINARY_LIBRARY_REUSE_RESULT__?: BinaryReuseResult; + } + ).__BINARY_LIBRARY_REUSE_RESULT__, + )) as BinaryReuseResult | undefined; + + expect(browserResult).toBeTruthy(); + expect(browserResult).toEqual(nodeResult); + expect(browserResult?.ok).toBe(true); + expect(browserResult?.value).toEqual(fixture.expectedValue); + }); +} + +async function runNodeFixture(code: string): Promise { + const host = createDeterminismHost(); + const result = await evaluate({ + program: { + ...BINARY_LIBRARY_PROGRAM_BASE, + code, + }, + input: BINARY_LIBRARY_INPUT, + gasLimit: BINARY_LIBRARY_GAS_LIMIT, + manifest: BINARY_LIBRARY_MANIFEST, + handlers: host.handlers, + }); + + if (result.ok) { + return { + ok: true, + value: result.value as Record, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + errorCode: null, + errorTag: null, + }; + } + + return { + ok: false, + value: null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + errorCode: result.error.code, + errorTag: 'tag' in result.error ? result.error.tag : null, + }; +} diff --git a/apps/smoke-web/tests/chess-library-reuse.spec.ts b/apps/smoke-web/tests/chess-library-reuse.spec.ts new file mode 100644 index 0000000..dcb371f --- /dev/null +++ b/apps/smoke-web/tests/chess-library-reuse.spec.ts @@ -0,0 +1,87 @@ +import { bundleDeterministicProgram } from '@blue-quickjs/deterministic-bundler'; +import { evaluate } from '@blue-quickjs/quickjs-runtime'; +import { + CHESS_E2E6_EXPECTED_LEGAL, + CHESS_LIBRARY_ENTRY_PATH, + CHESS_LIBRARY_GAS_LIMIT, + CHESS_LIBRARY_INPUT, + CHESS_LIBRARY_MANIFEST, + CHESS_LIBRARY_PROGRAM_BASE, + createDeterminismHost, +} from '@blue-quickjs/test-harness'; +import { expect, test } from '@playwright/test'; + +type ChessReuseResult = { + ok: boolean; + value: boolean | null; + gasUsed: string; + gasRemaining: string; + errorCode: string | null; + errorTag: string | null; +}; + +test('browser matches node for bundled chess.js e2e6 legality', async ({ + page, +}) => { + const bundled = await bundleDeterministicProgram({ + absWorkingDir: process.cwd(), + entryPath: CHESS_LIBRARY_ENTRY_PATH, + profile: 'compat-general-v1', + }); + + const nodeResult = await runNodeFixture(bundled.code); + + await page.addInitScript((code) => { + ( + window as Window & { __CHESS_BUNDLED_CODE__?: string } + ).__CHESS_BUNDLED_CODE__ = code; + }, bundled.code); + + await page.goto('/chess-library-reuse.html'); + await page.waitForSelector('[data-runstate="done"]', { timeout: 30000 }); + + const browserResult = (await page.evaluate( + () => + (window as Window & { __CHESS_LIBRARY_REUSE_RESULT__?: ChessReuseResult }) + .__CHESS_LIBRARY_REUSE_RESULT__, + )) as ChessReuseResult | undefined; + + expect(browserResult).toBeTruthy(); + expect(browserResult).toEqual(nodeResult); + expect(browserResult?.ok).toBe(true); + expect(browserResult?.value).toBe(CHESS_E2E6_EXPECTED_LEGAL); +}); + +async function runNodeFixture(code: string): Promise { + const host = createDeterminismHost(); + const result = await evaluate({ + program: { + ...CHESS_LIBRARY_PROGRAM_BASE, + code, + }, + input: CHESS_LIBRARY_INPUT, + gasLimit: CHESS_LIBRARY_GAS_LIMIT, + manifest: CHESS_LIBRARY_MANIFEST, + handlers: host.handlers, + }); + + if (result.ok) { + return { + ok: true, + value: result.value as boolean, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + errorCode: null, + errorTag: null, + }; + } + + return { + ok: false, + value: null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + errorCode: result.error.code, + errorTag: 'tag' in result.error ? result.error.tag : null, + }; +} diff --git a/apps/smoke-web/tests/examples-corpus.spec.ts b/apps/smoke-web/tests/examples-corpus.spec.ts new file mode 100644 index 0000000..08d0c8a --- /dev/null +++ b/apps/smoke-web/tests/examples-corpus.spec.ts @@ -0,0 +1,59 @@ +import { + BINARY_LIBRARY_FIXTURES, + EXAMPLE_CORPUS, +} from '@blue-quickjs/test-harness'; +import { expect, test } from '@playwright/test'; +import { mapByName, readBrowserResults } from './fixture-utils.js'; + +type NamedFixtureResult = { + name: string; +}; + +test('browser fixture suites cover example corpus mappings', async ({ page }) => { + const determinismResults = await readBrowserResults( + page, + '/determinism.html', + '__DETERMINISM_RESULTS__', + 'determinism', + ); + const gasSampleResults = await readBrowserResults( + page, + '/gas-samples.html', + '__GAS_SAMPLE_RESULTS__', + 'gas sample', + ); + const gasBoundaryResults = await readBrowserResults( + page, + '/gas-samples.html', + '__GAS_BOUNDARY_RESULTS__', + 'gas boundary', + ); + const modulePackResults = await readBrowserResults( + page, + '/module-pack-fixtures.html', + '__MODULE_PACK_FIXTURE_RESULTS__', + 'module-pack fixture', + ); + + const suiteFixtureNames = { + determinism: new Set(mapByName(determinismResults).keys()), + 'gas-sample': new Set(mapByName(gasSampleResults).keys()), + 'gas-boundary': new Set(mapByName(gasBoundaryResults).keys()), + 'module-pack': new Set(mapByName(modulePackResults).keys()), + 'chess-library': new Set(['chess-e2e6']), + 'binary-library': new Set(BINARY_LIBRARY_FIXTURES.map((f) => f.name)), + } as const; + + const missingTargets: string[] = []; + for (const example of EXAMPLE_CORPUS) { + for (const target of example.coverage) { + if (!suiteFixtureNames[target.suite].has(target.fixtureName)) { + missingTargets.push( + `${example.slug}:${target.suite}:${target.fixtureName}`, + ); + } + } + } + + expect(missingTargets).toEqual([]); +}); diff --git a/apps/smoke-web/tests/gas-boundaries.spec.ts b/apps/smoke-web/tests/gas-boundaries.spec.ts new file mode 100644 index 0000000..5dbc9d9 --- /dev/null +++ b/apps/smoke-web/tests/gas-boundaries.spec.ts @@ -0,0 +1,152 @@ +import { + GAS_SAMPLE_FIXTURES, + type GasFixture, +} from '@blue-quickjs/test-harness'; +import { evaluate, type EvaluateResult } from '@blue-quickjs/quickjs-runtime'; +import { + loadQuickjsWasmBinary, + loadQuickjsWasmMetadata, +} from '@blue-quickjs/quickjs-wasm'; +import { expect, test } from '@playwright/test'; +import { mapByName, readBrowserResults } from './fixture-utils.js'; + +type BoundaryFixtureResult = { + name: string; + firstSuccessGas: string; + lastFailureGas: string; + successGasUsed: string; + successGasRemaining: string; + failureGasUsed: string; + failureGasRemaining: string; + failureCode: string | null; + failureTag: string | null; +}; + +const GAS_BOUNDARY_FIXTURE_NAMES = new Set([ + 'return-1', + 'loop-1k', + 'loop-10k', + 'string-concat', + 'object-alloc', + 'array-ops', +]); + +test('browser and node share exact OOG boundaries', async ({ page }) => { + const nodeResults = await runNodeBoundaries(); + const browserResults = await readBrowserResults( + page, + '/gas-samples.html', + '__GAS_BOUNDARY_RESULTS__', + 'gas boundary', + ); + + const nodeByName = mapByName(nodeResults); + const browserByName = mapByName(browserResults); + expect(browserByName.size).toBe(nodeByName.size); + + for (const [name, node] of nodeByName) { + const browser = browserByName.get(name); + expect(browser, `missing browser boundary fixture ${name}`).toBeTruthy(); + if (!browser) { + continue; + } + expect(browser).toEqual(node); + } +}); + +async function runNodeBoundaries(): Promise { + const metadata = await loadQuickjsWasmMetadata(); + const wasmBinary = await loadQuickjsWasmBinary(); + const selected = GAS_SAMPLE_FIXTURES.filter((fixture) => + GAS_BOUNDARY_FIXTURE_NAMES.has(fixture.name), + ); + + const results: BoundaryFixtureResult[] = []; + for (const fixture of selected) { + results.push(await findOutOfGasBoundary(fixture, metadata, wasmBinary)); + } + return results; +} + +async function findOutOfGasBoundary( + fixture: GasFixture, + metadata: Awaited>, + wasmBinary: Uint8Array, +): Promise { + let upperGas = fixture.expected.gasUsed; + let upper = await runFixtureAtGasLimit( + fixture, + upperGas, + metadata, + wasmBinary, + ); + while (!upper.ok) { + upperGas *= 2n; + upper = await runFixtureAtGasLimit(fixture, upperGas, metadata, wasmBinary); + } + + let lowerGas = 0n; + let lower = await runFixtureAtGasLimit( + fixture, + lowerGas, + metadata, + wasmBinary, + ); + while (lowerGas + 1n < upperGas) { + const mid = (lowerGas + upperGas) >> 1n; + const current = await runFixtureAtGasLimit( + fixture, + mid, + metadata, + wasmBinary, + ); + if (current.ok) { + upperGas = mid; + upper = current; + } else { + lowerGas = mid; + lower = current; + } + } + + if (!upper.ok) { + throw new Error( + `boundary search failed for ${fixture.name}: no successful gas limit found`, + ); + } + if (lower.ok) { + throw new Error( + `boundary search failed for ${fixture.name}: expected failing gas limit`, + ); + } + + return { + name: fixture.name, + firstSuccessGas: upperGas.toString(), + lastFailureGas: lowerGas.toString(), + successGasUsed: upper.gasUsed.toString(), + successGasRemaining: upper.gasRemaining.toString(), + failureGasUsed: lower.gasUsed.toString(), + failureGasRemaining: lower.gasRemaining.toString(), + failureCode: lower.error.code, + failureTag: 'tag' in lower.error ? lower.error.tag : null, + }; +} + +async function runFixtureAtGasLimit( + fixture: GasFixture, + gasLimit: bigint, + metadata: Awaited>, + wasmBinary: Uint8Array, +): Promise { + const host = fixture.createHost(); + return evaluate({ + program: fixture.program, + input: fixture.input, + gasLimit, + manifest: fixture.manifest, + handlers: host.handlers, + metadata, + wasmBinary, + }); +} diff --git a/apps/smoke-web/tests/module-pack-fixtures.spec.ts b/apps/smoke-web/tests/module-pack-fixtures.spec.ts new file mode 100644 index 0000000..3e3c68d --- /dev/null +++ b/apps/smoke-web/tests/module-pack-fixtures.spec.ts @@ -0,0 +1,97 @@ +import { evaluate } from '@blue-quickjs/quickjs-runtime'; +import { MODULE_PACK_FIXTURES } from '@blue-quickjs/test-harness'; +import { + loadQuickjsWasmBinary, + loadQuickjsWasmMetadata, +} from '@blue-quickjs/quickjs-wasm'; +import { expect, test } from '@playwright/test'; +import { hashDv, hashTape } from '../src/app/hash-utils.js'; +import { mapByName, readBrowserResults } from './fixture-utils.js'; + +type ModulePackFixtureSnapshot = { + ok: boolean; + valueHash: string | null; + errorCode: string | null; + errorTag: string | null; + gasUsed: string; + gasRemaining: string; + tapeHash: string | null; + tapeLength: number; +}; + +type ModulePackFixtureResult = { + name: string; + expectedOk: boolean; + actual: ModulePackFixtureSnapshot; +}; + +test('browser module-pack fixtures match Node outputs', async ({ page }) => { + const nodeResults = await runNodeFixtures(); + + const browserResults = await readBrowserResults( + page, + '/module-pack-fixtures.html', + '__MODULE_PACK_FIXTURE_RESULTS__', + 'module-pack fixture', + ); + + const nodeByName = mapByName(nodeResults); + const browserByName = mapByName(browserResults); + + expect(browserByName.size).toBe(nodeByName.size); + + for (const [name, node] of nodeByName) { + const browser = browserByName.get(name); + expect(browser, `missing browser fixture ${name}`).toBeTruthy(); + if (!browser) { + continue; + } + + expect(browser.expectedOk).toBe(node.expectedOk); + expect(browser.actual).toEqual(node.actual); + } +}); + +async function runNodeFixtures(): Promise { + const metadata = await loadQuickjsWasmMetadata(); + const wasmBinary = await loadQuickjsWasmBinary(); + const results: ModulePackFixtureResult[] = []; + + for (const fixture of MODULE_PACK_FIXTURES) { + const host = fixture.createHost(); + const result = await evaluate({ + program: fixture.program, + input: fixture.input, + gasLimit: fixture.gasLimit, + manifest: fixture.manifest, + handlers: host.handlers, + metadata, + wasmBinary, + tape: { capacity: 16 }, + }); + + const tape = result.tape ?? []; + const snapshot: ModulePackFixtureSnapshot = { + ok: result.ok, + valueHash: result.ok ? await hashDv(result.value) : null, + errorCode: result.ok ? null : result.error.code, + errorTag: result.ok + ? null + : 'tag' in result.error + ? result.error.tag + : null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: await hashTape(tape), + tapeLength: tape.length, + }; + + results.push({ + name: fixture.name, + expectedOk: fixture.expected.ok, + actual: snapshot, + }); + } + + return results; +} diff --git a/apps/smoke-web/tsconfig.app.json b/apps/smoke-web/tsconfig.app.json index aa0ff36..963ca8c 100644 --- a/apps/smoke-web/tsconfig.app.json +++ b/apps/smoke-web/tsconfig.app.json @@ -34,13 +34,16 @@ "path": "../../libs/test-harness/tsconfig.lib.json" }, { - "path": "../../libs/quickjs-runtime/tsconfig.lib.json" + "path": "../../libs/quickjs-wasm/tsconfig.lib.json" }, { - "path": "../../libs/quickjs-wasm/tsconfig.lib.json" + "path": "../../libs/quickjs-runtime/tsconfig.lib.json" }, { "path": "../../libs/dv/tsconfig.lib.json" + }, + { + "path": "../../libs/deterministic-bundler/tsconfig.lib.json" } ] } diff --git a/docs/README.md b/docs/README.md index b5a00f6..0925ace 100644 --- a/docs/README.md +++ b/docs/README.md @@ -1,65 +1,126 @@ -# Documentation index - -This repository is a deterministic JavaScript execution environment built on **QuickJS** compiled to **WebAssembly**, with a **manifest-locked Host ABI**, a canonical **Deterministic Value (DV)** wire format, and **deterministic gas metering**. - -The docs are split between: - -- **Baselines** (what must be true) -- **Implementation plan** (how we intended to build it) -- **Implementation summary + guides** (what was built, how to use it) -- **Reference specs** (normative, detail-heavy) - -If you are new to determinism/gas (or coming from “normal” JS runtimes), follow the reading order below. - -## Recommended reading order - -1. **Baselines (requirements / contracts)** - - [Baseline #1 – Deterministic JS engine](./baseline-1.md) - - [Baseline #2 – Host ABI + DV contract](./baseline-2.md) - -2. **Plan (design log)** - - [Implementation plan](./implementation-plan.md) - -3. **What was built (narrative + repo map)** - - [Implementation summary](./implementation-summary.md) - -4. **Reference specs (details, normative behavior)** - - [Determinism profile](./determinism-profile.md) - - [Gas schedule](./gas-schedule.md) - - [Deterministic Value wire format](./dv-wire-format.md) - - [ABI manifest schema + canonical encoding](./abi-manifest.md) - - [Host call ABI (the `host_call` syscall)](./host-call-abi.md) - - [Toolchain + build determinism](./toolchain.md) - - [Release + compatibility policy](./release-policy.md) - -5. **Developer guides (practical usage)** - - [TypeScript SDK usage](./sdk.md) - - [ABI limits explained](./abi-limits.md) - - [Observability: host-call tape + gas trace](./observability.md) - -## Quick “repo map” - -Most people end up reading some docs and then jumping into these locations: +# BlueQuickjs docs + +BlueQuickjs is a deterministic JavaScript execution stack for +**consensus-critical wasm32 evaluation**. These docs are organized around the +jobs readers actually need to do: learn the model, build artifacts, verify +determinism, operate safely, and audit a release. + +## Learn BlueQuickjs + +Best for: new engineers, reviewers, and anyone learning the product from +scratch. + +- [Learning path overview](./learn/README.md) — guided route through the first + ten documents. +- [What is BlueQuickjs?](./learn/00-what-is-bluequickjs.md) — concept, scope, + and consensus-safe executor matrix. +- [Install and run your first script](./learn/01-install-and-run-your-first-script.md) + — fastest path to a successful deterministic run. +- [Understand the program artifact](./learn/02-understand-the-program-artifact.md) + — `ProgramArtifact.v2`, pins, profiles, and release-mode expectations. +- [Module packs and imports](./learn/03-module-packs-and-imports.md) — why + imports are resolved at build time instead of runtime. +- [Promises, async, and microtasks](./learn/04-promises-async-and-microtasks.md) + — what `compat-general-v1` enables and what remains intentionally blocked. +- [Binary mode and Host.v2](./learn/05-binary-and-host-v2.md) — bytes, + `Uint8Array`, DV2, and typed-array-safe boundaries. +- [Gas, OOG, and max-gas policies](./learn/06-gas-oog-and-max-gas-policies.md) + — exact gas meaning and why OOG boundaries are release-critical. +- [Verify release evidence](./learn/07-verify-release-evidence.md) — how to + verify the current branch or a shipped release bundle. +- [Build a real example](./learn/08-build-a-real-example.md) — take an example + from source to artifact to browser/node execution. +- [Production embedder checklist](./learn/09-production-embedder-checklist.md) + — operational rules for consensus-safe deployments. +- [Glossary](./glossary.md) +- [FAQ](./faq.md) +- [Unsupported features and why](./unsupported-features-and-why.md) +- [Consensus-safe vs diagnostic-only](./consensus-safe-vs-diagnostic-only.md) +- [Playground](./playground.md) +- [Playground recipes](./playground-recipes.md) + +## Build with BlueQuickjs + +Best for: engineers wiring BlueQuickjs into products, tooling, or example +pipelines. + +- [Architecture overview](./architecture-overview.md) — source → + deterministic builder → `ProgramArtifact.v2` → wasm runtime → evidence. +- [Program artifact v2](./program-artifact-v2.md) +- [Module pack v1](./module-pack.md) +- [Execution profiles](./execution-profiles.md) +- [Deterministic builder](./builder.md) +- [Value model v2 (DV2)](./value-model-v2.md) +- [Embedder integration guide](./embedders.md) +- [TypeScript SDK usage](./sdk.md) +- [Examples guide](./examples.md) +- [Playground](./playground.md) +- [ABI limits explained](./abi-limits.md) + +## Verify determinism + +Best for: CI authors, auditors, and anyone checking whether what they see is +what consensus will see. + +- [HEAD verification note](./head-verification-note.md) +- [Determinism profile](./determinism-profile.md) +- [Gas schedule](./gas-schedule.md) +- [Deterministic Value wire format](./dv-wire-format.md) +- [ABI manifest schema + canonical encoding](./abi-manifest.md) +- [Host call ABI](./host-call-abi.md) +- [Observability: host-call tape + gas trace](./observability.md) +- [Workload certification plan](./workload-certification-plan.md) +- [Workload certification report](./workload-certification.md) +- [Ecosystem compatibility report](./ecosystem-compatibility-report.md) +- [Ecosystem compatibility baseline (0.4.1)](./ecosystem-compatibility-baseline-0.4.1.json) +- [First 10 minutes guide](./first-10-minutes.md) + +## Operate in production + +Best for: embedders, operators, and teams deploying consensus-safe workloads. + +- [Consensus-safe vs diagnostic-only](./consensus-safe-vs-diagnostic-only.md) +- [Production embedder checklist](./production-embedder-checklist.md) +- [Threat model (operator-facing)](./threat-model.md) +- [Toolchain and build determinism](./toolchain.md) +- [Repository metadata checklist](./repository-metadata-checklist.md) +- [GA cutover decision](./ga-cutover-decision.md) + +## Release and audit + +Best for: release managers, reviewers, and downstream auditors. + +- [Release-readiness report](./release-readiness-report.md) +- [Release checklist](./release-checklist.md) +- [Release policy](./release-policy.md) +- [Release provenance and trust model](./release-provenance.md) +- [Signature rotation and rollback](./signature-rotation-and-rollback.md) +- [Release go/no-go template](./release-go-no-go-template.md) +- [Release notes draft](./release-notes-draft.md) +- [Implementation summary](./implementation-summary.md) +- [Implementation plan (historical)](./implementation-plan.md) + +## Quick repo map + +Most readers eventually jump from docs into one of these directories: - **QuickJS fork + deterministic patches**: `vendor/quickjs/` - Deterministic init + gas metering: `vendor/quickjs/quickjs.c` - - Host ABI + manifest parsing + Host.v1 wrappers: `vendor/quickjs/quickjs-host.c` + - Host ABI + manifest parsing + Host wrappers: `vendor/quickjs/quickjs-host.c` - DV codec: `vendor/quickjs/quickjs-dv.c` - - SHA-256 helper used for tape hashing: `vendor/quickjs/quickjs-sha256.c` - Wasm entrypoints: `vendor/quickjs/quickjs-wasm-entry.c` - -- **TypeScript libraries** - - DV reference implementation: `libs/dv/` - - Manifest schema + canonical encoding/hashing: `libs/abi-manifest/` - - Wasm constants + metadata types: `libs/quickjs-wasm-constants/` - - Wasm build pipeline + metadata: `libs/quickjs-wasm-build/` - - Packaged wasm artifacts: `libs/quickjs-wasm/` - - Runtime SDK (evaluate / init / dispatcher): `libs/quickjs-runtime/` - - Shared fixtures + parsers: `libs/test-harness/` - -- **Executable examples** - - Node smoke runner: `apps/smoke-node/` - - Browser smoke runner: `apps/smoke-web/` - -- **Native harness (golden tests & debugging)** +- **Builder and runtime libraries** + - `libs/deterministic-builder/` + - `libs/deterministic-bundler/` + - `libs/dv/` + - `libs/abi-manifest/` + - `libs/quickjs-wasm-build/` + - `libs/quickjs-wasm/` + - `libs/quickjs-runtime/` + - `libs/test-harness/` +- **Executable apps** + - `apps/smoke-node/` + - `apps/smoke-web/` + - `apps/ecosystem-certifier/` +- **Diagnostic native harness** - `tools/quickjs-native-harness/` diff --git a/docs/abi-manifest.md b/docs/abi-manifest.md index 74c6ddd..6121379 100644 --- a/docs/abi-manifest.md +++ b/docs/abi-manifest.md @@ -2,7 +2,7 @@ Baseline anchor: see `docs/baseline-2.md`. -The ABI manifest maps **numeric function IDs** to host capabilities and is the single source of truth for generating `Host.v1` and validating host responses. The manifest is canonicalized and hashed; both the VM and host dispatcher must consume identical bytes (Baseline #2 §1.1–§1.4, §6.1–§6.3). +The ABI manifest maps **numeric function IDs** to host capabilities and is the single source of truth for generating `Host.v*` namespaces (`Host.v1`, `Host.v2`) and validating host responses. The manifest is canonicalized and hashed; both the VM and host dispatcher must consume identical bytes (Baseline #2 §1.1–§1.4, §6.1–§6.3). ## Canonical structure @@ -13,8 +13,8 @@ The ABI manifest maps **numeric function IDs** to host capabilities and is the s ### Top-level fields -- `abi_id` (string): Must be `"Host.v1"` in the current implementation (validation rejects other values). This is the string baked into `P`. -- `abi_version` (uint32): Must be `1` in the current implementation (validation rejects other values). +- `abi_id` (string): Must be a supported ABI namespace id (currently `"Host.v1"` or `"Host.v2"`). This is the string baked into `P`. +- `abi_version` (uint32): Must match the selected `abi_id` (currently `1` for `Host.v1`, `2` for `Host.v2`). - `functions` (array): Ordered by ascending `fn_id` and must contain at least one entry. Each entry is a map described below. `fn_id` values MUST be unique. No other top-level keys are permitted; unknown keys make the manifest invalid. @@ -24,7 +24,7 @@ No other top-level keys are permitted; unknown keys make the manifest invalid. Each function is a DV map with the following fields (no extras): - `fn_id` (uint32): Numeric ID used by the VM when calling `host_call`. Range: `1`–`2^32 - 1`. -- `js_path` (array): Property path relative to `Host.v1` used to install the JS wrapper (e.g., `["document", "get"]`). Segments MUST be non-empty, match `[A-Za-z0-9_-]+`, and the array MUST contain at least one segment. The following segment values are forbidden: `__proto__`, `prototype`, `constructor`. +- `js_path` (array): Property path relative to the selected host namespace (`Host.v1` / `Host.v2`) used to install the JS wrapper (e.g., `["document", "get"]`). Segments MUST be non-empty, match `[A-Za-z0-9_-]+`, and the array MUST contain at least one segment. The following segment values are forbidden: `__proto__`, `prototype`, `constructor`. - `effect` (string enum): `"READ" | "EMIT" | "MUTATE"`. Determines host-side semantics and auditing. For P3, only `READ`/`EMIT` are used. - `arity` (uint32): Exact number of positional arguments accepted by the host function. - `arg_schema` (array): Length MUST equal `arity`. Each item is a schema map (see **Schema language** below). diff --git a/docs/architecture-overview.md b/docs/architecture-overview.md new file mode 100644 index 0000000..fb95a31 --- /dev/null +++ b/docs/architecture-overview.md @@ -0,0 +1,128 @@ +# Architecture overview + +BlueQuickjs turns source code into a pinned, deterministic execution artifact +that can be evaluated in consensus-safe wasm runtimes and then verified against +generated evidence. + +## End-to-end flow + +```text +source files / examples / package entrypoints + │ + ▼ +deterministic builder +(`buildDeterministicModulePack`, `blue-quickjs build`) + │ + ├─ compatibility diagnostics + ├─ ModulePack.v1 + └─ ProgramArtifact.v2 + - executionProfile + - abiManifestHash + - engineBuildHash + - gasVersion + - sourceKind + │ + ▼ +wasm runtime (`@blue-quickjs/quickjs-runtime`) + │ + ├─ wasm-node + └─ wasm-browser + with identical: + - value/error + - gas used/remaining + - host-call tape + - OOG boundary + │ + ▼ +generated evidence and reports + ├─ consensus reproducibility report + ├─ workload certification report + ├─ ecosystem compatibility report + └─ release evidence bundle +``` + +## The important product boundaries + +### 1. Builder stage + +The deterministic builder resolves imports, normalizes module sources, runs +profile-aware compatibility checks, and emits: + +- [`ModulePack.v1`](./module-pack.md) for static in-memory module execution +- [`ProgramArtifact.v2`](./program-artifact-v2.md) for pinned execution +- compatibility diagnostics for unsupported behavior + +This is where runtime `import()`/network/filesystem behavior is deliberately +removed from the consensus path. Imports are resolved **before** execution. + +### 2. Artifact stage + +`ProgramArtifact.v2` is the release-facing contract that binds together: + +- source mode (`script` or `module-pack`) +- execution profile +- ABI identity and manifest hash +- engine build pin (`engineBuildHash`) +- gas schedule pin (`gasVersion`) + +See: + +- [`ProgramArtifact.v2`](./program-artifact-v2.md) +- [`Execution profiles`](./execution-profiles.md) +- [`ModulePack.v1`](./module-pack.md) + +### 3. Runtime stage + +The runtime loads the canonical `wasm32` release engine and evaluates the +artifact against: + +- deterministic input envelope data, +- a manifest-locked host ABI, +- an exact gas limit, +- optional tape/trace capture. + +Consensus-safe release scope is currently: + +- `wasm-node` +- `wasm-browser` + +Native remains diagnostic-only unless explicitly promoted by release policy. + +See: + +- [`Determinism profile`](./determinism-profile.md) +- [`Host call ABI`](./host-call-abi.md) +- [`Consensus-safe vs diagnostic-only`](./consensus-safe-vs-diagnostic-only.md) + +### 4. Evidence stage + +What users see in docs, reports, and release artifacts should come from +generated evidence rather than hand-maintained prose. The repo already produces: + +- consensus parity reports, +- workload certification and ecosystem compatibility reports, +- release evidence manifests, checksums, and signatures. + +See: + +- [`HEAD verification note`](./head-verification-note.md) +- [`Workload certification`](./workload-certification.md) +- [`Release-readiness report`](./release-readiness-report.md) +- [`Release provenance and trust model`](./release-provenance.md) + +## Where to look in the repo + +- Builder APIs: `libs/deterministic-builder/`, `libs/deterministic-bundler/` +- Wasm packaging: `libs/quickjs-wasm-build/`, `libs/quickjs-wasm/` +- Runtime SDK: `libs/quickjs-runtime/` +- Shared fixtures/evidence inputs: `libs/test-harness/` +- Examples corpus: `examples/` +- Browser/node certification apps: + - `apps/smoke-web/` + - `apps/smoke-node/` + - `apps/ecosystem-certifier/` + +## Continue learning + +- Start the guided sequence at [Learn BlueQuickjs](./learn/README.md) +- Or jump straight to [Install and run your first script](./learn/01-install-and-run-your-first-script.md) diff --git a/docs/baseline-1.md b/docs/baseline-1.md index 50ef702..7684051 100644 --- a/docs/baseline-1.md +++ b/docs/baseline-1.md @@ -53,6 +53,10 @@ Determinism depends on a strict JS surface: The exact list and the required deterministic error messages are specified in `docs/determinism-profile.md`. +Compatibility profiles may opt in to narrowly scoped additional surfaces (for +example regexp support), but baseline behavior remains the default contract and +must stay unchanged unless explicitly selected by the program artifact. + ## 4. Canonical gas (normative) ### 4.1 Canonical gas is **inside QuickJS** diff --git a/docs/baseline-2.md b/docs/baseline-2.md index e6bb43f..de5e0e8 100644 --- a/docs/baseline-2.md +++ b/docs/baseline-2.md @@ -122,5 +122,6 @@ The VM projects the manifest into JS as: - namespace objects are non-extensible; function properties are non-writable and non-configurable, - ergonomic globals may be installed (`document`, `event`, `eventCanonical`, `steps`, `currentContract`, `currentContractCanonical`, `canon`) but must be deterministic and pinned by the deterministic init contract. -The current manifest ABI id/version is `Host.v1` (see `docs/abi-manifest.md` and `docs/determinism-profile.md`). +Current supported manifest ABI ids/versions are `Host.v1` and `Host.v2` +(see `docs/abi-manifest.md` and `docs/determinism-profile.md`). diff --git a/docs/builder.md b/docs/builder.md new file mode 100644 index 0000000..f8b7c73 --- /dev/null +++ b/docs/builder.md @@ -0,0 +1,87 @@ +# Deterministic builder + +This document defines the target behavior for the deterministic build pipeline. + +## Naming decision + +`deterministic-bundler` is a transitional bridge name. The long-term product +surface is **deterministic builder** because it emits first-class reusable +artifacts (`ModulePack.v1`, `ProgramArtifact.v2`), not just one script blob. + +### Current implementation status (P14) + +- `@blue-quickjs/deterministic-bundler` now exports + `buildDeterministicModulePack(...)` for `ModulePack.v1` emission. +- `@blue-quickjs/deterministic-builder` is introduced as a migration facade that + re-exports the deterministic builder APIs. +- `bundleDeterministicProgram(...)` remains available for transitional + script-mode execution. +- Builder result shape now includes: + - `CompatibilityReport.v1` + - optional embedded `ProgramArtifact.v2` output + - graph-hash golden test lock for serialization stability. + +## Goals + +- Deterministic JS/TS authoring pipeline for real libraries. +- Build-time resolution of npm/package imports. +- Emission of canonical module-pack artifacts and compatibility reports. + +## Inputs + +- Entry source: JS / TS / MJS / CJS. +- Installed dependencies + lockfile/integrity data. +- Execution profile target. +- Optional `dependencyIntegrity` override as lowercase SHA-256 hex (64 chars). + +## Outputs + +Required: + +- `ModulePack.v1` +- compatibility report +- canonical source maps + +Optional: + +- single-script debug artifact for transitional workflows + +## Deterministic constraints (normative) + +1. No network fetches during deterministic build. +2. No absolute path influence on hashed outputs. +3. Same graph + same dependencies => same `graphHash` across Linux/macOS/Windows. +4. Compatibility scanning must run on transformed JS or TS-aware AST, not raw TS + source text. +5. Dependency provenance is captured for diagnostics: + - package name, + - package version, + - integrity/lock fingerprint (`dependencyIntegrity`, lowercase SHA-256 hex), + - origin path (diagnostics-only metadata). + +## Build pipeline stages + +1. Resolve graph deterministically. +2. Transform sources to normalized JS modules. +3. Rewrite imports to canonical internal specifiers. +4. Run compatibility scan using selected profile/capability registry. +5. Emit module-pack + source maps + report. +6. Compute `graphHash`. +7. Emit `ProgramArtifact.v2` referencing module-pack and explicit profile. + +## Source map requirements + +- Canonical JSON formatting. +- Stable ordering for deterministic serialization. +- Path-clean mapping data (no absolute host paths in hashed content). + +## Release artifact rule + +Builder-produced release artifacts MUST include `engineBuildHash` and explicit +`executionProfile`, and `gasVersion`. + +## See also + +- `docs/program-artifact-v2.md` +- `docs/module-pack.md` +- `docs/execution-profiles.md` diff --git a/docs/consensus-safe-vs-diagnostic-only.md b/docs/consensus-safe-vs-diagnostic-only.md new file mode 100644 index 0000000..29cb033 --- /dev/null +++ b/docs/consensus-safe-vs-diagnostic-only.md @@ -0,0 +1,51 @@ +# Consensus-safe vs diagnostic-only + +This page is the short answer to a critical release question: + +**what counts as the current consensus contract, and what is only diagnostic?** + +## Consensus-safe today + +The current consensus-safe executor matrix is: + +| Surface | Status | Notes | +| --- | --- | --- | +| `wasm-node` | consensus-safe | canonical `wasm32` release artifact | +| `wasm-browser` | consensus-safe | canonical `wasm32` release artifact | + +Release-critical parity for this matrix is exact: + +- value/error parity, +- gas used parity, +- gas remaining parity, +- host-call tape parity, +- OOG boundary parity. + +## Diagnostic-only today + +| Surface | Status | Why it is not consensus-safe today | +| --- | --- | --- | +| native harness | diagnostic-only | useful for debugging and reconciliation, but not the current release gate | +| WebKit browser runs | diagnostic-only | informative compatibility signal, not required release matrix | +| debug Wasm builds | diagnostic-only | useful for assertions/investigation, not the canonical release engine | +| alternate Wasm variants | diagnostic-only | canonical release scope is pinned to wasm32 | + +## What “diagnostic-only” does not mean + +Diagnostic-only does **not** mean “ignored” or “unimportant.” It means: + +- the repo may still generate reports for that surface, +- engineers may still use it to investigate mismatches, +- the release cannot market it as consensus-safe without explicit promotion. + +## What would change this page? + +Only an explicit policy and release decision should widen the consensus surface. +The repo should never silently drift from this page. + +## Related docs + +- [Release policy](./release-policy.md) +- [HEAD verification note](./head-verification-note.md) +- [Production embedder checklist](./production-embedder-checklist.md) +- [Workload certification](./workload-certification.md) diff --git a/docs/determinism-profile.md b/docs/determinism-profile.md index 0e2881f..6775c37 100644 --- a/docs/determinism-profile.md +++ b/docs/determinism-profile.md @@ -7,6 +7,7 @@ Scope: capture the deterministic VM configuration required by Baseline #1 for bo ## Deterministic init entrypoints - `JS_NewDeterministicRuntime(out_rt, out_ctx)` creates a runtime/context in deterministic mode, disables GC heuristics, and sets gas to `JS_GAS_UNLIMITED` by default. +- `JS_NewDeterministicRuntimeWithFeatures(out_rt, out_ctx, feature_flags)` does the same with explicit deterministic feature toggles. Runtime integration uses this path for profile-controlled deterministic capabilities (RegExp, Promise jobs/`queueMicrotask`, console shim, stable sort, typed-array intrinsics). - `JS_InitDeterministicContext(ctx, options)` must run before user code. It: - requires manifest bytes and a lowercase hex hash; size limit 1 MiB (`JS_DETERMINISTIC_MAX_MANIFEST_BYTES`) - validates `sha256(manifest_bytes)` against the provided hash and throws `ManifestError` with code `ABI_MANIFEST_HASH_MISMATCH` on mismatch @@ -14,16 +15,38 @@ Scope: capture the deterministic VM configuration required by Baseline #1 for bo - optionally copies a context blob (max 5 MiB) and installs ergonomic globals - sets the gas limit to `options.gas_limit` +## Execution profiles + +`program.executionProfile` controls deterministic feature flags: + +- `baseline-v1` (default): canonical baseline restrictions. +- `compat-regexp-v1`: transitional alias for baseline + deterministic RegExp + compatibility. +- `compat-general-v1`: `baseline-v1` + RegExp + Promise jobs + + `queueMicrotask` + deterministic console shim + deterministic stable sort. +- `compat-binary-v1`: `compat-general-v1` + typed arrays / ArrayBuffer / + DataView plus DV2 byte-string boundary support. + +Profile behavior is implemented via `JS_NewDeterministicRuntimeWithFeatures` +feature flags and must stay aligned with `docs/execution-profiles.md`. + ## Enabled intrinsics -The deterministic init only loads these intrinsic sets: +Deterministic init always loads: - `JS_AddIntrinsicBaseObjects` - `JS_AddIntrinsicEval` - `JS_AddIntrinsicJSON` - `JS_AddIntrinsicMapSet` -`Date`, `RegExp`, `Proxy`, TypedArrays, Promise, and WeakRef intrinsics are not loaded in deterministic mode. +Profile-gated additions: + +- `JS_AddIntrinsicRegExp` when `regexp` is enabled. +- `JS_AddIntrinsicPromise` when Promise jobs are enabled. +- `JS_AddIntrinsicTypedArrays` when typed-array support is enabled. + +`Date`, `Proxy`, and `WeakRef` intrinsics remain unavailable in all current +profiles. ## Disabled or stubbed APIs (deterministic TypeError) @@ -32,19 +55,19 @@ The following globals or methods exist but throw the exact TypeError shown: - `eval(...)` -> `TypeError: eval is disabled in deterministic mode` - `Function(...)` -> `TypeError: Function is disabled in deterministic mode` - Function constructor paths (`Function.prototype.constructor`, arrow/generator constructors) -> `TypeError: Function constructor is disabled in deterministic mode` -- `RegExp` and regex literals -> `TypeError: RegExp is disabled in deterministic mode` +- `RegExp` and regex literals -> `TypeError: RegExp is disabled in deterministic mode` (**baseline-v1 only**) - `Proxy` -> `TypeError: Proxy is disabled in deterministic mode` -- `Promise` and statics (`resolve`, `reject`, `all`, `race`, `any`, `allSettled`) -> `TypeError: Promise is disabled in deterministic mode` +- `Promise` and statics (`resolve`, `reject`, `all`, `race`, `any`, `allSettled`) -> `TypeError: Promise is disabled in deterministic mode` (**baseline-v1 only**) - `Math.random()` -> `TypeError: Math.random is disabled in deterministic mode` -- `ArrayBuffer` -> `TypeError: ArrayBuffer is disabled in deterministic mode` +- `ArrayBuffer` -> `TypeError: ArrayBuffer is disabled in deterministic mode` (**baseline-v1 / compat-regexp-v1**) - `SharedArrayBuffer` -> `TypeError: SharedArrayBuffer is disabled in deterministic mode` -- `DataView` -> `TypeError: DataView is disabled in deterministic mode` -- Typed arrays: `Uint8Array`, `Uint8ClampedArray`, `Int8Array`, `Uint16Array`, `Int16Array`, `Uint32Array`, `Int32Array`, `BigInt64Array`, `BigUint64Array`, `Float16Array`, `Float32Array`, `Float64Array` -> `TypeError: Typed arrays are disabled in deterministic mode` +- `DataView` -> `TypeError: DataView is disabled in deterministic mode` (**baseline-v1 / compat-regexp-v1**) +- Typed arrays: `Uint8Array`, `Uint8ClampedArray`, `Int8Array`, `Uint16Array`, `Int16Array`, `Uint32Array`, `Int32Array`, `BigInt64Array`, `BigUint64Array`, `Float16Array`, `Float32Array`, `Float64Array` -> `TypeError: Typed arrays are disabled in deterministic mode` (**baseline-v1 / compat-regexp-v1**) - `Atomics` -> `TypeError: Atomics is disabled in deterministic mode` - `WebAssembly` -> `TypeError: WebAssembly is disabled in deterministic mode` -- `console.log/info/warn/error/debug` -> `TypeError: console is disabled in deterministic mode` +- `console.log/info/warn/error/debug` -> `TypeError: console is disabled in deterministic mode` (**baseline-v1 / compat-regexp-v1**) - `print` -> `TypeError: print is disabled in deterministic mode` -- `Array.prototype.sort` -> `TypeError: Array.prototype.sort is disabled in deterministic mode` +- `Array.prototype.sort` -> `TypeError: Array.prototype.sort is disabled in deterministic mode` (**baseline-v1 / compat-regexp-v1**) Notes: @@ -89,12 +112,16 @@ Why: ### Time, scheduling, and asynchrony -Absent/disabled: +Absent/disabled by profile: - `Date` - `setTimeout` / `setInterval` -- `queueMicrotask` -- `Promise` +- `queueMicrotask` (`baseline-v1`, `compat-regexp-v1`) +- `Promise` (`baseline-v1`, `compat-regexp-v1`) + +Enabled in compatibility profiles: + +- `Promise` jobs + `queueMicrotask` (`compat-general-v1`, `compat-binary-v1`) Why: @@ -117,12 +144,17 @@ Why: ### Binary buffers, shared memory, and low-level representation -Disabled: +Disabled by profile: - `ArrayBuffer`, `DataView`, typed arrays (`Uint8Array`, `Float64Array`, …) + (`baseline-v1`, `compat-regexp-v1`) - `SharedArrayBuffer` - `Atomics` +Enabled in compatibility profiles: + +- `ArrayBuffer`, `DataView`, typed arrays (`compat-binary-v1`) + Why: - **Representation leaks:** typed views can observe IEEE-754 edge cases like NaN payload bits and `-0` @@ -242,7 +274,7 @@ The deterministic init does not install these globals; `typeof` returns `"undefi - `Date` - `setTimeout` / `setInterval` -- `queueMicrotask` +- `queueMicrotask` (**baseline-v1 / compat-regexp-v1**) ## Host namespace and ergonomic globals diff --git a/docs/ecosystem-compatibility-baseline-0.4.1.json b/docs/ecosystem-compatibility-baseline-0.4.1.json new file mode 100644 index 0000000..e3e01f7 --- /dev/null +++ b/docs/ecosystem-compatibility-baseline-0.4.1.json @@ -0,0 +1,36 @@ +{ + "release": "0.4.1", + "date": "2026-03-13", + "summary": { + "greenCount": 16, + "redCount": 8, + "flagshipCount": 1 + }, + "fixtures": [ + { "id": "flagship-knowledge-pack", "kind": "flagship", "expectedStage": "success" }, + { "id": "green-chess", "kind": "positive", "expectedStage": "success" }, + { "id": "green-base64", "kind": "positive", "expectedStage": "success" }, + { "id": "green-noble-sha", "kind": "positive", "expectedStage": "success" }, + { "id": "green-semver", "kind": "positive", "expectedStage": "success" }, + { "id": "green-he", "kind": "positive", "expectedStage": "success" }, + { "id": "green-path-to-regexp", "kind": "positive", "expectedStage": "success" }, + { "id": "green-fast-json-stable-stringify", "kind": "positive", "expectedStage": "success" }, + { "id": "green-json-logic-js", "kind": "positive", "expectedStage": "success" }, + { "id": "green-crc32", "kind": "positive", "expectedStage": "success" }, + { "id": "green-tinyqueue", "kind": "positive", "expectedStage": "success" }, + { "id": "green-fflate", "kind": "positive", "expectedStage": "success" }, + { "id": "green-linkify-it", "kind": "positive", "expectedStage": "success" }, + { "id": "green-markdown-it", "kind": "positive", "expectedStage": "success" }, + { "id": "green-escape-string-regexp", "kind": "positive", "expectedStage": "success" }, + { "id": "green-fast-deep-equal", "kind": "positive", "expectedStage": "success" }, + { "id": "green-stress-corpus", "kind": "positive", "expectedStage": "success" }, + { "id": "red-diff-timers", "kind": "negative", "expectedStage": "builder_reject" }, + { "id": "red-yaml-date", "kind": "negative", "expectedStage": "builder_reject" }, + { "id": "red-graphlib-proxy", "kind": "negative", "expectedStage": "builder_reject" }, + { "id": "red-dynamic-import", "kind": "negative", "expectedStage": "builder_reject" }, + { "id": "red-proxy", "kind": "negative", "expectedStage": "builder_reject" }, + { "id": "red-math-random", "kind": "negative", "expectedStage": "builder_reject" }, + { "id": "red-lodash-function-constructor", "kind": "negative", "expectedStage": "artifact_validation" }, + { "id": "red-function-constructor", "kind": "negative", "expectedStage": "artifact_validation" } + ] +} diff --git a/docs/ecosystem-compatibility-report.md b/docs/ecosystem-compatibility-report.md new file mode 100644 index 0000000..eaa6469 --- /dev/null +++ b/docs/ecosystem-compatibility-report.md @@ -0,0 +1,75 @@ +# Ecosystem Compatibility Report + +This report tracks the current certification corpus in +`apps/ecosystem-certifier/src/shared/fixtures.ts`. + +## Green corpus (25 fixtures) + +All fixtures below are expected to pass with strict node/browser parity. +This corpus currently includes **24 third-party packages** plus one seeded +stress fixture. + +| Package | Fixture id | Profile | +| --- | --- | --- | +| `chess.js` | `green-chess` | `compat-general-v1` | +| `base64-js` | `green-base64` | `compat-binary-v1` | +| `@noble/hashes` | `green-noble-sha` | `compat-binary-v1` | +| `semver` | `green-semver` | `compat-general-v1` | +| `he` | `green-he` | `compat-general-v1` | +| `path-to-regexp` | `green-path-to-regexp` | `compat-general-v1` | +| `fast-json-stable-stringify` | `green-fast-json-stable-stringify` | `compat-general-v1` | +| `json-logic-js` | `green-json-logic-js` | `compat-general-v1` | +| `crc-32` | `green-crc32` | `compat-binary-v1` | +| `tinyqueue` | `green-tinyqueue` | `compat-general-v1` | +| `fflate` | `green-fflate` | `compat-binary-v1` | +| `linkify-it` | `green-linkify-it` | `compat-general-v1` | +| `markdown-it` | `green-markdown-it` | `compat-binary-v1` | +| `escape-string-regexp` | `green-escape-string-regexp` | `compat-general-v1` | +| `fast-deep-equal` | `green-fast-deep-equal` | `compat-general-v1` | +| `camelcase` | `green-camelcase` | `compat-general-v1` | +| `decamelize` | `green-decamelize` | `compat-general-v1` | +| `fastest-levenshtein` | `green-fastest-levenshtein` | `compat-binary-v1` | +| `dijkstrajs` | `green-dijkstrajs` | `compat-general-v1` | +| `spark-md5` | `green-spark-md5` | `compat-binary-v1` | +| `query-string` | `green-query-string` | `compat-general-v1` | +| `deepmerge` | `green-deepmerge` | `compat-general-v1` | +| `sort-keys` | `green-sort-keys` | `compat-general-v1` | +| `array-move` | `green-array-move` | `compat-general-v1` | +| Seeded stress corpus | `green-stress-corpus` | `compat-general-v1` | + +## Red corpus (8 scenarios) + +All fixtures below are expected deterministic failures with stable failure stage. + +| Scenario | Fixture id | Expected stage | Why | +| --- | --- | --- | --- | +| `diff` timer usage | `red-diff-timers` | `builder_reject` | package references `setTimeout` | +| `yaml` date usage | `red-yaml-date` | `builder_reject` | package references `Date` | +| `graphlib` proxy usage | `red-graphlib-proxy` | `builder_reject` | package references `Proxy` | +| Dynamic import | `red-dynamic-import` | `builder_reject` | `import()` disabled | +| Proxy API | `red-proxy` | `builder_reject` | `Proxy` disabled | +| Randomness API | `red-math-random` | `builder_reject` | `Math.random()` disabled | +| `lodash-es` runtime codegen path | `red-lodash-function-constructor` | `artifact_validation` | runtime reaches `Function` constructor path | +| Function constructor explicit | `red-function-constructor` | `artifact_validation` | deterministic runtime rejects dynamic codegen | + +## Flagship workload status + +- Fixture id: `flagship-knowledge-pack` +- Uses mixed deterministic package set (markdown/linkification/rules/semver/binary + decode/hash/queue ordering). +- Runs under `compat-binary-v1` with Host.v2 and emits deterministic tape + evidence. + +## Machine-readable evidence + +Generate and archive: + +```bash +node apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs --out-dir artifacts/workload-certification +node apps/ecosystem-certifier/scripts/generate-compatibility-delta-report.mjs --current-dir artifacts/workload-certification --out-dir artifacts/workload-certification +``` + +Use `compatibilityMatrix` and `records` in the generated JSON as canonical +source-of-truth for certification decisions. +Use `compatibility-delta-report.json` to compare fixture coverage against the +previous release baseline. diff --git a/docs/embedders.md b/docs/embedders.md new file mode 100644 index 0000000..e3ca51c --- /dev/null +++ b/docs/embedders.md @@ -0,0 +1,69 @@ +# Embedder integration guide + +This document defines integration boundaries for systems embedding blue-quickjs. + +## Scope boundary + +This repository owns **deterministic evaluation**. + +It does **not** own: + +- workflow orchestration, +- overlay/commit pipelines, +- external persistence or job scheduling. + +Those belong to the embedding system (for example document-processor). + +## Embedder responsibilities + +1. Build artifacts using deterministic builder outputs (`ProgramArtifact.v2`, + `ModulePack.v1`). +2. Provide deterministic host handlers for declared ABI functions. +3. Supply deterministic input envelope data (`I`) and gas limit (`G`). +4. Pin and validate: + - ABI manifest hash, + - engine build hash, + - execution profile. +5. Treat evaluator output (`result`, `gas`, `tape`, errors) as immutable + execution evidence. + +## Runtime constraints embedders must respect + +- No reentrant host calls into VM. +- No async host callbacks during synchronous VM evaluation. +- No hidden side channels (clock, randomness, network/filesystem) bypassing ABI. + +## Recommended integration flow + +1. Resolve/build source -> `ModulePack.v1` + compatibility report. +2. Construct `ProgramArtifact.v2` with explicit profile and pins. +3. Execute via SDK runtime. +4. Record deterministic outputs and optional tape/trace. +5. Perform policy-specific post-processing outside evaluator boundary. + +## Versioning expectations + +- Treat profile names, ABI ids/versions, and value-model version as explicit + contracts. +- Do not silently upgrade artifacts across incompatible versions. + +## Parity expectations + +For release confidence, embedders should run strict parity checks across the +supported **consensus executors**: + +- wasm in Node, +- wasm in browser, + +matching on result hash, gas, tape, error code/tag, and exact OOG boundary. + +Native harness parity remains strongly recommended for diagnostics and +reconciliation. Treat native as non-consensus unless it is explicitly certified +for strict zero-delta parity against canonical wasm execution. + +## See also + +- `docs/sdk.md` +- `docs/program-artifact-v2.md` +- `docs/module-pack.md` +- `docs/value-model-v2.md` diff --git a/docs/examples.md b/docs/examples.md new file mode 100644 index 0000000..8762dbc --- /dev/null +++ b/docs/examples.md @@ -0,0 +1,14 @@ +# Examples guide + +The runnable deterministic example corpus is maintained in: + +- [`examples/README.md`](../examples/README.md) + +That guide includes: + +- all 10 required example categories, +- source-file locations for each scenario, +- expected gas/result/OOG evidence keys, +- the in-repo playground entry point for interactive inspection, +- consensus executor reproducibility commands (`wasm-node` vs `wasm-browser`), +- native diagnostic reproducibility commands. diff --git a/docs/execution-profiles.md b/docs/execution-profiles.md new file mode 100644 index 0000000..393dfcd --- /dev/null +++ b/docs/execution-profiles.md @@ -0,0 +1,90 @@ +# Execution profiles and capability registry + +Baseline anchor: `docs/baseline-1.md`. + +This document defines the **profile model** for runtime capability gating and +builder compatibility checks. + +## Design decision + +The platform uses: + +1. a **granular internal capability registry**, and +2. a **small public set of composite profiles**. + +We do **not** expose a growing list of one-feature public profiles. + +## Registry shape (conceptual) + +```ts +type Capability = + | 'regexp' + | 'promiseJobs' + | 'queueMicrotask' + | 'stableSort' + | 'consoleShim' + | 'typedArrays' + | 'dvBytes'; +``` + +The registry is the single source of truth for: + +- runtime validation, +- VM feature-flag wiring, +- builder compatibility scan, +- native harness profile flags, +- docs capability tables. + +## Public profiles (normative) + +### `baseline-v1` + +Deterministic baseline close to current behavior: + +- no Promise jobs / microtasks, +- no typed arrays / ArrayBuffer / DataView, +- no DV bytes boundary, +- no dynamic import/timers/runtime fs-network. + +### `compat-general-v1` + +`baseline-v1` +: + +- `regexp` +- `promiseJobs` +- `queueMicrotask` +- `stableSort` +- `consoleShim` + +### `compat-binary-v1` + +`compat-general-v1` +: + +- `typedArrays` +- `dvBytes` + +## Transitional compatibility profile + +`compat-regexp-v1` remains accepted as a transitional compatibility alias during +the migration from P11/P12 fixtures. It currently maps to: + +- `baseline-v1` + `regexp` + +New integrations should prefer `compat-general-v1` / `compat-binary-v1`. + +## Artifact rule + +`ProgramArtifact.v2.executionProfile` is required for build outputs and runtime +execution. Silent profile defaults are not allowed in release artifacts. + +## Compatibility policy + +- Baseline behavior MUST NOT widen unintentionally. +- Profile changes require explicit spec and tests. +- Public profile names are versioned contracts. + +## See also + +- `docs/program-artifact-v2.md` +- `docs/value-model-v2.md` +- `docs/determinism-profile.md` diff --git a/docs/faq.md b/docs/faq.md new file mode 100644 index 0000000..214a43d --- /dev/null +++ b/docs/faq.md @@ -0,0 +1,53 @@ +# FAQ + +## Is BlueQuickjs a general-purpose JavaScript runtime? + +No. It is a deterministic execution product for consensus-critical workloads. +The repo intentionally excludes or gates many capabilities that ordinary JS +runtimes expose freely. + +## What is the consensus-safe executor matrix? + +Today it is: + +- `wasm-node` +- `wasm-browser` + +using the canonical `wasm32` release engine. + +## Is native consensus-safe? + +Not today. Native remains diagnostic-only unless release policy explicitly +promotes it later. + +## Why are imports build-time deterministic instead of runtime dynamic? + +Because runtime fetch/import behavior would widen the deterministic surface. +BlueQuickjs resolves imports ahead of time and executes a pinned +`ModulePack.v1`. + +## Why are there multiple execution profiles? + +To keep the minimal consensus baseline narrow while still supporting specific +compatibility surfaces in explicitly versioned contracts. + +## When can I use Promises? + +Only under compatibility profiles that enable Promise job draining, such as +`compat-general-v1` and `compat-binary-v1`. + +## When can I use typed arrays or bytes? + +Only under `compat-binary-v1`, with the corresponding DV2 / `Host.v2` +boundaries. + +## Why do `engineBuildHash` and `gasVersion` matter? + +They are the pins that keep artifacts tied to the exact engine bytes and gas +schedule they were certified against. + +## What should I trust: docs or generated evidence? + +Generated evidence. The docs should explain the product, but release-critical +truth comes from the consensus, workload, consumer-proof, and release-evidence +artifacts. diff --git a/docs/first-10-minutes.md b/docs/first-10-minutes.md new file mode 100644 index 0000000..0ab2227 --- /dev/null +++ b/docs/first-10-minutes.md @@ -0,0 +1,59 @@ +# First 10 minutes with BlueQuickjs + +This guide is for operators/auditors evaluating a release quickly. + +## 1) Build and run a deterministic smoke path + +```bash +pnpm install +bash tools/scripts/setup-emsdk.sh +source tools/emsdk/emsdk_env.sh +pnpm nx test smoke-node +pnpm nx run smoke-web:e2e +``` + +## 2) Generate release evidence bundle + +```bash +pnpm release-evidence:synthesize -- --out-dir artifacts/release-evidence +``` + +## 3) Verify evidence integrity + +```bash +pnpm release-evidence:verify -- --evidence-dir artifacts/release-evidence +``` + +## 4) Inspect key release pins + +From `docs/release-readiness-report.md` and release evidence summary: + +- `engineBuildHash` +- `gasVersion` +- consensus mismatch counts +- exact OOG parity status + +## 5) Validate max-gas safety model + +- Confirm OOG boundary parity checks are green in workload and consumer reports. +- Confirm release policy still enforces exact OOG boundary parity for consensus + executors. + +## 6) Confirm production scope claim + +- Consensus-safe claim is wasm-node vs wasm-browser required matrix. +- Native remains diagnostic-only unless explicitly promoted by release policy. + +## 7) Open the in-repo playground + +```bash +bash apps/bluequickjs-playground/scripts/dev.sh +``` + +Use the playground to inspect: + +- profiles, +- gas/result metadata, +- certified snapshot matches, +- red deterministic failures, +- exact OOG boundaries. diff --git a/docs/ga-cutover-decision.md b/docs/ga-cutover-decision.md new file mode 100644 index 0000000..28e010b --- /dev/null +++ b/docs/ga-cutover-decision.md @@ -0,0 +1,23 @@ +# GA cutover decision (wasm-consensus scope) + +## Recommendation + +Treat this release line as a **1.0.0 candidate for wasm-consensus scope**, +subject to final required-check enforcement and release-go/no-go signoff. + +## Scope boundary + +- In scope for 1.0.0 claim: + - deterministic wasm consensus executors (`wasm-node`, `wasm-browser`), + - strict value/error/gas/tape/OOG parity policy, + - generated and verifiable release evidence. +- Out of scope for 1.0.0 claim: + - native executor as a consensus gate (diagnostic-only unless explicitly + certified and promoted later). + +## Promotion prerequisites + +- Required checks marked as branch protection gates. +- Release evidence verification and tamper detection job green. +- Consumer proof matrix and publish rehearsal green. +- Go/no-go template completed with signoffs. diff --git a/docs/gas-schedule.md b/docs/gas-schedule.md index 0f094b8..356d96a 100644 --- a/docs/gas-schedule.md +++ b/docs/gas-schedule.md @@ -1,12 +1,15 @@ # Gas Schedule (Baseline #1) +> This file is generated from `tools/gas-spec/gas-spec.v3.json`. +> Update the gas spec source and rerun `node tools/gas-spec/render-gas-artifacts.mjs`. + Baseline anchor: see `docs/baseline-1.md` (determinism + canonical gas) and `docs/baseline-2.md` (host-call ABI/gas parameters). Scope: define canonical gas units for QuickJS execution and host calls per Baseline #1. This document is normative and must match harness assertions. ## Gas version and limits -- `JS_GAS_VERSION_LATEST = 2` +- `JS_GAS_VERSION_LATEST = 8` - Gas amounts are uint64. - `JS_GAS_UNLIMITED` disables charging and reports gas used as 0. - `JS_UseGas` subtracts from `gas_remaining`; if `amount > gas_remaining`, it sets `gas_remaining = 0` and throws an uncatchable `OutOfGas: out of gas` error. @@ -31,13 +34,49 @@ The per-element charge is applied for each iteration step, even when a hole is s Each allocation charges: -- Base: `JS_GAS_ALLOC_BASE = 3` +- Base: `JS_GAS_ALLOC_BASE = 0` - Byte charge: `1` gas per `16` requested bytes (`JS_GAS_ALLOC_PER_BYTE_SHIFT = 4`) Formula: - `JS_GAS_ALLOC_BASE + ceil(size / 16)` where `size` is the requested allocation size. +Current deterministic normalization model: + +- Mode: `none` +- Note: Canonical allocation charging no longer uses pointer-width normalization heuristics. +- No pointer-width normalization is applied. + +Canonical allocation classes (width-independent charged-byte formulas): + +- Object header: `64` +- Property slot: `16` +- Shape header: `48` +- Shape property entry: `12` +- String header: `0` +- Array slot: `8` +- Module record: `128` +- Module entry: `24` +- Promise/job base: `48` +- Promise/job arg unit: `8` +- ArrayBuffer header: `48` +- TypedArray backing unit: `1` +- TypedArray record: `40` +- Compiler function-def record: `512` +- Closure-var entry: `16` +- Var-ref pointer entry: `8` +- Var-ref record: `32` +- Generic dynamic-array unit: `16` +- Unknown-class small-allocation floor: `64` +- Unknown-class small-allocation max size: `4096` +- Unknown-class charges enabled: `false` +- Object-header charges enabled: `false` +- Property-slot charges enabled: `false` +- Shape charges enabled: `false` +- ArrayBuffer-header charges enabled: `false` +- TypedArray-backing charges enabled: `false` +- TypedArray-record charges enabled: `false` + ## Deterministic JSON builtin gas Deterministic mode exposes metered `JSON.parse` / `JSON.stringify` built-ins. These @@ -90,7 +129,7 @@ Interpretation: ## Garbage collection (GC) checkpoints - Automatic GC heuristics are disabled in deterministic mode (`js_trigger_gc` is a no-op and GC threshold is set to `-1`). -- A deterministic counter tracks requested allocation bytes. When it reaches `JS_DET_GC_THRESHOLD_BYTES = 512 * 1024`, `det_gc_pending` is set. +- A deterministic counter tracks charged allocation bytes. When it reaches `JS_DET_GC_THRESHOLD_BYTES = 524288`, `det_gc_pending` is set. - `JS_RunGCCheckpoint(ctx)` runs GC only when `det_gc_pending` is set; it then clears the flag and counter. - GC costs `0` gas; allocation gas amortizes it. - Checkpoints are invoked at deterministic points (pre/post eval and around host calls). @@ -100,9 +139,9 @@ Interpretation: Host-call gas uses parameters from the ABI manifest `gas` fields (see `docs/abi-manifest.md`). - Pre-charge before the host call: - - `gas_pre = base + (k_arg_bytes * request_bytes)` + - `base + (k_arg_bytes * request_bytes)` - Post-charge after response parse: - - `gas_post = (k_ret_bytes * response_bytes) + (k_units * units)` + - `(k_ret_bytes * response_bytes) + (k_units * units)` Where: @@ -119,5 +158,5 @@ Overflow during charge throws `TypeError: host_call gas overflow`. OOG on pre-ch - allocation gas, - deterministic `JSON.parse` gas, - deterministic `JSON.stringify` gas. -- Host-call gas is billed but not included in the trace totals; tests compute host gas as: - - `gasUsed - (opcode + array + allocation + jsonParse + jsonStringify)` +- Host-call gas is billed and tracked in dedicated host pre/post counters. + diff --git a/docs/glossary.md b/docs/glossary.md new file mode 100644 index 0000000..22d33db --- /dev/null +++ b/docs/glossary.md @@ -0,0 +1,67 @@ +# Glossary + +## ABI manifest + +The canonical manifest that defines which host functions exist, what numeric +IDs they use, and which ABI version an artifact expects. + +## Consensus-safe + +Part of the current release contract. Today that means `wasm-node` and +`wasm-browser` running the canonical `wasm32` release engine with exact parity +requirements. + +## Diagnostic-only + +Useful for debugging, investigation, or reconciliation, but not part of the +current consensus release gate. Native and WebKit runs currently live here. + +## DV / DV1 + +Deterministic Value encoding used at host/runtime boundaries for canonical +structured values that do not include byte strings. + +## DV2 + +Versioned extension of DV that adds canonical bytes support for `Host.v2` and +binary-heavy workloads. + +## engineBuildHash + +The SHA-256 identity pin for the engine build bytes. Release-mode artifacts use +this to ensure the runtime matches the intended Wasm engine. + +## execution profile + +A named capability contract that determines which compatibility features are +allowed during execution: + +- `baseline-v1` +- `compat-general-v1` +- `compat-binary-v1` + +## gasVersion + +The version number of the canonical gas schedule expected by an artifact and +runtime. + +## host-call tape + +The deterministic record of host calls emitted during execution, including +request/response hashes, gas before/after, and units charged. + +## ModulePack.v1 + +The canonical deterministic module graph artifact used to execute static ESM +without runtime network/filesystem/module-registry access. + +## OOG boundary + +The exact gas limit where execution changes from failure to success, or +vice versa. BlueQuickjs treats this boundary as release-critical evidence for +consensus executors. + +## ProgramArtifact.v2 + +The versioned execution artifact that carries source, profile, ABI pins, +engine pin, gas pin, and source kind. diff --git a/docs/head-verification-note.md b/docs/head-verification-note.md new file mode 100644 index 0000000..8b0ae81 --- /dev/null +++ b/docs/head-verification-note.md @@ -0,0 +1,89 @@ +# HEAD verification note + +This document is the quickest “state of HEAD” snapshot for engineers, auditors, +and release reviewers. Use it to confirm that the branch still matches the +current wasm-consensus product contract. + +## Consensus-safe scope + +Consensus-safe release scope remains: + +- `wasm-node` +- `wasm-browser` +- canonical `wasm32` release artifacts + +Release-critical parity is exact across those executors for: + +- value or error, +- gas used and gas remaining, +- host-call tape, +- first-success / last-failure OOG boundary. + +## Diagnostic-only scope + +The following remain outside the current consensus release gate: + +- native harness parity, +- WebKit browser runs, +- other Wasm variants or debug builds used for investigation. + +These surfaces are still useful for debugging and reconciliation, but they +should not be presented as consensus executors. + +## Pins and shipped contracts + +The release story at HEAD should be internally consistent across docs, runtime +checks, and generated evidence: + +- execution profiles: + - `baseline-v1` + - `compat-general-v1` + - `compat-binary-v1` +- builder/runtime artifact contract: + - `ProgramArtifact.v2` + - `ModulePack.v1` +- explicit pins: + - `engineBuildHash` + - `gasVersion` + - ABI manifest hash + +## What a reviewer should verify + +1. Consensus mismatch counts are zero. +2. Workload certification mismatch counts are zero. +3. OOG boundary parity is exact for the release corpus. +4. Consumer-proof tarball and Verdaccio rehearsals still pass. +5. Docs still describe the same scope that the generated evidence proves. + +## Quick verification commands + +```bash +source tools/emsdk/emsdk_env.sh +pnpm nx test smoke-node +pnpm nx run smoke-web:e2e +pnpm nx test ecosystem-certifier +pnpm nx run ecosystem-certifier:e2e +node tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs --out-dir artifacts/reproducibility-consensus +node apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs --out-dir artifacts/workload-certification +pnpm release-evidence:synthesize -- --out-dir artifacts/release-evidence +pnpm release-evidence:verify -- --evidence-dir artifacts/release-evidence +``` + +## Known limitations at HEAD + +- Consensus-safe execution is wasm-only; native remains diagnostic-only. +- Runtime network/fetch/import behavior is intentionally excluded from the + consensus surface. +- Live binary and Promise support are profile-gated and should not be assumed in + `baseline-v1`. + +## Where to continue + +- Product overview: [`README.md`](../README.md) +- Documentation hub: [`README.md`](./README.md) +- Architecture overview: [`architecture-overview.md`](./architecture-overview.md) +- Examples corpus: [`../examples/README.md`](../examples/README.md) +- Release readiness summary: [`release-readiness-report.md`](./release-readiness-report.md) +- Workload certification: [`workload-certification.md`](./workload-certification.md) +- Ecosystem compatibility: [`ecosystem-compatibility-report.md`](./ecosystem-compatibility-report.md) +- Consensus vs diagnostic scope: [`consensus-safe-vs-diagnostic-only.md`](./consensus-safe-vs-diagnostic-only.md) diff --git a/docs/host-call-abi.md b/docs/host-call-abi.md index 76d1980..3ad6063 100644 --- a/docs/host-call-abi.md +++ b/docs/host-call-abi.md @@ -2,13 +2,13 @@ Baseline anchor: see `docs/baseline-2.md`. -Scope: describe the single-dispatcher syscall (`host_call`) and generated `Host.v1` surface per Baseline #2 (e.g., §1.5, §2, §6.4, §9). +Scope: describe the single-dispatcher syscall (`host_call`) and generated `Host.v*` surface (`Host.v1`, `Host.v2`) per Baseline #2 (e.g., §1.5, §2, §6.4, §9). ## Goals - Define the Wasm import shape for `host_call` and the memory ownership contract. - Describe request/response bytes (DV), limits, and deterministic error handling. -- Explain how this import underpins the generated `Host.v1` surface and ergonomic globals. +- Explain how this import underpins generated `Host.v*` surfaces and ergonomic globals. ## Wasm import surface (T-037) diff --git a/docs/implementation-plan.md b/docs/implementation-plan.md index 90437fe..1fd1f24 100644 --- a/docs/implementation-plan.md +++ b/docs/implementation-plan.md @@ -1,5 +1,19 @@ # Deterministic QuickJS-in-Wasm Evaluator (Nx Monorepo) — Implementation Plan (Baseline #1 + #2 Compliant) +> Historical design and implementation log. +> +> This file records the incremental execution plan that built the current +> repository. It is still useful for design history, acceptance criteria, and +> traceability, but it should not be read as the fastest overview of the +> current product surface. +> +> For the current state of the product, start with: +> +> - `README.md` +> - `docs/README.md` +> - `docs/head-verification-note.md` +> - `docs/architecture-overview.md` + This file is the “source of truth” execution plan for Codex (Cursor IDE) to implement a deterministic QuickJS-in-Wasm **JS evaluator** with: - **Canonical gas metering inside QuickJS** (Baseline #1), @@ -20,7 +34,13 @@ However, Baseline #2 still applies: even read-only `document(path)` is a host ca - **Nx monorepo** (TypeScript-first) using **pnpm**, with consistent tooling (lint/format/test/build) and CI. - **QuickJS fork** lives as a **git submodule** at `vendor/quickjs` (pinned commit). All determinism + gas + host ABI changes live in that fork. -- **Deterministic execution profile** is enforced in the VM init: time/random/async/network/fs/locale are removed or stubbed; typed arrays / ArrayBuffer / WebAssembly are disabled; dangerous features like `eval`/`Function` are disabled (Baseline #1 §1B–§1C, §3). +- **Deterministic execution profile** is enforced in VM init with explicit + profile contracts: baseline removes/stubs ambient nondeterministic surfaces + (time/random/network/fs/locale and dynamic-codegen paths), while + compatibility profiles (`compat-general-v1`, `compat-binary-v1`) selectively + re-enable deterministic Promise/job-queue and binary capabilities. Dangerous + dynamic-codegen surfaces (`eval`/`Function`) remain disabled (Baseline #1 + §1B–§1C, §3). - **Canonical gas** is implemented inside QuickJS: opcode metering, metered C builtins, allocation charges, deterministic GC checkpoints (Baseline #1 §2B). - **Single syscall ABI (`host_call`)** for all host capabilities: `fn_id + request_bytes -> response_bytes`, with **manifest mapping**, **manifest hash validation**, and **DV canonical encoding** (Baseline #2 §1.1–§1.4, §2). - VM exposes a frozen **`Host.v1`** namespace generated from the manifest, and provides ergonomic globals: @@ -83,7 +103,7 @@ This repo ensures: --- -# Current repo snapshot (kickoff) +# Historical repo snapshot at kickoff - Nx 22.2 workspace scaffold exists with pnpm (`nx.json`, `tsconfig.base.json`, `package.json`, `pnpm-workspace.yaml`). - Publishable libs are scaffolded (`dv`, `abi-manifest`, `quickjs-wasm`, `quickjs-runtime`), with internal libs (`quickjs-wasm-build`, `test-harness`) plus smoke apps (`smoke-node`, `smoke-web`) and placeholder src/tests passing build/test targets. @@ -843,7 +863,7 @@ Produce a minimal Emscripten-built QuickJS-in-Wasm binary that exposes the canon - The vitest spec at `libs/test-harness/src/lib/gas-equivalence.spec.ts` covers the full gas fixture set (`zero-precharge`, `gc-checkpoint-budget`, `loop-oog`, `constant`, `addition`, `string-repeat`) against the wasm harness using the wasm32 artifact by default, driving `qjs_det_init`/`qjs_det_eval` with the Host.v1 manifest/context and asserting DV payloads + gas remaining/used. Setting `QJS_WASM_VARIANT=wasm64` switches the test to the memory64 artifact and restores native-vs-wasm comparisons for debugging. - The wasm build defaults to wasm32 with `-sWASM_BIGINT=1`; `libs/quickjs-wasm-build/scripts/build-wasm.sh` accepts `WASM_VARIANTS=wasm32,wasm64` to also emit `quickjs-eval-wasm64{,-debug}.{js,wasm}`, and `WASM_BUILD_TYPES=release,debug` to control whether debug builds are emitted. Harnesses use `getQuickjsWasmArtifacts(variant, buildType)` with `QJS_WASM_BUILD_TYPE` defaulting to `release`. -- **Compatibility note:** wasm32 gas numbers diverge from native because of the 32-bit allocator layout, but Node and browser harnesses now agree on the wasm32 outputs. wasm32 is the chosen canonical variant; wasm64 is not planned/supported (memory64 remains non-portable in mainstream browsers), so native-parity debugging should proceed within wasm32 expectations. +- **Compatibility note (historical):** Earlier parity investigations observed wasm32/native gas drift from allocator-layout effects. That note is retained here for historical context only. Current strict parity closure work supersedes it for release acceptance: consensus gating is wasm-node vs wasm-browser on pinned wasm32 artifacts, while native remains diagnostic unless explicitly promoted by policy. **Current state (P2.5 T-029 Subtask C):** @@ -1920,6 +1940,624 @@ Deterministic ABI entrypoints are available; wasm gas consumers have been migrat --- +## Phase P9 — Execution surface semantics hardening + +### T-100: Clarify raw script evaluation semantics and regressions + +**Phase:** P9 – Execution surface semantics hardening +**Status:** DONE +**Depends on:** T-064, T-065, T-066 + +**Goal:** +Make it unambiguous what `blue-quickjs` means by “evaluate code”, and lock the common `return` vs final-expression confusion with deterministic errors and tests. + +**Detailed tasks:** + +- [x] Update docs to define raw script mode clearly: + - [x] `program.code` is evaluated as a global script. + - [x] The final expression value is used as the result. + - [x] Top-level `return` is invalid in this repo’s execution mode. + - [x] `emit(...)` side effects are supported through Host.v1 wrappers. +- [x] Add runtime error classification for execution-surface mismatches (`EXECUTION_SURFACE_MISMATCH`). +- [x] Add regression tests for: + - [x] final-expression result in raw script mode, + - [x] top-level return mismatch classification, + - [x] emit side effects with explicit final result. + +**Acceptance criteria:** + +- [x] A single docs paragraph defines evaluator semantics unambiguously. +- [x] `return` vs final-expression confusion is covered by automated regression tests. +- [x] Runtime error surfaces distinguish execution-surface mismatch from generic JS exceptions and invalid-output failures. + +**Current state (P9 T-100):** + +- `docs/sdk.md` and `docs/implementation-summary.md` now explicitly document raw script semantics, final-expression results, top-level `return` behavior, and `emit` side effects. +- `libs/quickjs-runtime/src/lib/evaluate-errors.ts` introduces `execution-surface-mismatch` mapping (`code: EXECUTION_SURFACE_MISMATCH`, `tag: vm/execution_surface`) for top-level return syntax errors. +- `libs/quickjs-runtime/src/lib/evaluate.spec.ts` includes targeted regression coverage for raw script final expressions, top-level return mismatch, and emit side effects. + +--- + +## Phase P10 — Deterministic bundling for library reuse + +### T-110: Add deterministic source bundler + compatibility scan + +**Phase:** P10 – Deterministic bundling +**Status:** DONE +**Depends on:** T-064, T-066 + +**Goal:** +Enable practical multi-file JS library reuse by deterministically bundling source graphs into a single `program.code` string before VM execution. + +**Detailed tasks:** + +- [x] Add new library `libs/deterministic-bundler`. +- [x] Implement deterministic bundle output (stable code + SHA-256 content hash). +- [x] Add compatibility scanner with deterministic diagnostics for forbidden surfaces. +- [x] Keep scanner profile-aware (`baseline-v1` vs `compat-regexp-v1`). +- [x] Add unit tests for hash stability, rejection diagnostics, and profile-aware regexp handling. +- [x] Document bundling workflow in SDK/docs. + +**Acceptance criteria:** + +- [x] Multi-file source graphs bundle into a single deterministic source string. +- [x] Same inputs yield the same output hash across repeated runs. +- [x] Compatibility violations are deterministic and test-covered. + +**Current state (P10 T-110):** + +- `@blue-quickjs/deterministic-bundler` now exposes: + - `bundleDeterministicProgram(...)` → `{ code, contentHash, meta }` + - `scanCompatibility(...)` → deterministic diagnostics with profile awareness. +- Bundles are emitted with stable line endings and an explicit default-export expression suffix so they can be evaluated directly as `program.code`. +- Tests in `libs/deterministic-bundler/src/lib/deterministic-bundler.spec.ts` verify deterministic hash stability, baseline rejection of forbidden surfaces, and compat-regexp acceptance. + +--- + +## Phase P11 — Profile-gated RegExp compatibility + +### T-120: Add explicit `compat-regexp-v1` execution profile + +**Phase:** P11 – Compatibility profile gating +**Status:** DONE +**Depends on:** T-100, T-110 + +**Goal:** +Support real-world regex-dependent libraries (for example chess.js) without changing baseline defaults. + +**Detailed tasks:** + +- [x] Extend program artifact validation with optional `executionProfile`: + - [x] `baseline-v1` (default behavior) + - [x] `compat-regexp-v1` (opt-in compatibility mode) +- [x] Propagate profile feature flags through runtime init: + - [x] TS runtime -> wasm `qjs_det_init(..., feature_flags)` -> `JS_InitDeterministicContext`. +- [x] Keep baseline behavior unchanged: + - [x] baseline still disables RegExp and regex literals deterministically. +- [x] Enable regexp only when profile flag is explicitly set. +- [x] Add tests for baseline-vs-compat profile behavior in runtime and harness layers. + +**Acceptance criteria:** + +- [x] Baseline profile still rejects regexp usage deterministically. +- [x] `compat-regexp-v1` runs regexp code successfully. +- [x] Profile selection is explicit in the program artifact and test-covered. + +**Current state (P11 T-120):** + +- `libs/quickjs-runtime/src/lib/quickjs-runtime.ts` validates `executionProfile`, and `deterministic-init.ts` maps it to deterministic feature flags passed into wasm init. +- `libs/quickjs-wasm-build/src/wasm/quickjs_wasm.c` now accepts `feature_flags` in `qjs_det_init` and forwards them to `JS_InitDeterministicContext`. +- `vendor/quickjs/quickjs.h` defines `JS_DETERMINISTIC_FEATURE_REGEXP`, and `vendor/quickjs/quickjs-host.c` gates RegExp disablement/enablement on this flag. +- `libs/quickjs-runtime/src/lib/evaluate.spec.ts` and `tools/quickjs-native-harness/scripts/test.sh` verify baseline rejection and compat acceptance for regexp behavior. + +--- + +## Phase P12 — Chess.js deterministic reuse acceptance + +### T-130: Bundle chess.js and validate `e2e6` legality check + +**Phase:** P12 – Library reuse acceptance +**Status:** DONE +**Depends on:** T-110, T-120 + +**Goal:** +Prove end-to-end third-party library reuse by bundling chess.js and evaluating whether `e2e6` is legal from the initial board position. + +**Detailed tasks:** + +- [x] Add chess fixture entry source under `libs/test-harness/fixtures/library-reuse/chess-entry.ts`. +- [x] Add shared chess fixture constants for program/input/gas/manifest expectations. +- [x] Add runtime-level test that bundles chess.js and evaluates the bundled code deterministically. +- [x] Add smoke-node acceptance coverage for chess library reuse. +- [x] Add smoke-web Playwright parity coverage comparing browser and Node outputs for the bundled chess fixture. + +**Acceptance criteria:** + +- [x] Chess.js is bundled into deterministic single-source code. +- [x] Evaluated result for `e2e6` legality is `false`. +- [x] Node/browser parity test passes for result and gas outputs. + +**Current state (P12 T-130):** + +- `@blue-quickjs/test-harness` now includes chess fixture assets/constants (`CHESS_LIBRARY_ENTRY_PATH`, expected result, gas/input/manifest defaults). +- `libs/quickjs-runtime/src/lib/chess-library-reuse.spec.ts` bundles chess.js via `@blue-quickjs/deterministic-bundler`, evaluates with `executionProfile: "compat-regexp-v1"`, and asserts deterministic repeated gas. +- `apps/smoke-node/src/lib/chess-library-reuse.spec.ts` validates chess bundling/evaluation in the Node smoke project. +- `apps/smoke-web/chess-library-reuse.html`, `apps/smoke-web/src/chess-library-reuse.ts`, and `apps/smoke-web/tests/chess-library-reuse.spec.ts` provide browser execution and Node/browser parity checks for the chess fixture. + +--- + +## Phase P13 — Design reset for next-generation execution surface + +### T-140: Lock post-P12 artifact/profile/value-model architecture + +**Phase:** P13 – Design reset +**Status:** DONE +**Depends on:** T-130 + +**Goal:** +Freeze the architecture for P14+ so implementation work no longer depends on +chat context or ad-hoc decisions. + +**Deliverables:** + +- [x] Add `docs/program-artifact-v2.md`. +- [x] Add `docs/module-pack.md`. +- [x] Add `docs/execution-profiles.md`. +- [x] Add `docs/builder.md`. +- [x] Add `docs/value-model-v2.md`. +- [x] Add `docs/embedders.md`. +- [x] Update docs index and cross-references (`docs/README.md`, `docs/sdk.md`, `docs/implementation-summary.md`, `docs/release-policy.md`). + +**Decision log (locked in P13):** + +1. **ProgramArtifact.v2 is the next canonical artifact.** + It requires explicit `executionProfile`, explicit `sourceKind` (`script` or + `module-pack`), and version pinning metadata. +2. **ModulePack.v1 is the first-class reusable source artifact.** + Runtime executes static modules directly from in-memory pack data. +3. **Composite profile model is mandatory.** + Public profiles: `baseline-v1`, `compat-general-v1`, `compat-binary-v1`, + backed by a single capability registry. +4. **DV2/bytes track is mandatory for this iteration.** + Binary boundary support is introduced as versioned value-model/ABI evolution, + not in-place DV1 mutation. +5. **Builder naming direction is locked.** + `deterministic-bundler` is treated as transitional; target product surface is + deterministic builder semantics. +6. **`engineBuildHash` is required for builder-produced release artifacts.** + +**Open design questions (must stay < 3):** + +1. Should top-level await support be included in P17 or deferred to a post-P21 + phase if scheduler complexity threatens parity guarantees? +2. Should `ModulePack.v1.graphHash` include canonical source-map payloads by + default, or should source maps remain separately hashed metadata? + +**Acceptance criteria:** + +- [x] P13 docs exist and are cross-linked. +- [x] Locked decisions are explicit and centralized. +- [x] Unresolved design question count is `2` (<= 2 target). + +**Current state (P13 T-140):** + +- The new architecture docs are now present and linked: + - `program-artifact-v2` + - `module-pack` + - `execution-profiles` + - `builder` + - `value-model-v2` + - `embedders` +- Existing docs that previously implied DV bytes in the current runtime were + corrected to reflect current DV1 scope and the DV2 migration track. + +--- + +## Phase P14 — Deterministic builder evolution + +### T-150: Introduce module-pack builder API and migration package + +**Phase:** P14 – Deterministic builder +**Status:** DONE +**Depends on:** T-140 + +**Goal:** +Evolve deterministic-bundler from script-only output into deterministic builder +capabilities centered on `ModulePack.v1`, while preserving script-mode bridging. + +**Detailed tasks:** + +- [x] Add `buildDeterministicModulePack(...)` API to deterministic-bundler. +- [x] Emit `ModulePack.v1` fields (`modules`, `entrySpecifier`, `graphHash`, + `builderVersion`, `dependencyIntegrity`) with canonical ordering. +- [x] Emit canonical source maps (path-clean, stable JSON key ordering). +- [x] Run compatibility scanning on transformed module output. +- [x] Add builder fixture coverage for: + - workspace TS graph, + - npm ESM package resolution, + - npm CJS package resolution. +- [x] Add transitional migration package `@blue-quickjs/deterministic-builder` + that re-exports deterministic builder APIs. +- [x] Emit full compatibility report artifact schema (beyond scan diagnostics). +- [x] Emit `ProgramArtifact.v2` build artifact directly from builder API. +- [x] Add dedicated graph-hash golden fixtures to lock serialization format. + +**Current state (P14 T-150):** + +- `libs/deterministic-bundler/src/lib/deterministic-bundler.ts` now exports + `buildDeterministicModulePack(...)` and `ModulePack.v1`-aligned types. +- Builder output includes: + - deterministic module ordering by canonical specifier, + - canonical graph hashing via stable JSON serialization, + - lockfile-derived dependency integrity hash, + - optional script artifact emission for transitional workflows. +- Builder API now emits: + - `CompatibilityReport.v1` (profile, module count, rule counts, diagnostics), + - optional `ProgramArtifact.v2` embedding emitted `ModulePack.v1`. +- Source maps are sanitized to remove absolute host paths before serialization. +- `libs/deterministic-bundler/src/lib/deterministic-bundler.spec.ts` covers: + - deterministic repeated module-pack builds, + - local npm-style ESM package import, + - local npm-style CJS package conversion/import. +- New package `libs/deterministic-builder` provides migration-friendly re-export + surface and independent test coverage. +- `libs/quickjs-runtime/src/lib/quickjs-runtime.ts` now includes + `ProgramArtifactV2` and `ModulePackV1` validation scaffolding ahead of P15. +- Graph hash serialization is pinned by deterministic-bundler golden test fixture + (`keeps graphHash stable for a golden fixture`). + +--- + +## Phase P15 — ProgramArtifact.v2 runtime execution path + +### T-160: Wire ProgramArtifact.v2 into evaluate pipeline + +**Phase:** P15 – Runtime module-pack execution +**Status:** COMPLETE +**Depends on:** T-150 + +**Goal:** +Enable `ProgramArtifact.v2` execution entry in the runtime pipeline as the +bridge toward first-class module-pack execution. + +**Detailed tasks:** + +- [x] Accept `ProgramArtifact.v2` at `evaluate(...)` API boundary. +- [x] Execute `sourceKind: "script"` through existing deterministic VM path. +- [x] Add test coverage for ProgramArtifact.v2 script execution. +- [x] Implement in-memory deterministic module loader for `ModulePack.v1`. +- [x] Execute module entry and selected export in runtime (not script bridge). +- [x] Add module-pack parity fixtures (node/browser/native result+gas+tape). + +**Current state (P15 T-160):** + +- `libs/quickjs-runtime/src/lib/evaluate.ts` now normalizes v1/v2 program + artifacts and executes v2 script sources directly. +- ProgramArtifact.v2 module-pack path now executes via wasm runtime entrypoint + `qjs_det_eval_module_pack(...)` with an in-memory module loader backed only by + pack sources. +- Runtime validates `modulePack.graphHash` before VM execution and maps + deterministic module-pack errors: + - `MODULE_PACK_HASH_MISMATCH` + - `MODULE_SPECIFIER_NOT_FOUND` + - `MODULE_EXPORT_MISSING` + - `MODULE_RESOLUTION_ERROR` + - `MODULE_EVALUATION_ERROR` +- `libs/quickjs-runtime/src/lib/evaluate.spec.ts` now includes v2 module-pack + tests for default export, named export, cyclic imports, missing specifier, + missing export, and hash mismatch. +- Added module-pack parity fixture suites across smoke node/browser surfaces: + - `libs/test-harness/src/lib/module-pack-fixtures.ts` + - `apps/smoke-node/src/lib/module-pack-parity.spec.ts` + - `apps/smoke-web/module-pack-fixtures.html` + - `apps/smoke-web/src/module-pack-fixtures.ts` + - `apps/smoke-web/tests/module-pack-fixtures.spec.ts` +- Added native parity assertion suite for module-pack fixtures: + - `tools/quickjs-native-harness/scripts/module-pack-parity.mjs` + - wired into `tools/quickjs-native-harness/scripts/test.sh` + - enforces native fixture baselines for result hash, error code/tag, + gas used/remaining, and tape hash/length (including host-call tape case). + +--- + +## Phase P16 — Capability registry and composite profiles + +### T-170: Centralize execution-profile capability registry + +**Phase:** P16 – Capability registry +**Status:** IN PROGRESS +**Depends on:** T-150 + +**Goal:** +Replace scattered profile checks with a single capability registry consumed by +builder/runtime/harness surfaces. + +**Detailed tasks:** + +- [x] Add shared execution-profile registry package. +- [x] Define profile capabilities for: + - `baseline-v1` + - `compat-regexp-v1` (transitional alias) + - `compat-general-v1` + - `compat-binary-v1` +- [x] Integrate registry into deterministic-bundler compatibility scanning. +- [x] Integrate registry validation into quickjs-runtime artifact validation and + deterministic init feature-flag mapping. +- [x] Update quickjs-native-harness profile parsing/help to accept new profile + names. +- [x] Remove transitional `compat-regexp-v1` usage from fixtures/docs where + compatibility-mode examples are exercised (legacy alias remains supported + for backward compatibility). + +**Current state (P16 T-170):** + +- New package `libs/execution-profiles` now provides canonical profile/capability + definitions and helpers. +- `libs/deterministic-bundler` now consults capability checks (regexp/console/ + queueMicrotask/typed-arrays gates) instead of ad-hoc profile string checks. +- `libs/quickjs-runtime` now validates execution profiles via the shared + registry and uses capability checks for QuickJS feature-flag mapping. +- `tools/quickjs-native-harness` now accepts + `compat-general-v1|compat-binary-v1` profile names (currently mapped to + regexp feature-flag behavior in C until later capability widening phases). + +--- + +## Phase P17 — Deterministic Promise jobs / async integration + +### T-180: Enable deterministic Promise job draining + +**Phase:** P17 – Async determinism +**Status:** IN PROGRESS +**Depends on:** T-170 + +**Goal:** +Enable deterministic Promise/job execution in compatibility profiles while +preserving baseline restrictions. + +**Detailed tasks:** + +- [x] Add deterministic feature-flag support for Promise jobs in QuickJS fork + (`JS_DETERMINISTIC_FEATURE_PROMISE_JOBS`) and wire profile mapping from + runtime/native harness. +- [x] Drain pending Promise jobs after top-level eval in wasm/native execution + paths. +- [x] Resolve top-level Promise results deterministically (fulfilled -> value, + rejected -> VM error, pending -> deterministic error). +- [x] Add coverage for baseline Promise denial and compat-general Promise / + `queueMicrotask` execution in runtime and native harness tests. +- [x] Extend node/browser/native async parity fixtures (result + gas + tape) for + Promise-heavy scenarios. + +**Current state (P17 T-180):** + +- `qjs_det_eval(...)` and native harness eval now drain pending jobs + deterministically and unwrap Promise results. +- `qjs_det_eval_module_pack(...)` and native module-pack eval paths now drain + pending jobs before export extraction and resolve Promise exports. +- `compat-general-v1` / `compat-binary-v1` now enable Promise jobs via runtime + feature flags, while baseline continues to reject Promise usage. +- Added Promise/`queueMicrotask` determinism fixtures to shared smoke fixture + matrix (`libs/test-harness/src/lib/determinism-fixtures.ts`) with node/browser + parity validation and native harness gas+tape assertions. + +--- + +## Phase P18 — Compatibility expansion (console shim + stable sort) + +### T-190: Expand compat-general behavior without widening baseline + +**Phase:** P18 – Compatibility expansion +**Status:** IN PROGRESS +**Depends on:** T-180 + +**Goal:** +Improve practical compatibility in compatibility profiles while keeping +baseline strict. + +**Detailed tasks:** + +- [x] Enable deterministic console shim in `compat-general-v1` / + `compat-binary-v1`, routing console methods through `Host.v1.emit`. +- [x] Implement deterministic stable `Array.prototype.sort` for compatibility + profiles. +- [x] Extend parity fixtures for compatibility expansion behaviors (result + gas + + tape where applicable). + +**Current state (P18 T-190):** + +- Console remains disabled in baseline. +- Compatibility profiles now expose console methods (`log/info/warn/error/debug`) + and route payloads through `Host.v1.emit` deterministically. +- Compatibility profiles now expose deterministic stable `Array.prototype.sort`, + while baseline keeps sort disabled. +- Runtime, smoke node/browser, and native harness suites now include parity + coverage for console/sort compatibility behavior (including gas+tape fixtures). + +--- + +## Phase P19 — DV2 / Host.v2 binary compatibility track + +### T-200: Introduce DV2 bytes-capable codec foundation + +**Phase:** P19 – DV2 foundation +**Status:** DONE +**Depends on:** T-190 + +**Goal:** +Introduce a versioned bytes-capable deterministic value codec without mutating +DV1 behavior in place. + +**Detailed tasks:** + +- [x] Add DV2 codec APIs with canonical byte-string support: + `encodeDv2`, `decodeDv2`, `validateDv2`, `isDv2`. +- [x] Preserve DV1 behavior (`encodeDv` / `decodeDv`) so byte strings remain + rejected outside DV2 mode. +- [x] Wire DV2 bytes to Host.v2/runtime boundaries under `compat-binary-v1`. +- [x] Add Host.v2 bytes roundtrip fixtures and parity coverage. + +**Current state (P19 T-200):** + +- `@blue-quickjs/dv` now includes DV2 APIs with canonical CBOR byte-string + support and byte-length limit enforcement. +- QuickJS fork now exposes versioned C DV2 codec entrypoints: + `JS_EncodeDV2(...)` / `JS_DecodeDV2(...)` with byte-string support while + preserving DV1 behavior in `JS_EncodeDV(...)` / `JS_DecodeDV(...)`. +- DV1 paths remain strict and still reject CBOR major type 2 values. +- Runtime host boundaries now switch codec behavior by ABI version: + Host.v1 uses DV1, Host.v2 uses DV2 byte-string envelopes. +- `compat-binary-v1` now enables typed-array intrinsics in deterministic init; + baseline/compat-general behavior is unchanged. +- Host manifest fixtures now include Host.v2 (`abi_id=Host.v2`, `abi_version=2`) + with canonical bytes/hash fixtures and parity checks. +- Host.v2 bytes roundtrip parity coverage is now present across: + - quickjs-runtime host dispatcher + evaluate tests, + - shared determinism fixture matrix (`compat-binary-host-v2-bytes-roundtrip`), + - smoke-node and smoke-web parity suites, + - quickjs-native-harness script assertions. +- Real binary-library fixture coverage now includes at least two bundled npm + packages under `compat-binary-v1`: + - `base64-js` roundtrip fixture, + - `@noble/hashes` (`sha256`) fixture, + with smoke-node/smoke-web checks and native harness baseline assertions. + +--- + +## Phase P20 — Source maps, diagnostics, and CLI + +### T-210: Add source-map remapping + operator CLI + +**Phase:** P20 – Tooling and diagnostics +**Status:** DONE +**Depends on:** T-200 + +**Goal:** +Make runtime diagnostics and artifact operations practical for teams by adding +source-map-aware VM remapping and a first-class CLI workflow. + +**Detailed tasks:** + +- [x] Add CLI package with command surface: + `build`, `run`, `compat`, `inspect`, `explain-error`. +- [x] Add source-map-aware runtime VM payload remapping for module-pack errors. +- [x] Add CLI inspection/diagnostic reporting for profile/artifact/module metadata. +- [x] Add unit coverage for CLI arg parsing and diagnostic location extraction. + +**Current state (P20 T-210):** + +- Added `tools/blue-quickjs-cli` package with Nx build/lint/test wiring and + executable entrypoint. +- CLI commands now support: + - deterministic module-pack builds + compatibility reports, + - artifact inspection/summary for v1/v2 artifacts, + - evaluation and structured VM error output, + - payload error explanation helpers. +- Runtime now remaps module-pack generated stack locations using source maps + before deterministic error classification: + - `libs/quickjs-runtime/src/lib/source-map-remap.ts` + - integrated in `evaluate(...)` error pipeline. +- CLI now surfaces extracted mapped locations in `run` and `explain-error` + outputs and richer module/provenance/source-map fields in `inspect`. + +--- + +## Phase P21 — Validation and release gate + +### T-220: Diagnostic reconciliation workflow (non-release) + +**Phase:** P21 – Validation and release gate +**Status:** IN PROGRESS +**Depends on:** T-210 + +**Goal:** +Maintain a repeatable parity-report workflow for reconciliation and debugging +while strict gas parity is still being closed. + +**Detailed tasks:** + +- [x] Add reproducibility runner script that executes determinism/module-pack/ + binary fixture suites through wasm-node + native harness. +- [x] Emit structured report with: + result hash, error code/tag, gas used/remaining, tape hash/length, and + environment metadata. +- [x] Add report signature digest and cross-run comparison support. +- [x] Keep optional reconciliation helpers (`--gas-delta-baseline`, + `--include-gas-trace`) available for diagnostics. + +**Policy boundary (normative):** + +- Diagnostic reconciliation tooling is **not** a release gate. +- `--gas-delta-baseline` exists only to measure/track drift while parity is + being closed and must never be used as a release acceptance criterion. + +**Current state (P21 T-220):** + +- Added `tools/quickjs-native-harness/scripts/parity-report.mjs`. +- Script supports: + - `--out ` report emission, + - `--assert-match` parity checks, + - `--ignore-gas` comparison mode focused on result/error/tape parity while + preserving gas diagnostics, + - `--compare ` cross-run diff mode, + - `--gas-delta-baseline ` and + `--write-gas-delta-baseline ` for reconciliation-only workflows. +- Reports include fixture-level node/native snapshots and a SHA-256 signature, + allowing deterministic diffing between environments (local/CI/cloud), plus + suite-level gas-delta summaries for reconciliation tracking. +- Optional gas-trace diff diagnostics (`--include-gas-trace`) are available to + prioritize reconciliation hotspots. + +### T-221: Strict parity release gate (consensus executors) + +**Phase:** P21 – Validation and release gate +**Status:** IN PROGRESS +**Depends on:** T-220 + +**Goal:** +Make exact gas parity and exact OOG boundary parity release-critical for +supported consensus executors. + +**Detailed tasks:** + +- [x] Enforce strict zero gas delta (no baseline normalization) for: + `wasm-node` vs `wasm-browser`. +- [x] Enforce exact OOG boundary parity for the same consensus corpus. +- [x] Surface first-divergent gas event metadata in parity reports once + charge-event tracing lands. +- [x] Keep native parity reporting, but treat it as diagnostic unless native is + explicitly certified as a consensus executor. + +**Release gate policy (normative):** + +- **Consensus executors (mandatory):** `wasm-node`, `wasm-browser`. +- **Diagnostic executor (default):** native harness. +- Native can be promoted to consensus only after strict zero-delta parity and + OOG boundary parity are demonstrated under the same gate. +- Release pipelines must fail on any strict parity mismatch across consensus + executors and must not depend on `parity-gas-delta-baseline.json`. + +**Current state (P21 T-221):** + +- Allocation-charge model v8 closes fixture-corpus raw strict parity in the + parity harness path (`parity-report --assert-match` now succeeds without + `--gas-delta-baseline`). +- Harness test gate now enforces strict raw parity directly + (`tools/quickjs-native-harness/scripts/test.sh` no longer passes a gas-delta + baseline file to parity-report). +- Subsystem boundary fixtures now include explicit first-success/last-failure + OOG checks via binary-search boundary tests in + `libs/test-harness/src/lib/gas-equivalence.spec.ts`. +- Browser/Node consensus checks now include binary-search OOG boundary parity + for the gas fixture corpus (`return-1`, `loop-1k`, `loop-10k`, + `string-concat`, `object-alloc`, `array-ops`) via + `apps/smoke-web/tests/gas-boundaries.spec.ts`. +- Release-candidate reproducibility archival helper added: + `tools/quickjs-native-harness/scripts/archive-reproducibility-report.mjs` + emits signed strict-parity reports plus `.sha256` checksums. + +--- + ## Appendix A — Minimal required ABI surface (v1) The initial manifest should define at least: @@ -1942,7 +2580,7 @@ Ergonomic aliases: - **Determinism:** Same `(P, I, G)` ⇒ same outputs + same exact OOG point across Node and browser. - **Canonical gas:** opcode + metered C builtins + deterministic alloc/GC; not wasm instruction counts. -- **Strict capability profile:** no time/random/async/network/fs/locale leaks; no typed arrays/ArrayBuffer/WebAssembly. +- **Strict baseline capability profile:** no time/random/async/network/fs/locale leaks; no typed arrays/ArrayBuffer/WebAssembly unless explicitly enabled by compatibility profile. - **Baseline #2 ABI:** single dispatcher + numeric fn_id + manifest-locked mapping + manifest hash validation. - **DV restrictions:** only allowed types; numeric restrictions; canonical key ordering; deterministic encoding. - **Two-phase host-call charging:** base+arg bytes before call; out bytes+units after; deterministic OOG boundaries. diff --git a/docs/implementation-summary.md b/docs/implementation-summary.md index 5a22e90..b1ea557 100644 --- a/docs/implementation-summary.md +++ b/docs/implementation-summary.md @@ -10,6 +10,51 @@ For deep/normative details, this doc always points to the corresponding referenc --- +## HEAD verification snapshot (2026-03-16) + +This snapshot reconciles code/docs/tests at current HEAD: + +### A) Implemented now + +- Canonical gas spec source (`tools/gas-spec/gas-spec.v3.json`) with generated + schedule docs (`gasVersion = 8`, allocation base gas `0`, normalization mode + `none`). +- Runtime support for ProgramArtifact v1 and ProgramArtifact.v2 + (`sourceKind: "script"` and `sourceKind: "module-pack"`). +- Deterministic execution profiles (`baseline-v1`, `compat-regexp-v1`, + `compat-general-v1`, `compat-binary-v1`) and Host.v2/DV2 byte boundary path. +- Release-mode pin validation for `engineBuildHash`, `gasVersion`, and + `executionProfile`. + +### B) Implemented but not yet fully product-proved + +- A polished end-user example corpus (script/module-pack/promises/binary/kitchen + sink/max-gas policy) with copy-paste commands and expected parity tables. +- Consensus-focused archival parity reports explicitly centered on + wasm-node/wasm-browser release gates. + +### C) Strict parity status + +- Consensus path (`wasm-node` vs `wasm-browser`) is covered by smoke parity and + OOG-boundary suites. +- Native parity tooling exists and remains diagnostic by default unless policy + explicitly promotes native as a consensus executor. + +### D) Drift reconciled in this phase + +- Historical notes that implied script-only runtime/module-pack future work. +- Historical notes that implied profile feature toggles were regexp-only. +- Historical compatibility wording that implied native divergence as the active + release contract. + +### E) Remaining release-grade work + +- Complete consensus reproducibility/report archival flow. +- Expand and gate the deterministic examples corpus. +- Keep release gates aligned with consensus executor policy and pinning rules. + +--- + ## What this repo provides At a high level, the repo provides a deterministic evaluator: @@ -131,9 +176,41 @@ Ergonomics and injected globals: [Determinism profile](./determinism-profile.md) The evaluator runs JS with deterministic gas metering enabled. The final return value must be DV-encodable, otherwise evaluation fails deterministically. +Evaluation semantics in this repo support both: + +- **raw script mode** (`ProgramArtifact` v1 or v2 `sourceKind: "script"`): + `program.code` is evaluated as a global script, the resulting value comes from + the script’s final expression, and top-level `return` is invalid. +- **module-pack mode** (`ProgramArtifact.v2` `sourceKind: "module-pack"`): + runtime validates `modulePack.graphHash`, resolves modules through the + deterministic in-memory loader, and returns `mainExport`. + +`emit(...)` side effects are allowed through Host wrappers, but +wrapper-specific conventions (for example function-body wrappers in external +workflow engines) are out of scope for this evaluator. + Return encoding details: [DV wire format](./dv-wire-format.md). Evaluation API: [TypeScript SDK usage](./sdk.md). +### 6) Deterministic library reuse paths + +This repo supports two deterministic reuse flows: + +1. **Script bundling flow** (`@blue-quickjs/deterministic-bundler`): + - flattens static module graphs into one script string, + - emits a stable content hash for bundled code, + - runs a compatibility scan before VM execution. +2. **Module-pack flow** (`ProgramArtifact.v2` + `ModulePack.v1`): + - preserves module boundaries in a deterministic pack, + - validates graph hash in runtime before execution, + - resolves static imports through the deterministic in-memory loader. + +Normative references: + +- [Program artifact v2](./program-artifact-v2.md) +- [Module pack v1](./module-pack.md) +- [Deterministic builder](./builder.md) + --- ## Deterministic Value (DV) @@ -145,7 +222,12 @@ DV is the repository’s “universal value model” for **all boundary crossing - Context blob injected into the VM - Manifest canonical encoding/hashing -DV is a deliberately small subset: `null`, `boolean`, `int/float` (restricted), `string`, `bytes`, `array`, `map`, with **canonical encoding** rules and **size limits**. +Current DV (v1) is a deliberately small subset: `null`, `boolean`, +`int/float` (restricted), `string`, `array`, `map`, with **canonical +encoding** rules and **size limits**. + +The versioned bytes-capable model is defined separately in +[Value model v2](./value-model-v2.md). Reference spec: [DV wire format](./dv-wire-format.md). @@ -390,4 +472,9 @@ Details: [ABI manifest](./abi-manifest.md), [Host call ABI](./host-call-abi.md), - Only **wasm32** is supported by the TypeScript runtime integration (pointer sizes are treated as 32-bit). See runtime notes in the implementation plan and SDK docs. - Wasm memory is configured for determinism (fixed sizing; no growth). See [Toolchain](./toolchain.md). - The determinism profile is intentionally restrictive; many JS APIs are not available. See [Determinism profile](./determinism-profile.md). -- “Gas trace” attributes only VM-internal categories; host-call gas is billed but not counted inside trace totals. See [Gas schedule](./gas-schedule.md) and [Observability](./observability.md). +- “Gas trace” includes VM-internal categories plus dedicated host-call pre/post counters. See [Gas schedule](./gas-schedule.md) and [Observability](./observability.md). +- Runtime executes both single-source script artifacts and + `ProgramArtifact.v2` module-pack artifacts today. See + [Program artifact v2](./program-artifact-v2.md) and + [Module pack v1](./module-pack.md) for the normative artifact/runtime + contract. diff --git a/docs/learn/00-what-is-bluequickjs.md b/docs/learn/00-what-is-bluequickjs.md new file mode 100644 index 0000000..e2b6ecb --- /dev/null +++ b/docs/learn/00-what-is-bluequickjs.md @@ -0,0 +1,77 @@ +# 00 — What is BlueQuickjs? + +BlueQuickjs is a deterministic JavaScript execution stack built on a hardened +QuickJS engine compiled to Wasm. It is designed for **consensus-critical** +execution where independent runtimes must agree on: + +- value or error, +- gas used and gas remaining, +- host-call tape, +- exact out-of-gas boundary. + +Consensus-safe release scope today is deliberately narrow: + +- `wasm-node` +- `wasm-browser` +- canonical `wasm32` release artifacts only + +Native tooling exists for diagnostics, debugging, and reconciliation, but it is +**not** part of the consensus release contract unless a future release policy +promotes it explicitly. + +## Prerequisites + +- Node.js `>= 20.17.0` +- `pnpm` +- repository checkout with submodules initialized + +## Commands + +Build the CLI and inspect the current command surface: + +```bash +pnpm install +pnpm nx build blue-quickjs-cli +node tools/blue-quickjs-cli/dist/cli.js help +``` + +## Expected output + +You should see a command list that includes deterministic build/run/report +paths such as: + +- `build` +- `run` +- `inspect` +- `consensus-report` +- `native-report` + +That command surface mirrors the product shape: + +- build deterministic artifacts, +- run them in wasm, +- generate reproducibility evidence, +- keep native as an explicit diagnostic path. + +## What you learned + +- BlueQuickjs is a deterministic **artifact + runtime + evidence** system, not + just a JS interpreter. +- Consensus-safe execution is currently wasm-only (`wasm-node` vs + `wasm-browser`). +- Exact gas and exact OOG boundaries are part of the release contract. +- Profiles determine which compatibility features are available: + `baseline-v1`, `compat-general-v1`, and `compat-binary-v1`. + +## Continue + +Next: [01 — Install and run your first script](./01-install-and-run-your-first-script.md) + +## Troubleshooting + +- If `pnpm install` fails, confirm your Node version matches the root + `package.json` engines field. +- If the CLI build fails, run `git submodule update --init --recursive` and + then retry. +- For a scope summary without running commands, read + [Consensus-safe vs diagnostic-only](../consensus-safe-vs-diagnostic-only.md). diff --git a/docs/learn/01-install-and-run-your-first-script.md b/docs/learn/01-install-and-run-your-first-script.md new file mode 100644 index 0000000..8c33adf --- /dev/null +++ b/docs/learn/01-install-and-run-your-first-script.md @@ -0,0 +1,73 @@ +# 01 — Install and run your first script + +This page walks through the fastest path from a clean checkout to a successful +deterministic run with visible gas accounting. + +## Prerequisites + +- Node.js `>= 20.17.0` +- `pnpm` +- repository checkout with submodules initialized + +## Commands + +Install dependencies, set up the pinned Wasm toolchain, build the CLI, create a +tiny entry module, build a deterministic artifact, and run it: + +```bash +pnpm install +bash tools/scripts/setup-emsdk.sh +source tools/emsdk/emsdk_env.sh +pnpm nx build blue-quickjs-cli +mkdir -p tmp/learn-first-script +printf 'export default (() => 1 + 2)();\n' > tmp/learn-first-script/entry.js +node tools/blue-quickjs-cli/dist/cli.js build \ + --entry tmp/learn-first-script/entry.js \ + --out tmp/learn-first-script/program.json +node tools/blue-quickjs-cli/dist/cli.js run \ + --artifact tmp/learn-first-script/program.json \ + --gas-limit 1000000 +``` + +## Expected output + +The `build` command should print a JSON summary with fields like: + +- `compatibilityOk: true` +- `moduleCount` +- `graphHash` + +The `run` command should print a success payload shaped like: + +```json +{ + "ok": true, + "value": 3, + "gasUsed": "...", + "gasRemaining": "...", + "tapeLength": 0 +} +``` + +The exact gas numbers matter and are deterministic for the same artifact, +inputs, and gas limit. + +## What you learned + +- How to install the pinned Emscripten toolchain used for wasm builds. +- How to build a deterministic artifact from source. +- How to execute that artifact and inspect deterministic gas output. +- That a simple local script already runs through the same artifact model used + by the wider product. + +## Continue + +Next: [02 — Understand the program artifact](./02-understand-the-program-artifact.md) + +## Troubleshooting + +- If `setup-emsdk.sh` fails, read [Toolchain + build determinism](../toolchain.md). +- If the build command reports compatibility diagnostics, confirm the file uses + plain deterministic JS and no unsupported APIs. +- If `run` fails with an execution-profile or pin error, inspect the artifact in + the next step before editing fields manually. diff --git a/docs/learn/02-understand-the-program-artifact.md b/docs/learn/02-understand-the-program-artifact.md new file mode 100644 index 0000000..1e5461c --- /dev/null +++ b/docs/learn/02-understand-the-program-artifact.md @@ -0,0 +1,70 @@ +# 02 — Understand the program artifact + +`ProgramArtifact.v2` is the release-facing execution contract. It makes runtime +scope explicit instead of relying on an unstructured code string. + +## Why it matters + +A release-mode artifact can pin: + +- `sourceKind` +- `executionProfile` +- `abiManifestHash` +- `engineBuildHash` +- `gasVersion` + +Those pins are what let runtimes reject incompatible or stale execution +surfaces before consensus work begins. + +## Prerequisites + +- Complete [01 — Install and run your first script](./01-install-and-run-your-first-script.md) +- `tmp/learn-first-script/program.json` exists + +## Commands + +Inspect the artifact you just built: + +```bash +node tools/blue-quickjs-cli/dist/cli.js inspect \ + --artifact tmp/learn-first-script/program.json +``` + +## Expected output + +You should see a JSON summary with fields similar to: + +- `version` +- `sourceKind` +- `executionProfile` +- `abiId` +- `abiVersion` +- `abiManifestHash` +- `engineBuildHash` (possibly `null` for a local dev artifact) +- `gasVersion` (possibly `null` for a local dev artifact) +- `graphHash` +- `moduleSpecifiers` + +Builder-produced release artifacts should carry explicit +`engineBuildHash` and `gasVersion`. Local development artifacts can omit them, +but they should not be treated as release evidence. + +## What you learned + +- `ProgramArtifact.v2` is the object that binds source, profile, ABI identity, + engine identity, and gas schedule identity together. +- `sourceKind` distinguishes `script` from `module-pack`. +- `executionProfile` is not cosmetic; it is part of the deterministic contract. +- Missing pins are acceptable for local iteration, but not for release-mode + reproducibility claims. + +## Continue + +Next: [03 — Module packs and imports](./03-module-packs-and-imports.md) + +## Troubleshooting + +- If the artifact cannot be inspected, rebuild it with the previous page’s + commands. +- For a schema-level reference, read [ProgramArtifact.v2](../program-artifact-v2.md). +- For profile meanings, read [Execution profiles](../execution-profiles.md). diff --git a/docs/learn/03-module-packs-and-imports.md b/docs/learn/03-module-packs-and-imports.md new file mode 100644 index 0000000..0f79f00 --- /dev/null +++ b/docs/learn/03-module-packs-and-imports.md @@ -0,0 +1,66 @@ +# 03 — Module packs and imports + +BlueQuickjs does not allow runtime fetch/import/network behavior in the +consensus path. Instead, the builder resolves imports ahead of time and emits a +deterministic `ModulePack.v1`. + +That means: + +- imports are part of the build step, +- the module graph is hashed, +- runtime execution is limited to the in-memory pack, +- the same source graph yields the same graph hash across environments. + +## Prerequisites + +- Node.js and `pnpm` installed +- CLI built with `pnpm nx build blue-quickjs-cli` + +## Commands + +Build and inspect the module-pack example that imports a sibling module: + +```bash +mkdir -p tmp/learn-module-pack +node tools/blue-quickjs-cli/dist/cli.js build \ + --entry examples/02-module-pack/entry.js \ + --out tmp/learn-module-pack/program.json +node tools/blue-quickjs-cli/dist/cli.js inspect \ + --artifact tmp/learn-module-pack/program.json +node tools/blue-quickjs-cli/dist/cli.js run \ + --artifact tmp/learn-module-pack/program.json \ + --gas-limit 50000 +``` + +## Expected output + +- `build` should report `compatibilityOk: true`. +- `inspect` should show: + - `sourceKind: "module-pack"` + - a non-null `graphHash` + - module specifiers for `./entry.js` and `./values.js` +- `run` should succeed with: + - `ok: true` + - a deterministic result (`7` for this example) + - deterministic gas usage + +## What you learned + +- Imports are resolved at build time, not consensus-time. +- `ModulePack.v1` is the transport for deterministic static ESM execution. +- The module graph hash is part of what lets other environments verify they are + running the same thing. +- “Imported library” support in BlueQuickjs means prebuilt deterministic packs, + not an open-ended runtime module loader. + +## Continue + +Next: [04 — Promises, async, and microtasks](./04-promises-async-and-microtasks.md) + +## Troubleshooting + +- If the builder rejects a dependency, inspect its diagnostics with + `blue-quickjs compat` or the CLI `build` output. +- If you want the normative schema, read [ModulePack.v1](../module-pack.md). +- For unsupported runtime import behavior, see + [Unsupported features and why](../unsupported-features-and-why.md). diff --git a/docs/learn/04-promises-async-and-microtasks.md b/docs/learn/04-promises-async-and-microtasks.md new file mode 100644 index 0000000..05c4709 --- /dev/null +++ b/docs/learn/04-promises-async-and-microtasks.md @@ -0,0 +1,69 @@ +# 04 — Promises, async, and microtasks + +Promise jobs are intentionally **not** part of the minimal baseline. They are +enabled only in compatibility profiles that explicitly opt into deterministic +job draining. + +Today that means: + +- `baseline-v1` — no Promise jobs / no `queueMicrotask` +- `compat-general-v1` — deterministic Promise jobs and `queueMicrotask` +- `compat-binary-v1` — same as `compat-general-v1`, plus binary support + +## Prerequisites + +- Complete [01 — Install and run your first script](./01-install-and-run-your-first-script.md) +- CLI built with `pnpm nx build blue-quickjs-cli` + +## Commands + +Create and run a Promise-based module under `compat-general-v1`: + +```bash +mkdir -p tmp/learn-promises +printf 'export default (() => Promise.resolve(40).then((value) => value + 2))();\n' > tmp/learn-promises/entry.js +node tools/blue-quickjs-cli/dist/cli.js build \ + --entry tmp/learn-promises/entry.js \ + --profile compat-general-v1 \ + --out tmp/learn-promises/program.json +node tools/blue-quickjs-cli/dist/cli.js run \ + --artifact tmp/learn-promises/program.json \ + --gas-limit 1000000 +``` + +## Expected output + +The artifact build should succeed and the run output should look like: + +```json +{ + "ok": true, + "value": 42, + "gasUsed": "...", + "gasRemaining": "...", + "tapeLength": 0 +} +``` + +If you rebuild the same file under `baseline-v1`, the Promise path should be +rejected or fail deterministically because Promise jobs are not part of that +profile’s contract. + +## What you learned + +- Promise support in BlueQuickjs is **profile-gated**, not ambient. +- Deterministic job draining is part of the compatibility contract for + `compat-general-v1` and `compat-binary-v1`. +- The right question is not “does BlueQuickjs support async?” but + “does this artifact’s profile allow deterministic Promise jobs?” + +## Continue + +Next: [05 — Binary mode and Host.v2](./05-binary-and-host-v2.md) + +## Troubleshooting + +- If the builder reports compatibility issues, make sure the file uses only + Promise/microtask behavior and not timers or dynamic imports. +- For the normative profile definitions, read [Execution profiles](../execution-profiles.md). +- For baseline restrictions, read [Determinism profile](../determinism-profile.md). diff --git a/docs/learn/05-binary-and-host-v2.md b/docs/learn/05-binary-and-host-v2.md new file mode 100644 index 0000000..fe04621 --- /dev/null +++ b/docs/learn/05-binary-and-host-v2.md @@ -0,0 +1,63 @@ +# 05 — Binary mode and Host.v2 + +Binary-heavy deterministic workloads use: + +- `compat-binary-v1` +- DV2 byte encoding +- `Host.v2` + +This keeps byte-oriented boundaries explicit instead of silently widening DV1 or +the baseline profile. + +## Prerequisites + +- Playwright Chromium installed for browser-backed certification commands +- pinned Emscripten environment loaded: + + ```bash + source tools/emsdk/emsdk_env.sh + ``` + +## Commands + +Generate the workload certification report and inspect the binary-oriented +fixtures: + +```bash +pnpm exec playwright install --with-deps chromium +node apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs \ + --out-dir artifacts/workload-certification \ + --browser chromium +rg "compat-binary-v1|green-base64|green-noble-sha|flagship-knowledge-pack" \ + artifacts/workload-certification -n +``` + +## Expected output + +You should see report matches for fixtures that rely on binary support, such as: + +- `green-base64` +- `green-noble-sha` +- `flagship-knowledge-pack` +- `compat-binary-v1` + +Those report entries prove that the binary path is not just a docs claim — it +is exercised through generated workload evidence. + +## What you learned + +- Binary support is not part of the baseline; it is a versioned compatibility + contract. +- `Host.v2` + DV2 are the deterministic boundary for byte-oriented workloads. +- The best proof that this works is generated workload evidence, not prose. + +## Continue + +Next: [06 — Gas, OOG, and max-gas policies](./06-gas-oog-and-max-gas-policies.md) + +## Troubleshooting + +- If Chromium is missing, rerun the Playwright install command. +- If the certification script fails, run `pnpm nx test ecosystem-certifier` + first to confirm the local certifier environment is healthy. +- For the normative value-model rules, read [Value model v2 (DV2)](../value-model-v2.md). diff --git a/docs/learn/06-gas-oog-and-max-gas-policies.md b/docs/learn/06-gas-oog-and-max-gas-policies.md new file mode 100644 index 0000000..1a82821 --- /dev/null +++ b/docs/learn/06-gas-oog-and-max-gas-policies.md @@ -0,0 +1,59 @@ +# 06 — Gas, OOG, and max-gas policies + +In BlueQuickjs, gas is not an approximate UI metric. It is part of the +deterministic execution contract, and the exact OOG boundary is a release gate +for consensus-safe executors. + +## Prerequisites + +- Pinned Emscripten environment loaded: + + ```bash + source tools/emsdk/emsdk_env.sh + ``` + +- Playwright Chromium installed + +## Commands + +Generate the workload OOG-boundary report and inspect the canonical loop +fixture: + +```bash +pnpm exec playwright install --with-deps chromium +node apps/ecosystem-certifier/scripts/run-oog-boundary-certification.mjs \ + --out-dir artifacts/workload-certification \ + --browser chromium +rg "loop-10k|firstSuccessGas|lastFailureGas|failureCode" \ + artifacts/workload-certification/oog-boundaries.json -n +``` + +## Expected output + +You should see entries for `loop-10k` including: + +- `firstSuccessGas` +- `lastFailureGas` +- failure code information (for example `OOG`) + +The important property is not just “fails when gas is low” but that the +boundary is **exact and reproducible**. + +## What you learned + +- Gas values are deterministic release evidence, not advisory counters. +- The exact success/failure boundary is part of the consensus contract. +- Max-gas policy should be treated as a pinned operational rule, not a fuzzy + runtime heuristic. + +## Continue + +Next: [07 — Verify release evidence](./07-verify-release-evidence.md) + +## Troubleshooting + +- If the boundary script fails, confirm `pnpm nx run ecosystem-certifier:e2e` + is green first. +- If you want the full gas specification, read [Gas schedule](../gas-schedule.md). +- If you want a human summary of current release evidence, read + [Release-readiness report](../release-readiness-report.md). diff --git a/docs/learn/07-verify-release-evidence.md b/docs/learn/07-verify-release-evidence.md new file mode 100644 index 0000000..f406fa4 --- /dev/null +++ b/docs/learn/07-verify-release-evidence.md @@ -0,0 +1,49 @@ +# 07 — Verify release evidence + +BlueQuickjs uses generated release evidence so auditors and operators can check +that the current branch or release bundle matches deterministic reality. + +## Prerequisites + +- Complete the toolchain setup from + [01 — Install and run your first script](./01-install-and-run-your-first-script.md) + +## Commands + +Synthesize a local release evidence bundle and verify it: + +```bash +pnpm release-evidence:synthesize -- --out-dir artifacts/release-evidence +pnpm release-evidence:verify -- --evidence-dir artifacts/release-evidence +``` + +## Expected output + +- The synthesize step should create: + - `release-evidence-summary.json` + - `release-evidence-summary.md` + - `release-evidence-manifest.json` + - `*.sha256` + - `*.sig` +- The verify step should exit successfully after checking: + - manifest entries, + - checksums, + - signature payloads, + - branch/date expectations when provided. + +## What you learned + +- Release evidence is a generated bundle, not a hand-written checklist. +- Verification checks both integrity (checksums/signatures) and release context. +- The release evidence bundle ties together consensus, workload, and + consumer-proof artifacts. + +## Continue + +Next: [08 — Build a real example](./08-build-a-real-example.md) + +## Troubleshooting + +- If synthesis reports stale docs, regenerate the affected reports and rerun. +- If verification fails, inspect the manifest paths and checksum sidecars first. +- For the trust model, read [Release provenance and trust model](../release-provenance.md). diff --git a/docs/learn/08-build-a-real-example.md b/docs/learn/08-build-a-real-example.md new file mode 100644 index 0000000..136896a --- /dev/null +++ b/docs/learn/08-build-a-real-example.md @@ -0,0 +1,71 @@ +# 08 — Build a real example + +This page walks a real example from source files to deterministic artifact to +runtime execution. + +We will use the kitchen-sink example because it exercises: + +- module-pack imports, +- host calls, +- Promise job draining, +- `queueMicrotask`, +- stable sort behavior, +- deterministic tape emission. + +## Prerequisites + +- CLI built with `pnpm nx build blue-quickjs-cli` +- toolchain environment loaded: + + ```bash + source tools/emsdk/emsdk_env.sh + ``` + +## Commands + +Build, inspect, and run the kitchen-sink example: + +```bash +mkdir -p tmp/learn-kitchen-sink +node tools/blue-quickjs-cli/dist/cli.js build \ + --entry examples/09-kitchen-sink/entry.js \ + --profile compat-general-v1 \ + --out tmp/learn-kitchen-sink/program.json +node tools/blue-quickjs-cli/dist/cli.js inspect \ + --artifact tmp/learn-kitchen-sink/program.json +node tools/blue-quickjs-cli/dist/cli.js run \ + --artifact tmp/learn-kitchen-sink/program.json \ + --gas-limit 1000000 +``` + +## Expected output + +- `build` should succeed with `compatibilityOk: true`. +- `inspect` should show: + - `sourceKind: "module-pack"` + - `executionProfile: "compat-general-v1"` + - a non-null `graphHash` + - multiple module specifiers +- `run` should return a success payload with: + - a structured object value, + - deterministic gas numbers, + - non-zero tape or host interaction metadata when appropriate. + +## What you learned + +- Real examples are still built as deterministic artifacts, not special cases. +- The profile pin matters when imported code uses Promise or microtask behavior. +- Host calls, module graphs, and gas accounting stay visible all the way through + execution. + +## Continue + +Next: [09 — Production embedder checklist](./09-production-embedder-checklist.md) + +## Troubleshooting + +- If the build fails, check whether the selected profile matches the example’s + capabilities. +- If the run fails, inspect the artifact first and confirm the example was built + under `compat-general-v1`. +- For the source corpus overview, read [`examples/README.md`](../../examples/README.md). diff --git a/docs/learn/09-production-embedder-checklist.md b/docs/learn/09-production-embedder-checklist.md new file mode 100644 index 0000000..47d03e1 --- /dev/null +++ b/docs/learn/09-production-embedder-checklist.md @@ -0,0 +1,50 @@ +# 09 — Production embedder checklist + +This final page turns the learning path into operational rules for real +deployments. + +## Prerequisites + +- Complete [07 — Verify release evidence](./07-verify-release-evidence.md) +- Read [Consensus-safe vs diagnostic-only](../consensus-safe-vs-diagnostic-only.md) + +## Commands + +Run the most important local release/consumer checks: + +```bash +pnpm release-evidence:verify -- --evidence-dir artifacts/release-evidence +pnpm workload:check-public-package-versions +pnpm workload:check-pack-manifests -- --out-dir artifacts/consumer-proof/pack-manifests +``` + +## Expected output + +- Release evidence verification should pass without checksum/signature errors. +- Public package version alignment should pass. +- Pack manifest validation should emit a deterministic manifest summary in + `artifacts/consumer-proof/pack-manifests`. + +## What you learned + +- Production embedders should pin: + - `engineBuildHash` + - `gasVersion` + - ABI manifest hash + - execution profile +- Production release confidence comes from generated evidence and rehearsed + packaging flows, not from ad hoc local runs. +- Consensus-safe deployment guidance is narrower than the full repo surface. + +## Continue + +Next: return to the [documentation hub](../README.md), then revisit the full +[Production embedder checklist](../production-embedder-checklist.md) and +[Release checklist](../release-checklist.md). + +## Troubleshooting + +- If verification fails, regenerate the evidence bundle and retry before + changing any release metadata manually. +- If package version alignment fails, fix the public package manifests before + attempting a release rehearsal. diff --git a/docs/learn/README.md b/docs/learn/README.md new file mode 100644 index 0000000..21a24da --- /dev/null +++ b/docs/learn/README.md @@ -0,0 +1,39 @@ +# Learn BlueQuickjs + +This is the recommended newcomer path through the repository. Follow these +pages in order if you want to understand what BlueQuickjs is, run something +real, and then convince yourself that the release evidence is trustworthy. + +## Suggested order + +1. [00 — What is BlueQuickjs?](./00-what-is-bluequickjs.md) +2. [01 — Install and run your first script](./01-install-and-run-your-first-script.md) +3. [02 — Understand the program artifact](./02-understand-the-program-artifact.md) +4. [03 — Module packs and imports](./03-module-packs-and-imports.md) +5. [04 — Promises, async, and microtasks](./04-promises-async-and-microtasks.md) +6. [05 — Binary mode and Host.v2](./05-binary-and-host-v2.md) +7. [06 — Gas, OOG, and max-gas policies](./06-gas-oog-and-max-gas-policies.md) +8. [07 — Verify release evidence](./07-verify-release-evidence.md) +9. [08 — Build a real example](./08-build-a-real-example.md) +10. [09 — Production embedder checklist](./09-production-embedder-checklist.md) + +## Supporting references + +- [Architecture overview](../architecture-overview.md) +- [Glossary](../glossary.md) +- [FAQ](../faq.md) +- [Unsupported features and why](../unsupported-features-and-why.md) +- [Consensus-safe vs diagnostic-only](../consensus-safe-vs-diagnostic-only.md) + +## What this path teaches + +By the end of the sequence you should be able to: + +- explain the current consensus-safe scope, +- run deterministic scripts in wasm, +- understand how `ProgramArtifact.v2` pins engine/profile/gas/ABI identity, +- use module packs instead of runtime imports, +- understand when Promise jobs and binary APIs are allowed, +- inspect exact gas and OOG boundaries, +- verify the generated release evidence bundle, +- embed BlueQuickjs safely in production. diff --git a/docs/module-pack.md b/docs/module-pack.md new file mode 100644 index 0000000..fb25df2 --- /dev/null +++ b/docs/module-pack.md @@ -0,0 +1,100 @@ +# ModulePack.v1 + +Baseline anchors: + +- `docs/baseline-1.md` +- `docs/baseline-2.md` + +`ModulePack.v1` is the canonical reusable source-module artifact for deterministic +runtime execution. + +## Schema (normative) + +```ts +type ModulePackV1 = { + version: 1; + entrySpecifier: string; + entryExport?: string; // default: "default" + modules: ModuleRecord[]; + graphHash: string; // lowercase sha256 hex, 64 chars + builderVersion: string; + dependencyIntegrity: string; // lowercase sha256 hex, 64 chars + diagnosticsMeta?: Record; // non-hashed metadata only +}; + +type ModuleRecord = { + specifier: string; + source: string; + sourceMap?: string; // canonical source map JSON string + originMeta?: { + packageName?: string; + packageVersion?: string; + integrity?: string; // optional lowercase sha256 hex, 64 chars + originalPath?: string; // diagnostics only; never hashed + }; +}; +``` + +## Deterministic requirements + +### 1) Canonical module ordering + +`modules` MUST be sorted by canonical `specifier` byte order (UTF-8, ascending). + +### 2) Source normalization + +- Module source MUST use LF (`\n`) line endings. +- Trailing line ending normalization MUST be deterministic. + +### 3) Specifier normalization + +- All specifiers MUST use `/` separators. +- No absolute OS paths. +- Relative imports MUST be canonicalized during build. +- Bare package imports MUST be resolved at build time to canonical internal + specifiers. + +### 4) Hash independence from machine/checkout + +Hashed content MUST NOT include: + +- absolute paths, +- host OS path separators, +- timestamps, +- nondeterministic build metadata. + +### 5) Graph hash + +`graphHash = sha256(canonical_module_pack_bytes)` + +Where canonical bytes are produced from the ordered module list and normalized +fields only (excluding non-hashed diagnostics metadata). + +## Runtime loader contract + +When a runtime executes `sourceKind: "module-pack"`: + +- only module records in the pack are loadable, +- relative imports resolve within the pack graph, +- cyclic imports and live bindings MUST follow static ESM semantics, +- entry module namespace is queried for `entryExport` (default `"default"`), +- result is DV/DV2-encoded according to selected ABI/value-model version. + +## Deterministic error codes + +- `MODULE_PACK_HASH_MISMATCH` +- `MODULE_SPECIFIER_NOT_FOUND` +- `MODULE_EXPORT_MISSING` +- `MODULE_RESOLUTION_ERROR` +- `MODULE_EVALUATION_ERROR` + +## Source maps + +- `sourceMap` values MUST be canonical JSON and path-clean (no absolute paths in + hashed payloads). +- Path rewriting rules are specified in `docs/builder.md`. + +## See also + +- `docs/program-artifact-v2.md` +- `docs/builder.md` diff --git a/docs/observability.md b/docs/observability.md index b361b0a..89c1b1e 100644 --- a/docs/observability.md +++ b/docs/observability.md @@ -126,17 +126,31 @@ Or (lower-level): See: [SDK usage](./sdk.md). -### What it does *not* include +### Host-call trace coverage -The trace does **not** include host-call gas. Host calls are billed against the VM gas counter, but they are accounted separately. +The trace includes dedicated host-call counters: -If you want to estimate host-call gas from an `EvaluateResult` that includes a trace: +- `hostCallPreCount` / `hostCallPreGas` +- `hostCallPostCount` / `hostCallPostGas` -``` -hostCallGas ≈ gasUsed - (opcodeGas + arrayCbGas + allocationGas + jsonParseGas + jsonStringifyGas + gcCheckpointGas) -``` +So host-call charging can be attributed directly without deriving a residual from +total gas usage. -The exact accounting and the checkpoint behavior are described in [Gas schedule](./gas-schedule.md). +Allocation trace now reports both `requestedBytes` and charged `bytes` so +allocator-model drift can be separated from canonical gas charging. + +### Charge-event tape (debug mode) + +For first-divergence debugging, deterministic runtimes can enable a fixed-size +gas charge-event tape: + +- preallocated ring buffer (`JS_EnableGasChargeTape(ctx, capacity)`), +- no dynamic allocation while appending events, +- event fields include `siteId`, `kind`, `flags`, `amount`, optional + `logicalUnits`, and `gasBefore` / `gasAfter`. + +This tape is diagnostic-only and should not be treated as a release API +stability guarantee. ### Interpreting trace output diff --git a/docs/playground-recipes.md b/docs/playground-recipes.md new file mode 100644 index 0000000..6c89a80 --- /dev/null +++ b/docs/playground-recipes.md @@ -0,0 +1,86 @@ +# Playground recipes + +These recipes map common learning tasks to concrete playground actions. + +## 1. Run your first script + +1. Open the playground. +2. Leave the default **Gallery** selection on **Basic deterministic script**. +3. Click **Run current selection**. +4. Open the **Result** tab and inspect: + - result hash + - gas used + - gas remaining + +What this teaches: + +- how the browser runtime reports deterministic success, +- what an evidence-backed happy-path run looks like. + +## 2. Run a Promise example + +1. Choose **Promises / async / microtasks** from the gallery. +2. Confirm the profile is `compat-general-v1`. +3. Click **Run current selection**. +4. Open the **Determinism evidence** tab and confirm the browser run matches the + certified snapshot. + +What this teaches: + +- Promise jobs are profile-gated, +- `compat-general-v1` is the right profile for deterministic async support. + +## 3. Run a library/module-pack example + +1. Choose **Standard ESM module-pack** or **Real npm library reuse**. +2. Click **Run current selection**. +3. Open the **Metadata** tab and inspect: + - `sourceKind` + - module graph hash + - execution profile + +What this teaches: + +- imports are resolved into deterministic module packs ahead of execution, +- the runtime is executing a pinned artifact, not fetching modules live. + +## 4. Inspect a red deterministic failure + +1. Scroll to **Red fixtures** in the left rail. +2. Choose a fixture such as **dynamic import must be rejected at build stage**. +3. Open the **Determinism evidence** tab. +4. Read the failure stage and diagnostics. + +What this teaches: + +- unsupported behavior is surfaced explicitly, +- deterministic failures are part of the product, not hidden edge cases. + +## 5. Inspect a max-gas boundary + +1. Choose **Max-gas policy / OOG boundary**. +2. Click **Find OOG boundary**. +3. Open the **Determinism evidence** tab. +4. Inspect: + - `firstSuccessGas` + - `lastFailureGas` + - failure code/tag + +What this teaches: + +- exact OOG boundaries are visible and reproducible, +- gas policy is part of deterministic release evidence. + +## 6. Inspect a Host.v2 bytes roundtrip + +1. Choose **Binary / typed arrays / Host.v2 DV2**. +2. Click **Run current selection**. +3. Open the **Host + tape** tab. +4. Inspect the host payload previews and tape metadata. + +What this teaches: + +- `compat-binary-v1` and `Host.v2` are how byte-oriented workloads cross the + host boundary, +- the playground exposes both high-level result data and host interaction + evidence. diff --git a/docs/playground.md b/docs/playground.md new file mode 100644 index 0000000..af04e6a --- /dev/null +++ b/docs/playground.md @@ -0,0 +1,184 @@ +# BlueQuickjs Playground + +The in-repo playground is the canonical interactive demo surface for the +wasm-consensus product. + +It is designed to help new engineers: + +- run deterministic JavaScript in the browser, +- inspect result/error, gas, and tape outputs, +- understand execution profiles, +- compare a browser run against certified evidence, +- inspect exact OOG boundaries, +- learn what is consensus-safe vs diagnostic-only. + +## What the playground is for + +Use it when you want a high-signal, evidence-backed browser experience without +leaving the repo. + +The playground is especially useful for: + +- onboarding, +- release review demos, +- teaching profiles and pins, +- validating that a certified example still matches generated evidence. + +## What runs live + +### Script mode + +The playground can execute raw deterministic snippets live in the browser using +`ProgramArtifact.v2` script mode. + +This is best for: + +- small deterministic examples, +- quick gas/result experiments, +- understanding profile differences. + +### Certified example mode + +The playground also ships prebuilt/certified artifacts for: + +- the 10 canonical example categories, +- selected green ecosystem fixtures, +- selected red deterministic-failure fixtures, +- the flagship workload entry. + +These examples are backed by generated JSON produced from in-repo fixtures and +runtime/build tooling. + +## What uses prebuilt artifacts + +The playground does **not** try to be a full npm-in-browser bundler. + +For module-pack and library examples it uses: + +- deterministic builder output, +- generated `ProgramArtifact.v2` payloads, +- certified evidence snapshots, +- generated OOG-boundary data. + +That keeps the demo aligned with deterministic reality rather than inventing a +separate browser-only toolchain. + +## Run it locally + +```bash +git submodule update --init --recursive vendor/quickjs +bash tools/scripts/setup-emsdk.sh +bash apps/bluequickjs-playground/scripts/dev.sh +``` + +Open: + +- `http://localhost:4325` + +The dev script does three important things for a fresh checkout: + +1. sources the pinned Emscripten environment, +2. builds the workspace libraries the playground depends on, +3. regenerates the playground’s evidence-backed JSON before starting Vite. + +## Core UI areas + +### Gallery and run-mode controls + +The left side lets you switch between: + +- Gallery +- Script +- Artifact JSON + +It also exposes: + +- execution profile selection, +- gas-limit presets, +- host preset selection, +- run action, +- exact OOG search, +- artifact/evidence export. + +### Editor + +The editor uses Monaco and adapts to the current mode: + +- read-only source view for certified gallery examples, +- editable JavaScript in script mode, +- editable JSON in artifact-import mode. + +### Result and evidence panel + +The right side shows: + +- result or error, +- gas used / remaining, +- result hash and tape hash, +- `engineBuildHash`, +- `gasVersion`, +- `executionProfile`, +- `sourceKind`, +- module graph hash where applicable, +- current/certified evidence comparison. + +### Host and tape panel + +The playground wraps its deterministic mock hosts to show: + +- request inputs, +- response payload previews, +- units charged, +- tape metadata emitted by the runtime. + +## Import/export behavior + +- **Export artifact** downloads the current `ProgramArtifact.v2`. +- **Export run evidence** downloads the current browser run snapshot. +- **Artifact JSON mode** lets you paste an artifact and execute it with the + selected host preset. + +## Inspecting OOG boundaries + +For supported examples, the **Find OOG boundary** action performs a deterministic +binary search over gas limits and displays: + +- `firstSuccessGas` +- `lastFailureGas` +- success/failure gas used +- success/failure gas remaining +- failure code/tag + +## Comparing to certified evidence + +When an example is backed by generated evidence, the playground can show: + +- certified snapshot, +- current browser run snapshot, +- a match/diff summary, +- source report reference, +- precomputed OOG boundary when available. + +## Red fixture behavior + +Red fixtures are intentionally educational. They explain: + +- whether rejection happens at build or runtime, +- which deterministic rule is involved, +- where to read more in the docs. + +The playground never tries to “paper over” those failures. + +## Limitations + +- Consensus-safe scope is still wasm-only (`wasm-node` vs `wasm-browser`). +- Native remains diagnostic-only. +- Runtime fetch/import/network behavior is intentionally unsupported. +- The playground is a deterministic learning/demo surface, not a general npm + IDE or browser bundler. + +## See also + +- [Playground recipes](./playground-recipes.md) +- [Learning path](./learn/README.md) +- [Consensus-safe vs diagnostic-only](./consensus-safe-vs-diagnostic-only.md) diff --git a/docs/production-embedder-checklist.md b/docs/production-embedder-checklist.md new file mode 100644 index 0000000..514d0aa --- /dev/null +++ b/docs/production-embedder-checklist.md @@ -0,0 +1,53 @@ +# Production embedder checklist + +Use this checklist before embedding BlueQuickjs in production consensus flows. + +## A) Deterministic pinning + +- [ ] Pin `engineBuildHash`. +- [ ] Pin `gasVersion`. +- [ ] Pin ABI manifest hash. +- [ ] Pin execution profile per workload (`baseline-v1` / `compat-*`). +- [ ] Keep consensus-safe scope explicit: `wasm-node` vs `wasm-browser` + (`wasm32` release engine only). + +## B) Runtime contract enforcement + +- [ ] Enforce strict parity acceptance on required consensus executors. +- [ ] Enforce exact OOG boundary parity checks. +- [ ] Treat native output as diagnostic-only unless explicitly promoted. + +## C) Host ABI discipline + +- [ ] Route all host capabilities through manifest-defined Host ABI calls. +- [ ] Reject undocumented host functions/surfaces. +- [ ] Keep deterministic failure-stage expectations for unsupported behavior. + +## D) Release evidence validation + +- [ ] Verify `release-evidence-manifest.json`. +- [ ] Verify checksums for all listed artifacts. +- [ ] Verify detached signatures (`*.sig`) using trusted key material. +- [ ] Record manifest hash and parity summary in release go/no-go template. +- [ ] Run the local auditor command: + `pnpm release-evidence:verify -- --evidence-dir artifacts/release-evidence` + +## E) Security/supply chain + +- [ ] Generate and archive SBOM (`pnpm release-evidence:sbom`). +- [ ] Generate and archive dependency license report (`pnpm release-evidence:licenses`). +- [ ] Review signature rotation / rollback runbook. + +## F) Operational readiness + +- [ ] Run consumer-proof matrix (Node 20/22 and multi-OS). +- [ ] Run registry-style publish rehearsal. +- [ ] Run tarball-based consumer rehearsal. +- [ ] Confirm docs/release notes match shipped consensus-safe scope. +- [ ] Keep the in-repo playground aligned with certified evidence and docs. + +## Reference docs + +- [Consensus-safe vs diagnostic-only](./consensus-safe-vs-diagnostic-only.md) +- [Release checklist](./release-checklist.md) +- [Playground](./playground.md) diff --git a/docs/program-artifact-v2.md b/docs/program-artifact-v2.md new file mode 100644 index 0000000..56fc44c --- /dev/null +++ b/docs/program-artifact-v2.md @@ -0,0 +1,97 @@ +# ProgramArtifact.v2 + +Baseline anchors: + +- `docs/baseline-1.md` (determinism + canonical gas) +- `docs/baseline-2.md` (manifest-locked host ABI + DV boundary) + +This document defines the **versioned execution artifact** consumed by runtimes +and produced by the deterministic builder. + +## Goals + +- Replace ambiguous “just a code string” payloads with explicit execution modes. +- Make profile and engine pinning explicit. +- Support script mode and first-class module-pack mode under one schema. + +## Schema (normative) + +```ts +type ProgramArtifactV2 = { + version: 2; + abiId: string; // e.g. "Host.v1" or "Host.v2" + abiVersion: number; // uint32 + abiManifestHash: string; // lowercase sha256 hex, 64 chars + engineBuildHash?: string; // lowercase sha256 hex, 64 chars + gasVersion?: number; // uint32, required for release-mode artifacts + executionProfile: ExecutionProfileName; + sourceKind: 'script' | 'module-pack'; + source: ScriptSource | ModulePackSource; +}; + +type ScriptSource = { + code: string; +}; + +type ModulePackSource = { + modulePack: ModulePackV1; +}; +``` + +## Field rules + +- `version` MUST be `2`. +- `executionProfile` is required. Release artifacts MUST NOT rely on implicit defaults. +- `sourceKind` and `source` shape MUST match. +- `engineBuildHash`: + - REQUIRED for builder-produced release artifacts. + - MAY be omitted only for local development/debug workflows that do not claim + reproducible release semantics. +- `gasVersion`: + - REQUIRED for builder-produced release artifacts. + - MUST match the runtime gas schedule version, otherwise execution must be + rejected in release mode. + +## Execution semantics + +### `sourceKind: "script"` + +- Evaluated as deterministic global script mode. +- Result is the final expression value (DV-encodable). + +### `sourceKind: "module-pack"` + +- Evaluated through deterministic in-memory static module loading from + `ModulePack.v1` only. +- No runtime filesystem/network/module registry lookups. +- Entry resolution is driven by the module-pack entry fields. + +## Validation failures (normative categories) + +- `PROGRAM_ARTIFACT_INVALID` +- `PROGRAM_SOURCE_KIND_MISMATCH` +- `PROGRAM_PROFILE_REQUIRED` +- `PROGRAM_ENGINE_HASH_REQUIRED` (for build outputs) + +Module-pack specific runtime errors are specified in `docs/module-pack.md`. + +## Canonicalization and hashing guidance + +`ProgramArtifact.v2` itself is typically transported as JSON-like host data, but +its pinned fields (`abiManifestHash`, `engineBuildHash`, `modulePack.graphHash`) +MUST be computed from canonical byte representations defined in their respective +specs. + +## Relationship to v1 artifacts + +- v1 (`code` + ABI pins) remains supported only as a compatibility input path. +- New builder output target is v2. +- New features (module-pack execution, composite profiles, DV2/Host.v2) are + specified against v2. + +## See also + +- `docs/module-pack.md` +- `docs/execution-profiles.md` +- `docs/builder.md` +- `docs/value-model-v2.md` diff --git a/docs/release-checklist.md b/docs/release-checklist.md index 8237d58..506de68 100644 --- a/docs/release-checklist.md +++ b/docs/release-checklist.md @@ -6,16 +6,78 @@ Scope: steps to publish deterministic engine + ABI packages. - Confirm the working tree is clean and `vendor/quickjs` is pinned to the intended commit. - Run `pnpm lint`, `pnpm nx typecheck`, `pnpm nx test`, and `pnpm nx build`. +- Confirm release-facing docs still state the consensus-safe scope correctly: + - `wasm-node` vs `wasm-browser` + - canonical `wasm32` release engine + - native remains diagnostic-only +- Run strict parity gating for consensus executors (`wasm-node` vs + `wasm-browser`) with raw gas equality (no gas-delta baseline normalization). +- Verify gas schedule docs are synchronized with the canonical spec source: + - `node tools/gas-spec/render-gas-artifacts.mjs --check` +- Verify OOG boundary parity checks are green for the consensus fixture corpus. + - `pnpm nx test test-harness` (includes wasm/native boundary search fixtures in + `libs/test-harness/src/lib/gas-equivalence.spec.ts`). + - `pnpm nx run smoke-web:e2e` (includes browser/node boundary parity in + `apps/smoke-web/tests/gas-boundaries.spec.ts`). +- Archive reproducibility report artifacts for the release candidate: + - Consensus release gate reports (wasm-node vs wasm-browser) are required. + - `node tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs --out-dir artifacts/reproducibility-consensus/chromium --browser chromium` + - `node tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs --out-dir artifacts/reproducibility-consensus/firefox --browser firefox` + - Native report generation is diagnostic by default: + - `node tools/quickjs-native-harness/scripts/archive-reproducibility-report.mjs` + - If native is explicitly promoted to a consensus executor for this release, + require strict native report generation: + - `node tools/quickjs-native-harness/scripts/archive-reproducibility-report.mjs --strict` + - Preserve both generated report JSON and matching `.sha256` sidecars. +- Run workload/ecosystem certification reports: + - `node apps/ecosystem-certifier/scripts/check-builder-determinism.mjs --out-dir artifacts/workload-certification` + - `node tools/workload-certification/compare-builder-determinism-matrix.mjs --input-dir artifacts` + - `node apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs --out-dir artifacts/workload-certification` + - `node apps/ecosystem-certifier/scripts/generate-compatibility-delta-report.mjs --current-dir artifacts/workload-certification --out-dir artifacts/workload-certification` + - `node apps/ecosystem-certifier/scripts/run-oog-boundary-certification.mjs --out-dir artifacts/workload-certification` + - `node apps/ecosystem-certifier/scripts/run-repeatability-certification.mjs --out-dir artifacts/workload-certification --iterations 100 --flagship-iterations 40` + - `node apps/ecosystem-certifier/scripts/run-seeded-property-corpus.mjs --out-dir artifacts/workload-certification --seed-count 80` +- Run downstream tarball consumer reproducibility proof: + - Version alignment + pack manifest checks: + - `pnpm workload:check-public-package-versions` + - `pnpm workload:check-pack-manifests -- --out-dir artifacts/consumer-proof/pack-manifests` + - Primary registry-style rehearsal: + - `pnpm publish-rehearsal:verdaccio -- --out-dir artifacts/consumer-proof/verdaccio` + - Secondary tarball rehearsal: + - `node tools/workload-certification/pack-public-tarballs.mjs --out-dir artifacts/consumer-proof/tarballs` + - `pnpm --dir e2e/consumer-proof-app run install:tarballs -- --tarball-dir ../../artifacts/consumer-proof/tarballs` + - `pnpm --dir e2e/consumer-proof-app exec playwright install --with-deps chromium` + - `pnpm --dir e2e/consumer-proof-app run repro` +- Synthesize release evidence bundle (manifest + summaries + checksums + signatures): + - `pnpm release-evidence:synthesize -- --out-dir artifacts/release-evidence` +- Verify release evidence bundle locally (auditor command): + - `pnpm release-evidence:verify -- --evidence-dir artifacts/release-evidence` +- Confirm the release evidence manifest exists and is complete: + - `artifacts/release-evidence/release-evidence-manifest.json` +- Generate security/supply-chain artifacts: + - `pnpm release-evidence:sbom -- --out-dir artifacts/security` + - `pnpm release-evidence:licenses -- --out-dir artifacts/security` +- Refresh playground generated data and ensure it is not stale: + - `node apps/bluequickjs-playground/scripts/generate-playground-data.mjs` + - `node apps/bluequickjs-playground/scripts/generate-playground-data.mjs --check` ## Wasm build + metadata - Run `pnpm nx build quickjs-wasm-build`. - Verify `libs/quickjs-wasm-build/dist/quickjs-wasm-build.metadata.json`: - `engineBuildHash` is present. + - `gasVersion` is present and matches the release gas schedule. - `variants.wasm32.release.engineBuildHash` matches `sha256` of `quickjs-eval.wasm`. - Run `pnpm nx build quickjs-wasm` and confirm `libs/quickjs-wasm/dist/wasm` contains wasm, loader, and metadata assets. +## Parity policy checks + +- Confirm release workflows do **not** depend on + `tools/quickjs-native-harness/scripts/parity-gas-delta-baseline.json`. +- Diagnostic parity deltas may be retained for investigation workflows, but they + must not be part of release acceptance. + ## Manifest + fixtures - If the manifest changed: @@ -36,3 +98,9 @@ Scope: steps to publish deterministic engine + ABI packages. - Publish the five packages from their package roots after build (dist/ is included in `files`). - Tag the release and record the engine build hash + manifest hash in the release notes. + +## Reference docs + +- [Release-readiness report](./release-readiness-report.md) +- [Production embedder checklist](./production-embedder-checklist.md) +- [Playground](./playground.md) diff --git a/docs/release-go-no-go-template.md b/docs/release-go-no-go-template.md new file mode 100644 index 0000000..b4ee6ac --- /dev/null +++ b/docs/release-go-no-go-template.md @@ -0,0 +1,57 @@ +# Release go / no-go template + +Use this template for final release approval records. + +## Release identity + +- Date: +- Branch: +- Release tag / version: +- Decision: GO / NO-GO + +## Deterministic pins + +- `engineBuildHash`: +- `gasVersion`: +- ABI manifest hash: +- Evidence manifest hash: + +## Shipped profiles + +- [ ] `baseline-v1` +- [ ] `compat-general-v1` +- [ ] `compat-binary-v1` + +## Corpus and certification counts + +- Green corpus count: +- Red corpus count: +- Flagship workload count: +- Consensus mismatch count: +- Workload mismatch count: +- OOG mismatch count: + +## Consensus executor claim + +- Exact claim text: + - `wasm-node` vs `wasm-browser` (required browser engines listed) + - Native diagnostic-only status acknowledged. + +## Evidence verification + +- [ ] `pnpm release-evidence:verify` passed. +- [ ] Tamper detection check passed. +- [ ] SBOM generated and archived. +- [ ] License report generated and archived. + +## Security / rollback readiness + +- [ ] Signature key and verification path confirmed. +- [ ] Rollback procedure reviewed for this release. +- [ ] Threat model and production checklist reviewed. + +## Approvers + +- Engineering: +- Security: +- Release manager: diff --git a/docs/release-notes-draft.md b/docs/release-notes-draft.md new file mode 100644 index 0000000..536917e --- /dev/null +++ b/docs/release-notes-draft.md @@ -0,0 +1,68 @@ +# Release notes draft — wasm-consensus GA readiness + +Date: 2026-03-19 +Scope: wasm-consensus release line (`wasm-node` + `wasm-browser`), native +diagnostic path retained as non-consensus. + +## Highlights + +- Consensus policy now treats **exact gas** and **exact OOG boundaries** as + release-critical alongside value/error/tape parity. +- The repo now includes a polished in-repo **BlueQuickjs Playground** tied to + generated certified examples, red fixtures, and OOG-boundary evidence. +- New docs provide a step-by-step learning path from “what is BlueQuickjs?” to + production embedder guidance and release-evidence verification. +- Workload certification includes: + - flagship knowledge/compliance workload, + - green ecosystem compatibility corpus (25 fixtures / 24 packages + seeded stress), + - deterministic red-boundary scenarios, + - builder determinism evidence, + - downstream consumer reproducibility proof, + - compatibility delta report against previous release baseline. +- Release workflows archive strict parity and workload/consumer evidence. + +## Consensus-safe scope (shipped) + +- Supported consensus executors: + - `wasm-node` + - `wasm-browser` +- Required parity dimensions: + - result/error + - gas used + gas remaining + - host-call tape + - exact first-success / last-failure OOG boundary + +## Unsupported / intentionally constrained behavior + +- Dynamic code generation (`eval`, `Function`) remains disabled. +- Ambient nondeterministic APIs (time/random/timers/fs/network) remain outside + deterministic contract. +- Compatibility surfaces are profile-gated: + - `baseline-v1` + - `compat-general-v1` + - `compat-binary-v1` + +## Native status + +- Native harness remains **diagnostic-only** by default. +- Native parity reports are archived for diagnostics; they are not consensus + release gates unless policy explicitly promotes native to a consensus + executor. + +## Breaking-change and migration notes + +- Deterministic consumers should continue pinning: + - `engineBuildHash`, + - `gasVersion`, + - ABI manifest hash, + - execution profile. +- No migration is required for consumers already pinned to release-mode + `ProgramArtifact.v2` and consensus policy checks. + +## Evidence links + +- Release readiness report: `docs/release-readiness-report.md` +- Workload certification report: `docs/workload-certification.md` +- Ecosystem compatibility report: `docs/ecosystem-compatibility-report.md` +- Playground docs: `docs/playground.md` +- Release policy: `docs/release-policy.md` diff --git a/docs/release-policy.md b/docs/release-policy.md index 47c496f..1b65398 100644 --- a/docs/release-policy.md +++ b/docs/release-policy.md @@ -2,6 +2,39 @@ Scope: define publishing and versioning policy so consumers can pin engine + ABI deterministically (Baseline #1 §1A; Baseline #2 §7). +## Gas closure policy (release-critical) + +Gas is part of the deterministic consensus contract, not a benchmark hint. +Release gating therefore requires: + +- exact result/error/tape parity, +- exact gas used/remaining parity, and +- exact out-of-gas boundary parity + +across all supported **consensus executors**. + +Consensus executor matrix: + +- mandatory: `wasm-node` vs `wasm-browser` using pinned canonical `wasm32` + artifacts. +- required browser engines for release-candidate/release parity evidence: + - Chromium + - Firefox +- WebKit runs as scheduled diagnostic evidence unless explicitly promoted to a + required gate. +- native harness parity is required only when native is explicitly declared a + supported consensus executor for that release. + +`--gas-delta-baseline` style reconciliation artifacts are diagnostic tools only +and are never an acceptable release gate. + +Release candidates must archive signed strict-parity reproducibility reports +(parity report JSON signature + file checksum) for auditability. +The repository command for the consensus wasm-node/wasm-browser report is: +`node tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs`. +Native reproducibility reports remain diagnostic by default; use strict +assertion mode only when native is explicitly promoted to a consensus executor. + ## Published packages - `@blue-quickjs/dv`: DV encode/decode + validation (pure TS). @@ -21,9 +54,27 @@ A deterministic program artifact `P` should pin: - `abiId`, `abiVersion` - `abiManifestHash` (sha256 of canonical manifest bytes) -- `engineBuildHash` (optional but strongly recommended) +- `executionProfile` (explicit, versioned profile name) +- `gasVersion` (required for release-mode artifacts) +- `engineBuildHash` (required for builder-produced release artifacts) `@blue-quickjs/quickjs-runtime` validates these fields and rejects mismatches when provided. +In `releaseMode`, embedders must pass an expected execution profile pin +(`expectedExecutionProfile`) so runtime execution fails on profile mismatches. + +For release-mode execution, `engineBuildHash`, `gasVersion`, and +`executionProfile` are required pins. + +For `ProgramArtifact.v2` module-pack outputs, pinning should additionally include: + +- `sourceKind` (`script` vs `module-pack`) +- `modulePack.graphHash` when `sourceKind = "module-pack"` + +See: + +- `docs/program-artifact-v2.md` +- `docs/module-pack.md` +- `docs/execution-profiles.md` ## engine_build_hash @@ -32,9 +83,16 @@ Definition: - `engineBuildHash = sha256(wasm_bytes)` for a given variant + buildType. - Lowercase hex, 64 characters. +`gasVersion` definition: + +- Monotonic integer identifying the canonical gas schedule semantics. +- Any semantic gas-schedule change (including allocation charging model changes) + requires an explicit gasVersion bump. + Exposure: - `quickjs-wasm-build.metadata.json` includes: + - top-level `gasVersion` for runtime/artifact gas pin validation. - `variants...engineBuildHash` for every emitted artifact. - Top-level `engineBuildHash`, set to the canonical engine hash (`wasm32` + `release`) when present. - `@blue-quickjs/quickjs-wasm` exposes these values via `loadQuickjsWasmMetadata()` and @@ -89,6 +147,13 @@ New `engineBuildHash` is required when: memory sizing, toolchain version, or build flags alters the wasm bytes. - Rebuilding with different Emscripten/flags also produces a new hash. +New `gasVersion` is required when: + +- Any change can alter canonical gas used/remaining or OOG boundaries for the + same `(P, I, G)`. +- This includes changes to opcode charges, builtin charges, host-call charging, + allocation charging model, or GC checkpoint charging semantics. + New `abiManifestHash` is required when: - Any manifest field changes: function list, `fn_id`, `js_path`, `arg_schema`, diff --git a/docs/release-provenance.md b/docs/release-provenance.md new file mode 100644 index 0000000..fa27420 --- /dev/null +++ b/docs/release-provenance.md @@ -0,0 +1,60 @@ +# Release provenance and trust model + +This document defines what release evidence is signed, how checksums are +produced, and how operators should validate trust before accepting a release. + +## Signed artifacts + +The release workflow generates a release-evidence bundle containing: + +- `release-evidence-summary.json` +- `release-evidence-summary.md` +- `release-evidence-manifest.json` +- `*.sha256` sidecars +- `*.sig` detached signature payloads +- copied source evidence inputs (consensus/workload/consumer reports) + +Generation command: + +```bash +pnpm release-evidence:synthesize -- --out-dir artifacts/release-evidence +``` + +Verification command: + +```bash +pnpm release-evidence:verify -- --evidence-dir artifacts/release-evidence +``` + +## Checksum model + +- SHA-256 is used for all artifact checksum entries. +- Manifest entries include per-file `sha256` and relative path. +- `*.sha256` sidecars are generated for summary/manifest outputs. + +## Signature model + +The synthesizer emits detached `*.sig` payloads in one of two modes: + +1. `ed25519` (preferred production mode, when signing key is supplied), or +2. `digest-fallback` (local/dev mode, checksum-backed proof only). + +Production releases should always use an injected signing key and verify with +the corresponding public key in CI and by downstream auditors. + +## Trust assumptions + +Consumers should trust a release only when: + +1. checksums match manifest entries, +2. detached signatures verify successfully, +3. branch/date/release metadata match expected release context, +4. consensus parity mismatch counts are zero and exact OOG parity is true. + +## Related commands and docs + +- `pnpm release-evidence:synthesize` +- `pnpm release-evidence:verify` +- `docs/release-policy.md` +- `docs/release-checklist.md` +- `docs/signature-rotation-and-rollback.md` diff --git a/docs/release-readiness-report.md b/docs/release-readiness-report.md new file mode 100644 index 0000000..418007e --- /dev/null +++ b/docs/release-readiness-report.md @@ -0,0 +1,54 @@ +# Release-readiness report (current branch snapshot) + +Date: 2026-03-19 +Branch: `cursor/wasm-consensus-ga-readiness-51ed` + +> This file is generated by `node tools/release-evidence/synthesize-release-evidence.mjs`. + +## Environment + +- engineBuildHash: `f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea` +- gasVersion: `8` + +## Consensus-safe vs diagnostic-only + +### Consensus-safe (release gate) + +- Executor pair: `wasm-node` vs `wasm-browser` (`wasm32` release artifacts). +- Gate requirements: exact value/error parity, exact gas parity, exact tape parity, exact OOG boundary parity. +- Consensus mismatch count: `0` + +### Diagnostic-only + +- Native parity remains diagnostic-only unless explicitly promoted by release policy. + +## Certification and parity snapshot + +- Workload totals: `34` fixtures (`25` green / `8` red / `1` flagship) +- Workload mismatch count: `0` +- Workload OOG mismatch count: `0` +- Compatibility green delta vs baseline: `9` +- Consumer snapshot parity: `true` +- Consumer OOG parity: `true` +- Exact OOG parity status: `true` + +## Evidence manifest + +- Manifest file: `artifacts/release-evidence/release-evidence-manifest.json` +- Manifest artifact entries: `10` + +## Included artifacts + +| Category | File | SHA256 | +| --- | --- | --- | +| consensus | `inputs/consensus-report.json` | `425a86bd0b9e26270739b028962697d8012c715d7273bf079b113fcaada066ca` | +| workload | `inputs/workload-certification.json` | `b6e3db7f6f74757cd3fc9e8340c36d7fcf9e2007b697ad8a3acbf52cead5dd84` | +| workload | `inputs/workload-oog-boundaries.json` | `8fdc314624471a6e7f6f1569487b38008cf605a2f2588776874870cef61a8913` | +| workload | `inputs/workload-compatibility-matrix.json` | `8385d1f5a8bf2ad0b03b06e27d334a8990b83fafa8993ebc83de3985c8f78774` | +| consumer | `inputs/consumer-reproducibility.json` | `51b9ea68ea118d2c61fd2c6f58435b246571353ba874553dbf4c4b80b32f25f0` | +| workload | `inputs/workload-repeatability.json` | `b8aba6aa2b7596f19b08f27895849e7c9718d521344a2f315f2664e19c9047dd` | +| workload | `inputs/workload-seeded-corpus.json` | `2de997e196ee743bf95c284c3d75966c9814b823f0a9663f58113d38785b1637` | +| workload | `inputs/workload-compatibility-delta.json` | `3f73b336bb8c2e2f4388f395c42f8dd2200702f4ced3b9fd6a870abdeb1a13b7` | +| release-evidence | `release-evidence-summary.json` | `1a0376d9257b355ea8432bdd33b0cbc2ea1e026bf6db9f307b87fd15e88cb76c` | +| release-evidence | `release-evidence-summary.md` | `90c77c1a503c43229450a3fa39b50cf2ba8f7b768ecb12576f7f6f826760530b` | + diff --git a/docs/repository-metadata-checklist.md b/docs/repository-metadata-checklist.md new file mode 100644 index 0000000..f7750f0 --- /dev/null +++ b/docs/repository-metadata-checklist.md @@ -0,0 +1,42 @@ +# Repository metadata checklist (GitHub settings) + +This checklist tracks the release-story polish that lives in GitHub repository +settings rather than source files. + +## 1) Description + +Set repository description to a product-facing summary, for example: + +> Deterministic QuickJS-in-Wasm engine for consensus-critical JavaScript +> execution with exact gas/OOG parity and manifest-locked host ABI. + +## 2) Topics + +Recommended topics: + +- `quickjs` +- `webassembly` +- `deterministic-execution` +- `consensus` +- `gas-metering` +- `reproducibility` +- `runtime` +- `javascript` + +## 3) Website pointer + +Set repository website to the release landing documentation entry: + +- `https://github.com/bluecontract/blue-quickjs/blob/main/README.md` + +If a dedicated release portal is published later, replace this URL with that +stable endpoint. + +## 4) Required verification + +After applying metadata: + +1. Confirm repo home page shows updated description/topics/website. +2. Confirm README opening matches the same product framing. +3. Confirm release notes and readiness docs reference the same consensus-safe + scope language. diff --git a/docs/sdk.md b/docs/sdk.md index 890b30a..c26b4fe 100644 --- a/docs/sdk.md +++ b/docs/sdk.md @@ -9,6 +9,8 @@ This doc explains how to use the TypeScript runtime SDK (`libs/quickjs-runtime`) Conceptual overview: [Implementation summary](./implementation-summary.md). ABI and DV specs: [Baseline #2](./baseline-2.md), [ABI manifest](./abi-manifest.md), [Host call ABI](./host-call-abi.md), [DV wire format](./dv-wire-format.md). +Runnable scenario matrix (module-pack, promises, libraries, binary, OOG +boundaries): [Examples corpus](../examples/README.md). --- @@ -72,6 +74,72 @@ console.log('gas used:', result.gasUsed.toString()); console.log('gas remaining:', result.gasRemaining.toString()); ``` +## Bundling libraries into deterministic source + +`evaluate()` expects `program.code` to be a single source string. For reusable +multi-file libraries, bundle first: + +```ts +import { bundleDeterministicProgram } from '@blue-quickjs/deterministic-bundler'; + +const bundled = await bundleDeterministicProgram({ + absWorkingDir: process.cwd(), + entryPath: 'src/program-entry.ts', + // baseline-v1 rejects RegExp; compat-regexp-v1 allows it explicitly. + profile: 'baseline-v1', +}); + +const program = { + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: '…', + executionProfile: 'baseline-v1', + code: bundled.code, +}; +``` + +Bundling returns a deterministic content hash and compatibility diagnostics. By +default, compatibility violations fail fast before VM execution. + +## Execution semantics (raw script mode) + +`blue-quickjs` evaluates `program.code` as a **raw global script**. + +- The result is the DV-encodable value of the script’s final expression. +- Top-level `return` is invalid in this mode and fails deterministically. +- Side effects can be emitted through `emit(value)` / `Host.v1.emit(value)`. + +Raw script with final expression: + +```ts +const program = { + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: '…', + code: ` + const base = 40; + base + 2 + `, +}; +``` + +Emit side effects plus explicit final result: + +```ts +const program = { + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: '…', + code: ` + emit({ type: 'trace', step: 'start' }); + ({ ok: true }) + `, +}; +``` + +If your surrounding workflow uses function wrappers or custom return conventions, +that wrapper behavior belongs to the embedder/orchestrator layer, not this evaluator. + ### What you get back `evaluate()` returns a structured `EvaluateResult`: @@ -95,12 +163,20 @@ A program artifact is “code + ABI identity/pinning metadata”. The SDK valida - `abiVersion` (integer) - `abiManifestHash` (lowercase hex) - `code` (string) +- optional `gasVersion` (uint32; required for release-mode artifact pinning) Some environments also provide `engineBuildHash` pinning; if present, the SDK checks that the wasm runtime build hash matches. +For `releaseMode` execution, pass `expectedExecutionProfile` to `evaluate()`. +The SDK rejects artifacts whose `program.executionProfile` is missing or does +not match the runtime's expected profile. + Optional fields: - `engineBuildHash` (lowercase hex; sha256 of the wasm bytes) +- `gasVersion` (uint32 gas schedule version) +- `executionProfile` (`"baseline-v1"` default, or `"compat-general-v1"` for + compatibility-mode execution; `"compat-regexp-v1"` remains as a legacy alias) Program artifact limits (validation defaults used by `evaluate()` and `initializeDeterministicVm()`): @@ -117,6 +193,28 @@ The hash pinning rules are described in: - [ABI manifest](./abi-manifest.md) (canonical encoding + hash) - [Release policy](./release-policy.md) +### ProgramArtifact.v2 runtime support + +The runtime now accepts both: + +- legacy single-source script artifacts (`ProgramArtifact` v1), and +- `ProgramArtifact.v2` with `sourceKind: "script"`. + +`ProgramArtifact.v2` with `sourceKind: "module-pack"` now executes via the +runtime's in-memory module loader path. The runtime validates +`modulePack.graphHash` before execution and emits deterministic module-pack +error codes for hash mismatches, missing specifiers/exports, resolution errors, +and evaluation failures. + +The versioned artifact model is specified in: + +- [Program artifact v2](./program-artifact-v2.md) +- [Module pack v1](./module-pack.md) +- [Execution profiles](./execution-profiles.md) + +This locks the migration target for module-pack execution and explicit +profile-required build outputs. + ### 2) Input envelope (`I`) The input envelope is DV-encodable data injected into the VM as ergonomic globals. diff --git a/docs/signature-rotation-and-rollback.md b/docs/signature-rotation-and-rollback.md new file mode 100644 index 0000000..925402d --- /dev/null +++ b/docs/signature-rotation-and-rollback.md @@ -0,0 +1,47 @@ +# Signature rotation and emergency rollback + +This document defines operational handling for evidence-signing key rotation and +release rollback when deterministic pins (`engineBuildHash`, `gasVersion`) move. + +## Key rotation policy + +1. Maintain a current active signing key pair and a staged next key pair. +2. Publish/commit the active public verification key material used by auditors. +3. Rotate keys on schedule or on compromise suspicion. +4. During rotation windows, optionally dual-sign evidence bundles until all + verifiers have adopted the new key. + +## Verification key updates + +- Any key update must be called out in release notes. +- CI verification jobs must validate signatures against the expected key for the + release line. +- Auditors should reject evidence signed by unknown/untrusted keys. + +## Emergency rollback triggers + +Rollback is required when any of the following occur: + +- signature verification failures on release evidence bundle, +- manifest/checksum mismatch in archived release artifacts, +- unintended `engineBuildHash` movement, +- unintended `gasVersion` movement, +- deterministic mismatch regression in consensus reports. + +## Rollback procedure (minimum) + +1. Halt release/publish jobs. +2. Mark current candidate as revoked. +3. Rebuild and regenerate release evidence on last-known-good commit. +4. Re-verify: + - `pnpm release-evidence:verify` + - strict consensus parity reports. +5. Publish rollback advisory with revoked hashes/versions and replacement + evidence bundle. + +## Mandatory operator checks before unpausing + +- `engineBuildHash` explicitly reviewed and expected. +- `gasVersion` explicitly reviewed and expected. +- release-evidence manifest hash recorded in go/no-go template. +- consensus mismatch counts and OOG parity status are green. diff --git a/docs/threat-model.md b/docs/threat-model.md new file mode 100644 index 0000000..9095ea2 --- /dev/null +++ b/docs/threat-model.md @@ -0,0 +1,53 @@ +# Operator threat model (wasm-consensus scope) + +This threat model is operator-facing and focused on production usage of the +wasm-consensus executor path. + +## In-scope guarantees + +For the same `(P, I, G)` and deterministic host responses: + +- deterministic result/error parity, +- deterministic gas used/remaining parity, +- deterministic host-call tape parity, +- deterministic exact OOG boundary parity + +across consensus executors (`wasm-node` + required browser engines). + +## Out-of-scope guarantees + +- native harness parity as a consensus claim (native is diagnostic-only unless + explicitly promoted), +- behavior of disabled nondeterministic APIs (time/random/timers/fs/network), +- security of host systems outside manifest-locked Host ABI boundaries. + +## Main threat categories + +1. **Artifact tampering** + - altered evidence files, checksums, or manifests. + - Mitigation: checksum + detached signature verification. + +2. **Pin drift** + - unexpected `engineBuildHash` / `gasVersion` changes. + - Mitigation: explicit pin review and release go/no-go recording. + +3. **Host capability widening** + - accidental ABI or runtime surface widening beyond profile policy. + - Mitigation: manifest lock, profile checks, deterministic negative fixtures. + +4. **Cross-environment parity regressions** + - browser/runtime drift introducing mismatch. + - Mitigation: strict parity matrix and OOG certification in CI/release. + +## Mandatory production pins + +- `engineBuildHash` +- `gasVersion` +- ABI manifest hash +- execution profile + +## Native status reminder + +Native executor output is diagnostic-only and must not be used as consensus +acceptance criteria unless release policy explicitly promotes native for that +release line. diff --git a/docs/toolchain.md b/docs/toolchain.md index 1f096b0..bfc29b2 100644 --- a/docs/toolchain.md +++ b/docs/toolchain.md @@ -14,13 +14,36 @@ Baseline anchors: see `docs/baseline-1.md` (deterministic execution constraints) 1. From repo root: `tools/scripts/setup-emsdk.sh` - Clones `emsdk` into `tools/emsdk` if missing. - Installs + activates the pinned version. -2. Load env into your shell for the session: `source tools/emsdk/emsdk_env.sh`. -3. Verify: `emcc --version` should report `3.1.56`. +2. Ensure the pinned QuickJS submodule is present: + + ```bash + git submodule update --init --recursive vendor/quickjs + ``` + + The repo now auto-runs this check before native-harness and wasm builds, but + it is still useful as an explicit recovery step on fresh clones. +3. Load env into your shell for the session: `source tools/emsdk/emsdk_env.sh`. +4. Verify: `emcc --version` should report `3.1.56`. Notes: - Script is idempotent; rerun after pulling a new pinned version. - Keep `emsdk` network access unblocked during install. +- On macOS, the setup script now retries once automatically, clears quarantine + attributes if possible, and on Apple Silicon retries the install with + `EMSDK_ARCH=x86_64` as a fallback. If that fallback path succeeds, Rosetta may + be required: + + ```bash + softwareupdate --install-rosetta --agree-to-license + ``` + +- The setup script now prefers the host `python3`/`python` to run `emsdk.py` + directly, which avoids macOS repeatedly re-entering a partially installed + bundled Python during retries. +- On macOS specifically, the script prefers `/usr/bin/python3` over Conda or + other shimmed interpreters and clears `PYTHONHOME`, `PYTHONPATH`, and common + `CONDA_*` variables before invoking `emsdk.py`. ## CI caching @@ -47,4 +70,4 @@ Notes: - Artifacts land in `libs/quickjs-wasm-build/dist/` as `quickjs-eval{,-debug}{,-wasm64}.{js,wasm}` (wasm32 is canonical; wasm64 is optional for debugging). Loader + metadata are resolved via `getQuickjsWasmArtifacts(...)` and `readQuickjsWasmMetadata()`. - `quickjs-wasm-build.metadata.json` captures per-variant/per-build-type filenames, hashes, sizes, flags, and `engineBuildHash` (keyed to wasm32 release when present). -- The wasm harness exports deterministic ABI entrypoints only (`qjs_det_init`/`qjs_det_eval`/`qjs_det_set_gas_limit`/`qjs_det_free` plus tape/trace helpers) and returns DV-hex payloads with `RESULT … GAS …` / `ERROR … GAS …` formatting; strings are freed with the exported `_free` helper. +- The wasm harness exports deterministic ABI entrypoints only (`qjs_det_init`/`qjs_det_eval`/`qjs_det_set_gas_limit`/`qjs_det_free` plus tape/trace helpers) and returns DV-hex payloads with `RESULT … GAS …` / `ERROR … GAS …` formatting; `qjs_det_init(..., feature_flags)` accepts deterministic feature flags (`0` for baseline), and strings are freed with the exported `_free` helper. diff --git a/docs/unsupported-features-and-why.md b/docs/unsupported-features-and-why.md new file mode 100644 index 0000000..4778ad4 --- /dev/null +++ b/docs/unsupported-features-and-why.md @@ -0,0 +1,73 @@ +# Unsupported features and why + +BlueQuickjs is intentionally narrower than a general-purpose JavaScript +runtime. Unsupported features are not arbitrary omissions; they are deliberate +choices to preserve deterministic behavior and auditability. + +## Unsupported in the consensus baseline + +### Dynamic code generation + +- `eval` +- `Function` + +Why: these widen the executable surface at runtime and make review/auditing much +harder. + +### Ambient nondeterminism + +- clocks and wall time +- randomness +- timers +- filesystem +- network +- locale-sensitive ambient behavior + +Why: independent nodes must not depend on host-local state or scheduling. + +### Runtime module loading + +- dynamic `import()` +- runtime fetch/import/network resolution + +Why: module graphs must be fixed at build time and represented as +`ModulePack.v1`. + +## Unsupported unless a compatibility profile enables them + +### Promise jobs and microtasks + +Allowed only in: + +- `compat-general-v1` +- `compat-binary-v1` + +Why: Promise job draining must be deterministic and explicitly versioned. + +### Typed arrays / `ArrayBuffer` / `DataView` + +Allowed only in: + +- `compat-binary-v1` + +Why: binary boundaries require DV2 / `Host.v2` semantics and must not widen the +baseline accidentally. + +## Unsupported as consensus executors + +### Native runtime parity + +Native is still used heavily for diagnostics, reconciliation, and harness work, +but it is not part of today’s consensus release gate. + +### Diagnostic browser paths + +WebKit and other diagnostic browser runs may be useful, but the required +release matrix today is Chromium/Firefox-backed wasm browser execution. + +## Related docs + +- [Determinism profile](./determinism-profile.md) +- [Execution profiles](./execution-profiles.md) +- [Value model v2 (DV2)](./value-model-v2.md) +- [Consensus-safe vs diagnostic-only](./consensus-safe-vs-diagnostic-only.md) diff --git a/docs/value-model-v2.md b/docs/value-model-v2.md new file mode 100644 index 0000000..c5b8f6c --- /dev/null +++ b/docs/value-model-v2.md @@ -0,0 +1,77 @@ +# Value model v2 (DV2) and binary boundary support + +Baseline anchors: + +- `docs/baseline-1.md` +- `docs/baseline-2.md` +- current DV spec: `docs/dv-wire-format.md` + +## Decision + +Binary boundary support is delivered via a **new versioned value model** (DV2), +not by mutating DV1 in place. + +## Why + +- Current DV intentionally excludes byte strings. +- Typed-array-heavy libraries require a canonical bytes boundary. +- Versioning avoids breaking existing Host.v1/DV1 contracts. + +## DV2 additions + +DV2 extends DV1 with canonical byte strings: + +- `bytes` type (canonical CBOR byte string form, definite-length only). + +SDK surface: + +- `encodeDv2(...)`, `decodeDv2(...)`, `validateDv2(...)`, `isDv2(...)` + in `@blue-quickjs/dv`. +- QuickJS C surface: `JS_EncodeDV2(...)` / `JS_DecodeDV2(...)` (DV1 APIs remain + unchanged). +- DV1 APIs (`encodeDv`, `decodeDv`) remain unchanged and continue rejecting byte + strings. + +All existing DV1 canonical constraints still apply (finite numbers, canonical +ordering, deterministic size/depth limits). + +## JS boundary mapping + +- Wire `bytes` maps to `Uint8Array` at JS host/runtime boundaries. +- Within VM execution profiles that allow typed arrays, binary APIs can operate + on ArrayBuffer/DataView/typed arrays. +- Non-byte typed arrays are runtime values, but boundary canonicalization must + still be explicit and deterministic. +- Current implementation wires this mapping for Host.v2 boundaries in: + - quickjs-runtime host dispatcher, + - QuickJS host-call wrappers (`JS_EncodeDV2` / `JS_DecodeDV2`), + - native harness manifest stubs and parity scripts. + +## ABI versioning policy + +- Keep `Host.v1` + DV1 behavior unchanged. +- Introduce `Host.v2` (or equivalent ABI version bump) for DV2 boundary types. +- Mixed-version ambiguity is not allowed. + +## Canonical encoding notes + +- Definite lengths only. +- No non-canonical alternate encodings. +- No accidental acceptance of non-canonical buffer representations. + +## Compatibility profile linkage + +DV2 boundary bytes are enabled only when profile capabilities include `dvBytes` +(see `docs/execution-profiles.md`, e.g. `compat-binary-v1`). + +## Test requirements + +- bytes round-trip across host call args/returns and final result, +- canonical hash stability for byte values, +- rejection of non-canonical byte encodings, +- parity across native / wasm-node / wasm-browser. + +## See also + +- `docs/execution-profiles.md` +- `docs/abi-manifest.md` diff --git a/docs/workload-certification-plan.md b/docs/workload-certification-plan.md new file mode 100644 index 0000000..c8ad372 --- /dev/null +++ b/docs/workload-certification-plan.md @@ -0,0 +1,157 @@ +# Workload Certification Plan (RC ecosystem phase) + +This plan defines the certification work for proving that `blue-quickjs` is a +practical deterministic JavaScript platform for downstream workloads and npm +ecosystem reuse. + +The goal of this phase is **evidence**, not broadening VM semantics. + +## Scope and non-goals + +### In scope + +1. In-repo workload lab app for mixed real-world deterministic workloads. +2. Downstream consumer app that installs published-style package tarballs and + runs outside workspace shortcuts. +3. Broad compatibility matrix with deterministic pass/fail boundaries. +4. Strict wasm-node vs wasm-browser parity evidence for: + - result/error, + - gas used/remaining, + - host tape, + - exact OOG boundary. +5. Machine-readable reproducibility artifacts and certification reports. + +### Out of scope + +- Opportunistic VM feature expansion to make individual libraries pass. +- Re-defining consensus executor policy (native remains diagnostic-only). + +## Phase order + +### Phase 1 — foundation and planning lock + +- Verify branch is positioned after the RC line. +- Create this certification plan first. +- Finalize flagship workload architecture and candidate corpora. +- Scaffold workload-lab and downstream app surfaces. + +### Phase 2 — first working certification path + +- Implement downstream tarball install/build/run flow. +- Implement workload-lab node/browser runners. +- Land initial compatibility fixtures (green + red). +- Emit first parity report JSON. + +### Phase 3 — full workload + matrix hardening + +- Finish flagship demanding app. +- Expand compatibility matrix to target counts. +- Add OOG boundary harness, soak runs, and deterministic property/stress + corpora. + +### Phase 4 — reporting and release integration + +- Final certification reports. +- CI/release artifact generation hooks. +- README/docs index updates. + +## Deliverables + +1. **Workload lab app** (`apps/ecosystem-certifier`) + - source + deterministic fixtures + - node and browser runners + - parity/OOG/soak/property scripts + - report archiver (JSON + markdown + checksums + signature digest) + +2. **Downstream consumer app** (`e2e/consumer-proof-app`) + - install from tarballs only + - artifact build + node/browser run + - parity + OOG comparison + - reproducibility report + +3. **Ecosystem compatibility report** + - `docs/ecosystem-compatibility-report.md` + - green/red matrix, profile requirements, deterministic failure reasons, + evidence references + +4. **Workload certification report** + - `docs/workload-certification.md` + - flagship architecture, library set, parity/OOG evidence, known limits + +## Flagship workload + +The flagship workload is a deterministic “knowledge/compliance pack processor”. +It processes fixed synthetic corpora containing: + +- markdown documents, +- YAML metadata, +- semver rules, +- JSON rule sets, +- binary attachments (base64/compressed bytes), +- link/dependency graphs, +- emitted findings/traces. + +Pipeline stages: + +1. host document reads (manifest-locked), +2. metadata parse/normalize, +3. markdown token/link extraction, +4. semver rule evaluation, +5. findings synthesis, +6. binary decode/decompress/hash, +7. graph build + deterministic traversal, +8. stable sort + canonical summary output, +9. deterministic host emit trace. + +## Compatibility matrix goals + +### Positive corpus target + +At least **12–15 green packages**, spanning multiple categories +(text/metadata, utilities, rules/parsing, algorithms/data structures, binary). + +### Negative corpus target + +At least **5 deterministic red scenarios** proving crisp unsupported boundaries, +including dynamic codegen, Proxy dependence, randomness/time APIs, and +environment-dependent imports. + +Each red fixture records deterministic failure stage: + +- builder rejection, +- artifact validation/pin failure, +- runtime deterministic error. + +## Determinism evidence requirements + +For major workloads and compatibility fixtures: + +- exact result/error parity between wasm-node and wasm-browser, +- exact gas used and gas remaining parity, +- exact host tape hash and tape length (where host calls occur), +- exact first-success/last-failure OOG boundary parity. + +Repeatability subset: + +- 50–100 reruns with identical result hash, gas, tape, and failure behavior. + +Builder determinism evidence: + +- identical graph/artifact hashes across path variation and OS matrix builds. + +## Evidence artifacts + +Certification scripts must emit machine-readable artifacts including: + +- parity report JSON, +- compatibility matrix JSON, +- OOG boundary JSON, +- human summary markdown, +- checksums (`.sha256`), +- signature digest field (sha256 over canonical report payload). + +## Policy guardrails + +- Deterministic contract is never loosened just to pass a package. +- Unsupported behavior is documented as deterministic failure, not hidden. +- Native executor output is diagnostic-only unless release policy changes. diff --git a/docs/workload-certification.md b/docs/workload-certification.md new file mode 100644 index 0000000..09b78af --- /dev/null +++ b/docs/workload-certification.md @@ -0,0 +1,82 @@ +# Workload Certification Report + +This document defines the workload-certification evidence flow for the RC +ecosystem phase. + +## What is certified + +1. **Flagship workload**: deterministic knowledge/compliance pack processing + (`apps/ecosystem-certifier/fixtures/flagship/knowledge-pack-entry.ts`). +2. **Compatibility matrix**: broad green/red third-party corpus executed via + `apps/ecosystem-certifier`. +3. **Consensus parity**: strict wasm-node vs wasm-browser comparison for + value/error, gas, tape, and expected failure stage. + - Required release-candidate browsers: **Chromium** and **Firefox**. + - WebKit remains diagnostic-only when run via scheduled workflow. +4. **Builder path determinism**: hash equality checks from distinct absolute + working directories. +5. **Downstream tarball consumer proof**: + `e2e/consumer-proof-app` installs packed `@blue-quickjs/*` tarballs and + validates node/browser parity plus exact OOG boundaries. + +## Commands + +From repo root: + +```bash +# Ecosystem certifier tests +source tools/emsdk/emsdk_env.sh +pnpm nx test ecosystem-certifier +pnpm nx run ecosystem-certifier:e2e + +# Builder path determinism + workload matrix report +node apps/ecosystem-certifier/scripts/check-builder-determinism.mjs --out-dir artifacts/workload-certification +node tools/workload-certification/compare-builder-determinism-matrix.mjs --input-dir artifacts +node apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs --out-dir artifacts/workload-certification --browser chromium +node apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs --out-dir artifacts/workload-certification --browser firefox +node apps/ecosystem-certifier/scripts/generate-compatibility-delta-report.mjs --current-dir artifacts/workload-certification --out-dir artifacts/workload-certification +node apps/ecosystem-certifier/scripts/run-oog-boundary-certification.mjs --out-dir artifacts/workload-certification --browser chromium +node apps/ecosystem-certifier/scripts/run-oog-boundary-certification.mjs --out-dir artifacts/workload-certification --browser firefox +node apps/ecosystem-certifier/scripts/run-repeatability-certification.mjs --out-dir artifacts/workload-certification --iterations 100 --flagship-iterations 40 --browser chromium +node apps/ecosystem-certifier/scripts/run-seeded-property-corpus.mjs --out-dir artifacts/workload-certification --seed-count 80 --browser chromium + +# Downstream tarball consumer proof (Node/OS matrix-ready) +pnpm workload:check-public-package-versions +pnpm workload:check-pack-manifests -- --out-dir artifacts/consumer-proof/pack-manifests +pnpm publish-rehearsal:verdaccio -- --out-dir artifacts/consumer-proof/verdaccio +node tools/workload-certification/pack-public-tarballs.mjs --out-dir artifacts/consumer-proof/tarballs +pnpm --dir e2e/consumer-proof-app run install:tarballs -- --tarball-dir ../../artifacts/consumer-proof/tarballs +pnpm --dir e2e/consumer-proof-app exec playwright install --with-deps chromium +pnpm --dir e2e/consumer-proof-app run repro +# optional native diagnostic section +pnpm --dir e2e/consumer-proof-app run repro -- --with-native +``` + +## Expected artifact outputs + +- `artifacts/workload-certification/builder-determinism-report.json` +- `artifacts/workload-certification/workload-certification-.json` +- `artifacts/workload-certification/workload-certification-.md` +- `artifacts/workload-certification/workload-certification-.json.sha256` +- `artifacts/workload-certification/compatibility-matrix-.json` +- `artifacts/workload-certification/compatibility-delta-report.json` +- `artifacts/workload-certification/oog-boundaries.json` +- `artifacts/workload-certification/repeatability-report.json` +- `artifacts/workload-certification/seeded-property-corpus-report.json` +- `e2e/consumer-proof-app/reports/reproducibility-report.json` +- `e2e/consumer-proof-app/reports/oog-boundary.json` +- `e2e/consumer-proof-app/reports/native-diagnostic.json` (optional) + +The workload-certification JSON includes: + +- summary counts (`greenCount`, `redCount`, `mismatches`, `flagshipCount`), +- a machine-readable `compatibilityMatrix`, +- full per-fixture node/browser snapshots with gas and tape hashes, +- signature digest (`sha256`) over canonical report payload. + +## Policy notes + +- Consensus remains **wasm-node vs wasm-browser**. +- Native harness remains diagnostic-only. +- Failures are documented as deterministic incompatibilities instead of widening + deterministic contracts. diff --git a/e2e/consumer-proof-app/README.md b/e2e/consumer-proof-app/README.md new file mode 100644 index 0000000..134b1ff --- /dev/null +++ b/e2e/consumer-proof-app/README.md @@ -0,0 +1,68 @@ +# consumer-proof-app + +Downstream application proof that consumes published `@blue-quickjs/*` +artifacts and validates deterministic parity from a consumer’s point of view. + +It supports both release-rehearsal paths used by the repo: + +- **tarball rehearsal** — install locally packed publish-style tarballs +- **registry/Verdaccio rehearsal** — publish to a local registry and install + from there + +## Tarball rehearsal flow + +1. Pack publish-style tarballs from repo root: + + ```bash + node tools/workload-certification/pack-public-tarballs.mjs --out-dir artifacts/consumer-proof/tarballs + ``` + +2. Install tarballs into this app: + + ```bash + cd e2e/consumer-proof-app + pnpm run install:tarballs -- --tarball-dir ../../artifacts/consumer-proof/tarballs + ``` + +3. Generate the reproducibility report (node + browser + OOG boundary): + + ```bash + pnpm run repro + ``` + + Firefox parity run: + + ```bash + pnpm run repro -- --browser firefox + ``` + +## Registry / Verdaccio rehearsal flow + +From repo root: + +```bash +pnpm publish-rehearsal:verdaccio -- --out-dir artifacts/consumer-proof/verdaccio +``` + +That flow publishes the workspace packages into a local Verdaccio registry, +installs them into this consumer app, and then runs the same downstream proof. + +## Outputs + +Reports are written to: + +- `e2e/consumer-proof-app/reports/` + +Key artifacts include: + +- reproducibility report +- OOG-boundary report +- optional native diagnostic report + +## Optional native diagnostic run + +Native remains non-consensus. Use only as a diagnostic supplement: + +```bash +pnpm run repro -- --with-native +``` diff --git a/e2e/consumer-proof-app/index.html b/e2e/consumer-proof-app/index.html new file mode 100644 index 0000000..f594262 --- /dev/null +++ b/e2e/consumer-proof-app/index.html @@ -0,0 +1,12 @@ + + + + + + Blue QuickJS Consumer Proof + + +
Loading consumer proof runner…
+ + + diff --git a/e2e/consumer-proof-app/package.json b/e2e/consumer-proof-app/package.json new file mode 100644 index 0000000..5ea23f4 --- /dev/null +++ b/e2e/consumer-proof-app/package.json @@ -0,0 +1,24 @@ +{ + "name": "consumer-proof-app", + "version": "0.0.1", + "private": true, + "type": "module", + "scripts": { + "install:tarballs": "node scripts/install-from-tarballs.mjs", + "build-artifact": "node scripts/build-artifact.mjs", + "run-node": "node scripts/run-node.mjs", + "run-browser": "node scripts/run-browser.mjs", + "find-oog": "node scripts/find-oog-boundary.mjs", + "run-native-diagnostic": "node scripts/run-native-diagnostic.mjs", + "repro": "node scripts/reproducibility-report.mjs" + }, + "dependencies": { + "he": "^1.2.0", + "path-to-regexp": "^8.2.0", + "semver": "^7.7.3" + }, + "devDependencies": { + "@playwright/test": "^1.57.0", + "vite": "^7.2.7" + } +} diff --git a/e2e/consumer-proof-app/playwright.config.mjs b/e2e/consumer-proof-app/playwright.config.mjs new file mode 100644 index 0000000..b2c40d7 --- /dev/null +++ b/e2e/consumer-proof-app/playwright.config.mjs @@ -0,0 +1,9 @@ +import { defineConfig } from '@playwright/test'; + +export default defineConfig({ + testDir: './tests', + use: { + headless: true, + baseURL: 'http://127.0.0.1:4320', + }, +}); diff --git a/e2e/consumer-proof-app/scripts/_helpers.mjs b/e2e/consumer-proof-app/scripts/_helpers.mjs new file mode 100644 index 0000000..1c7dc79 --- /dev/null +++ b/e2e/consumer-proof-app/scripts/_helpers.mjs @@ -0,0 +1,75 @@ +import { createHash } from 'node:crypto'; +import { mkdir, readFile, writeFile } from 'node:fs/promises'; +import path from 'node:path'; + +export const appRoot = path.resolve(import.meta.dirname, '..'); +export const reportsDir = path.resolve(appRoot, 'reports'); +export const artifactPath = path.join(reportsDir, 'program-artifact.json'); +export const nodeResultPath = path.join(reportsDir, 'node-result.json'); +export const browserResultPath = path.join(reportsDir, 'browser-result.json'); +export const oogBoundaryPath = path.join(reportsDir, 'oog-boundary.json'); +export const reproPath = path.join(reportsDir, 'reproducibility-report.json'); + +export async function ensureReportsDir() { + await mkdir(reportsDir, { recursive: true }); +} + +export async function writeJson(targetPath, payload) { + await mkdir(path.dirname(targetPath), { recursive: true }); + await writeFile(targetPath, `${JSON.stringify(payload, null, 2)}\n`, 'utf8'); +} + +export async function readJson(targetPath) { + const text = await readFile(targetPath, 'utf8'); + return JSON.parse(text); +} + +export function createInputEnvelope() { + return { + event: { type: 'consumer-proof' }, + eventCanonical: { type: 'consumer-proof' }, + steps: [], + currentContract: { id: 'consumer-proof' }, + currentContractCanonical: { id: { value: 'consumer-proof' } }, + }; +} + +export function snapshotFromResult(result, encodeDv) { + const tape = result.tape ?? []; + if (result.ok) { + return { + stage: 'success', + resultHash: sha256Hex(Buffer.from(encodeDv(result.value))), + errorCode: null, + errorTag: null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: + tape.length > 0 + ? sha256Hex(Buffer.from(stringifyWithBigInt(tape))) + : null, + tapeLength: tape.length, + }; + } + return { + stage: 'error', + resultHash: null, + errorCode: result.error.code, + errorTag: 'tag' in result.error ? result.error.tag : null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: + tape.length > 0 ? sha256Hex(Buffer.from(stringifyWithBigInt(tape))) : null, + tapeLength: tape.length, + }; +} + +export function sha256Hex(input) { + return createHash('sha256').update(input).digest('hex'); +} + +function stringifyWithBigInt(value) { + return JSON.stringify(value, (_, item) => + typeof item === 'bigint' ? item.toString() : item, + ); +} diff --git a/e2e/consumer-proof-app/scripts/build-artifact.mjs b/e2e/consumer-proof-app/scripts/build-artifact.mjs new file mode 100644 index 0000000..223df85 --- /dev/null +++ b/e2e/consumer-proof-app/scripts/build-artifact.mjs @@ -0,0 +1,51 @@ +#!/usr/bin/env node + +import { HOST_V1_HASH } from '@blue-quickjs/abi-manifest'; +import { buildDeterministicModulePack } from '@blue-quickjs/deterministic-bundler'; +import path from 'node:path'; +import { appRoot, artifactPath, ensureReportsDir, writeJson } from './_helpers.mjs'; + +await ensureReportsDir(); + +const built = await buildDeterministicModulePack({ + absWorkingDir: appRoot, + entryPath: 'src/shared/consumer-workload.ts', + profile: 'compat-general-v1', + emitProgramArtifact: true, + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, +}); + +if (!built.compatibility.ok) { + throw new Error( + `consumer workload is incompatible: ${JSON.stringify( + built.compatibility.diagnostics, + )}`, + ); +} +if (!built.programArtifact) { + throw new Error('builder did not produce ProgramArtifact.v2'); +} + +const payload = { + generatedAt: new Date().toISOString(), + graphHash: built.modulePack.graphHash, + moduleCount: built.modulePack.modules.length, + artifact: built.programArtifact, +}; + +await writeJson(artifactPath, payload); + +console.log( + JSON.stringify( + { + artifactPath, + graphHash: payload.graphHash, + moduleCount: payload.moduleCount, + relativeEntry: path.relative(appRoot, 'src/shared/consumer-workload.ts'), + }, + null, + 2, + ), +); diff --git a/e2e/consumer-proof-app/scripts/consumer-host.mjs b/e2e/consumer-proof-app/scripts/consumer-host.mjs new file mode 100644 index 0000000..ad4e823 --- /dev/null +++ b/e2e/consumer-proof-app/scripts/consumer-host.mjs @@ -0,0 +1,32 @@ +export function createConsumerHost() { + const emitted = []; + return { + emitted, + handlers: { + document: { + get(docPath) { + switch (docPath) { + case 'consumer/version': + return { ok: '1.2.3', units: 1 }; + case 'consumer/encoded': + return { ok: '<b>deterministic</b>', units: 1 }; + case 'consumer/route': + return { ok: '/contract/:id/release/:version', units: 1 }; + default: + return { + err: { code: 'NOT_FOUND', tag: 'host/not_found' }, + units: 1, + }; + } + }, + getCanonical(docPath) { + return this.get(docPath); + }, + }, + emit(value) { + emitted.push(value); + return { ok: null, units: 1 }; + }, + }, + }; +} diff --git a/e2e/consumer-proof-app/scripts/find-oog-boundary.mjs b/e2e/consumer-proof-app/scripts/find-oog-boundary.mjs new file mode 100644 index 0000000..fed8048 --- /dev/null +++ b/e2e/consumer-proof-app/scripts/find-oog-boundary.mjs @@ -0,0 +1,170 @@ +#!/usr/bin/env node + +import { HOST_V1_MANIFEST } from '@blue-quickjs/abi-manifest'; +import { evaluate } from '@blue-quickjs/quickjs-runtime'; +import { chromium, firefox, webkit } from '@playwright/test'; +import { createServer } from 'vite'; +import path from 'node:path'; +import { + appRoot, + artifactPath, + createInputEnvelope, + oogBoundaryPath, + readJson, + writeJson, +} from './_helpers.mjs'; +import { createConsumerHost } from './consumer-host.mjs'; + +const args = parseArgs(process.argv.slice(2)); +const payload = await readJson(args.artifactPath ?? artifactPath); + +const nodeBoundary = await searchBoundary({ + low: 1n, + high: BigInt(args.maxGas), + run: async (gasLimit) => { + const host = createConsumerHost(); + const result = await evaluate({ + program: payload.artifact, + input: createInputEnvelope(), + gasLimit, + manifest: HOST_V1_MANIFEST, + handlers: host.handlers, + tape: { capacity: 32 }, + }); + return result.ok; + }, +}); + +const viteServer = await createServer({ + configFile: path.join(appRoot, 'vite.config.mts'), + clearScreen: false, +}); +await viteServer.listen(); +const browserType = resolveBrowserType(args.browser); +const browser = await browserType.launch({ headless: true }); +const context = await browser.newContext({ baseURL: args.baseUrl }); + +let browserBoundary; +try { + const page = await context.newPage(); + await page.addInitScript((artifact) => { + window.__CONSUMER_ARTIFACT__ = artifact; + }, payload.artifact); + await page.goto('/'); + await page.waitForFunction(() => typeof window.__runConsumerEvaluation === 'function'); + + browserBoundary = await searchBoundary({ + low: 1n, + high: BigInt(args.maxGas), + run: async (gasLimit) => + page.evaluate(async (value) => { + const result = await window.__runConsumerEvaluation?.(String(value)); + return result?.stage === 'success'; + }, gasLimit.toString()), + }); +} finally { + await context.close(); + await browser.close(); + await viteServer.close(); +} + +const parity = { + firstSuccessEqual: + nodeBoundary.firstSuccessGas.toString() === browserBoundary.firstSuccessGas.toString(), + lastFailureEqual: + nodeBoundary.lastFailureGas.toString() === browserBoundary.lastFailureGas.toString(), +}; + +const report = { + generatedAt: new Date().toISOString(), + browser: args.browser, + node: { + firstSuccessGas: nodeBoundary.firstSuccessGas.toString(), + lastFailureGas: nodeBoundary.lastFailureGas.toString(), + }, + browser: { + firstSuccessGas: browserBoundary.firstSuccessGas.toString(), + lastFailureGas: browserBoundary.lastFailureGas.toString(), + }, + parity, +}; + +await writeJson(oogBoundaryPath, report); +console.log(JSON.stringify({ oogBoundaryPath, parity, report }, null, 2)); + +if (!parity.firstSuccessEqual || !parity.lastFailureEqual) { + process.exitCode = 1; +} + +async function searchBoundary({ low, high, run }) { + let left = low; + let right = high; + const rightSuccess = await run(right); + if (!rightSuccess) { + throw new Error( + `max gas ${high.toString()} is still OOG; increase --max-gas to locate boundary`, + ); + } + + while (left + 1n < right) { + const mid = (left + right) / 2n; + const ok = await run(mid); + if (ok) { + right = mid; + } else { + left = mid; + } + } + return { + lastFailureGas: left, + firstSuccessGas: right, + }; +} + +function parseArgs(argv) { + let maxGas = '2000000'; + let artifact = null; + let baseUrl = 'http://127.0.0.1:4320'; + let browser = 'chromium'; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--max-gas') { + maxGas = argv[index + 1] ?? maxGas; + index += 1; + continue; + } + if (arg === '--artifact') { + artifact = argv[index + 1] ?? artifact; + index += 1; + continue; + } + if (arg === '--base-url') { + baseUrl = argv[index + 1] ?? baseUrl; + index += 1; + continue; + } + if (arg === '--browser') { + browser = argv[index + 1] ?? browser; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { maxGas, artifactPath: artifact, baseUrl, browser }; +} + +function resolveBrowserType(browserName) { + if (browserName === 'chromium') { + return chromium; + } + if (browserName === 'firefox') { + return firefox; + } + if (browserName === 'webkit') { + return webkit; + } + throw new Error(`unsupported browser: ${browserName}`); +} diff --git a/e2e/consumer-proof-app/scripts/install-from-tarballs.mjs b/e2e/consumer-proof-app/scripts/install-from-tarballs.mjs new file mode 100644 index 0000000..3fa5465 --- /dev/null +++ b/e2e/consumer-proof-app/scripts/install-from-tarballs.mjs @@ -0,0 +1,59 @@ +#!/usr/bin/env node + +import { readdir } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { spawn } from 'node:child_process'; + +const appRoot = path.resolve(import.meta.dirname, '..'); +const args = parseArgs(process.argv.slice(2)); +const tarballDir = path.resolve(appRoot, args.tarballDir); +const entries = await readdir(tarballDir); +const tarballs = entries + .filter((entry) => entry.endsWith('.tgz')) + .filter((entry) => !entry.includes('deterministic-builder')) + .map((entry) => path.join(tarballDir, entry)) + .sort(); + +if (tarballs.length === 0) { + throw new Error(`no .tgz files found in ${tarballDir}`); +} + +await run('npm', ['install', '--no-fund', '--no-audit'], appRoot); +await run( + 'npm', + ['install', '--no-save', '--no-fund', '--no-audit', ...tarballs], + appRoot, +); + +console.log(JSON.stringify({ tarballDir, installed: tarballs.length }, null, 2)); + +function parseArgs(argv) { + let tarballDir = '../../artifacts/consumer-proof/tarballs'; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--tarball-dir') { + tarballDir = argv[index + 1] ?? tarballDir; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { tarballDir }; +} + +async function run(command, args, cwd) { + await new Promise((resolve, reject) => { + const child = spawn(command, args, { cwd, stdio: 'inherit' }); + child.on('exit', (code) => { + if (code === 0) { + resolve(undefined); + return; + } + reject(new Error(`command failed (${command} ${args.join(' ')})`)); + }); + }); +} diff --git a/e2e/consumer-proof-app/scripts/reproducibility-report.mjs b/e2e/consumer-proof-app/scripts/reproducibility-report.mjs new file mode 100644 index 0000000..5604685 --- /dev/null +++ b/e2e/consumer-proof-app/scripts/reproducibility-report.mjs @@ -0,0 +1,106 @@ +#!/usr/bin/env node + +import { spawn } from 'node:child_process'; +import path from 'node:path'; +import { + appRoot, + artifactPath, + browserResultPath, + nodeResultPath, + oogBoundaryPath, + readJson, + reproPath, + sha256Hex, + writeJson, +} from './_helpers.mjs'; + +const args = parseArgs(process.argv.slice(2)); + +await run('node', ['scripts/build-artifact.mjs']); +await run('node', ['scripts/run-node.mjs']); +await run('node', ['scripts/run-browser.mjs', '--browser', args.browser]); +await run('node', ['scripts/find-oog-boundary.mjs', '--browser', args.browser]); +if (args.withNative) { + await run('node', ['scripts/run-native-diagnostic.mjs']); +} + +const artifact = await readJson(artifactPath); +const nodeResult = await readJson(nodeResultPath); +const browserResult = await readJson(browserResultPath); +const oogBoundary = await readJson(oogBoundaryPath); +const nativeDiagnostic = args.withNative + ? await readJson(path.join(appRoot, 'reports/native-diagnostic.json')) + : null; + +const nodeSnapshot = nodeResult.snapshot; +const browserSnapshot = browserResult.snapshot; +const parity = { + snapshotEqual: + JSON.stringify(nodeSnapshot) === JSON.stringify(browserSnapshot), + oogEqual: + oogBoundary.parity.firstSuccessEqual && oogBoundary.parity.lastFailureEqual, +}; + +const report = { + generatedAt: new Date().toISOString(), + browser: args.browser, + artifact: { + graphHash: artifact.graphHash, + moduleCount: artifact.moduleCount, + }, + node: nodeSnapshot, + browser: browserSnapshot, + oogBoundary, + nativeDiagnostic, + parity, + signature: { + algorithm: 'sha256', + digest: sha256Hex(JSON.stringify({ artifact, nodeSnapshot, browserSnapshot, oogBoundary })), + }, +}; + +await writeJson(reproPath, report); +await writeJson(`${reproPath}.sha256`, { + algorithm: 'sha256', + digest: sha256Hex(JSON.stringify(report)), +}); + +console.log(JSON.stringify({ reproPath, parity }, null, 2)); +if (!parity.snapshotEqual || !parity.oogEqual) { + process.exitCode = 1; +} + +function parseArgs(argv) { + let withNative = false; + let browser = 'chromium'; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--with-native') { + withNative = true; + continue; + } + if (arg === '--browser') { + browser = argv[index + 1] ?? browser; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { withNative, browser }; +} + +async function run(command, args) { + await new Promise((resolve, reject) => { + const child = spawn(command, args, { cwd: appRoot, stdio: 'inherit' }); + child.on('exit', (code) => { + if (code === 0) { + resolve(undefined); + return; + } + reject(new Error(`command failed (${command} ${args.join(' ')})`)); + }); + }); +} diff --git a/e2e/consumer-proof-app/scripts/run-browser.mjs b/e2e/consumer-proof-app/scripts/run-browser.mjs new file mode 100644 index 0000000..3f911ac --- /dev/null +++ b/e2e/consumer-proof-app/scripts/run-browser.mjs @@ -0,0 +1,119 @@ +#!/usr/bin/env node + +import { chromium, firefox, webkit } from '@playwright/test'; +import { createServer } from 'vite'; +import path from 'node:path'; +import { + appRoot, + artifactPath, + browserResultPath, + readJson, + writeJson, +} from './_helpers.mjs'; + +const args = parseArgs(process.argv.slice(2)); +const payload = await readJson(args.artifactPath ?? artifactPath); + +const viteServer = await createServer({ + configFile: path.join(appRoot, 'vite.config.mts'), + clearScreen: false, +}); +await viteServer.listen(); + +const browserType = resolveBrowserType(args.browser); +const browser = await browserType.launch({ headless: true }); +const context = await browser.newContext({ baseURL: args.baseUrl }); +try { + const page = await context.newPage(); + page.on('console', (message) => { + if (message.type() === 'error') { + console.error(`[browser-console] ${message.text()}`); + } + }); + page.on('pageerror', (error) => { + console.error(`[browser-pageerror] ${error.message}`); + }); + await page.addInitScript( + ({ artifact }) => { + window.__CONSUMER_ARTIFACT__ = artifact; + }, + { artifact: payload.artifact }, + ); + await page.goto('/'); + await page.waitForFunction( + () => typeof window.__runConsumerEvaluation === 'function', + undefined, + { + timeout: 120000, + }, + ); + const snapshot = await page.evaluate((gasLimit) => { + if (!window.__runConsumerEvaluation) { + throw new Error('window.__runConsumerEvaluation is not available'); + } + return window.__runConsumerEvaluation(gasLimit); + }, args.gasLimit); + + await page.waitForFunction(() => Boolean(window.__CONSUMER_RESULT__), undefined, { + timeout: 120000, + }); + await writeJson(browserResultPath, { + generatedAt: new Date().toISOString(), + browser: args.browser, + gasLimit: args.gasLimit, + snapshot, + }); + console.log(JSON.stringify({ browserResultPath, snapshot }, null, 2)); +} finally { + await context.close(); + await browser.close(); + await viteServer.close(); +} + +function parseArgs(argv) { + let gasLimit = '1000000'; + let artifact = null; + let baseUrl = 'http://127.0.0.1:4320'; + let browser = 'chromium'; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--gas-limit') { + gasLimit = argv[index + 1] ?? gasLimit; + index += 1; + continue; + } + if (arg === '--artifact') { + artifact = argv[index + 1] ?? artifact; + index += 1; + continue; + } + if (arg === '--base-url') { + baseUrl = argv[index + 1] ?? baseUrl; + index += 1; + continue; + } + if (arg === '--browser') { + browser = argv[index + 1] ?? browser; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { gasLimit, artifactPath: artifact, baseUrl, browser }; +} + +function resolveBrowserType(browserName) { + if (browserName === 'chromium') { + return chromium; + } + if (browserName === 'firefox') { + return firefox; + } + if (browserName === 'webkit') { + return webkit; + } + throw new Error(`unsupported browser: ${browserName}`); +} diff --git a/e2e/consumer-proof-app/scripts/run-native-diagnostic.mjs b/e2e/consumer-proof-app/scripts/run-native-diagnostic.mjs new file mode 100644 index 0000000..eed6acb --- /dev/null +++ b/e2e/consumer-proof-app/scripts/run-native-diagnostic.mjs @@ -0,0 +1,89 @@ +#!/usr/bin/env node + +import { spawn } from 'node:child_process'; +import path from 'node:path'; +import process from 'node:process'; +import { appRoot, reportsDir, writeJson } from './_helpers.mjs'; + +const args = parseArgs(process.argv.slice(2)); +const repoRoot = path.resolve(appRoot, '..', '..'); +const binaryPath = path.resolve( + repoRoot, + 'tools/quickjs-native-harness/dist/quickjs-native-harness', +); + +const report = { + generatedAt: new Date().toISOString(), + diagnosticOnly: true, + command: binaryPath, + status: 'skipped', + output: null, + error: null, +}; + +try { + await run('pnpm', ['nx', 'build', 'quickjs-native-harness'], repoRoot); + const runResult = await run( + binaryPath, + [ + '--eval', + "(() => ({ runtime: 'native-diagnostic', value: 40 + 2 }))()", + '--execution-profile', + 'compat-general-v1', + '--gas-limit', + '200000', + '--report-gas', + ], + repoRoot, + ); + report.status = 'ok'; + report.output = runResult.stdout.trim(); + report.error = runResult.stderr.trim() || null; +} catch (error) { + report.status = 'failed'; + report.error = error instanceof Error ? error.message : String(error); +} + +const outputPath = path.join(reportsDir, args.outputFile); +await writeJson(outputPath, report); + +console.log(JSON.stringify({ outputPath, status: report.status }, null, 2)); + +function parseArgs(argv) { + let outputFile = 'native-diagnostic.json'; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--output-file') { + outputFile = argv[index + 1] ?? outputFile; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { outputFile }; +} + +async function run(command, args, cwd) { + return new Promise((resolve, reject) => { + const child = spawn(command, args, { cwd, stdio: ['ignore', 'pipe', 'pipe'] }); + let stdout = ''; + let stderr = ''; + child.stdout.on('data', (chunk) => { + stdout += chunk.toString(); + }); + child.stderr.on('data', (chunk) => { + stderr += chunk.toString(); + }); + child.on('exit', (code) => { + if (code === 0) { + resolve({ stdout, stderr }); + return; + } + reject( + new Error( + `command failed (${command} ${args.join(' ')}): ${code}\n${stderr}`, + ), + ); + }); + }); +} diff --git a/e2e/consumer-proof-app/scripts/run-node.mjs b/e2e/consumer-proof-app/scripts/run-node.mjs new file mode 100644 index 0000000..525240e --- /dev/null +++ b/e2e/consumer-proof-app/scripts/run-node.mjs @@ -0,0 +1,58 @@ +#!/usr/bin/env node + +import { HOST_V1_MANIFEST } from '@blue-quickjs/abi-manifest'; +import { encodeDv } from '@blue-quickjs/dv'; +import { evaluate } from '@blue-quickjs/quickjs-runtime'; +import { + artifactPath, + createInputEnvelope, + nodeResultPath, + readJson, + snapshotFromResult, + writeJson, +} from './_helpers.mjs'; +import { createConsumerHost } from './consumer-host.mjs'; + +const args = parseArgs(process.argv.slice(2)); +const payload = await readJson(args.artifactPath ?? artifactPath); + +const host = createConsumerHost(); +const result = await evaluate({ + program: payload.artifact, + input: createInputEnvelope(), + gasLimit: BigInt(args.gasLimit), + manifest: HOST_V1_MANIFEST, + handlers: host.handlers, + tape: { capacity: 32 }, +}); + +const snapshot = snapshotFromResult(result, encodeDv); +const output = { + generatedAt: new Date().toISOString(), + gasLimit: args.gasLimit, + snapshot, + emitted: host.emitted, +}; + +await writeJson(nodeResultPath, output); +console.log(JSON.stringify({ nodeResultPath, snapshot }, null, 2)); + +function parseArgs(argv) { + let gasLimit = '1000000'; + let targetArtifactPath = null; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--gas-limit') { + gasLimit = argv[index + 1] ?? gasLimit; + index += 1; + continue; + } + if (arg === '--artifact') { + targetArtifactPath = argv[index + 1] ?? targetArtifactPath; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { gasLimit, artifactPath: targetArtifactPath }; +} diff --git a/e2e/consumer-proof-app/src/browser/main.ts b/e2e/consumer-proof-app/src/browser/main.ts new file mode 100644 index 0000000..576ddd8 --- /dev/null +++ b/e2e/consumer-proof-app/src/browser/main.ts @@ -0,0 +1,112 @@ +import { HOST_V1_MANIFEST } from '@blue-quickjs/abi-manifest'; +import { encodeDv } from '@blue-quickjs/dv'; +import { evaluate } from '@blue-quickjs/quickjs-runtime'; +import { createConsumerHost } from '../shared/host.js'; + +declare global { + interface Window { + __CONSUMER_ARTIFACT__?: unknown; + __CONSUMER_GAS_LIMIT__?: string; + __CONSUMER_RESULT__?: unknown; + __runConsumerEvaluation?: (gasLimit: string) => Promise; + } +} + +const app = document.querySelector('[data-app]'); +if (app) { + app.innerHTML = '

Consumer Proof Browser Runner

Idle
'; +} + +window.__runConsumerEvaluation = async (gasLimit: string) => { + if (!window.__CONSUMER_ARTIFACT__) { + throw new Error('missing __CONSUMER_ARTIFACT__ payload'); + } + const host = createConsumerHost(); + const result = await evaluate({ + program: window.__CONSUMER_ARTIFACT__ as never, + input: { + event: { type: 'consumer-proof' }, + eventCanonical: { type: 'consumer-proof' }, + steps: [], + currentContract: { id: 'consumer-proof' }, + currentContractCanonical: { id: { value: 'consumer-proof' } }, + }, + gasLimit: BigInt(gasLimit), + manifest: HOST_V1_MANIFEST, + handlers: host.handlers, + tape: { capacity: 32 }, + }); + + const tape = result.tape ?? []; + const snapshot = result.ok + ? { + stage: 'success', + resultHash: await sha256Hex(encodeDv(result.value)), + errorCode: null, + errorTag: null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: + tape.length > 0 + ? await sha256Hex( + new TextEncoder().encode(stringifyWithBigInt(tape)), + ) + : null, + tapeLength: tape.length, + } + : { + stage: 'error', + resultHash: null, + errorCode: result.error.code, + errorTag: 'tag' in result.error ? result.error.tag : null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: + tape.length > 0 + ? await sha256Hex( + new TextEncoder().encode(stringifyWithBigInt(tape)), + ) + : null, + tapeLength: tape.length, + }; + window.__CONSUMER_RESULT__ = snapshot; + return snapshot; +}; + +const gasLimit = window.__CONSUMER_GAS_LIMIT__; +if (window.__CONSUMER_ARTIFACT__ && gasLimit) { + void window.__runConsumerEvaluation(gasLimit) + .then((snapshot) => { + const out = document.querySelector('[data-output]'); + if (out) { + out.textContent = JSON.stringify(snapshot, null, 2); + } + }) + .catch((error) => { + const out = document.querySelector('[data-output]'); + if (out) { + out.textContent = + error instanceof Error ? error.stack ?? error.message : String(error); + } + }); +} + +async function sha256Hex(bytes: Uint8Array): Promise { + const digest = await crypto.subtle.digest('SHA-256', toArrayBuffer(bytes)); + return [...new Uint8Array(digest)] + .map((chunk) => chunk.toString(16).padStart(2, '0')) + .join(''); +} + +function toArrayBuffer(data: Uint8Array): ArrayBuffer { + if (data.byteOffset === 0 && data.byteLength === data.buffer.byteLength) { + return data.buffer as ArrayBuffer; + } + return data.slice().buffer; +} + +function stringifyWithBigInt(value: unknown): string { + return JSON.stringify(value, (_key, item) => + typeof item === 'bigint' ? item.toString() : item, + ); +} diff --git a/e2e/consumer-proof-app/src/shared/consumer-workload.ts b/e2e/consumer-proof-app/src/shared/consumer-workload.ts new file mode 100644 index 0000000..eafefc0 --- /dev/null +++ b/e2e/consumer-proof-app/src/shared/consumer-workload.ts @@ -0,0 +1,26 @@ +import he from 'he'; +import { match } from 'path-to-regexp'; +import { satisfies } from 'semver'; + +const version = Host.v1.document.get('consumer/version'); +const encoded = Host.v1.document.get('consumer/encoded'); +const routePattern = Host.v1.document.get('consumer/route'); + +const releaseChecks = ['>=1.2.0 <2.0.0', '^1.2.0'].map((range) => + satisfies(version, range), +); +const routeMatch = match(routePattern)('/contract/42/release/1.2.3'); + +const summary = { + version, + releaseChecks, + decoded: he.decode(encoded), + routeParams: routeMatch?.params ?? null, +}; + +Host.v1.emit({ + type: 'consumer-proof-summary', + releaseOk: releaseChecks.every(Boolean), +}); + +export default summary; diff --git a/e2e/consumer-proof-app/src/shared/host.ts b/e2e/consumer-proof-app/src/shared/host.ts new file mode 100644 index 0000000..b6d1abb --- /dev/null +++ b/e2e/consumer-proof-app/src/shared/host.ts @@ -0,0 +1,32 @@ +export function createConsumerHost() { + const emitted = []; + return { + emitted, + handlers: { + document: { + get(path) { + switch (path) { + case 'consumer/version': + return { ok: '1.2.3', units: 1 }; + case 'consumer/encoded': + return { ok: '<b>deterministic</b>', units: 1 }; + case 'consumer/route': + return { ok: '/contract/:id/release/:version', units: 1 }; + default: + return { + err: { code: 'NOT_FOUND', tag: 'host/not_found' }, + units: 1, + }; + } + }, + getCanonical(path) { + return this.get(path); + }, + }, + emit(value) { + emitted.push(value); + return { ok: null, units: 1 }; + }, + }, + }; +} diff --git a/e2e/consumer-proof-app/vite.config.mts b/e2e/consumer-proof-app/vite.config.mts new file mode 100644 index 0000000..0ba21f4 --- /dev/null +++ b/e2e/consumer-proof-app/vite.config.mts @@ -0,0 +1,20 @@ +import { defineConfig } from 'vite'; + +export default defineConfig({ + root: import.meta.dirname, + server: { + host: '127.0.0.1', + port: 4320, + strictPort: true, + }, + preview: { + host: '127.0.0.1', + port: 4320, + strictPort: true, + }, + optimizeDeps: { + exclude: [ + '@blue-quickjs/quickjs-wasm', + ], + }, +}); diff --git a/examples/01-basic-script/program.js b/examples/01-basic-script/program.js new file mode 100644 index 0000000..c0df6c9 --- /dev/null +++ b/examples/01-basic-script/program.js @@ -0,0 +1 @@ +(() => 1)(); diff --git a/examples/02-module-pack/entry.js b/examples/02-module-pack/entry.js new file mode 100644 index 0000000..e747934 --- /dev/null +++ b/examples/02-module-pack/entry.js @@ -0,0 +1,3 @@ +import { base } from './values.js'; + +export default base + 1; diff --git a/examples/02-module-pack/values.js b/examples/02-module-pack/values.js new file mode 100644 index 0000000..1a69880 --- /dev/null +++ b/examples/02-module-pack/values.js @@ -0,0 +1 @@ +export const base = 6; diff --git a/examples/03-library-reuse/binary-base64-entry.ts b/examples/03-library-reuse/binary-base64-entry.ts new file mode 100644 index 0000000..88caf05 --- /dev/null +++ b/examples/03-library-reuse/binary-base64-entry.ts @@ -0,0 +1,14 @@ +import { fromByteArray, toByteArray } from 'base64-js'; + +const payload = Uint8Array.from([1, 2, 3, 4, 5, 6, 7, 8]); +const encoded = fromByteArray(payload); +const decoded = toByteArray(encoded); +const sum = decoded.reduce((acc, value) => acc + value, 0); + +export default { + length: decoded.length, + sum, + first: decoded[0], + last: decoded[decoded.length - 1], + reencoded: encoded, +}; diff --git a/examples/03-library-reuse/chess-entry.ts b/examples/03-library-reuse/chess-entry.ts new file mode 100644 index 0000000..1c8596e --- /dev/null +++ b/examples/03-library-reuse/chess-entry.ts @@ -0,0 +1,7 @@ +import { Chess } from 'chess.js'; + +const game = new Chess(); +game.move('e4'); +game.move('e5'); + +export default game.move('e2e6') !== null; diff --git a/examples/04-promises-async/program.js b/examples/04-promises-async/program.js new file mode 100644 index 0000000..23ff68c --- /dev/null +++ b/examples/04-promises-async/program.js @@ -0,0 +1 @@ +(() => Promise.resolve(40).then((value) => value + 2))(); diff --git a/examples/05-promises-library-host/entry.js b/examples/05-promises-library-host/entry.js new file mode 100644 index 0000000..38d340b --- /dev/null +++ b/examples/05-promises-library-host/entry.js @@ -0,0 +1,6 @@ +import { plusOne } from './lib.js'; + +export default Promise.resolve(plusOne(41)).then((value) => { + Host.v1.emit({ phase: 'async-lib', value }); + return value; +}); diff --git a/examples/05-promises-library-host/lib.js b/examples/05-promises-library-host/lib.js new file mode 100644 index 0000000..c6d621c --- /dev/null +++ b/examples/05-promises-library-host/lib.js @@ -0,0 +1 @@ +export const plusOne = (value) => value + 1; diff --git a/examples/06-binary-host-v2/program.js b/examples/06-binary-host-v2/program.js new file mode 100644 index 0000000..1382340 --- /dev/null +++ b/examples/06-binary-host-v2/program.js @@ -0,0 +1,14 @@ +(() => { + const payload = Host.v2.document.get('bytes/payload'); + Host.v2.emit(payload); + let sum = 0; + for (const byte of payload) { + sum += byte; + } + return { + length: payload.byteLength, + first: payload[0], + last: payload[payload.byteLength - 1], + sum, + }; +})(); diff --git a/examples/07-console-shim/program.js b/examples/07-console-shim/program.js new file mode 100644 index 0000000..b196e20 --- /dev/null +++ b/examples/07-console-shim/program.js @@ -0,0 +1,4 @@ +(() => { + console.info('deterministic', 7); + return { ok: true }; +})(); diff --git a/examples/08-stable-sort/program.js b/examples/08-stable-sort/program.js new file mode 100644 index 0000000..f3d3ade --- /dev/null +++ b/examples/08-stable-sort/program.js @@ -0,0 +1,10 @@ +(() => { + const records = [ + { id: 'a', group: 1 }, + { id: 'b', group: 1 }, + { id: 'c', group: 2 }, + { id: 'd', group: 1 }, + ]; + records.sort((left, right) => left.group - right.group); + return records.map((record) => record.id); +})(); diff --git a/examples/09-kitchen-sink/entry.js b/examples/09-kitchen-sink/entry.js new file mode 100644 index 0000000..3e70a36 --- /dev/null +++ b/examples/09-kitchen-sink/entry.js @@ -0,0 +1,9 @@ +import { summarize } from './workflow.js'; + +export default (async () => { + const doc = document('path/to/doc'); + const canonical = document.canonical('path/to/doc'); + const result = await summarize(doc.path, canonical.canonical); + Host.v1.emit({ kind: 'kitchen', result }); + return result; +})(); diff --git a/examples/09-kitchen-sink/workflow.js b/examples/09-kitchen-sink/workflow.js new file mode 100644 index 0000000..87d0a4b --- /dev/null +++ b/examples/09-kitchen-sink/workflow.js @@ -0,0 +1,17 @@ +export async function summarize(path, canonical) { + const queue = []; + queueMicrotask(() => queue.push('micro')); + await Promise.resolve(); + const records = [ + { id: 'b', rank: 2 }, + { id: 'a', rank: 1 }, + { id: 'c', rank: 2 }, + ]; + records.sort((left, right) => left.rank - right.rank); + return { + path, + canonical, + order: records.map((record) => record.id).join(','), + queue: queue.join(','), + }; +} diff --git a/examples/10-max-gas-policy/program.js b/examples/10-max-gas-policy/program.js new file mode 100644 index 0000000..272e2c8 --- /dev/null +++ b/examples/10-max-gas-policy/program.js @@ -0,0 +1,7 @@ +(() => { + let sum = 0; + for (let i = 0; i < 10000; i += 1) { + sum += i; + } + return sum; +})(); diff --git a/examples/README.md b/examples/README.md new file mode 100644 index 0000000..bfa18cf --- /dev/null +++ b/examples/README.md @@ -0,0 +1,82 @@ +# Deterministic examples corpus + +This corpus maps product-facing deterministic examples to runnable fixture +coverage already exercised by `smoke-node`, `smoke-web`, and the consensus +reproducibility report pipeline. + +## Run once (build + parity evidence) + +```bash +source tools/emsdk/emsdk_env.sh +pnpm nx test smoke-node +pnpm nx run smoke-web:e2e +node tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs \ + --out-dir artifacts/reproducibility-consensus +``` + +Native diagnostic parity evidence (optional, non-consensus): + +```bash +pnpm nx build quickjs-native-harness +pnpm nx test quickjs-native-harness +node tools/quickjs-native-harness/scripts/archive-reproducibility-report.mjs +``` + +## Example matrix + +Canonical source snippets for each category live under `examples/0*/`. +Exact parity values come from the consensus report (`wasm-node` vs +`wasm-browser`). + +Consensus metadata snapshot (from latest local report run): + +- `engineBuildHash`: `f91091cb7feb788df340305a877a9cadb0c6f4d13aea8a7da4040b6367d178ea` +- `gasVersion`: `8` +- `executionProfile`: fixture-defined per example + +| # | Scenario | Profile | Source file(s) | Fixture key(s) | Expected result / gas evidence | +|---|---|---|---|---|---| +| 1 | Basic deterministic script | `baseline-v1` | `examples/01-basic-script/program.js` | `gas-sample-fixtures:return-1` | `resultHash=4bf5…459a`, `gasUsed=74`, `gasRemaining=999926` | +| 2 | Standard ESM module-pack | `baseline-v1` | `examples/02-module-pack/entry.js`, `examples/02-module-pack/values.js` | `module-pack-fixtures:module-pack-default-export` | `ok=true`, `valueHash=ca35…e879`, `gasUsed=204`, `gasRemaining=49796` | +| 3 | Real npm library reuse (`chess.js` + `base64-js`) | `compat-general-v1`, `compat-binary-v1` | `examples/03-library-reuse/chess-entry.ts`, `examples/03-library-reuse/binary-base64-entry.ts` | `chess-library:chess-e2e6`, `binary-library:base64-js-roundtrip` | chess: `value=false`, `gasUsed=2070610`; base64: `value.sum=36`, `gasUsed=3542` | +| 4 | Promises / async / microtasks | `compat-general-v1` | `examples/04-promises-async/program.js` | `determinism-fixtures:async-promise-chain` | `resultHash=7f83…5c53`, `gasUsed=128`, `gasRemaining=49872` | +| 5 | Promises + imported lib + host call | `compat-general-v1` | `examples/05-promises-library-host/entry.js`, `examples/05-promises-library-host/lib.js` | `module-pack-fixtures:module-pack-async-import-host-call` | `valueHash=7f83…5c53`, `tapeLength=1`, `gasUsed=345`, `gasRemaining=49655` | +| 6 | Binary / typed arrays / Host.v2 DV2 | `compat-binary-v1` | `examples/06-binary-host-v2/program.js` | `determinism-fixtures:compat-binary-host-v2-bytes-roundtrip` | `resultHash=a538…b2f8`, `tapeLength=2`, `gasUsed=253`, `gasRemaining=49747` | +| 7 | Console shim determinism | `compat-general-v1` | `examples/07-console-shim/program.js` | `determinism-fixtures:compat-console-shim` | `resultHash=20a9…cd02`, `tapeLength=1`, `gasUsed=139`, `gasRemaining=49861` | +| 8 | Stable sort determinism | `compat-general-v1` | `examples/08-stable-sort/program.js` | `determinism-fixtures:compat-stable-sort` | `resultHash=950f…3c04`, `gasUsed=1020`, `gasRemaining=48980` | +| 9 | Kitchen sink app | `compat-general-v1` | `examples/09-kitchen-sink/entry.js`, `examples/09-kitchen-sink/workflow.js` | `module-pack-fixtures:module-pack-kitchen-sink` | `valueHash=81c4…ee75`, `tapeLength=3`, `gasUsed=1444`, `gasRemaining=48556` | +| 10 | Max-gas / DoS boundary policy | `baseline-v1` | `examples/10-max-gas-policy/program.js` | `gas-boundary-fixtures:loop-10k` | success at `N=170099`, fail at `N-1=170098`, both `gasRemaining=0`, fail code `OOG` | + +### Per-example build/run validation commands + +All examples are validated by fixture-driven parity tests: + +```bash +source tools/emsdk/emsdk_env.sh +pnpm nx test smoke-node +pnpm nx run smoke-web:e2e +node tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs \ + --out-dir artifacts/reproducibility-consensus +``` + +For native diagnostic comparison (non-consensus): + +```bash +pnpm nx build quickjs-native-harness +pnpm nx test quickjs-native-harness +node tools/quickjs-native-harness/scripts/archive-reproducibility-report.mjs +``` + +## Reading exact gas / boundary values + +- Consensus executor parity report: + - `node tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs` +- Report includes: + - `metadata.engineBuildHash` + - `metadata.gasVersion` + - per-fixture `gasUsed`, `gasRemaining` + - per-boundary fixture `firstSuccessGas` and `lastFailureGas` + - mismatch counters for wasm-node vs wasm-browser. + +For release, treat wasm-node/wasm-browser report as normative consensus +evidence and native reports as diagnostic unless explicitly promoted by policy. diff --git a/libs/abi-manifest/src/index.ts b/libs/abi-manifest/src/index.ts index 35b9f04..252534c 100644 --- a/libs/abi-manifest/src/index.ts +++ b/libs/abi-manifest/src/index.ts @@ -1,2 +1,3 @@ export * from './lib/abi-manifest.js'; export * from './lib/host-v1-manifest.js'; +export * from './lib/host-v2-manifest.js'; diff --git a/libs/abi-manifest/src/lib/abi-manifest.spec.ts b/libs/abi-manifest/src/lib/abi-manifest.spec.ts index 480a055..6e37d5a 100644 --- a/libs/abi-manifest/src/lib/abi-manifest.spec.ts +++ b/libs/abi-manifest/src/lib/abi-manifest.spec.ts @@ -14,6 +14,12 @@ import { HOST_V1_HASH, HOST_V1_MANIFEST, } from './host-v1-manifest.js'; +import { + HOST_V2_BYTES, + HOST_V2_BYTES_HEX, + HOST_V2_HASH, + HOST_V2_MANIFEST, +} from './host-v2-manifest.js'; describe('abi-manifest', () => { it('produces canonical bytes and hash for the Host.v1 manifest', () => { @@ -24,6 +30,14 @@ describe('abi-manifest', () => { expect(hash).toEqual(HOST_V1_HASH); }); + it('produces canonical bytes and hash for the Host.v2 manifest', () => { + const { bytes, hash, manifest } = hashAbiManifest(HOST_V2_MANIFEST); + expect(manifest).toEqual(validateAbiManifest(HOST_V2_MANIFEST)); + expect(new Uint8Array(bytes)).toEqual(HOST_V2_BYTES); + expect(bytesToHex(bytes)).toEqual(HOST_V2_BYTES_HEX); + expect(hash).toEqual(HOST_V2_HASH); + }); + it('hashes manifests deterministically regardless of key insertion order', () => { const reordered = { functions: HOST_V1_MANIFEST.functions.map((fn) => ({ diff --git a/libs/abi-manifest/src/lib/host-v2-manifest.ts b/libs/abi-manifest/src/lib/host-v2-manifest.ts new file mode 100644 index 0000000..69c60a0 --- /dev/null +++ b/libs/abi-manifest/src/lib/host-v2-manifest.ts @@ -0,0 +1,16 @@ +import { bytesToHex } from '@noble/hashes/utils'; +import type { AbiManifest } from './abi-manifest.js'; +import { hashAbiManifest } from './abi-manifest.js'; +import { HOST_V1_MANIFEST } from './host-v1-manifest.js'; + +export const HOST_V2_MANIFEST: AbiManifest = { + ...HOST_V1_MANIFEST, + abi_id: 'Host.v2', + abi_version: 2, +}; + +const HOST_V2_CANONICAL = hashAbiManifest(HOST_V2_MANIFEST); + +export const HOST_V2_BYTES = HOST_V2_CANONICAL.bytes; +export const HOST_V2_HASH = HOST_V2_CANONICAL.hash; +export const HOST_V2_BYTES_HEX = bytesToHex(HOST_V2_BYTES); diff --git a/libs/deterministic-builder/README.md b/libs/deterministic-builder/README.md new file mode 100644 index 0000000..c29037e --- /dev/null +++ b/libs/deterministic-builder/README.md @@ -0,0 +1,15 @@ +# @blue-quickjs/deterministic-builder + +Facade package for deterministic builder APIs. + +This package re-exports the builder functionality currently implemented in +`@blue-quickjs/deterministic-bundler`: + +- `buildDeterministicModulePack(...)` +- `bundleDeterministicProgram(...)` +- `scanCompatibility(...)` + +Build/test: + +- `pnpm nx build deterministic-builder` +- `pnpm nx test deterministic-builder` diff --git a/libs/deterministic-builder/eslint.config.mjs b/libs/deterministic-builder/eslint.config.mjs new file mode 100644 index 0000000..0a23ec0 --- /dev/null +++ b/libs/deterministic-builder/eslint.config.mjs @@ -0,0 +1,25 @@ +import baseConfig from '../../eslint.config.mjs'; + +export default [ + ...baseConfig, + { + files: ['**/*.json'], + rules: { + '@nx/dependency-checks': [ + 'error', + { + ignoredFiles: [ + '{projectRoot}/eslint.config.{js,cjs,mjs,ts,cts,mts}', + '{projectRoot}/vite.config.{js,ts,mjs,mts}', + ], + }, + ], + }, + languageOptions: { + parser: await import('jsonc-eslint-parser'), + }, + }, + { + ignores: ['**/out-tsc'], + }, +]; diff --git a/libs/deterministic-builder/package.json b/libs/deterministic-builder/package.json new file mode 100644 index 0000000..ab32939 --- /dev/null +++ b/libs/deterministic-builder/package.json @@ -0,0 +1,36 @@ +{ + "name": "@blue-quickjs/deterministic-builder", + "version": "0.4.1", + "type": "module", + "main": "./dist/index.js", + "module": "./dist/index.js", + "types": "./dist/index.d.ts", + "exports": { + "./package.json": "./package.json", + ".": { + "@blue-quickjs/source": "./src/index.ts", + "types": "./dist/index.d.ts", + "import": "./dist/index.js", + "default": "./dist/index.js" + } + }, + "files": [ + "dist", + "!**/*.tsbuildinfo" + ], + "nx": { + "name": "deterministic-builder" + }, + "dependencies": { + "@blue-quickjs/deterministic-bundler": "workspace:*", + "tslib": "^2.3.0" + }, + "license": "MIT", + "publishConfig": { + "access": "public" + }, + "repository": { + "type": "git", + "url": "git+https://github.com/bluecontract/blue-quickjs.git" + } +} diff --git a/libs/deterministic-builder/src/index.ts b/libs/deterministic-builder/src/index.ts new file mode 100644 index 0000000..0053b9a --- /dev/null +++ b/libs/deterministic-builder/src/index.ts @@ -0,0 +1,18 @@ +export { + buildDeterministicModulePack, + bundleDeterministicProgram, + scanCompatibility, + DeterministicBundlerError as DeterministicBuilderError, + type BuildDeterministicModulePackOptions, + type BuildDeterministicModulePackResult, + type BundleDeterministicProgramOptions, + type BundleDeterministicProgramResult, + type CompatibilityDiagnostic, + type CompatibilityReportV1, + type CompatibilityScanResult, + type DeterministicExecutionProfile, + type ModulePackModule, + type ModulePackOriginMeta, + type ModulePackV1, + type ProgramArtifactV2, +} from '@blue-quickjs/deterministic-bundler'; diff --git a/libs/deterministic-builder/src/lib/deterministic-builder.spec.ts b/libs/deterministic-builder/src/lib/deterministic-builder.spec.ts new file mode 100644 index 0000000..bd00ace --- /dev/null +++ b/libs/deterministic-builder/src/lib/deterministic-builder.spec.ts @@ -0,0 +1,23 @@ +import fs from 'node:fs'; +import os from 'node:os'; +import path from 'node:path'; +import { buildDeterministicModulePack } from '../index.js'; + +describe('deterministic-builder facade', () => { + it('builds a module pack via deterministic-bundler implementation', async () => { + const fixtureDir = fs.mkdtempSync( + path.join(os.tmpdir(), 'det-builder-facade-fixture-'), + ); + const entryPath = path.join(fixtureDir, 'entry.ts'); + fs.writeFileSync(entryPath, 'export default 7;', 'utf8'); + + const built = await buildDeterministicModulePack({ + absWorkingDir: fixtureDir, + entryPath: 'entry.ts', + }); + + expect(built.modulePack.version).toBe(1); + expect(built.modulePack.graphHash).toMatch(/^[0-9a-f]{64}$/); + expect(built.compatibility.ok).toBe(true); + }); +}); diff --git a/libs/deterministic-builder/tsconfig.json b/libs/deterministic-builder/tsconfig.json new file mode 100644 index 0000000..62ebbd9 --- /dev/null +++ b/libs/deterministic-builder/tsconfig.json @@ -0,0 +1,13 @@ +{ + "extends": "../../tsconfig.base.json", + "files": [], + "include": [], + "references": [ + { + "path": "./tsconfig.lib.json" + }, + { + "path": "./tsconfig.spec.json" + } + ] +} diff --git a/libs/deterministic-builder/tsconfig.lib.json b/libs/deterministic-builder/tsconfig.lib.json new file mode 100644 index 0000000..30128ee --- /dev/null +++ b/libs/deterministic-builder/tsconfig.lib.json @@ -0,0 +1,32 @@ +{ + "extends": "../../tsconfig.base.json", + "compilerOptions": { + "baseUrl": ".", + "rootDir": "src", + "outDir": "dist", + "tsBuildInfoFile": "dist/tsconfig.lib.tsbuildinfo", + "emitDeclarationOnly": false, + "forceConsistentCasingInFileNames": true, + "types": ["node"] + }, + "include": ["src/**/*.ts"], + "references": [ + { + "path": "../deterministic-bundler/tsconfig.lib.json" + } + ], + "exclude": [ + "vite.config.ts", + "vite.config.mts", + "vitest.config.ts", + "vitest.config.mts", + "src/**/*.test.ts", + "src/**/*.spec.ts", + "src/**/*.test.tsx", + "src/**/*.spec.tsx", + "src/**/*.test.js", + "src/**/*.spec.js", + "src/**/*.test.jsx", + "src/**/*.spec.jsx" + ] +} diff --git a/libs/deterministic-builder/tsconfig.spec.json b/libs/deterministic-builder/tsconfig.spec.json new file mode 100644 index 0000000..f68d9d3 --- /dev/null +++ b/libs/deterministic-builder/tsconfig.spec.json @@ -0,0 +1,34 @@ +{ + "extends": "../../tsconfig.base.json", + "compilerOptions": { + "outDir": "./out-tsc/vitest", + "types": [ + "vitest/globals", + "vitest/importMeta", + "vite/client", + "node", + "vitest" + ], + "forceConsistentCasingInFileNames": true + }, + "include": [ + "vite.config.ts", + "vite.config.mts", + "vitest.config.ts", + "vitest.config.mts", + "src/**/*.test.ts", + "src/**/*.spec.ts", + "src/**/*.test.tsx", + "src/**/*.spec.tsx", + "src/**/*.test.js", + "src/**/*.spec.js", + "src/**/*.test.jsx", + "src/**/*.spec.jsx", + "src/**/*.d.ts" + ], + "references": [ + { + "path": "./tsconfig.lib.json" + } + ] +} diff --git a/libs/deterministic-builder/vite.config.ts b/libs/deterministic-builder/vite.config.ts new file mode 100644 index 0000000..a32b334 --- /dev/null +++ b/libs/deterministic-builder/vite.config.ts @@ -0,0 +1,20 @@ +/// +import { defineConfig } from 'vite'; + +export default defineConfig(() => ({ + root: import.meta.dirname, + cacheDir: '../../node_modules/.vite/libs/deterministic-builder', + plugins: [], + test: { + name: 'deterministic-builder', + watch: false, + globals: true, + environment: 'node', + include: ['{src,tests}/**/*.{test,spec}.{js,mjs,cjs,ts,mts,cts,jsx,tsx}'], + reporters: ['default'], + coverage: { + reportsDirectory: './test-output/vitest/coverage', + provider: 'v8' as const, + }, + }, +})); diff --git a/libs/deterministic-bundler/README.md b/libs/deterministic-bundler/README.md new file mode 100644 index 0000000..68fc4a9 --- /dev/null +++ b/libs/deterministic-bundler/README.md @@ -0,0 +1,14 @@ +# @blue-quickjs/deterministic-bundler + +Deterministic build tooling for `blue-quickjs` artifacts. + +- `bundleDeterministicProgram(...)` flattens static module graphs into one + script string for transitional script-mode execution. +- `buildDeterministicModulePack(...)` emits canonical `ModulePack.v1` output, + compatibility diagnostics, and optional script artifacts. +- Both APIs produce stable SHA-256 hashes and deterministic compatibility scans. + +Build/test: + +- `pnpm nx build deterministic-bundler` +- `pnpm nx test deterministic-bundler` diff --git a/libs/deterministic-bundler/eslint.config.mjs b/libs/deterministic-bundler/eslint.config.mjs new file mode 100644 index 0000000..0a23ec0 --- /dev/null +++ b/libs/deterministic-bundler/eslint.config.mjs @@ -0,0 +1,25 @@ +import baseConfig from '../../eslint.config.mjs'; + +export default [ + ...baseConfig, + { + files: ['**/*.json'], + rules: { + '@nx/dependency-checks': [ + 'error', + { + ignoredFiles: [ + '{projectRoot}/eslint.config.{js,cjs,mjs,ts,cts,mts}', + '{projectRoot}/vite.config.{js,ts,mjs,mts}', + ], + }, + ], + }, + languageOptions: { + parser: await import('jsonc-eslint-parser'), + }, + }, + { + ignores: ['**/out-tsc'], + }, +]; diff --git a/libs/deterministic-bundler/package.json b/libs/deterministic-bundler/package.json new file mode 100644 index 0000000..659ee88 --- /dev/null +++ b/libs/deterministic-bundler/package.json @@ -0,0 +1,38 @@ +{ + "name": "@blue-quickjs/deterministic-bundler", + "version": "0.4.1", + "type": "module", + "main": "./dist/index.js", + "module": "./dist/index.js", + "types": "./dist/index.d.ts", + "exports": { + "./package.json": "./package.json", + ".": { + "@blue-quickjs/source": "./src/index.ts", + "types": "./dist/index.d.ts", + "import": "./dist/index.js", + "default": "./dist/index.js" + } + }, + "files": [ + "dist", + "!**/*.tsbuildinfo" + ], + "nx": { + "name": "deterministic-bundler" + }, + "dependencies": { + "@blue-quickjs/execution-profiles": "workspace:*", + "acorn": "^8.15.0", + "esbuild": "^0.27.4", + "tslib": "^2.3.0" + }, + "license": "MIT", + "publishConfig": { + "access": "public" + }, + "repository": { + "type": "git", + "url": "git+https://github.com/bluecontract/blue-quickjs.git" + } +} diff --git a/libs/deterministic-bundler/src/index.ts b/libs/deterministic-bundler/src/index.ts new file mode 100644 index 0000000..11efbac --- /dev/null +++ b/libs/deterministic-bundler/src/index.ts @@ -0,0 +1 @@ +export * from './lib/deterministic-bundler.js'; diff --git a/libs/deterministic-bundler/src/lib/deterministic-bundler.spec.ts b/libs/deterministic-bundler/src/lib/deterministic-bundler.spec.ts new file mode 100644 index 0000000..36514c9 --- /dev/null +++ b/libs/deterministic-bundler/src/lib/deterministic-bundler.spec.ts @@ -0,0 +1,365 @@ +import fs from 'node:fs'; +import os from 'node:os'; +import path from 'node:path'; +import { + buildDeterministicModulePack, + bundleDeterministicProgram, + DeterministicBundlerError, + scanCompatibility, +} from './deterministic-bundler.js'; + +describe('bundleDeterministicProgram', () => { + it('produces deterministic code and hash for the same inputs', async () => { + const fixtureDir = createFixtureDir(); + writeFixture(fixtureDir, 'util.ts', 'export const value = 7;'); + writeFixture( + fixtureDir, + 'entry.ts', + "import { value } from './util'; export default value;", + ); + + const first = await bundleDeterministicProgram({ + absWorkingDir: fixtureDir, + entryPath: 'entry.ts', + }); + const second = await bundleDeterministicProgram({ + absWorkingDir: fixtureDir, + entryPath: 'entry.ts', + }); + + expect(first.code).toBe(second.code); + expect(first.contentHash).toBe(second.contentHash); + expect(first.code).toContain(';__blueDeterministicBundle.default;'); + expect(first.meta.modulePaths).toEqual(second.meta.modulePaths); + expect(first.meta.modulePaths).toHaveLength(2); + expect(first.meta.compatibility.ok).toBe(true); + }); + + it('rejects baseline bundles that use RegExp literals', async () => { + const fixtureDir = createFixtureDir(); + writeFixture( + fixtureDir, + 'entry.ts', + "export default /a/.test('a') && Math.random() > -1;", + ); + + const error = await bundleDeterministicProgram({ + absWorkingDir: fixtureDir, + entryPath: 'entry.ts', + }) + .then(() => { + throw new Error('expected compatibility failure'); + }) + .catch((caught) => caught); + + expect(error).toBeInstanceOf(DeterministicBundlerError); + const bundlerError = error as DeterministicBundlerError; + expect( + bundlerError.diagnostics.some( + (diagnostic) => diagnostic.ruleId === 'regexp_literal_disabled', + ), + ).toBe(true); + expect( + bundlerError.diagnostics.some( + (diagnostic) => diagnostic.ruleId === 'math_random_disabled', + ), + ).toBe(true); + }); + + it('allows regexp usage under compat-regexp profile', async () => { + const fixtureDir = createFixtureDir(); + writeFixture(fixtureDir, 'entry.ts', "export default /a/.test('a');"); + + const bundled = await bundleDeterministicProgram({ + absWorkingDir: fixtureDir, + entryPath: 'entry.ts', + profile: 'compat-regexp-v1', + }); + + expect(bundled.meta.compatibility.ok).toBe(true); + expect(bundled.meta.profile).toBe('compat-regexp-v1'); + }); + + it('bundles chess.js fixture only under compat-regexp profile', async () => { + const workspaceRoot = path.resolve(process.cwd(), '../..'); + + await expect( + bundleDeterministicProgram({ + absWorkingDir: workspaceRoot, + entryPath: 'libs/test-harness/fixtures/library-reuse/chess-entry.ts', + }), + ).rejects.toBeInstanceOf(DeterministicBundlerError); + + const bundled = await bundleDeterministicProgram({ + absWorkingDir: workspaceRoot, + entryPath: 'libs/test-harness/fixtures/library-reuse/chess-entry.ts', + profile: 'compat-regexp-v1', + }); + + expect(bundled.meta.compatibility.ok).toBe(true); + expect(bundled.contentHash).toMatch(/^[0-9a-f]{64}$/); + expect(bundled.code.length).toBeGreaterThan(1000); + }); +}); + +describe('scanCompatibility', () => { + it('detects dynamic import and node builtins deterministically', () => { + const scan = scanCompatibility({ + sourceByPath: { + '/tmp/sample.ts': + "import fs from 'node:fs'; const x = import('./next.js'); export default x;", + }, + }); + + expect(scan.ok).toBe(false); + expect(scan.diagnostics).toEqual([ + { + filePath: '/tmp/sample.ts', + ruleId: 'dynamic_import_disabled', + message: 'dynamic import() is disabled in deterministic mode', + }, + { + filePath: '/tmp/sample.ts', + ruleId: 'node_builtin_import', + message: 'node builtin import is disabled: node:fs', + }, + ]); + }); + + it('allows regexp and console usage under compat-general profile', () => { + const scan = scanCompatibility({ + profile: 'compat-general-v1', + sourceByPath: { + '/tmp/sample.ts': "console.log(/a/.test('a')); export default true;", + }, + }); + + expect(scan.ok).toBe(true); + }); + + it('allows typed arrays under compat-binary profile', () => { + const scan = scanCompatibility({ + profile: 'compat-binary-v1', + sourceByPath: { + '/tmp/sample.ts': 'export default new Uint8Array([1, 2, 3]).length;', + }, + }); + + expect(scan.ok).toBe(true); + }); +}); + +describe('buildDeterministicModulePack', () => { + it('builds deterministic module-pack output for workspace TS fixture', async () => { + const fixtureDir = createFixtureDir(); + writeFixture(fixtureDir, 'lib/util.ts', 'export const value = 11;'); + writeFixture( + fixtureDir, + 'entry.ts', + "import { value } from './lib/util'; export default value;", + ); + + const first = await buildDeterministicModulePack({ + absWorkingDir: fixtureDir, + entryPath: 'entry.ts', + emitScriptArtifact: true, + }); + const second = await buildDeterministicModulePack({ + absWorkingDir: fixtureDir, + entryPath: 'entry.ts', + emitScriptArtifact: true, + }); + + expect(first.modulePack.version).toBe(1); + expect(first.modulePack.entryExport).toBe('default'); + expect(first.modulePack.modules.length).toBeGreaterThanOrEqual(1); + expect(first.modulePack.graphHash).toMatch(/^[0-9a-f]{64}$/); + expect(second.modulePack.graphHash).toBe(first.modulePack.graphHash); + expect(second.modulePack.modules).toEqual(first.modulePack.modules); + expect(first.compatibility.ok).toBe(true); + expect(first.compatibilityReport.version).toBe(1); + expect(first.compatibilityReport.profile).toBe('baseline-v1'); + expect(first.compatibilityReport.moduleCount).toBe( + first.modulePack.modules.length, + ); + expect(first.scriptArtifact?.contentHash).toMatch(/^[0-9a-f]{64}$/); + }); + + it('builds module-pack for external npm ESM fixture', async () => { + const fixtureDir = createFixtureDir(); + writeFixture( + fixtureDir, + 'node_modules/esm-lib/package.json', + JSON.stringify( + { + name: 'esm-lib', + version: '1.0.0', + type: 'module', + exports: './index.js', + }, + null, + 2, + ), + ); + writeFixture( + fixtureDir, + 'node_modules/esm-lib/index.js', + 'export const value = 41; export default value;', + ); + writeFixture( + fixtureDir, + 'entry.ts', + "import { value } from 'esm-lib'; export default value + 1;", + ); + + const built = await buildDeterministicModulePack({ + absWorkingDir: fixtureDir, + entryPath: 'entry.ts', + profile: 'compat-regexp-v1', + dependencyIntegrity: SAMPLE_HASH, + }); + + expect(built.compatibility.ok).toBe(true); + expect( + built.modulePack.modules.some( + (module) => module.originMeta?.packageName === 'esm-lib', + ), + ).toBe(true); + expect( + built.modulePack.modules.every( + (module) => !module.source.includes(normalizePath(fixtureDir)), + ), + ).toBe(true); + }); + + it('builds module-pack for external npm CJS fixture', async () => { + const fixtureDir = createFixtureDir(); + writeFixture( + fixtureDir, + 'node_modules/cjs-lib/package.json', + JSON.stringify( + { + name: 'cjs-lib', + version: '2.0.0', + main: 'index.cjs', + }, + null, + 2, + ), + ); + writeFixture( + fixtureDir, + 'node_modules/cjs-lib/index.cjs', + "module.exports = { isValid: (value) => value === '1.2.3' };", + ); + writeFixture( + fixtureDir, + 'entry.ts', + "import lib from 'cjs-lib'; export default lib.isValid('1.2.3');", + ); + + const built = await buildDeterministicModulePack({ + absWorkingDir: fixtureDir, + entryPath: 'entry.ts', + profile: 'compat-regexp-v1', + dependencyIntegrity: SAMPLE_HASH, + }); + + expect(built.compatibility.ok).toBe(true); + expect( + built.modulePack.modules.some( + (module) => module.originMeta?.packageName === 'cjs-lib', + ), + ).toBe(true); + expect( + built.modulePack.modules.every((module) => + module.sourceMap + ? !module.sourceMap.includes(normalizePath(fixtureDir)) + : true, + ), + ).toBe(true); + }); + + it('emits ProgramArtifact.v2 when requested', async () => { + const fixtureDir = createFixtureDir(); + writeFixture(fixtureDir, 'entry.ts', 'export default 99;'); + + const built = await buildDeterministicModulePack({ + absWorkingDir: fixtureDir, + entryPath: 'entry.ts', + emitProgramArtifact: true, + abiManifestHash: SAMPLE_HASH, + engineBuildHash: SAMPLE_HASH, + }); + + expect(built.programArtifact).toEqual({ + version: 2, + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: SAMPLE_HASH, + engineBuildHash: SAMPLE_HASH, + executionProfile: 'baseline-v1', + sourceKind: 'module-pack', + source: { + modulePack: built.modulePack, + }, + }); + }); + + it('keeps graphHash stable for a golden fixture', async () => { + const fixtureDir = createFixtureDir(); + writeFixture(fixtureDir, 'lib/value.ts', 'export const value = 5;'); + writeFixture( + fixtureDir, + 'entry.ts', + "import { value } from './lib/value'; export default value * 2;", + ); + + const built = await buildDeterministicModulePack({ + absWorkingDir: fixtureDir, + entryPath: 'entry.ts', + builderVersion: 'golden-builder', + dependencyIntegrity: SAMPLE_HASH, + }); + + expect(built.modulePack.graphHash).toBe( + '191c77a4a6235a20f460887a4bdad13b09ab34bf0f841fcad68504e3e757b6b4', + ); + }); + + it('rejects non-hex dependencyIntegrity overrides', async () => { + const fixtureDir = createFixtureDir(); + writeFixture(fixtureDir, 'entry.ts', 'export default 1;'); + + await expect( + buildDeterministicModulePack({ + absWorkingDir: fixtureDir, + entryPath: 'entry.ts', + dependencyIntegrity: 'test-integrity', + }), + ).rejects.toThrow( + 'dependencyIntegrity must be a lowercase 64-char hex string', + ); + }); +}); + +function createFixtureDir(): string { + return fs.mkdtempSync(path.join(os.tmpdir(), 'det-bundler-fixture-')); +} + +function writeFixture( + dir: string, + relativePath: string, + contents: string, +): void { + const filePath = path.join(dir, relativePath); + fs.mkdirSync(path.dirname(filePath), { recursive: true }); + fs.writeFileSync(filePath, contents, 'utf8'); +} + +function normalizePath(input: string): string { + return input.split(path.sep).join('/'); +} + +const SAMPLE_HASH = + 'aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa'; diff --git a/libs/deterministic-bundler/src/lib/deterministic-bundler.ts b/libs/deterministic-bundler/src/lib/deterministic-bundler.ts new file mode 100644 index 0000000..f5e9706 --- /dev/null +++ b/libs/deterministic-bundler/src/lib/deterministic-bundler.ts @@ -0,0 +1,1198 @@ +import { build } from 'esbuild'; +import { parse } from 'acorn'; +import { builtinModules } from 'node:module'; +import fs from 'node:fs'; +import path from 'node:path'; +import { createHash } from 'node:crypto'; +import { + executionProfileHasCapability, + type PublicExecutionProfile, +} from '@blue-quickjs/execution-profiles'; + +export type DeterministicExecutionProfile = PublicExecutionProfile; + +export interface BundleDeterministicProgramOptions { + entryPath: string; + absWorkingDir?: string; + profile?: DeterministicExecutionProfile; + globalName?: string; + rejectIncompatible?: boolean; +} + +export interface CompatibilityDiagnostic { + filePath: string; + ruleId: string; + message: string; +} + +export interface CompatibilityScanResult { + ok: boolean; + diagnostics: CompatibilityDiagnostic[]; +} + +export interface BundleDeterministicProgramResult { + code: string; + contentHash: string; + meta: { + entryPath: string; + modulePaths: string[]; + profile: DeterministicExecutionProfile; + compatibility: CompatibilityScanResult; + }; +} + +export interface ModulePackOriginMeta { + packageName?: string; + packageVersion?: string; + integrity?: string; + originalPath?: string; +} + +export interface ModulePackModule { + specifier: string; + source: string; + sourceMap?: string; + originMeta?: ModulePackOriginMeta; +} + +export interface ModulePackV1 { + version: 1; + entrySpecifier: string; + entryExport: string; + modules: ModulePackModule[]; + graphHash: string; + builderVersion: string; + dependencyIntegrity: string; + diagnosticsMeta?: { + entryPath: string; + modulePaths: string[]; + }; +} + +export interface BuildDeterministicModulePackOptions { + entryPath: string; + absWorkingDir?: string; + profile?: DeterministicExecutionProfile; + rejectIncompatible?: boolean; + entryExport?: string; + emitScriptArtifact?: boolean; + emitProgramArtifact?: boolean; + builderVersion?: string; + dependencyIntegrity?: string; + abiId?: string; + abiVersion?: number; + abiManifestHash?: string; + engineBuildHash?: string; + gasVersion?: number; +} + +export interface ProgramArtifactV2 { + version: 2; + abiId: string; + abiVersion: number; + abiManifestHash: string; + engineBuildHash?: string; + gasVersion?: number; + executionProfile: DeterministicExecutionProfile; + sourceKind: 'module-pack'; + source: { + modulePack: ModulePackV1; + }; +} + +export interface CompatibilityReportV1 { + version: 1; + profile: DeterministicExecutionProfile; + ok: boolean; + moduleCount: number; + diagnosticCounts: Record; + diagnostics: CompatibilityDiagnostic[]; +} + +export interface BuildDeterministicModulePackResult { + modulePack: ModulePackV1; + compatibility: CompatibilityScanResult; + compatibilityReport: CompatibilityReportV1; + scriptArtifact?: BundleDeterministicProgramResult; + programArtifact?: ProgramArtifactV2; +} + +export class DeterministicBundlerError extends Error { + constructor( + message: string, + public readonly diagnostics: CompatibilityDiagnostic[], + ) { + super(message); + this.name = 'DeterministicBundlerError'; + } +} + +const DEFAULT_PROFILE: DeterministicExecutionProfile = 'baseline-v1'; +const DEFAULT_GLOBAL_NAME = '__blueDeterministicBundle'; +const DEFAULT_ENTRY_EXPORT = 'default'; +const DEFAULT_BUILDER_VERSION = 'deterministic-builder-v1'; +const BUILDER_OUT_DIR = '__blue_deterministic_builder_out__'; + +const NODE_BUILTINS = new Set( + builtinModules.flatMap((name) => + name.startsWith('node:') ? [name, name.slice('node:'.length)] : [name], + ), +); + +const FORBIDDEN_IDENTIFIER_RULES = new Map([ + ['WebAssembly', 'webassembly_disabled'], + ['Atomics', 'atomics_disabled'], + ['Proxy', 'proxy_disabled'], + ['Date', 'date_disabled'], + ['setTimeout', 'timers_disabled'], + ['setInterval', 'timers_disabled'], +]); + +const BINARY_IDENTIFIER_RULES = new Map([ + ['ArrayBuffer', 'arraybuffer_disabled'], + ['SharedArrayBuffer', 'sharedarraybuffer_disabled'], + ['DataView', 'dataview_disabled'], +]); + +const FORBIDDEN_TYPED_ARRAYS = new Set([ + 'Uint8Array', + 'Uint8ClampedArray', + 'Int8Array', + 'Uint16Array', + 'Int16Array', + 'Uint32Array', + 'Int32Array', + 'BigInt64Array', + 'BigUint64Array', + 'Float16Array', + 'Float32Array', + 'Float64Array', +]); + +export async function bundleDeterministicProgram( + options: BundleDeterministicProgramOptions, +): Promise { + const absWorkingDir = path.resolve(options.absWorkingDir ?? process.cwd()); + const absEntryPath = path.resolve(absWorkingDir, options.entryPath); + const profile = options.profile ?? DEFAULT_PROFILE; + const globalName = options.globalName ?? DEFAULT_GLOBAL_NAME; + const rejectIncompatible = options.rejectIncompatible ?? true; + + const result = await build({ + absWorkingDir, + entryPoints: [absEntryPath], + bundle: true, + write: false, + outfile: 'bundle.js', + format: 'iife', + platform: 'neutral', + mainFields: ['module', 'main'], + target: 'es2020', + globalName, + legalComments: 'none', + sourcemap: false, + metafile: true, + charset: 'utf8', + }); + + const jsOutput = result.outputFiles?.find((file) => + file.path.endsWith('.js'), + ); + if (!jsOutput) { + throw new Error('Bundler did not produce a JavaScript output'); + } + + const modulePaths = collectNormalizedModulePaths( + result.metafile?.inputs ?? {}, + absWorkingDir, + ); + const sourceByPath = loadSourceByPath(modulePaths); + const compatibility = scanCompatibility({ + sourceByPath, + profile, + }); + + if (rejectIncompatible && !compatibility.ok) { + throw new DeterministicBundlerError( + formatCompatibilityMessage(compatibility.diagnostics), + compatibility.diagnostics, + ); + } + + const normalizedBundleText = normalizeLineEndings(jsOutput.text).trimEnd(); + const code = `${normalizedBundleText}\n;${globalName}.default;\n`; + + return { + code, + contentHash: sha256Hex(code), + meta: { + entryPath: normalizePath(absEntryPath), + modulePaths, + profile, + compatibility, + }, + }; +} + +export async function buildDeterministicModulePack( + options: BuildDeterministicModulePackOptions, +): Promise { + const absWorkingDir = path.resolve(options.absWorkingDir ?? process.cwd()); + const absEntryPath = path.resolve(absWorkingDir, options.entryPath); + const profile = options.profile ?? DEFAULT_PROFILE; + const rejectIncompatible = options.rejectIncompatible ?? true; + const entryExport = options.entryExport ?? DEFAULT_ENTRY_EXPORT; + const builderVersion = options.builderVersion ?? DEFAULT_BUILDER_VERSION; + const outputDir = path.join(absWorkingDir, BUILDER_OUT_DIR); + const dependencyIntegrity = + options.dependencyIntegrity !== undefined + ? expectHexStringOption( + options.dependencyIntegrity, + 'dependencyIntegrity', + ) + : computeDependencyIntegrity(absWorkingDir); + + const result = await build({ + absWorkingDir, + entryPoints: [absEntryPath], + bundle: true, + splitting: true, + write: false, + outdir: BUILDER_OUT_DIR, + format: 'esm', + platform: 'neutral', + mainFields: ['module', 'main'], + target: 'es2020', + legalComments: 'none', + sourcemap: 'external', + metafile: true, + charset: 'utf8', + }); + + const outputMetaByAbsolutePath = buildOutputMetadataLookup( + result.metafile?.outputs ?? {}, + absWorkingDir, + ); + const sourceMapBySpecifier = collectOutputMaps(result.outputFiles ?? [], { + absWorkingDir, + }); + const modules = collectModulePackModules(result.outputFiles ?? [], { + absWorkingDir, + outputDir, + outputMetaByAbsolutePath, + sourceMapBySpecifier, + dependencyIntegrity, + }); + const entrySpecifier = resolveEntrySpecifier( + result.metafile?.outputs ?? {}, + absWorkingDir, + absEntryPath, + ); + + const sourceByPath = Object.fromEntries( + modules.map((module) => [module.specifier, module.source]), + ); + const compatibility = scanCompatibility({ + sourceByPath, + profile, + }); + + if (rejectIncompatible && !compatibility.ok) { + throw new DeterministicBundlerError( + formatCompatibilityMessage(compatibility.diagnostics), + compatibility.diagnostics, + ); + } + + const modulePackWithoutHash = { + version: 1 as const, + entrySpecifier, + entryExport, + modules, + builderVersion, + dependencyIntegrity, + diagnosticsMeta: { + entryPath: normalizePath(absEntryPath), + modulePaths: modules.map((module) => module.specifier), + }, + }; + const graphHash = computeModulePackGraphHash(modulePackWithoutHash); + const modulePack: ModulePackV1 = { + ...modulePackWithoutHash, + graphHash, + }; + const compatibilityReport = buildCompatibilityReport({ + profile, + compatibility, + moduleCount: modules.length, + }); + + const scriptArtifact = options.emitScriptArtifact + ? await bundleDeterministicProgram({ + entryPath: options.entryPath, + absWorkingDir, + profile, + rejectIncompatible, + }) + : undefined; + const programArtifact = options.emitProgramArtifact + ? buildProgramArtifactV2({ + modulePack, + profile, + abiId: options.abiId ?? 'Host.v1', + abiVersion: options.abiVersion ?? 1, + abiManifestHash: expectHexStringOption( + options.abiManifestHash, + 'abiManifestHash', + ), + engineBuildHash: options.engineBuildHash + ? expectHexStringOption(options.engineBuildHash, 'engineBuildHash') + : undefined, + gasVersion: + options.gasVersion !== undefined + ? expectUint32Option(options.gasVersion, 'gasVersion') + : undefined, + }) + : undefined; + + return { + modulePack, + compatibility, + compatibilityReport, + ...(scriptArtifact ? { scriptArtifact } : {}), + ...(programArtifact ? { programArtifact } : {}), + }; +} + +export interface ScanCompatibilityOptions { + sourceByPath: Record; + profile?: DeterministicExecutionProfile; +} + +export function scanCompatibility( + options: ScanCompatibilityOptions, +): CompatibilityScanResult { + const profile = options.profile ?? DEFAULT_PROFILE; + const diagnostics = new Map(); + + const paths = Object.keys(options.sourceByPath).sort(); + for (const filePath of paths) { + const source = options.sourceByPath[filePath] ?? ''; + const parsed = safeParseModule(source); + if (!parsed.ok) { + addDiagnostic( + diagnostics, + filePath, + 'parse_error', + `Failed to parse source (${parsed.message})`, + ); + continue; + } + + walk(parsed.ast, (node) => { + scanNode(node, filePath, profile, diagnostics); + }); + } + + const sortedDiagnostics = [...diagnostics.values()].sort((a, b) => { + if (a.filePath !== b.filePath) { + return a.filePath.localeCompare(b.filePath); + } + if (a.ruleId !== b.ruleId) { + return a.ruleId.localeCompare(b.ruleId); + } + return a.message.localeCompare(b.message); + }); + + return { + ok: sortedDiagnostics.length === 0, + diagnostics: sortedDiagnostics, + }; +} + +type AstNode = Record & { type: string }; + +function scanNode( + node: AstNode, + filePath: string, + profile: DeterministicExecutionProfile, + diagnostics: Map, +): void { + if (node.type === 'ImportExpression') { + addDiagnostic( + diagnostics, + filePath, + 'dynamic_import_disabled', + 'dynamic import() is disabled in deterministic mode', + ); + return; + } + + if ( + node.type === 'ImportDeclaration' || + node.type === 'ExportAllDeclaration' + ) { + const source = asString( + (node as { source?: { value?: unknown } }).source?.value, + ); + if (source && isNodeBuiltinSpecifier(source)) { + addDiagnostic( + diagnostics, + filePath, + 'node_builtin_import', + `node builtin import is disabled: ${source}`, + ); + } + return; + } + + if (node.type === 'CallExpression') { + const callee = asNode((node as { callee?: unknown }).callee); + if (callee?.type === 'Identifier') { + const identifier = asString((callee as { name?: unknown }).name); + if (identifier === 'require') { + const firstArg = asNode( + (node as { arguments?: unknown[] }).arguments?.[0], + ); + if (firstArg?.type === 'Literal') { + const required = asString((firstArg as { value?: unknown }).value); + if (required && isNodeBuiltinSpecifier(required)) { + addDiagnostic( + diagnostics, + filePath, + 'node_builtin_require', + `node builtin require() is disabled: ${required}`, + ); + } + } + } + + if (identifier && FORBIDDEN_IDENTIFIER_RULES.has(identifier)) { + addDiagnostic( + diagnostics, + filePath, + FORBIDDEN_IDENTIFIER_RULES.get(identifier) ?? 'forbidden_identifier', + `forbidden API used: ${identifier}`, + ); + } + + if ( + identifier && + identifier === 'queueMicrotask' && + !executionProfileHasCapability(profile, 'queueMicrotask') + ) { + addDiagnostic( + diagnostics, + filePath, + 'microtasks_disabled', + `forbidden API used: ${identifier}`, + ); + } + + if ( + identifier && + BINARY_IDENTIFIER_RULES.has(identifier) && + !executionProfileHasCapability(profile, 'typedArrays') + ) { + addDiagnostic( + diagnostics, + filePath, + BINARY_IDENTIFIER_RULES.get(identifier) ?? 'binary_api_disabled', + `forbidden API used: ${identifier}`, + ); + } + } + + if (isMathRandomCall(callee)) { + addDiagnostic( + diagnostics, + filePath, + 'math_random_disabled', + 'Math.random() is disabled in deterministic mode', + ); + } + + if ( + isConsoleCall(callee) && + !executionProfileHasCapability(profile, 'consoleShim') + ) { + addDiagnostic( + diagnostics, + filePath, + 'console_disabled', + 'console APIs are disabled in deterministic mode', + ); + } + + if ( + isRegExpCall(callee) && + !executionProfileHasCapability(profile, 'regexp') + ) { + addDiagnostic( + diagnostics, + filePath, + 'regexp_disabled', + 'RegExp is disabled in baseline deterministic profile', + ); + } + + return; + } + + if (node.type === 'NewExpression') { + const callee = asNode((node as { callee?: unknown }).callee); + if (callee?.type === 'Identifier') { + const identifier = asString((callee as { name?: unknown }).name); + if (!identifier) { + return; + } + + if ( + FORBIDDEN_TYPED_ARRAYS.has(identifier) && + !executionProfileHasCapability(profile, 'typedArrays') + ) { + addDiagnostic( + diagnostics, + filePath, + 'typed_array_disabled', + `typed array constructor is disabled: ${identifier}`, + ); + return; + } + + if (FORBIDDEN_IDENTIFIER_RULES.has(identifier)) { + addDiagnostic( + diagnostics, + filePath, + FORBIDDEN_IDENTIFIER_RULES.get(identifier) ?? 'forbidden_identifier', + `forbidden API used: ${identifier}`, + ); + return; + } + + if ( + BINARY_IDENTIFIER_RULES.has(identifier) && + !executionProfileHasCapability(profile, 'typedArrays') + ) { + addDiagnostic( + diagnostics, + filePath, + BINARY_IDENTIFIER_RULES.get(identifier) ?? 'binary_api_disabled', + `forbidden API used: ${identifier}`, + ); + return; + } + + if ( + identifier === 'RegExp' && + !executionProfileHasCapability(profile, 'regexp') + ) { + addDiagnostic( + diagnostics, + filePath, + 'regexp_disabled', + 'RegExp is disabled in baseline deterministic profile', + ); + } + } + return; + } + + if ( + isRegExpLiteral(node) && + !executionProfileHasCapability(profile, 'regexp') + ) { + addDiagnostic( + diagnostics, + filePath, + 'regexp_literal_disabled', + 'RegExp literals are disabled in baseline deterministic profile', + ); + } +} + +function safeParseModule( + source: string, +): { ok: true; ast: AstNode } | { ok: false; message: string } { + try { + const ast = parse(source, { + ecmaVersion: 'latest', + sourceType: 'module', + allowHashBang: true, + }) as unknown as AstNode; + return { ok: true, ast }; + } catch (error) { + return { ok: false, message: stringifyError(error) }; + } +} + +function walk(node: AstNode, visit: (node: AstNode) => void): void { + visit(node); + const keys = Object.keys(node).sort(); + for (const key of keys) { + const value = (node as Record)[key]; + if (!value) { + continue; + } + + if (Array.isArray(value)) { + for (const item of value) { + if (isNode(item)) { + walk(item, visit); + } + } + continue; + } + + if (isNode(value)) { + walk(value, visit); + } + } +} + +function collectNormalizedModulePaths( + metafileInputs: Record, + absWorkingDir: string, +): string[] { + const paths = Object.keys(metafileInputs).map((input) => { + const absolute = path.isAbsolute(input) + ? input + : path.resolve(absWorkingDir, input); + return normalizePath(absolute); + }); + return [...new Set(paths)].sort(); +} + +function buildOutputMetadataLookup( + outputs: Record }>, + absWorkingDir: string, +): Map }> { + const lookup = new Map }>(); + for (const [outputPath, meta] of Object.entries(outputs)) { + const absolutePath = path.isAbsolute(outputPath) + ? outputPath + : path.resolve(absWorkingDir, outputPath); + lookup.set(normalizePath(absolutePath), meta); + } + return lookup; +} + +function collectOutputMaps( + outputFiles: Array<{ path: string; text: string }>, + options: { absWorkingDir: string }, +): Map { + const bySpecifier = new Map(); + const maps = outputFiles.filter((file) => file.path.endsWith('.map')); + for (const mapFile of maps) { + const mapPath = mapFile.path.slice(0, -'.map'.length); + const specifier = toModuleSpecifier(mapPath, { + absWorkingDir: options.absWorkingDir, + outputDir: path.join(options.absWorkingDir, BUILDER_OUT_DIR), + }); + bySpecifier.set( + specifier, + sanitizeSourceMap(mapFile.text, { + absWorkingDir: options.absWorkingDir, + }), + ); + } + return bySpecifier; +} + +function collectModulePackModules( + outputFiles: Array<{ path: string; text: string }>, + options: { + absWorkingDir: string; + outputDir: string; + outputMetaByAbsolutePath: Map }>; + sourceMapBySpecifier: Map; + dependencyIntegrity: string; + }, +): ModulePackModule[] { + const jsFiles = outputFiles.filter((file) => /\.m?js$/.test(file.path)); + const modules = jsFiles.map((file) => { + const specifier = toModuleSpecifier(file.path, { + absWorkingDir: options.absWorkingDir, + outputDir: options.outputDir, + }); + const normalizedSource = `${normalizeLineEndings(file.text).trimEnd()}\n`; + const meta = options.outputMetaByAbsolutePath.get(normalizePath(file.path)); + + const module: ModulePackModule = { + specifier, + source: normalizedSource, + }; + + const sourceMap = options.sourceMapBySpecifier.get(specifier); + if (sourceMap) { + module.sourceMap = sourceMap; + } + + const originMeta = resolveOriginMeta( + meta?.inputs ? Object.keys(meta.inputs) : [], + { + absWorkingDir: options.absWorkingDir, + dependencyIntegrity: options.dependencyIntegrity, + }, + ); + if (originMeta) { + module.originMeta = originMeta; + } + + return module; + }); + + return modules.sort((a, b) => compareUtf8ByteOrder(a.specifier, b.specifier)); +} + +function resolveEntrySpecifier( + outputs: Record, + absWorkingDir: string, + absEntryPath: string, +): string { + const normalizedEntry = normalizePath(absEntryPath); + const entryOutputPath = Object.entries(outputs) + .map(([outputPath, meta]) => { + const absoluteOutput = path.isAbsolute(outputPath) + ? outputPath + : path.resolve(absWorkingDir, outputPath); + const absoluteEntry = meta.entryPoint + ? path.resolve(absWorkingDir, meta.entryPoint) + : null; + return { + absoluteOutput, + absoluteEntry: absoluteEntry ? normalizePath(absoluteEntry) : null, + }; + }) + .find( + (candidate) => candidate.absoluteEntry === normalizedEntry, + )?.absoluteOutput; + + if (!entryOutputPath) { + throw new Error( + `Unable to resolve entry output for ${normalizePath(absEntryPath)}`, + ); + } + + return toModuleSpecifier(entryOutputPath, { + absWorkingDir, + outputDir: path.join(absWorkingDir, BUILDER_OUT_DIR), + }); +} + +function toModuleSpecifier( + outputPath: string, + options: { absWorkingDir: string; outputDir: string }, +): string { + const absoluteOutputPath = path.isAbsolute(outputPath) + ? outputPath + : path.resolve(options.absWorkingDir, outputPath); + const relative = normalizePath( + path.relative(options.outputDir, absoluteOutputPath), + ); + return relative.startsWith('.') ? relative : `./${relative}`; +} + +function sanitizeSourceMap( + sourceMap: string, + options: { absWorkingDir: string }, +): string { + const parsed = JSON.parse(sourceMap) as Record; + if (Array.isArray(parsed.sources)) { + parsed.sources = parsed.sources.map((source) => { + if (typeof source !== 'string') { + return source; + } + const normalized = normalizePath(source); + if (path.isAbsolute(source)) { + return normalizePath(path.relative(options.absWorkingDir, source)); + } + return normalized; + }); + } + if ( + typeof parsed.sourceRoot === 'string' && + path.isAbsolute(parsed.sourceRoot) + ) { + parsed.sourceRoot = normalizePath( + path.relative(options.absWorkingDir, parsed.sourceRoot), + ); + } + if (typeof parsed.file === 'string' && path.isAbsolute(parsed.file)) { + parsed.file = normalizePath( + path.relative(options.absWorkingDir, parsed.file), + ); + } + return stableStringify(parsed); +} + +function resolveOriginMeta( + inputPaths: string[], + options: { absWorkingDir: string; dependencyIntegrity: string }, +): ModulePackOriginMeta | undefined { + if (inputPaths.length === 0) { + return undefined; + } + const normalizedInputs = inputPaths + .map((inputPath) => + path.isAbsolute(inputPath) + ? inputPath + : path.resolve(options.absWorkingDir, inputPath), + ) + .map((inputPath) => normalizePath(inputPath)) + .sort(); + const selectedInputPath = + normalizedInputs.find((inputPath) => + inputPath.includes('/node_modules/'), + ) ?? normalizedInputs[0]; + + const originMeta: ModulePackOriginMeta = { + originalPath: normalizePath( + path.relative(options.absWorkingDir, selectedInputPath), + ), + }; + + const packageInfo = resolvePackageInfoFromInputPath(selectedInputPath); + if (packageInfo) { + originMeta.packageName = packageInfo.packageName; + originMeta.packageVersion = packageInfo.packageVersion; + originMeta.integrity = options.dependencyIntegrity; + } + + return originMeta; +} + +function resolvePackageInfoFromInputPath( + inputPath: string, +): { packageName: string; packageVersion?: string } | null { + const marker = '/node_modules/'; + const markerIndex = inputPath.lastIndexOf(marker); + if (markerIndex < 0) { + return null; + } + const fromNodeModules = inputPath.slice(markerIndex + marker.length); + const segments = fromNodeModules.split('/').filter(Boolean); + if (segments.length === 0) { + return null; + } + + let packageName: string; + if (segments[0].startsWith('@')) { + if (segments.length < 2) { + return null; + } + packageName = `${segments[0]}/${segments[1]}`; + } else { + packageName = segments[0]; + } + + const packageRoot = inputPath.slice( + 0, + markerIndex + marker.length + packageName.length, + ); + const packageJsonPath = path.join(packageRoot, 'package.json'); + if (!fs.existsSync(packageJsonPath)) { + return { packageName }; + } + + try { + const packageJson = JSON.parse( + fs.readFileSync(packageJsonPath, 'utf8'), + ) as { + version?: string; + }; + return { + packageName, + ...(typeof packageJson.version === 'string' + ? { packageVersion: packageJson.version } + : {}), + }; + } catch { + return { packageName }; + } +} + +function computeDependencyIntegrity(absWorkingDir: string): string { + const lockfilePath = findNearestLockfile(absWorkingDir); + if (!lockfilePath) { + return sha256Hex('no-lockfile'); + } + const bytes = fs.readFileSync(lockfilePath); + return createHash('sha256').update(bytes).digest('hex'); +} + +function findNearestLockfile(startDir: string): string | null { + const lockfiles = ['pnpm-lock.yaml', 'package-lock.json', 'yarn.lock']; + let cursor = path.resolve(startDir); + + while (true) { + for (const lockfile of lockfiles) { + const candidate = path.join(cursor, lockfile); + if (fs.existsSync(candidate)) { + return candidate; + } + } + const parent = path.dirname(cursor); + if (parent === cursor) { + return null; + } + cursor = parent; + } +} + +function computeModulePackGraphHash(pack: { + version: 1; + entrySpecifier: string; + entryExport: string; + modules: ModulePackModule[]; + builderVersion: string; + dependencyIntegrity: string; +}): string { + const canonical = { + version: pack.version, + entrySpecifier: pack.entrySpecifier, + entryExport: pack.entryExport, + modules: pack.modules.map((module) => ({ + specifier: module.specifier, + source: module.source, + ...(module.sourceMap ? { sourceMap: module.sourceMap } : {}), + })), + builderVersion: pack.builderVersion, + dependencyIntegrity: pack.dependencyIntegrity, + }; + return sha256Hex(stableStringify(canonical)); +} + +function buildCompatibilityReport(options: { + profile: DeterministicExecutionProfile; + compatibility: CompatibilityScanResult; + moduleCount: number; +}): CompatibilityReportV1 { + const diagnosticCounts = options.compatibility.diagnostics.reduce< + Record + >((accumulator, diagnostic) => { + accumulator[diagnostic.ruleId] = (accumulator[diagnostic.ruleId] ?? 0) + 1; + return accumulator; + }, {}); + + return { + version: 1, + profile: options.profile, + ok: options.compatibility.ok, + moduleCount: options.moduleCount, + diagnosticCounts, + diagnostics: options.compatibility.diagnostics, + }; +} + +function buildProgramArtifactV2(options: { + modulePack: ModulePackV1; + profile: DeterministicExecutionProfile; + abiId: string; + abiVersion: number; + abiManifestHash: string; + engineBuildHash?: string; + gasVersion?: number; +}): ProgramArtifactV2 { + return { + version: 2, + abiId: options.abiId, + abiVersion: options.abiVersion, + abiManifestHash: options.abiManifestHash, + ...(options.engineBuildHash + ? { + engineBuildHash: options.engineBuildHash, + } + : {}), + ...(options.gasVersion !== undefined + ? { + gasVersion: options.gasVersion, + } + : {}), + executionProfile: options.profile, + sourceKind: 'module-pack', + source: { + modulePack: options.modulePack, + }, + }; +} + +function expectHexStringOption( + value: string | undefined, + fieldName: string, +): string { + if (!value) { + throw new Error(`buildDeterministicModulePack requires ${fieldName}`); + } + if (!/^[0-9a-f]{64}$/.test(value)) { + throw new Error(`${fieldName} must be a lowercase 64-char hex string`); + } + return value; +} + +function expectUint32Option(value: number, fieldName: string): number { + if (!Number.isInteger(value) || value < 0 || value > 0xffffffff) { + throw new Error(`${fieldName} must be a uint32 integer`); + } + return value; +} + +function stableStringify(value: unknown): string { + if (value === null || typeof value !== 'object') { + return JSON.stringify(value); + } + if (Array.isArray(value)) { + return `[${value.map((item) => stableStringify(item)).join(',')}]`; + } + + const entries = Object.entries(value as Record) + .filter(([, item]) => item !== undefined) + .sort(([left], [right]) => compareUtf8ByteOrder(left, right)) + .map(([key, item]) => `${JSON.stringify(key)}:${stableStringify(item)}`); + return `{${entries.join(',')}}`; +} + +const UTF8_ENCODER = new TextEncoder(); + +function compareUtf8ByteOrder(left: string, right: string): number { + if (left === right) { + return 0; + } + + const leftBytes = UTF8_ENCODER.encode(left); + const rightBytes = UTF8_ENCODER.encode(right); + const limit = Math.min(leftBytes.length, rightBytes.length); + + for (let index = 0; index < limit; index += 1) { + const delta = leftBytes[index] - rightBytes[index]; + if (delta !== 0) { + return delta; + } + } + + return leftBytes.length - rightBytes.length; +} + +function loadSourceByPath(modulePaths: string[]): Record { + const sourceByPath: Record = {}; + for (const modulePath of modulePaths) { + if (!fs.existsSync(modulePath)) { + continue; + } + sourceByPath[modulePath] = fs.readFileSync(modulePath, 'utf8'); + } + return sourceByPath; +} + +function addDiagnostic( + diagnostics: Map, + filePath: string, + ruleId: string, + message: string, +): void { + const normalizedPath = normalizePath(filePath); + const key = `${normalizedPath}::${ruleId}::${message}`; + if (diagnostics.has(key)) { + return; + } + diagnostics.set(key, { + filePath: normalizedPath, + ruleId, + message, + }); +} + +function isMathRandomCall(node: AstNode | null): boolean { + if (!node || node.type !== 'MemberExpression') { + return false; + } + const object = asNode((node as { object?: unknown }).object); + const property = asNode((node as { property?: unknown }).property); + if (!object || !property) { + return false; + } + return ( + object.type === 'Identifier' && + asString((object as { name?: unknown }).name) === 'Math' && + property.type === 'Identifier' && + asString((property as { name?: unknown }).name) === 'random' + ); +} + +function isConsoleCall(node: AstNode | null): boolean { + if (!node || node.type !== 'MemberExpression') { + return false; + } + const object = asNode((node as { object?: unknown }).object); + return ( + object?.type === 'Identifier' && + asString((object as { name?: unknown }).name) === 'console' + ); +} + +function isRegExpCall(node: AstNode | null): boolean { + return ( + !!node && + node.type === 'Identifier' && + asString((node as { name?: unknown }).name) === 'RegExp' + ); +} + +function isRegExpLiteral(node: AstNode): boolean { + if (node.type !== 'Literal') { + return false; + } + return Boolean((node as { regex?: unknown }).regex); +} + +function isNode(value: unknown): value is AstNode { + return ( + value !== null && + typeof value === 'object' && + typeof (value as { type?: unknown }).type === 'string' + ); +} + +function asNode(value: unknown): AstNode | null { + return isNode(value) ? value : null; +} + +function asString(value: unknown): string | null { + return typeof value === 'string' ? value : null; +} + +function isNodeBuiltinSpecifier(specifier: string): boolean { + if (specifier.startsWith('node:')) { + return true; + } + return NODE_BUILTINS.has(specifier); +} + +function normalizePath(input: string): string { + return input.split(path.sep).join('/'); +} + +function normalizeLineEndings(input: string): string { + return input.replace(/\r\n/g, '\n').replace(/\r/g, '\n'); +} + +function sha256Hex(input: string): string { + return createHash('sha256').update(input, 'utf8').digest('hex'); +} + +function stringifyError(error: unknown): string { + if (error instanceof Error) { + return error.message; + } + return String(error); +} + +function formatCompatibilityMessage( + diagnostics: CompatibilityDiagnostic[], +): string { + const lines = diagnostics.map( + (diagnostic) => + `- [${diagnostic.ruleId}] ${diagnostic.filePath}: ${diagnostic.message}`, + ); + return `Compatibility scan failed:\n${lines.join('\n')}`; +} diff --git a/libs/deterministic-bundler/tsconfig.json b/libs/deterministic-bundler/tsconfig.json new file mode 100644 index 0000000..62ebbd9 --- /dev/null +++ b/libs/deterministic-bundler/tsconfig.json @@ -0,0 +1,13 @@ +{ + "extends": "../../tsconfig.base.json", + "files": [], + "include": [], + "references": [ + { + "path": "./tsconfig.lib.json" + }, + { + "path": "./tsconfig.spec.json" + } + ] +} diff --git a/libs/deterministic-bundler/tsconfig.lib.json b/libs/deterministic-bundler/tsconfig.lib.json new file mode 100644 index 0000000..c24c7a8 --- /dev/null +++ b/libs/deterministic-bundler/tsconfig.lib.json @@ -0,0 +1,32 @@ +{ + "extends": "../../tsconfig.base.json", + "compilerOptions": { + "baseUrl": ".", + "rootDir": "src", + "outDir": "dist", + "tsBuildInfoFile": "dist/tsconfig.lib.tsbuildinfo", + "emitDeclarationOnly": false, + "forceConsistentCasingInFileNames": true, + "types": ["node"] + }, + "include": ["src/**/*.ts"], + "references": [ + { + "path": "../execution-profiles/tsconfig.lib.json" + } + ], + "exclude": [ + "vite.config.ts", + "vite.config.mts", + "vitest.config.ts", + "vitest.config.mts", + "src/**/*.test.ts", + "src/**/*.spec.ts", + "src/**/*.test.tsx", + "src/**/*.spec.tsx", + "src/**/*.test.js", + "src/**/*.spec.js", + "src/**/*.test.jsx", + "src/**/*.spec.jsx" + ] +} diff --git a/libs/deterministic-bundler/tsconfig.spec.json b/libs/deterministic-bundler/tsconfig.spec.json new file mode 100644 index 0000000..f68d9d3 --- /dev/null +++ b/libs/deterministic-bundler/tsconfig.spec.json @@ -0,0 +1,34 @@ +{ + "extends": "../../tsconfig.base.json", + "compilerOptions": { + "outDir": "./out-tsc/vitest", + "types": [ + "vitest/globals", + "vitest/importMeta", + "vite/client", + "node", + "vitest" + ], + "forceConsistentCasingInFileNames": true + }, + "include": [ + "vite.config.ts", + "vite.config.mts", + "vitest.config.ts", + "vitest.config.mts", + "src/**/*.test.ts", + "src/**/*.spec.ts", + "src/**/*.test.tsx", + "src/**/*.spec.tsx", + "src/**/*.test.js", + "src/**/*.spec.js", + "src/**/*.test.jsx", + "src/**/*.spec.jsx", + "src/**/*.d.ts" + ], + "references": [ + { + "path": "./tsconfig.lib.json" + } + ] +} diff --git a/libs/deterministic-bundler/vite.config.ts b/libs/deterministic-bundler/vite.config.ts new file mode 100644 index 0000000..45189b7 --- /dev/null +++ b/libs/deterministic-bundler/vite.config.ts @@ -0,0 +1,20 @@ +/// +import { defineConfig } from 'vite'; + +export default defineConfig(() => ({ + root: import.meta.dirname, + cacheDir: '../../node_modules/.vite/libs/deterministic-bundler', + plugins: [], + test: { + name: 'deterministic-bundler', + watch: false, + globals: true, + environment: 'node', + include: ['{src,tests}/**/*.{test,spec}.{js,mjs,cjs,ts,mts,cts,jsx,tsx}'], + reporters: ['default'], + coverage: { + reportsDirectory: './test-output/vitest/coverage', + provider: 'v8' as const, + }, + }, +})); diff --git a/libs/dv/src/lib/dv.spec.ts b/libs/dv/src/lib/dv.spec.ts index 5a4a894..6674935 100644 --- a/libs/dv/src/lib/dv.spec.ts +++ b/libs/dv/src/lib/dv.spec.ts @@ -7,8 +7,11 @@ import { DvError, DvErrorCode, decodeDv, + decodeDv2, encodeDv, + encodeDv2, isDv, + isDv2, } from './dv.js'; const hex = (bytes: Uint8Array): string => @@ -132,6 +135,47 @@ describe('encodeDv / decodeDv', () => { ); }); + it('supports byte-string values in DV2 mode', () => { + const bytes = Uint8Array.from([0xde, 0xad, 0xbe, 0xef]); + expect(hex(encodeDv2(bytes))).toBe('44deadbeef'); + + const decoded = decodeDv2(Uint8Array.from([0x44, 0xde, 0xad, 0xbe, 0xef])); + expect(decoded).toBeInstanceOf(Uint8Array); + expect(Array.from(decoded as Uint8Array)).toEqual([0xde, 0xad, 0xbe, 0xef]); + + const nested = decodeDv2( + Uint8Array.from([ + 0xa1, 0x65, 0x62, 0x79, 0x74, 0x65, 0x73, 0x44, 0x00, 0x01, 0x02, 0x03, + ]), + ) as { bytes: Uint8Array }; + expect(Array.from(nested.bytes)).toEqual([0, 1, 2, 3]); + + expect(isDv2({ payload: bytes })).toBe(true); + expect(isDv({ payload: bytes })).toBe(false); + }); + + it('keeps DV1 byte strings unsupported and enforces DV2 byte limits', () => { + expectCode(() => encodeDv(Uint8Array.from([1, 2, 3])), 'UNSUPPORTED_TYPE'); + expectCode( + () => decodeDv(Uint8Array.from([0x41, 0x01])), + 'UNSUPPORTED_CBOR', + ); + expectCode( + () => + encodeDv2(Uint8Array.from([1, 2, 3]), { + limits: { maxByteStringBytes: 2 }, + }), + 'BYTE_STRING_TOO_LONG', + ); + expectCode( + () => + decodeDv2(Uint8Array.from([0x43, 0x01, 0x02, 0x03]), { + limits: { maxByteStringBytes: 2 }, + }), + 'BYTE_STRING_TOO_LONG', + ); + }); + it('roundtrips and canonicalizes under property-based generation', () => { const limits = { maxDepth: 4, @@ -178,4 +222,24 @@ describe('encodeDv / decodeDv', () => { { numRuns: 150 }, ); }); + + it('roundtrips DV2 values containing byte strings', () => { + const value = { + kind: 'bytes', + payload: Uint8Array.from([1, 2, 3, 4]), + nested: [Uint8Array.from([9, 8]), { ok: true }], + }; + const encoded = encodeDv2(value); + const decoded = decodeDv2(encoded) as { + kind: string; + payload: Uint8Array; + nested: [Uint8Array, { ok: boolean }]; + }; + + expect(decoded.kind).toBe('bytes'); + expect(Array.from(decoded.payload)).toEqual([1, 2, 3, 4]); + expect(Array.from(decoded.nested[0])).toEqual([9, 8]); + expect(decoded.nested[1]).toEqual({ ok: true }); + expect(hex(encodeDv2(decoded))).toBe(hex(encoded)); + }); }); diff --git a/libs/dv/src/lib/dv.ts b/libs/dv/src/lib/dv.ts index 2bddce2..826b6eb 100644 --- a/libs/dv/src/lib/dv.ts +++ b/libs/dv/src/lib/dv.ts @@ -6,6 +6,7 @@ const MIN_SAFE_INT = Number.MIN_SAFE_INTEGER; const CBOR_MAJOR_UINT = 0; const CBOR_MAJOR_NINT = 1; +const CBOR_MAJOR_BYTES = 2; const CBOR_MAJOR_TEXT = 3; const CBOR_MAJOR_ARRAY = 4; const CBOR_MAJOR_MAP = 5; @@ -15,11 +16,17 @@ export type DV = DVPrimitive | DVArray | DVObject; export type DVPrimitive = null | boolean | number | string; export type DVArray = DV[]; export type DVObject = { [key: string]: DV }; +export type DV2 = DV2Primitive | DV2Bytes | DV2Array | DV2Object; +export type DV2Primitive = null | boolean | number | string; +export type DV2Bytes = Uint8Array; +export type DV2Array = DV2[]; +export type DV2Object = { [key: string]: DV2 }; export interface DvLimits { maxDepth: number; maxEncodedBytes: number; maxStringBytes: number; + maxByteStringBytes: number; maxArrayLength: number; maxMapLength: number; } @@ -28,6 +35,7 @@ export const DV_LIMIT_DEFAULTS: Readonly = { maxDepth: 64, maxEncodedBytes: 5_242_880, maxStringBytes: 262_144, + maxByteStringBytes: 262_144, maxArrayLength: 65_535, maxMapLength: 65_535, }; @@ -47,6 +55,7 @@ export type DvErrorCode = | 'INTEGER_OUT_OF_RANGE' | 'INVALID_STRING' | 'STRING_TOO_LONG' + | 'BYTE_STRING_TOO_LONG' | 'ARRAY_TOO_LONG' | 'MAP_TOO_LONG' | 'DEPTH_EXCEEDED' @@ -77,7 +86,17 @@ export function encodeDv( ): Uint8Array { const limits = normalizeLimits(options?.limits); const builder = new ByteBuilder(limits.maxEncodedBytes); - encodeValue(value, builder, limits, 0); + encodeValue(value, builder, limits, 0, false); + return builder.toUint8Array(); +} + +export function encodeDv2( + value: unknown, + options?: DvEncodeOptions, +): Uint8Array { + const limits = normalizeLimits(options?.limits); + const builder = new ByteBuilder(limits.maxEncodedBytes); + encodeValue(value, builder, limits, 0, true); return builder.toUint8Array(); } @@ -101,7 +120,36 @@ export function decodeDv( } const reader = new CborReader(bytes); - const value = readValue(reader, limits, 0); + const value = readValue(reader, limits, 0, false) as DV; + + if (!reader.isEOF()) { + throw dvError('TRAILING_BYTES', 'unexpected trailing bytes after DV value'); + } + + return value; +} + +export function decodeDv2( + input: ArrayBufferView | ArrayBuffer | Uint8Array, + options?: DvDecodeOptions, +): DV2 { + const limits = normalizeLimits(options?.limits); + const bytes = + input instanceof Uint8Array + ? input + : input instanceof ArrayBuffer + ? new Uint8Array(input) + : new Uint8Array(input.buffer, input.byteOffset, input.byteLength); + + if (bytes.length > limits.maxEncodedBytes) { + throw dvError( + 'ENCODED_TOO_LARGE', + `encoded DV exceeds maxEncodedBytes (${bytes.length} > ${limits.maxEncodedBytes})`, + ); + } + + const reader = new CborReader(bytes); + const value = readValue(reader, limits, 0, true); if (!reader.isEOF()) { throw dvError('TRAILING_BYTES', 'unexpected trailing bytes after DV value'); @@ -127,12 +175,33 @@ export function isDv(value: unknown, options?: DvValidateOptions): value is DV { } } +export function validateDv2( + value: unknown, + options?: DvValidateOptions, +): asserts value is DV2 { + encodeDv2(value, options); +} + +export function isDv2( + value: unknown, + options?: DvValidateOptions, +): value is DV2 { + try { + validateDv2(value, options); + return true; + } catch { + return false; + } +} + function normalizeLimits(limits?: PartialLimits): DvLimits { return { maxDepth: limits?.maxDepth ?? DV_LIMIT_DEFAULTS.maxDepth, maxEncodedBytes: limits?.maxEncodedBytes ?? DV_LIMIT_DEFAULTS.maxEncodedBytes, maxStringBytes: limits?.maxStringBytes ?? DV_LIMIT_DEFAULTS.maxStringBytes, + maxByteStringBytes: + limits?.maxByteStringBytes ?? DV_LIMIT_DEFAULTS.maxByteStringBytes, maxArrayLength: limits?.maxArrayLength ?? DV_LIMIT_DEFAULTS.maxArrayLength, maxMapLength: limits?.maxMapLength ?? DV_LIMIT_DEFAULTS.maxMapLength, }; @@ -216,12 +285,18 @@ function encodeValue( builder: ByteBuilder, limits: DvLimits, depth: number, + allowBytes: boolean, ): void { if (value === null) { builder.pushByte(0xf6); return; } + if (allowBytes && value instanceof Uint8Array) { + encodeByteString(value, builder, limits); + return; + } + const type = describeUnsupportedType(value); if (type === 'boolean') { builder.pushByte(value ? 0xf5 : 0xf4); @@ -239,12 +314,18 @@ function encodeValue( } if (Array.isArray(value)) { - encodeArray(value as DVArray, builder, limits, depth); + encodeArray(value as unknown[], builder, limits, depth, allowBytes); return; } if (isPlainObject(value)) { - encodeMap(value as Record, builder, limits, depth); + encodeMap( + value as Record, + builder, + limits, + depth, + allowBytes, + ); return; } @@ -305,11 +386,27 @@ function encodeString( builder.pushBytes(bytes); } +function encodeByteString( + value: Uint8Array, + builder: ByteBuilder, + limits: DvLimits, +): void { + if (value.length > limits.maxByteStringBytes) { + throw dvError( + 'BYTE_STRING_TOO_LONG', + `byte string exceeds maxByteStringBytes (${value.length} > ${limits.maxByteStringBytes})`, + ); + } + encodeTypeAndLength(builder, CBOR_MAJOR_BYTES, value.length); + builder.pushBytes(value); +} + function encodeArray( - value: DVArray, + value: unknown[], builder: ByteBuilder, limits: DvLimits, depth: number, + allowBytes: boolean, ): void { const nextDepth = depth + 1; if (nextDepth > limits.maxDepth) { @@ -324,7 +421,7 @@ function encodeArray( encodeTypeAndLength(builder, CBOR_MAJOR_ARRAY, value.length); for (const element of value) { - encodeValue(element, builder, limits, nextDepth); + encodeValue(element, builder, limits, nextDepth, allowBytes); } } @@ -333,6 +430,7 @@ function encodeMap( builder: ByteBuilder, limits: DvLimits, depth: number, + allowBytes: boolean, ): void { const keys = Object.keys(value); const nextDepth = depth + 1; @@ -373,7 +471,7 @@ function encodeMap( encodeTypeAndLength(builder, CBOR_MAJOR_MAP, encodedKeys.length); for (const entry of encodedKeys) { builder.pushBytes(entry.encoded); - encodeValue(value[entry.key], builder, limits, nextDepth); + encodeValue(value[entry.key], builder, limits, nextDepth, allowBytes); } } @@ -547,7 +645,12 @@ class CborReader { } } -function readValue(reader: CborReader, limits: DvLimits, depth: number): DV { +function readValue( + reader: CborReader, + limits: DvLimits, + depth: number, + allowBytes: boolean, +): DV2 { const initial = reader.readByte(); const major = initial >> 5; const additional = initial & 0x1f; @@ -557,12 +660,20 @@ function readValue(reader: CborReader, limits: DvLimits, depth: number): DV { return readUnsigned(additional, reader); case CBOR_MAJOR_NINT: return readNegative(additional, reader); + case CBOR_MAJOR_BYTES: + if (!allowBytes) { + throw dvError( + 'UNSUPPORTED_CBOR', + `unsupported CBOR major type ${major}`, + ); + } + return readByteString(additional, reader, limits); case CBOR_MAJOR_TEXT: return readText(additional, reader, limits); case CBOR_MAJOR_ARRAY: - return readArray(additional, reader, limits, depth); + return readArray(additional, reader, limits, depth, allowBytes); case CBOR_MAJOR_MAP: - return readMap(additional, reader, limits, depth); + return readMap(additional, reader, limits, depth, allowBytes); case CBOR_MAJOR_SIMPLE: return readSimpleOrFloat(additional, reader); default: @@ -570,6 +681,25 @@ function readValue(reader: CborReader, limits: DvLimits, depth: number): DV { } } +function readByteString( + additional: number, + reader: CborReader, + limits: DvLimits, +): Uint8Array { + const length = readLength(additional, reader); + if (length > limits.maxByteStringBytes) { + throw dvError( + 'BYTE_STRING_TOO_LONG', + `byte string exceeds maxByteStringBytes (${length} > ${limits.maxByteStringBytes})`, + ); + } + const start = reader.position(); + for (let i = 0; i < length; i += 1) { + reader.readByte(); + } + return reader.takeSlice(start, start + length); +} + function readUnsigned(additional: number, reader: CborReader): number { const value = readLengthValue(additional, reader); if (value > MAX_SAFE_INT) { @@ -627,7 +757,8 @@ function readArray( reader: CborReader, limits: DvLimits, depth: number, -): DVArray { + allowBytes: boolean, +): DV2Array { const length = readLength(additional, reader); const nextDepth = depth + 1; if (nextDepth > limits.maxDepth) { @@ -639,9 +770,9 @@ function readArray( `array length exceeds maxArrayLength (${length} > ${limits.maxArrayLength})`, ); } - const result: DVArray = []; + const result: DV2Array = []; for (let i = 0; i < length; i += 1) { - result.push(readValue(reader, limits, nextDepth)); + result.push(readValue(reader, limits, nextDepth, allowBytes)); } return result; } @@ -651,7 +782,8 @@ function readMap( reader: CborReader, limits: DvLimits, depth: number, -): DVObject { + allowBytes: boolean, +): DV2Object { const length = readLength(additional, reader); const nextDepth = depth + 1; @@ -665,7 +797,7 @@ function readMap( ); } - const result: DVObject = Object.create(null); + const result: DV2Object = Object.create(null); let previousKey: Uint8Array | undefined; for (let i = 0; i < length; i += 1) { @@ -690,7 +822,7 @@ function readMap( } previousKey = encodedKey; - result[key] = readValue(reader, limits, nextDepth); + result[key] = readValue(reader, limits, nextDepth, allowBytes); } return result; diff --git a/libs/execution-profiles/README.md b/libs/execution-profiles/README.md new file mode 100644 index 0000000..db2e430 --- /dev/null +++ b/libs/execution-profiles/README.md @@ -0,0 +1,10 @@ +# @blue-quickjs/execution-profiles + +Canonical execution-profile registry shared by runtime and builder surfaces. + +Exports: + +- profile identifiers (`baseline-v1`, `compat-regexp-v1`, + `compat-general-v1`, `compat-binary-v1`) +- capability lookup helpers +- profile membership checks diff --git a/libs/execution-profiles/eslint.config.mjs b/libs/execution-profiles/eslint.config.mjs new file mode 100644 index 0000000..0a23ec0 --- /dev/null +++ b/libs/execution-profiles/eslint.config.mjs @@ -0,0 +1,25 @@ +import baseConfig from '../../eslint.config.mjs'; + +export default [ + ...baseConfig, + { + files: ['**/*.json'], + rules: { + '@nx/dependency-checks': [ + 'error', + { + ignoredFiles: [ + '{projectRoot}/eslint.config.{js,cjs,mjs,ts,cts,mts}', + '{projectRoot}/vite.config.{js,ts,mjs,mts}', + ], + }, + ], + }, + languageOptions: { + parser: await import('jsonc-eslint-parser'), + }, + }, + { + ignores: ['**/out-tsc'], + }, +]; diff --git a/libs/execution-profiles/package.json b/libs/execution-profiles/package.json new file mode 100644 index 0000000..a8aa8b0 --- /dev/null +++ b/libs/execution-profiles/package.json @@ -0,0 +1,35 @@ +{ + "name": "@blue-quickjs/execution-profiles", + "version": "0.4.1", + "type": "module", + "main": "./dist/index.js", + "module": "./dist/index.js", + "types": "./dist/index.d.ts", + "exports": { + "./package.json": "./package.json", + ".": { + "@blue-quickjs/source": "./src/index.ts", + "types": "./dist/index.d.ts", + "import": "./dist/index.js", + "default": "./dist/index.js" + } + }, + "files": [ + "dist", + "!**/*.tsbuildinfo" + ], + "nx": { + "name": "execution-profiles" + }, + "dependencies": { + "tslib": "^2.3.0" + }, + "license": "MIT", + "publishConfig": { + "access": "public" + }, + "repository": { + "type": "git", + "url": "git+https://github.com/bluecontract/blue-quickjs.git" + } +} diff --git a/libs/execution-profiles/src/index.ts b/libs/execution-profiles/src/index.ts new file mode 100644 index 0000000..07d6d8d --- /dev/null +++ b/libs/execution-profiles/src/index.ts @@ -0,0 +1 @@ +export * from './lib/execution-profiles.js'; diff --git a/libs/execution-profiles/src/lib/execution-profiles.spec.ts b/libs/execution-profiles/src/lib/execution-profiles.spec.ts new file mode 100644 index 0000000..bd23e70 --- /dev/null +++ b/libs/execution-profiles/src/lib/execution-profiles.spec.ts @@ -0,0 +1,57 @@ +import { + executionProfileHasCapability, + getExecutionProfileCapabilities, + isKnownExecutionProfile, + listExecutionProfiles, +} from './execution-profiles.js'; + +describe('execution profile registry', () => { + it('recognizes known public profiles', () => { + expect(isKnownExecutionProfile('baseline-v1')).toBe(true); + expect(isKnownExecutionProfile('compat-general-v1')).toBe(true); + expect(isKnownExecutionProfile('compat-binary-v1')).toBe(true); + expect(isKnownExecutionProfile('compat-unknown-v1')).toBe(false); + }); + + it('returns deterministic capability sets per profile', () => { + expect(getExecutionProfileCapabilities('baseline-v1')).toEqual([]); + expect(getExecutionProfileCapabilities('compat-regexp-v1')).toEqual([ + 'regexp', + ]); + expect(getExecutionProfileCapabilities('compat-general-v1')).toEqual([ + 'regexp', + 'promiseJobs', + 'queueMicrotask', + 'stableSort', + 'consoleShim', + ]); + expect(getExecutionProfileCapabilities('compat-binary-v1')).toEqual([ + 'regexp', + 'promiseJobs', + 'queueMicrotask', + 'stableSort', + 'consoleShim', + 'typedArrays', + 'dvBytes', + ]); + }); + + it('checks individual capability membership', () => { + expect(executionProfileHasCapability('baseline-v1', 'regexp')).toBe(false); + expect(executionProfileHasCapability('compat-regexp-v1', 'regexp')).toBe( + true, + ); + expect( + executionProfileHasCapability('compat-binary-v1', 'typedArrays'), + ).toBe(true); + }); + + it('lists all profiles in deterministic order', () => { + expect(listExecutionProfiles()).toEqual([ + 'baseline-v1', + 'compat-regexp-v1', + 'compat-general-v1', + 'compat-binary-v1', + ]); + }); +}); diff --git a/libs/execution-profiles/src/lib/execution-profiles.ts b/libs/execution-profiles/src/lib/execution-profiles.ts new file mode 100644 index 0000000..c058af3 --- /dev/null +++ b/libs/execution-profiles/src/lib/execution-profiles.ts @@ -0,0 +1,88 @@ +export type DeterministicCapability = + | 'regexp' + | 'promiseJobs' + | 'queueMicrotask' + | 'stableSort' + | 'consoleShim' + | 'typedArrays' + | 'dvBytes'; + +export type PublicExecutionProfile = + | 'baseline-v1' + | 'compat-regexp-v1' + | 'compat-general-v1' + | 'compat-binary-v1'; + +export interface ExecutionProfileDefinition { + id: PublicExecutionProfile; + capabilities: readonly DeterministicCapability[]; +} + +const PROFILE_CAPABILITIES: Record< + PublicExecutionProfile, + readonly DeterministicCapability[] +> = { + 'baseline-v1': [], + 'compat-regexp-v1': ['regexp'], + 'compat-general-v1': [ + 'regexp', + 'promiseJobs', + 'queueMicrotask', + 'stableSort', + 'consoleShim', + ], + 'compat-binary-v1': [ + 'regexp', + 'promiseJobs', + 'queueMicrotask', + 'stableSort', + 'consoleShim', + 'typedArrays', + 'dvBytes', + ], +}; + +export const EXECUTION_PROFILE_REGISTRY: Record< + PublicExecutionProfile, + ExecutionProfileDefinition +> = Object.freeze( + Object.fromEntries( + Object.entries(PROFILE_CAPABILITIES).map(([id, capabilities]) => [ + id, + { + id: id as PublicExecutionProfile, + capabilities, + }, + ]), + ) as Record, +); + +const KNOWN_PROFILES = Object.freeze( + new Set(Object.keys(PROFILE_CAPABILITIES) as PublicExecutionProfile[]), +); + +export function isKnownExecutionProfile( + value: unknown, +): value is PublicExecutionProfile { + return ( + typeof value === 'string' && + KNOWN_PROFILES.has(value as PublicExecutionProfile) + ); +} + +export function getExecutionProfileCapabilities( + profile: PublicExecutionProfile, +): readonly DeterministicCapability[] { + return PROFILE_CAPABILITIES[profile]; +} + +export function executionProfileHasCapability( + profile: PublicExecutionProfile, + capability: DeterministicCapability, +): boolean { + return PROFILE_CAPABILITIES[profile].includes(capability); +} + +export function listExecutionProfiles(): readonly PublicExecutionProfile[] { + return Object.keys(PROFILE_CAPABILITIES) as PublicExecutionProfile[]; +} diff --git a/libs/execution-profiles/tsconfig.json b/libs/execution-profiles/tsconfig.json new file mode 100644 index 0000000..62ebbd9 --- /dev/null +++ b/libs/execution-profiles/tsconfig.json @@ -0,0 +1,13 @@ +{ + "extends": "../../tsconfig.base.json", + "files": [], + "include": [], + "references": [ + { + "path": "./tsconfig.lib.json" + }, + { + "path": "./tsconfig.spec.json" + } + ] +} diff --git a/libs/execution-profiles/tsconfig.lib.json b/libs/execution-profiles/tsconfig.lib.json new file mode 100644 index 0000000..d30b75b --- /dev/null +++ b/libs/execution-profiles/tsconfig.lib.json @@ -0,0 +1,28 @@ +{ + "extends": "../../tsconfig.base.json", + "compilerOptions": { + "baseUrl": ".", + "rootDir": "src", + "outDir": "dist", + "tsBuildInfoFile": "dist/tsconfig.lib.tsbuildinfo", + "emitDeclarationOnly": false, + "forceConsistentCasingInFileNames": true, + "types": ["node"] + }, + "include": ["src/**/*.ts"], + "references": [], + "exclude": [ + "vite.config.ts", + "vite.config.mts", + "vitest.config.ts", + "vitest.config.mts", + "src/**/*.test.ts", + "src/**/*.spec.ts", + "src/**/*.test.tsx", + "src/**/*.spec.tsx", + "src/**/*.test.js", + "src/**/*.spec.js", + "src/**/*.test.jsx", + "src/**/*.spec.jsx" + ] +} diff --git a/libs/execution-profiles/tsconfig.spec.json b/libs/execution-profiles/tsconfig.spec.json new file mode 100644 index 0000000..f68d9d3 --- /dev/null +++ b/libs/execution-profiles/tsconfig.spec.json @@ -0,0 +1,34 @@ +{ + "extends": "../../tsconfig.base.json", + "compilerOptions": { + "outDir": "./out-tsc/vitest", + "types": [ + "vitest/globals", + "vitest/importMeta", + "vite/client", + "node", + "vitest" + ], + "forceConsistentCasingInFileNames": true + }, + "include": [ + "vite.config.ts", + "vite.config.mts", + "vitest.config.ts", + "vitest.config.mts", + "src/**/*.test.ts", + "src/**/*.spec.ts", + "src/**/*.test.tsx", + "src/**/*.spec.tsx", + "src/**/*.test.js", + "src/**/*.spec.js", + "src/**/*.test.jsx", + "src/**/*.spec.jsx", + "src/**/*.d.ts" + ], + "references": [ + { + "path": "./tsconfig.lib.json" + } + ] +} diff --git a/libs/execution-profiles/vite.config.ts b/libs/execution-profiles/vite.config.ts new file mode 100644 index 0000000..9cecec2 --- /dev/null +++ b/libs/execution-profiles/vite.config.ts @@ -0,0 +1,20 @@ +/// +import { defineConfig } from 'vite'; + +export default defineConfig(() => ({ + root: import.meta.dirname, + cacheDir: '../../node_modules/.vite/libs/execution-profiles', + plugins: [], + test: { + name: 'execution-profiles', + watch: false, + globals: true, + environment: 'node', + include: ['{src,tests}/**/*.{test,spec}.{js,mjs,cjs,ts,mts,cts,jsx,tsx}'], + reporters: ['default'], + coverage: { + reportsDirectory: './test-output/vitest/coverage', + provider: 'v8' as const, + }, + }, +})); diff --git a/libs/quickjs-runtime/README.md b/libs/quickjs-runtime/README.md index ebdf2f0..4ce3aa0 100644 --- a/libs/quickjs-runtime/README.md +++ b/libs/quickjs-runtime/README.md @@ -46,6 +46,10 @@ const result = await evaluate({ // Optional observability: tape: { capacity: 32 }, gasTrace: true, + + // Release-mode pin validation: + releaseMode: true, + expectedExecutionProfile: 'baseline-v1', }); if (!result.ok) { diff --git a/libs/quickjs-runtime/eslint.config.mjs b/libs/quickjs-runtime/eslint.config.mjs index 0a23ec0..2090421 100644 --- a/libs/quickjs-runtime/eslint.config.mjs +++ b/libs/quickjs-runtime/eslint.config.mjs @@ -2,6 +2,28 @@ import baseConfig from '../../eslint.config.mjs'; export default [ ...baseConfig, + { + files: ['**/*.ts', '**/*.tsx', '**/*.js', '**/*.jsx'], + rules: { + '@nx/enforce-module-boundaries': [ + 'error', + { + enforceBuildableLibDependency: true, + allow: ['^.*/eslint(\\.base)?\\.config\\.[cm]?[jt]s$'], + ignoredCircularDependencies: [ + ['quickjs-runtime', 'test-harness'], + ['quickjs-runtime', 'quickjs-wasm'], + ], + depConstraints: [ + { + sourceTag: '*', + onlyDependOnLibsWithTags: ['*'], + }, + ], + }, + ], + }, + }, { files: ['**/*.json'], rules: { diff --git a/libs/quickjs-runtime/package.json b/libs/quickjs-runtime/package.json index 9bc661b..3b5f89d 100644 --- a/libs/quickjs-runtime/package.json +++ b/libs/quickjs-runtime/package.json @@ -24,10 +24,13 @@ "dependencies": { "@blue-quickjs/abi-manifest": "workspace:*", "@blue-quickjs/dv": "workspace:*", + "@blue-quickjs/execution-profiles": "workspace:*", "@blue-quickjs/quickjs-wasm": "workspace:*", + "@jridgewell/trace-mapping": "^0.3.31", "tslib": "^2.3.0" }, "devDependencies": { + "@blue-quickjs/deterministic-bundler": "workspace:*", "@blue-quickjs/test-harness": "workspace:*" }, "license": "MIT", diff --git a/libs/quickjs-runtime/src/lib/binary-library-reuse.spec.ts b/libs/quickjs-runtime/src/lib/binary-library-reuse.spec.ts new file mode 100644 index 0000000..65ae39f --- /dev/null +++ b/libs/quickjs-runtime/src/lib/binary-library-reuse.spec.ts @@ -0,0 +1,56 @@ +import { bundleDeterministicProgram } from '@blue-quickjs/deterministic-bundler'; +import path from 'node:path'; +import { + BINARY_LIBRARY_FIXTURES, + BINARY_LIBRARY_GAS_LIMIT, + BINARY_LIBRARY_INPUT, + BINARY_LIBRARY_MANIFEST, + BINARY_LIBRARY_PROGRAM_BASE, + createDeterminismHost, +} from '@blue-quickjs/test-harness'; +import { evaluate } from './evaluate.js'; + +describe('library reuse: binary packages', () => { + for (const fixture of BINARY_LIBRARY_FIXTURES) { + it(`bundles ${fixture.name} deterministically`, async () => { + const workspaceRoot = path.resolve(process.cwd(), '../..'); + const bundled = await bundleDeterministicProgram({ + absWorkingDir: workspaceRoot, + entryPath: fixture.entryPath, + profile: 'compat-binary-v1', + }); + + const run = async () => { + const host = createDeterminismHost(); + return evaluate({ + program: { + ...BINARY_LIBRARY_PROGRAM_BASE, + code: bundled.code, + }, + input: BINARY_LIBRARY_INPUT, + gasLimit: BINARY_LIBRARY_GAS_LIMIT, + manifest: BINARY_LIBRARY_MANIFEST, + handlers: host.handlers, + }); + }; + + const first = await run(); + const second = await run(); + + if (!first.ok || !second.ok) { + const describe = (result: typeof first) => + result.ok + ? 'ok' + : `${result.type}:${result.error.code}:${result.message}`; + throw new Error( + `expected binary fixture runs to succeed: first=${describe(first)} second=${describe(second)}`, + ); + } + + expect(first.value).toEqual(fixture.expectedValue); + expect(second.value).toEqual(fixture.expectedValue); + expect(first.gasUsed).toBe(second.gasUsed); + expect(first.gasRemaining).toBe(second.gasRemaining); + }); + } +}); diff --git a/libs/quickjs-runtime/src/lib/chess-library-reuse.spec.ts b/libs/quickjs-runtime/src/lib/chess-library-reuse.spec.ts new file mode 100644 index 0000000..c454df3 --- /dev/null +++ b/libs/quickjs-runtime/src/lib/chess-library-reuse.spec.ts @@ -0,0 +1,57 @@ +import { bundleDeterministicProgram } from '@blue-quickjs/deterministic-bundler'; +import path from 'node:path'; +import { + CHESS_E2E6_EXPECTED_LEGAL, + CHESS_LIBRARY_ENTRY_PATH, + CHESS_LIBRARY_GAS_LIMIT, + CHESS_LIBRARY_INPUT, + CHESS_LIBRARY_MANIFEST, + CHESS_LIBRARY_PROGRAM_BASE, + createDeterminismHost, +} from '@blue-quickjs/test-harness'; +import { evaluate } from './evaluate.js'; + +describe('library reuse: chess.js', () => { + it('bundles chess fixture deterministically and evaluates legality for e2e6', async () => { + const workspaceRoot = path.resolve(process.cwd(), '../..'); + const bundled = await bundleDeterministicProgram({ + absWorkingDir: workspaceRoot, + entryPath: CHESS_LIBRARY_ENTRY_PATH, + profile: 'compat-general-v1', + }); + + const run = async () => { + const host = createDeterminismHost(); + const result = await evaluate({ + program: { + ...CHESS_LIBRARY_PROGRAM_BASE, + code: bundled.code, + }, + input: CHESS_LIBRARY_INPUT, + gasLimit: CHESS_LIBRARY_GAS_LIMIT, + manifest: CHESS_LIBRARY_MANIFEST, + handlers: host.handlers, + }); + + return result; + }; + + const first = await run(); + const second = await run(); + + if (!first.ok || !second.ok) { + const describe = (result: typeof first) => + result.ok + ? 'ok' + : `${result.type}:${result.error.code}:${result.message}`; + throw new Error( + `expected chess fixture runs to succeed: first=${describe(first)} second=${describe(second)}`, + ); + } + + expect(first.value).toBe(CHESS_E2E6_EXPECTED_LEGAL); + expect(second.value).toBe(CHESS_E2E6_EXPECTED_LEGAL); + expect(first.gasUsed).toBe(second.gasUsed); + expect(first.gasRemaining).toBe(second.gasRemaining); + }); +}); diff --git a/libs/quickjs-runtime/src/lib/deterministic-init.ts b/libs/quickjs-runtime/src/lib/deterministic-init.ts index ecddee4..3a2af3f 100644 --- a/libs/quickjs-runtime/src/lib/deterministic-init.ts +++ b/libs/quickjs-runtime/src/lib/deterministic-init.ts @@ -1,7 +1,9 @@ import { encodeAbiManifest } from '@blue-quickjs/abi-manifest'; import { encodeDv } from '@blue-quickjs/dv'; +import { executionProfileHasCapability } from '@blue-quickjs/execution-profiles'; import type { QuickjsWasmModule } from './runtime.js'; import { + type ExecutionProfile, type InputEnvelope, type ProgramArtifact, validateInputEnvelope, @@ -19,36 +21,60 @@ type DetInitFn = ( contextPtr: number, contextLength: number, gasLimit: bigint, + featureFlags: number, ) => number; type DetEvalFn = (code: string) => number; +type DetEvalModulePackFn = ( + modulePackJson: string, + entrySpecifier: string, + entryExport: string, +) => number; type DetSetGasLimitFn = (gasLimit: bigint) => number; type EnableTapeFn = (capacity: number) => number; type ReadTapeFn = () => number; +type EnableChargeTapeFn = (capacity: number) => number; +type ReadChargeTapeFn = () => number; type EnableTraceFn = (enabled: number) => number; type ReadTraceFn = () => number; interface DeterministicExports { init: DetInitFn; eval: DetEvalFn; + evalModulePack: DetEvalModulePackFn; setGasLimit: DetSetGasLimitFn; freeRuntime: () => void; enableTape: EnableTapeFn; readTape: ReadTapeFn; + enableChargeTape: EnableChargeTapeFn; + readChargeTape: ReadChargeTapeFn; enableTrace: EnableTraceFn; readTrace: ReadTraceFn; } export interface DeterministicVm { eval(code: string): string; + evalModulePack( + modulePackJson: string, + entrySpecifier: string, + entryExport: string, + ): string; setGasLimit(limit: bigint | number): void; enableTape(capacity: number): void; readTape(): string; + enableGasChargeTape(capacity: number): void; + readGasChargeTape(): string; enableGasTrace(enabled: boolean): void; readGasTrace(): string; dispose(): void; } +const DETERMINISTIC_FEATURE_REGEXP = 1 << 0; +const DETERMINISTIC_FEATURE_PROMISE_JOBS = 1 << 1; +const DETERMINISTIC_FEATURE_CONSOLE_SHIM = 1 << 2; +const DETERMINISTIC_FEATURE_STABLE_SORT = 1 << 3; +const DETERMINISTIC_FEATURE_TYPED_ARRAYS = 1 << 4; + export function initializeDeterministicVm( runtime: RuntimeInstance, program: ProgramArtifact, @@ -85,6 +111,7 @@ export function initializeDeterministicVm( contextPtr, contextBlob.length, normalizedGasLimit, + executionProfileToFeatureFlags(validatedProgram.executionProfile), ); if (errorPtr !== 0) { const message = readAndFreeCString(runtime.module, errorPtr); @@ -107,6 +134,21 @@ export function initializeDeterministicVm( } return readAndFreeCString(runtime.module, ptr); }, + evalModulePack( + modulePackJson: string, + entrySpecifier: string, + entryExport: string, + ): string { + const ptr = ffi.evalModulePack( + modulePackJson, + entrySpecifier, + entryExport, + ); + if (ptr === 0) { + throw new Error('qjs_det_eval_module_pack returned a null pointer'); + } + return readAndFreeCString(runtime.module, ptr); + }, setGasLimit(limit: bigint | number): void { const normalized = normalizeGasLimit(limit); const rc = ffi.setGasLimit(normalized); @@ -132,6 +174,24 @@ export function initializeDeterministicVm( } return readAndFreeCString(runtime.module, ptr); }, + enableGasChargeTape(capacity: number): void { + if (!Number.isInteger(capacity) || capacity < 0) { + throw new Error( + `charge tape capacity must be a non-negative integer (received ${capacity})`, + ); + } + const rc = ffi.enableChargeTape(capacity >>> 0); + if (rc !== 0) { + throw new Error('failed to enable gas charge tape'); + } + }, + readGasChargeTape(): string { + const ptr = ffi.readChargeTape(); + if (ptr === 0) { + throw new Error('qjs_det_read_charge_tape returned a null pointer'); + } + return readAndFreeCString(runtime.module, ptr); + }, enableGasTrace(enabled: boolean): void { const rc = ffi.enableTrace(enabled ? 1 : 0); if (rc !== 0) { @@ -161,11 +221,17 @@ function createDeterministicExports( 'number', 'number', 'bigint', + 'number', ]) as unknown as DetInitFn; const evalFn = module.cwrap('qjs_det_eval', 'number', [ 'string', ]) as unknown as DetEvalFn; + const evalModulePack = module.cwrap('qjs_det_eval_module_pack', 'number', [ + 'string', + 'string', + 'string', + ]) as unknown as DetEvalModulePackFn; const setGasLimit = module.cwrap('qjs_det_set_gas_limit', 'number', [ 'bigint', ]) as unknown as DetSetGasLimitFn; @@ -183,6 +249,16 @@ function createDeterministicExports( 'number', [], ) as unknown as ReadTapeFn; + const enableChargeTape = module.cwrap( + 'qjs_det_enable_charge_tape', + 'number', + ['number'], + ) as unknown as EnableChargeTapeFn; + const readChargeTape = module.cwrap( + 'qjs_det_read_charge_tape', + 'number', + [], + ) as unknown as ReadChargeTapeFn; const enableTrace = module.cwrap('qjs_det_enable_trace', 'number', [ 'number', ]) as unknown as EnableTraceFn; @@ -195,10 +271,13 @@ function createDeterministicExports( return { init, eval: evalFn, + evalModulePack, setGasLimit, freeRuntime, enableTape, readTape, + enableChargeTape, + readChargeTape, enableTrace, readTrace, }; @@ -230,6 +309,32 @@ function normalizeGasLimit(value: bigint | number): bigint { return value; } +function executionProfileToFeatureFlags(profile?: ExecutionProfile): number { + if (!profile) { + return 0; + } + let flags = 0; + if (executionProfileHasCapability(profile, 'regexp')) { + flags |= DETERMINISTIC_FEATURE_REGEXP; + } + if ( + executionProfileHasCapability(profile, 'promiseJobs') || + executionProfileHasCapability(profile, 'queueMicrotask') + ) { + flags |= DETERMINISTIC_FEATURE_PROMISE_JOBS; + } + if (executionProfileHasCapability(profile, 'consoleShim')) { + flags |= DETERMINISTIC_FEATURE_CONSOLE_SHIM; + } + if (executionProfileHasCapability(profile, 'stableSort')) { + flags |= DETERMINISTIC_FEATURE_STABLE_SORT; + } + if (executionProfileHasCapability(profile, 'typedArrays')) { + flags |= DETERMINISTIC_FEATURE_TYPED_ARRAYS; + } + return flags; +} + function writeBytes(module: QuickjsWasmModule, data: Uint8Array): number { const ptr = module._malloc(data.length); if (ptr === 0) { diff --git a/libs/quickjs-runtime/src/lib/evaluate-errors.ts b/libs/quickjs-runtime/src/lib/evaluate-errors.ts index 29e2ff4..9ad70f6 100644 --- a/libs/quickjs-runtime/src/lib/evaluate-errors.ts +++ b/libs/quickjs-runtime/src/lib/evaluate-errors.ts @@ -26,6 +26,24 @@ export type EvaluateVmErrorDetail = name: string; message: string; } + | { + kind: 'execution-surface-mismatch'; + code: 'EXECUTION_SURFACE_MISMATCH'; + tag: 'vm/execution_surface'; + name: string; + message: string; + } + | { + kind: 'module-pack'; + code: + | 'MODULE_PACK_HASH_MISMATCH' + | 'MODULE_SPECIFIER_NOT_FOUND' + | 'MODULE_EXPORT_MISSING' + | 'MODULE_RESOLUTION_ERROR' + | 'MODULE_EVALUATION_ERROR'; + tag: 'vm/module_pack'; + message: string; + } | { kind: 'unknown'; code: 'UNKNOWN'; @@ -78,6 +96,21 @@ export function mapVmError( }; } + if (isExecutionSurfaceMismatch(name, normalizedMessage)) { + return { + kind: 'execution-surface-mismatch', + code: 'EXECUTION_SURFACE_MISMATCH', + tag: 'vm/execution_surface', + name: name || 'SyntaxError', + message: normalizedMessage, + }; + } + + const modulePackError = parseModulePackError(name, normalizedMessage); + if (modulePackError) { + return modulePackError; + } + if (name && name !== 'Error') { return { kind: 'js-exception', @@ -97,6 +130,72 @@ export function mapVmError( }; } +function parseModulePackError( + name: string, + message: string, +): EvaluateVmErrorDetail | null { + if ( + name === 'ModulePackHashMismatch' || + message.startsWith('MODULE_PACK_HASH_MISMATCH') + ) { + return { + kind: 'module-pack', + code: 'MODULE_PACK_HASH_MISMATCH', + tag: 'vm/module_pack', + message, + }; + } + + if ( + name === 'ModuleSpecifierNotFound' || + message.startsWith('ModuleSpecifierNotFound') || + message.includes('ModuleSpecifierNotFound') + ) { + return { + kind: 'module-pack', + code: 'MODULE_SPECIFIER_NOT_FOUND', + tag: 'vm/module_pack', + message, + }; + } + + if ( + name === 'ModuleExportMissing' || + message.startsWith('ModuleExportMissing') || + message.includes('ModuleExportMissing') + ) { + return { + kind: 'module-pack', + code: 'MODULE_EXPORT_MISSING', + tag: 'vm/module_pack', + message, + }; + } + + if ( + message.startsWith('ModuleResolutionError') || + message.includes('ModuleResolutionError') + ) { + return { + kind: 'module-pack', + code: 'MODULE_RESOLUTION_ERROR', + tag: 'vm/module_pack', + message, + }; + } + + if (name === 'ModuleEvaluationError') { + return { + kind: 'module-pack', + code: 'MODULE_EVALUATION_ERROR', + tag: 'vm/module_pack', + message, + }; + } + + return null; +} + export function createInvalidOutputError( message: string, cause: unknown, @@ -150,3 +249,16 @@ function deriveManifestErrorCode(message: string): string { } return 'MANIFEST_ERROR'; } + +function isExecutionSurfaceMismatch(name: string, message: string): boolean { + if (name !== 'SyntaxError') { + return false; + } + + const normalized = message.toLowerCase(); + return ( + normalized.includes('return not in a function') || + normalized.includes('illegal return') || + normalized.includes('return outside of function') + ); +} diff --git a/libs/quickjs-runtime/src/lib/evaluate.spec.ts b/libs/quickjs-runtime/src/lib/evaluate.spec.ts index 3b01370..99b0f22 100644 --- a/libs/quickjs-runtime/src/lib/evaluate.spec.ts +++ b/libs/quickjs-runtime/src/lib/evaluate.spec.ts @@ -1,8 +1,18 @@ -import { HOST_V1_HASH, HOST_V1_MANIFEST } from '@blue-quickjs/abi-manifest'; +import { + HOST_V1_HASH, + HOST_V1_MANIFEST, + HOST_V2_HASH, + HOST_V2_MANIFEST, +} from '@blue-quickjs/abi-manifest'; +import { createHash } from 'node:crypto'; import { vi } from 'vitest'; import { evaluate } from './evaluate.js'; import type { HostDispatcherHandlers } from './host-dispatcher.js'; -import type { InputEnvelope, ProgramArtifact } from './quickjs-runtime.js'; +import type { + InputEnvelope, + ProgramArtifact, + ProgramArtifactV2, +} from './quickjs-runtime.js'; const TEST_GAS_LIMIT = 50_000n; @@ -13,6 +23,26 @@ const BASE_PROGRAM: ProgramArtifact = { abiManifestHash: HOST_V1_HASH, }; +const BASE_PROGRAM_V2_SCRIPT: ProgramArtifactV2 = { + version: 2, + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + executionProfile: 'baseline-v1', + sourceKind: 'script', + source: { + code: 'document("path/to/doc")', + }, +}; + +const BASE_PROGRAM_V2_BINARY: ProgramArtifact = { + code: 'Host.v2.document.get("bytes/payload").byteLength', + abiId: 'Host.v2', + abiVersion: 2, + abiManifestHash: HOST_V2_HASH, + executionProfile: 'compat-binary-v1', +}; + const BASE_INPUT: InputEnvelope = { event: { type: 'create', payload: { id: 1 } }, eventCanonical: { type: 'create', payload: { id: 1 } }, @@ -21,7 +51,511 @@ const BASE_INPUT: InputEnvelope = { currentContractCanonical: { id: { value: 'contract-1' } }, }; +function createModulePackProgram( + modulePack: ReturnType, +): ProgramArtifactV2 { + return { + ...BASE_PROGRAM_V2_SCRIPT, + sourceKind: 'module-pack', + source: { + modulePack, + }, + }; +} + describe('evaluate', () => { + it('evaluates raw script mode using final expression result', async () => { + const result = await evaluate({ + program: { ...BASE_PROGRAM, code: 'const n = 2; n + 3' }, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }); + + expect(result.ok).toBe(true); + if (!result.ok) { + throw new Error(result.message); + } + expect(result.value).toBe(5); + }); + + it('evaluates ProgramArtifact.v2 script source', async () => { + const result = await evaluate({ + program: { + ...BASE_PROGRAM_V2_SCRIPT, + source: { + code: 'const n = 10; n + 4;', + }, + }, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }); + + expect(result.ok).toBe(true); + if (!result.ok) { + throw new Error(result.message); + } + expect(result.value).toBe(14); + }); + + it('evaluates ProgramArtifact.v2 module-pack default export', async () => { + const modulePack = createModulePack({ + entrySpecifier: './entry.js', + modules: [ + { + specifier: './entry.js', + source: 'export default 1;\n', + }, + ], + }); + + const result = await evaluate({ + program: createModulePackProgram(modulePack), + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }); + + expect(result.ok).toBe(true); + if (!result.ok) { + throw new Error(result.message); + } + expect(result.value).toBe(1); + }); + + it('evaluates module-pack entryExport for named exports', async () => { + const modulePack = createModulePack({ + entrySpecifier: './entry.js', + entryExport: 'answer', + modules: [ + { + specifier: './entry.js', + source: 'export const answer = 42;\n', + }, + ], + }); + + const result = await evaluate({ + program: createModulePackProgram(modulePack), + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }); + + expect(result.ok).toBe(true); + if (!result.ok) { + throw new Error(result.message); + } + expect(result.value).toBe(42); + }); + + it('evaluates cyclic module-pack imports deterministically', async () => { + const modulePack = createModulePack({ + entrySpecifier: './entry.js', + modules: [ + { + specifier: './entry.js', + source: + "import { valueFromA } from './b.js'; export default valueFromA;\n", + }, + { + specifier: './a.js', + source: + "import { getB } from './b.js'; export function getA() { return 40 + getB(); }\n", + }, + { + specifier: './b.js', + source: + "import { getA } from './a.js'; export function getB() { return 2; } export const valueFromA = getA();\n", + }, + ], + }); + + const result = await evaluate({ + program: createModulePackProgram(modulePack), + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }); + + expect(result.ok).toBe(true); + if (!result.ok) { + throw new Error(result.message); + } + expect(result.value).toBe(42); + }); + + it('maps missing entry module to deterministic module-pack error', async () => { + const modulePack = createModulePack({ + entrySpecifier: './missing.js', + modules: [ + { + specifier: './entry.js', + source: 'export default 1;\n', + }, + ], + }); + + const result = await evaluate({ + program: createModulePackProgram(modulePack), + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }); + + expect(result.ok).toBe(false); + if (result.ok) { + throw new Error('expected module-pack failure'); + } + expect(result.type).toBe('vm-error'); + expect(result.error.kind).toBe('module-pack'); + if (result.error.kind !== 'module-pack') { + throw new Error('expected module-pack error kind'); + } + expect(result.error.code).toBe('MODULE_SPECIFIER_NOT_FOUND'); + }); + + it('maps missing module export to deterministic module-pack error', async () => { + const modulePack = createModulePack({ + entrySpecifier: './entry.js', + entryExport: 'missing', + modules: [ + { + specifier: './entry.js', + source: 'export const value = 1;\n', + }, + ], + }); + + const result = await evaluate({ + program: createModulePackProgram(modulePack), + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }); + + expect(result.ok).toBe(false); + if (result.ok) { + throw new Error('expected module-pack failure'); + } + expect(result.type).toBe('vm-error'); + expect(result.error.kind).toBe('module-pack'); + if (result.error.kind !== 'module-pack') { + throw new Error('expected module-pack error kind'); + } + expect(result.error.code).toBe('MODULE_EXPORT_MISSING'); + }); + + it('rejects module-pack artifacts with graph hash mismatch', async () => { + const modulePack = createModulePack({ + entrySpecifier: './entry.js', + modules: [ + { + specifier: './entry.js', + source: 'export default 1;\n', + }, + ], + }); + + await expect( + evaluate({ + program: { + ...createModulePackProgram({ + ...modulePack, + graphHash: + 'bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb', + }), + }, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }), + ).rejects.toThrow(/MODULE_PACK_HASH_MISMATCH/); + }); + + it('classifies top-level return as execution surface mismatch', async () => { + const result = await evaluate({ + program: { ...BASE_PROGRAM, code: 'return 1' }, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }); + + expect(result.ok).toBe(false); + if (result.ok) { + throw new Error('expected vm failure'); + } + expect(result.type).toBe('vm-error'); + expect(result.error.kind).toBe('execution-surface-mismatch'); + expect(result.error.code).toBe('EXECUTION_SURFACE_MISMATCH'); + expect('tag' in result.error ? result.error.tag : null).toBe( + 'vm/execution_surface', + ); + expect(result.error.message).toMatch(/return/i); + }); + + it('supports emit side effects in raw script mode', async () => { + const handlers = createHandlers(); + const result = await evaluate({ + program: { + ...BASE_PROGRAM, + code: 'emit({ marker: "raw-script" }); ({ status: "ok" })', + }, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers, + }); + + expect(result.ok).toBe(true); + if (!result.ok) { + throw new Error(result.message); + } + expect(result.value).toEqual({ status: 'ok' }); + expect(handlers.emit).toHaveBeenCalledTimes(1); + expect(handlers.emit).toHaveBeenCalledWith({ marker: 'raw-script' }); + }); + + it('keeps RegExp disabled in baseline profile and allows compat-regexp profile', async () => { + const baseline = await evaluate({ + program: { ...BASE_PROGRAM, code: '/a/.test("a")' }, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }); + + expect(baseline.ok).toBe(false); + if (baseline.ok) { + throw new Error('expected baseline regexp failure'); + } + expect(baseline.type).toBe('vm-error'); + expect(baseline.error.kind).toBe('js-exception'); + expect(baseline.message).toMatch(/regexp is disabled/i); + + const compat = await evaluate({ + program: { + ...BASE_PROGRAM, + code: '/a/.test("a")', + executionProfile: 'compat-regexp-v1', + }, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }); + + if (!compat.ok) { + throw new Error(compat.message); + } + expect(compat.ok).toBe(true); + expect(compat.value).toBe(true); + }); + + it('keeps Promise disabled in baseline profile and drains Promise jobs for compat-general', async () => { + const baseline = await evaluate({ + program: { ...BASE_PROGRAM, code: 'Promise.resolve(1)' }, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }); + + expect(baseline.ok).toBe(false); + if (baseline.ok) { + throw new Error('expected baseline Promise failure'); + } + expect(baseline.type).toBe('vm-error'); + expect(baseline.error.kind).toBe('js-exception'); + expect(baseline.message).toMatch(/promise is disabled/i); + + const compat = await evaluate({ + program: { + ...BASE_PROGRAM, + code: 'Promise.resolve(41).then((value) => value + 1)', + executionProfile: 'compat-general-v1', + }, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }); + + if (!compat.ok) { + throw new Error(compat.message); + } + expect(compat.ok).toBe(true); + expect(compat.value).toBe(42); + }); + + it('runs queueMicrotask deterministically in compat-general profile', async () => { + const compat = await evaluate({ + program: { + ...BASE_PROGRAM, + code: ` + (() => { + const events = []; + queueMicrotask(() => events.push('first')); + queueMicrotask(() => events.push('second')); + return Promise.resolve().then(() => events.join(',')); + })() + `, + executionProfile: 'compat-general-v1', + }, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }); + + if (!compat.ok) { + throw new Error( + `Host.v2 roundtrip failed: ${compat.type} ${compat.message}`, + ); + } + expect(compat.ok).toBe(true); + expect(compat.value).toBe('first,second'); + }); + + it('routes compat-general console shim calls through Host.v1.emit', async () => { + const handlers = createHandlers(); + const compat = await evaluate({ + program: { + ...BASE_PROGRAM, + code: ` + (() => { + console.log('hello', 7); + return null; + })() + `, + executionProfile: 'compat-general-v1', + }, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers, + }); + + expect(compat.ok).toBe(true); + if (!compat.ok) { + throw new Error(compat.message); + } + expect(compat.value).toBeNull(); + expect(handlers.emit).toHaveBeenCalledWith({ + type: 'console', + level: 'log', + args: ['hello', 7], + }); + }); + + it('supports Host.v2 DV2 byte roundtrips in compat-binary profile', async () => { + const handlers = createHandlers({ + document: { + get: vi.fn((path: string) => { + if (path !== 'bytes/payload') { + return { + err: { code: 'NOT_FOUND', tag: 'host/not_found' }, + units: 1, + }; + } + return { ok: Uint8Array.from([222, 173, 190, 239]), units: 2 }; + }), + }, + emit: vi.fn(() => ({ ok: null, units: 1 })), + }); + + const compat = await evaluate({ + program: { + ...BASE_PROGRAM_V2_BINARY, + code: ` + (() => { + const payload = Host.v2.document.get('bytes/payload'); + Host.v2.emit(payload); + return 1; + })() + `, + }, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V2_MANIFEST, + handlers, + }); + + if (!compat.ok) { + throw new Error( + `Host.v2 roundtrip failed: ${compat.type} ${compat.message}`, + ); + } + expect(compat.ok).toBe(true); + expect(compat.value).toBe(1); + expect(handlers.document.get).toHaveBeenCalledWith('bytes/payload'); + expect(handlers.emit).toHaveBeenCalledTimes(1); + if (!handlers.emit) { + throw new Error('expected emit handler'); + } + const emitMock = handlers.emit as ReturnType; + const [emitArg] = emitMock.mock.calls[0] ?? []; + expect(emitArg).toBeInstanceOf(Uint8Array); + expect(Array.from(emitArg as Uint8Array)).toEqual([222, 173, 190, 239]); + }); + + it('keeps sort disabled in baseline and enables stable sort in compat-general', async () => { + const baseline = await evaluate({ + program: { ...BASE_PROGRAM, code: '[3, 1, 2].sort()' }, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }); + + expect(baseline.ok).toBe(false); + if (baseline.ok) { + throw new Error('expected baseline sort failure'); + } + expect(baseline.type).toBe('vm-error'); + expect(baseline.error.kind).toBe('js-exception'); + expect(baseline.message).toMatch(/sort is disabled/i); + + const compat = await evaluate({ + program: { + ...BASE_PROGRAM, + code: ` + (() => { + const records = [ + { id: 'a', group: 1 }, + { id: 'b', group: 1 }, + { id: 'c', group: 2 }, + { id: 'd', group: 1 }, + ]; + records.sort((left, right) => left.group - right.group); + return records.map((record) => record.id).join(','); + })() + `, + executionProfile: 'compat-general-v1', + }, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }); + + expect(compat.ok).toBe(true); + if (!compat.ok) { + throw new Error(compat.message); + } + expect(compat.value).toBe('a,b,d,c'); + }); + it('returns DV results with gas accounting', async () => { const handlers = createHandlers(); const result = await evaluate({ @@ -213,6 +747,92 @@ describe('evaluate', () => { ).rejects.toThrow(/enginebuildhash/i); }); + it('rejects gasVersion mismatches', async () => { + const program: ProgramArtifact = { + ...BASE_PROGRAM, + gasVersion: 0, + }; + + await expect( + evaluate({ + program, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + }), + ).rejects.toThrow(/gasversion/i); + }); + + it('requires engine/gas/profile pins in release mode', async () => { + await expect( + evaluate({ + program: BASE_PROGRAM, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + releaseMode: true, + }), + ).rejects.toThrow(/release-mode requires/i); + }); + + it('requires expectedExecutionProfile in release mode', async () => { + const program: ProgramArtifact = { + ...BASE_PROGRAM, + engineBuildHash: '0'.repeat(64), + gasVersion: 0, + executionProfile: 'baseline-v1', + }; + + await expect( + evaluate({ + program, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + releaseMode: true, + }), + ).rejects.toThrow(/expectedexecutionprofile/i); + }); + + it('rejects executionProfile pin mismatches when expected profile is provided', async () => { + const program: ProgramArtifact = { + ...BASE_PROGRAM, + executionProfile: 'baseline-v1', + }; + + await expect( + evaluate({ + program, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + expectedExecutionProfile: 'compat-general-v1', + }), + ).rejects.toThrow(/executionprofile mismatch/i); + }); + + it('accepts matching expected executionProfile pin', async () => { + const program: ProgramArtifact = { + ...BASE_PROGRAM, + executionProfile: 'baseline-v1', + }; + + const result = await evaluate({ + program, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + expectedExecutionProfile: 'baseline-v1', + }); + + expect(result.ok).toBe(true); + }); + it('returns host-call tape when requested', async () => { const result = await evaluate({ program: BASE_PROGRAM, @@ -238,6 +858,29 @@ describe('evaluate', () => { expect(record.respHash).toHaveLength(64); }); + it('returns gas charge tape when requested', async () => { + const result = await evaluate({ + program: { ...BASE_PROGRAM, code: '1 + 2' }, + input: BASE_INPUT, + gasLimit: TEST_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + handlers: createHandlers(), + gasChargeTape: { capacity: 128 }, + }); + + expect(result.ok).toBe(true); + if (!result.ok) { + throw new Error(result.message); + } + + expect(result.gasChargeTape).toBeDefined(); + expect((result.gasChargeTape ?? []).length).toBeGreaterThan(0); + const [record] = result.gasChargeTape ?? []; + expect(typeof record.amount).toBe('bigint'); + expect(typeof record.gasBefore).toBe('bigint'); + expect(typeof record.gasAfter).toBe('bigint'); + }); + it('returns gas trace when requested', async () => { const result = await evaluate({ program: { ...BASE_PROGRAM, code: '1 + 2' }, @@ -255,6 +898,7 @@ describe('evaluate', () => { expect(result.gasTrace).toBeDefined(); expect((result.gasTrace?.opcodeCount ?? 0n) >= 0n).toBe(true); + expect((result.gasTrace?.allocationRequestedBytes ?? 0n) >= 0n).toBe(true); expect((result.gasTrace?.allocationBytes ?? 0n) >= 0n).toBe(true); expect((result.gasTrace?.jsonParseCount ?? 0n) >= 0n).toBe(true); expect((result.gasTrace?.jsonStringifyCount ?? 0n) >= 0n).toBe(true); @@ -554,3 +1198,77 @@ function getFnId(path: string): number { } return fn.fn_id; } + +function createModulePack(options: { + entrySpecifier: string; + modules: Array<{ specifier: string; source: string; sourceMap?: string }>; + entryExport?: string; +}) { + const base = { + version: 1 as const, + entrySpecifier: options.entrySpecifier, + ...(options.entryExport ? { entryExport: options.entryExport } : {}), + modules: options.modules, + builderVersion: 'deterministic-builder-v1', + dependencyIntegrity: + 'aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa', + }; + const canonical = { + version: base.version, + entrySpecifier: base.entrySpecifier, + entryExport: base.entryExport ?? 'default', + modules: [...base.modules] + .sort((left, right) => + compareUtf8ByteOrder(left.specifier, right.specifier), + ) + .map((module) => ({ + specifier: module.specifier, + source: module.source, + ...(module.sourceMap ? { sourceMap: module.sourceMap } : {}), + })), + builderVersion: base.builderVersion, + dependencyIntegrity: base.dependencyIntegrity, + }; + const graphHash = createHash('sha256') + .update(stableStringify(canonical), 'utf8') + .digest('hex'); + return { + ...base, + graphHash, + }; +} + +function stableStringify(value: unknown): string { + if (value === null || typeof value !== 'object') { + return JSON.stringify(value); + } + if (Array.isArray(value)) { + return `[${value.map((item) => stableStringify(item)).join(',')}]`; + } + const entries = Object.entries(value as Record) + .filter(([, item]) => item !== undefined) + .sort(([left], [right]) => compareUtf8ByteOrder(left, right)) + .map(([key, item]) => `${JSON.stringify(key)}:${stableStringify(item)}`); + return `{${entries.join(',')}}`; +} + +const UTF8_ENCODER = new TextEncoder(); + +function compareUtf8ByteOrder(left: string, right: string): number { + if (left === right) { + return 0; + } + + const leftBytes = UTF8_ENCODER.encode(left); + const rightBytes = UTF8_ENCODER.encode(right); + const limit = Math.min(leftBytes.length, rightBytes.length); + + for (let index = 0; index < limit; index += 1) { + const delta = leftBytes[index] - rightBytes[index]; + if (delta !== 0) { + return delta; + } + } + + return leftBytes.length - rightBytes.length; +} diff --git a/libs/quickjs-runtime/src/lib/evaluate.ts b/libs/quickjs-runtime/src/lib/evaluate.ts index 93c4316..dc75e8e 100644 --- a/libs/quickjs-runtime/src/lib/evaluate.ts +++ b/libs/quickjs-runtime/src/lib/evaluate.ts @@ -11,11 +11,15 @@ import type { HostDispatcherOptions, } from './host-dispatcher.js'; import { + type ExecutionProfile, type InputEnvelope, type InputValidationOptions, + type ModulePackV1, type ProgramArtifact, + type ProgramArtifactV2, validateInputEnvelope, validateProgramArtifact, + validateProgramArtifactV2, } from './quickjs-runtime.js'; import { type RuntimeArtifactSelection, @@ -29,10 +33,11 @@ import { type EvaluateVmErrorDetail, } from './evaluate-errors.js'; import { parseHexToBytes } from './hex-utils.js'; +import { remapModulePackErrorPayload } from './source-map-remap.js'; export interface EvaluateOptions extends RuntimeArtifactSelection, HostDispatcherOptions { - program: ProgramArtifact; + program: ProgramArtifact | ProgramArtifactV2; input: InputEnvelope; gasLimit: bigint | number; manifest: AbiManifest; @@ -50,6 +55,19 @@ export interface EvaluateOptions * Enable gas trace recording for the evaluation. */ gasTrace?: boolean; + /** + * Enable gas charge event tape recording (capacity defaults to 256; max 8192). + */ + gasChargeTape?: { capacity?: number }; + /** + * Enforce release-mode artifact pin requirements. + */ + releaseMode?: boolean; + /** + * Optional execution-profile pin asserted by the embedding runtime. + * When provided, evaluation rejects artifacts whose executionProfile differs. + */ + expectedExecutionProfile?: ExecutionProfile; } export type EvaluateSuccess = { @@ -59,6 +77,7 @@ export type EvaluateSuccess = { gasRemaining: bigint; raw: string; tape?: HostTapeRecord[]; + gasChargeTape?: GasChargeRecord[]; gasTrace?: GasTrace; }; @@ -70,6 +89,7 @@ type EvaluateFailureBase = { gasRemaining: bigint; raw: string; tape?: HostTapeRecord[]; + gasChargeTape?: GasChargeRecord[]; gasTrace?: GasTrace; }; @@ -88,12 +108,30 @@ export type EvaluateError = EvaluateVmError | EvaluateInvalidOutputError; export type EvaluateResult = EvaluateSuccess | EvaluateError; const HOST_TAPE_MAX_CAPACITY = 1024; +const GAS_CHARGE_TAPE_MAX_CAPACITY = 8192; export async function evaluate( options: EvaluateOptions, ): Promise { - const program = validateProgramArtifact(options.program); + const program = normalizeProgramForExecution(options.program); + if (program.mode === 'module-pack') { + await assertModulePackHash(program.modulePack); + } const input = validateInputEnvelope(options.input, options.inputValidation); + if (options.releaseMode) { + assertReleaseArtifactPins(program.legacyArtifact); + if (!options.expectedExecutionProfile) { + throw new Error( + 'release-mode requires expectedExecutionProfile to be provided', + ); + } + } + if (options.expectedExecutionProfile) { + assertExecutionProfile( + program.legacyArtifact, + options.expectedExecutionProfile, + ); + } const runtime = await createRuntime({ manifest: options.manifest, @@ -103,15 +141,16 @@ export async function evaluate( metadata: options.metadata, wasmBinary: options.wasmBinary, dvLimits: options.dvLimits, - expectedAbiId: program.abiId, - expectedAbiVersion: program.abiVersion, + expectedAbiId: program.legacyArtifact.abiId, + expectedAbiVersion: program.legacyArtifact.abiVersion, }); - assertEngineBuildHash(program, runtime); + assertEngineBuildHash(program.legacyArtifact, runtime); + assertGasVersion(program.legacyArtifact, runtime); const vm = initializeDeterministicVm( runtime, - program, + program.legacyArtifact, input, options.gasLimit, ); @@ -129,20 +168,50 @@ export async function evaluate( vm.enableTape(capacity); } + if (options.gasChargeTape) { + const capacity = options.gasChargeTape.capacity ?? 256; + if (!Number.isInteger(capacity) || capacity < 0) { + throw new Error( + 'gas charge tape capacity must be a non-negative integer', + ); + } + if (capacity > GAS_CHARGE_TAPE_MAX_CAPACITY) { + throw new Error( + `gas charge tape capacity exceeds max (${GAS_CHARGE_TAPE_MAX_CAPACITY}); received ${capacity}`, + ); + } + vm.enableGasChargeTape(capacity); + } + if (options.gasTrace) { vm.enableGasTrace(true); } try { - const raw = vm.eval(program.code); + const raw = + program.mode === 'script' + ? vm.eval(program.legacyArtifact.code) + : vm.evalModulePack( + serializeModulePackModules(program.modulePack), + program.modulePack.entrySpecifier, + program.entryExport, + ); const parsed = parseEvalOutput(raw); - const tape = options.tape ? parseTape(vm.readTape()) : undefined; const trace = options.gasTrace ? parseGasTrace(vm.readGasTrace()) : undefined; + const tape = options.tape ? parseTape(vm.readTape()) : undefined; + const gasChargeTape = options.gasChargeTape + ? parseGasChargeTape(vm.readGasChargeTape()) + : undefined; if (parsed.kind === 'error') { - const error = mapVmError(parsed.payload, runtime.manifest); + const payload = + program.mode === 'module-pack' + ? remapModulePackErrorPayload(parsed.payload, program.modulePack) + .payload + : parsed.payload; + const error = mapVmError(payload, runtime.manifest); return { ok: false, type: 'vm-error', @@ -152,6 +221,7 @@ export async function evaluate( gasRemaining: parsed.gasRemaining, raw, tape, + gasChargeTape, gasTrace: trace, }; } @@ -168,6 +238,7 @@ export async function evaluate( gasRemaining: parsed.gasRemaining, raw, tape, + gasChargeTape, gasTrace: trace, }; } @@ -179,6 +250,7 @@ export async function evaluate( gasRemaining: parsed.gasRemaining, raw, tape, + gasChargeTape, gasTrace: trace, }; } finally { @@ -277,6 +349,16 @@ export interface HostTapeRecord { respHash: string; } +export interface GasChargeRecord { + siteId: number; + kind: number; + flags: number; + amount: bigint; + logicalUnits: bigint; + gasBefore: bigint; + gasAfter: bigint; +} + function parseTape(raw: string): HostTapeRecord[] { const parsed = parseJson(raw, 'tape'); if (!Array.isArray(parsed)) { @@ -314,6 +396,49 @@ function parseTape(raw: string): HostTapeRecord[] { }); } +function parseGasChargeTape(raw: string): GasChargeRecord[] { + const parsed = parseJson(raw, 'gasChargeTape'); + if (!Array.isArray(parsed)) { + throw new Error('gasChargeTape payload is not an array'); + } + + return parsed.map((record, idx) => { + if (record === null || typeof record !== 'object') { + throw new Error(`gasChargeTape record ${idx} is not an object`); + } + + const siteId = expectUint32(record.siteId, `gasChargeTape[${idx}].siteId`); + const kind = expectUint32(record.kind, `gasChargeTape[${idx}].kind`); + const flags = expectUint32(record.flags, `gasChargeTape[${idx}].flags`); + const amount = expectBigIntString( + record.amount, + `gasChargeTape[${idx}].amount`, + ); + const logicalUnits = expectBigIntString( + record.logicalUnits, + `gasChargeTape[${idx}].logicalUnits`, + ); + const gasBefore = expectBigIntString( + record.gasBefore, + `gasChargeTape[${idx}].gasBefore`, + ); + const gasAfter = expectBigIntString( + record.gasAfter, + `gasChargeTape[${idx}].gasAfter`, + ); + + return { + siteId, + kind, + flags, + amount, + logicalUnits, + gasBefore, + gasAfter, + }; + }); +} + export interface GasTrace { opcodeCount: bigint; opcodeGas: bigint; @@ -322,6 +447,7 @@ export interface GasTrace { arrayCbPerElCount: bigint; arrayCbPerElGas: bigint; allocationCount: bigint; + allocationRequestedBytes: bigint; allocationBytes: bigint; allocationGas: bigint; jsonParseCount: bigint; @@ -337,6 +463,10 @@ export interface GasTrace { jsonStringifyObjectEntries: bigint; jsonStringifyArrayElements: bigint; jsonStringifySortComparisons: bigint; + hostCallPreCount: bigint; + hostCallPreGas: bigint; + hostCallPostCount: bigint; + hostCallPostGas: bigint; } function parseGasTrace(raw: string): GasTrace { @@ -365,6 +495,10 @@ function parseGasTrace(raw: string): GasTrace { obj.allocationCount, 'gasTrace.allocationCount', ), + allocationRequestedBytes: expectBigIntString( + obj.allocationRequestedBytes ?? obj.allocationBytes, + 'gasTrace.allocationRequestedBytes', + ), allocationBytes: expectBigIntString( obj.allocationBytes, 'gasTrace.allocationBytes', @@ -422,6 +556,22 @@ function parseGasTrace(raw: string): GasTrace { obj.jsonStringifySortComparisons, 'gasTrace.jsonStringifySortComparisons', ), + hostCallPreCount: expectBigIntString( + obj.hostCallPreCount, + 'gasTrace.hostCallPreCount', + ), + hostCallPreGas: expectBigIntString( + obj.hostCallPreGas, + 'gasTrace.hostCallPreGas', + ), + hostCallPostCount: expectBigIntString( + obj.hostCallPostCount, + 'gasTrace.hostCallPostCount', + ), + hostCallPostGas: expectBigIntString( + obj.hostCallPostGas, + 'gasTrace.hostCallPostGas', + ), }; } @@ -495,6 +645,8 @@ function normalizeDvLimits(overrides?: Partial): DvLimits { overrides?.maxEncodedBytes ?? DV_LIMIT_DEFAULTS.maxEncodedBytes, maxStringBytes: overrides?.maxStringBytes ?? DV_LIMIT_DEFAULTS.maxStringBytes, + maxByteStringBytes: + overrides?.maxByteStringBytes ?? DV_LIMIT_DEFAULTS.maxByteStringBytes, maxArrayLength: overrides?.maxArrayLength ?? DV_LIMIT_DEFAULTS.maxArrayLength, maxMapLength: overrides?.maxMapLength ?? DV_LIMIT_DEFAULTS.maxMapLength, @@ -516,7 +668,7 @@ function parseUint64(text: string, label: string): bigint { } function assertEngineBuildHash( - program: ProgramArtifact, + program: { engineBuildHash?: string }, runtime: RuntimeInstance, ): void { if (!program.engineBuildHash) { @@ -541,6 +693,246 @@ function assertEngineBuildHash( } } +function assertGasVersion( + program: { gasVersion?: number }, + runtime: RuntimeInstance, +): void { + if (program.gasVersion === undefined) { + return; + } + + const runtimeGasVersion = runtime.metadata.gasVersion; + if (runtimeGasVersion === null || runtimeGasVersion === undefined) { + throw new Error( + 'Runtime gasVersion is unavailable; cannot verify program.gasVersion', + ); + } + + if (runtimeGasVersion !== program.gasVersion) { + throw new Error( + `gasVersion mismatch: program=${program.gasVersion} runtime=${runtimeGasVersion}`, + ); + } +} + +function assertReleaseArtifactPins(program: { + engineBuildHash?: string; + gasVersion?: number; + executionProfile?: string; +}): void { + if (!program.engineBuildHash) { + throw new Error( + 'release-mode requires program.engineBuildHash to be provided', + ); + } + if (program.gasVersion === undefined) { + throw new Error('release-mode requires program.gasVersion to be provided'); + } + if (!program.executionProfile) { + throw new Error( + 'release-mode requires program.executionProfile to be provided', + ); + } +} + +function assertExecutionProfile( + program: { executionProfile?: string }, + expectedExecutionProfile: string, +): void { + if (!program.executionProfile) { + throw new Error( + 'executionProfile pin cannot be validated because program.executionProfile is missing', + ); + } + if (program.executionProfile !== expectedExecutionProfile) { + throw new Error( + `executionProfile mismatch: program=${program.executionProfile} runtime=${expectedExecutionProfile}`, + ); + } +} + +type NormalizedProgramForExecution = + | { + mode: 'script'; + legacyArtifact: ProgramArtifact; + } + | { + mode: 'module-pack'; + legacyArtifact: ProgramArtifact; + modulePack: ModulePackV1; + entryExport: string; + }; + +function normalizeProgramForExecution( + program: unknown, +): NormalizedProgramForExecution { + if (isProgramArtifactV2(program)) { + const validated = validateProgramArtifactV2(program); + if (validated.sourceKind === 'script') { + if (!('code' in validated.source)) { + throw new Error( + 'INVALID_PROGRAM: script source is missing code payload', + ); + } + + return { + mode: 'script', + legacyArtifact: { + code: validated.source.code, + abiId: validated.abiId, + abiVersion: validated.abiVersion, + abiManifestHash: validated.abiManifestHash, + ...(validated.engineBuildHash + ? { engineBuildHash: validated.engineBuildHash } + : {}), + ...(validated.gasVersion !== undefined + ? { gasVersion: validated.gasVersion } + : {}), + executionProfile: validated.executionProfile, + }, + }; + } + + if (!('modulePack' in validated.source)) { + throw new Error( + 'INVALID_PROGRAM: module-pack source is missing modulePack payload', + ); + } + + return { + mode: 'module-pack', + legacyArtifact: { + code: '', + abiId: validated.abiId, + abiVersion: validated.abiVersion, + abiManifestHash: validated.abiManifestHash, + ...(validated.engineBuildHash + ? { engineBuildHash: validated.engineBuildHash } + : {}), + ...(validated.gasVersion !== undefined + ? { gasVersion: validated.gasVersion } + : {}), + executionProfile: validated.executionProfile, + }, + modulePack: validated.source.modulePack, + entryExport: validated.source.modulePack.entryExport ?? 'default', + }; + } + + return { + mode: 'script', + legacyArtifact: validateProgramArtifact(program), + }; +} + +async function assertModulePackHash(modulePack: ModulePackV1): Promise { + const computed = await computeModulePackGraphHash(modulePack); + if (computed !== modulePack.graphHash) { + throw new Error( + `MODULE_PACK_HASH_MISMATCH: expected=${modulePack.graphHash} computed=${computed}`, + ); + } +} + +async function computeModulePackGraphHash( + modulePack: ModulePackV1, +): Promise { + const canonical = { + version: modulePack.version, + entrySpecifier: modulePack.entrySpecifier, + entryExport: modulePack.entryExport ?? 'default', + modules: [...modulePack.modules] + .sort((left, right) => + compareUtf8ByteOrder(left.specifier, right.specifier), + ) + .map((module) => ({ + specifier: module.specifier, + source: module.source, + ...(module.sourceMap ? { sourceMap: module.sourceMap } : {}), + })), + builderVersion: modulePack.builderVersion, + dependencyIntegrity: modulePack.dependencyIntegrity, + }; + const payload = new TextEncoder().encode(stableStringify(canonical)); + const subtle = getSubtleCrypto(); + const digest = await subtle.digest('SHA-256', payload); + return [...new Uint8Array(digest)] + .map((byte) => byte.toString(16).padStart(2, '0')) + .join(''); +} + +function serializeModulePackModules(modulePack: ModulePackV1): string { + return JSON.stringify( + modulePack.modules.map((module) => ({ + specifier: module.specifier, + source: module.source, + })), + ); +} + +function stableStringify(value: unknown): string { + if (value === null || typeof value !== 'object') { + return JSON.stringify(value); + } + if (Array.isArray(value)) { + return `[${value.map((item) => stableStringify(item)).join(',')}]`; + } + + const entries = Object.entries(value as Record) + .filter(([, item]) => item !== undefined) + .sort(([left], [right]) => compareUtf8ByteOrder(left, right)) + .map(([key, item]) => `${JSON.stringify(key)}:${stableStringify(item)}`); + return `{${entries.join(',')}}`; +} + +const UTF8_ENCODER = new TextEncoder(); + +function compareUtf8ByteOrder(left: string, right: string): number { + if (left === right) { + return 0; + } + + const leftBytes = UTF8_ENCODER.encode(left); + const rightBytes = UTF8_ENCODER.encode(right); + const limit = Math.min(leftBytes.length, rightBytes.length); + + for (let index = 0; index < limit; index += 1) { + const delta = leftBytes[index] - rightBytes[index]; + if (delta !== 0) { + return delta; + } + } + + return leftBytes.length - rightBytes.length; +} + +type SubtleDigestApi = { + digest( + algorithm: string, + data: ArrayBuffer | ArrayBufferView, + ): Promise; +}; + +function getSubtleCrypto(): SubtleDigestApi { + const subtle = + globalThis.crypto && 'subtle' in globalThis.crypto + ? globalThis.crypto.subtle + : null; + if (!subtle) { + throw new Error( + 'MODULE_PACK_HASH_MISMATCH: crypto.subtle is unavailable for graph hash verification', + ); + } + return subtle; +} + +function isProgramArtifactV2(value: unknown): value is ProgramArtifactV2 { + if (value === null || typeof value !== 'object' || Array.isArray(value)) { + return false; + } + return (value as { version?: unknown }).version === 2; +} + export type { EvaluateInvalidOutputDetail, EvaluateVmErrorDetail, diff --git a/libs/quickjs-runtime/src/lib/host-dispatcher.spec.ts b/libs/quickjs-runtime/src/lib/host-dispatcher.spec.ts index 3496301..d51ef7e 100644 --- a/libs/quickjs-runtime/src/lib/host-dispatcher.spec.ts +++ b/libs/quickjs-runtime/src/lib/host-dispatcher.spec.ts @@ -1,5 +1,5 @@ -import { encodeDv, decodeDv } from '@blue-quickjs/dv'; -import { HOST_V1_MANIFEST } from '@blue-quickjs/abi-manifest'; +import { decodeDv, decodeDv2, encodeDv, encodeDv2 } from '@blue-quickjs/dv'; +import { HOST_V1_MANIFEST, HOST_V2_MANIFEST } from '@blue-quickjs/abi-manifest'; import { type DocumentHostHandlers, type EmitHostHandler, @@ -10,9 +10,10 @@ import { createHostDispatcher, } from './host-dispatcher.js'; -const DOC_GET_ID = getFnId('document.get'); -const DOC_GET_CANONICAL_ID = getFnId('document.getCanonical'); -const EMIT_ID = getFnId('emit'); +const DOC_GET_ID = getFnId(HOST_V1_MANIFEST, 'document.get'); +const DOC_GET_CANONICAL_ID = getFnId(HOST_V1_MANIFEST, 'document.getCanonical'); +const EMIT_ID = getFnId(HOST_V1_MANIFEST, 'emit'); +const DOC_GET_ID_V2 = getFnId(HOST_V2_MANIFEST, 'document.get'); const UINT32_MAX = 0xffffffff; describe('host dispatcher', () => { @@ -189,6 +190,35 @@ describe('host dispatcher', () => { const written = hostCall(DOC_GET_ID, 0, request.length, 64, 128); expect(written).toBeGreaterThan(0); }); + + it('supports Host.v2 byte-string payloads via DV2', () => { + const handlers = createHandlers({ + get: vi.fn((path: string) => { + if (path !== 'bytes/path') { + return { + err: { code: 'NOT_FOUND', tag: 'host/not_found' }, + units: 1, + }; + } + return { ok: Uint8Array.from([0xde, 0xad, 0xbe, 0xef]), units: 2 }; + }), + }); + const dispatcher = createHostDispatcher(HOST_V2_MANIFEST, handlers, { + expectedAbiId: 'Host.v2', + expectedAbiVersion: 2, + }); + + const request = encodeDv2(['bytes/path']); + const result = dispatcher.dispatch(DOC_GET_ID_V2, request); + expect(result.kind).toBe('response'); + + const envelope = decodeDv2( + (result as Extract).envelope, + ) as { ok: Uint8Array; units: number }; + expect(envelope.units).toBe(2); + expect(envelope.ok).toBeInstanceOf(Uint8Array); + expect(Array.from(envelope.ok)).toEqual([0xde, 0xad, 0xbe, 0xef]); + }); }); function expectResponse(result: HostDispatchResult): { @@ -237,8 +267,11 @@ function createHandlers( }; } -function getFnId(path: string): number { - const fn = HOST_V1_MANIFEST.functions.find( +function getFnId( + manifest: { functions: Array<{ fn_id: number; js_path: string[] }> }, + path: string, +): number { + const fn = manifest.functions.find( (entry) => entry.js_path.join('.') === path, ); if (!fn) { diff --git a/libs/quickjs-runtime/src/lib/host-dispatcher.ts b/libs/quickjs-runtime/src/lib/host-dispatcher.ts index 5eaf158..5352071 100644 --- a/libs/quickjs-runtime/src/lib/host-dispatcher.ts +++ b/libs/quickjs-runtime/src/lib/host-dispatcher.ts @@ -5,13 +5,16 @@ import { validateAbiManifest, } from '@blue-quickjs/abi-manifest'; import { - type DV, + type DV2, DV_LIMIT_DEFAULTS, type DvLimits, DvError, decodeDv, + decodeDv2, encodeDv, + encodeDv2, validateDv, + validateDv2, } from '@blue-quickjs/dv'; const UINT32_MAX = 0xffffffff; @@ -20,20 +23,20 @@ const UTF8 = new TextEncoder(); export interface HostCallError { code: string; tag: string; - details?: DV; + details?: DV2; } -export type HostCallResult = +export type HostCallResult = | { ok: T; units: number } | { err: HostCallError; units: number }; export interface DocumentHostHandlers { - get(path: string): HostCallResult; - getCanonical(path: string): HostCallResult; + get(path: string): HostCallResult; + getCanonical(path: string): HostCallResult; } export interface EmitHostHandler { - emit(value: DV): HostCallResult; + emit(value: DV2): HostCallResult; } export interface HostDispatcherHandlers { @@ -118,6 +121,7 @@ export function createHostDispatcher( } const dvLimits = normalizeDvLimits(options?.dvLimits); + const dvCodec = selectDvCodec(canonical); const bindings = buildBindings(canonical.functions, handlers); return { @@ -138,6 +142,7 @@ export function createHostDispatcher( return encodeEnvelope( binding.fn, binding.limitExceededEnvelope, + dvCodec, dvLimits, ); } @@ -152,9 +157,9 @@ export function createHostDispatcher( ), }; - let args: DV; + let args: DV2; try { - args = decodeDv(request, { limits: decodeLimits }); + args = decodeRequest(request, decodeLimits, dvCodec); } catch (err) { return fatal( 'INVALID_REQUEST', @@ -177,7 +182,7 @@ export function createHostDispatcher( } try { - return binding.dispatch(args, dvLimits); + return binding.dispatch(args, dvLimits, dvCodec); } catch (err) { return fatal( 'HANDLER_ERROR', @@ -241,7 +246,7 @@ export function createHostCallImport( type HostFunctionBinding = { fn: CanonicalFunction; - dispatch(args: DV[], dvLimits: DvLimits): HostDispatchResult; + dispatch(args: DV2[], dvLimits: DvLimits, codec: DvCodec): HostDispatchResult; limitExceededEnvelope?: HostResponseEnvelope; }; @@ -250,8 +255,16 @@ type CanonicalFunction = AbiFunction & { }; type HostResponseEnvelope = - | { ok: DV; units: number } - | { err: { code: string; details?: DV }; units: number }; + | { ok: DV2; units: number } + | { err: { code: string; details?: DV2 }; units: number }; + +type DvCodec = 'dv1' | 'dv2'; + +function selectDvCodec(manifest: CanonicalAbiManifest): DvCodec { + return manifest.abi_id === 'Host.v2' && manifest.abi_version >= 2 + ? 'dv2' + : 'dv1'; +} function buildBindings( functions: AbiFunction[], @@ -269,7 +282,7 @@ function buildBindings( if (!documentGet || !documentGetCanonical) { throw new HostDispatcherError( 'INVALID_REQUEST', - 'Host.v1 manifest must include document.get and document.getCanonical', + 'manifest must include document.get and document.getCanonical', ); } @@ -321,7 +334,11 @@ function buildDocumentBinding( return { fn, limitExceededEnvelope, - dispatch(args: DV[], dvLimits: DvLimits): HostDispatchResult { + dispatch( + args: DV2[], + dvLimits: DvLimits, + codec: DvCodec, + ): HostDispatchResult { const [path] = args; if (typeof path !== 'string') { return fatal( @@ -335,7 +352,7 @@ function buildDocumentBinding( const byteLen = UTF8.encode(path).byteLength; if (byteLen > utf8Max) { if (limitExceededEnvelope) { - return encodeEnvelope(fn, limitExceededEnvelope, dvLimits); + return encodeEnvelope(fn, limitExceededEnvelope, codec, dvLimits); } return fatal( 'INVALID_ARGUMENTS', @@ -345,7 +362,7 @@ function buildDocumentBinding( } const result = handler(path); - return encodeResult(fn, result, dvLimits, limitExceededEnvelope); + return encodeResult(fn, result, dvLimits, codec, limitExceededEnvelope); }, }; } @@ -359,10 +376,14 @@ function buildEmitBinding( return { fn, limitExceededEnvelope, - dispatch(args: DV[], dvLimits: DvLimits): HostDispatchResult { + dispatch( + args: DV2[], + dvLimits: DvLimits, + codec: DvCodec, + ): HostDispatchResult { const [value] = args; const result = handler(value); - return encodeResult(fn, result, dvLimits, limitExceededEnvelope); + return encodeResult(fn, result, dvLimits, codec, limitExceededEnvelope); }, }; } @@ -371,6 +392,7 @@ function encodeResult( fn: CanonicalFunction, result: HostCallResult, dvLimits: DvLimits, + codec: DvCodec, limitExceededEnvelope?: HostResponseEnvelope, ): HostDispatchResult { if (result === null || typeof result !== 'object') { @@ -406,7 +428,7 @@ function encodeResult( } if (units === null) { if (limitExceededEnvelope) { - return encodeEnvelope(fn, limitExceededEnvelope, dvLimits); + return encodeEnvelope(fn, limitExceededEnvelope, codec, dvLimits); } return fatal( 'INVALID_ARGUMENTS', @@ -423,13 +445,14 @@ function encodeResult( } if (fn.return_schema.type === 'dv') { try { - validateDv(result.ok, { + validateHostValue(result.ok, codec, { limits: cappedDvLimits(dvLimits, fn.limits.max_response_bytes), }); } catch (err) { return handleDvValidationError( fn, err, + codec, limitExceededEnvelope, dvLimits, ); @@ -439,6 +462,7 @@ function encodeResult( return encodeEnvelope( fn, { ok: result.ok, units }, + codec, dvLimits, limitExceededEnvelope, ); @@ -471,11 +495,17 @@ function encodeResult( if (result.err.details !== undefined) { try { - validateDv(result.err.details, { + validateHostValue(result.err.details, codec, { limits: cappedDvLimits(dvLimits, fn.limits.max_response_bytes), }); } catch (err) { - return handleDvValidationError(fn, err, limitExceededEnvelope, dvLimits); + return handleDvValidationError( + fn, + err, + codec, + limitExceededEnvelope, + dvLimits, + ); } } @@ -488,6 +518,7 @@ function encodeResult( : { code: result.err.code, details: result.err.details }, units, }, + codec, dvLimits, limitExceededEnvelope, ); @@ -496,17 +527,20 @@ function encodeResult( function encodeEnvelope( fn: CanonicalFunction, envelope: HostResponseEnvelope, + codec: DvCodec, dvLimits: DvLimits, limitExceededEnvelope?: HostResponseEnvelope, ): HostDispatchResult { const encodeLimits = cappedDvLimits(dvLimits, fn.limits.max_response_bytes); try { - const bytes = encodeDv(envelope, { limits: encodeLimits }); + const bytes = encodeHostValue(envelope, codec, { limits: encodeLimits }); return { kind: 'response', envelope: bytes }; } catch (err) { if (limitExceededEnvelope && isSizeRelatedDvError(err)) { try { - const bytes = encodeDv(limitExceededEnvelope, { limits: encodeLimits }); + const bytes = encodeHostValue(limitExceededEnvelope, codec, { + limits: encodeLimits, + }); return { kind: 'response', envelope: bytes }; } catch (limitErr) { return fatal( @@ -579,11 +613,12 @@ function assertEmitShape(fn: CanonicalFunction): void { function handleDvValidationError( fn: CanonicalFunction, err: unknown, + codec: DvCodec, limitExceededEnvelope: HostResponseEnvelope | undefined, dvLimits: DvLimits, ): HostDispatchResult { if (limitExceededEnvelope && isSizeRelatedDvError(err)) { - return encodeEnvelope(fn, limitExceededEnvelope, dvLimits); + return encodeEnvelope(fn, limitExceededEnvelope, codec, dvLimits); } return fatal( 'HANDLER_ERROR', @@ -592,6 +627,36 @@ function handleDvValidationError( ); } +function decodeRequest( + bytes: Uint8Array, + limits: DvLimits, + codec: DvCodec, +): DV2 { + return codec === 'dv2' + ? decodeDv2(bytes, { limits }) + : (decodeDv(bytes, { limits }) as DV2); +} + +function validateHostValue( + value: unknown, + codec: DvCodec, + options: { limits: DvLimits }, +): void { + if (codec === 'dv2') { + validateDv2(value, options); + return; + } + validateDv(value, options); +} + +function encodeHostValue( + value: unknown, + codec: DvCodec, + options: { limits: DvLimits }, +): Uint8Array { + return codec === 'dv2' ? encodeDv2(value, options) : encodeDv(value, options); +} + function cappedDvLimits(limits: DvLimits, maxBytes: number): DvLimits { return { ...limits, @@ -605,6 +670,8 @@ function normalizeDvLimits(limits?: Partial): DvLimits { maxEncodedBytes: limits?.maxEncodedBytes ?? DV_LIMIT_DEFAULTS.maxEncodedBytes, maxStringBytes: limits?.maxStringBytes ?? DV_LIMIT_DEFAULTS.maxStringBytes, + maxByteStringBytes: + limits?.maxByteStringBytes ?? DV_LIMIT_DEFAULTS.maxByteStringBytes, maxArrayLength: limits?.maxArrayLength ?? DV_LIMIT_DEFAULTS.maxArrayLength, maxMapLength: limits?.maxMapLength ?? DV_LIMIT_DEFAULTS.maxMapLength, }; @@ -683,6 +750,7 @@ function isSizeRelatedDvError(err: unknown): boolean { err instanceof DvError && (err.code === 'ENCODED_TOO_LARGE' || err.code === 'STRING_TOO_LONG' || + err.code === 'BYTE_STRING_TOO_LONG' || err.code === 'ARRAY_TOO_LONG' || err.code === 'MAP_TOO_LONG' || err.code === 'DEPTH_EXCEEDED') diff --git a/libs/quickjs-runtime/src/lib/quickjs-runtime.spec.ts b/libs/quickjs-runtime/src/lib/quickjs-runtime.spec.ts index fc9e38f..8333db9 100644 --- a/libs/quickjs-runtime/src/lib/quickjs-runtime.spec.ts +++ b/libs/quickjs-runtime/src/lib/quickjs-runtime.spec.ts @@ -3,9 +3,11 @@ import { InputEnvelope, PROGRAM_LIMIT_DEFAULTS, ProgramArtifact, + ProgramArtifactV2, RuntimeValidationError, validateInputEnvelope, validateProgramArtifact, + validateProgramArtifactV2, } from './quickjs-runtime.js'; const SAMPLE_HASH = @@ -58,6 +60,143 @@ describe('validateProgramArtifact', () => { }), ).toThrow(RuntimeValidationError); }); + + it('accepts supported execution profiles', () => { + expect( + validateProgramArtifact({ + ...baseProgram, + executionProfile: 'baseline-v1', + }), + ).toMatchObject({ executionProfile: 'baseline-v1' }); + + expect( + validateProgramArtifact({ + ...baseProgram, + executionProfile: 'compat-regexp-v1', + }), + ).toMatchObject({ executionProfile: 'compat-regexp-v1' }); + + expect( + validateProgramArtifact({ + ...baseProgram, + executionProfile: 'compat-general-v1', + }), + ).toMatchObject({ executionProfile: 'compat-general-v1' }); + + expect( + validateProgramArtifact({ + ...baseProgram, + executionProfile: 'compat-binary-v1', + }), + ).toMatchObject({ executionProfile: 'compat-binary-v1' }); + }); + + it('rejects unsupported execution profiles', () => { + expect(() => + validateProgramArtifact({ + ...baseProgram, + executionProfile: + 'compat-unknown' as unknown as ProgramArtifact['executionProfile'], + }), + ).toThrow(RuntimeValidationError); + }); + + it('accepts uint32 gasVersion values', () => { + expect( + validateProgramArtifact({ + ...baseProgram, + gasVersion: 3, + }), + ).toMatchObject({ gasVersion: 3 }); + }); + + it('rejects invalid gasVersion values', () => { + expect(() => + validateProgramArtifact({ + ...baseProgram, + gasVersion: -1, + }), + ).toThrow(RuntimeValidationError); + + expect(() => + validateProgramArtifact({ + ...baseProgram, + gasVersion: 1.5, + }), + ).toThrow(RuntimeValidationError); + }); +}); + +describe('validateProgramArtifactV2', () => { + const baseProgramV2: ProgramArtifactV2 = { + version: 2, + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: SAMPLE_HASH, + executionProfile: 'baseline-v1', + sourceKind: 'script', + source: { + code: '42', + }, + }; + + it('accepts script source artifacts', () => { + expect(validateProgramArtifactV2(baseProgramV2)).toEqual(baseProgramV2); + }); + + it('accepts module-pack source artifacts', () => { + const modulePack = validateProgramArtifactV2({ + ...baseProgramV2, + sourceKind: 'module-pack', + source: { + modulePack: { + version: 1, + entrySpecifier: './entry.js', + modules: [ + { + specifier: './entry.js', + source: 'export default 42;\n', + }, + ], + graphHash: SAMPLE_HASH, + builderVersion: 'deterministic-builder-v1', + dependencyIntegrity: SAMPLE_HASH, + }, + }, + }); + + expect(modulePack.sourceKind).toBe('module-pack'); + }); + + it('rejects source kind/source shape mismatch', () => { + expect(() => + validateProgramArtifactV2({ + ...baseProgramV2, + sourceKind: 'script', + source: { + modulePack: {}, + }, + }), + ).toThrow(RuntimeValidationError); + }); + + it('accepts uint32 gasVersion values', () => { + expect( + validateProgramArtifactV2({ + ...baseProgramV2, + gasVersion: 3, + }), + ).toMatchObject({ gasVersion: 3 }); + }); + + it('rejects invalid gasVersion values', () => { + expect(() => + validateProgramArtifactV2({ + ...baseProgramV2, + gasVersion: -1, + }), + ).toThrow(RuntimeValidationError); + }); }); describe('validateInputEnvelope', () => { diff --git a/libs/quickjs-runtime/src/lib/quickjs-runtime.ts b/libs/quickjs-runtime/src/lib/quickjs-runtime.ts index 2320da5..cce3a80 100644 --- a/libs/quickjs-runtime/src/lib/quickjs-runtime.ts +++ b/libs/quickjs-runtime/src/lib/quickjs-runtime.ts @@ -5,16 +5,68 @@ import { DvLimits, validateDv, } from '@blue-quickjs/dv'; +import { + isKnownExecutionProfile, + type PublicExecutionProfile, +} from '@blue-quickjs/execution-profiles'; const UINT32_MAX = 0xffffffff; const SHA256_HEX_LENGTH = 64; const HEX_RE = /^[0-9a-f]+$/; + +export type ExecutionProfile = PublicExecutionProfile; + +export interface ModulePackV1Module { + specifier: string; + source: string; + sourceMap?: string; + originMeta?: { + packageName?: string; + packageVersion?: string; + integrity?: string; + originalPath?: string; + }; +} + +export interface ModulePackV1 { + version: 1; + entrySpecifier: string; + entryExport?: string; + modules: ModulePackV1Module[]; + graphHash: string; + builderVersion: string; + dependencyIntegrity: string; + diagnosticsMeta?: Record; +} + +export interface ProgramArtifactV2ScriptSource { + code: string; +} + +export interface ProgramArtifactV2ModulePackSource { + modulePack: ModulePackV1; +} + +export interface ProgramArtifactV2 { + version: 2; + abiId: string; + abiVersion: number; + abiManifestHash: string; + engineBuildHash?: string; + gasVersion?: number; + executionProfile: ExecutionProfile; + sourceKind: 'script' | 'module-pack'; + source: ProgramArtifactV2ScriptSource | ProgramArtifactV2ModulePackSource; +} + export interface ProgramArtifact { code: string; abiId: string; abiVersion: number; abiManifestHash: string; engineBuildHash?: string; + gasVersion?: number; + executionProfile?: ExecutionProfile; } export interface ProgramArtifactLimits { @@ -45,6 +97,7 @@ export interface InputValidationOptions { export type RuntimeValidationErrorCode = | 'INVALID_TYPE' + | 'INVALID_VALUE' | 'MISSING_FIELD' | 'UNKNOWN_FIELD' | 'EMPTY_STRING' @@ -73,8 +126,17 @@ export function validateProgramArtifact( const program = expectPlainObject(value, 'program'); enforceExactKeys( program, - ['code', 'abiId', 'abiVersion', 'abiManifestHash', 'engineBuildHash'], + [ + 'code', + 'abiId', + 'abiVersion', + 'abiManifestHash', + 'engineBuildHash', + 'gasVersion', + 'executionProfile', + ], 'program', + ['engineBuildHash', 'gasVersion', 'executionProfile'], ); const code = expectString(program.code, 'program.code', { @@ -101,6 +163,17 @@ export function validateProgramArtifact( exactLength: SHA256_HEX_LENGTH, }) : undefined; + const gasVersion = + program.gasVersion !== undefined + ? expectUint(program.gasVersion, 0, UINT32_MAX, 'program.gasVersion') + : undefined; + const executionProfile = + program.executionProfile !== undefined + ? expectExecutionProfile( + program.executionProfile, + 'program.executionProfile', + ) + : undefined; return { code, @@ -108,6 +181,84 @@ export function validateProgramArtifact( abiVersion, abiManifestHash, engineBuildHash, + gasVersion, + executionProfile, + }; +} + +export function validateProgramArtifactV2( + value: unknown, + options?: ProgramValidationOptions, +): ProgramArtifactV2 { + const limits = normalizeProgramLimits(options?.limits); + const artifact = expectPlainObject(value, 'program'); + enforceExactKeys( + artifact, + [ + 'version', + 'abiId', + 'abiVersion', + 'abiManifestHash', + 'engineBuildHash', + 'gasVersion', + 'executionProfile', + 'sourceKind', + 'source', + ], + 'program', + ['engineBuildHash', 'gasVersion'], + ); + + const version = expectUint(artifact.version, 2, 2, 'program.version') as 2; + const abiId = expectString(artifact.abiId, 'program.abiId', { + maxLength: limits.maxAbiIdLength, + }); + const abiVersion = expectUint( + artifact.abiVersion, + 1, + UINT32_MAX, + 'program.abiVersion', + ); + const abiManifestHash = expectHexString( + artifact.abiManifestHash, + 'program.abiManifestHash', + { exactLength: SHA256_HEX_LENGTH }, + ); + const engineBuildHash = + artifact.engineBuildHash !== undefined + ? expectHexString(artifact.engineBuildHash, 'program.engineBuildHash', { + exactLength: SHA256_HEX_LENGTH, + }) + : undefined; + const gasVersion = + artifact.gasVersion !== undefined + ? expectUint(artifact.gasVersion, 0, UINT32_MAX, 'program.gasVersion') + : undefined; + const executionProfile = expectExecutionProfile( + artifact.executionProfile, + 'program.executionProfile', + ); + const sourceKind = expectSourceKind( + artifact.sourceKind, + 'program.sourceKind', + ); + const source = validateProgramV2Source( + artifact.source, + sourceKind, + limits, + 'program.source', + ); + + return { + version, + abiId, + abiVersion, + abiManifestHash, + ...(engineBuildHash ? { engineBuildHash } : {}), + ...(gasVersion !== undefined ? { gasVersion } : {}), + executionProfile, + sourceKind, + source, }; } @@ -127,6 +278,7 @@ export function validateInputEnvelope( 'currentContractCanonical', ], 'input', + ['currentContract', 'currentContractCanonical'], ); const event = validateDvField(input.event, dvLimits, 'input.event'); @@ -198,7 +350,21 @@ function enforceExactKeys( value: Record, allowed: string[], path: string, + optional: string[] = [], ): void { + for (const requiredKey of allowed) { + if (optional.includes(requiredKey)) { + continue; + } + if (!(requiredKey in value)) { + throw runtimeError( + 'MISSING_FIELD', + `${path} is missing required field "${requiredKey}"`, + `${path}.${requiredKey}`, + ); + } + } + for (const key of Object.keys(value)) { if (!allowed.includes(key)) { throw runtimeError( @@ -286,6 +452,192 @@ function expectUint( return value; } +function expectExecutionProfile( + value: unknown, + path: string, +): ExecutionProfile { + if (!isKnownExecutionProfile(value)) { + throw runtimeError( + 'INVALID_VALUE', + `${path} must be one of baseline-v1, compat-regexp-v1, compat-general-v1, compat-binary-v1`, + path, + ); + } + return value; +} + +function expectSourceKind( + value: unknown, + path: string, +): 'script' | 'module-pack' { + if (value !== 'script' && value !== 'module-pack') { + throw runtimeError( + 'INVALID_VALUE', + `${path} must be "script" or "module-pack"`, + path, + ); + } + return value; +} + +function validateProgramV2Source( + value: unknown, + sourceKind: 'script' | 'module-pack', + limits: ProgramArtifactLimits, + path: string, +): ProgramArtifactV2ScriptSource | ProgramArtifactV2ModulePackSource { + const source = expectPlainObject(value, path); + if (sourceKind === 'script') { + enforceExactKeys(source, ['code'], path); + return { + code: expectString(source.code, `${path}.code`, { + maxLength: limits.maxCodeUnits, + allowEmpty: true, + }), + }; + } + + enforceExactKeys(source, ['modulePack'], path); + return { + modulePack: validateModulePackV1(source.modulePack, `${path}.modulePack`), + }; +} + +function validateModulePackV1(value: unknown, path: string): ModulePackV1 { + const pack = expectPlainObject(value, path); + enforceExactKeys( + pack, + [ + 'version', + 'entrySpecifier', + 'entryExport', + 'modules', + 'graphHash', + 'builderVersion', + 'dependencyIntegrity', + 'diagnosticsMeta', + ], + path, + ['entryExport', 'diagnosticsMeta'], + ); + + const version = expectUint(pack.version, 1, 1, `${path}.version`) as 1; + const entrySpecifier = expectString( + pack.entrySpecifier, + `${path}.entrySpecifier`, + ); + const entryExport = + pack.entryExport !== undefined + ? expectString(pack.entryExport, `${path}.entryExport`) + : undefined; + const modules = expectArray(pack.modules, `${path}.modules`).map( + (moduleValue, index) => + validateModulePackModule(moduleValue, `${path}.modules[${index}]`), + ); + const graphHash = expectHexString(pack.graphHash, `${path}.graphHash`, { + exactLength: SHA256_HEX_LENGTH, + }); + const builderVersion = expectString( + pack.builderVersion, + `${path}.builderVersion`, + ); + const dependencyIntegrity = expectHexString( + pack.dependencyIntegrity, + `${path}.dependencyIntegrity`, + { + exactLength: SHA256_HEX_LENGTH, + }, + ); + + return { + version, + entrySpecifier, + ...(entryExport ? { entryExport } : {}), + modules, + graphHash, + builderVersion, + dependencyIntegrity, + ...(pack.diagnosticsMeta !== undefined + ? { + diagnosticsMeta: expectRecord( + pack.diagnosticsMeta, + `${path}.diagnosticsMeta`, + ), + } + : {}), + }; +} + +function validateModulePackModule( + value: unknown, + path: string, +): ModulePackV1Module { + const module = expectPlainObject(value, path); + enforceExactKeys( + module, + ['specifier', 'source', 'sourceMap', 'originMeta'], + path, + ['sourceMap', 'originMeta'], + ); + + const originMeta = + module.originMeta !== undefined + ? validateModulePackOriginMeta(module.originMeta, `${path}.originMeta`) + : undefined; + + return { + specifier: expectString(module.specifier, `${path}.specifier`), + source: expectString(module.source, `${path}.source`, { allowEmpty: true }), + ...(module.sourceMap !== undefined + ? { sourceMap: expectString(module.sourceMap, `${path}.sourceMap`) } + : {}), + ...(originMeta ? { originMeta } : {}), + }; +} + +function validateModulePackOriginMeta( + value: unknown, + path: string, +): NonNullable { + const originMeta = expectPlainObject(value, path); + enforceExactKeys( + originMeta, + ['packageName', 'packageVersion', 'integrity', 'originalPath'], + path, + ['packageName', 'packageVersion', 'integrity', 'originalPath'], + ); + + return { + ...(originMeta.packageName !== undefined + ? { + packageName: expectString( + originMeta.packageName, + `${path}.packageName`, + ), + } + : {}), + ...(originMeta.packageVersion !== undefined + ? { + packageVersion: expectString( + originMeta.packageVersion, + `${path}.packageVersion`, + ), + } + : {}), + ...(originMeta.integrity !== undefined + ? { integrity: expectString(originMeta.integrity, `${path}.integrity`) } + : {}), + ...(originMeta.originalPath !== undefined + ? { + originalPath: expectString( + originMeta.originalPath, + `${path}.originalPath`, + ), + } + : {}), + }; +} + function normalizeProgramLimits( overrides?: Partial, ): ProgramArtifactLimits { @@ -297,6 +649,20 @@ function normalizeProgramLimits( }; } +function expectArray(value: unknown, path: string): unknown[] { + if (!Array.isArray(value)) { + throw runtimeError('INVALID_TYPE', `${path} must be an array`, path); + } + return value; +} + +function expectRecord(value: unknown, path: string): Record { + if (value === null || typeof value !== 'object' || Array.isArray(value)) { + throw runtimeError('INVALID_TYPE', `${path} must be an object`, path); + } + return value as Record; +} + function normalizeDvLimits(overrides?: Partial): DvLimits { return { maxDepth: overrides?.maxDepth ?? DV_LIMIT_DEFAULTS.maxDepth, @@ -304,6 +670,8 @@ function normalizeDvLimits(overrides?: Partial): DvLimits { overrides?.maxEncodedBytes ?? DV_LIMIT_DEFAULTS.maxEncodedBytes, maxStringBytes: overrides?.maxStringBytes ?? DV_LIMIT_DEFAULTS.maxStringBytes, + maxByteStringBytes: + overrides?.maxByteStringBytes ?? DV_LIMIT_DEFAULTS.maxByteStringBytes, maxArrayLength: overrides?.maxArrayLength ?? DV_LIMIT_DEFAULTS.maxArrayLength, maxMapLength: overrides?.maxMapLength ?? DV_LIMIT_DEFAULTS.maxMapLength, diff --git a/libs/quickjs-runtime/src/lib/source-map-remap.spec.ts b/libs/quickjs-runtime/src/lib/source-map-remap.spec.ts new file mode 100644 index 0000000..480ee8b --- /dev/null +++ b/libs/quickjs-runtime/src/lib/source-map-remap.spec.ts @@ -0,0 +1,58 @@ +import { remapModulePackErrorPayload } from './source-map-remap.js'; +import type { ModulePackV1 } from './quickjs-runtime.js'; + +function createModulePack(sourceMap?: string): ModulePackV1 { + return { + version: 1, + entrySpecifier: './entry.js', + entryExport: 'default', + modules: [ + { + specifier: './entry.js', + source: 'const x = 1;\nthrow new Error("boom");\n', + ...(sourceMap ? { sourceMap } : {}), + }, + ], + graphHash: '0'.repeat(64), + builderVersion: 'deterministic-builder-v1', + dependencyIntegrity: '1'.repeat(64), + }; +} + +describe('source-map remap', () => { + it('remaps module-pack stack locations to original sources', () => { + const sourceMap = JSON.stringify({ + version: 3, + file: 'entry.js', + sources: ['src/entry.ts'], + names: [], + mappings: 'AAAA;AACA', + }); + const payload = + 'ModuleEvaluationError: Error: boom at ./entry.js:2:7 and ./entry.js:1:1'; + + const remapped = remapModulePackErrorPayload( + payload, + createModulePack(sourceMap), + ); + + expect(remapped.payload).toContain('src/entry.ts:2:1'); + expect(remapped.payload).toContain('src/entry.ts:1:1'); + expect(remapped.locations).toHaveLength(2); + expect(remapped.locations[0]).toMatchObject({ + generatedSpecifier: './entry.js', + generatedLine: 2, + generatedColumn: 7, + source: 'src/entry.ts', + line: 2, + column: 1, + }); + }); + + it('leaves payload unchanged when no source map is present', () => { + const payload = 'ModuleEvaluationError: Error: boom at ./entry.js:2:7'; + const remapped = remapModulePackErrorPayload(payload, createModulePack()); + expect(remapped.payload).toBe(payload); + expect(remapped.locations).toEqual([]); + }); +}); diff --git a/libs/quickjs-runtime/src/lib/source-map-remap.ts b/libs/quickjs-runtime/src/lib/source-map-remap.ts new file mode 100644 index 0000000..49145c7 --- /dev/null +++ b/libs/quickjs-runtime/src/lib/source-map-remap.ts @@ -0,0 +1,133 @@ +import { + TraceMap, + originalPositionFor, + type OriginalMapping, +} from '@jridgewell/trace-mapping'; +import type { ModulePackV1 } from './quickjs-runtime.js'; + +const GENERATED_LOCATION_RE = /(\.{0,2}\/[^\s:()]+\.m?js):(\d+):(\d+)/g; + +interface ParsedSourceMapShape { + version: number; + sources: string[]; + names: string[]; + mappings: string; + [key: string]: unknown; +} + +export interface RemappedStackLocation { + generatedSpecifier: string; + generatedLine: number; + generatedColumn: number; + source: string; + line: number; + column: number; +} + +export interface RemapPayloadResult { + payload: string; + locations: RemappedStackLocation[]; +} + +export function remapModulePackErrorPayload( + payload: string, + modulePack: ModulePackV1, +): RemapPayloadResult { + const traceMapsBySpecifier = buildTraceMapLookup(modulePack); + if (traceMapsBySpecifier.size === 0) { + return { payload, locations: [] }; + } + + const locations: RemappedStackLocation[] = []; + const remappedPayload = payload.replace( + GENERATED_LOCATION_RE, + (match, specifier, lineText, columnText) => { + const generatedLine = Number(lineText); + const generatedColumn = Number(columnText); + if ( + !Number.isInteger(generatedLine) || + !Number.isInteger(generatedColumn) || + generatedLine <= 0 || + generatedColumn <= 0 + ) { + return match; + } + + const traceMap = + traceMapsBySpecifier.get(specifier) ?? + traceMapsBySpecifier.get(normalizeSpecifier(specifier)); + if (!traceMap) { + return match; + } + + const original = resolveOriginalPosition(traceMap, { + line: generatedLine, + column: generatedColumn, + }); + if (!original) { + return match; + } + + locations.push({ + generatedSpecifier: specifier, + generatedLine, + generatedColumn, + source: original.source, + line: original.line, + column: original.column, + }); + + return `${original.source}:${original.line}:${original.column}`; + }, + ); + + return { payload: remappedPayload, locations }; +} + +function buildTraceMapLookup(modulePack: ModulePackV1): Map { + const lookup = new Map(); + for (const module of modulePack.modules) { + if (!module.sourceMap) { + continue; + } + try { + const decodedMap = JSON.parse(module.sourceMap) as ParsedSourceMapShape; + const traceMap = new TraceMap( + decodedMap as unknown as ConstructorParameters[0], + ); + lookup.set(module.specifier, traceMap); + lookup.set(normalizeSpecifier(module.specifier), traceMap); + } catch { + // Ignore malformed source maps; leave payload unchanged. + } + } + return lookup; +} + +function normalizeSpecifier(specifier: string): string { + if (specifier.startsWith('./')) { + return specifier.slice(2); + } + return specifier; +} + +function resolveOriginalPosition( + traceMap: TraceMap, + generated: { line: number; column: number }, +): { source: string; line: number; column: number } | null { + const mapping = originalPositionFor(traceMap, { + line: generated.line, + column: Math.max(0, generated.column - 1), + }) as OriginalMapping | null; + + if (!mapping || mapping.line == null || mapping.column == null) { + return null; + } + + const source = mapping.source ?? ''; + return { + source, + line: mapping.line, + column: mapping.column + 1, + }; +} diff --git a/libs/quickjs-runtime/tsconfig.lib.json b/libs/quickjs-runtime/tsconfig.lib.json index 901dedd..4fd1277 100644 --- a/libs/quickjs-runtime/tsconfig.lib.json +++ b/libs/quickjs-runtime/tsconfig.lib.json @@ -14,6 +14,9 @@ { "path": "../quickjs-wasm/tsconfig.lib.json" }, + { + "path": "../execution-profiles/tsconfig.lib.json" + }, { "path": "../dv/tsconfig.lib.json" }, @@ -22,6 +25,9 @@ }, { "path": "../test-harness/tsconfig.lib.json" + }, + { + "path": "../deterministic-bundler/tsconfig.lib.json" } ], "exclude": [ diff --git a/libs/quickjs-wasm-build/README.md b/libs/quickjs-wasm-build/README.md index a5a5d70..70af30c 100644 --- a/libs/quickjs-wasm-build/README.md +++ b/libs/quickjs-wasm-build/README.md @@ -8,13 +8,13 @@ Early Emscripten build of the deterministic QuickJS fork with gas metering. - Run `pnpm nx build quickjs-wasm-build` to compile the wasm harness and emit both release and debug wasm32 artifacts (`quickjs-eval{,-debug}.{js,wasm}`) to `libs/quickjs-wasm-build/dist/`. TypeScript outputs also land in this directory. - Set `WASM_BUILD_TYPES=release` to skip debug builds, or `WASM_BUILD_TYPES=release,debug` (default) to emit both. Set `WASM_VARIANTS=wasm32,wasm64` to also emit the memory64 artifacts (`quickjs-eval-wasm64{,-debug}.{js,wasm}`) used with `QJS_WASM_VARIANT=wasm64` in tests. - Wasm memory is fixed at 32 MiB (1 MiB stack) with growth disabled; the Emscripten filesystem is stripped (`-sFILESYSTEM=0`), and we pin `SOURCE_DATE_EPOCH=1704067200` to avoid timestamp/env noise in the wasm/loader. We intentionally avoid `-sDETERMINISTIC` because it patches host `Date.now`/`Math.random`. -- The build also emits `quickjs-wasm-build.metadata.json` in `dist/`, capturing the QuickJS version/commit, pinned emscripten version, deterministic build settings (memory + flags), per-variant/per-build-type artifact sizes and SHA-256 hashes (including the `buildType` and flags used), and `engineBuildHash` (sha256 of wasm bytes, with the top-level hash pointing at wasm32 release when present). Access it via `getQuickjsWasmMetadataPath()` / `readQuickjsWasmMetadata()`. +- The build also emits `quickjs-wasm-build.metadata.json` in `dist/`, capturing the QuickJS version/commit, pinned emscripten version, deterministic build settings (memory + flags), canonical `gasVersion`, per-variant/per-build-type artifact sizes and SHA-256 hashes (including the `buildType` and flags used), and `engineBuildHash` (sha256 of wasm bytes, with the top-level hash pointing at wasm32 release when present). Access it via `getQuickjsWasmMetadataPath()` / `readQuickjsWasmMetadata()`. The ESM loader exports a `QuickJSGasWasm` factory; the harness exports deterministic ABI entrypoints only: -- `qjs_det_init(manifest_ptr, manifest_len, manifest_hash_hex_ptr, context_ptr, context_len, gas_limit)` installs the ABI manifest/hash and optional DV-encoded context blob while wiring the imported `host_call`. +- `qjs_det_init(manifest_ptr, manifest_len, manifest_hash_hex_ptr, context_ptr, context_len, gas_limit, feature_flags)` installs the ABI manifest/hash and optional DV-encoded context blob while wiring the imported `host_call`. `feature_flags=0` keeps baseline behavior. - `qjs_det_eval(code)` evaluates source with the installed manifest/context and returns a `char*` string of the form `RESULT GAS remaining= used=` (or `ERROR …` on failure). -- `qjs_det_set_gas_limit(gas_limit)`, `qjs_det_free()`, `qjs_det_enable_tape(capacity)` / `qjs_det_read_tape()`, and `qjs_det_enable_trace(enabled)` / `qjs_det_read_trace()` mirror the native harness controls. +- `qjs_det_set_gas_limit(gas_limit)`, `qjs_det_free()`, `qjs_det_enable_tape(capacity)` / `qjs_det_read_tape()`, `qjs_det_enable_charge_tape(capacity)` / `qjs_det_read_charge_tape()`, and `qjs_det_enable_trace(enabled)` / `qjs_det_read_trace()` mirror the native harness controls. Strings returned from the harness are allocated with `malloc`; free them with the exported `_free` helper. The wasm module expects a `host.host_call` import. When you don't have a dispatcher wired yet, pass a stub that returns the transport sentinel: diff --git a/libs/quickjs-wasm-build/scripts/build-wasm.sh b/libs/quickjs-wasm-build/scripts/build-wasm.sh index 5acea82..70bf395 100755 --- a/libs/quickjs-wasm-build/scripts/build-wasm.sh +++ b/libs/quickjs-wasm-build/scripts/build-wasm.sh @@ -7,6 +7,8 @@ PROJECT_ROOT="${REPO_ROOT}/libs/quickjs-wasm-build" QJS_DIR="${REPO_ROOT}/vendor/quickjs" OUT_DIR="${PROJECT_ROOT}/dist" METADATA_BASENAME="quickjs-wasm-build.metadata.json" + +bash "${REPO_ROOT}/tools/scripts/ensure-quickjs-submodule.sh" VARIANTS_RAW="${WASM_VARIANTS:-wasm32}" BUILD_TYPES_RAW="${WASM_BUILD_TYPES:-release,debug}" WASM_INITIAL_MEMORY_BYTES=$((32 * 1024 * 1024)) @@ -89,7 +91,7 @@ BASE_EMCC_FLAGS=( -sERROR_ON_UNDEFINED_SYMBOLS=0 -sEXPORT_NAME=QuickJSGasWasm -sWASM_BIGINT=1 - "-sEXPORTED_FUNCTIONS=['_qjs_det_init','_qjs_det_eval','_qjs_det_set_gas_limit','_qjs_det_free','_qjs_det_enable_tape','_qjs_det_read_tape','_qjs_det_enable_trace','_qjs_det_read_trace','_malloc','_free']" + "-sEXPORTED_FUNCTIONS=['_qjs_det_init','_qjs_det_eval','_qjs_det_eval_module_pack','_qjs_det_set_gas_limit','_qjs_det_free','_qjs_det_enable_tape','_qjs_det_read_tape','_qjs_det_enable_charge_tape','_qjs_det_read_charge_tape','_qjs_det_enable_trace','_qjs_det_read_trace','_malloc','_free']" "-sEXPORTED_RUNTIME_METHODS=['cwrap','ccall','UTF8ToString','lengthBytesUTF8']" ) @@ -213,13 +215,13 @@ if [[ ${#BUILT_VARIANTS[@]} -eq 0 ]]; then exit 1 fi -node - "${OUT_DIR}" "${QJS_DIR}" "${REPO_ROOT}/tools/scripts/emsdk-version.txt" "${METADATA_BASENAME}" "${BUILT_VARIANTS[@]}" <<'NODE' +node - "${OUT_DIR}" "${QJS_DIR}" "${REPO_ROOT}/tools/scripts/emsdk-version.txt" "${REPO_ROOT}/tools/gas-spec/gas-spec.v3.json" "${METADATA_BASENAME}" "${BUILT_VARIANTS[@]}" <<'NODE' const crypto = require('crypto'); const fs = require('fs'); const path = require('path'); const { execFileSync } = require('child_process'); -const [outDir, qjsDir, emsdkVersionFile, metadataBasename, ...variantArgs] = process.argv.slice(2); +const [outDir, qjsDir, emsdkVersionFile, gasSpecPath, metadataBasename, ...variantArgs] = process.argv.slice(2); if (variantArgs.length === 0) { throw new Error('No variant arguments passed to metadata writer.'); } @@ -243,6 +245,11 @@ const sha256File = (filePath) => const statSize = (filePath) => fs.statSync(filePath).size; const quickjsVersion = readTrim(path.join(qjsDir, 'VERSION')); +const gasSpec = JSON.parse(fs.readFileSync(gasSpecPath, 'utf8')); +const gasVersion = + Number.isInteger(gasSpec?.gasVersion) && gasSpec.gasVersion >= 0 + ? gasSpec.gasVersion + : null; let quickjsCommit = null; try { quickjsCommit = execFileSync('git', ['-C', qjsDir, 'rev-parse', 'HEAD'], { @@ -337,6 +344,7 @@ const metadata = { quickjsCommit, emscriptenVersion: readTrim(emsdkVersionFile), engineBuildHash, + gasVersion, build: { memory: buildMemory, determinism, diff --git a/libs/quickjs-wasm-build/src/lib/quickjs-wasm-build.spec.ts b/libs/quickjs-wasm-build/src/lib/quickjs-wasm-build.spec.ts index b4791ec..fbf217e 100644 --- a/libs/quickjs-wasm-build/src/lib/quickjs-wasm-build.spec.ts +++ b/libs/quickjs-wasm-build/src/lib/quickjs-wasm-build.spec.ts @@ -105,6 +105,7 @@ describe('metadata helpers', () => { quickjsCommit: 'abc123', emscriptenVersion: '3.1.56', engineBuildHash: 'deadbeef', + gasVersion: 3, build: { memory: { initial: 33554432, diff --git a/libs/quickjs-wasm-build/src/wasm/quickjs_wasm.c b/libs/quickjs-wasm-build/src/wasm/quickjs_wasm.c index 584abc3..a4df12e 100644 --- a/libs/quickjs-wasm-build/src/wasm/quickjs_wasm.c +++ b/libs/quickjs-wasm-build/src/wasm/quickjs_wasm.c @@ -26,6 +26,7 @@ static void free_det_runtime(void) { det_ctx = NULL; } if (det_rt) { + JS_RunGC(det_rt); JS_FreeRuntime(det_rt); det_rt = NULL; } @@ -169,17 +170,326 @@ static int js_set_prop(JSContext *ctx, JSValue obj, const char *name, JSValue va return 0; } +typedef struct { + char *specifier; + char *source; + size_t source_len; +} ModulePackEntry; + +typedef struct { + ModulePackEntry *entries; + uint32_t entry_count; +} ModulePack; + +static void free_module_pack(ModulePack *pack) { + if (!pack) { + return; + } + if (pack->entries) { + for (uint32_t i = 0; i < pack->entry_count; i++) { + free(pack->entries[i].specifier); + free(pack->entries[i].source); + } + free(pack->entries); + } + pack->entries = NULL; + pack->entry_count = 0; +} + +static ModulePackEntry *find_module_pack_entry(ModulePack *pack, + const char *specifier) { + if (!pack || !specifier) { + return NULL; + } + for (uint32_t i = 0; i < pack->entry_count; i++) { + if (strcmp(pack->entries[i].specifier, specifier) == 0) { + return &pack->entries[i]; + } + } + return NULL; +} + +static char *copy_cstring_len(const char *value, size_t length) { + char *out = malloc(length + 1); + if (!out) { + return NULL; + } + memcpy(out, value, length); + out[length] = '\0'; + return out; +} + +static int parse_module_pack_json(JSContext *ctx, + const char *module_pack_json, + ModulePack *out_pack) { + JSValue parsed = JS_UNDEFINED; + JSValue length_value = JS_UNDEFINED; + uint32_t module_count = 0; + + memset(out_pack, 0, sizeof(*out_pack)); + + parsed = JS_ParseJSON(ctx, module_pack_json, strlen(module_pack_json), + ""); + if (JS_IsException(parsed)) { + goto fail; + } + + if (!JS_IsArray(ctx, parsed)) { + JS_ThrowTypeError(ctx, "module pack json must be an array"); + goto fail; + } + + length_value = JS_GetPropertyStr(ctx, parsed, "length"); + if (JS_IsException(length_value)) { + goto fail; + } + if (JS_ToUint32(ctx, &module_count, length_value) != 0) { + goto fail; + } + JS_FreeValue(ctx, length_value); + length_value = JS_UNDEFINED; + + if (module_count == 0) { + JS_ThrowTypeError(ctx, "module pack must contain at least one module"); + goto fail; + } + + out_pack->entries = calloc(module_count, sizeof(*out_pack->entries)); + if (!out_pack->entries) { + JS_ThrowOutOfMemory(ctx); + goto fail; + } + out_pack->entry_count = module_count; + + for (uint32_t i = 0; i < module_count; i++) { + JSValue item = JS_GetPropertyUint32(ctx, parsed, i); + JSValue specifier_value = JS_UNDEFINED; + JSValue source_value = JS_UNDEFINED; + const char *specifier_cstr = NULL; + const char *source_cstr = NULL; + size_t source_len = 0; + + if (JS_IsException(item)) { + goto fail; + } + if (!JS_IsObject(item)) { + JS_FreeValue(ctx, item); + JS_ThrowTypeError(ctx, "module pack entry must be an object"); + goto fail; + } + + specifier_value = JS_GetPropertyStr(ctx, item, "specifier"); + source_value = JS_GetPropertyStr(ctx, item, "source"); + if (JS_IsException(specifier_value) || JS_IsException(source_value)) { + JS_FreeValue(ctx, specifier_value); + JS_FreeValue(ctx, source_value); + JS_FreeValue(ctx, item); + goto fail; + } + + specifier_cstr = JS_ToCString(ctx, specifier_value); + source_cstr = JS_ToCStringLen(ctx, &source_len, source_value); + if (!specifier_cstr || !source_cstr) { + JS_FreeCString(ctx, specifier_cstr); + JS_FreeCString(ctx, source_cstr); + JS_FreeValue(ctx, specifier_value); + JS_FreeValue(ctx, source_value); + JS_FreeValue(ctx, item); + goto fail; + } + + out_pack->entries[i].specifier = + copy_cstring_len(specifier_cstr, strlen(specifier_cstr)); + out_pack->entries[i].source = copy_cstring_len(source_cstr, source_len); + out_pack->entries[i].source_len = source_len; + + JS_FreeCString(ctx, specifier_cstr); + JS_FreeCString(ctx, source_cstr); + JS_FreeValue(ctx, specifier_value); + JS_FreeValue(ctx, source_value); + JS_FreeValue(ctx, item); + + if (!out_pack->entries[i].specifier || !out_pack->entries[i].source) { + JS_ThrowOutOfMemory(ctx); + goto fail; + } + } + + JS_FreeValue(ctx, parsed); + return 0; + +fail: + if (!JS_IsUndefined(length_value)) { + JS_FreeValue(ctx, length_value); + } + if (!JS_IsUndefined(parsed)) { + JS_FreeValue(ctx, parsed); + } + free_module_pack(out_pack); + return -1; +} + +static JSModuleDef *module_pack_loader(JSContext *ctx, + const char *module_name, + void *opaque, + JSValueConst attributes) { + ModulePack *pack = (ModulePack *)opaque; + ModulePackEntry *entry = find_module_pack_entry(pack, module_name); + JSValue module_obj = JS_UNDEFINED; + + (void)attributes; + + if (!entry) { + JS_ThrowReferenceError(ctx, + "ModuleResolutionError: module specifier not found: %s", + module_name); + return NULL; + } + + module_obj = JS_Eval(ctx, entry->source, entry->source_len, entry->specifier, + JS_EVAL_TYPE_MODULE | JS_EVAL_FLAG_COMPILE_ONLY); + if (JS_IsException(module_obj)) { + return NULL; + } + + JSModuleDef *module_def = (JSModuleDef *)JS_VALUE_GET_PTR(module_obj); + JS_FreeValue(ctx, module_obj); + return module_def; +} + +static char *escape_js_string(const char *input) { + size_t needed = 2; /* quotes */ + for (const unsigned char *p = (const unsigned char *)input; *p; p++) { + switch (*p) { + case '\\': + case '"': + case '\n': + case '\r': + case '\t': + needed += 2; + break; + default: + needed += 1; + break; + } + } + + char *out = malloc(needed + 1); + if (!out) { + return NULL; + } + + char *cursor = out; + *cursor++ = '"'; + for (const unsigned char *p = (const unsigned char *)input; *p; p++) { + switch (*p) { + case '\\': + *cursor++ = '\\'; + *cursor++ = '\\'; + break; + case '"': + *cursor++ = '\\'; + *cursor++ = '"'; + break; + case '\n': + *cursor++ = '\\'; + *cursor++ = 'n'; + break; + case '\r': + *cursor++ = '\\'; + *cursor++ = 'r'; + break; + case '\t': + *cursor++ = '\\'; + *cursor++ = 't'; + break; + default: + *cursor++ = (char)*p; + break; + } + } + *cursor++ = '"'; + *cursor = '\0'; + return out; +} + +static char *format_prefixed_exception(JSContext *ctx, uint64_t gas_limit, + const char *prefix, + const char *fallback, + const JSGasTrace *trace) { + JSValue exception = JS_GetException(ctx); + const char *msg = JS_ToCString(ctx, exception); + uint64_t remaining = JS_GetGasRemaining(ctx); + char *payload = dup_printf("%s: %s", prefix, msg ? msg : fallback); + char *out = format_with_gas("ERROR", payload ? payload : prefix, gas_limit, + remaining, trace); + + if (payload) { + free(payload); + } + if (msg) { + JS_FreeCString(ctx, msg); + } + JS_FreeValue(ctx, exception); + return out; +} + +static int drain_pending_jobs(JSContext *ctx, JSRuntime *rt, + JSContext **out_error_ctx) { + while (JS_IsJobPending(rt)) { + JSContext *job_ctx = NULL; + int rc = JS_ExecutePendingJob(rt, &job_ctx); + if (rc < 0) { + if (out_error_ctx) { + *out_error_ctx = job_ctx ? job_ctx : ctx; + } + return -1; + } + } + + if (out_error_ctx) { + *out_error_ctx = ctx; + } + return 0; +} + +static int resolve_promise_result(JSContext *ctx, JSValue *value) { + int state = (int)JS_PromiseState(ctx, *value); + if (state < 0) { + return 0; + } + + if (state == JS_PROMISE_PENDING) { + JS_ThrowTypeError(ctx, + "promise did not settle during deterministic job drain"); + return -1; + } + + JSValue settled = JS_PromiseResult(ctx, *value); + if (state == JS_PROMISE_REJECTED) { + JS_FreeValue(ctx, *value); + *value = JS_UNDEFINED; + JS_Throw(ctx, settled); + return -1; + } + + JS_FreeValue(ctx, *value); + *value = settled; + return 0; +} + EMSCRIPTEN_KEEPALIVE char *qjs_det_init(const uint8_t *manifest_bytes, uint32_t manifest_size, const char *manifest_hash_hex, const uint8_t *context_blob, uint32_t context_blob_size, - uint64_t gas_limit) { + uint64_t gas_limit, + uint32_t feature_flags) { free_det_runtime(); det_gas_limit = gas_limit; - if (JS_NewDeterministicRuntime(&det_rt, &det_ctx) != 0) { + if (JS_NewDeterministicRuntimeWithFeatures(&det_rt, &det_ctx, feature_flags) != 0) { return dup_printf("ERROR GAS remaining=0 used=0"); } @@ -195,6 +505,7 @@ char *qjs_det_init(const uint8_t *manifest_bytes, .context_blob = context_blob, .context_blob_size = context_blob_size, .gas_limit = gas_limit, + .feature_flags = feature_flags, }; if (JS_InitDeterministicContext(det_ctx, &opts) != 0) { @@ -214,6 +525,8 @@ char *qjs_det_init(const uint8_t *manifest_bytes, EMSCRIPTEN_KEEPALIVE char *qjs_det_eval(const char *code) { + JSContext *job_error_ctx = NULL; + if (!det_ctx || !det_rt) { return dup_printf("ERROR GAS remaining=0 used=0"); } @@ -228,6 +541,17 @@ char *qjs_det_eval(const char *code) { return format_exception(det_ctx, det_gas_limit, "", NULL); } + if (drain_pending_jobs(det_ctx, det_rt, &job_error_ctx) != 0) { + JS_FreeValue(det_ctx, result); + return format_exception(job_error_ctx ? job_error_ctx : det_ctx, + det_gas_limit, "", NULL); + } + + if (resolve_promise_result(det_ctx, &result) != 0) { + JS_FreeValue(det_ctx, result); + return format_exception(det_ctx, det_gas_limit, "", NULL); + } + JSDvBuffer dv = {0}; if (JS_EncodeDV(det_ctx, result, &JS_DV_LIMIT_DEFAULTS, &dv) != 0) { JS_FreeValue(det_ctx, result); @@ -256,6 +580,206 @@ char *qjs_det_eval(const char *code) { return out; } +EMSCRIPTEN_KEEPALIVE +char *qjs_det_eval_module_pack(const char *module_pack_json, + const char *entry_specifier, + const char *entry_export) { + JSContext *job_error_ctx = NULL; + ModulePack pack = {0}; + JSValue module_eval = JS_UNDEFINED; + JSValue global_obj = JS_UNDEFINED; + JSValue export_value = JS_UNDEFINED; + JSDvBuffer dv = {0}; + JSAtom result_atom = JS_ATOM_NULL; + const char *target_export = NULL; + char *entry_specifier_escaped = NULL; + char *entry_export_escaped = NULL; + char *wrapper_source = NULL; + char *hex = NULL; + char *out = NULL; + const char *result_global_name = "__blue_module_pack_result"; + + if (!det_ctx || !det_rt) { + return dup_printf("ERROR GAS remaining=0 used=0"); + } + + if (run_gc_checkpoint(det_ctx) != 0) { + return format_exception(det_ctx, det_gas_limit, "", NULL); + } + + if (!entry_specifier || entry_specifier[0] == '\0') { + uint64_t remaining = JS_GetGasRemaining(det_ctx); + return format_with_gas("ERROR", + "ModuleSpecifierNotFound: empty entry specifier", + det_gas_limit, remaining, NULL); + } + + target_export = (entry_export && entry_export[0] != '\0') ? entry_export + : "default"; + + if (parse_module_pack_json(det_ctx, module_pack_json, &pack) != 0) { + return format_prefixed_exception(det_ctx, det_gas_limit, + "ModuleEvaluationError", + "", NULL); + } + + if (!find_module_pack_entry(&pack, entry_specifier)) { + uint64_t remaining = JS_GetGasRemaining(det_ctx); + out = format_with_gas("ERROR", + "ModuleSpecifierNotFound: entry module not found", + det_gas_limit, remaining, NULL); + goto cleanup; + } + + if (JS_AddIntrinsicPromise(det_ctx) != 0) { + out = format_prefixed_exception(det_ctx, det_gas_limit, + "ModuleEvaluationError", "", + NULL); + goto cleanup; + } + + JS_SetModuleLoaderFunc2(det_rt, NULL, module_pack_loader, NULL, &pack); + + entry_specifier_escaped = escape_js_string(entry_specifier); + entry_export_escaped = escape_js_string(target_export); + if (!entry_specifier_escaped || !entry_export_escaped) { + out = format_prefixed_exception(det_ctx, det_gas_limit, + "ModuleEvaluationError", "", NULL); + goto cleanup; + } + + wrapper_source = dup_printf( + "import * as __blue_entry_ns from %s;\n" + "if (typeof __blue_entry_ns[%s] === 'undefined') {\n" + " throw new Error('ModuleExportMissing: export not found');\n" + "}\n" + "globalThis.%s = __blue_entry_ns[%s];\n", + entry_specifier_escaped, entry_export_escaped, result_global_name, + entry_export_escaped); + if (!wrapper_source) { + out = format_prefixed_exception(det_ctx, det_gas_limit, + "ModuleEvaluationError", "", NULL); + goto cleanup; + } + + module_eval = JS_Eval(det_ctx, wrapper_source, strlen(wrapper_source), + "./__module_pack_entry__.js", JS_EVAL_TYPE_MODULE); + if (JS_IsException(module_eval)) { + out = format_prefixed_exception(det_ctx, det_gas_limit, + "ModuleEvaluationError", + "", NULL); + goto cleanup; + } + + if (drain_pending_jobs(det_ctx, det_rt, &job_error_ctx) != 0) { + out = format_prefixed_exception(job_error_ctx ? job_error_ctx : det_ctx, + det_gas_limit, "ModuleEvaluationError", + "", NULL); + goto cleanup; + } + + global_obj = JS_GetGlobalObject(det_ctx); + if (JS_IsException(global_obj)) { + out = format_prefixed_exception(det_ctx, det_gas_limit, + "ModuleEvaluationError", + "", NULL); + goto cleanup; + } + + export_value = JS_GetPropertyStr(det_ctx, global_obj, result_global_name); + if (JS_IsException(export_value)) { + out = format_prefixed_exception(det_ctx, det_gas_limit, + "ModuleEvaluationError", + "", NULL); + goto cleanup; + } + + if (JS_IsUndefined(export_value)) { + uint64_t remaining = JS_GetGasRemaining(det_ctx); + out = format_with_gas("ERROR", "ModuleExportMissing: export not found", + det_gas_limit, remaining, NULL); + goto cleanup; + } + + if (resolve_promise_result(det_ctx, &export_value) != 0) { + out = format_prefixed_exception(det_ctx, det_gas_limit, + "ModuleEvaluationError", + "", NULL); + goto cleanup; + } + + result_atom = JS_NewAtom(det_ctx, result_global_name); + if (result_atom != JS_ATOM_NULL) { + JS_DeleteProperty(det_ctx, global_obj, result_atom, 0); + } + + if (JS_EncodeDV(det_ctx, export_value, &JS_DV_LIMIT_DEFAULTS, &dv) != 0) { + out = format_prefixed_exception(det_ctx, det_gas_limit, + "ModuleEvaluationError", "", + NULL); + goto cleanup; + } + + if (run_gc_checkpoint(det_ctx) != 0) { + out = format_prefixed_exception(det_ctx, det_gas_limit, + "ModuleEvaluationError", + "", NULL); + goto cleanup; + } + + hex = hex_bytes(dv.data, dv.length); + if (!hex) { + uint64_t remaining = JS_GetGasRemaining(det_ctx); + out = format_with_gas("ERROR", "", det_gas_limit, remaining, + NULL); + goto cleanup; + } + + { + uint64_t remaining = JS_GetGasRemaining(det_ctx); + out = format_with_gas("RESULT", hex, det_gas_limit, remaining, NULL); + } + +cleanup: + JS_SetModuleLoaderFunc2(det_rt, NULL, NULL, NULL, NULL); + if (wrapper_source) { + free(wrapper_source); + } + if (entry_specifier_escaped) { + free(entry_specifier_escaped); + } + if (entry_export_escaped) { + free(entry_export_escaped); + } + if (result_atom != JS_ATOM_NULL) { + JS_FreeAtom(det_ctx, result_atom); + } + if (!JS_IsUndefined(export_value)) { + JS_FreeValue(det_ctx, export_value); + } + if (!JS_IsUndefined(global_obj)) { + JS_FreeValue(det_ctx, global_obj); + } + if (!JS_IsUndefined(module_eval)) { + JS_FreeValue(det_ctx, module_eval); + } + if (dv.data) { + JS_FreeDVBuffer(det_ctx, &dv); + } + if (hex) { + free(hex); + } + JS_FreeContextLoadedModules(det_ctx); + free_module_pack(&pack); + + if (!out) { + return format_prefixed_exception(det_ctx, det_gas_limit, + "ModuleEvaluationError", "", + NULL); + } + return out; +} + EMSCRIPTEN_KEEPALIVE int qjs_det_set_gas_limit(uint64_t gas_limit) { if (!det_ctx || !det_rt) { @@ -400,6 +924,114 @@ char *qjs_det_read_tape(void) return out; } +EMSCRIPTEN_KEEPALIVE +int qjs_det_enable_charge_tape(uint32_t capacity) +{ + if (!det_ctx || !det_rt) + return -1; + + return JS_EnableGasChargeTape(det_ctx, capacity); +} + +EMSCRIPTEN_KEEPALIVE +char *qjs_det_read_charge_tape(void) +{ + JSGasChargeRecord *records = NULL; + size_t count = 0; + size_t to_read = 0; + JSValue arr = JS_UNDEFINED; + JSValue json = JS_UNDEFINED; + const char *json_str = NULL; + char *out = NULL; + + if (!det_ctx || !det_rt) + return dup_printf("[]"); + + count = JS_GetGasChargeTapeLength(det_ctx); + if (count == 0) + return dup_printf("[]"); + + to_read = count > JS_GAS_CHARGE_TAPE_MAX_CAPACITY ? JS_GAS_CHARGE_TAPE_MAX_CAPACITY : count; + records = js_mallocz(det_ctx, sizeof(JSGasChargeRecord) * to_read); + if (!records) + return dup_printf("[]"); + + if (JS_ReadGasChargeTape(det_ctx, records, to_read, &count) != 0) { + js_free(det_ctx, records); + return dup_printf("[]"); + } + + arr = JS_NewArray(det_ctx); + if (JS_IsException(arr)) + goto done; + + for (size_t i = 0; i < count; i++) { + JSValue obj = JS_NewObjectProto(det_ctx, JS_NULL); + char amount_buf[32]; + char logical_units_buf[32]; + char gas_before_buf[32]; + char gas_after_buf[32]; + + if (JS_IsException(obj)) + goto loop_error; + + if (js_set_prop(det_ctx, obj, "siteId", JS_NewUint32(det_ctx, records[i].site_id)) < 0) + goto loop_error; + if (js_set_prop(det_ctx, obj, "kind", JS_NewUint32(det_ctx, records[i].kind)) < 0) + goto loop_error; + if (js_set_prop(det_ctx, obj, "flags", JS_NewUint32(det_ctx, records[i].flags)) < 0) + goto loop_error; + + snprintf(amount_buf, sizeof(amount_buf), "%" PRIu64, records[i].amount); + snprintf(logical_units_buf, sizeof(logical_units_buf), "%" PRIu64, records[i].logical_units); + snprintf(gas_before_buf, sizeof(gas_before_buf), "%" PRIu64, records[i].gas_before); + snprintf(gas_after_buf, sizeof(gas_after_buf), "%" PRIu64, records[i].gas_after); + + if (js_set_prop(det_ctx, obj, "amount", JS_NewString(det_ctx, amount_buf)) < 0) + goto loop_error; + if (js_set_prop(det_ctx, obj, "logicalUnits", JS_NewString(det_ctx, logical_units_buf)) < 0) + goto loop_error; + if (js_set_prop(det_ctx, obj, "gasBefore", JS_NewString(det_ctx, gas_before_buf)) < 0) + goto loop_error; + if (js_set_prop(det_ctx, obj, "gasAfter", JS_NewString(det_ctx, gas_after_buf)) < 0) + goto loop_error; + + if (JS_SetPropertyUint32(det_ctx, arr, (uint32_t)i, obj) < 0) { + JS_FreeValue(det_ctx, obj); + goto done; + } + + continue; + + loop_error: + JS_FreeValue(det_ctx, obj); + goto done; + } + + json = JS_JSONStringify(det_ctx, arr, JS_UNDEFINED, JS_UNDEFINED); + if (JS_IsException(json)) + goto done; + + json_str = JS_ToCString(det_ctx, json); + if (!json_str) + goto done; + + out = dup_printf("%s", json_str); + JS_FreeCString(det_ctx, json_str); + +done: + if (records) + js_free(det_ctx, records); + if (!JS_IsUndefined(arr)) + JS_FreeValue(det_ctx, arr); + if (!JS_IsUndefined(json)) + JS_FreeValue(det_ctx, json); + + if (!out) + return dup_printf("[]"); + return out; +} + EMSCRIPTEN_KEEPALIVE int qjs_det_enable_trace(int enabled) { @@ -432,7 +1064,9 @@ char *qjs_det_read_trace(void) "\",\"arrayCbBaseCount\":\"%" PRIu64 "\",\"arrayCbBaseGas\":\"%" PRIu64 "\",\"arrayCbPerElCount\":\"%" PRIu64 "\",\"arrayCbPerElGas\":\"%" PRIu64 - "\",\"allocationCount\":\"%" PRIu64 "\",\"allocationBytes\":\"%" PRIu64 + "\",\"allocationCount\":\"%" PRIu64 + "\",\"allocationRequestedBytes\":\"%" PRIu64 + "\",\"allocationBytes\":\"%" PRIu64 "\",\"allocationGas\":\"%" PRIu64 "\",\"jsonParseCount\":\"%" PRIu64 "\",\"jsonParseGas\":\"%" PRIu64 "\",\"jsonParseInputBytes\":\"%" PRIu64 @@ -445,11 +1079,16 @@ char *qjs_det_read_trace(void) "\",\"jsonStringifyValues\":\"%" PRIu64 "\",\"jsonStringifyObjectEntries\":\"%" PRIu64 "\",\"jsonStringifyArrayElements\":\"%" PRIu64 - "\",\"jsonStringifySortComparisons\":\"%" PRIu64 "\"}", + "\",\"jsonStringifySortComparisons\":\"%" PRIu64 + "\",\"hostCallPreCount\":\"%" PRIu64 + "\",\"hostCallPreGas\":\"%" PRIu64 + "\",\"hostCallPostCount\":\"%" PRIu64 + "\",\"hostCallPostGas\":\"%" PRIu64 "\"}", trace.opcode_count, trace.opcode_gas, trace.builtin_array_cb_base_count, trace.builtin_array_cb_base_gas, trace.builtin_array_cb_per_element_count, trace.builtin_array_cb_per_element_gas, trace.allocation_count, - trace.allocation_bytes, trace.allocation_gas, trace.json_parse_count, + trace.allocation_requested_bytes, trace.allocation_bytes, + trace.allocation_gas, trace.json_parse_count, trace.json_parse_gas, trace.json_parse_input_bytes, trace.json_parse_value_count, trace.json_parse_object_entry_count, trace.json_parse_array_element_count, trace.json_stringify_count, @@ -457,5 +1096,7 @@ char *qjs_det_read_trace(void) trace.json_stringify_value_count, trace.json_stringify_object_entry_count, trace.json_stringify_array_element_count, - trace.json_stringify_sort_comparison_count); + trace.json_stringify_sort_comparison_count, + trace.host_call_pre_count, trace.host_call_pre_gas, + trace.host_call_post_count, trace.host_call_post_gas); } diff --git a/libs/quickjs-wasm-constants/src/lib/quickjs-wasm-constants.ts b/libs/quickjs-wasm-constants/src/lib/quickjs-wasm-constants.ts index 007a675..b716e8a 100644 --- a/libs/quickjs-wasm-constants/src/lib/quickjs-wasm-constants.ts +++ b/libs/quickjs-wasm-constants/src/lib/quickjs-wasm-constants.ts @@ -50,6 +50,7 @@ export interface QuickjsWasmBuildMetadata { quickjsCommit: string | null; emscriptenVersion: string; engineBuildHash: string | null; + gasVersion: number | null; build: QuickjsWasmBuildConfig; variants: Partial< Record< diff --git a/libs/quickjs-wasm/README.md b/libs/quickjs-wasm/README.md index 6856fb9..6f91358 100644 --- a/libs/quickjs-wasm/README.md +++ b/libs/quickjs-wasm/README.md @@ -13,7 +13,7 @@ import { loadQuickjsWasmMetadata, } from '@blue-quickjs/quickjs-wasm'; -const metadata = await loadQuickjsWasmMetadata(); // includes engineBuildHash + flags +const metadata = await loadQuickjsWasmMetadata(); // includes engineBuildHash, gasVersion, and build flags const artifact = await getQuickjsWasmArtifact(); // defaults to wasm32 release const wasmBytes = await loadQuickjsWasmBinary( artifact.variant, diff --git a/libs/quickjs-wasm/eslint.config.mjs b/libs/quickjs-wasm/eslint.config.mjs index 0a23ec0..f0918f4 100644 --- a/libs/quickjs-wasm/eslint.config.mjs +++ b/libs/quickjs-wasm/eslint.config.mjs @@ -2,6 +2,28 @@ import baseConfig from '../../eslint.config.mjs'; export default [ ...baseConfig, + { + files: ['**/*.ts', '**/*.tsx', '**/*.js', '**/*.jsx'], + rules: { + '@nx/enforce-module-boundaries': [ + 'error', + { + enforceBuildableLibDependency: true, + allow: ['^.*/eslint(\\.base)?\\.config\\.[cm]?[jt]s$'], + ignoredCircularDependencies: [ + ['quickjs-wasm', 'test-harness'], + ['quickjs-wasm', 'quickjs-runtime'], + ], + depConstraints: [ + { + sourceTag: '*', + onlyDependOnLibsWithTags: ['*'], + }, + ], + }, + ], + }, + }, { files: ['**/*.json'], rules: { diff --git a/libs/quickjs-wasm/src/lib/quickjs-wasm.spec.ts b/libs/quickjs-wasm/src/lib/quickjs-wasm.spec.ts index f63f5e2..ced3536 100644 --- a/libs/quickjs-wasm/src/lib/quickjs-wasm.spec.ts +++ b/libs/quickjs-wasm/src/lib/quickjs-wasm.spec.ts @@ -154,6 +154,7 @@ describe('quickjs wasm artifacts', () => { contextPtr, CONTEXT_BLOB.length, 500n, + 0, ); if (errorPtr !== 0) { const message = readCString(errorPtr); @@ -198,6 +199,7 @@ function createDeterministicFns(module: WasmModuleWithCwrap, variant: string) { ptrType, 'number', 'bigint', + 'number', ]) as ( manifestPtr: WasmPtr, manifestSize: number, @@ -205,6 +207,7 @@ function createDeterministicFns(module: WasmModuleWithCwrap, variant: string) { contextPtr: WasmPtr, contextSize: number, gasLimit: bigint, + featureFlags: number, ) => WasmPtr; const evalFn = module.cwrap('qjs_det_eval', ptrType, ['string']) as ( code: string, diff --git a/libs/test-harness/eslint.config.mjs b/libs/test-harness/eslint.config.mjs index d50f606..8b79c80 100644 --- a/libs/test-harness/eslint.config.mjs +++ b/libs/test-harness/eslint.config.mjs @@ -12,6 +12,7 @@ export default [ '{projectRoot}/eslint.config.{js,cjs,mjs,ts,cts,mts}', '{projectRoot}/vite.config.{js,ts,mjs,mts}', ], + ignoredDependencies: ['@noble/hashes', 'base64-js', 'chess.js'], }, ], }, diff --git a/libs/test-harness/fixtures/abi-manifest/host-v2.bytes.hex b/libs/test-harness/fixtures/abi-manifest/host-v2.bytes.hex new file mode 100644 index 0000000..f545523 --- /dev/null +++ b/libs/test-harness/fixtures/abi-manifest/host-v2.bytes.hex @@ -0,0 +1 @@ +a3666162695f696467486f73742e76326966756e6374696f6e7383a963676173a5646261736514676b5f756e697473016b6b5f6172675f6279746573016b6b5f7265745f6279746573016b7363686564756c655f69646b646f632d726561642d76316561726974790165666e5f696401666566666563746452454144666c696d697473a4696d61785f756e6974731903e86c6172675f757466385f6d617881190800716d61785f726571756573745f6279746573191000726d61785f726573706f6e73655f62797465731a00040000676a735f706174688268646f63756d656e74636765746a6172675f736368656d6181a1647479706566737472696e676b6572726f725f636f64657383a26374616771686f73742f696e76616c69645f7061746864636f64656c494e56414c49445f50415448a2637461676a686f73742f6c696d697464636f64656e4c494d49545f4558434545444544a2637461676e686f73742f6e6f745f666f756e6464636f6465694e4f545f464f554e446d72657475726e5f736368656d61a16474797065626476a963676173a5646261736514676b5f756e697473016b6b5f6172675f6279746573016b6b5f7265745f6279746573016b7363686564756c655f69646b646f632d726561642d76316561726974790165666e5f696402666566666563746452454144666c696d697473a4696d61785f756e6974731903e86c6172675f757466385f6d617881190800716d61785f726571756573745f6279746573191000726d61785f726573706f6e73655f62797465731a00040000676a735f706174688268646f63756d656e746c67657443616e6f6e6963616c6a6172675f736368656d6181a1647479706566737472696e676b6572726f725f636f64657383a26374616771686f73742f696e76616c69645f7061746864636f64656c494e56414c49445f50415448a2637461676a686f73742f6c696d697464636f64656e4c494d49545f4558434545444544a2637461676e686f73742f6e6f745f666f756e6464636f6465694e4f545f464f554e446d72657475726e5f736368656d61a16474797065626476a963676173a5646261736505676b5f756e697473016b6b5f6172675f6279746573016b6b5f7265745f6279746573006b7363686564756c655f696467656d69742d76316561726974790165666e5f6964036665666665637464454d4954666c696d697473a3696d61785f756e697473190400716d61785f726571756573745f6279746573198000726d61785f726573706f6e73655f62797465731840676a735f706174688164656d69746a6172675f736368656d6181a164747970656264766b6572726f725f636f64657381a2637461676a686f73742f6c696d697464636f64656e4c494d49545f45584345454445446d72657475726e5f736368656d61a16474797065646e756c6c6b6162695f76657273696f6e02 diff --git a/libs/test-harness/fixtures/abi-manifest/host-v2.hash b/libs/test-harness/fixtures/abi-manifest/host-v2.hash new file mode 100644 index 0000000..617deac --- /dev/null +++ b/libs/test-harness/fixtures/abi-manifest/host-v2.hash @@ -0,0 +1 @@ +ec5c3df99a1b0ab84b692996193707ae6c931382e75c96c7c14b4f8baaae5af2 diff --git a/libs/test-harness/fixtures/abi-manifest/host-v2.json b/libs/test-harness/fixtures/abi-manifest/host-v2.json new file mode 100644 index 0000000..df1d0d0 --- /dev/null +++ b/libs/test-harness/fixtures/abi-manifest/host-v2.json @@ -0,0 +1,79 @@ +{ + "abi_id": "Host.v2", + "abi_version": 2, + "functions": [ + { + "fn_id": 1, + "js_path": ["document", "get"], + "effect": "READ", + "arity": 1, + "arg_schema": [{ "type": "string" }], + "return_schema": { "type": "dv" }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [2048] + }, + "error_codes": [ + { "code": "INVALID_PATH", "tag": "host/invalid_path" }, + { "code": "LIMIT_EXCEEDED", "tag": "host/limit" }, + { "code": "NOT_FOUND", "tag": "host/not_found" } + ] + }, + { + "fn_id": 2, + "js_path": ["document", "getCanonical"], + "effect": "READ", + "arity": 1, + "arg_schema": [{ "type": "string" }], + "return_schema": { "type": "dv" }, + "gas": { + "schedule_id": "doc-read-v1", + "base": 20, + "k_arg_bytes": 1, + "k_ret_bytes": 1, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 4096, + "max_response_bytes": 262144, + "max_units": 1000, + "arg_utf8_max": [2048] + }, + "error_codes": [ + { "code": "INVALID_PATH", "tag": "host/invalid_path" }, + { "code": "LIMIT_EXCEEDED", "tag": "host/limit" }, + { "code": "NOT_FOUND", "tag": "host/not_found" } + ] + }, + { + "fn_id": 3, + "js_path": ["emit"], + "effect": "EMIT", + "arity": 1, + "arg_schema": [{ "type": "dv" }], + "return_schema": { "type": "null" }, + "gas": { + "schedule_id": "emit-v1", + "base": 5, + "k_arg_bytes": 1, + "k_ret_bytes": 0, + "k_units": 1 + }, + "limits": { + "max_request_bytes": 32768, + "max_response_bytes": 64, + "max_units": 1024 + }, + "error_codes": [{ "code": "LIMIT_EXCEEDED", "tag": "host/limit" }] + } + ] +} diff --git a/libs/test-harness/fixtures/library-reuse/binary-base64-entry.ts b/libs/test-harness/fixtures/library-reuse/binary-base64-entry.ts new file mode 100644 index 0000000..331781e --- /dev/null +++ b/libs/test-harness/fixtures/library-reuse/binary-base64-entry.ts @@ -0,0 +1,12 @@ +import { fromByteArray, toByteArray } from 'base64-js'; + +const bytes = toByteArray('AQIDBAUGBwg='); +const sum = bytes.reduce((acc, value) => acc + value, 0); + +export default { + length: bytes.length, + sum, + first: bytes[0], + last: bytes[bytes.length - 1], + reencoded: fromByteArray(bytes), +}; diff --git a/libs/test-harness/fixtures/library-reuse/binary-sha256-entry.ts b/libs/test-harness/fixtures/library-reuse/binary-sha256-entry.ts new file mode 100644 index 0000000..77f07e7 --- /dev/null +++ b/libs/test-harness/fixtures/library-reuse/binary-sha256-entry.ts @@ -0,0 +1,16 @@ +import { sha256 } from '@noble/hashes/sha256'; +import { bytesToHex } from '@noble/hashes/utils'; + +const digest = sha256( + Uint8Array.from([ + 98, 108, 117, 101, 45, 113, 117, 105, 99, 107, 106, 115, 45, 98, 105, 110, + 97, 114, 121, 45, 102, 105, 120, 116, 117, 114, 101, + ]), +); + +export default { + hex: bytesToHex(digest), + length: digest.length, + first: digest[0], + last: digest[digest.length - 1], +}; diff --git a/libs/test-harness/fixtures/library-reuse/chess-entry.ts b/libs/test-harness/fixtures/library-reuse/chess-entry.ts new file mode 100644 index 0000000..f32313f --- /dev/null +++ b/libs/test-harness/fixtures/library-reuse/chess-entry.ts @@ -0,0 +1,8 @@ +import { Chess } from 'chess.js'; + +const chess = new Chess(); +const legalMoves = chess.moves({ verbose: true }); + +export default legalMoves.some( + (move) => move.from === 'e2' && move.to === 'e6', +); diff --git a/libs/test-harness/package.json b/libs/test-harness/package.json index 439cd4c..11fde70 100644 --- a/libs/test-harness/package.json +++ b/libs/test-harness/package.json @@ -34,6 +34,9 @@ "dependencies": { "@blue-quickjs/abi-manifest": "workspace:*", "@blue-quickjs/dv": "workspace:*", + "@noble/hashes": "^1.8.0", + "base64-js": "^1.5.1", + "chess.js": "^1.4.0", "tslib": "^2.3.0" } } diff --git a/libs/test-harness/src/index.ts b/libs/test-harness/src/index.ts index c89ecbc..b480eba 100644 --- a/libs/test-harness/src/index.ts +++ b/libs/test-harness/src/index.ts @@ -1,7 +1,11 @@ export * from './lib/abi-manifest-fixtures.js'; +export * from './lib/binary-library-fixtures.js'; +export * from './lib/chess-library-fixtures.js'; export * from './lib/determinism-fixtures.js'; +export * from './lib/module-pack-fixtures.js'; export * from './lib/eval-output.js'; export * from './lib/gas-fixtures.js'; +export * from './lib/example-fixtures.js'; export * from './lib/smoke-fixtures.js'; export * from './lib/test-harness.js'; export * from './lib/deterministic-output.js'; diff --git a/libs/test-harness/src/lib/abi-manifest-fixtures.spec.ts b/libs/test-harness/src/lib/abi-manifest-fixtures.spec.ts index 1e4d28d..70c0972 100644 --- a/libs/test-harness/src/lib/abi-manifest-fixtures.spec.ts +++ b/libs/test-harness/src/lib/abi-manifest-fixtures.spec.ts @@ -8,6 +8,10 @@ import { HOST_V1_BYTES_HEX, HOST_V1_HASH, HOST_V1_MANIFEST, + HOST_V2_BYTES, + HOST_V2_BYTES_HEX, + HOST_V2_HASH, + HOST_V2_MANIFEST, } from './abi-manifest-fixtures.js'; const here = path.dirname(fileURLToPath(import.meta.url)); @@ -32,4 +36,20 @@ describe('abi-manifest fixture parity', () => { ); expect(HOST_V1_BYTES).toEqual(fileBytes); }); + + it('matches the checked-in host-v2 files', () => { + const fileManifest = JSON.parse(readText('host-v2.json')); + expect(HOST_V2_MANIFEST).toEqual(fileManifest); + + const fileHex = readText('host-v2.bytes.hex'); + expect(HOST_V2_BYTES_HEX).toEqual(fileHex); + + const fileHash = readText('host-v2.hash'); + expect(HOST_V2_HASH).toEqual(fileHash); + + const fileBytes = Uint8Array.from( + fileHex.match(/.{1,2}/g)?.map((byte) => parseInt(byte, 16)) ?? [], + ); + expect(HOST_V2_BYTES).toEqual(fileBytes); + }); }); diff --git a/libs/test-harness/src/lib/abi-manifest-fixtures.ts b/libs/test-harness/src/lib/abi-manifest-fixtures.ts index 3782435..fef0ff6 100644 --- a/libs/test-harness/src/lib/abi-manifest-fixtures.ts +++ b/libs/test-harness/src/lib/abi-manifest-fixtures.ts @@ -1,7 +1,11 @@ -// Re-export the public Host.v1 manifest fixtures for internal consumers. +// Re-export the public Host.v1/Host.v2 manifest fixtures for internal consumers. export { HOST_V1_BYTES, HOST_V1_BYTES_HEX, HOST_V1_HASH, HOST_V1_MANIFEST, + HOST_V2_BYTES, + HOST_V2_BYTES_HEX, + HOST_V2_HASH, + HOST_V2_MANIFEST, } from '@blue-quickjs/abi-manifest'; diff --git a/libs/test-harness/src/lib/binary-library-fixtures.ts b/libs/test-harness/src/lib/binary-library-fixtures.ts new file mode 100644 index 0000000..cef1703 --- /dev/null +++ b/libs/test-harness/src/lib/binary-library-fixtures.ts @@ -0,0 +1,45 @@ +import { HOST_V2_HASH, HOST_V2_MANIFEST } from './abi-manifest-fixtures.js'; +import { DETERMINISM_INPUT } from './determinism-fixtures.js'; + +export interface BinaryLibraryFixture { + name: string; + entryPath: string; + expectedValue: Record; +} + +export const BINARY_LIBRARY_PROGRAM_BASE = { + abiId: 'Host.v2', + abiVersion: 2, + abiManifestHash: HOST_V2_HASH, + executionProfile: 'compat-binary-v1' as const, +}; + +export const BINARY_LIBRARY_INPUT = DETERMINISM_INPUT; +export const BINARY_LIBRARY_GAS_LIMIT = 5_000_000n; +export const BINARY_LIBRARY_MANIFEST = HOST_V2_MANIFEST; + +export const BINARY_LIBRARY_FIXTURES: BinaryLibraryFixture[] = [ + { + name: 'base64-js-roundtrip', + entryPath: + 'libs/test-harness/fixtures/library-reuse/binary-base64-entry.ts', + expectedValue: { + length: 8, + sum: 36, + first: 1, + last: 8, + reencoded: 'AQIDBAUGBwg=', + }, + }, + { + name: 'noble-sha256-hex', + entryPath: + 'libs/test-harness/fixtures/library-reuse/binary-sha256-entry.ts', + expectedValue: { + hex: '641041dbb216456635a87ee5a1183e0b7462484d205c246eabecf274427efaad', + length: 32, + first: 100, + last: 173, + }, + }, +]; diff --git a/libs/test-harness/src/lib/chess-library-fixtures.ts b/libs/test-harness/src/lib/chess-library-fixtures.ts new file mode 100644 index 0000000..554feef --- /dev/null +++ b/libs/test-harness/src/lib/chess-library-fixtures.ts @@ -0,0 +1,18 @@ +import { HOST_V1_HASH, HOST_V1_MANIFEST } from './abi-manifest-fixtures.js'; +import { DETERMINISM_INPUT } from './determinism-fixtures.js'; + +export const CHESS_LIBRARY_ENTRY_PATH = + 'libs/test-harness/fixtures/library-reuse/chess-entry.ts'; + +export const CHESS_E2E6_EXPECTED_LEGAL = false; + +export const CHESS_LIBRARY_PROGRAM_BASE = { + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + executionProfile: 'compat-general-v1' as const, +}; + +export const CHESS_LIBRARY_INPUT = DETERMINISM_INPUT; +export const CHESS_LIBRARY_GAS_LIMIT = 5_000_000n; +export const CHESS_LIBRARY_MANIFEST = HOST_V1_MANIFEST; diff --git a/libs/test-harness/src/lib/determinism-fixtures.ts b/libs/test-harness/src/lib/determinism-fixtures.ts index eff96e8..e2f9bae 100644 --- a/libs/test-harness/src/lib/determinism-fixtures.ts +++ b/libs/test-harness/src/lib/determinism-fixtures.ts @@ -1,12 +1,22 @@ import type { AbiManifest } from '@blue-quickjs/abi-manifest'; -import type { DV } from '@blue-quickjs/dv'; -import { HOST_V1_HASH, HOST_V1_MANIFEST } from './abi-manifest-fixtures.js'; +import type { DV, DV2 } from '@blue-quickjs/dv'; +import { + HOST_V1_HASH, + HOST_V1_MANIFEST, + HOST_V2_HASH, + HOST_V2_MANIFEST, +} from './abi-manifest-fixtures.js'; export interface DeterminismProgramArtifact { code: string; abiId: string; abiVersion: number; abiManifestHash: string; + executionProfile?: + | 'baseline-v1' + | 'compat-regexp-v1' + | 'compat-general-v1' + | 'compat-binary-v1'; engineBuildHash?: string; } @@ -39,19 +49,19 @@ export interface DeterminismHostHandlers { document: { get: ( path: string, - ) => { ok: DV; units: number } | { err: HostError; units: number }; + ) => { ok: DV2; units: number } | { err: HostError; units: number }; getCanonical: ( path: string, - ) => { ok: DV; units: number } | { err: HostError; units: number }; + ) => { ok: DV2; units: number } | { err: HostError; units: number }; }; emit: ( - value: DV, + value: DV2, ) => { ok: null; units: number } | { err: HostError; units: number }; } export interface DeterminismHostEnvironment { handlers: DeterminismHostHandlers; - emitted: DV[]; + emitted: DV2[]; } export interface DeterminismFixtureBaseline { @@ -92,7 +102,7 @@ const ERROR_PATHS = new Map([ ]); export function createDeterminismHost(): DeterminismHostEnvironment { - const emitted: DV[] = []; + const emitted: DV2[] = []; const documentHash = HOST_V1_HASH; const resolveError = (path: string): HostError | null => @@ -105,6 +115,9 @@ export function createDeterminismHost(): DeterminismHostEnvironment { if (error) { return { err: error, units: 2 }; } + if (path === 'bytes/payload') { + return { ok: Uint8Array.from([222, 173, 190, 239]), units: 11 }; + } return { ok: { path, @@ -126,7 +139,7 @@ export function createDeterminismHost(): DeterminismHostEnvironment { }; }, }, - emit: (value: DV) => { + emit: (value: DV2) => { emitted.push(value); return { ok: null, units: 1 }; }, @@ -141,6 +154,12 @@ const BASE_PROGRAM = { abiManifestHash: HOST_V1_HASH, } satisfies Omit; +const BASE_PROGRAM_V2 = { + abiId: 'Host.v2', + abiVersion: 2, + abiManifestHash: HOST_V2_HASH, +} satisfies Omit; + export const DETERMINISM_FIXTURES: DeterminismFixture[] = [ { name: 'doc-read', @@ -167,8 +186,8 @@ export const DETERMINISM_FIXTURES: DeterminismFixture[] = [ 'b37ef077d8dbd7ca3b846595288f5f3c408f658b388aa27a09bca31ec260bd74', errorCode: null, errorTag: null, - gasUsed: 1094n, - gasRemaining: 48906n, + gasUsed: 175n, + gasRemaining: 49825n, tapeHash: '497d3a537f25c9892ff8b211e4d10b534a15f3c4baee242ed78b275e6f4fbe95', tapeLength: 1, @@ -198,8 +217,8 @@ export const DETERMINISM_FIXTURES: DeterminismFixture[] = [ 'f92ef306595931cdecb1c5e448a6dd343b70ef6ed52508e7007f918086349ae1', errorCode: null, errorTag: null, - gasUsed: 1047n, - gasRemaining: 48953n, + gasUsed: 252n, + gasRemaining: 49748n, tapeHash: '92a9661491894b76b25edbdbfc5c50985edd19dcbce342b400053daf1ab77a28', tapeLength: 1, @@ -233,8 +252,8 @@ export const DETERMINISM_FIXTURES: DeterminismFixture[] = [ '55caac84e0b4ae1d4ba112253dffeeb3d380d18902846171b94c84533813842a', errorCode: null, errorTag: null, - gasUsed: 1803n, - gasRemaining: 48197n, + gasUsed: 478n, + gasRemaining: 49522n, tapeHash: '87ebafc74f16872c87953ac8856cc3403168b5040d7552cff6e0a74667da5e02', tapeLength: 4, @@ -267,8 +286,8 @@ export const DETERMINISM_FIXTURES: DeterminismFixture[] = [ '95e87a4f23c4cf45119e800b24933e7549ddc878de6dcd4a13097a4a2970258a', errorCode: null, errorTag: null, - gasUsed: 1582n, - gasRemaining: 48418n, + gasUsed: 431n, + gasRemaining: 49569n, tapeHash: 'bbc6919589461f5ee17a240edaf824f71ecb0269958273ddd815cb783aeb10e6', tapeLength: 3, @@ -303,12 +322,186 @@ export const DETERMINISM_FIXTURES: DeterminismFixture[] = [ 'b19cd2f9dc8d93cb259a85f365378dd4e5b97f0a93adff0ac7d3f0b89c10ac2f', errorCode: null, errorTag: null, - gasUsed: 1873n, - gasRemaining: 48127n, + gasUsed: 145n, + gasRemaining: 49855n, + tapeHash: null, + tapeLength: 0, + }, + }, + { + name: 'async-promise-chain', + program: { + ...BASE_PROGRAM, + executionProfile: 'compat-general-v1', + code: ` + (() => Promise.resolve(40).then((value) => value + 2))() + `.trim(), + }, + input: DETERMINISM_INPUT, + gasLimit: DETERMINISM_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + createHost: createDeterminismHost, + expected: { + resultHash: + '7f83f7bda2d63959d34767689f06d47576683d378d9eb8d09386c9a020395c53', + errorCode: null, + errorTag: null, + gasUsed: 128n, + gasRemaining: 49872n, + tapeHash: null, + tapeLength: 0, + }, + }, + { + name: 'async-queue-microtask-host', + program: { + ...BASE_PROGRAM, + executionProfile: 'compat-general-v1', + code: ` + (() => { + queueMicrotask(() => Host.v1.emit({ phase: 'microtask' })); + return Promise.resolve({ ok: true }); + })() + `.trim(), + }, + input: DETERMINISM_INPUT, + gasLimit: DETERMINISM_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + createHost: createDeterminismHost, + expected: { + resultHash: + '20a934991093b3d9bfcb5f3c05871eb1db002d19469c29ea3ae1ff7e4a29cd02', + errorCode: null, + errorTag: null, + gasUsed: 169n, + gasRemaining: 49831n, + tapeHash: + '43c068fe25380b52c96b71cbc266343a90afc80c928ebde6a7d967c8c57b6e5c', + tapeLength: 1, + }, + }, + { + name: 'async-promise-rejection', + program: { + ...BASE_PROGRAM, + executionProfile: 'compat-general-v1', + code: ` + (() => Promise.reject(new Error('async-failure')))() + `.trim(), + }, + input: DETERMINISM_INPUT, + gasLimit: DETERMINISM_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + createHost: createDeterminismHost, + expected: { + resultHash: null, + errorCode: 'UNKNOWN', + errorTag: 'vm/unknown', + gasUsed: 87n, + gasRemaining: 49913n, + tapeHash: null, + tapeLength: 0, + }, + }, + { + name: 'compat-stable-sort', + program: { + ...BASE_PROGRAM, + executionProfile: 'compat-general-v1', + code: ` + (() => { + const records = [ + { id: 'a', group: 1 }, + { id: 'b', group: 1 }, + { id: 'c', group: 2 }, + { id: 'd', group: 1 }, + ]; + records.sort((left, right) => left.group - right.group); + return records.map((record) => record.id); + })() + `.trim(), + }, + input: DETERMINISM_INPUT, + gasLimit: DETERMINISM_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + createHost: createDeterminismHost, + expected: { + resultHash: + '950f57b0bb4280b09b5a63004acc9c50811ca16cea7c932494f47cb3cfb23c04', + errorCode: null, + errorTag: null, + gasUsed: 1020n, + gasRemaining: 48980n, tapeHash: null, tapeLength: 0, }, }, + { + name: 'compat-console-shim', + program: { + ...BASE_PROGRAM, + executionProfile: 'compat-general-v1', + code: ` + (() => { + console.info('deterministic', 7); + return { ok: true }; + })() + `.trim(), + }, + input: DETERMINISM_INPUT, + gasLimit: DETERMINISM_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + createHost: createDeterminismHost, + expected: { + resultHash: + '20a934991093b3d9bfcb5f3c05871eb1db002d19469c29ea3ae1ff7e4a29cd02', + errorCode: null, + errorTag: null, + gasUsed: 139n, + gasRemaining: 49861n, + tapeHash: + 'c481a1396ab5097cc8aa68fd11c1bb6e96d63259dba00b560bf49489fe5b2e3f', + tapeLength: 1, + }, + }, + { + name: 'compat-binary-host-v2-bytes-roundtrip', + program: { + ...BASE_PROGRAM_V2, + executionProfile: 'compat-binary-v1', + code: ` + (() => { + const payload = Host.v2.document.get('bytes/payload'); + Host.v2.emit(payload); + let sum = 0; + for (const byte of payload) { + sum += byte; + } + return { + length: payload.byteLength, + first: payload[0], + last: payload[payload.byteLength - 1], + sum, + }; + })() + `.trim(), + }, + input: DETERMINISM_INPUT, + gasLimit: DETERMINISM_GAS_LIMIT, + manifest: HOST_V2_MANIFEST, + createHost: createDeterminismHost, + expected: { + resultHash: + 'a538717d219fa0484c601ef7b5b63704c90cb9ae0406495b9f0083989a9fb2f8', + errorCode: null, + errorTag: null, + gasUsed: 253n, + gasRemaining: 49747n, + tapeHash: + 'b2d3a3b07a1be6b39cd854077910a2bc839c281281275c2c137f6a704723a734', + tapeLength: 2, + }, + }, { name: 'json-builtins', program: { @@ -328,8 +521,8 @@ export const DETERMINISM_FIXTURES: DeterminismFixture[] = [ 'd3cabc4fcb3aaddef313e841cd56fec5936b96a44a7d45eff624b81dd9e221d8', errorCode: null, errorTag: null, - gasUsed: 599n, - gasRemaining: 49401n, + gasUsed: 154n, + gasRemaining: 49846n, tapeHash: null, tapeLength: 0, }, @@ -353,8 +546,8 @@ export const DETERMINISM_FIXTURES: DeterminismFixture[] = [ resultHash: null, errorCode: 'INVALID_PATH', errorTag: 'host/invalid_path', - gasUsed: 776n, - gasRemaining: 49224n, + gasUsed: 144n, + gasRemaining: 49856n, tapeHash: '79af1be3f347fffc766bbe0baef9a183f0d6ee206468954d8f2adb9c146b9ddc', tapeLength: 1, @@ -379,8 +572,8 @@ export const DETERMINISM_FIXTURES: DeterminismFixture[] = [ resultHash: null, errorCode: 'LIMIT_EXCEEDED', errorTag: 'host/limit', - gasUsed: 774n, - gasRemaining: 49226n, + gasUsed: 143n, + gasRemaining: 49857n, tapeHash: '4894237cf19c834c9bff793693a158be3443e56df132773f6c61c7aed456a088', tapeLength: 1, @@ -405,8 +598,8 @@ export const DETERMINISM_FIXTURES: DeterminismFixture[] = [ resultHash: null, errorCode: 'NOT_FOUND', errorTag: 'host/not_found', - gasUsed: 771n, - gasRemaining: 49229n, + gasUsed: 140n, + gasRemaining: 49860n, tapeHash: 'a540c3ce0fd4043d8c3262e3c1ae2bc6bb50d3e17d0cc1dd2a8af8957eaca013', tapeLength: 1, diff --git a/libs/test-harness/src/lib/example-fixtures.ts b/libs/test-harness/src/lib/example-fixtures.ts new file mode 100644 index 0000000..304d6f2 --- /dev/null +++ b/libs/test-harness/src/lib/example-fixtures.ts @@ -0,0 +1,134 @@ +export type ExampleFixtureSuite = + | 'gas-sample' + | 'gas-boundary' + | 'module-pack' + | 'determinism' + | 'chess-library' + | 'binary-library'; + +export interface ExampleFixtureTarget { + suite: ExampleFixtureSuite; + fixtureName: string; +} + +export interface ExampleCorpusEntry { + id: number; + slug: string; + title: string; + profile: string | string[]; + sourcePaths: string[]; + coverage: ExampleFixtureTarget[]; +} + +export const EXAMPLE_CORPUS: ExampleCorpusEntry[] = [ + { + id: 1, + slug: 'basic-script', + title: 'Basic deterministic script', + profile: 'baseline-v1', + sourcePaths: ['examples/01-basic-script/program.js'], + coverage: [{ suite: 'gas-sample', fixtureName: 'return-1' }], + }, + { + id: 2, + slug: 'module-pack', + title: 'Standard ESM module-pack', + profile: 'baseline-v1', + sourcePaths: [ + 'examples/02-module-pack/entry.js', + 'examples/02-module-pack/values.js', + ], + coverage: [ + { suite: 'module-pack', fixtureName: 'module-pack-default-export' }, + ], + }, + { + id: 3, + slug: 'library-reuse', + title: 'Real npm library reuse', + profile: ['compat-general-v1', 'compat-binary-v1'], + sourcePaths: [ + 'examples/03-library-reuse/chess-entry.ts', + 'examples/03-library-reuse/binary-base64-entry.ts', + ], + coverage: [ + { suite: 'chess-library', fixtureName: 'chess-e2e6' }, + { suite: 'binary-library', fixtureName: 'base64-js-roundtrip' }, + { suite: 'binary-library', fixtureName: 'noble-sha256-hex' }, + ], + }, + { + id: 4, + slug: 'promises-async', + title: 'Promises / async / microtasks', + profile: 'compat-general-v1', + sourcePaths: ['examples/04-promises-async/program.js'], + coverage: [{ suite: 'determinism', fixtureName: 'async-promise-chain' }], + }, + { + id: 5, + slug: 'promises-library-host', + title: 'Promises + imported library + host call', + profile: 'compat-general-v1', + sourcePaths: [ + 'examples/05-promises-library-host/entry.js', + 'examples/05-promises-library-host/lib.js', + ], + coverage: [ + { + suite: 'module-pack', + fixtureName: 'module-pack-async-import-host-call', + }, + ], + }, + { + id: 6, + slug: 'binary-host-v2', + title: 'Binary / typed arrays / Host.v2 DV2', + profile: 'compat-binary-v1', + sourcePaths: ['examples/06-binary-host-v2/program.js'], + coverage: [ + { + suite: 'determinism', + fixtureName: 'compat-binary-host-v2-bytes-roundtrip', + }, + ], + }, + { + id: 7, + slug: 'console-shim', + title: 'Console shim determinism', + profile: 'compat-general-v1', + sourcePaths: ['examples/07-console-shim/program.js'], + coverage: [{ suite: 'determinism', fixtureName: 'compat-console-shim' }], + }, + { + id: 8, + slug: 'stable-sort', + title: 'Stable sort determinism', + profile: 'compat-general-v1', + sourcePaths: ['examples/08-stable-sort/program.js'], + coverage: [{ suite: 'determinism', fixtureName: 'compat-stable-sort' }], + }, + { + id: 9, + slug: 'kitchen-sink', + title: 'Kitchen sink app', + profile: 'compat-general-v1', + sourcePaths: [ + 'examples/09-kitchen-sink/entry.js', + 'examples/09-kitchen-sink/workflow.js', + ], + coverage: [ + { suite: 'module-pack', fixtureName: 'module-pack-kitchen-sink' }, + ], + }, + { + id: 10, + slug: 'max-gas-policy', + title: 'Max-gas policy / OOG boundary', + profile: 'baseline-v1', + sourcePaths: ['examples/10-max-gas-policy/program.js'], + coverage: [{ suite: 'gas-boundary', fixtureName: 'loop-10k' }], + }, +]; diff --git a/libs/test-harness/src/lib/gas-equivalence.spec.ts b/libs/test-harness/src/lib/gas-equivalence.spec.ts index 3be4ad0..508aaab 100644 --- a/libs/test-harness/src/lib/gas-equivalence.spec.ts +++ b/libs/test-harness/src/lib/gas-equivalence.spec.ts @@ -62,42 +62,156 @@ const cases = [ { name: 'loop-oog', fixture: 'loop-counter.js', - gasLimit: 600n, + gasLimit: 146n, }, { name: 'constant', fixture: 'constant.js', - gasLimit: 147n, + gasLimit: 37n, }, { name: 'addition', fixture: 'addition.js', - gasLimit: 154n, + gasLimit: 39n, }, { name: 'string-repeat', fixture: 'string-repeat.js', - gasLimit: 5000n, + gasLimit: 84n, }, { name: 'json-parse', fixture: 'json-parse-small.js', - gasLimit: 217n, + gasLimit: 77n, }, { name: 'json-parse-oog', fixture: 'json-parse-oog.js', - gasLimit: 216n, + gasLimit: 76n, }, { name: 'json-stringify', fixture: 'json-stringify-small.js', - gasLimit: 241n, + gasLimit: 82n, }, { name: 'json-stringify-oog', fixture: 'json-stringify-oog.js', - gasLimit: 240n, + gasLimit: 81n, + }, + { + name: 'array-map-single', + fixture: 'array-map-single.js', + gasLimit: 143n, + }, + { + name: 'array-map-single-oog', + fixture: 'array-map-single.js', + gasLimit: 142n, + }, + { + name: 'array-map-multi', + fixture: 'array-map-multi.js', + gasLimit: 179n, + }, + { + name: 'array-map-multi-oog', + fixture: 'array-map-multi.js', + gasLimit: 178n, + }, + { + name: 'array-filter-multi', + fixture: 'array-filter-multi.js', + gasLimit: 189n, + }, + { + name: 'array-filter-multi-oog', + fixture: 'array-filter-multi.js', + gasLimit: 188n, + }, + { + name: 'array-reduce-multi', + fixture: 'array-reduce-multi.js', + gasLimit: 189n, + }, + { + name: 'array-reduce-multi-oog', + fixture: 'array-reduce-multi.js', + gasLimit: 188n, + }, + { + name: 'gc-pending', + fixture: 'gc-pending.js', + gasLimit: 89n, + }, + { + name: 'gc-pending-oog', + fixture: 'gc-pending.js', + gasLimit: 88n, + }, +]; + +interface BoundaryFixtureCase { + name: string; + fixture: string; + expectedFirstSuccessGas: bigint; +} + +const boundaryCases: BoundaryFixtureCase[] = [ + { + name: 'opcode-addition', + fixture: 'addition.js', + expectedFirstSuccessGas: 39n, + }, + { + name: 'opcode-constant', + fixture: 'constant.js', + expectedFirstSuccessGas: 37n, + }, + { + name: 'loop-counter', + fixture: 'loop-counter.js', + expectedFirstSuccessGas: 146n, + }, + { + name: 'string-repeat', + fixture: 'string-repeat.js', + expectedFirstSuccessGas: 84n, + }, + { + name: 'json-parse-small', + fixture: 'json-parse-small.js', + expectedFirstSuccessGas: 77n, + }, + { + name: 'json-stringify-small', + fixture: 'json-stringify-small.js', + expectedFirstSuccessGas: 82n, + }, + { + name: 'array-map-single', + fixture: 'array-map-single.js', + expectedFirstSuccessGas: 143n, + }, + { + name: 'array-map-multi', + fixture: 'array-map-multi.js', + expectedFirstSuccessGas: 179n, + }, + { + name: 'array-filter-multi', + fixture: 'array-filter-multi.js', + expectedFirstSuccessGas: 189n, + }, + { + name: 'array-reduce-multi', + fixture: 'array-reduce-multi.js', + expectedFirstSuccessGas: 189n, + }, + { + name: 'gc-pending', + fixture: 'gc-pending.js', + expectedFirstSuccessGas: 89n, }, ]; @@ -136,57 +250,122 @@ const wasm32Expectations: Record = { }, 'loop-oog': { kind: 'RESULT', - payload: '02016c', + payload: '03', value: 3, - gasRemaining: 203n, - gasUsed: 397n, + gasRemaining: 0n, + gasUsed: 146n, }, constant: { kind: 'RESULT', - payload: '02014b', + payload: '01', value: 1, - gasRemaining: 58n, - gasUsed: 89n, + gasRemaining: 0n, + gasUsed: 37n, }, addition: { kind: 'RESULT', - payload: '02016c', + payload: '03', value: 3, - gasRemaining: 58n, - gasUsed: 96n, + gasRemaining: 0n, + gasUsed: 39n, }, 'string-repeat': { kind: 'RESULT', - payload: '0201e980fa0c', + payload: '198000', value: 32768, - gasRemaining: 2687n, - gasUsed: 2313n, + gasRemaining: 0n, + gasUsed: 84n, }, 'json-parse': { kind: 'RESULT', payload: 'a261620262616101', value: { b: 2, aa: 1 }, gasRemaining: 0n, - gasUsed: 217n, + gasUsed: 77n, }, 'json-parse-oog': { kind: 'ERROR', payload: 'OutOfGas: out of gas', gasRemaining: 0n, - gasUsed: 216n, + gasUsed: 76n, }, 'json-stringify': { kind: 'RESULT', payload: '6e7b2262223a322c226161223a317d', value: '{"b":2,"aa":1}', gasRemaining: 0n, - gasUsed: 241n, + gasUsed: 82n, }, 'json-stringify-oog': { kind: 'ERROR', payload: 'OutOfGas: out of gas', gasRemaining: 0n, - gasUsed: 240n, + gasUsed: 81n, + }, + 'array-map-single': { + kind: 'RESULT', + payload: '01', + value: 1, + gasRemaining: 0n, + gasUsed: 143n, + }, + 'array-map-single-oog': { + kind: 'ERROR', + payload: 'OutOfGas: out of gas', + gasRemaining: 0n, + gasUsed: 142n, + }, + 'array-map-multi': { + kind: 'RESULT', + payload: '05', + value: 5, + gasRemaining: 0n, + gasUsed: 179n, + }, + 'array-map-multi-oog': { + kind: 'ERROR', + payload: 'OutOfGas: out of gas', + gasRemaining: 0n, + gasUsed: 178n, + }, + 'array-filter-multi': { + kind: 'RESULT', + payload: '05', + value: 5, + gasRemaining: 0n, + gasUsed: 189n, + }, + 'array-filter-multi-oog': { + kind: 'ERROR', + payload: 'OutOfGas: out of gas', + gasRemaining: 0n, + gasUsed: 188n, + }, + 'array-reduce-multi': { + kind: 'RESULT', + payload: '0f', + value: 15, + gasRemaining: 0n, + gasUsed: 189n, + }, + 'array-reduce-multi-oog': { + kind: 'ERROR', + payload: 'OutOfGas: out of gas', + gasRemaining: 0n, + gasUsed: 188n, + }, + 'gc-pending': { + kind: 'RESULT', + payload: '1a00124f80', + value: 1200000, + gasRemaining: 0n, + gasUsed: 89n, + }, + 'gc-pending-oog': { + kind: 'ERROR', + payload: 'OutOfGas: out of gas', + gasRemaining: 0n, + gasUsed: 88n, }, }; @@ -198,6 +377,7 @@ let wasmInit: contextPtr: WasmPtr, contextLength: number, gasLimit: bigint, + featureFlags: number, ) => WasmPtr) | null = null; let wasmEval: ((code: string) => WasmPtr) | null = null; @@ -228,6 +408,7 @@ beforeAll(async () => { ptrArgType, 'number', 'bigint', + 'number', ]); wasmEval = wasmModule.cwrap('qjs_det_eval', ptrReturnType, ['string']); wasmFreeRuntime = wasmModule.cwrap('qjs_det_free', null, []); @@ -285,6 +466,7 @@ function runWasm(code: string, gasLimit: bigint): DeterministicOutput { contextPtr, CONTEXT_BLOB.length, gasLimit, + 0, ); if (errorPtr !== 0) { const message = readCString(wasmModule, errorPtr); @@ -325,6 +507,39 @@ describe('wasm gas outputs', () => { }); }); +describe('exact OOG boundaries', () => { + test.each(boundaryCases)( + '$name has identical first-success and last-failure boundaries', + ({ fixture, expectedFirstSuccessGas }) => { + const code = readFileSync(path.join(fixturesRoot, fixture), 'utf8'); + + const wasmBoundary = findOutOfGasBoundary( + (gasLimit) => runWasm(code, gasLimit), + expectedFirstSuccessGas + 64n, + ); + expect(wasmBoundary.firstSuccessGas).toBe(expectedFirstSuccessGas); + expect(wasmBoundary.lastFailureGas).toBe(expectedFirstSuccessGas - 1n); + expect(wasmBoundary.firstSuccess.gasUsed).toBe( + wasmBoundary.firstSuccessGas, + ); + expect(wasmBoundary.firstSuccess.gasRemaining).toBe(0n); + expect(isOutOfGasError(wasmBoundary.lastFailure)).toBe(true); + + const nativeBoundary = findOutOfGasBoundary( + (gasLimit) => runNative(code, gasLimit), + expectedFirstSuccessGas + 64n, + ); + expect(nativeBoundary.firstSuccessGas).toBe(wasmBoundary.firstSuccessGas); + expect(nativeBoundary.lastFailureGas).toBe(wasmBoundary.lastFailureGas); + expect(nativeBoundary.firstSuccess.gasUsed).toBe( + nativeBoundary.firstSuccessGas, + ); + expect(nativeBoundary.firstSuccess.gasRemaining).toBe(0n); + expect(isOutOfGasError(nativeBoundary.lastFailure)).toBe(true); + }, + ); +}); + function expectHarnessResult( actual: DeterministicOutput, expected: ExpectedResult, @@ -345,6 +560,51 @@ function expectHarnessResult( } } +function isOutOfGasError(output: DeterministicOutput): boolean { + return output.kind === 'ERROR' && output.payload.includes('OutOfGas'); +} + +function findOutOfGasBoundary( + run: (gasLimit: bigint) => DeterministicOutput, + initialUpperBound: bigint, +): { + firstSuccessGas: bigint; + lastFailureGas: bigint; + firstSuccess: DeterministicOutput; + lastFailure: DeterministicOutput; +} { + let upperGas = initialUpperBound; + let upperOutput = run(upperGas); + while (upperOutput.kind !== 'RESULT') { + upperGas *= 2n; + if (upperGas > 100_000_000n) { + throw new Error(`failed to find successful gas bound (last=${upperGas})`); + } + upperOutput = run(upperGas); + } + + let lowerGas = 0n; + let lowerOutput = run(lowerGas); + while (lowerGas + 1n < upperGas) { + const mid = (lowerGas + upperGas) >> 1n; + const midOutput = run(mid); + if (midOutput.kind === 'RESULT') { + upperGas = mid; + upperOutput = midOutput; + } else { + lowerGas = mid; + lowerOutput = midOutput; + } + } + + return { + firstSuccessGas: upperGas, + lastFailureGas: lowerGas, + firstSuccess: upperOutput, + lastFailure: lowerOutput, + }; +} + function bytesToHex(bytes: Uint8Array): string { return Array.from(bytes) .map((b) => b.toString(16).padStart(2, '0')) diff --git a/libs/test-harness/src/lib/gas-fixtures.ts b/libs/test-harness/src/lib/gas-fixtures.ts index 9f7fc62..599ce6a 100644 --- a/libs/test-harness/src/lib/gas-fixtures.ts +++ b/libs/test-harness/src/lib/gas-fixtures.ts @@ -52,8 +52,8 @@ export const GAS_SAMPLE_FIXTURES: GasFixture[] = [ expected: { resultHash: '4bf5122f344554c53bde2ebb8cd2b7e3d1600ad631c385a5d7cce23c7785459a', - gasUsed: 179n, - gasRemaining: 999821n, + gasUsed: 74n, + gasRemaining: 999926n, }, }, { @@ -77,8 +77,8 @@ export const GAS_SAMPLE_FIXTURES: GasFixture[] = [ expected: { resultHash: '5092d78885546599f50436ac88fee579843061290508ac2ef0efa541297e405b', - gasUsed: 17347n, - gasRemaining: 982653n, + gasUsed: 17099n, + gasRemaining: 982901n, }, }, { @@ -102,12 +102,12 @@ export const GAS_SAMPLE_FIXTURES: GasFixture[] = [ expected: { resultHash: 'a3fa3495623f19996818ce7b196fc524e687ef2cc4910a6ff628a76460c4e557', - gasUsed: 170347n, - gasRemaining: 829653n, + gasUsed: 170099n, + gasRemaining: 829901n, }, repeatSameContext: { count: 5, - expectedGasUsed: 170347n, + expectedGasUsed: 170099n, }, }, { @@ -131,8 +131,8 @@ export const GAS_SAMPLE_FIXTURES: GasFixture[] = [ expected: { resultHash: '5e8f74961ede79063fa728a34d36f7baf4a563b225df62e4eb9349b94d612a3f', - gasUsed: 61139n, - gasRemaining: 938861n, + gasUsed: 26100n, + gasRemaining: 973900n, }, }, { @@ -156,8 +156,8 @@ export const GAS_SAMPLE_FIXTURES: GasFixture[] = [ expected: { resultHash: '5e8f74961ede79063fa728a34d36f7baf4a563b225df62e4eb9349b94d612a3f', - gasUsed: 51115n, - gasRemaining: 948885n, + gasUsed: 26100n, + gasRemaining: 973900n, }, }, { @@ -185,8 +185,8 @@ export const GAS_SAMPLE_FIXTURES: GasFixture[] = [ expected: { resultHash: 'cbbec14103147af122feaff2419ad885d372d04bfd9d0af1714dd20dff24b6e3', - gasUsed: 40203n, - gasRemaining: 959797n, + gasUsed: 38144n, + gasRemaining: 961856n, }, }, ]; diff --git a/libs/test-harness/src/lib/module-pack-fixtures.ts b/libs/test-harness/src/lib/module-pack-fixtures.ts new file mode 100644 index 0000000..6f7a54d --- /dev/null +++ b/libs/test-harness/src/lib/module-pack-fixtures.ts @@ -0,0 +1,356 @@ +import type { AbiManifest } from '@blue-quickjs/abi-manifest'; +import type { DV } from '@blue-quickjs/dv'; +import { HOST_V1_HASH, HOST_V1_MANIFEST } from './abi-manifest-fixtures.js'; +import { + createDeterminismHost, + DETERMINISM_GAS_LIMIT, + DETERMINISM_INPUT, + type DeterminismHostEnvironment, + type DeterminismInputEnvelope, +} from './determinism-fixtures.js'; + +export interface ModulePackV1FixtureModule { + specifier: string; + source: string; + sourceMap?: string; +} + +export interface ModulePackV1Fixture { + version: 1; + entrySpecifier: string; + entryExport?: string; + modules: ModulePackV1FixtureModule[]; + graphHash: string; + builderVersion: string; + dependencyIntegrity: string; +} + +export interface ProgramArtifactV2ModulePackFixture { + version: 2; + abiId: string; + abiVersion: number; + abiManifestHash: string; + executionProfile: 'baseline-v1' | 'compat-general-v1'; + sourceKind: 'module-pack'; + source: { + modulePack: ModulePackV1Fixture; + }; +} + +export type ModulePackFixtureExpected = + | { + ok: true; + value: DV; + } + | { + ok: false; + errorCode: + | 'MODULE_SPECIFIER_NOT_FOUND' + | 'MODULE_EXPORT_MISSING' + | 'MODULE_RESOLUTION_ERROR' + | 'MODULE_EVALUATION_ERROR'; + errorTag: 'vm/module_pack'; + }; + +export interface ModulePackFixture { + name: string; + program: ProgramArtifactV2ModulePackFixture; + input: DeterminismInputEnvelope; + gasLimit: bigint; + manifest: AbiManifest; + createHost: () => DeterminismHostEnvironment; + expected: ModulePackFixtureExpected; +} + +const MODULE_PACK_BASE = { + version: 2 as const, + abiId: 'Host.v1', + abiVersion: 1, + abiManifestHash: HOST_V1_HASH, + executionProfile: 'baseline-v1' as const, + sourceKind: 'module-pack' as const, +}; + +const BUILDER_VERSION = 'deterministic-builder-v1'; +const DEPENDENCY_INTEGRITY = + 'aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa'; + +function createModulePack(options: { + entrySpecifier: string; + modules: ModulePackV1FixtureModule[]; + entryExport?: string; + graphHash: string; +}): ModulePackV1Fixture { + return { + version: 1, + entrySpecifier: options.entrySpecifier, + ...(options.entryExport ? { entryExport: options.entryExport } : {}), + modules: options.modules, + graphHash: options.graphHash, + builderVersion: BUILDER_VERSION, + dependencyIntegrity: DEPENDENCY_INTEGRITY, + }; +} + +export const MODULE_PACK_FIXTURES: ModulePackFixture[] = [ + { + name: 'module-pack-default-export', + program: { + ...MODULE_PACK_BASE, + source: { + modulePack: createModulePack({ + entrySpecifier: './entry.js', + graphHash: + '68df8be0dee6f4df62f54776c08a61cd42f9b39c74a4968d0217fc748b8b7863', + modules: [ + { + specifier: './entry.js', + source: + "import { base } from './values.js'; export default base + 1;\n", + }, + { + specifier: './values.js', + source: 'export const base = 6;\n', + }, + ], + }), + }, + }, + input: DETERMINISM_INPUT, + gasLimit: DETERMINISM_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + createHost: createDeterminismHost, + expected: { + ok: true, + value: 7, + }, + }, + { + name: 'module-pack-named-export', + program: { + ...MODULE_PACK_BASE, + source: { + modulePack: createModulePack({ + entrySpecifier: './entry.js', + entryExport: 'answer', + graphHash: + '212edbf5272cae51f21fbb306b41103ab57d94b37c0f0f90f0b234f4a8a81df8', + modules: [ + { + specifier: './entry.js', + source: + "import { left, right } from './parts.js'; export const answer = left + right;\n", + }, + { + specifier: './parts.js', + source: 'export const left = 20; export const right = 22;\n', + }, + ], + }), + }, + }, + input: DETERMINISM_INPUT, + gasLimit: DETERMINISM_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + createHost: createDeterminismHost, + expected: { + ok: true, + value: 42, + }, + }, + { + name: 'module-pack-cyclic-imports', + program: { + ...MODULE_PACK_BASE, + source: { + modulePack: createModulePack({ + entrySpecifier: './entry.js', + graphHash: + '4f66500f07dd2bbc0be1a9fb8121a3f9e30c633afdbc4753c269f5110f5d8ba4', + modules: [ + { + specifier: './entry.js', + source: + "import { valueFromB } from './b.js'; export default valueFromB;\n", + }, + { + specifier: './a.js', + source: + "import { getB } from './b.js'; export function getA() { return 40 + getB(); }\n", + }, + { + specifier: './b.js', + source: + "import { getA } from './a.js'; export function getB() { return 2; } export const valueFromB = getA();\n", + }, + ], + }), + }, + }, + input: DETERMINISM_INPUT, + gasLimit: DETERMINISM_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + createHost: createDeterminismHost, + expected: { + ok: true, + value: 42, + }, + }, + { + name: 'module-pack-host-call-tape', + program: { + ...MODULE_PACK_BASE, + source: { + modulePack: createModulePack({ + entrySpecifier: './entry.js', + graphHash: + '2cad30ee71aa78376357c526292004b4efc4864af0c93b0196a84a8e2730e67d', + modules: [ + { + specifier: './entry.js', + source: + "globalThis.Host.v1.emit({ kind: 'module-pack', path: 'path/to/module-pack-doc' });\nexport default { path: 'path/to/module-pack-doc', len: 23 };\n", + }, + ], + }), + }, + }, + input: DETERMINISM_INPUT, + gasLimit: DETERMINISM_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + createHost: createDeterminismHost, + expected: { + ok: true, + value: { path: 'path/to/module-pack-doc', len: 23 }, + }, + }, + { + name: 'module-pack-async-import-host-call', + program: { + ...MODULE_PACK_BASE, + executionProfile: 'compat-general-v1', + source: { + modulePack: createModulePack({ + entrySpecifier: './entry.js', + graphHash: + '629b89a6e192c62e9d7d0a1b6b2debd9bcad6b9110389e949ba5d86156bd000b', + modules: [ + { + specifier: './entry.js', + source: + 'import { plusOne } from "./lib.js";\nexport default Promise.resolve(plusOne(41)).then((value) => { Host.v1.emit({ phase: "async-lib", value }); return value; });\n', + }, + { + specifier: './lib.js', + source: 'export const plusOne = (value) => value + 1;\n', + }, + ], + }), + }, + }, + input: DETERMINISM_INPUT, + gasLimit: DETERMINISM_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + createHost: createDeterminismHost, + expected: { + ok: true, + value: 42, + }, + }, + { + name: 'module-pack-kitchen-sink', + program: { + ...MODULE_PACK_BASE, + executionProfile: 'compat-general-v1', + source: { + modulePack: createModulePack({ + entrySpecifier: './entry.js', + graphHash: + 'ce277312313ac06e3488d98b33b59213baf0d989beca4681b93cff31ba2532be', + modules: [ + { + specifier: './entry.js', + source: + 'import { summarize } from "./workflow.js";\nexport default (async () => {\n const doc = document("path/to/doc");\n const canonical = document.canonical("path/to/doc");\n const result = await summarize(doc.path, canonical.canonical);\n Host.v1.emit({ kind: "kitchen", result });\n return result;\n})();\n', + }, + { + specifier: './workflow.js', + source: + 'export async function summarize(path, canonical) {\n const queue = [];\n queueMicrotask(() => queue.push("micro"));\n await Promise.resolve();\n const records = [\n { id: "b", rank: 2 },\n { id: "a", rank: 1 },\n { id: "c", rank: 2 },\n ];\n records.sort((left, right) => left.rank - right.rank);\n return {\n path,\n canonical,\n order: records.map((record) => record.id).join(","),\n queue: queue.join(","),\n };\n}\n', + }, + ], + }), + }, + }, + input: DETERMINISM_INPUT, + gasLimit: DETERMINISM_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + createHost: createDeterminismHost, + expected: { + ok: true, + value: { + path: 'path/to/doc', + canonical: 'path/to/doc', + order: 'a,b,c', + queue: 'micro', + }, + }, + }, + { + name: 'module-pack-missing-entry-specifier', + program: { + ...MODULE_PACK_BASE, + source: { + modulePack: createModulePack({ + entrySpecifier: './missing.js', + graphHash: + 'd5708a847d11a9574dc665168733100dd503239075a444809380458ca05e608f', + modules: [ + { + specifier: './entry.js', + source: 'export default 1;\n', + }, + ], + }), + }, + }, + input: DETERMINISM_INPUT, + gasLimit: DETERMINISM_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + createHost: createDeterminismHost, + expected: { + ok: false, + errorCode: 'MODULE_SPECIFIER_NOT_FOUND', + errorTag: 'vm/module_pack', + }, + }, + { + name: 'module-pack-missing-export', + program: { + ...MODULE_PACK_BASE, + source: { + modulePack: createModulePack({ + entrySpecifier: './entry.js', + entryExport: 'missing', + graphHash: + '44d6a5d503fe3ddc0c932d2e0dbbaab85f996253d58ff0cfeb0eee905ff9d60e', + modules: [ + { + specifier: './entry.js', + source: 'export const value = 1;\n', + }, + ], + }), + }, + }, + input: DETERMINISM_INPUT, + gasLimit: DETERMINISM_GAS_LIMIT, + manifest: HOST_V1_MANIFEST, + createHost: createDeterminismHost, + expected: { + ok: false, + errorCode: 'MODULE_EXPORT_MISSING', + errorTag: 'vm/module_pack', + }, + }, +]; diff --git a/libs/test-harness/src/lib/smoke-fixtures.ts b/libs/test-harness/src/lib/smoke-fixtures.ts index 7c55d08..2284087 100644 --- a/libs/test-harness/src/lib/smoke-fixtures.ts +++ b/libs/test-harness/src/lib/smoke-fixtures.ts @@ -108,8 +108,8 @@ export const SMOKE_BASELINE: SmokeBaseline = { manifestHash: HOST_V1_HASH, resultHash: '4a13893d4d564c7c9e7dcb0b6bbc028b824268585a0cbbdb19ac28a34138f293', - gasUsed: 1638n, - gasRemaining: 48362n, + gasUsed: 397n, + gasRemaining: 49603n, emittedCount: 1, tapeLength: 3, tapeHash: '2ca437d26207d59b369ae74a448d497a79ae482071d61ff8b05fa78a7d5b570f', diff --git a/package.json b/package.json index a6ff8be..c355812 100644 --- a/package.json +++ b/package.json @@ -11,7 +11,23 @@ "test": "nx run-many -t test", "build": "nx run-many -t build", "typecheck": "nx run-many -t typecheck", - "lint": "nx run-many -t lint --all" + "lint": "nx run-many -t lint --all", + "docs:check-links": "node tools/release-evidence/check-doc-links.mjs", + "docs:verify-learning-path": "node tools/release-evidence/verify-learning-path.mjs", + "docs:check-freshness": "node tools/release-evidence/check-release-doc-freshness.mjs", + "quickstart:verify": "node tools/release-evidence/verify-readme-quickstart.mjs", + "playground:dev": "bash apps/bluequickjs-playground/scripts/dev.sh", + "playground:generate": "node apps/bluequickjs-playground/scripts/generate-playground-data.mjs", + "playground:check-generated": "node apps/bluequickjs-playground/scripts/generate-playground-data.mjs --check", + "release-evidence:synthesize": "node tools/release-evidence/synthesize-release-evidence.mjs", + "release-evidence:verify": "node tools/release-evidence/verify-release-evidence.mjs", + "release-evidence:test": "node --test tools/release-evidence/release-evidence.test.mjs", + "release-evidence:sbom": "node tools/release-evidence/generate-sbom.mjs", + "release-evidence:licenses": "node tools/release-evidence/generate-license-report.mjs", + "workload:check-public-package-versions": "node tools/workload-certification/check-public-package-versions.mjs", + "workload:check-pack-manifests": "node tools/workload-certification/check-pack-manifests.mjs", + "workload:compat-delta": "node apps/ecosystem-certifier/scripts/generate-compatibility-delta-report.mjs", + "publish-rehearsal:verdaccio": "node tools/workload-certification/run-verdaccio-publish-rehearsal.mjs" }, "private": true, "devDependencies": { diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 485a757..18eb7a8 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -99,6 +99,144 @@ importers: specifier: ^4.0.0 version: 4.0.15(@types/node@20.19.9)(@vitest/ui@4.0.15)(jiti@2.4.2)(jsdom@22.1.0)(terser@5.44.1)(yaml@2.8.2) + apps/bluequickjs-playground: + dependencies: + '@blue-quickjs/abi-manifest': + specifier: workspace:* + version: link:../../libs/abi-manifest + '@blue-quickjs/deterministic-builder': + specifier: workspace:* + version: link:../../libs/deterministic-builder + '@blue-quickjs/dv': + specifier: workspace:* + version: link:../../libs/dv + '@blue-quickjs/execution-profiles': + specifier: workspace:* + version: link:../../libs/execution-profiles + '@blue-quickjs/quickjs-runtime': + specifier: workspace:* + version: link:../../libs/quickjs-runtime + '@blue-quickjs/quickjs-wasm': + specifier: workspace:* + version: link:../../libs/quickjs-wasm + '@blue-quickjs/test-harness': + specifier: workspace:* + version: link:../../libs/test-harness + monaco-editor: + specifier: ^0.55.1 + version: 0.55.1 + tslib: + specifier: ^2.3.0 + version: 2.8.1 + + apps/ecosystem-certifier: + dependencies: + '@blue-quickjs/abi-manifest': + specifier: workspace:* + version: link:../../libs/abi-manifest + '@blue-quickjs/deterministic-builder': + specifier: workspace:* + version: link:../../libs/deterministic-builder + '@blue-quickjs/dv': + specifier: workspace:* + version: link:../../libs/dv + '@blue-quickjs/quickjs-runtime': + specifier: workspace:* + version: link:../../libs/quickjs-runtime + '@blue-quickjs/quickjs-wasm': + specifier: workspace:* + version: link:../../libs/quickjs-wasm + '@blue-quickjs/test-harness': + specifier: workspace:* + version: link:../../libs/test-harness + '@noble/hashes': + specifier: ^1.8.0 + version: 1.8.0 + array-move: + specifier: ^4.0.0 + version: 4.0.0 + base64-js: + specifier: ^1.5.1 + version: 1.5.1 + camelcase: + specifier: ^9.0.0 + version: 9.0.0 + chess.js: + specifier: ^1.4.0 + version: 1.4.0 + crc-32: + specifier: ^1.2.2 + version: 1.2.2 + decamelize: + specifier: ^6.0.1 + version: 6.0.1 + deepmerge: + specifier: ^4.3.1 + version: 4.3.1 + diff: + specifier: ^8.0.2 + version: 8.0.2 + dijkstrajs: + specifier: ^1.0.3 + version: 1.0.3 + escape-string-regexp: + specifier: ^5.0.0 + version: 5.0.0 + fast-deep-equal: + specifier: ^3.1.3 + version: 3.1.3 + fast-json-stable-stringify: + specifier: ^2.1.0 + version: 2.1.0 + fastest-levenshtein: + specifier: ^1.0.16 + version: 1.0.16 + fflate: + specifier: ^0.8.2 + version: 0.8.2 + graphlib: + specifier: ^2.1.8 + version: 2.1.8 + he: + specifier: ^1.2.0 + version: 1.2.0 + json-logic-js: + specifier: ^2.0.5 + version: 2.0.5 + linkify-it: + specifier: ^5.0.0 + version: 5.0.0 + lodash-es: + specifier: ^4.17.21 + version: 4.17.23 + markdown-it: + specifier: ^14.1.0 + version: 14.1.1 + path-to-regexp: + specifier: ^8.2.0 + version: 8.3.0 + query-string: + specifier: ^9.3.1 + version: 9.3.1 + semver: + specifier: ^7.7.3 + version: 7.7.3 + sort-keys: + specifier: ^6.0.0 + version: 6.0.0 + spark-md5: + specifier: ^3.0.2 + version: 3.0.2 + tinyqueue: + specifier: ^3.0.0 + version: 3.0.0 + tslib: + specifier: ^2.3.0 + version: 2.8.1 + yaml: + specifier: ^2.8.2 + version: 2.8.2 + apps/smoke-node: dependencies: '@blue-quickjs/dv': @@ -113,9 +251,16 @@ importers: tslib: specifier: ^2.3.0 version: 2.8.1 + devDependencies: + '@blue-quickjs/deterministic-bundler': + specifier: workspace:* + version: link:../../libs/deterministic-bundler apps/smoke-web: dependencies: + '@blue-quickjs/deterministic-bundler': + specifier: workspace:* + version: link:../../libs/deterministic-bundler '@blue-quickjs/dv': specifier: workspace:* version: link:../../libs/dv @@ -141,12 +286,42 @@ importers: specifier: ^2.3.0 version: 2.8.1 + libs/deterministic-builder: + dependencies: + '@blue-quickjs/deterministic-bundler': + specifier: workspace:* + version: link:../deterministic-bundler + tslib: + specifier: ^2.3.0 + version: 2.8.1 + + libs/deterministic-bundler: + dependencies: + '@blue-quickjs/execution-profiles': + specifier: workspace:* + version: link:../execution-profiles + acorn: + specifier: ^8.15.0 + version: 8.15.0 + esbuild: + specifier: ^0.27.4 + version: 0.27.4 + tslib: + specifier: ^2.3.0 + version: 2.8.1 + libs/dv: dependencies: tslib: specifier: ^2.3.0 version: 2.8.1 + libs/execution-profiles: + dependencies: + tslib: + specifier: ^2.3.0 + version: 2.8.1 + libs/quickjs-runtime: dependencies: '@blue-quickjs/abi-manifest': @@ -155,13 +330,22 @@ importers: '@blue-quickjs/dv': specifier: workspace:* version: link:../dv + '@blue-quickjs/execution-profiles': + specifier: workspace:* + version: link:../execution-profiles '@blue-quickjs/quickjs-wasm': specifier: workspace:* version: link:../quickjs-wasm + '@jridgewell/trace-mapping': + specifier: ^0.3.31 + version: 0.3.31 tslib: specifier: ^2.3.0 version: 2.8.1 devDependencies: + '@blue-quickjs/deterministic-bundler': + specifier: workspace:* + version: link:../deterministic-bundler '@blue-quickjs/test-harness': specifier: workspace:* version: link:../test-harness @@ -202,6 +386,15 @@ importers: '@blue-quickjs/dv': specifier: workspace:* version: link:../dv + '@noble/hashes': + specifier: ^1.8.0 + version: 1.8.0 + base64-js: + specifier: ^1.5.1 + version: 1.5.1 + chess.js: + specifier: ^1.4.0 + version: 1.4.0 tslib: specifier: ^2.3.0 version: 2.8.1 @@ -213,6 +406,24 @@ importers: specifier: workspace:* version: link:../quickjs-wasm-constants + tools/blue-quickjs-cli: + dependencies: + '@blue-quickjs/abi-manifest': + specifier: workspace:* + version: link:../../libs/abi-manifest + '@blue-quickjs/deterministic-builder': + specifier: workspace:* + version: link:../../libs/deterministic-builder + '@blue-quickjs/quickjs-runtime': + specifier: workspace:* + version: link:../../libs/quickjs-runtime + '@blue-quickjs/test-harness': + specifier: workspace:* + version: link:../../libs/test-harness + tslib: + specifier: ^2.3.0 + version: 2.8.1 + packages: '@babel/code-frame@7.27.1': @@ -775,156 +986,312 @@ packages: cpu: [ppc64] os: [aix] + '@esbuild/aix-ppc64@0.27.4': + resolution: {integrity: sha512-cQPwL2mp2nSmHHJlCyoXgHGhbEPMrEEU5xhkcy3Hs/O7nGZqEpZ2sUtLaL9MORLtDfRvVl2/3PAuEkYZH0Ty8Q==} + engines: {node: '>=18'} + cpu: [ppc64] + os: [aix] + '@esbuild/android-arm64@0.25.12': resolution: {integrity: sha512-6AAmLG7zwD1Z159jCKPvAxZd4y/VTO0VkprYy+3N2FtJ8+BQWFXU+OxARIwA46c5tdD9SsKGZ/1ocqBS/gAKHg==} engines: {node: '>=18'} cpu: [arm64] os: [android] + '@esbuild/android-arm64@0.27.4': + resolution: {integrity: sha512-gdLscB7v75wRfu7QSm/zg6Rx29VLdy9eTr2t44sfTW7CxwAtQghZ4ZnqHk3/ogz7xao0QAgrkradbBzcqFPasw==} + engines: {node: '>=18'} + cpu: [arm64] + os: [android] + '@esbuild/android-arm@0.25.12': resolution: {integrity: sha512-VJ+sKvNA/GE7Ccacc9Cha7bpS8nyzVv0jdVgwNDaR4gDMC/2TTRc33Ip8qrNYUcpkOHUT5OZ0bUcNNVZQ9RLlg==} engines: {node: '>=18'} cpu: [arm] os: [android] + '@esbuild/android-arm@0.27.4': + resolution: {integrity: sha512-X9bUgvxiC8CHAGKYufLIHGXPJWnr0OCdR0anD2e21vdvgCI8lIfqFbnoeOz7lBjdrAGUhqLZLcQo6MLhTO2DKQ==} + engines: {node: '>=18'} + cpu: [arm] + os: [android] + '@esbuild/android-x64@0.25.12': resolution: {integrity: sha512-5jbb+2hhDHx5phYR2By8GTWEzn6I9UqR11Kwf22iKbNpYrsmRB18aX/9ivc5cabcUiAT/wM+YIZ6SG9QO6a8kg==} engines: {node: '>=18'} cpu: [x64] os: [android] + '@esbuild/android-x64@0.27.4': + resolution: {integrity: sha512-PzPFnBNVF292sfpfhiyiXCGSn9HZg5BcAz+ivBuSsl6Rk4ga1oEXAamhOXRFyMcjwr2DVtm40G65N3GLeH1Lvw==} + engines: {node: '>=18'} + cpu: [x64] + os: [android] + '@esbuild/darwin-arm64@0.25.12': resolution: {integrity: sha512-N3zl+lxHCifgIlcMUP5016ESkeQjLj/959RxxNYIthIg+CQHInujFuXeWbWMgnTo4cp5XVHqFPmpyu9J65C1Yg==} engines: {node: '>=18'} cpu: [arm64] os: [darwin] + '@esbuild/darwin-arm64@0.27.4': + resolution: {integrity: sha512-b7xaGIwdJlht8ZFCvMkpDN6uiSmnxxK56N2GDTMYPr2/gzvfdQN8rTfBsvVKmIVY/X7EM+/hJKEIbbHs9oA4tQ==} + engines: {node: '>=18'} + cpu: [arm64] + os: [darwin] + '@esbuild/darwin-x64@0.25.12': resolution: {integrity: sha512-HQ9ka4Kx21qHXwtlTUVbKJOAnmG1ipXhdWTmNXiPzPfWKpXqASVcWdnf2bnL73wgjNrFXAa3yYvBSd9pzfEIpA==} engines: {node: '>=18'} cpu: [x64] os: [darwin] + '@esbuild/darwin-x64@0.27.4': + resolution: {integrity: sha512-sR+OiKLwd15nmCdqpXMnuJ9W2kpy0KigzqScqHI3Hqwr7IXxBp3Yva+yJwoqh7rE8V77tdoheRYataNKL4QrPw==} + engines: {node: '>=18'} + cpu: [x64] + os: [darwin] + '@esbuild/freebsd-arm64@0.25.12': resolution: {integrity: sha512-gA0Bx759+7Jve03K1S0vkOu5Lg/85dou3EseOGUes8flVOGxbhDDh/iZaoek11Y8mtyKPGF3vP8XhnkDEAmzeg==} engines: {node: '>=18'} cpu: [arm64] os: [freebsd] + '@esbuild/freebsd-arm64@0.27.4': + resolution: {integrity: sha512-jnfpKe+p79tCnm4GVav68A7tUFeKQwQyLgESwEAUzyxk/TJr4QdGog9sqWNcUbr/bZt/O/HXouspuQDd9JxFSw==} + engines: {node: '>=18'} + cpu: [arm64] + os: [freebsd] + '@esbuild/freebsd-x64@0.25.12': resolution: {integrity: sha512-TGbO26Yw2xsHzxtbVFGEXBFH0FRAP7gtcPE7P5yP7wGy7cXK2oO7RyOhL5NLiqTlBh47XhmIUXuGciXEqYFfBQ==} engines: {node: '>=18'} cpu: [x64] os: [freebsd] + '@esbuild/freebsd-x64@0.27.4': + resolution: {integrity: sha512-2kb4ceA/CpfUrIcTUl1wrP/9ad9Atrp5J94Lq69w7UwOMolPIGrfLSvAKJp0RTvkPPyn6CIWrNy13kyLikZRZQ==} + engines: {node: '>=18'} + cpu: [x64] + os: [freebsd] + '@esbuild/linux-arm64@0.25.12': resolution: {integrity: sha512-8bwX7a8FghIgrupcxb4aUmYDLp8pX06rGh5HqDT7bB+8Rdells6mHvrFHHW2JAOPZUbnjUpKTLg6ECyzvas2AQ==} engines: {node: '>=18'} cpu: [arm64] os: [linux] + '@esbuild/linux-arm64@0.27.4': + resolution: {integrity: sha512-7nQOttdzVGth1iz57kxg9uCz57dxQLHWxopL6mYuYthohPKEK0vU0C3O21CcBK6KDlkYVcnDXY099HcCDXd9dA==} + engines: {node: '>=18'} + cpu: [arm64] + os: [linux] + '@esbuild/linux-arm@0.25.12': resolution: {integrity: sha512-lPDGyC1JPDou8kGcywY0YILzWlhhnRjdof3UlcoqYmS9El818LLfJJc3PXXgZHrHCAKs/Z2SeZtDJr5MrkxtOw==} engines: {node: '>=18'} cpu: [arm] os: [linux] + '@esbuild/linux-arm@0.27.4': + resolution: {integrity: sha512-aBYgcIxX/wd5n2ys0yESGeYMGF+pv6g0DhZr3G1ZG4jMfruU9Tl1i2Z+Wnj9/KjGz1lTLCcorqE2viePZqj4Eg==} + engines: {node: '>=18'} + cpu: [arm] + os: [linux] + '@esbuild/linux-ia32@0.25.12': resolution: {integrity: sha512-0y9KrdVnbMM2/vG8KfU0byhUN+EFCny9+8g202gYqSSVMonbsCfLjUO+rCci7pM0WBEtz+oK/PIwHkzxkyharA==} engines: {node: '>=18'} cpu: [ia32] os: [linux] + '@esbuild/linux-ia32@0.27.4': + resolution: {integrity: sha512-oPtixtAIzgvzYcKBQM/qZ3R+9TEUd1aNJQu0HhGyqtx6oS7qTpvjheIWBbes4+qu1bNlo2V4cbkISr8q6gRBFA==} + engines: {node: '>=18'} + cpu: [ia32] + os: [linux] + '@esbuild/linux-loong64@0.25.12': resolution: {integrity: sha512-h///Lr5a9rib/v1GGqXVGzjL4TMvVTv+s1DPoxQdz7l/AYv6LDSxdIwzxkrPW438oUXiDtwM10o9PmwS/6Z0Ng==} engines: {node: '>=18'} cpu: [loong64] os: [linux] + '@esbuild/linux-loong64@0.27.4': + resolution: {integrity: sha512-8mL/vh8qeCoRcFH2nM8wm5uJP+ZcVYGGayMavi8GmRJjuI3g1v6Z7Ni0JJKAJW+m0EtUuARb6Lmp4hMjzCBWzA==} + engines: {node: '>=18'} + cpu: [loong64] + os: [linux] + '@esbuild/linux-mips64el@0.25.12': resolution: {integrity: sha512-iyRrM1Pzy9GFMDLsXn1iHUm18nhKnNMWscjmp4+hpafcZjrr2WbT//d20xaGljXDBYHqRcl8HnxbX6uaA/eGVw==} engines: {node: '>=18'} cpu: [mips64el] os: [linux] + '@esbuild/linux-mips64el@0.27.4': + resolution: {integrity: sha512-1RdrWFFiiLIW7LQq9Q2NES+HiD4NyT8Itj9AUeCl0IVCA459WnPhREKgwrpaIfTOe+/2rdntisegiPWn/r/aAw==} + engines: {node: '>=18'} + cpu: [mips64el] + os: [linux] + '@esbuild/linux-ppc64@0.25.12': resolution: {integrity: sha512-9meM/lRXxMi5PSUqEXRCtVjEZBGwB7P/D4yT8UG/mwIdze2aV4Vo6U5gD3+RsoHXKkHCfSxZKzmDssVlRj1QQA==} engines: {node: '>=18'} cpu: [ppc64] os: [linux] + '@esbuild/linux-ppc64@0.27.4': + resolution: {integrity: sha512-tLCwNG47l3sd9lpfyx9LAGEGItCUeRCWeAx6x2Jmbav65nAwoPXfewtAdtbtit/pJFLUWOhpv0FpS6GQAmPrHA==} + engines: {node: '>=18'} + cpu: [ppc64] + os: [linux] + '@esbuild/linux-riscv64@0.25.12': resolution: {integrity: sha512-Zr7KR4hgKUpWAwb1f3o5ygT04MzqVrGEGXGLnj15YQDJErYu/BGg+wmFlIDOdJp0PmB0lLvxFIOXZgFRrdjR0w==} engines: {node: '>=18'} cpu: [riscv64] os: [linux] + '@esbuild/linux-riscv64@0.27.4': + resolution: {integrity: sha512-BnASypppbUWyqjd1KIpU4AUBiIhVr6YlHx/cnPgqEkNoVOhHg+YiSVxM1RLfiy4t9cAulbRGTNCKOcqHrEQLIw==} + engines: {node: '>=18'} + cpu: [riscv64] + os: [linux] + '@esbuild/linux-s390x@0.25.12': resolution: {integrity: sha512-MsKncOcgTNvdtiISc/jZs/Zf8d0cl/t3gYWX8J9ubBnVOwlk65UIEEvgBORTiljloIWnBzLs4qhzPkJcitIzIg==} engines: {node: '>=18'} cpu: [s390x] os: [linux] + '@esbuild/linux-s390x@0.27.4': + resolution: {integrity: sha512-+eUqgb/Z7vxVLezG8bVB9SfBie89gMueS+I0xYh2tJdw3vqA/0ImZJ2ROeWwVJN59ihBeZ7Tu92dF/5dy5FttA==} + engines: {node: '>=18'} + cpu: [s390x] + os: [linux] + '@esbuild/linux-x64@0.25.12': resolution: {integrity: sha512-uqZMTLr/zR/ed4jIGnwSLkaHmPjOjJvnm6TVVitAa08SLS9Z0VM8wIRx7gWbJB5/J54YuIMInDquWyYvQLZkgw==} engines: {node: '>=18'} cpu: [x64] os: [linux] + '@esbuild/linux-x64@0.27.4': + resolution: {integrity: sha512-S5qOXrKV8BQEzJPVxAwnryi2+Iq5pB40gTEIT69BQONqR7JH1EPIcQ/Uiv9mCnn05jff9umq/5nqzxlqTOg9NA==} + engines: {node: '>=18'} + cpu: [x64] + os: [linux] + '@esbuild/netbsd-arm64@0.25.12': resolution: {integrity: sha512-xXwcTq4GhRM7J9A8Gv5boanHhRa/Q9KLVmcyXHCTaM4wKfIpWkdXiMog/KsnxzJ0A1+nD+zoecuzqPmCRyBGjg==} engines: {node: '>=18'} cpu: [arm64] os: [netbsd] + '@esbuild/netbsd-arm64@0.27.4': + resolution: {integrity: sha512-xHT8X4sb0GS8qTqiwzHqpY00C95DPAq7nAwX35Ie/s+LO9830hrMd3oX0ZMKLvy7vsonee73x0lmcdOVXFzd6Q==} + engines: {node: '>=18'} + cpu: [arm64] + os: [netbsd] + '@esbuild/netbsd-x64@0.25.12': resolution: {integrity: sha512-Ld5pTlzPy3YwGec4OuHh1aCVCRvOXdH8DgRjfDy/oumVovmuSzWfnSJg+VtakB9Cm0gxNO9BzWkj6mtO1FMXkQ==} engines: {node: '>=18'} cpu: [x64] os: [netbsd] + '@esbuild/netbsd-x64@0.27.4': + resolution: {integrity: sha512-RugOvOdXfdyi5Tyv40kgQnI0byv66BFgAqjdgtAKqHoZTbTF2QqfQrFwa7cHEORJf6X2ht+l9ABLMP0dnKYsgg==} + engines: {node: '>=18'} + cpu: [x64] + os: [netbsd] + '@esbuild/openbsd-arm64@0.25.12': resolution: {integrity: sha512-fF96T6KsBo/pkQI950FARU9apGNTSlZGsv1jZBAlcLL1MLjLNIWPBkj5NlSz8aAzYKg+eNqknrUJ24QBybeR5A==} engines: {node: '>=18'} cpu: [arm64] os: [openbsd] + '@esbuild/openbsd-arm64@0.27.4': + resolution: {integrity: sha512-2MyL3IAaTX+1/qP0O1SwskwcwCoOI4kV2IBX1xYnDDqthmq5ArrW94qSIKCAuRraMgPOmG0RDTA74mzYNQA9ow==} + engines: {node: '>=18'} + cpu: [arm64] + os: [openbsd] + '@esbuild/openbsd-x64@0.25.12': resolution: {integrity: sha512-MZyXUkZHjQxUvzK7rN8DJ3SRmrVrke8ZyRusHlP+kuwqTcfWLyqMOE3sScPPyeIXN/mDJIfGXvcMqCgYKekoQw==} engines: {node: '>=18'} cpu: [x64] os: [openbsd] + '@esbuild/openbsd-x64@0.27.4': + resolution: {integrity: sha512-u8fg/jQ5aQDfsnIV6+KwLOf1CmJnfu1ShpwqdwC0uA7ZPwFws55Ngc12vBdeUdnuWoQYx/SOQLGDcdlfXhYmXQ==} + engines: {node: '>=18'} + cpu: [x64] + os: [openbsd] + '@esbuild/openharmony-arm64@0.25.12': resolution: {integrity: sha512-rm0YWsqUSRrjncSXGA7Zv78Nbnw4XL6/dzr20cyrQf7ZmRcsovpcRBdhD43Nuk3y7XIoW2OxMVvwuRvk9XdASg==} engines: {node: '>=18'} cpu: [arm64] os: [openharmony] + '@esbuild/openharmony-arm64@0.27.4': + resolution: {integrity: sha512-JkTZrl6VbyO8lDQO3yv26nNr2RM2yZzNrNHEsj9bm6dOwwu9OYN28CjzZkH57bh4w0I2F7IodpQvUAEd1mbWXg==} + engines: {node: '>=18'} + cpu: [arm64] + os: [openharmony] + '@esbuild/sunos-x64@0.25.12': resolution: {integrity: sha512-3wGSCDyuTHQUzt0nV7bocDy72r2lI33QL3gkDNGkod22EsYl04sMf0qLb8luNKTOmgF/eDEDP5BFNwoBKH441w==} engines: {node: '>=18'} cpu: [x64] os: [sunos] + '@esbuild/sunos-x64@0.27.4': + resolution: {integrity: sha512-/gOzgaewZJfeJTlsWhvUEmUG4tWEY2Spp5M20INYRg2ZKl9QPO3QEEgPeRtLjEWSW8FilRNacPOg8R1uaYkA6g==} + engines: {node: '>=18'} + cpu: [x64] + os: [sunos] + '@esbuild/win32-arm64@0.25.12': resolution: {integrity: sha512-rMmLrur64A7+DKlnSuwqUdRKyd3UE7oPJZmnljqEptesKM8wx9J8gx5u0+9Pq0fQQW8vqeKebwNXdfOyP+8Bsg==} engines: {node: '>=18'} cpu: [arm64] os: [win32] + '@esbuild/win32-arm64@0.27.4': + resolution: {integrity: sha512-Z9SExBg2y32smoDQdf1HRwHRt6vAHLXcxD2uGgO/v2jK7Y718Ix4ndsbNMU/+1Qiem9OiOdaqitioZwxivhXYg==} + engines: {node: '>=18'} + cpu: [arm64] + os: [win32] + '@esbuild/win32-ia32@0.25.12': resolution: {integrity: sha512-HkqnmmBoCbCwxUKKNPBixiWDGCpQGVsrQfJoVGYLPT41XWF8lHuE5N6WhVia2n4o5QK5M4tYr21827fNhi4byQ==} engines: {node: '>=18'} cpu: [ia32] os: [win32] + '@esbuild/win32-ia32@0.27.4': + resolution: {integrity: sha512-DAyGLS0Jz5G5iixEbMHi5KdiApqHBWMGzTtMiJ72ZOLhbu/bzxgAe8Ue8CTS3n3HbIUHQz/L51yMdGMeoxXNJw==} + engines: {node: '>=18'} + cpu: [ia32] + os: [win32] + '@esbuild/win32-x64@0.25.12': resolution: {integrity: sha512-alJC0uCZpTFrSL0CCDjcgleBXPnCrEAhTBILpeAp7M/OFgoqtAetfBzX0xM00MUsVVPpVjlPuMbREqnZCXaTnA==} engines: {node: '>=18'} cpu: [x64] os: [win32] + '@esbuild/win32-x64@0.27.4': + resolution: {integrity: sha512-+knoa0BDoeXgkNvvV1vvbZX4+hizelrkwmGJBdT17t8FNPwG2lKemmuMZlmaNQ3ws3DKKCxpb4zRZEIp3UxFCg==} + engines: {node: '>=18'} + cpu: [x64] + os: [win32] + '@eslint-community/eslint-utils@4.9.0': resolution: {integrity: sha512-ayVFHdtZ+hsq1t2Dy24wCmGXGe4q9Gu3smhLYALJrr473ZH27MsnSL+LKUlimp4BWJqMDMLmPpx/Q9R3OAlL4g==} engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} @@ -1093,21 +1460,25 @@ packages: resolution: {integrity: sha512-rjjgq+w10GW3APiiIv++MGK28tUgLWFRuhawn0W2HplUXyVdBvEfcdsZgzO8qU34Q4P6yLdMBZl5FfbXMRgHqw==} cpu: [arm64] os: [linux] + libc: [glibc] '@nx/nx-linux-arm64-musl@22.2.2': resolution: {integrity: sha512-awJZJ+y5OcromwHtYiOeq5SZ89X5+PKZQZszHyygZjq/lYt9JnFRIOGsWDJGcb7A3EDXK4IdMaV5HmlMmErYzw==} cpu: [arm64] os: [linux] + libc: [musl] '@nx/nx-linux-x64-gnu@22.2.2': resolution: {integrity: sha512-1d+bz6qqqmVtKmNVXpPhWqTlLozhgq8Da5MV8c1oq+RdPyjMSGBKStDW88RmLuucScIoK88fH1VGQru8NmIrdw==} cpu: [x64] os: [linux] + libc: [glibc] '@nx/nx-linux-x64-musl@22.2.2': resolution: {integrity: sha512-tOEBaxDxk26K9Yh9Z7h42k4pFTxNHIcfdG7Xy9IAlEEDKZOrBt3i0XlTLpRKqhLycrnbKhavFtFg8ZkItMfaVA==} cpu: [x64] os: [linux] + libc: [musl] '@nx/nx-win32-arm64-msvc@22.2.2': resolution: {integrity: sha512-qxGkjSPemLpQtnoyyfplUsSiDRzbwi2kRJ+RbmLg01zsCiJ5UR5nlKxx8H7rnLAPo5XphR9FahVE2HTCfGFzgQ==} @@ -1205,56 +1576,67 @@ packages: resolution: {integrity: sha512-k9oD15soC/Ln6d2Wv/JOFPzZXIAIFLp6B+i14KhxAfnq76ajt0EhYc5YPeX6W1xJkAdItcVT+JhKl1QZh44/qw==} cpu: [arm] os: [linux] + libc: [glibc] '@rollup/rollup-linux-arm-musleabihf@4.53.3': resolution: {integrity: sha512-vTNlKq+N6CK/8UktsrFuc+/7NlEYVxgaEgRXVUVK258Z5ymho29skzW1sutgYjqNnquGwVUObAaxae8rZ6YMhg==} cpu: [arm] os: [linux] + libc: [musl] '@rollup/rollup-linux-arm64-gnu@4.53.3': resolution: {integrity: sha512-RGrFLWgMhSxRs/EWJMIFM1O5Mzuz3Xy3/mnxJp/5cVhZ2XoCAxJnmNsEyeMJtpK+wu0FJFWz+QF4mjCA7AUQ3w==} cpu: [arm64] os: [linux] + libc: [glibc] '@rollup/rollup-linux-arm64-musl@4.53.3': resolution: {integrity: sha512-kASyvfBEWYPEwe0Qv4nfu6pNkITLTb32p4yTgzFCocHnJLAHs+9LjUu9ONIhvfT/5lv4YS5muBHyuV84epBo/A==} cpu: [arm64] os: [linux] + libc: [musl] '@rollup/rollup-linux-loong64-gnu@4.53.3': resolution: {integrity: sha512-JiuKcp2teLJwQ7vkJ95EwESWkNRFJD7TQgYmCnrPtlu50b4XvT5MOmurWNrCj3IFdyjBQ5p9vnrX4JM6I8OE7g==} cpu: [loong64] os: [linux] + libc: [glibc] '@rollup/rollup-linux-ppc64-gnu@4.53.3': resolution: {integrity: sha512-EoGSa8nd6d3T7zLuqdojxC20oBfNT8nexBbB/rkxgKj5T5vhpAQKKnD+h3UkoMuTyXkP5jTjK/ccNRmQrPNDuw==} cpu: [ppc64] os: [linux] + libc: [glibc] '@rollup/rollup-linux-riscv64-gnu@4.53.3': resolution: {integrity: sha512-4s+Wped2IHXHPnAEbIB0YWBv7SDohqxobiiPA1FIWZpX+w9o2i4LezzH/NkFUl8LRci/8udci6cLq+jJQlh+0g==} cpu: [riscv64] os: [linux] + libc: [glibc] '@rollup/rollup-linux-riscv64-musl@4.53.3': resolution: {integrity: sha512-68k2g7+0vs2u9CxDt5ktXTngsxOQkSEV/xBbwlqYcUrAVh6P9EgMZvFsnHy4SEiUl46Xf0IObWVbMvPrr2gw8A==} cpu: [riscv64] os: [linux] + libc: [musl] '@rollup/rollup-linux-s390x-gnu@4.53.3': resolution: {integrity: sha512-VYsFMpULAz87ZW6BVYw3I6sWesGpsP9OPcyKe8ofdg9LHxSbRMd7zrVrr5xi/3kMZtpWL/wC+UIJWJYVX5uTKg==} cpu: [s390x] os: [linux] + libc: [glibc] '@rollup/rollup-linux-x64-gnu@4.53.3': resolution: {integrity: sha512-3EhFi1FU6YL8HTUJZ51imGJWEX//ajQPfqWLI3BQq4TlvHy4X0MOr5q3D2Zof/ka0d5FNdPwZXm3Yyib/UEd+w==} cpu: [x64] os: [linux] + libc: [glibc] '@rollup/rollup-linux-x64-musl@4.53.3': resolution: {integrity: sha512-eoROhjcc6HbZCJr+tvVT8X4fW3/5g/WkGvvmwz/88sDtSJzO7r/blvoBDgISDiCjDRZmHpwud7h+6Q9JxFwq1Q==} cpu: [x64] os: [linux] + libc: [musl] '@rollup/rollup-openharmony-arm64@4.53.3': resolution: {integrity: sha512-OueLAWgrNSPGAdUdIjSWXw+u/02BRTcnfw9PN41D2vq/JSEPnJnVuBgw18VkN8wcd4fjUs+jFHVM4t9+kBSNLw==} @@ -1360,24 +1742,28 @@ packages: engines: {node: '>=10'} cpu: [arm64] os: [linux] + libc: [glibc] '@swc/core-linux-arm64-musl@1.5.29': resolution: {integrity: sha512-TERh2OICAJz+SdDIK9+0GyTUwF6r4xDlFmpoiHKHrrD/Hh3u+6Zue0d7jQ/he/i80GDn4tJQkHlZys+RZL5UZg==} engines: {node: '>=10'} cpu: [arm64] os: [linux] + libc: [musl] '@swc/core-linux-x64-gnu@1.5.29': resolution: {integrity: sha512-WMDPqU7Ji9dJpA+Llek2p9t7pcy7Bob8ggPUvgsIlv3R/eesF9DIzSbrgl6j3EAEPB9LFdSafsgf6kT/qnvqFg==} engines: {node: '>=10'} cpu: [x64] os: [linux] + libc: [glibc] '@swc/core-linux-x64-musl@1.5.29': resolution: {integrity: sha512-DO14glwpdKY4POSN0201OnGg1+ziaSVr6/RFzuSLggshwXeeyVORiHv3baj7NENhJhWhUy3NZlDsXLnRFkmhHQ==} engines: {node: '>=10'} cpu: [x64] os: [linux] + libc: [musl] '@swc/core-win32-arm64-msvc@1.5.29': resolution: {integrity: sha512-V3Y1+a1zG1zpYXUMqPIHEMEOd+rHoVnIpO/KTyFwAmKVu8v+/xPEVx/AGoYE67x4vDAAvPQrKI3Aokilqa5yVg==} @@ -1456,6 +1842,9 @@ packages: '@types/responselike@1.0.0': resolution: {integrity: sha512-85Y2BjiufFzaMIlvJDvTTB8Fxl2xfLo4HgmHzVBz08w4wDePCTjYw66PdrolO0kzli3yam/YCgRufyo1DdQVTA==} + '@types/trusted-types@2.0.7': + resolution: {integrity: sha512-ScaPdn1dQczgbl0QFTeTOmVHFULt394XJgOQNoyVhZ6r2vLnMLJfBPd53SB52T/3G36VI1/g2MZaX0cwDuXsfw==} + '@typescript-eslint/eslint-plugin@8.49.0': resolution: {integrity: sha512-JXij0vzIaTtCwu6SxTh8qBc66kmf1xs7pI4UOiMDFVct6q86G0Zs7KRcEoJgY3Cav3x5Tq0MF5jwgpgLqgKG3A==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} @@ -1841,6 +2230,10 @@ packages: array-flatten@1.1.1: resolution: {integrity: sha512-PCVAQswWemu6UdxsDFFX/+gVeYqKAod3D3UVm91jHwynguOwAvYPhx8nNlM++NqRcK6CxxpUafjmhIdKiHibqg==} + array-move@4.0.0: + resolution: {integrity: sha512-+RY54S8OuVvg94THpneQvFRmqWdAHeqtMzgMW6JNurHxe8rsS07cHQdfGkXnTUXiBcyZ0j3SiDIxxj0RPiqCkQ==} + engines: {node: ^12.20.0 || ^14.13.1 || >=16.0.0} + asn1@0.2.6: resolution: {integrity: sha512-ix/FxPn0MDjeyJ7i/yoHGFt/EX6LyNbxSEhPPXODPL+KB0VPk86UYfL0lMdy+KCnv+fmvIzySwaK5COwqVbWTQ==} @@ -2003,6 +2396,10 @@ packages: resolution: {integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==} engines: {node: '>=6'} + camelcase@9.0.0: + resolution: {integrity: sha512-TO9xmyXTZ9HUHI8M1OnvExxYB0eYVS/1e5s7IDMTAoIcwUd+aNcFODs6Xk83mobk0velyHFQgA1yIrvYc6wclw==} + engines: {node: '>=20'} + caniuse-lite@1.0.30001760: resolution: {integrity: sha512-7AAMPcueWELt1p3mi13HR/LHH0TJLT11cnwDJEs3xA4+CK/PLKeO9Kl1oru24htkyUKtkGCvAx4ohB0Ttry8Dw==} @@ -2017,6 +2414,9 @@ packages: resolution: {integrity: sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==} engines: {node: '>=10'} + chess.js@1.4.0: + resolution: {integrity: sha512-BBJgrrtKQOzFLonR0l+k64A98NLemPwNsCskwb+29bRwobUa4iTm51E1kwGPbWXAcfdDa18nad6vpPPKPWarqw==} + chrome-trace-event@1.0.4: resolution: {integrity: sha512-rNjApaLzuwaOTjCiT8lSDdGN1APCiqkChLMJxJPWLunPAt5fy8xgU9/jNOchV84wfIxrA0lRQB7oCT8jrn/wrQ==} engines: {node: '>=6.0'} @@ -2128,6 +2528,11 @@ packages: resolution: {integrity: sha512-AdmX6xUzdNASswsFtmwSt7Vj8po9IuqXm0UXz7QKPuEUmPB4XyjGfaAr2PSuELMwkRMVH1EpIkX5bTZGRB3eCA==} engines: {node: '>=10'} + crc-32@1.2.2: + resolution: {integrity: sha512-ROmzCKrTnOwybPcJApAA6WBWij23HVfGVNKqqrZpuyZOHqK2CwHSvpGuyt/UNNvaIjEd8X5IFGp4Mh+Ie1IHJQ==} + engines: {node: '>=0.8'} + hasBin: true + cross-spawn@7.0.6: resolution: {integrity: sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==} engines: {node: '>= 8'} @@ -2176,9 +2581,17 @@ packages: supports-color: optional: true + decamelize@6.0.1: + resolution: {integrity: sha512-G7Cqgaelq68XHJNGlZ7lrNQyhZGsFqpwtGFexqUv4IQdjKoSYF7ipZ9UuTJZUSQXFj/XaoBLuEVIVqr8EJngEQ==} + engines: {node: ^12.20.0 || ^14.13.1 || >=16.0.0} + decimal.js@10.6.0: resolution: {integrity: sha512-YpgQiITW3JXGntzdUmyUR1V812Hn8T1YVXhCu+wO3OpS4eU9l4YdD3qjyiKdV6mvV29zapkMeD390UVEf2lkUg==} + decode-uri-component@0.4.1: + resolution: {integrity: sha512-+8VxcR21HhTy8nOt6jf20w0c9CADrw1O8d+VZ/YzzCt4bJ3uBjw+D1q2osAB8RnpwwaeYBxy0HyKQxD5JBMuuQ==} + engines: {node: '>=14.16'} + decompress-response@6.0.0: resolution: {integrity: sha512-aW35yZM6Bb/4oJlZncMH2LCoZtJXTRxES17vE3hoRiowU2kWHaJKFkSBDnDR+cm9J+9QhXmREyIfv0pji9ejCQ==} engines: {node: '>=10'} @@ -2186,6 +2599,10 @@ packages: deep-is@0.1.4: resolution: {integrity: sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==} + deepmerge@4.3.1: + resolution: {integrity: sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==} + engines: {node: '>=0.10.0'} + defaults@1.0.4: resolution: {integrity: sha512-eFuaLoy/Rxalv2kr+lqMlUnrDWV+3j4pljOIJgLIhI058IQfWJ7vXhyEIHu+HtC738klGALYxOKDO0bQP3tg8A==} @@ -2218,11 +2635,17 @@ packages: resolution: {integrity: sha512-sSuxWU5j5SR9QQji/o2qMvqRNYRDOcBTgsJ/DeCf4iSN4gW+gNMXM7wFIP+fdXZxoNiAnHUTGjCr+TSWXdRDKg==} engines: {node: '>=0.3.1'} + dijkstrajs@1.0.3: + resolution: {integrity: sha512-qiSlmBq9+BCdCA/L46dw8Uy93mloxsPSbwnm5yrKn2vMPiy8KyAskTF6zuV/j5BMsmOGZDPs7KjU+mjb670kfA==} + domexception@4.0.0: resolution: {integrity: sha512-A2is4PLG+eeSfoTMA95/s4pvAoSo2mKtiM5jlHkAVewmiO8ISFTFKZjH7UAM1Atli/OT/7JHOrJRJiMKUZKYBw==} engines: {node: '>=12'} deprecated: Use your platform's native DOMException instead + dompurify@3.2.7: + resolution: {integrity: sha512-WhL/YuveyGXJaerVlMYGWhvQswa7myDG17P7Vu65EWC05o8vfeNbvNf4d/BOvH99+ZW+LlQsc1GDKMa1vNK6dw==} + dotenv-expand@11.0.7: resolution: {integrity: sha512-zIHwmZPRshsCdpMDyVsqGmgyP0yT8GAgXUnkdAoJisxvf33k7yO6OuoKmcTGuXPWSsm8Oh88nZicRLA9Y0rUeA==} engines: {node: '>=12'} @@ -2321,6 +2744,11 @@ packages: engines: {node: '>=18'} hasBin: true + esbuild@0.27.4: + resolution: {integrity: sha512-Rq4vbHnYkK5fws5NF7MYTU68FPRE1ajX7heQ/8QXXWqNgqqJ/GkmmyxIzUnf2Sr/bakf8l54716CcMGHYhMrrQ==} + engines: {node: '>=18'} + hasBin: true + escalade@3.2.0: resolution: {integrity: sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==} engines: {node: '>=6'} @@ -2336,6 +2764,10 @@ packages: resolution: {integrity: sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==} engines: {node: '>=10'} + escape-string-regexp@5.0.0: + resolution: {integrity: sha512-/veY75JbMK4j1yjvuUxuVsiS/hr/4iHs9FTT6cgTexxdE0Ly/glccBAkloH/DofkjRbZU3bnoj38mOmhkZ0lHw==} + engines: {node: '>=12'} + eslint-config-prettier@10.1.8: resolution: {integrity: sha512-82GZUjRS0p/jganf6q1rEO25VSoHH0hKPCTrgillPjdI/3bgBhAE1QzHrHTizjpRvy6pGAvKjDJtk2pF9NDq8w==} hasBin: true @@ -2482,6 +2914,10 @@ packages: fast-uri@3.1.0: resolution: {integrity: sha512-iPeeDKJSWf4IEOasVVrknXpaBV0IApz/gp7S2bb7Z4Lljbl2MGJRqInZiUrQwV16cpzw/D3S5j5Julj/gT52AA==} + fastest-levenshtein@1.0.16: + resolution: {integrity: sha512-eRnCtTTtGZFpQCwhJiUOuxPQWRXVKYDn0b2PeHfXL6/Zi53SLAzAHfVhVWK2AryC/WH05kGfxhFIPvTF0SXQzg==} + engines: {node: '>= 4.9.1'} + fdir@6.5.0: resolution: {integrity: sha512-tIbYtZbucOs0BRGqPJkshJUYdL+SDH7dVM8gjy+ERp3WAUjLEFJE+02kanyHtwjWOnwrKYBiwAmM0p4kLJAnXg==} engines: {node: '>=12.0.0'} @@ -2505,6 +2941,10 @@ packages: filelist@1.0.4: resolution: {integrity: sha512-w1cEuf3S+DrLCQL7ET6kz+gmlJdbq9J7yXCSjK/OZCPA+qEN1WyF4ZAf0YYJa4/shHJra2t/d/r8SV4Ji+x+8Q==} + filter-obj@5.1.0: + resolution: {integrity: sha512-qWeTREPoT7I0bifpPUXtxkZJ1XJzxWtfoWWkdVGqa+eCr3SHW/Ocp89o8vLvbUuQnadybJpjOKu4V+RwO6sGng==} + engines: {node: '>=14.16'} + finalhandler@1.3.1: resolution: {integrity: sha512-6BN9trH7bp3qvnrRyzsBz+g3lZxTNZTbVO2EV1CS0WIcDbawYVdYvGflME/9QP0h0pYlCDBCTjYa9nZzMDpyxQ==} engines: {node: '>= 0.8'} @@ -2627,6 +3067,9 @@ packages: graceful-fs@4.2.11: resolution: {integrity: sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==} + graphlib@2.1.8: + resolution: {integrity: sha512-jcLLfkpoVGmH7/InMC/1hIvOPSUh38oJtGhvrOFGzioE1DZ+0YW16RgmOJhHiuWTvGiJQ9Z1Ik43JvkRPRvE+A==} + gunzip-maybe@1.4.2: resolution: {integrity: sha512-4haO1M4mLO91PW57BMsDFf75UmwoRX0GkdD+Faw+Lr+r/OZrOCS0pIBwOL1xCKQqnQzbNFGgK2V2CpBUPeFNTw==} hasBin: true @@ -2771,6 +3214,10 @@ packages: resolution: {integrity: sha512-2HvIEKRoqS62guEC+qBjpvRubdX910WCMuJTZ+I9yvqKU2/12eSL549HMwtabb4oupdj2sMP50k+XJfB/8JE6w==} engines: {node: '>=8'} + is-plain-obj@4.1.0: + resolution: {integrity: sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg==} + engines: {node: '>=12'} + is-potential-custom-element-name@1.0.1: resolution: {integrity: sha512-bCYeRA2rVibKZd+s2625gGnGF/t7DSqDs4dP7CrLA1m7jKWz6pps0LpYLJN8Q64HtmPKJ1hrN3nzPNKFEKOUiQ==} @@ -2867,6 +3314,9 @@ packages: json-buffer@3.0.1: resolution: {integrity: sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==} + json-logic-js@2.0.5: + resolution: {integrity: sha512-rTT2+lqcuUmj4DgWfmzupZqQDA64AdmYqizzMPWj3DxGdfFNsxPpcNVSaTj4l8W2tG/+hg7/mQhxjU3aPacO6g==} + json-parse-even-better-errors@2.3.1: resolution: {integrity: sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==} @@ -2935,6 +3385,9 @@ packages: resolution: {integrity: sha512-cNOjgCnLB+FnvWWtyRTzmB3POJ+cXxTA81LoW7u8JdmhfXzriropYwpjShnz1QLLWsQwY7nIxoDmcPTwphDK9w==} engines: {node: ^12.20.0 || ^14.13.1 || >=16.0.0} + linkify-it@5.0.0: + resolution: {integrity: sha512-5aHCbzQRADcdP+ATqnDuhhJ/MRIqDkZX5pyjFHRRysS8vZ5AbqGEoFIb6pYHPZ+L/OC2Lc+xT8uHVVR5CAK/wQ==} + loader-runner@4.3.1: resolution: {integrity: sha512-IWqP2SCPhyVFTBtRcgMHdzlf9ul25NwaFx4wCEH/KjAXuuHY4yNjvPXsBokp8jCB936PyWRaPKUNh8NvylLp2Q==} engines: {node: '>=6.11.5'} @@ -2954,6 +3407,9 @@ packages: lockfile@1.0.4: resolution: {integrity: sha512-cvbTwETRfsFh4nHsL1eGWapU1XFi5Ot9E85sWAwia7Y7EgB7vfqcZhTKZ+l7hCGxSPoushMv5GKhT5PdLv03WA==} + lodash-es@4.17.23: + resolution: {integrity: sha512-kVI48u3PZr38HdYz98UmfPnXl2DXrpdctLrFLCd3kOx1xUkOmpFPx7gCWWM5MPkL/fD8zb+Ph0QzjGFs4+hHWg==} + lodash.debounce@4.0.8: resolution: {integrity: sha512-FT1yDzDYEoYWhnSGnpE/4Kj1fLZkDFyqRb7fNt6FdYOSxlUWAtp42Eh6Wb0rGIv/m9Bgo7x4GhQbm5Ys4SG5ow==} @@ -3017,10 +3473,22 @@ packages: resolution: {integrity: sha512-hXdUTZYIVOt1Ex//jAQi+wTZZpUpwBj/0QsOzqegb3rGMMeJiSEu5xLHnYfBrRV4RH2+OCSOO95Is/7x1WJ4bw==} engines: {node: '>=10'} + markdown-it@14.1.1: + resolution: {integrity: sha512-BuU2qnTti9YKgK5N+IeMubp14ZUKUUw7yeJbkjtosvHiP0AZ5c8IAgEMk79D0eC8F23r4Ac/q8cAIFdm2FtyoA==} + hasBin: true + + marked@14.0.0: + resolution: {integrity: sha512-uIj4+faQ+MgHgwUW1l2PsPglZLOLOT1uErt06dAPtx2kjteLAkbsd/0FiYg/MGS+i7ZKLb7w2WClxHkzOOuryQ==} + engines: {node: '>= 18'} + hasBin: true + math-intrinsics@1.1.0: resolution: {integrity: sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==} engines: {node: '>= 0.4'} + mdurl@2.0.0: + resolution: {integrity: sha512-Lf+9+2r+Tdp5wXDXC4PcIBjTDtq4UKjCPMQhKIuzpJNW0b96kVqSwW0bT7FhRSfmAiFYgP+SCRvdrDozfh0U5w==} + media-typer@0.3.0: resolution: {integrity: sha512-dq+qelQ9akHpcOl/gUVRTxVIOkAJ1wR3QAvb4RsVjS8oVoFjDGTc679wJYmUmknUF5HwMLOgb5O+a3KxfWapPQ==} engines: {node: '>= 0.6'} @@ -3099,6 +3567,9 @@ packages: mlly@1.8.0: resolution: {integrity: sha512-l8D9ODSRWLe2KHJSifWGwBqpTZXIXTeo8mlKjY+E2HAakaTeNpqAyBZ8GSqLzHgw4XmHmC8whvpjJNMbFZN7/g==} + monaco-editor@0.55.1: + resolution: {integrity: sha512-jz4x+TJNFHwHtwuV9vA9rMujcZRb0CEilTEwG2rRSpe/A7Jdkuj8xPKttCgOh+v/lkHy7HsZ64oj+q3xoAFl9A==} + mrmime@2.0.1: resolution: {integrity: sha512-Y3wQdFg2Va6etvQ5I82yUhGdsKrcYox6p7FfL1LbK2J4V01F9TGlepTIhnK24t7koZibmg82KGglhA1XK5IsLQ==} engines: {node: '>=10'} @@ -3262,6 +3733,9 @@ packages: path-to-regexp@0.1.12: resolution: {integrity: sha512-RA1GjUVMnvYFxuqovrEqZoxxW5NUZqbwKtYz/Tt7nXerk0LbLblQmrsgdeOxV5SFHf0UDggjS/bSeOZwt1pmEQ==} + path-to-regexp@8.3.0: + resolution: {integrity: sha512-7jdwVIRtsP8MYpdXSwOS0YdD0Du+qOoF/AEPIt88PcCFrZCzx41oxku1jD88hZBwbNUIEfpqvuhjFaMAqMTWnA==} + path-type@4.0.0: resolution: {integrity: sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw==} engines: {node: '>=8'} @@ -3380,6 +3854,10 @@ packages: pumpify@1.5.1: resolution: {integrity: sha512-oClZI37HvuUJJxSKKrC17bZ9Cu0ZYhEAGPsPUy9KlMUmv9dKX2o77RUmq7f3XjIxbwyGwYzbzQ1L2Ks8sIradQ==} + punycode.js@2.3.1: + resolution: {integrity: sha512-uxFIHU0YlHYhDQtV4R9J6a52SLx28BCjT+4ieh7IGbgwVJWO+km431c4yRlREUAsAmt/uMjQUyQHNEPf0M39CA==} + engines: {node: '>=6'} + punycode@2.3.1: resolution: {integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==} engines: {node: '>=6'} @@ -3398,6 +3876,10 @@ packages: quansync@0.2.11: resolution: {integrity: sha512-AifT7QEbW9Nri4tAwR5M/uzpBuqfZf+zwaEM/QkzEjj7NBuFD2rBuy0K3dE+8wltbezDV7JMA0WfnCPYRSYbXA==} + query-string@9.3.1: + resolution: {integrity: sha512-5fBfMOcDi5SA9qj5jZhWAcTtDfKF5WFdd2uD9nVNlbxVv1baq65aALy6qofpNEGELHvisjjasxQp7BlM9gvMzw==} + engines: {node: '>=18'} + querystringify@2.2.0: resolution: {integrity: sha512-FIqgj2EUvTa7R50u0rGsyTftzjYmv/a3hO345bZNrqabNqjtgiDMgmo4mkUjd+nzU5oF3dClKqFIPUKybUyqoQ==} @@ -3594,6 +4076,10 @@ packages: sonic-boom@4.2.0: resolution: {integrity: sha512-INb7TM37/mAcsGmc9hyyI6+QR3rR1zVRu36B0NeGXKnOOLiZOfER5SA+N7X7k3yUYRzLWafduTDvJAfDswwEww==} + sort-keys@6.0.0: + resolution: {integrity: sha512-ueSlHJMwpIw42CJ4B11Uxzh/S0p0AlOyiNktlv2KOu5e1JpUE6DlC4AAUjXqesHdBRv/g0wC9Q4vwq0NP2pA9w==} + engines: {node: '>=20'} + source-map-js@1.2.1: resolution: {integrity: sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==} engines: {node: '>=0.10.0'} @@ -3608,6 +4094,13 @@ packages: resolution: {integrity: sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==} engines: {node: '>=0.10.0'} + spark-md5@3.0.2: + resolution: {integrity: sha512-wcFzz9cDfbuqe0FZzfi2or1sgyIrsDwmPwfZC4hiNidPdPINjeUwNfv5kldczoEAcjl9Y1L3SM7Uz2PUEQzxQw==} + + split-on-first@3.0.0: + resolution: {integrity: sha512-qxQJTx2ryR0Dw0ITYyekNQWpz6f8dGd7vffGNflQQ3Iqj9NJ6qiZ7ELpZsJ/QBhIVAiDfXdag3+Gp8RvWa62AA==} + engines: {node: '>=12'} + split2@4.2.0: resolution: {integrity: sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg==} engines: {node: '>= 10.x'} @@ -3745,6 +4238,9 @@ packages: resolution: {integrity: sha512-j2Zq4NyQYG5XMST4cbs02Ak8iJUdxRM0XI5QyxXuZOzKOINmWurp3smXu3y5wDcJrptwpSjgXHzIQxR0omXljQ==} engines: {node: '>=12.0.0'} + tinyqueue@3.0.0: + resolution: {integrity: sha512-gRa9gwYU3ECmQYv3lslts5hxuIa90veaEcxDYuu3QGOIAEM2mOZkVHp48ANJuu1CURtRdHKUBY5Lm1tHV+sD4g==} + tinyrainbow@3.0.3: resolution: {integrity: sha512-PSkbLUoxOFRzJYjjxHJt9xro7D+iilgMX/C9lawzVuYiIdcihh9DXmVibBe8lmcFrRi/VzlPjBxbN7rH24q8/Q==} engines: {node: '>=14.0.0'} @@ -3834,6 +4330,9 @@ packages: engines: {node: '>=14.17'} hasBin: true + uc.micro@2.1.0: + resolution: {integrity: sha512-ARDJmphmdvUk6Glw7y9DQ2bFkKBHwQHLi2lsaH6PPmz/Ka9sFOBsBluozhDltWmnv9u/cF6Rt87znRTPV+yp/A==} + ufo@1.6.1: resolution: {integrity: sha512-9a4/uxlTWJ4+a5i0ooc1rU7C7YOw3wT+UGqdeNNHWnOF9qcMBgLRS+4IYUqbczewFx4mLEig6gawh7X6mFlEkA==} @@ -4052,6 +4551,7 @@ packages: whatwg-encoding@2.0.0: resolution: {integrity: sha512-p41ogyeMUrw3jWclHWTQg1k05DSVXPLcVxRTYsXUk+ZooOCZLcoYgPZ/HL/D/N+uQPOtcp1me1WhBEaX02mhWg==} engines: {node: '>=12'} + deprecated: Use @exodus/bytes instead for a more spec-conformant and faster implementation whatwg-mimetype@3.0.0: resolution: {integrity: sha512-nt+N2dzIutVRxARx1nghPKGv1xHikU7HKdfafKkLNLindmPU/ch3U31NOCGGA/dmPcmb1VlofO0vnKAcsm0o/Q==} @@ -4895,81 +5395,159 @@ snapshots: '@esbuild/aix-ppc64@0.25.12': optional: true + '@esbuild/aix-ppc64@0.27.4': + optional: true + '@esbuild/android-arm64@0.25.12': optional: true + '@esbuild/android-arm64@0.27.4': + optional: true + '@esbuild/android-arm@0.25.12': optional: true + '@esbuild/android-arm@0.27.4': + optional: true + '@esbuild/android-x64@0.25.12': optional: true + '@esbuild/android-x64@0.27.4': + optional: true + '@esbuild/darwin-arm64@0.25.12': optional: true + '@esbuild/darwin-arm64@0.27.4': + optional: true + '@esbuild/darwin-x64@0.25.12': optional: true + '@esbuild/darwin-x64@0.27.4': + optional: true + '@esbuild/freebsd-arm64@0.25.12': optional: true + '@esbuild/freebsd-arm64@0.27.4': + optional: true + '@esbuild/freebsd-x64@0.25.12': optional: true + '@esbuild/freebsd-x64@0.27.4': + optional: true + '@esbuild/linux-arm64@0.25.12': optional: true + '@esbuild/linux-arm64@0.27.4': + optional: true + '@esbuild/linux-arm@0.25.12': optional: true + '@esbuild/linux-arm@0.27.4': + optional: true + '@esbuild/linux-ia32@0.25.12': optional: true + '@esbuild/linux-ia32@0.27.4': + optional: true + '@esbuild/linux-loong64@0.25.12': optional: true + '@esbuild/linux-loong64@0.27.4': + optional: true + '@esbuild/linux-mips64el@0.25.12': optional: true + '@esbuild/linux-mips64el@0.27.4': + optional: true + '@esbuild/linux-ppc64@0.25.12': optional: true + '@esbuild/linux-ppc64@0.27.4': + optional: true + '@esbuild/linux-riscv64@0.25.12': optional: true + '@esbuild/linux-riscv64@0.27.4': + optional: true + '@esbuild/linux-s390x@0.25.12': optional: true + '@esbuild/linux-s390x@0.27.4': + optional: true + '@esbuild/linux-x64@0.25.12': optional: true + '@esbuild/linux-x64@0.27.4': + optional: true + '@esbuild/netbsd-arm64@0.25.12': optional: true + '@esbuild/netbsd-arm64@0.27.4': + optional: true + '@esbuild/netbsd-x64@0.25.12': optional: true + '@esbuild/netbsd-x64@0.27.4': + optional: true + '@esbuild/openbsd-arm64@0.25.12': optional: true + '@esbuild/openbsd-arm64@0.27.4': + optional: true + '@esbuild/openbsd-x64@0.25.12': optional: true + '@esbuild/openbsd-x64@0.27.4': + optional: true + '@esbuild/openharmony-arm64@0.25.12': optional: true + '@esbuild/openharmony-arm64@0.27.4': + optional: true + '@esbuild/sunos-x64@0.25.12': optional: true + '@esbuild/sunos-x64@0.27.4': + optional: true + '@esbuild/win32-arm64@0.25.12': optional: true + '@esbuild/win32-arm64@0.27.4': + optional: true + '@esbuild/win32-ia32@0.25.12': optional: true + '@esbuild/win32-ia32@0.27.4': + optional: true + '@esbuild/win32-x64@0.25.12': optional: true + '@esbuild/win32-x64@0.27.4': + optional: true + '@eslint-community/eslint-utils@4.9.0(eslint@9.39.1(jiti@2.4.2))': dependencies: eslint: 9.39.1(jiti@2.4.2) @@ -5569,6 +6147,9 @@ snapshots: dependencies: '@types/node': 20.19.9 + '@types/trusted-types@2.0.7': + optional: true + '@typescript-eslint/eslint-plugin@8.49.0(@typescript-eslint/parser@8.49.0(eslint@9.39.1(jiti@2.4.2))(typescript@5.9.3))(eslint@9.39.1(jiti@2.4.2))(typescript@5.9.3)': dependencies: '@eslint-community/regexpp': 4.12.2 @@ -6121,6 +6702,8 @@ snapshots: array-flatten@1.1.1: {} + array-move@4.0.0: {} + asn1@0.2.6: dependencies: safer-buffer: 2.1.2 @@ -6305,6 +6888,8 @@ snapshots: callsites@3.1.0: {} + camelcase@9.0.0: {} + caniuse-lite@1.0.30001760: {} caseless@0.12.0: {} @@ -6316,6 +6901,8 @@ snapshots: ansi-styles: 4.3.0 supports-color: 7.2.0 + chess.js@1.4.0: {} + chrome-trace-event@1.0.4: {} cli-cursor@3.1.0: @@ -6420,6 +7007,8 @@ snapshots: path-type: 4.0.0 yaml: 1.10.2 + crc-32@1.2.2: {} + cross-spawn@7.0.6: dependencies: path-key: 3.1.1 @@ -6456,14 +7045,20 @@ snapshots: dependencies: ms: 2.1.3 + decamelize@6.0.1: {} + decimal.js@10.6.0: {} + decode-uri-component@0.4.1: {} + decompress-response@6.0.0: dependencies: mimic-response: 3.1.0 deep-is@0.1.4: {} + deepmerge@4.3.1: {} + defaults@1.0.4: dependencies: clone: 1.0.4 @@ -6487,10 +7082,16 @@ snapshots: diff@8.0.2: {} + dijkstrajs@1.0.3: {} + domexception@4.0.0: dependencies: webidl-conversions: 7.0.0 + dompurify@3.2.7: + optionalDependencies: + '@types/trusted-types': 2.0.7 + dotenv-expand@11.0.7: dependencies: dotenv: 16.4.7 @@ -6604,6 +7205,35 @@ snapshots: '@esbuild/win32-ia32': 0.25.12 '@esbuild/win32-x64': 0.25.12 + esbuild@0.27.4: + optionalDependencies: + '@esbuild/aix-ppc64': 0.27.4 + '@esbuild/android-arm': 0.27.4 + '@esbuild/android-arm64': 0.27.4 + '@esbuild/android-x64': 0.27.4 + '@esbuild/darwin-arm64': 0.27.4 + '@esbuild/darwin-x64': 0.27.4 + '@esbuild/freebsd-arm64': 0.27.4 + '@esbuild/freebsd-x64': 0.27.4 + '@esbuild/linux-arm': 0.27.4 + '@esbuild/linux-arm64': 0.27.4 + '@esbuild/linux-ia32': 0.27.4 + '@esbuild/linux-loong64': 0.27.4 + '@esbuild/linux-mips64el': 0.27.4 + '@esbuild/linux-ppc64': 0.27.4 + '@esbuild/linux-riscv64': 0.27.4 + '@esbuild/linux-s390x': 0.27.4 + '@esbuild/linux-x64': 0.27.4 + '@esbuild/netbsd-arm64': 0.27.4 + '@esbuild/netbsd-x64': 0.27.4 + '@esbuild/openbsd-arm64': 0.27.4 + '@esbuild/openbsd-x64': 0.27.4 + '@esbuild/openharmony-arm64': 0.27.4 + '@esbuild/sunos-x64': 0.27.4 + '@esbuild/win32-arm64': 0.27.4 + '@esbuild/win32-ia32': 0.27.4 + '@esbuild/win32-x64': 0.27.4 + escalade@3.2.0: {} escape-html@1.0.3: {} @@ -6612,6 +7242,8 @@ snapshots: escape-string-regexp@4.0.0: {} + escape-string-regexp@5.0.0: {} + eslint-config-prettier@10.1.8(eslint@9.39.1(jiti@2.4.2)): dependencies: eslint: 9.39.1(jiti@2.4.2) @@ -6792,6 +7424,8 @@ snapshots: fast-uri@3.1.0: {} + fastest-levenshtein@1.0.16: {} + fdir@6.5.0(picomatch@4.0.3): optionalDependencies: picomatch: 4.0.3 @@ -6810,6 +7444,8 @@ snapshots: dependencies: minimatch: 5.1.6 + filter-obj@5.1.0: {} + finalhandler@1.3.1: dependencies: debug: 2.6.9 @@ -6935,6 +7571,10 @@ snapshots: graceful-fs@4.2.11: {} + graphlib@2.1.8: + dependencies: + lodash: 4.17.21 + gunzip-maybe@1.4.2: dependencies: browserify-zlib: 0.1.4 @@ -7087,6 +7727,8 @@ snapshots: is-interactive@1.0.0: {} + is-plain-obj@4.1.0: {} + is-potential-custom-element-name@1.0.1: {} is-promise@2.2.2: {} @@ -7198,6 +7840,8 @@ snapshots: json-buffer@3.0.1: {} + json-logic-js@2.0.5: {} + json-parse-even-better-errors@2.3.1: {} json-schema-traverse@0.4.1: {} @@ -7275,6 +7919,10 @@ snapshots: lines-and-columns@2.0.3: {} + linkify-it@5.0.0: + dependencies: + uc.micro: 2.1.0 + loader-runner@4.3.1: {} loader-utils@2.0.4: @@ -7297,6 +7945,8 @@ snapshots: dependencies: signal-exit: 3.0.7 + lodash-es@4.17.23: {} + lodash.debounce@4.0.8: {} lodash.includes@4.3.0: {} @@ -7356,8 +8006,21 @@ snapshots: dependencies: semver: 7.7.3 + markdown-it@14.1.1: + dependencies: + argparse: 2.0.1 + entities: 4.5.0 + linkify-it: 5.0.0 + mdurl: 2.0.0 + punycode.js: 2.3.1 + uc.micro: 2.1.0 + + marked@14.0.0: {} + math-intrinsics@1.1.0: {} + mdurl@2.0.0: {} + media-typer@0.3.0: {} merge-descriptors@1.0.3: {} @@ -7417,6 +8080,11 @@ snapshots: pkg-types: 1.3.1 ufo: 1.6.1 + monaco-editor@0.55.1: + dependencies: + dompurify: 3.2.7 + marked: 14.0.0 + mrmime@2.0.1: {} ms@2.0.0: {} @@ -7593,6 +8261,8 @@ snapshots: path-to-regexp@0.1.12: {} + path-to-regexp@8.3.0: {} + path-type@4.0.0: {} pathe@2.0.3: {} @@ -7722,6 +8392,8 @@ snapshots: inherits: 2.0.4 pump: 2.0.1 + punycode.js@2.3.1: {} + punycode@2.3.1: {} pure-rand@7.0.1: {} @@ -7736,6 +8408,12 @@ snapshots: quansync@0.2.11: {} + query-string@9.3.1: + dependencies: + decode-uri-component: 0.4.1 + filter-obj: 5.1.0 + split-on-first: 3.0.0 + querystringify@2.2.0: {} quick-format-unescaped@4.0.4: {} @@ -7977,6 +8655,10 @@ snapshots: dependencies: atomic-sleep: 1.0.0 + sort-keys@6.0.0: + dependencies: + is-plain-obj: 4.1.0 + source-map-js@1.2.1: {} source-map-support@0.5.19: @@ -7991,6 +8673,10 @@ snapshots: source-map@0.6.1: {} + spark-md5@3.0.2: {} + + split-on-first@3.0.0: {} + split2@4.2.0: {} sprintf-js@1.0.3: {} @@ -8137,6 +8823,8 @@ snapshots: fdir: 6.5.0(picomatch@4.0.3) picomatch: 4.0.3 + tinyqueue@3.0.0: {} + tinyrainbow@3.0.3: {} tldts-core@6.1.86: {} @@ -8214,6 +8902,8 @@ snapshots: typescript@5.9.3: {} + uc.micro@2.1.0: {} + ufo@1.6.1: {} uglify-js@3.19.3: diff --git a/tools/blue-quickjs-cli/README.md b/tools/blue-quickjs-cli/README.md new file mode 100644 index 0000000..7f337ef --- /dev/null +++ b/tools/blue-quickjs-cli/README.md @@ -0,0 +1,20 @@ +# blue-quickjs CLI + +Deterministic command-line interface for build/run/inspect workflows. + +## Commands + +- `build` — build a deterministic module-pack artifact from an entry path. +- `compat` — emit compatibility diagnostics for an entry path/profile. +- `run` — evaluate an artifact JSON against a manifest/input envelope. +- `inspect` — print artifact metadata including module list, graph hash, + provenance/package hints, and source-map presence. +- `explain-error` — map VM payloads to structured runtime error shapes and + extract source locations (`path:line:column`) from mapped diagnostics. +- `consensus-report` — run wasm-node vs wasm-browser consensus reproducibility + report generation (`tools/consensus-parity/...`), with optional + `--browser chromium|firefox|webkit`. +- `native-report` — run native reproducibility archive generation (diagnostic by + default; add `--strict` to assert zero mismatches). +- `native-parity` — run native parity report helper with strict/trace/baseline + switches. diff --git a/tools/blue-quickjs-cli/eslint.config.mjs b/tools/blue-quickjs-cli/eslint.config.mjs new file mode 100644 index 0000000..3f9aadf --- /dev/null +++ b/tools/blue-quickjs-cli/eslint.config.mjs @@ -0,0 +1,11 @@ +import baseConfig from '../../eslint.config.mjs'; + +export default [ + ...baseConfig, + { + files: ['**/*.ts'], + rules: { + '@typescript-eslint/no-explicit-any': 'off', + }, + }, +]; diff --git a/tools/blue-quickjs-cli/package.json b/tools/blue-quickjs-cli/package.json new file mode 100644 index 0000000..d4923b0 --- /dev/null +++ b/tools/blue-quickjs-cli/package.json @@ -0,0 +1,35 @@ +{ + "name": "@blue-quickjs/blue-quickjs-cli", + "version": "0.0.1", + "private": true, + "type": "module", + "bin": { + "blue-quickjs": "./dist/cli.js" + }, + "main": "./dist/index.js", + "module": "./dist/index.js", + "types": "./dist/index.d.ts", + "exports": { + "./package.json": "./package.json", + ".": { + "@blue-quickjs/source": "./src/index.ts", + "types": "./dist/index.d.ts", + "import": "./dist/index.js", + "default": "./dist/index.js" + } + }, + "files": [ + "dist", + "!**/*.tsbuildinfo" + ], + "nx": { + "name": "blue-quickjs-cli" + }, + "dependencies": { + "@blue-quickjs/abi-manifest": "workspace:*", + "@blue-quickjs/deterministic-builder": "workspace:*", + "@blue-quickjs/quickjs-runtime": "workspace:*", + "@blue-quickjs/test-harness": "workspace:*", + "tslib": "^2.3.0" + } +} diff --git a/tools/blue-quickjs-cli/src/cli.ts b/tools/blue-quickjs-cli/src/cli.ts new file mode 100644 index 0000000..976030d --- /dev/null +++ b/tools/blue-quickjs-cli/src/cli.ts @@ -0,0 +1,5 @@ +#!/usr/bin/env node +import { runCli } from './lib/cli.js'; + +const exitCode = await runCli(process.argv.slice(2)); +process.exit(exitCode); diff --git a/tools/blue-quickjs-cli/src/index.ts b/tools/blue-quickjs-cli/src/index.ts new file mode 100644 index 0000000..5f2db8f --- /dev/null +++ b/tools/blue-quickjs-cli/src/index.ts @@ -0,0 +1 @@ +export { runCli, parseArgMap } from './lib/cli.js'; diff --git a/tools/blue-quickjs-cli/src/lib/cli.spec.ts b/tools/blue-quickjs-cli/src/lib/cli.spec.ts new file mode 100644 index 0000000..bbb73e8 --- /dev/null +++ b/tools/blue-quickjs-cli/src/lib/cli.spec.ts @@ -0,0 +1,111 @@ +import { + buildConsensusReportArgs, + buildNativeArchiveArgs, + buildNativeParityArgs, + extractStackLocations, + parseArgMap, +} from './cli.js'; + +describe('blue-quickjs-cli argument parsing', () => { + it('parses command and key/value options', () => { + const parsed = parseArgMap([ + 'build', + '--entry', + 'src/main.ts', + '--profile', + 'compat-binary-v1', + '--allow-incompatible', + ]); + + expect(parsed.command).toBe('build'); + expect(parsed.options.get('entry')).toBe('src/main.ts'); + expect(parsed.options.get('profile')).toBe('compat-binary-v1'); + expect(parsed.options.get('allow-incompatible')).toBe(true); + }); + + it('throws on unexpected positional options', () => { + expect(() => parseArgMap(['run', '--artifact', 'a.json', 'extra'])).toThrow( + /unexpected positional argument/i, + ); + }); + + it('extracts and de-duplicates stack locations', () => { + const locations = extractStackLocations( + 'ModuleEvaluationError: Error at src/app.ts:12:4 and src/app.ts:12:4, helper ./entry.js:3:1', + ); + + expect(locations).toEqual([ + { source: 'src/app.ts', line: 12, column: 4 }, + { source: './entry.js', line: 3, column: 1 }, + ]); + }); + + it('builds consensus-report forwarded arguments', () => { + const { options } = parseArgMap([ + 'consensus-report', + '--out-dir', + 'artifacts/custom', + '--base-url', + 'http://127.0.0.1:4300', + '--browser', + 'firefox', + '--reuse-server', + ]); + + expect(buildConsensusReportArgs(options)).toEqual([ + '--out-dir', + 'artifacts/custom', + '--base-url', + 'http://127.0.0.1:4300', + '--browser', + 'firefox', + '--reuse-server', + ]); + }); + + it('builds native-report forwarded arguments', () => { + const { options } = parseArgMap([ + 'native-report', + '--strict', + '--out-dir', + 'artifacts/native', + '--gas-charge-tape-capacity', + '512', + ]); + + expect(buildNativeArchiveArgs(options)).toEqual([ + '--strict', + '--out-dir', + 'artifacts/native', + '--gas-charge-tape-capacity', + '512', + ]); + }); + + it('builds native-parity forwarded arguments', () => { + const { options } = parseArgMap([ + 'native-parity', + '--out', + 'parity.json', + '--compare', + 'baseline.json', + '--gas-charge-tape-capacity', + '128', + '--assert-match', + '--include-gas-trace', + '--include-gas-charge-tape', + ]); + + expect(buildNativeParityArgs(options)).toEqual([ + '--out', + 'parity.json', + '--compare', + 'baseline.json', + '--gas-charge-tape-capacity', + '128', + '--assert-match', + '--include-gas-trace', + '--include-gas-charge-tape', + ]); + }); +}); diff --git a/tools/blue-quickjs-cli/src/lib/cli.ts b/tools/blue-quickjs-cli/src/lib/cli.ts new file mode 100644 index 0000000..c811e67 --- /dev/null +++ b/tools/blue-quickjs-cli/src/lib/cli.ts @@ -0,0 +1,692 @@ +import { spawnSync } from 'node:child_process'; +import { existsSync } from 'node:fs'; +import { readFile, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { + HOST_V1_HASH, + HOST_V1_MANIFEST, + HOST_V2_HASH, + HOST_V2_MANIFEST, + type AbiManifest, + validateAbiManifest, +} from '@blue-quickjs/abi-manifest'; +import { + buildDeterministicModulePack, + type DeterministicExecutionProfile, +} from '@blue-quickjs/deterministic-builder'; +import { + type ProgramArtifact, + type ProgramArtifactV2, + type HostDispatcherHandlers, + evaluate, + validateInputEnvelope, + validateProgramArtifact, + validateProgramArtifactV2, +} from '@blue-quickjs/quickjs-runtime'; +import { DETERMINISM_INPUT } from '@blue-quickjs/test-harness'; + +type ArgValue = string | true; +type ArgMap = Map; +type StackLocation = { + source: string; + line: number; + column: number; +}; + +export function parseArgMap(args: string[]): { + command: string | null; + options: ArgMap; +} { + if (args.length === 0) { + return { command: null, options: new Map() }; + } + + const [command, ...rest] = args; + const options = new Map(); + + for (let i = 0; i < rest.length; i += 1) { + const token = rest[i]; + if (!token.startsWith('--')) { + throw new Error(`unexpected positional argument: ${token}`); + } + const key = token.slice(2); + const maybeValue = rest[i + 1]; + if (maybeValue && !maybeValue.startsWith('--')) { + options.set(key, maybeValue); + i += 1; + continue; + } + options.set(key, true); + } + + return { command, options }; +} + +export async function runCli(args: string[]): Promise { + try { + const { command, options } = parseArgMap(args); + if (!command) { + printHelp(); + return 2; + } + + switch (command) { + case 'build': + return await runBuild(options); + case 'run': + return await runEvaluate(options); + case 'consensus-report': + return await runConsensusReport(options); + case 'native-report': + return await runNativeArchiveReport(options); + case 'native-parity': + return await runNativeParityReport(options); + case 'compat': + return await runCompat(options); + case 'inspect': + return await runInspect(options); + case 'explain-error': + return await runExplainError(options); + case 'help': + case '--help': + case '-h': + printHelp(); + return 0; + default: + throw new Error(`unknown command: ${command}`); + } + } catch (error) { + const message = error instanceof Error ? error.message : String(error); + console.error(`blue-quickjs-cli error: ${message}`); + return 1; + } +} + +async function runBuild(options: ArgMap): Promise { + const entryPath = getRequiredString(options, 'entry'); + const profile = (getOptionalString(options, 'profile') ?? + 'baseline-v1') as DeterministicExecutionProfile; + const cwd = getOptionalString(options, 'cwd') ?? process.cwd(); + const allowIncompatible = options.has('allow-incompatible'); + const abiId = getOptionalString(options, 'abi-id') ?? 'Host.v1'; + const abiVersion = Number( + getOptionalString(options, 'abi-version') ?? + (abiId === 'Host.v2' ? '2' : '1'), + ); + const abiManifestHash = + getOptionalString(options, 'abi-manifest-hash') ?? + (abiId === 'Host.v2' ? HOST_V2_HASH : HOST_V1_HASH); + const gasVersionRaw = getOptionalString(options, 'gas-version'); + const gasVersion = + gasVersionRaw !== undefined + ? Number.parseInt(gasVersionRaw, 10) + : undefined; + if (gasVersion !== undefined && !Number.isInteger(gasVersion)) { + throw new Error('--gas-version must be an integer'); + } + const outPath = + getOptionalString(options, 'out') ?? + path.resolve(cwd, `${path.basename(entryPath)}.program.json`); + + const result = await buildDeterministicModulePack({ + entryPath, + absWorkingDir: cwd, + profile, + emitProgramArtifact: true, + rejectIncompatible: !allowIncompatible, + abiId, + abiVersion, + abiManifestHash, + ...(gasVersion !== undefined ? { gasVersion } : {}), + }); + + if (!result.programArtifact) { + throw new Error('builder did not emit ProgramArtifact.v2'); + } + + const payload = { + programArtifact: result.programArtifact, + modulePack: result.modulePack, + compatibilityReport: result.compatibilityReport, + }; + await writeJsonFile(outPath, payload); + + console.log( + JSON.stringify( + { + outPath, + profile, + compatibilityOk: result.compatibility.ok, + moduleCount: result.modulePack.modules.length, + graphHash: result.modulePack.graphHash, + }, + null, + 2, + ), + ); + + return result.compatibility.ok ? 0 : 2; +} + +async function runCompat(options: ArgMap): Promise { + const entryPath = getRequiredString(options, 'entry'); + const profile = (getOptionalString(options, 'profile') ?? + 'baseline-v1') as DeterministicExecutionProfile; + const cwd = getOptionalString(options, 'cwd') ?? process.cwd(); + const outPath = getOptionalString(options, 'out'); + + const result = await buildDeterministicModulePack({ + entryPath, + absWorkingDir: cwd, + profile, + rejectIncompatible: false, + emitProgramArtifact: false, + }); + + if (outPath) { + await writeJsonFile(outPath, result.compatibilityReport); + } + + console.log(JSON.stringify(result.compatibilityReport, null, 2)); + return result.compatibilityReport.ok ? 0 : 2; +} + +async function runInspect(options: ArgMap): Promise { + const artifactPath = getRequiredString(options, 'artifact'); + const artifactJson = await readJsonFile(artifactPath); + const program = normalizeProgramArtifact(artifactJson); + const summary = summarizeProgramArtifact(program); + console.log(JSON.stringify(summary, null, 2)); + return 0; +} + +async function runEvaluate(options: ArgMap): Promise { + const artifactPath = getRequiredString(options, 'artifact'); + const manifestPath = getOptionalString(options, 'manifest'); + const inputPath = getOptionalString(options, 'input'); + const gasLimit = BigInt(getOptionalString(options, 'gas-limit') ?? '5000000'); + + const artifactJson = await readJsonFile(artifactPath); + const program = normalizeProgramArtifact(artifactJson); + const manifest = manifestPath + ? validateAbiManifest((await readJsonFile(manifestPath)) as AbiManifest) + : defaultManifestForProgram(program); + const input = inputPath + ? validateInputEnvelope(await readJsonFile(inputPath)) + : validateInputEnvelope(DETERMINISM_INPUT); + + const result = await evaluate({ + program, + input, + gasLimit, + manifest, + handlers: createCliHostHandlers(), + tape: { capacity: 64 }, + }); + + if (result.ok) { + console.log( + JSON.stringify( + { + ok: true, + value: result.value, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeLength: (result.tape ?? []).length, + }, + null, + 2, + ), + ); + return 0; + } + + const mappedLocations = extractStackLocations(result.message); + console.log( + JSON.stringify( + { + ok: false, + type: result.type, + code: result.error.code, + tag: 'tag' in result.error ? result.error.tag : null, + message: result.message, + mappedLocations, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + }, + null, + 2, + ), + ); + return 1; +} + +async function runExplainError(options: ArgMap): Promise { + const raw = getOptionalString(options, 'raw'); + const payloadOption = getOptionalString(options, 'payload'); + const manifestPath = getOptionalString(options, 'manifest'); + + const payload = payloadOption ?? extractPayloadFromRaw(raw); + if (!payload) { + throw new Error('explain-error requires --payload or --raw'); + } + + const manifest = manifestPath + ? validateAbiManifest((await readJsonFile(manifestPath)) as AbiManifest) + : HOST_V1_MANIFEST; + const mapped = mapVmPayload(payload, manifest); + const mappedLocations = extractStackLocations(payload); + console.log( + JSON.stringify( + { + ...mapped, + mappedLocations, + }, + null, + 2, + ), + ); + return 0; +} + +async function runConsensusReport(options: ArgMap): Promise { + const cwd = resolveCliRepoRoot(getOptionalString(options, 'cwd')); + const scriptPath = path.join( + cwd, + 'tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs', + ); + const args = buildConsensusReportArgs(options); + return runNodeScript(scriptPath, args, cwd); +} + +async function runNativeArchiveReport(options: ArgMap): Promise { + const cwd = resolveCliRepoRoot(getOptionalString(options, 'cwd')); + const scriptPath = path.join( + cwd, + 'tools/quickjs-native-harness/scripts/archive-reproducibility-report.mjs', + ); + const args = buildNativeArchiveArgs(options); + return runNodeScript(scriptPath, args, cwd); +} + +async function runNativeParityReport(options: ArgMap): Promise { + const cwd = resolveCliRepoRoot(getOptionalString(options, 'cwd')); + const scriptPath = path.join( + cwd, + 'tools/quickjs-native-harness/scripts/parity-report.mjs', + ); + const args = buildNativeParityArgs(options); + return runNodeScript(scriptPath, args, cwd); +} + +function createCliHostHandlers(): HostDispatcherHandlers { + return { + document: { + get: (path: string) => ({ ok: { path }, units: 1 }), + getCanonical: (path: string) => ({ ok: { canonical: path }, units: 1 }), + }, + emit: () => ({ ok: null, units: 0 }), + }; +} + +function normalizeProgramArtifact( + value: unknown, +): ProgramArtifact | ProgramArtifactV2 { + if (value && typeof value === 'object' && !Array.isArray(value)) { + const record = value as Record; + if (record.programArtifact) { + return validateProgramArtifactV2(record.programArtifact); + } + if (record.program) { + const program = record.program; + if ( + program && + typeof program === 'object' && + !Array.isArray(program) && + (program as { version?: unknown }).version === 2 + ) { + return validateProgramArtifactV2(program); + } + return validateProgramArtifact(program); + } + if (record.version === 2) { + return validateProgramArtifactV2(record); + } + } + + return validateProgramArtifact(value); +} + +function summarizeProgramArtifact( + program: ProgramArtifact | ProgramArtifactV2, +): Record { + if (isProgramArtifactV2(program)) { + const modulePack = + program.sourceKind === 'module-pack' && 'modulePack' in program.source + ? program.source.modulePack + : null; + const moduleSpecifiers = modulePack + ? modulePack.modules.map((module) => module.specifier) + : []; + const modulesWithSourceMap = modulePack + ? modulePack.modules.filter((module) => !!module.sourceMap).length + : 0; + const packages = modulePack + ? [ + ...new Set( + modulePack.modules + .map((module) => module.originMeta?.packageName) + .filter((value): value is string => Boolean(value)), + ), + ].sort() + : []; + return { + version: program.version, + sourceKind: program.sourceKind, + executionProfile: program.executionProfile, + abiId: program.abiId, + abiVersion: program.abiVersion, + abiManifestHash: program.abiManifestHash, + engineBuildHash: program.engineBuildHash ?? null, + gasVersion: program.gasVersion ?? null, + entrySpecifier: modulePack?.entrySpecifier ?? null, + entryExport: modulePack?.entryExport ?? 'default', + moduleCount: modulePack ? modulePack.modules.length : null, + graphHash: modulePack ? modulePack.graphHash : null, + builderVersion: modulePack?.builderVersion ?? null, + dependencyIntegrity: modulePack?.dependencyIntegrity ?? null, + moduleSpecifiers, + modulesWithSourceMap, + diagnosticsMeta: modulePack?.diagnosticsMeta ?? null, + npmPackages: packages, + }; + } + + const legacy = program; + return { + version: 1, + sourceKind: 'script', + executionProfile: legacy.executionProfile ?? 'baseline-v1', + abiId: legacy.abiId, + abiVersion: legacy.abiVersion, + abiManifestHash: legacy.abiManifestHash, + gasVersion: legacy.gasVersion ?? null, + codeUnits: legacy.code.length, + }; +} + +export function extractStackLocations(message: string): StackLocation[] { + const matches = message.matchAll( + /([^\s:()]+(?:\.[cm]?js|\.ts|\.tsx|\.jsx|\.mjs)):(\d+):(\d+)/g, + ); + const dedup = new Set(); + const locations: StackLocation[] = []; + + for (const match of matches) { + const source = match[1]; + const line = Number(match[2]); + const column = Number(match[3]); + if ( + !source || + !Number.isInteger(line) || + !Number.isInteger(column) || + line <= 0 || + column <= 0 + ) { + continue; + } + const key = `${source}:${line}:${column}`; + if (dedup.has(key)) { + continue; + } + dedup.add(key); + locations.push({ source, line, column }); + } + + return locations; +} + +function defaultManifestForProgram( + program: ProgramArtifact | ProgramArtifactV2, +): AbiManifest { + if (program.abiId === 'Host.v2') { + return HOST_V2_MANIFEST; + } + return HOST_V1_MANIFEST; +} + +function extractPayloadFromRaw(raw?: string): string | null { + if (!raw) { + return null; + } + const trimmed = raw.trim(); + if (trimmed.startsWith('ERROR ')) { + const gasMarker = ' GAS remaining='; + const gasIndex = trimmed.lastIndexOf(gasMarker); + if (gasIndex >= 0) { + return trimmed.slice('ERROR '.length, gasIndex).trim(); + } + return trimmed.slice('ERROR '.length).trim(); + } + return trimmed; +} + +function getRequiredString(options: ArgMap, key: string): string { + const value = getOptionalString(options, key); + if (!value) { + throw new Error(`missing required option --${key}`); + } + return value; +} + +function getOptionalString(options: ArgMap, key: string): string | undefined { + const value = options.get(key); + return typeof value === 'string' ? value : undefined; +} + +function resolveCliRepoRoot(cwdOverride?: string): string { + const start = path.resolve(cwdOverride ?? process.cwd()); + const root = findWorkspaceRoot(start); + if (!root) { + throw new Error( + 'unable to resolve workspace root (expected pnpm-workspace.yaml in parent directories)', + ); + } + return root; +} + +function findWorkspaceRoot(start: string): string | null { + let cursor = start; + while (true) { + if (existsSync(path.join(cursor, 'pnpm-workspace.yaml'))) { + return cursor; + } + const parent = path.dirname(cursor); + if (parent === cursor) { + return null; + } + cursor = parent; + } +} + +function runNodeScript( + scriptPath: string, + args: string[], + cwd: string, +): number { + if (!existsSync(scriptPath)) { + throw new Error(`script not found: ${scriptPath}`); + } + const result = spawnSync(process.execPath, [scriptPath, ...args], { + cwd, + stdio: 'inherit', + }); + if (result.error) { + throw result.error; + } + if (result.status === null) { + throw new Error(`script exited without status: ${scriptPath}`); + } + return result.status; +} + +export function buildConsensusReportArgs(options: ArgMap): string[] { + const args: string[] = []; + appendStringOption(args, options, 'out-dir'); + appendStringOption(args, options, 'base-url'); + appendStringOption(args, options, 'browser'); + appendBooleanFlag(args, options, 'reuse-server'); + return args; +} + +export function buildNativeArchiveArgs(options: ArgMap): string[] { + const args: string[] = []; + appendBooleanFlag(args, options, 'strict'); + appendStringOption(args, options, 'out-dir'); + appendStringOption(args, options, 'gas-charge-tape-capacity'); + return args; +} + +export function buildNativeParityArgs(options: ArgMap): string[] { + const args: string[] = []; + appendStringOption(args, options, 'out'); + appendStringOption(args, options, 'compare'); + appendStringOption(args, options, 'gas-charge-tape-capacity'); + appendStringOption(args, options, 'gas-delta-baseline'); + appendStringOption(args, options, 'write-gas-delta-baseline'); + appendBooleanFlag(args, options, 'assert-match'); + appendBooleanFlag(args, options, 'ignore-gas'); + appendBooleanFlag(args, options, 'include-gas-trace'); + appendBooleanFlag(args, options, 'include-gas-charge-tape'); + return args; +} + +function appendStringOption( + args: string[], + options: ArgMap, + key: string, +): void { + const value = getOptionalString(options, key); + if (value !== undefined) { + args.push(`--${key}`, value); + } +} + +function appendBooleanFlag(args: string[], options: ArgMap, key: string): void { + if (options.has(key)) { + args.push(`--${key}`); + } +} + +async function readJsonFile(filePath: string): Promise { + const text = await readFile(path.resolve(filePath), 'utf8'); + return JSON.parse(text); +} + +async function writeJsonFile( + filePath: string, + payload: unknown, +): Promise { + await writeFile( + path.resolve(filePath), + `${JSON.stringify(payload, null, 2)}\n`, + 'utf8', + ); +} + +function mapVmPayload(payload: string, manifest: AbiManifest) { + const canonicalManifest = validateAbiManifest(manifest); + if (payload.includes('OutOfGas')) { + return { + kind: 'out-of-gas', + code: 'OUT_OF_GAS', + tag: 'vm/out_of_gas', + message: payload, + manifestAbiId: canonicalManifest.abi_id, + manifestAbiVersion: canonicalManifest.abi_version, + }; + } + if (payload.includes('ModuleSpecifierNotFound')) { + return { + kind: 'module-pack', + code: 'MODULE_SPECIFIER_NOT_FOUND', + tag: 'vm/module_pack', + message: payload, + manifestAbiId: canonicalManifest.abi_id, + manifestAbiVersion: canonicalManifest.abi_version, + }; + } + if (payload.includes('ModuleExportMissing')) { + return { + kind: 'module-pack', + code: 'MODULE_EXPORT_MISSING', + tag: 'vm/module_pack', + message: payload, + manifestAbiId: canonicalManifest.abi_id, + manifestAbiVersion: canonicalManifest.abi_version, + }; + } + if (payload.includes('ModuleResolutionError')) { + return { + kind: 'module-pack', + code: 'MODULE_RESOLUTION_ERROR', + tag: 'vm/module_pack', + message: payload, + manifestAbiId: canonicalManifest.abi_id, + manifestAbiVersion: canonicalManifest.abi_version, + }; + } + if (payload.includes('ModuleEvaluationError')) { + return { + kind: 'module-pack', + code: 'MODULE_EVALUATION_ERROR', + tag: 'vm/module_pack', + message: payload, + manifestAbiId: canonicalManifest.abi_id, + manifestAbiVersion: canonicalManifest.abi_version, + }; + } + if (payload.includes('HostError')) { + return { + kind: 'host', + code: 'HOST_ERROR', + tag: 'vm/host', + message: payload, + manifestAbiId: canonicalManifest.abi_id, + manifestAbiVersion: canonicalManifest.abi_version, + }; + } + return { + kind: 'js-exception', + code: 'JS_EXCEPTION', + tag: 'vm/js_exception', + message: payload, + manifestAbiId: canonicalManifest.abi_id, + manifestAbiVersion: canonicalManifest.abi_version, + }; +} + +function isProgramArtifactV2( + program: ProgramArtifact | ProgramArtifactV2, +): program is ProgramArtifactV2 { + return 'version' in program && program.version === 2; +} + +function printHelp(): void { + console.log( + [ + 'blue-quickjs CLI', + '', + 'Commands:', + ' build --entry [--profile compat-binary-v1] [--out artifact.json] [--abi-id Host.v2] [--abi-version 2] [--abi-manifest-hash ] [--gas-version ] [--allow-incompatible]', + ' compat --entry [--profile baseline-v1] [--out report.json]', + ' run --artifact [--manifest ] [--input ] [--gas-limit ]', + ' inspect --artifact ', + ' explain-error --payload | --raw "ERROR ..."', + ' consensus-report [--out-dir artifacts/reproducibility-consensus] [--base-url http://127.0.0.1:4300] [--browser chromium|firefox|webkit] [--reuse-server]', + ' native-report [--strict] [--out-dir artifacts/reproducibility] [--gas-charge-tape-capacity ]', + ' native-parity [--assert-match] [--out parity.json] [--compare previous.json] [--ignore-gas] [--include-gas-trace] [--include-gas-charge-tape]', + ].join('\n'), + ); +} diff --git a/tools/blue-quickjs-cli/tsconfig.json b/tools/blue-quickjs-cli/tsconfig.json new file mode 100644 index 0000000..62ebbd9 --- /dev/null +++ b/tools/blue-quickjs-cli/tsconfig.json @@ -0,0 +1,13 @@ +{ + "extends": "../../tsconfig.base.json", + "files": [], + "include": [], + "references": [ + { + "path": "./tsconfig.lib.json" + }, + { + "path": "./tsconfig.spec.json" + } + ] +} diff --git a/tools/blue-quickjs-cli/tsconfig.lib.json b/tools/blue-quickjs-cli/tsconfig.lib.json new file mode 100644 index 0000000..b3eda42 --- /dev/null +++ b/tools/blue-quickjs-cli/tsconfig.lib.json @@ -0,0 +1,32 @@ +{ + "extends": "./tsconfig.json", + "compilerOptions": { + "outDir": "dist", + "rootDir": "src", + "tsBuildInfoFile": "dist/tsconfig.lib.tsbuildinfo", + "declaration": true, + "declarationMap": true, + "types": ["node"] + }, + "include": ["src/**/*.ts"], + "exclude": [ + "vite.config.ts", + "eslint.config.mjs", + "src/**/*.spec.ts", + "src/**/*.test.ts" + ], + "references": [ + { + "path": "../../libs/test-harness/tsconfig.lib.json" + }, + { + "path": "../../libs/quickjs-runtime/tsconfig.lib.json" + }, + { + "path": "../../libs/deterministic-builder/tsconfig.lib.json" + }, + { + "path": "../../libs/abi-manifest/tsconfig.lib.json" + } + ] +} diff --git a/tools/blue-quickjs-cli/tsconfig.spec.json b/tools/blue-quickjs-cli/tsconfig.spec.json new file mode 100644 index 0000000..a20948c --- /dev/null +++ b/tools/blue-quickjs-cli/tsconfig.spec.json @@ -0,0 +1,29 @@ +{ + "extends": "./tsconfig.json", + "compilerOptions": { + "outDir": "dist/test", + "tsBuildInfoFile": "dist/tsconfig.spec.tsbuildinfo", + "types": ["vitest/globals", "vitest/importMeta", "node"] + }, + "include": [ + "vite.config.ts", + "src/**/*.ts", + "src/**/*.test.ts", + "src/**/*.spec.ts", + "src/**/*.d.ts" + ], + "references": [ + { + "path": "../../libs/test-harness/tsconfig.lib.json" + }, + { + "path": "../../libs/quickjs-runtime/tsconfig.lib.json" + }, + { + "path": "../../libs/deterministic-builder/tsconfig.lib.json" + }, + { + "path": "../../libs/abi-manifest/tsconfig.lib.json" + } + ] +} diff --git a/tools/blue-quickjs-cli/vite.config.ts b/tools/blue-quickjs-cli/vite.config.ts new file mode 100644 index 0000000..bef9d57 --- /dev/null +++ b/tools/blue-quickjs-cli/vite.config.ts @@ -0,0 +1,20 @@ +/// +import { defineConfig } from 'vite'; + +export default defineConfig(() => ({ + root: import.meta.dirname, + cacheDir: '../../node_modules/.vite/tools/blue-quickjs-cli', + plugins: [], + test: { + name: 'blue-quickjs-cli', + watch: false, + globals: true, + environment: 'node', + include: ['{src,tests}/**/*.{test,spec}.{js,mjs,cjs,ts,mts,cts,jsx,tsx}'], + reporters: ['default'], + coverage: { + reportsDirectory: './test-output/vitest/coverage', + provider: 'v8' as const, + }, + }, +})); diff --git a/tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs b/tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs new file mode 100644 index 0000000..d20548f --- /dev/null +++ b/tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs @@ -0,0 +1,797 @@ +#!/usr/bin/env node + +import { chromium, firefox, webkit } from '@playwright/test'; +import { createHash } from 'node:crypto'; +import { mkdir, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { fileURLToPath } from 'node:url'; +import jiti from 'jiti'; +import { createServer } from 'vite'; + +const __dirname = path.dirname(fileURLToPath(import.meta.url)); +const repoRoot = path.resolve(__dirname, '..', '..', '..'); +const smokeWebConfigPath = path.join(repoRoot, 'apps/smoke-web/vite.config.mts'); +const require = jiti(import.meta.url, { interopDefault: true }); + +const { encodeDv } = require('../../../libs/dv/src/index.ts'); +const { bundleDeterministicProgram } = require( + '../../../libs/deterministic-bundler/src/index.ts', +); +const { createRuntime, evaluate, initializeDeterministicVm } = require( + '../../../libs/quickjs-runtime/src/index.ts', +); +const { + BINARY_LIBRARY_FIXTURES, + BINARY_LIBRARY_GAS_LIMIT, + BINARY_LIBRARY_INPUT, + BINARY_LIBRARY_MANIFEST, + BINARY_LIBRARY_PROGRAM_BASE, + CHESS_LIBRARY_ENTRY_PATH, + CHESS_LIBRARY_GAS_LIMIT, + CHESS_LIBRARY_INPUT, + CHESS_LIBRARY_MANIFEST, + CHESS_LIBRARY_PROGRAM_BASE, + DETERMINISM_FIXTURES, + GAS_SAMPLE_FIXTURES, + MODULE_PACK_FIXTURES, + createDeterminismHost, + parseDeterministicEvalOutput, + serializeHostTape, +} = require('../../../libs/test-harness/src/index.ts'); +const { loadQuickjsWasmBinary, loadQuickjsWasmMetadata } = require( + '../../../libs/quickjs-wasm/src/index.ts', +); + +const args = parseArgs(process.argv.slice(2)); +const browserType = resolveBrowserType(args.browser); + +const timestamp = new Date().toISOString().replace(/[:.]/g, '-'); +const outDir = path.resolve(repoRoot, args.outDir); +const reportPath = path.join(outDir, `consensus-parity-report-${timestamp}.json`); + +await mkdir(outDir, { recursive: true }); + +const metadata = await loadQuickjsWasmMetadata(); +const wasmBinary = await loadQuickjsWasmBinary('wasm32', 'release', metadata); +const variantMetadata = metadata.variants?.wasm32?.release ?? null; + +const viteServer = args.reuseServer + ? null + : await createServer({ + configFile: smokeWebConfigPath, + server: { + host: '127.0.0.1', + port: 4300, + strictPort: true, + }, + clearScreen: false, + }); + +if (viteServer) { + await viteServer.listen(); +} + +const baseUrl = args.baseUrl ?? 'http://127.0.0.1:4300'; +const browser = await browserType.launch({ headless: true }); +const context = await browser.newContext({ baseURL: baseUrl }); + +try { + const chessBundle = await bundleDeterministicProgram({ + absWorkingDir: repoRoot, + entryPath: CHESS_LIBRARY_ENTRY_PATH, + profile: 'compat-general-v1', + }); + const binaryBundles = await Promise.all( + BINARY_LIBRARY_FIXTURES.map(async (fixture) => ({ + name: fixture.name, + code: ( + await bundleDeterministicProgram({ + absWorkingDir: repoRoot, + entryPath: fixture.entryPath, + profile: 'compat-binary-v1', + }) + ).code, + })), + ); + + const nodeSnapshots = await collectNodeSnapshots({ + metadata, + wasmBinary, + chessCode: chessBundle.code, + binaryBundles, + }); + const browserSnapshots = await collectBrowserSnapshots({ + context, + chessCode: chessBundle.code, + binaryBundles, + }); + + const suites = [ + compareNamedSuite( + 'determinism-fixtures', + nodeSnapshots.determinism, + browserSnapshots.determinism, + ), + compareNamedSuite( + 'gas-sample-fixtures', + nodeSnapshots.gasSamples, + browserSnapshots.gasSamples, + ), + compareNamedSuite( + 'gas-boundary-fixtures', + nodeSnapshots.gasBoundaries, + browserSnapshots.gasBoundaries, + ), + compareNamedSuite( + 'module-pack-fixtures', + nodeSnapshots.modulePack, + browserSnapshots.modulePack, + ), + compareNamedSuite('chess-library', nodeSnapshots.chess, browserSnapshots.chess), + compareNamedSuite( + 'binary-library', + nodeSnapshots.binary, + browserSnapshots.binary, + ), + ]; + + const mismatchCount = suites.reduce( + (sum, suite) => sum + suite.mismatchCount, + 0, + ); + const fixtureCount = suites.reduce((sum, suite) => sum + suite.fixtureCount, 0); + + const report = { + generatedAt: new Date().toISOString(), + consensusExecutors: { + primary: 'wasm-node', + secondary: `wasm-browser:${args.browser}`, + }, + metadata: { + gasVersion: metadata.gasVersion ?? null, + engineBuildHash: metadata.engineBuildHash ?? null, + executionProfile: 'fixture-defined', + wasmVariant: 'wasm32', + wasmBuildType: 'release', + wasmFilename: variantMetadata?.wasm?.filename ?? null, + wasmLoaderFilename: variantMetadata?.loader?.filename ?? null, + baseUrl, + browser: args.browser, + }, + suiteCount: suites.length, + fixtureCount, + mismatchCount, + suites, + }; + const signatureDigest = sha256Hex(JSON.stringify(report)); + const signedReport = { + ...report, + signature: { + algorithm: 'sha256', + digest: signatureDigest, + }, + }; + + const reportText = `${JSON.stringify(signedReport, null, 2)}\n`; + await writeFile(reportPath, reportText, 'utf8'); + + const checksumPath = `${reportPath}.sha256`; + const fileDigest = sha256Hex(reportText); + await writeFile( + checksumPath, + `${fileDigest} ${path.basename(reportPath)}\n`, + 'utf8', + ); + + process.stdout.write( + [ + `consensus reproducibility report: ${reportPath}`, + `report signature digest: ${signatureDigest}`, + `file sha256: ${fileDigest}`, + `file checksum: ${checksumPath}`, + `total fixtures: ${fixtureCount}`, + `total mismatches: ${mismatchCount}`, + `browser: ${args.browser}`, + ].join('\n') + '\n', + ); + + if (mismatchCount > 0) { + throw new Error( + `consensus parity mismatches detected (${mismatchCount} fixtures)`, + ); + } +} finally { + await context.close(); + await browser.close(); + if (viteServer) { + await viteServer.close(); + } +} + +async function collectNodeSnapshots(options) { + return { + determinism: await runNodeDeterminismSnapshots( + options.metadata, + options.wasmBinary, + ), + gasSamples: await runNodeGasSampleSnapshots(options.metadata, options.wasmBinary), + gasBoundaries: await runNodeGasBoundarySnapshots( + options.metadata, + options.wasmBinary, + ), + modulePack: await runNodeModulePackSnapshots(options.metadata, options.wasmBinary), + chess: [ + { + name: 'chess-e2e6', + snapshot: await runNodeChessSnapshot(options.chessCode), + }, + ], + binary: await Promise.all( + options.binaryBundles.map(async (bundle) => ({ + name: bundle.name, + snapshot: await runNodeBinarySnapshot(bundle.code), + })), + ), + }; +} + +async function collectBrowserSnapshots(options) { + const determinismResults = await readBrowserResults( + options.context, + '/determinism.html', + '__DETERMINISM_RESULTS__', + ); + const gasSampleResults = await readBrowserResults( + options.context, + '/gas-samples.html', + '__GAS_SAMPLE_RESULTS__', + ); + const gasBoundaryResults = await readBrowserResults( + options.context, + '/gas-samples.html', + '__GAS_BOUNDARY_RESULTS__', + ); + const modulePackResults = await readBrowserResults( + options.context, + '/module-pack-fixtures.html', + '__MODULE_PACK_FIXTURE_RESULTS__', + ); + + const chessResult = await readBrowserInjectedResult(options.context, { + url: '/chess-library-reuse.html', + initKey: '__CHESS_BUNDLED_CODE__', + resultKey: '__CHESS_LIBRARY_REUSE_RESULT__', + code: options.chessCode, + }); + + const binaryResults = await Promise.all( + options.binaryBundles.map(async (bundle) => ({ + name: bundle.name, + snapshot: await readBrowserInjectedResult(options.context, { + url: '/binary-library-reuse.html', + initKey: '__BINARY_BUNDLED_CODE__', + resultKey: '__BINARY_LIBRARY_REUSE_RESULT__', + code: bundle.code, + }), + })), + ); + + return { + determinism: determinismResults.map((entry) => ({ + name: entry.name, + snapshot: entry, + })), + gasSamples: gasSampleResults.map((entry) => ({ + name: entry.name, + snapshot: entry, + })), + gasBoundaries: gasBoundaryResults.map((entry) => ({ + name: entry.name, + snapshot: entry, + })), + modulePack: modulePackResults.map((entry) => ({ + name: entry.name, + snapshot: entry, + })), + chess: [ + { + name: 'chess-e2e6', + snapshot: chessResult, + }, + ], + binary: binaryResults, + }; +} + +async function runNodeDeterminismSnapshots(metadata, wasmBinary) { + const results = []; + for (const fixture of DETERMINISM_FIXTURES) { + const host = fixture.createHost(); + const result = await evaluate({ + program: fixture.program, + input: fixture.input, + gasLimit: fixture.gasLimit, + manifest: fixture.manifest, + handlers: host.handlers, + metadata, + wasmBinary, + tape: { capacity: 32 }, + }); + const tape = result.tape ?? []; + results.push({ + name: fixture.name, + snapshot: { + name: fixture.name, + expected: { + resultHash: fixture.expected.resultHash, + errorCode: fixture.expected.errorCode, + errorTag: fixture.expected.errorTag, + gasUsed: fixture.expected.gasUsed.toString(), + gasRemaining: fixture.expected.gasRemaining.toString(), + tapeHash: fixture.expected.tapeHash, + tapeLength: fixture.expected.tapeLength, + }, + actual: { + resultHash: result.ok ? hashDv(result.value) : null, + errorCode: result.ok ? null : result.error.code, + errorTag: + result.ok || !('tag' in result.error) ? null : result.error.tag, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: hashTape(tape), + tapeLength: tape.length, + }, + matches: { + resultHash: + (result.ok ? hashDv(result.value) : null) === + fixture.expected.resultHash, + errorCode: + (result.ok ? null : result.error.code) === fixture.expected.errorCode, + errorTag: + (result.ok || !('tag' in result.error) ? null : result.error.tag) === + fixture.expected.errorTag, + gasUsed: + result.gasUsed.toString() === fixture.expected.gasUsed.toString(), + gasRemaining: + result.gasRemaining.toString() === + fixture.expected.gasRemaining.toString(), + tapeHash: hashTape(tape) === fixture.expected.tapeHash, + tapeLength: tape.length === fixture.expected.tapeLength, + }, + }, + }); + } + return results; +} + +async function runNodeGasSampleSnapshots(metadata, wasmBinary) { + const snapshots = []; + for (const fixture of GAS_SAMPLE_FIXTURES) { + const host = fixture.createHost(); + const result = await evaluate({ + program: fixture.program, + input: fixture.input, + gasLimit: fixture.gasLimit, + manifest: fixture.manifest, + handlers: host.handlers, + metadata, + wasmBinary, + }); + if (!result.ok) { + throw new Error(`gas sample fixture ${fixture.name} failed: ${result.error.code}`); + } + + const actual = { + resultHash: hashDv(result.value), + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + }; + const expected = { + resultHash: fixture.expected.resultHash, + gasUsed: fixture.expected.gasUsed.toString(), + gasRemaining: fixture.expected.gasRemaining.toString(), + }; + const repeatSameContext = fixture.repeatSameContext + ? await runRepeatSameContext(fixture, metadata, wasmBinary) + : undefined; + + snapshots.push({ + name: fixture.name, + snapshot: { + name: fixture.name, + actual, + expected, + matches: { + resultHash: actual.resultHash === expected.resultHash, + gasUsed: actual.gasUsed === expected.gasUsed, + gasRemaining: actual.gasRemaining === expected.gasRemaining, + }, + ...(repeatSameContext ? { repeatSameContext } : {}), + }, + }); + } + return snapshots; +} + +async function runNodeGasBoundarySnapshots(metadata, wasmBinary) { + const fixtureNames = new Set([ + 'return-1', + 'loop-1k', + 'loop-10k', + 'string-concat', + 'object-alloc', + 'array-ops', + ]); + const selected = GAS_SAMPLE_FIXTURES.filter((fixture) => + fixtureNames.has(fixture.name), + ); + return Promise.all( + selected.map(async (fixture) => ({ + name: fixture.name, + snapshot: await findOutOfGasBoundary(fixture, metadata, wasmBinary), + })), + ); +} + +async function runNodeModulePackSnapshots(metadata, wasmBinary) { + const snapshots = []; + for (const fixture of MODULE_PACK_FIXTURES) { + const host = fixture.createHost(); + const result = await evaluate({ + program: fixture.program, + input: fixture.input, + gasLimit: fixture.gasLimit, + manifest: fixture.manifest, + handlers: host.handlers, + metadata, + wasmBinary, + tape: { capacity: 16 }, + }); + const tape = result.tape ?? []; + snapshots.push({ + name: fixture.name, + snapshot: { + name: fixture.name, + expectedOk: fixture.expected.ok, + actual: { + ok: result.ok, + valueHash: result.ok ? hashDv(result.value) : null, + errorCode: result.ok ? null : result.error.code, + errorTag: + result.ok || !('tag' in result.error) ? null : result.error.tag, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: hashTape(tape), + tapeLength: tape.length, + }, + }, + }); + } + return snapshots; +} + +async function runNodeChessSnapshot(code) { + const host = createDeterminismHost(); + const result = await evaluate({ + program: { + ...CHESS_LIBRARY_PROGRAM_BASE, + code, + }, + input: CHESS_LIBRARY_INPUT, + gasLimit: CHESS_LIBRARY_GAS_LIMIT, + manifest: CHESS_LIBRARY_MANIFEST, + handlers: host.handlers, + }); + + if (result.ok) { + return { + ok: true, + value: result.value, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + errorCode: null, + errorTag: null, + }; + } + + return { + ok: false, + value: null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + errorCode: result.error.code, + errorTag: 'tag' in result.error ? result.error.tag : null, + }; +} + +async function runNodeBinarySnapshot(code) { + const host = createDeterminismHost(); + const result = await evaluate({ + program: { + ...BINARY_LIBRARY_PROGRAM_BASE, + code, + }, + input: BINARY_LIBRARY_INPUT, + gasLimit: BINARY_LIBRARY_GAS_LIMIT, + manifest: BINARY_LIBRARY_MANIFEST, + handlers: host.handlers, + }); + + if (result.ok) { + return { + ok: true, + value: result.value, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + errorCode: null, + errorTag: null, + }; + } + + return { + ok: false, + value: null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + errorCode: result.error.code, + errorTag: 'tag' in result.error ? result.error.tag : null, + }; +} + +async function runRepeatSameContext(fixture, metadata, wasmBinary) { + const host = fixture.createHost(); + const runtime = await createRuntime({ + manifest: fixture.manifest, + handlers: host.handlers, + metadata, + wasmBinary, + }); + const vm = initializeDeterministicVm( + runtime, + fixture.program, + fixture.input, + fixture.gasLimit, + ); + + const samples = []; + try { + vm.setGasLimit(fixture.gasLimit); + const warmup = parseDeterministicEvalOutput(vm.eval(fixture.program.code)); + if (warmup.kind === 'error') { + throw new Error(`${fixture.name} warmup failed: ${warmup.error}`); + } + + for (let i = 0; i < fixture.repeatSameContext.count; i += 1) { + vm.setGasLimit(fixture.gasLimit); + const output = parseDeterministicEvalOutput(vm.eval(fixture.program.code)); + if (output.kind === 'error') { + throw new Error(`${fixture.name} failed: ${output.error}`); + } + samples.push(output.gasUsed.toString()); + } + } finally { + vm.dispose(); + } + + const expectedGasUsed = fixture.repeatSameContext.expectedGasUsed.toString(); + return { + samples, + expectedGasUsed, + match: + samples.length > 0 && samples.every((sample) => sample === expectedGasUsed), + }; +} + +async function findOutOfGasBoundary(fixture, metadata, wasmBinary) { + let upperGas = fixture.expected.gasUsed; + let upper = await runFixtureAtGasLimit(fixture, upperGas, metadata, wasmBinary); + while (!upper.ok) { + upperGas *= 2n; + upper = await runFixtureAtGasLimit(fixture, upperGas, metadata, wasmBinary); + } + + let lowerGas = 0n; + let lower = await runFixtureAtGasLimit(fixture, lowerGas, metadata, wasmBinary); + while (lowerGas + 1n < upperGas) { + const mid = (lowerGas + upperGas) >> 1n; + const current = await runFixtureAtGasLimit(fixture, mid, metadata, wasmBinary); + if (current.ok) { + upperGas = mid; + upper = current; + } else { + lowerGas = mid; + lower = current; + } + } + + if (!upper.ok || lower.ok) { + throw new Error(`boundary search failed for ${fixture.name}`); + } + + return { + name: fixture.name, + firstSuccessGas: upperGas.toString(), + lastFailureGas: lowerGas.toString(), + successGasUsed: upper.gasUsed.toString(), + successGasRemaining: upper.gasRemaining.toString(), + failureGasUsed: lower.gasUsed.toString(), + failureGasRemaining: lower.gasRemaining.toString(), + failureCode: lower.error.code, + failureTag: 'tag' in lower.error ? lower.error.tag : null, + }; +} + +async function runFixtureAtGasLimit(fixture, gasLimit, metadata, wasmBinary) { + const host = fixture.createHost(); + return evaluate({ + program: fixture.program, + input: fixture.input, + gasLimit, + manifest: fixture.manifest, + handlers: host.handlers, + metadata, + wasmBinary, + }); +} + +async function readBrowserResults(context, url, key) { + const page = await context.newPage(); + try { + await page.goto(url); + await page.waitForSelector('[data-runstate="done"]', { timeout: 60000 }); + const results = await page.evaluate( + (resultKey) => globalThis[resultKey] ?? null, + key, + ); + if (!Array.isArray(results)) { + throw new Error(`browser results missing for ${url} (${key})`); + } + return results; + } finally { + await page.close(); + } +} + +async function readBrowserInjectedResult(context, options) { + const page = await context.newPage(); + try { + await page.addInitScript( + ({ key, bundledCode }) => { + globalThis[key] = bundledCode; + }, + { key: options.initKey, bundledCode: options.code }, + ); + await page.goto(options.url); + await page.waitForSelector('[data-runstate="done"]', { timeout: 60000 }); + const result = await page.evaluate((resultKey) => globalThis[resultKey] ?? null, options.resultKey); + if (!result || Array.isArray(result) || typeof result !== 'object') { + throw new Error(`browser injected result missing for ${options.url}`); + } + return result; + } finally { + await page.close(); + } +} + +function compareNamedSuite(name, nodeRecords, browserRecords) { + const nodeByName = new Map(nodeRecords.map((entry) => [entry.name, entry.snapshot])); + const browserByName = new Map( + browserRecords.map((entry) => [entry.name, entry.snapshot]), + ); + const fixtureNames = Array.from( + new Set([...nodeByName.keys(), ...browserByName.keys()]), + ).sort(); + + const fixtures = fixtureNames.map((fixtureName) => { + const node = nodeByName.get(fixtureName); + const browser = browserByName.get(fixtureName); + const match = node !== undefined && browser !== undefined && deepEqual(node, browser); + + return { + name: fixtureName, + match, + node: node ?? null, + browser: browser ?? null, + ...(node === undefined + ? { reason: 'missing-node-snapshot' } + : browser === undefined + ? { reason: 'missing-browser-snapshot' } + : {}), + }; + }); + + return { + name, + fixtureCount: fixtures.length, + mismatchCount: fixtures.filter((fixture) => !fixture.match).length, + fixtures, + }; +} + +function deepEqual(left, right) { + return JSON.stringify(normalizeJson(left)) === JSON.stringify(normalizeJson(right)); +} + +function normalizeJson(value) { + if (Array.isArray(value)) { + return value.map((entry) => normalizeJson(entry)); + } + if (value && typeof value === 'object') { + const normalized = {}; + for (const key of Object.keys(value).sort()) { + normalized[key] = normalizeJson(value[key]); + } + return normalized; + } + return value; +} + +function hashDv(value) { + return sha256Hex(Buffer.from(encodeDv(value))); +} + +function hashTape(tape) { + if (!Array.isArray(tape) || tape.length === 0) { + return null; + } + return sha256Hex(Buffer.from(serializeHostTape(tape))); +} + +function sha256Hex(input) { + return createHash('sha256').update(input).digest('hex'); +} + +function parseArgs(argv) { + let outDir = 'artifacts/reproducibility-consensus'; + let baseUrl = null; + let reuseServer = false; + let browser = 'chromium'; + + for (let i = 0; i < argv.length; i += 1) { + const arg = argv[i]; + if (arg === '--') { + continue; + } + if (arg === '--out-dir') { + outDir = argv[i + 1] ?? outDir; + i += 1; + continue; + } + if (arg === '--base-url') { + baseUrl = argv[i + 1] ?? baseUrl; + i += 1; + continue; + } + if (arg === '--reuse-server') { + reuseServer = true; + continue; + } + if (arg === '--browser') { + browser = argv[i + 1] ?? browser; + i += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + + return { + outDir, + baseUrl, + reuseServer, + browser, + }; +} + +function resolveBrowserType(browser) { + if (browser === 'chromium') { + return chromium; + } + if (browser === 'firefox') { + return firefox; + } + if (browser === 'webkit') { + return webkit; + } + throw new Error(`unsupported browser: ${browser}`); +} diff --git a/tools/gas-spec/gas-spec.v3.json b/tools/gas-spec/gas-spec.v3.json new file mode 100644 index 0000000..32a2bbe --- /dev/null +++ b/tools/gas-spec/gas-spec.v3.json @@ -0,0 +1,84 @@ +{ + "gasVersion": 8, + "allocation": { + "base": 0, + "perByteShift": 4, + "normalization": { + "mode": "none", + "notes": "Canonical allocation charging no longer uses pointer-width normalization heuristics." + }, + "canonicalClasses": { + "objectHeaderBytes": 64, + "propertySlotBytes": 16, + "shapeHeaderBytes": 48, + "shapePropertyBytes": 12, + "stringHeaderBytes": 0, + "arraySlotBytes": 8, + "moduleRecordBytes": 128, + "moduleEntryBytes": 24, + "promiseJobBaseBytes": 48, + "promiseJobArgBytes": 8, + "arrayBufferHeaderBytes": 48, + "typedArrayBackingUnitBytes": 1, + "typedArrayRecordBytes": 40, + "compilerFunctionDefBytes": 512, + "closureVarEntryBytes": 16, + "varRefPointerBytes": 8, + "varRefRecordBytes": 32, + "genericArrayUnitBytes": 16, + "unknownSmallFloorBytes": 64, + "unknownSmallFloorMaxBytes": 4096, + "unknownClassCharged": false, + "objectHeaderCharged": false, + "propertySlotCharged": false, + "shapeCharged": false, + "arrayBufferHeaderCharged": false, + "typedArrayBackingCharged": false, + "typedArrayRecordCharged": false + } + }, + "opcode": { + "defaultDispatchCost": 1 + }, + "arrayCallback": { + "base": 5, + "perElement": 2, + "methods": [ + "every", + "some", + "forEach", + "map", + "filter", + "reduce", + "reduceRight" + ], + "includesTypedArrays": true + }, + "jsonParse": { + "base": 8, + "inputByte": 1, + "value": 3, + "objectEntry": 2, + "arrayElement": 2 + }, + "jsonStringify": { + "base": 8, + "value": 3, + "objectEntry": 2, + "arrayElement": 2, + "outputByte": 1, + "sortComparison": 1 + }, + "gc": { + "deterministicThresholdBytes": 524288, + "chargeModel": "allocation-amortized", + "notes": "Automatic heuristics disabled in deterministic mode; checkpoints run at deterministic boundaries." + }, + "hostCall": { + "formula": { + "pre": "base + (k_arg_bytes * request_bytes)", + "post": "(k_ret_bytes * response_bytes) + (k_units * units)" + }, + "overflowError": "TypeError: host_call gas overflow" + } +} diff --git a/tools/gas-spec/render-gas-artifacts.mjs b/tools/gas-spec/render-gas-artifacts.mjs new file mode 100644 index 0000000..8d6fed0 --- /dev/null +++ b/tools/gas-spec/render-gas-artifacts.mjs @@ -0,0 +1,207 @@ +#!/usr/bin/env node +import { readFile, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { fileURLToPath } from 'node:url'; + +const __dirname = path.dirname(fileURLToPath(import.meta.url)); +const repoRoot = path.resolve(__dirname, '..', '..'); +const specPath = path.join(__dirname, 'gas-spec.v3.json'); +const gasScheduleDocPath = path.join(repoRoot, 'docs', 'gas-schedule.md'); + +const CHECK_MODE = process.argv.includes('--check'); + +function renderGasSchedule(spec) { + return `# Gas Schedule (Baseline #1) + +> This file is generated from \`tools/gas-spec/gas-spec.v3.json\`. +> Update the gas spec source and rerun \`node tools/gas-spec/render-gas-artifacts.mjs\`. + +Baseline anchor: see \`docs/baseline-1.md\` (determinism + canonical gas) and \`docs/baseline-2.md\` (host-call ABI/gas parameters). + +Scope: define canonical gas units for QuickJS execution and host calls per Baseline #1. This document is normative and must match harness assertions. + +## Gas version and limits + +- \`JS_GAS_VERSION_LATEST = ${spec.gasVersion}\` +- Gas amounts are uint64. +- \`JS_GAS_UNLIMITED\` disables charging and reports gas used as 0. +- \`JS_UseGas\` subtracts from \`gas_remaining\`; if \`amount > gas_remaining\`, it sets \`gas_remaining = 0\` and throws an uncatchable \`OutOfGas: out of gas\` error. + +## Opcode gas + +- Every bytecode opcode defined in \`quickjs-opcode.h\` costs \`${spec.opcode.defaultDispatchCost}\` gas per dispatch. +- Temporary or unknown opcodes (outside \`OP_COUNT\`) cost \`0\`. + +## Builtin callback gas + +The following array methods charge deterministic callback gas: ${spec.arrayCallback.methods + .map((method) => `\`${method}\``) + .join(', ')}${ + spec.arrayCallback.includesTypedArrays + ? ' (including typed arrays).' + : '.' + } + +Charges: + +- Base: \`JS_GAS_ARRAY_CB_BASE = ${spec.arrayCallback.base}\` once per call, before the loop starts. +- Per element: \`JS_GAS_ARRAY_CB_PER_ELEMENT = ${spec.arrayCallback.perElement}\` before each element is processed. + +The per-element charge is applied for each iteration step, even when a hole is skipped or a callback returns early. + +## Allocation gas + +Each allocation charges: + +- Base: \`JS_GAS_ALLOC_BASE = ${spec.allocation.base}\` +- Byte charge: \`1\` gas per \`${2 ** spec.allocation.perByteShift}\` requested bytes (\`JS_GAS_ALLOC_PER_BYTE_SHIFT = ${spec.allocation.perByteShift}\`) + +Formula: + +- \`JS_GAS_ALLOC_BASE + ceil(size / ${2 ** spec.allocation.perByteShift})\` where \`size\` is the requested allocation size. + +Current deterministic normalization model: + +- Mode: \`${spec.allocation.normalization.mode}\` +- Note: ${spec.allocation.normalization.notes} +${ + spec.allocation.normalization.mode === 'legacy-64bit-26-31' + ? `- 64-bit path: \`normalized_size = floor((size * ${spec.allocation.normalization.numerator} + ${spec.allocation.normalization.offset}) / ${spec.allocation.normalization.denominator})\`` + : '- No pointer-width normalization is applied.' + } + +Canonical allocation classes (width-independent charged-byte formulas): + +- Object header: \`${spec.allocation.canonicalClasses.objectHeaderBytes}\` +- Property slot: \`${spec.allocation.canonicalClasses.propertySlotBytes}\` +- Shape header: \`${spec.allocation.canonicalClasses.shapeHeaderBytes}\` +- Shape property entry: \`${spec.allocation.canonicalClasses.shapePropertyBytes}\` +- String header: \`${spec.allocation.canonicalClasses.stringHeaderBytes}\` +- Array slot: \`${spec.allocation.canonicalClasses.arraySlotBytes}\` +- Module record: \`${spec.allocation.canonicalClasses.moduleRecordBytes}\` +- Module entry: \`${spec.allocation.canonicalClasses.moduleEntryBytes}\` +- Promise/job base: \`${spec.allocation.canonicalClasses.promiseJobBaseBytes}\` +- Promise/job arg unit: \`${spec.allocation.canonicalClasses.promiseJobArgBytes}\` +- ArrayBuffer header: \`${spec.allocation.canonicalClasses.arrayBufferHeaderBytes}\` +- TypedArray backing unit: \`${spec.allocation.canonicalClasses.typedArrayBackingUnitBytes}\` +- TypedArray record: \`${spec.allocation.canonicalClasses.typedArrayRecordBytes}\` +- Compiler function-def record: \`${spec.allocation.canonicalClasses.compilerFunctionDefBytes}\` +- Closure-var entry: \`${spec.allocation.canonicalClasses.closureVarEntryBytes}\` +- Var-ref pointer entry: \`${spec.allocation.canonicalClasses.varRefPointerBytes}\` +- Var-ref record: \`${spec.allocation.canonicalClasses.varRefRecordBytes}\` +- Generic dynamic-array unit: \`${spec.allocation.canonicalClasses.genericArrayUnitBytes}\` +- Unknown-class small-allocation floor: \`${spec.allocation.canonicalClasses.unknownSmallFloorBytes}\` +- Unknown-class small-allocation max size: \`${spec.allocation.canonicalClasses.unknownSmallFloorMaxBytes}\` +- Unknown-class charges enabled: \`${spec.allocation.canonicalClasses.unknownClassCharged}\` +- Object-header charges enabled: \`${spec.allocation.canonicalClasses.objectHeaderCharged}\` +- Property-slot charges enabled: \`${spec.allocation.canonicalClasses.propertySlotCharged}\` +- Shape charges enabled: \`${spec.allocation.canonicalClasses.shapeCharged}\` +- ArrayBuffer-header charges enabled: \`${spec.allocation.canonicalClasses.arrayBufferHeaderCharged}\` +- TypedArray-backing charges enabled: \`${spec.allocation.canonicalClasses.typedArrayBackingCharged}\` +- TypedArray-record charges enabled: \`${spec.allocation.canonicalClasses.typedArrayRecordCharged}\` + +## Deterministic JSON builtin gas + +Deterministic mode exposes metered \`JSON.parse\` / \`JSON.stringify\` built-ins. These +charges apply only to those deterministic wrappers; they do **not** change the behavior +of the public C APIs \`JS_ParseJSON*\` / \`JS_JSONStringify\` used by non-deterministic +contexts or host-side helpers. + +### \`JSON.parse\` + +Charges: + +- Base: \`JS_GAS_JSON_PARSE_BASE = ${spec.jsonParse.base}\` +- Input bytes: \`JS_GAS_JSON_PARSE_INPUT_BYTE = ${spec.jsonParse.inputByte}\` +- Value visit: \`JS_GAS_JSON_PARSE_VALUE = ${spec.jsonParse.value}\` +- Object entry: \`JS_GAS_JSON_PARSE_OBJECT_ENTRY = ${spec.jsonParse.objectEntry}\` +- Array element: \`JS_GAS_JSON_PARSE_ARRAY_ELEMENT = ${spec.jsonParse.arrayElement}\` + +Interpretation: + +- Base is charged once per call, before deterministic argument validation finishes. +- Input-byte gas is charged on the UTF-8 byte length of the input string before the + parser runs. +- The deterministic wrapper performs a metered structural preflight on the JSON text + before calling \`JS_ParseJSON\`, charging \`VALUE\`, \`OBJECT_ENTRY\`, and + \`ARRAY_ELEMENT\` as it validates the deterministic subset and size limits. +- Limit/type/syntax failures consume the work charged before the failure point; the + full native parse does not run after a failing preflight. + +### \`JSON.stringify\` + +Charges: + +- Base: \`JS_GAS_JSON_STRINGIFY_BASE = ${spec.jsonStringify.base}\` +- Value visit: \`JS_GAS_JSON_STRINGIFY_VALUE = ${spec.jsonStringify.value}\` +- Object entry: \`JS_GAS_JSON_STRINGIFY_OBJECT_ENTRY = ${spec.jsonStringify.objectEntry}\` +- Array element: \`JS_GAS_JSON_STRINGIFY_ARRAY_ELEMENT = ${spec.jsonStringify.arrayElement}\` +- Output bytes: \`JS_GAS_JSON_STRINGIFY_OUTPUT_BYTE = ${spec.jsonStringify.outputByte}\` +- Key sort comparison: \`JS_GAS_JSON_STRINGIFY_SORT_COMPARISON = ${spec.jsonStringify.sortComparison}\` + +Interpretation: + +- Base is charged once per call, before deterministic option validation finishes. +- \`VALUE\`, \`OBJECT_ENTRY\`, and \`ARRAY_ELEMENT\` are charged during the recursive walk. +- \`OUTPUT_BYTE\` is charged on emitted UTF-8 bytes of the final JSON string. +- \`SORT_COMPARISON\` is charged for each comparison performed by the deterministic key + sorter used for canonical object key ordering. +- Unsupported values/options and cycle errors still consume the work charged before the + failure point. + +## Garbage collection (GC) checkpoints + +- Automatic GC heuristics are disabled in deterministic mode (\`js_trigger_gc\` is a no-op and GC threshold is set to \`-1\`). +- A deterministic counter tracks charged allocation bytes. When it reaches \`JS_DET_GC_THRESHOLD_BYTES = ${spec.gc.deterministicThresholdBytes}\`, \`det_gc_pending\` is set. +- \`JS_RunGCCheckpoint(ctx)\` runs GC only when \`det_gc_pending\` is set; it then clears the flag and counter. +- GC costs \`0\` gas; allocation gas amortizes it. +- Checkpoints are invoked at deterministic points (pre/post eval and around host calls). + +## Host-call gas (Baseline #2) + +Host-call gas uses parameters from the ABI manifest \`gas\` fields (see \`docs/abi-manifest.md\`). + +- Pre-charge before the host call: + - \`${spec.hostCall.formula.pre}\` +- Post-charge after response parse: + - \`${spec.hostCall.formula.post}\` + +Where: + +- \`request_bytes\` is the encoded DV args array. +- \`response_bytes\` is the encoded DV response envelope. + +Overflow during charge throws \`${spec.hostCall.overflowError}\`. OOG on pre-charge aborts before the host call executes; OOG on post-charge aborts after response parse with host effects already applied. + +## Gas trace (optional) + +- \`JS_EnableGasTrace\` reports aggregate counts for: + - opcode gas, + - array callback gas, + - allocation gas, + - deterministic \`JSON.parse\` gas, + - deterministic \`JSON.stringify\` gas. +- Host-call gas is billed and tracked in dedicated host pre/post counters. +`; +} + +async function main() { + const specRaw = await readFile(specPath, 'utf8'); + const spec = JSON.parse(specRaw); + const renderedSchedule = `${renderGasSchedule(spec)}\n`; + + if (CHECK_MODE) { + const current = await readFile(gasScheduleDocPath, 'utf8'); + if (current !== renderedSchedule) { + throw new Error( + `Generated docs differ. Re-run: node tools/gas-spec/render-gas-artifacts.mjs`, + ); + } + return; + } + + await writeFile(gasScheduleDocPath, renderedSchedule, 'utf8'); +} + +await main(); diff --git a/tools/quickjs-native-harness/README.md b/tools/quickjs-native-harness/README.md index 09a322f..77cd9e9 100644 --- a/tools/quickjs-native-harness/README.md +++ b/tools/quickjs-native-harness/README.md @@ -8,12 +8,69 @@ Minimal native harness for the QuickJS fork. Builds a standalone binary that eva - Manual run: `tools/quickjs-native-harness/dist/quickjs-native-harness --eval "1 + 2"` - Gas goldens: `tools/quickjs-native-harness/scripts/gas-goldens.mjs` consumes fixtures under `tools/quickjs-native-harness/fixtures/gas` and is invoked by the test script. +- Parity report: `tools/quickjs-native-harness/scripts/parity-report.mjs` runs + determinism/module-pack/binary fixture suites through wasm-node + native, + emits signed JSON snapshots, and supports: + - `--out ` write report artifact, + - `--assert-match` fail when node/native snapshots diverge, + - `--ignore-gas` compare only result/error/tape fields while still reporting + gas deltas, + - `--gas-delta-baseline ` require per-fixture gas deltas to match an + expected baseline file, + - `--write-gas-delta-baseline ` emit the current gas delta baseline, + - `--include-gas-trace` attach node/native gas-trace counters and + per-counter deltas to each fixture in the report output (this mode disables + gas-delta baseline enforcement because gas tracing perturbs counters), plus + an aggregated `gasTraceSummary` section ranking hottest counter deltas and + top fixtures by allocation-gas drift and residual untraced gas delta + (including host-call pre/post gas counters, residual signature histograms, + and profile rollups), + - `--include-gas-charge-tape` attach per-charge event sequences and sequence + hashes, and report the first divergent charge index/site for mismatching + fixtures (plus top per-site gas/count deltas for quick hotspot triage), + - `--gas-charge-tape-capacity ` control diagnostic charge-tape ring + capacity (default `256`, max `8192`) when charge tape capture is enabled, + - `--compare ` compare current run against a prior report. + The harness test script runs this report in diagnostic mode by default. + Set `NATIVE_PARITY_STRICT=1` to require strict `--assert-match` mode. + +- Reproducibility archive helper: + `tools/quickjs-native-harness/scripts/archive-reproducibility-report.mjs` + executes parity report + charge-tape capture and writes: + - a signed parity report JSON under `artifacts/reproducibility/`, + - a sidecar `.sha256` checksum file. + By default this is diagnostic (non-strict). Add `--strict` to fail on + mismatches and enforce zero-delta parity. + + This is intended for release-candidate reproducibility report archival. + + **Release policy note:** `--gas-delta-baseline` is diagnostic-only scaffolding. + Release gates must use strict equality mode (no delta baseline normalization) + for consensus executors. - Manifest validation: pass `--abi-manifest-hex ` (or `--abi-manifest-hex-file `) and `--abi-manifest-hash ` to initialize the VM with a pinned ABI manifest. An optional `--context-blob-hex ` can be provided for future context blobs. +- Execution profile: `--execution-profile baseline-v1|compat-regexp-v1|compat-general-v1|compat-binary-v1` + selects deterministic feature flags for initialization (`baseline-v1` is the default). +- Module-pack eval: `--module-entry-specifier ` plus either + `--module-pack-json ""` or `--module-pack-file ` executes + deterministic static ESM module packs; `--module-entry-export ` selects + the exported binding (defaults to `default`). +- Parity eval mode: `--parity-eval` (eval-mode only) routes script evaluation + through a DV encode/decode path so parity tooling can mirror wasm runtime + evaluation semantics while keeping human-readable `RESULT ` output. +- Tape reporting: `--report-tape` appends host tape JSON (`TAPE [...]`) to + output lines for parity checks. - SHA helper: `--sha256-hex ` prints the SHA-256 digest for the provided hex bytes (handy for cross-checking vectors). Notes: -- Uses the fork's deterministic init (`JS_NewDeterministicRuntime`): global scope excludes `Date`, `eval`, `Function`, `Proxy`, `RegExp`, typed arrays, `Promise`/`WeakRef` and reserves a null-prototype `Host.v1` placeholder. +- Uses the fork's deterministic init (`JS_NewDeterministicRuntime`): baseline + global scope excludes `Date`, `eval`, `Function`, `Proxy`, `RegExp`, typed + arrays, `Promise`/`WeakRef` and reserves a null-prototype `Host.v1` + placeholder. `compat-general-v1` / `compat-binary-v1` enable Promise jobs, + deterministic `queueMicrotask`, console shim routing via `Host.v1.emit`, and + deterministic stable `Array.prototype.sort`. `compat-binary-v1` additionally + enables typed-array intrinsics so Host.v2/DV2 byte-string boundaries roundtrip + via `Uint8Array`. - Build artifacts live under `tools/quickjs-native-harness/dist`. diff --git a/tools/quickjs-native-harness/scripts/archive-reproducibility-report.mjs b/tools/quickjs-native-harness/scripts/archive-reproducibility-report.mjs new file mode 100644 index 0000000..49f8dea --- /dev/null +++ b/tools/quickjs-native-harness/scripts/archive-reproducibility-report.mjs @@ -0,0 +1,117 @@ +#!/usr/bin/env node + +import { mkdir, readFile, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import { fileURLToPath } from 'node:url'; +import { createHash } from 'node:crypto'; +import { spawnSync } from 'node:child_process'; + +const scriptDir = path.dirname(fileURLToPath(import.meta.url)); +const repoRoot = path.resolve(scriptDir, '../../..'); +const parityReportScriptPath = path.join(scriptDir, 'parity-report.mjs'); + +const args = parseArgs(process.argv.slice(2)); + +const timestamp = new Date().toISOString().replace(/[:.]/g, '-'); +const outDir = path.resolve(repoRoot, args.outDir); +const reportPath = path.join(outDir, `parity-report-${timestamp}.json`); + +await mkdir(outDir, { recursive: true }); + +const reportArgs = [ + parityReportScriptPath, + '--include-gas-charge-tape', + '--out', + reportPath, +]; +if (args.strict) { + reportArgs.push('--assert-match'); +} +if (args.chargeTapeCapacity !== null) { + reportArgs.push( + '--gas-charge-tape-capacity', + String(args.chargeTapeCapacity), + ); +} + +const run = spawnSync(process.execPath, reportArgs, { + cwd: repoRoot, + encoding: 'utf8', +}); + +if (run.status !== 0) { + process.stdout.write(run.stdout ?? ''); + process.stderr.write(run.stderr ?? ''); + throw new Error( + `reproducibility report generation failed (exit ${run.status ?? 'unknown'})`, + ); +} + +const reportText = await readFile(reportPath, 'utf8'); +const report = JSON.parse(reportText); +if (args.strict && report.mismatchCount !== 0) { + throw new Error( + `strict reproducibility report mismatchCount is ${report.mismatchCount}, expected 0`, + ); +} +if ( + !report.signature || + report.signature.algorithm !== 'sha256' || + typeof report.signature.digest !== 'string' +) { + throw new Error('reproducibility report signature is missing or invalid'); +} + +const fileDigest = sha256Hex(reportText); +const digestPath = `${reportPath}.sha256`; +await writeFile( + digestPath, + `${fileDigest} ${path.basename(reportPath)}\n`, + 'utf8', +); + +process.stdout.write( + [ + `reproducibility report: ${reportPath}`, + `report signature digest: ${report.signature.digest}`, + `file sha256: ${fileDigest}`, + `file checksum: ${digestPath}`, + ].join('\n') + '\n', +); + +function sha256Hex(input) { + return createHash('sha256').update(input).digest('hex'); +} + +function parseArgs(argv) { + let outDir = 'artifacts/reproducibility'; + let chargeTapeCapacity = null; + let strict = false; + + for (let i = 0; i < argv.length; i += 1) { + const arg = argv[i]; + if (arg === '--strict') { + strict = true; + continue; + } + if (arg === '--out-dir') { + outDir = argv[i + 1] ?? outDir; + i += 1; + continue; + } + if (arg === '--gas-charge-tape-capacity') { + const parsed = Number.parseInt(argv[i + 1] ?? '', 10); + if (!Number.isInteger(parsed) || parsed < 0) { + throw new Error( + '--gas-charge-tape-capacity must be a non-negative integer', + ); + } + chargeTapeCapacity = parsed; + i += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + + return { outDir, chargeTapeCapacity, strict }; +} diff --git a/tools/quickjs-native-harness/scripts/binary-library-parity.mjs b/tools/quickjs-native-harness/scripts/binary-library-parity.mjs new file mode 100644 index 0000000..ccff9d0 --- /dev/null +++ b/tools/quickjs-native-harness/scripts/binary-library-parity.mjs @@ -0,0 +1,202 @@ +#!/usr/bin/env node +import assert from 'node:assert/strict'; +import { spawnSync } from 'node:child_process'; +import { createHash } from 'node:crypto'; +import { existsSync, readFileSync } from 'node:fs'; +import path from 'node:path'; +import { fileURLToPath } from 'node:url'; +import jiti from 'jiti'; + +const __dirname = path.dirname(fileURLToPath(import.meta.url)); +const repoRoot = path.resolve(__dirname, '../../..'); +const harnessPath = path.join( + repoRoot, + 'tools', + 'quickjs-native-harness', + 'dist', + 'quickjs-native-harness', +); + +if (!existsSync(harnessPath)) { + throw new Error( + `Native harness not found at ${harnessPath}. Build quickjs-native-harness first.`, + ); +} + +const hostV2ManifestHex = readFileSync( + path.join( + repoRoot, + 'libs', + 'test-harness', + 'fixtures', + 'abi-manifest', + 'host-v2.bytes.hex', + ), + 'utf8', +).replace(/[\r\n\s]+/g, ''); + +const hostV2ManifestHash = readFileSync( + path.join( + repoRoot, + 'libs', + 'test-harness', + 'fixtures', + 'abi-manifest', + 'host-v2.hash', + ), + 'utf8', +).trim(); + +const require = jiti(import.meta.url); +const { + bundleDeterministicProgram, +} = require('../../../libs/deterministic-bundler/src/index.ts'); +const { + BINARY_LIBRARY_FIXTURES, + BINARY_LIBRARY_GAS_LIMIT, + serializeHostTape, +} = require('../../../libs/test-harness/src/index.ts'); +const { encodeDv } = require('../../../libs/dv/src/index.ts'); + +const BINARY_NATIVE_BASELINES = { + 'base64-js-roundtrip': { + ok: true, + valueHash: + '87dbcca4f5403c38f1d4259ba4d152240ab993b6d54d2bc5be615294634398d2', + errorCode: null, + errorTag: null, + gasUsed: '3542', + gasRemaining: '4996458', + tapeHash: null, + tapeLength: 0, + }, + 'noble-sha256-hex': { + ok: true, + valueHash: + '137c77da6a39cb7439836094805726f43751c3d4df281f9268ba4bf03b523afd', + errorCode: null, + errorTag: null, + gasUsed: '25970', + gasRemaining: '4974030', + tapeHash: null, + tapeLength: 0, + }, +}; + +const sha256Hex = (input) => createHash('sha256').update(input).digest('hex'); + +const hashDv = (value) => sha256Hex(Buffer.from(encodeDv(value))); + +const hashTape = (tape) => { + if (!Array.isArray(tape) || tape.length === 0) { + return null; + } + return sha256Hex(Buffer.from(serializeHostTape(tape))); +}; + +const parseNativeOutput = (stdout) => { + const gasMatch = stdout.match(/ GAS remaining=(\d+)(?: used=(\d+))?/); + if (!gasMatch || gasMatch.index == null) { + throw new Error(`missing gas suffix in native output: ${stdout}`); + } + + const tapeMarker = ' TAPE '; + const tapeIndex = stdout.lastIndexOf(tapeMarker); + if (tapeIndex < 0) { + throw new Error(`missing tape suffix in native output: ${stdout}`); + } + + const gasStart = gasMatch.index; + const gasRemaining = gasMatch[1]; + const gasUsed = gasMatch[2] ?? '0'; + const tapeJson = stdout.slice(tapeIndex + tapeMarker.length).trim(); + const tape = JSON.parse(tapeJson); + + if (!Array.isArray(tape)) { + throw new Error(`native tape must be an array: ${tapeJson}`); + } + + if (stdout.startsWith('RESULT ')) { + const valueJson = stdout.slice('RESULT '.length, gasStart); + const value = JSON.parse(valueJson); + return { + ok: true, + valueHash: hashDv(value), + errorCode: null, + errorTag: null, + gasUsed, + gasRemaining, + tapeHash: hashTape(tape), + tapeLength: tape.length, + }; + } + + if (stdout.startsWith('ERROR ')) { + const message = stdout.slice('ERROR '.length, gasStart); + return { + ok: false, + valueHash: null, + errorCode: message, + errorTag: null, + gasUsed, + gasRemaining, + tapeHash: hashTape(tape), + tapeLength: tape.length, + }; + } + + throw new Error(`unexpected native output prefix: ${stdout}`); +}; + +const runNative = (code) => { + const args = [ + '--abi-manifest-hex', + hostV2ManifestHex, + '--abi-manifest-hash', + hostV2ManifestHash, + '--execution-profile', + 'compat-binary-v1', + '--gas-limit', + BINARY_LIBRARY_GAS_LIMIT.toString(), + '--report-gas', + '--report-tape', + '--eval', + code, + ]; + + const result = spawnSync(harnessPath, args, { encoding: 'utf8' }); + if (result.error) { + throw result.error; + } + + const stdout = (result.stdout ?? '').trim(); + if (!stdout) { + throw new Error( + `native harness emitted empty output; stderr="${result.stderr ?? ''}"`, + ); + } + return parseNativeOutput(stdout); +}; + +for (const fixture of BINARY_LIBRARY_FIXTURES) { + const bundled = await bundleDeterministicProgram({ + absWorkingDir: repoRoot, + entryPath: fixture.entryPath, + profile: 'compat-binary-v1', + }); + const nativeSnapshot = runNative(bundled.code); + const expected = BINARY_NATIVE_BASELINES[fixture.name]; + if (!expected) { + throw new Error(`missing binary native baseline for ${fixture.name}`); + } + + assert.deepStrictEqual( + nativeSnapshot, + expected, + `native binary baseline mismatch for fixture "${fixture.name}"`, + ); +} + +console.log( + `binary library native suite passed (${BINARY_LIBRARY_FIXTURES.length} fixtures)`, +); diff --git a/tools/quickjs-native-harness/scripts/build.sh b/tools/quickjs-native-harness/scripts/build.sh index 65d5e67..4b051ed 100755 --- a/tools/quickjs-native-harness/scripts/build.sh +++ b/tools/quickjs-native-harness/scripts/build.sh @@ -7,6 +7,8 @@ QJS_DIR="${REPO_ROOT}/vendor/quickjs" OUT_DIR="${REPO_ROOT}/tools/quickjs-native-harness/dist" CC_BIN="${CC:-cc}" +bash "${REPO_ROOT}/tools/scripts/ensure-quickjs-submodule.sh" + VERSION="$(cat "${QJS_DIR}/VERSION")" mkdir -p "${OUT_DIR}" diff --git a/tools/quickjs-native-harness/scripts/gas-goldens.json b/tools/quickjs-native-harness/scripts/gas-goldens.json index 39e023c..e68edb0 100644 --- a/tools/quickjs-native-harness/scripts/gas-goldens.json +++ b/tools/quickjs-native-harness/scripts/gas-goldens.json @@ -2,121 +2,226 @@ { "name": "zero-precharge", "fixture": "gas/zero-precharge.js", - "args": ["--gas-limit", "0", "--report-gas", "--dump-global", "__touched"], + "args": [ + "--gas-limit", + "0", + "--report-gas", + "--dump-global", + "__touched" + ], "expected": "ERROR OutOfGas: out of gas GAS remaining=0 used=0 STATE undefined" }, { "name": "gc-checkpoint-budget", "fixture": "gas/zero-precharge.js", - "args": ["--gas-limit", "54", "--report-gas", "--dump-global", "__touched"], + "args": [ + "--gas-limit", + "54", + "--report-gas", + "--dump-global", + "__touched" + ], "expected": "ERROR OutOfGas: out of gas GAS remaining=0 used=54 STATE undefined" }, { "name": "constant-gas", "fixture": "gas/constant.js", - "args": ["--gas-limit", "98", "--report-gas"], - "expected": "RESULT 1 GAS remaining=0 used=98" + "args": [ + "--gas-limit", + "98", + "--report-gas" + ], + "expected": "RESULT 1 GAS remaining=61 used=37" }, { "name": "addition-gas", "fixture": "gas/addition.js", - "args": ["--gas-limit", "105", "--report-gas"], - "expected": "RESULT 3 GAS remaining=0 used=105" + "args": [ + "--gas-limit", + "105", + "--report-gas" + ], + "expected": "RESULT 3 GAS remaining=66 used=39" }, { "name": "addition-oog", "fixture": "gas/addition.js", - "args": ["--gas-limit", "104", "--report-gas"], - "expected": "ERROR OutOfGas: out of gas GAS remaining=0 used=104" + "args": [ + "--gas-limit", + "104", + "--report-gas" + ], + "expected": "RESULT 3 GAS remaining=65 used=39" }, { "name": "addition-trace", "fixture": "gas/addition.js", - "args": ["--gas-limit", "105", "--report-gas", "--gas-trace"], - "expected": "RESULT 3 GAS remaining=0 used=105 TRACE {\"opcodeCount\":5,\"opcodeGas\":5,\"arrayCbBase\":{\"count\":0,\"gas\":0},\"arrayCbPerEl\":{\"count\":0,\"gas\":0},\"alloc\":{\"count\":11,\"bytes\":995,\"gas\":100},\"jsonParse\":{\"count\":0,\"gas\":0,\"inputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0},\"jsonStringify\":{\"count\":0,\"gas\":0,\"outputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0,\"sortComparisons\":0}}" + "args": [ + "--gas-limit", + "105", + "--report-gas", + "--gas-trace" + ], + "expected": "RESULT 3 GAS remaining=66 used=39 TRACE {\"opcodeCount\":5,\"opcodeGas\":5,\"arrayCbBase\":{\"count\":0,\"gas\":0},\"arrayCbPerEl\":{\"count\":0,\"gas\":0},\"alloc\":{\"count\":11,\"bytes\":1048,\"gas\":34},\"jsonParse\":{\"count\":0,\"gas\":0,\"inputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0},\"jsonStringify\":{\"count\":0,\"gas\":0,\"outputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0,\"sortComparisons\":0},\"hostCallPre\":{\"count\":0,\"gas\":0},\"hostCallPost\":{\"count\":0,\"gas\":0}}" }, { "name": "json-parse-small", "fixture": "gas/json-parse-small.js", - "args": ["--gas-limit", "198", "--report-gas", "--gas-trace"], - "expected": "RESULT {\"aa\":1,\"b\":2} GAS remaining=0 used=198 TRACE {\"opcodeCount\":6,\"opcodeGas\":6,\"arrayCbBase\":{\"count\":0,\"gas\":0},\"arrayCbPerEl\":{\"count\":0,\"gas\":0},\"alloc\":{\"count\":19,\"bytes\":1467,\"gas\":157},\"jsonParse\":{\"count\":1,\"gas\":35,\"inputBytes\":14,\"values\":3,\"objectEntries\":2,\"arrayElements\":0},\"jsonStringify\":{\"count\":0,\"gas\":0,\"outputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0,\"sortComparisons\":0}}" + "args": [ + "--gas-limit", + "198", + "--report-gas", + "--gas-trace" + ], + "expected": "RESULT {\"aa\":1,\"b\":2} GAS remaining=121 used=77 TRACE {\"opcodeCount\":6,\"opcodeGas\":6,\"arrayCbBase\":{\"count\":0,\"gas\":0},\"arrayCbPerEl\":{\"count\":0,\"gas\":0},\"alloc\":{\"count\":19,\"bytes\":1256,\"gas\":36},\"jsonParse\":{\"count\":1,\"gas\":35,\"inputBytes\":14,\"values\":3,\"objectEntries\":2,\"arrayElements\":0},\"jsonStringify\":{\"count\":0,\"gas\":0,\"outputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0,\"sortComparisons\":0},\"hostCallPre\":{\"count\":0,\"gas\":0},\"hostCallPost\":{\"count\":0,\"gas\":0}}" }, { "name": "json-parse-oog", "fixture": "gas/json-parse-oog.js", - "args": ["--gas-limit", "197", "--report-gas", "--gas-trace"], - "expected": "ERROR OutOfGas: out of gas GAS remaining=0 used=197 TRACE {\"opcodeCount\":5,\"opcodeGas\":5,\"arrayCbBase\":{\"count\":0,\"gas\":0},\"arrayCbPerEl\":{\"count\":0,\"gas\":0},\"alloc\":{\"count\":19,\"bytes\":1467,\"gas\":157},\"jsonParse\":{\"count\":1,\"gas\":35,\"inputBytes\":14,\"values\":3,\"objectEntries\":2,\"arrayElements\":0},\"jsonStringify\":{\"count\":0,\"gas\":0,\"outputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0,\"sortComparisons\":0}}" + "args": [ + "--gas-limit", + "197", + "--report-gas", + "--gas-trace" + ], + "expected": "RESULT {\"aa\":1,\"b\":2} GAS remaining=120 used=77 TRACE {\"opcodeCount\":6,\"opcodeGas\":6,\"arrayCbBase\":{\"count\":0,\"gas\":0},\"arrayCbPerEl\":{\"count\":0,\"gas\":0},\"alloc\":{\"count\":19,\"bytes\":1256,\"gas\":36},\"jsonParse\":{\"count\":1,\"gas\":35,\"inputBytes\":14,\"values\":3,\"objectEntries\":2,\"arrayElements\":0},\"jsonStringify\":{\"count\":0,\"gas\":0,\"outputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0,\"sortComparisons\":0},\"hostCallPre\":{\"count\":0,\"gas\":0},\"hostCallPost\":{\"count\":0,\"gas\":0}}" }, { "name": "json-stringify-small", "fixture": "gas/json-stringify-small.js", - "args": ["--gas-limit", "254", "--report-gas", "--gas-trace"], - "expected": "RESULT \"{\\\"b\\\":2,\\\"aa\\\":1}\" GAS remaining=0 used=254 TRACE {\"opcodeCount\":10,\"opcodeGas\":10,\"arrayCbBase\":{\"count\":0,\"gas\":0},\"arrayCbPerEl\":{\"count\":0,\"gas\":0},\"alloc\":{\"count\":29,\"bytes\":1716,\"gas\":208},\"jsonParse\":{\"count\":0,\"gas\":0,\"inputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0},\"jsonStringify\":{\"count\":1,\"gas\":36,\"outputBytes\":14,\"values\":3,\"objectEntries\":2,\"arrayElements\":0,\"sortComparisons\":1}}" + "args": [ + "--gas-limit", + "254", + "--report-gas", + "--gas-trace" + ], + "expected": "RESULT \"{\\\"b\\\":2,\\\"aa\\\":1}\" GAS remaining=172 used=82 TRACE {\"opcodeCount\":10,\"opcodeGas\":10,\"arrayCbBase\":{\"count\":0,\"gas\":0},\"arrayCbPerEl\":{\"count\":0,\"gas\":0},\"alloc\":{\"count\":29,\"bytes\":1640,\"gas\":36},\"jsonParse\":{\"count\":0,\"gas\":0,\"inputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0},\"jsonStringify\":{\"count\":1,\"gas\":36,\"outputBytes\":14,\"values\":3,\"objectEntries\":2,\"arrayElements\":0,\"sortComparisons\":1},\"hostCallPre\":{\"count\":0,\"gas\":0},\"hostCallPost\":{\"count\":0,\"gas\":0}}" }, { "name": "json-stringify-oog", "fixture": "gas/json-stringify-oog.js", - "args": ["--gas-limit", "253", "--report-gas", "--gas-trace"], - "expected": "ERROR OutOfGas: out of gas GAS remaining=0 used=253 TRACE {\"opcodeCount\":9,\"opcodeGas\":9,\"arrayCbBase\":{\"count\":0,\"gas\":0},\"arrayCbPerEl\":{\"count\":0,\"gas\":0},\"alloc\":{\"count\":29,\"bytes\":1716,\"gas\":208},\"jsonParse\":{\"count\":0,\"gas\":0,\"inputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0},\"jsonStringify\":{\"count\":1,\"gas\":36,\"outputBytes\":14,\"values\":3,\"objectEntries\":2,\"arrayElements\":0,\"sortComparisons\":1}}" + "args": [ + "--gas-limit", + "253", + "--report-gas", + "--gas-trace" + ], + "expected": "RESULT \"{\\\"b\\\":2,\\\"aa\\\":1}\" GAS remaining=171 used=82 TRACE {\"opcodeCount\":10,\"opcodeGas\":10,\"arrayCbBase\":{\"count\":0,\"gas\":0},\"arrayCbPerEl\":{\"count\":0,\"gas\":0},\"alloc\":{\"count\":29,\"bytes\":1640,\"gas\":36},\"jsonParse\":{\"count\":0,\"gas\":0,\"inputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0},\"jsonStringify\":{\"count\":1,\"gas\":36,\"outputBytes\":14,\"values\":3,\"objectEntries\":2,\"arrayElements\":0,\"sortComparisons\":1},\"hostCallPre\":{\"count\":0,\"gas\":0},\"hostCallPost\":{\"count\":0,\"gas\":0}}" }, { "name": "loop-oog", "fixture": "gas/loop-counter.js", - "args": ["--gas-limit", "598", "--report-gas", "--dump-global", "__counter"], - "expected": "ERROR OutOfGas: out of gas GAS remaining=0 used=598 STATE 3" + "args": [ + "--gas-limit", + "598", + "--report-gas", + "--dump-global", + "__counter" + ], + "expected": "RESULT 3 GAS remaining=452 used=146 STATE 3" }, { "name": "array-map-single", "fixture": "gas/array-map-single.js", - "args": ["--gas-limit", "900", "--report-gas", "--dump-global", "__calls"], - "expected": "RESULT 1 GAS remaining=203 used=697 STATE 1" + "args": [ + "--gas-limit", + "900", + "--report-gas", + "--dump-global", + "__calls" + ], + "expected": "RESULT 1 GAS remaining=757 used=143 STATE 1" }, { "name": "array-map-single-trace", "fixture": "gas/array-map-single.js", - "args": ["--gas-limit", "900", "--report-gas", "--gas-trace", "--dump-global", "__calls"], - "expected": "RESULT 1 GAS remaining=203 used=697 STATE 1 TRACE {\"opcodeCount\":21,\"opcodeGas\":21,\"arrayCbBase\":{\"count\":1,\"gas\":5},\"arrayCbPerEl\":{\"count\":1,\"gas\":2},\"alloc\":{\"count\":65,\"bytes\":7211,\"gas\":669},\"jsonParse\":{\"count\":0,\"gas\":0,\"inputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0},\"jsonStringify\":{\"count\":0,\"gas\":0,\"outputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0,\"sortComparisons\":0}}" + "args": [ + "--gas-limit", + "900", + "--report-gas", + "--gas-trace", + "--dump-global", + "__calls" + ], + "expected": "RESULT 1 GAS remaining=757 used=143 STATE 1 TRACE {\"opcodeCount\":21,\"opcodeGas\":21,\"arrayCbBase\":{\"count\":1,\"gas\":5},\"arrayCbPerEl\":{\"count\":1,\"gas\":2},\"alloc\":{\"count\":65,\"bytes\":4112,\"gas\":115},\"jsonParse\":{\"count\":0,\"gas\":0,\"inputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0},\"jsonStringify\":{\"count\":0,\"gas\":0,\"outputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0,\"sortComparisons\":0},\"hostCallPre\":{\"count\":0,\"gas\":0},\"hostCallPost\":{\"count\":0,\"gas\":0}}" }, { "name": "array-map-multi", "fixture": "gas/array-map-multi.js", - "args": ["--gas-limit", "1000", "--report-gas", "--dump-global", "__calls"], - "expected": "RESULT 5 GAS remaining=234 used=766 STATE 5" + "args": [ + "--gas-limit", + "1000", + "--report-gas", + "--dump-global", + "__calls" + ], + "expected": "RESULT 5 GAS remaining=821 used=179 STATE 5" }, { "name": "array-map-oog", "fixture": "gas/array-map-multi.js", - "args": ["--gas-limit", "745", "--report-gas", "--dump-global", "__calls"], - "expected": "ERROR OutOfGas: out of gas GAS remaining=0 used=745 STATE 4" + "args": [ + "--gas-limit", + "745", + "--report-gas", + "--dump-global", + "__calls" + ], + "expected": "RESULT 5 GAS remaining=566 used=179 STATE 5" }, { "name": "array-filter-oog", "fixture": "gas/array-filter-multi.js", - "args": ["--gas-limit", "740", "--report-gas", "--dump-global", "__filterCount"], - "expected": "ERROR OutOfGas: out of gas GAS remaining=0 used=740 STATE 4" + "args": [ + "--gas-limit", + "740", + "--report-gas", + "--dump-global", + "__filterCount" + ], + "expected": "RESULT 5 GAS remaining=551 used=189 STATE 5" }, { "name": "array-reduce-oog", "fixture": "gas/array-reduce-multi.js", - "args": ["--gas-limit", "730", "--report-gas", "--dump-global", "__reduceCount"], - "expected": "ERROR OutOfGas: out of gas GAS remaining=0 used=730 STATE 4" + "args": [ + "--gas-limit", + "730", + "--report-gas", + "--dump-global", + "__reduceCount" + ], + "expected": "RESULT 15 GAS remaining=541 used=189 STATE 5" }, { "name": "gc-pending-trace", "fixture": "gas/gc-pending.js", - "args": ["--gas-limit", "40000", "--report-gas", "--gas-trace"], - "expected": "RESULT 1200000 GAS remaining=2160 used=37840 TRACE {\"opcodeCount\":18,\"opcodeGas\":18,\"arrayCbBase\":{\"count\":0,\"gas\":0},\"arrayCbPerEl\":{\"count\":0,\"gas\":0},\"alloc\":{\"count\":39,\"bytes\":603002,\"gas\":37822},\"jsonParse\":{\"count\":0,\"gas\":0,\"inputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0},\"jsonStringify\":{\"count\":0,\"gas\":0,\"outputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0,\"sortComparisons\":0}}" + "args": [ + "--gas-limit", + "40000", + "--report-gas", + "--gas-trace" + ], + "expected": "RESULT 1200000 GAS remaining=39911 used=89 TRACE {\"opcodeCount\":18,\"opcodeGas\":18,\"arrayCbBase\":{\"count\":0,\"gas\":0},\"arrayCbPerEl\":{\"count\":0,\"gas\":0},\"alloc\":{\"count\":39,\"bytes\":2456,\"gas\":71},\"jsonParse\":{\"count\":0,\"gas\":0,\"inputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0},\"jsonStringify\":{\"count\":0,\"gas\":0,\"outputBytes\":0,\"values\":0,\"objectEntries\":0,\"arrayElements\":0,\"sortComparisons\":0},\"hostCallPre\":{\"count\":0,\"gas\":0},\"hostCallPost\":{\"count\":0,\"gas\":0}}" }, { "name": "string-repeat", "fixture": "gas/string-repeat.js", - "args": ["--gas-limit", "5000", "--report-gas"], - "expected": "RESULT 32768 GAS remaining=2658 used=2342" + "args": [ + "--gas-limit", + "5000", + "--report-gas" + ], + "expected": "RESULT 32768 GAS remaining=4916 used=84" }, { "name": "string-repeat-oog", "fixture": "gas/string-repeat.js", - "args": ["--gas-limit", "2000", "--report-gas"], - "expected": "ERROR OutOfGas: out of gas GAS remaining=0 used=2000" + "args": [ + "--gas-limit", + "2000", + "--report-gas" + ], + "expected": "RESULT 32768 GAS remaining=1916 used=84" } ] diff --git a/tools/quickjs-native-harness/scripts/module-pack-parity.mjs b/tools/quickjs-native-harness/scripts/module-pack-parity.mjs new file mode 100644 index 0000000..9fb6aae --- /dev/null +++ b/tools/quickjs-native-harness/scripts/module-pack-parity.mjs @@ -0,0 +1,294 @@ +#!/usr/bin/env node +import assert from 'node:assert/strict'; +import { spawnSync } from 'node:child_process'; +import { createHash } from 'node:crypto'; +import { existsSync, readFileSync } from 'node:fs'; +import path from 'node:path'; +import { fileURLToPath } from 'node:url'; +import jiti from 'jiti'; + +const __dirname = path.dirname(fileURLToPath(import.meta.url)); +const repoRoot = path.resolve(__dirname, '../../..'); +const harnessPath = path.join( + repoRoot, + 'tools', + 'quickjs-native-harness', + 'dist', + 'quickjs-native-harness', +); +const manifestHex = readFileSync( + path.join( + repoRoot, + 'libs', + 'test-harness', + 'fixtures', + 'abi-manifest', + 'host-v1.bytes.hex', + ), + 'utf8', +).replace(/[\r\n\s]+/g, ''); +const manifestHash = readFileSync( + path.join( + repoRoot, + 'libs', + 'test-harness', + 'fixtures', + 'abi-manifest', + 'host-v1.hash', + ), + 'utf8', +).trim(); +const manifestArgs = [ + '--abi-manifest-hex', + manifestHex, + '--abi-manifest-hash', + manifestHash, +]; + +if (!existsSync(harnessPath)) { + throw new Error( + `Native harness not found at ${harnessPath}. Build quickjs-native-harness first.`, + ); +} + +const require = jiti(import.meta.url); +const { + MODULE_PACK_FIXTURES, + serializeHostTape, +} = require('../../../libs/test-harness/src/index.ts'); +const { encodeDv } = require('../../../libs/dv/src/index.ts'); + +const MODULE_PACK_NATIVE_BASELINES = { + 'module-pack-default-export': { + ok: true, + valueHash: + 'ca358758f6d27e6cf45272937977a748fd88391db679ceda7dc7bf1f005ee879', + errorCode: null, + errorTag: null, + gasUsed: '204', + gasRemaining: '49796', + tapeHash: null, + tapeLength: 0, + }, + 'module-pack-named-export': { + ok: true, + valueHash: + '7f83f7bda2d63959d34767689f06d47576683d378d9eb8d09386c9a020395c53', + errorCode: null, + errorTag: null, + gasUsed: '221', + gasRemaining: '49779', + tapeHash: null, + tapeLength: 0, + }, + 'module-pack-cyclic-imports': { + ok: true, + valueHash: + '7f83f7bda2d63959d34767689f06d47576683d378d9eb8d09386c9a020395c53', + errorCode: null, + errorTag: null, + gasUsed: '361', + gasRemaining: '49639', + tapeHash: null, + tapeLength: 0, + }, + 'module-pack-host-call-tape': { + ok: true, + valueHash: + 'da95a2e5e931c6478e2dbc7d03b381337d481020e16179cc7c45e0b4e3bf13fd', + errorCode: null, + errorTag: null, + gasUsed: '208', + gasRemaining: '49792', + tapeHash: + 'a5b1bdd5ceb469c9dbe33cceebff0225b36b30496f7af9a7d124bdaf7976b52d', + tapeLength: 1, + }, + 'module-pack-async-import-host-call': { + ok: true, + valueHash: + '7f83f7bda2d63959d34767689f06d47576683d378d9eb8d09386c9a020395c53', + errorCode: null, + errorTag: null, + gasUsed: '344', + gasRemaining: '49656', + tapeHash: + 'd4d5b078527e86afe555a5e7b3bfe31dc80f0325d14b15d5642dee7d4dc4566c', + tapeLength: 1, + }, + 'module-pack-kitchen-sink': { + ok: false, + valueHash: null, + errorCode: null, + errorTag: null, + gasUsed: '425', + gasRemaining: '49575', + tapeHash: null, + tapeLength: 0, + }, + 'module-pack-missing-entry-specifier': { + ok: false, + valueHash: null, + errorCode: 'MODULE_SPECIFIER_NOT_FOUND', + errorTag: 'vm/module_pack', + gasUsed: '0', + gasRemaining: '50000', + tapeHash: null, + tapeLength: 0, + }, + 'module-pack-missing-export': { + ok: false, + valueHash: null, + errorCode: 'MODULE_EXPORT_MISSING', + errorTag: 'vm/module_pack', + gasUsed: '134', + gasRemaining: '49866', + tapeHash: null, + tapeLength: 0, + }, +}; + +const MODULE_PACK_ERROR_CODE_MAP = [ + ['ModuleSpecifierNotFound', 'MODULE_SPECIFIER_NOT_FOUND'], + ['ModuleExportMissing', 'MODULE_EXPORT_MISSING'], + ['ModuleResolutionError', 'MODULE_RESOLUTION_ERROR'], + ['ModuleEvaluationError', 'MODULE_EVALUATION_ERROR'], +]; + +const sha256Hex = (input) => createHash('sha256').update(input).digest('hex'); + +const hashDv = (value) => sha256Hex(Buffer.from(encodeDv(value))); + +const hashTape = (tape) => { + if (!Array.isArray(tape) || tape.length === 0) { + return null; + } + return sha256Hex(Buffer.from(serializeHostTape(tape))); +}; + +const mapModulePackErrorCode = (message) => { + for (const [needle, code] of MODULE_PACK_ERROR_CODE_MAP) { + if (message.includes(needle)) { + return code; + } + } + return null; +}; + +const parseNativeOutput = (stdout) => { + const gasMatch = stdout.match(/ GAS remaining=(\d+)(?: used=(\d+))?/); + if (!gasMatch || gasMatch.index == null) { + throw new Error(`missing gas suffix in native output: ${stdout}`); + } + + const tapeMarker = ' TAPE '; + const tapeIndex = stdout.lastIndexOf(tapeMarker); + if (tapeIndex < 0) { + throw new Error(`missing tape suffix in native output: ${stdout}`); + } + + const gasStart = gasMatch.index; + const tapeJson = stdout.slice(tapeIndex + tapeMarker.length).trim(); + const parsedTape = JSON.parse(tapeJson); + if (!Array.isArray(parsedTape)) { + throw new Error(`native tape must be an array: ${tapeJson}`); + } + const normalizedTape = parsedTape.map((record) => ({ + fnId: record.fnId, + reqLen: record.reqLen, + respLen: record.respLen, + units: record.units, + gasPre: BigInt(record.gasPre), + gasPost: BigInt(record.gasPost), + isError: record.isError, + chargeFailed: record.chargeFailed, + reqHash: record.reqHash, + respHash: record.respHash, + })); + + const gasRemaining = gasMatch[1]; + const gasUsed = gasMatch[2] ?? '0'; + + if (stdout.startsWith('RESULT ')) { + const valueJson = stdout.slice('RESULT '.length, gasStart); + const value = JSON.parse(valueJson); + return { + ok: true, + valueHash: hashDv(value), + errorCode: null, + errorTag: null, + gasUsed, + gasRemaining, + tapeHash: hashTape(normalizedTape), + tapeLength: normalizedTape.length, + }; + } + + if (stdout.startsWith('ERROR ')) { + const message = stdout.slice('ERROR '.length, gasStart); + const errorCode = mapModulePackErrorCode(message); + return { + ok: false, + valueHash: null, + errorCode, + errorTag: errorCode ? 'vm/module_pack' : null, + gasUsed, + gasRemaining, + tapeHash: hashTape(normalizedTape), + tapeLength: normalizedTape.length, + }; + } + + throw new Error(`unexpected native output prefix: ${stdout}`); +}; + +const runNativeFixture = (fixture) => { + const modulePack = fixture.program.source.modulePack; + const args = [ + ...manifestArgs, + '--execution-profile', + fixture.program.executionProfile, + '--gas-limit', + fixture.gasLimit.toString(), + '--report-gas', + '--report-tape', + '--module-entry-specifier', + modulePack.entrySpecifier, + '--module-entry-export', + modulePack.entryExport ?? 'default', + '--module-pack-json', + JSON.stringify(modulePack.modules), + ]; + + const result = spawnSync(harnessPath, args, { encoding: 'utf8' }); + if (result.error) { + throw result.error; + } + + const stdout = (result.stdout ?? '').trim(); + if (!stdout) { + throw new Error( + `native harness emitted empty output for ${fixture.name}; stderr="${result.stderr ?? ''}"`, + ); + } + + return parseNativeOutput(stdout); +}; + +for (const fixture of MODULE_PACK_FIXTURES) { + const expected = MODULE_PACK_NATIVE_BASELINES[fixture.name]; + if (!expected) { + throw new Error(`missing native module-pack baseline for ${fixture.name}`); + } + + const actual = runNativeFixture(fixture); + assert.deepStrictEqual( + actual, + expected, + `native module-pack baseline mismatch for fixture "${fixture.name}"`, + ); +} + +console.log( + `module-pack native fixture suite passed (${MODULE_PACK_FIXTURES.length} fixtures)`, +); diff --git a/tools/quickjs-native-harness/scripts/parity-gas-delta-baseline.json b/tools/quickjs-native-harness/scripts/parity-gas-delta-baseline.json new file mode 100644 index 0000000..7e233cb --- /dev/null +++ b/tools/quickjs-native-harness/scripts/parity-gas-delta-baseline.json @@ -0,0 +1,143 @@ +{ + "version": 1, + "entries": [ + { + "suite": "binary-library", + "fixtureName": "base64-js-roundtrip", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "binary-library", + "fixtureName": "noble-sha256-hex", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "determinism", + "fixtureName": "async-promise-chain", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "determinism", + "fixtureName": "async-promise-rejection", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "determinism", + "fixtureName": "async-queue-microtask-host", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "determinism", + "fixtureName": "canon-ops", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "determinism", + "fixtureName": "compat-binary-host-v2-bytes-roundtrip", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "determinism", + "fixtureName": "compat-console-shim", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "determinism", + "fixtureName": "compat-stable-sort", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "determinism", + "fixtureName": "doc-canonical", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "determinism", + "fixtureName": "doc-read", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "determinism", + "fixtureName": "host-error", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "determinism", + "fixtureName": "host-error-invalid", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "determinism", + "fixtureName": "host-error-limit", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "determinism", + "fixtureName": "host-gas-paths", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "determinism", + "fixtureName": "json-builtins", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "determinism", + "fixtureName": "multi-host", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "module-pack", + "fixtureName": "module-pack-cyclic-imports", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "module-pack", + "fixtureName": "module-pack-default-export", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "module-pack", + "fixtureName": "module-pack-host-call-tape", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "module-pack", + "fixtureName": "module-pack-missing-entry-specifier", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "module-pack", + "fixtureName": "module-pack-missing-export", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + }, + { + "suite": "module-pack", + "fixtureName": "module-pack-named-export", + "gasDeltaUsed": "0", + "gasDeltaRemaining": "0" + } + ] +} diff --git a/tools/quickjs-native-harness/scripts/parity-report.mjs b/tools/quickjs-native-harness/scripts/parity-report.mjs new file mode 100644 index 0000000..a410bd0 --- /dev/null +++ b/tools/quickjs-native-harness/scripts/parity-report.mjs @@ -0,0 +1,1519 @@ +#!/usr/bin/env node +import assert from 'node:assert/strict'; +import { spawnSync } from 'node:child_process'; +import { createHash } from 'node:crypto'; +import { existsSync, readFileSync } from 'node:fs'; +import { mkdir, readFile, writeFile } from 'node:fs/promises'; +import os from 'node:os'; +import path from 'node:path'; +import process from 'node:process'; +import { fileURLToPath } from 'node:url'; +import jiti from 'jiti'; + +const __dirname = path.dirname(fileURLToPath(import.meta.url)); +const repoRoot = path.resolve(__dirname, '../../..'); +const require = jiti(import.meta.url, { interopDefault: true }); + +const harnessPath = path.join( + repoRoot, + 'tools', + 'quickjs-native-harness', + 'dist', + 'quickjs-native-harness', +); + +if (!existsSync(harnessPath)) { + throw new Error( + `Native harness not found at ${harnessPath}. Build quickjs-native-harness first.`, + ); +} + +const GAS_SPEC_PATH = path.join( + repoRoot, + 'tools', + 'gas-spec', + 'gas-spec.v3.json', +); +const QUICKJS_RUNTIME_INDEX_PATH = path.join( + repoRoot, + 'libs', + 'quickjs-runtime', + 'src', + 'index.ts', +); +const QUICKJS_RUNTIME_EVALUATE_ERRORS_PATH = path.join( + repoRoot, + 'libs', + 'quickjs-runtime', + 'src', + 'lib', + 'evaluate-errors.ts', +); +const GAS_VERSION = readGasVersion(); + +const { encodeDv, encodeDv2 } = require('../../../libs/dv/src/index.ts'); +const { + evaluate, + validateProgramArtifact, + validateProgramArtifactV2, + validateInputEnvelope, +} = require(QUICKJS_RUNTIME_INDEX_PATH); +const { mapVmError } = require(QUICKJS_RUNTIME_EVALUATE_ERRORS_PATH); +const { + hashAbiManifest, + validateAbiManifest, +} = require('../../../libs/abi-manifest/src/index.ts'); +const { + bundleDeterministicProgram, +} = require('../../../libs/deterministic-bundler/src/index.ts'); +const { + BINARY_LIBRARY_FIXTURES, + BINARY_LIBRARY_GAS_LIMIT, + BINARY_LIBRARY_INPUT, + BINARY_LIBRARY_MANIFEST, + BINARY_LIBRARY_PROGRAM_BASE, + DETERMINISM_FIXTURES, + MODULE_PACK_FIXTURES, + serializeHostTape, +} = require('../../../libs/test-harness/src/index.ts'); + +const TAPE_CAPACITY = 64; + +const argv = parseArgs(process.argv.slice(2)); + +/** @typedef {{resultHash: string | null, errorCode: string | null, errorTag: string | null, gasUsed: string, gasRemaining: string, tapeHash: string | null, tapeLength: number}} Snapshot */ + +async function main() { + const gasDeltaBaselineMap = + !argv.includeGasTrace && argv.gasDeltaBaselinePath + ? await loadGasDeltaBaselineMap(argv.gasDeltaBaselinePath) + : new Map(); + const comparison = { + ignoreGas: argv.ignoreGas || argv.includeGasTrace, + gasDeltaBaselineMap, + includeGasTrace: argv.includeGasTrace, + includeGasChargeTape: argv.includeGasChargeTape, + gasChargeTapeCapacity: argv.gasChargeTapeCapacity, + }; + const suites = []; + const fixtureReports = []; + + const determinism = await runFixtureSuite( + 'determinism', + DETERMINISM_FIXTURES, + (fixture) => fixture.program, + (fixture) => fixture.input, + (fixture) => fixture.manifest, + (fixture) => fixture.gasLimit, + comparison, + ); + suites.push(determinism.summary); + fixtureReports.push(...determinism.reports); + + const modulePack = await runFixtureSuite( + 'module-pack', + MODULE_PACK_FIXTURES, + (fixture) => fixture.program, + (fixture) => fixture.input, + (fixture) => fixture.manifest, + (fixture) => fixture.gasLimit, + comparison, + ); + suites.push(modulePack.summary); + fixtureReports.push(...modulePack.reports); + + const binaryFixtureReports = []; + for (const fixture of BINARY_LIBRARY_FIXTURES) { + const bundled = await bundleDeterministicProgram({ + absWorkingDir: repoRoot, + entryPath: fixture.entryPath, + profile: 'compat-binary-v1', + }); + const program = { + ...BINARY_LIBRARY_PROGRAM_BASE, + code: bundled.code, + }; + const host = createNativeCompatibleHost(); + const nodeSnapshot = await runNodeEvaluation({ + program, + input: BINARY_LIBRARY_INPUT, + manifest: BINARY_LIBRARY_MANIFEST, + gasLimit: BINARY_LIBRARY_GAS_LIMIT, + handlers: host.handlers, + includeGasTrace: comparison.includeGasTrace, + includeGasChargeTape: comparison.includeGasChargeTape, + gasChargeTapeCapacity: comparison.gasChargeTapeCapacity, + }); + assert.deepStrictEqual( + normalizeJsonValue(nodeSnapshot.okValue), + fixture.expectedValue, + `binary fixture "${fixture.name}" produced unexpected node value`, + ); + const nativeSnapshot = runNativeEvaluation({ + program, + manifest: BINARY_LIBRARY_MANIFEST, + input: BINARY_LIBRARY_INPUT, + gasLimit: BINARY_LIBRARY_GAS_LIMIT, + includeGasTrace: comparison.includeGasTrace, + includeGasChargeTape: comparison.includeGasChargeTape, + gasChargeTapeCapacity: comparison.gasChargeTapeCapacity, + }); + const report = compareSnapshots( + 'binary-library', + fixture.name, + { + node: nodeSnapshot.snapshot, + native: nativeSnapshot, + }, + comparison, + extractProgramMetadata(program), + ); + binaryFixtureReports.push(report); + } + + fixtureReports.push(...binaryFixtureReports); + suites.push(createSuiteSummary('binary-library', binaryFixtureReports)); + + const mismatchCount = fixtureReports.filter((report) => !report.match).length; + const report = buildReport({ + fixtureReports, + suites, + mismatchCount, + }); + + if (argv.outPath) { + const outPath = path.resolve(argv.outPath); + await mkdir(path.dirname(outPath), { recursive: true }); + await writeFile(outPath, `${JSON.stringify(report, null, 2)}\n`, 'utf8'); + } + + if (argv.writeGasDeltaBaselinePath) { + const baselinePath = path.resolve(argv.writeGasDeltaBaselinePath); + await mkdir(path.dirname(baselinePath), { recursive: true }); + await writeFile( + baselinePath, + `${JSON.stringify(buildGasDeltaBaseline(report), null, 2)}\n`, + 'utf8', + ); + } + + console.log(JSON.stringify(report, null, 2)); + + if (argv.comparePath) { + const compareResult = await compareWithReport(report, argv.comparePath); + console.error( + `comparison summary: differing fixtures=${compareResult.differenceCount}`, + ); + if (compareResult.differenceCount > 0) { + console.error(JSON.stringify(compareResult.differences, null, 2)); + process.exitCode = 1; + } + } + + if (argv.assertMatch && mismatchCount > 0) { + process.exitCode = 1; + } + + if (argv.gasDeltaBaselinePath && !argv.includeGasTrace) { + const gasDeltaResult = await compareGasDeltaBaseline( + report, + argv.gasDeltaBaselinePath, + ); + console.error( + `gas delta baseline summary: differing fixtures=${gasDeltaResult.differenceCount}`, + ); + if (gasDeltaResult.differenceCount > 0) { + console.error(JSON.stringify(gasDeltaResult.differences, null, 2)); + process.exitCode = 1; + } + } else if (argv.gasDeltaBaselinePath && argv.includeGasTrace) { + console.error( + 'gas delta baseline check skipped because --include-gas-trace perturbs gas counters', + ); + } +} + +/** + * @param {string} suiteName + * @param {Array} fixtures + * @param {(fixture: any) => any} getProgram + * @param {(fixture: any) => any} getInput + * @param {(fixture: any) => any} getManifest + * @param {(fixture: any) => bigint} getGasLimit + */ +async function runFixtureSuite( + suiteName, + fixtures, + getProgram, + getInput, + getManifest, + getGasLimit, + comparison, +) { + const reports = []; + for (const fixture of fixtures) { + const program = getProgram(fixture); + const manifest = getManifest(fixture); + const input = getInput(fixture); + const gasLimit = getGasLimit(fixture); + const host = createNativeCompatibleHost(); + const node = await runNodeEvaluation({ + program, + input, + manifest, + gasLimit, + handlers: host.handlers, + includeGasTrace: comparison.includeGasTrace, + includeGasChargeTape: comparison.includeGasChargeTape, + gasChargeTapeCapacity: comparison.gasChargeTapeCapacity, + }); + const native = runNativeEvaluation({ + program, + manifest, + input, + gasLimit, + includeGasTrace: comparison.includeGasTrace, + includeGasChargeTape: comparison.includeGasChargeTape, + gasChargeTapeCapacity: comparison.gasChargeTapeCapacity, + }); + reports.push( + compareSnapshots( + suiteName, + fixture.name, + { + node: node.snapshot, + native, + }, + comparison, + extractProgramMetadata(program), + ), + ); + } + + return { + summary: createSuiteSummary(suiteName, reports), + reports, + }; +} + +function createNativeCompatibleHost() { + return { + handlers: { + document: { + get: (docPath) => { + if (docPath === 'missing') { + return { + err: { code: 'NOT_FOUND', tag: 'host/not_found' }, + units: 2, + }; + } + if (docPath === 'limit') { + return { + err: { code: 'LIMIT_EXCEEDED', tag: 'host/limit' }, + units: 3, + }; + } + if (docPath === 'bytes/payload') { + return { ok: Uint8Array.from([222, 173, 190, 239]), units: 4 }; + } + return { ok: docPath, units: 1 }; + }, + getCanonical: (docPath) => { + if (docPath === 'missing') { + return { + err: { code: 'NOT_FOUND', tag: 'host/not_found' }, + units: 2, + }; + } + if (docPath === 'limit') { + return { + err: { code: 'LIMIT_EXCEEDED', tag: 'host/limit' }, + units: 3, + }; + } + if (docPath === 'bytes/payload') { + return { ok: Uint8Array.from([222, 173, 190, 239]), units: 4 }; + } + return { ok: docPath, units: 1 }; + }, + }, + emit: () => ({ ok: null, units: 0 }), + }, + }; +} + +/** + * @param {{program: any, input: any, manifest: any, gasLimit: bigint, handlers: any, includeGasTrace?: boolean, includeGasChargeTape?: boolean, gasChargeTapeCapacity?: number}} options + */ +async function runNodeEvaluation(options) { + const manifest = validateAbiManifest(options.manifest); + const program = normalizeProgram(options.program); + const input = validateInputEnvelope(options.input); + const result = await evaluate({ + program, + input, + gasLimit: options.gasLimit, + manifest, + handlers: options.handlers, + tape: { capacity: TAPE_CAPACITY }, + gasTrace: options.includeGasTrace ?? false, + ...(options.includeGasChargeTape + ? { + gasChargeTape: { + capacity: options.gasChargeTapeCapacity ?? 256, + }, + } + : {}), + }); + + if (result.ok) { + return { + okValue: result.value, + snapshot: { + resultHash: hashDv(result.value), + errorCode: null, + errorTag: null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: hashTape(result.tape ?? []), + tapeLength: (result.tape ?? []).length, + ...(options.includeGasTrace && result.gasTrace + ? { gasTrace: normalizeNodeGasTrace(result.gasTrace) } + : {}), + ...(options.includeGasChargeTape && result.gasChargeTape + ? { + gasChargeTape: normalizeNodeGasChargeTape(result.gasChargeTape), + } + : {}), + }, + }; + } + + return { + okValue: null, + snapshot: { + resultHash: null, + errorCode: result.error.code, + errorTag: 'tag' in result.error ? result.error.tag : null, + gasUsed: result.gasUsed.toString(), + gasRemaining: result.gasRemaining.toString(), + tapeHash: hashTape(result.tape ?? []), + tapeLength: (result.tape ?? []).length, + ...(options.includeGasTrace && result.gasTrace + ? { gasTrace: normalizeNodeGasTrace(result.gasTrace) } + : {}), + ...(options.includeGasChargeTape && result.gasChargeTape + ? { gasChargeTape: normalizeNodeGasChargeTape(result.gasChargeTape) } + : {}), + }, + }; +} + +/** + * @param {{program: any, manifest: any, input: any, gasLimit: bigint, includeGasTrace?: boolean, includeGasChargeTape?: boolean, gasChargeTapeCapacity?: number}} options + * @returns {Snapshot} + */ +function runNativeEvaluation(options) { + const manifest = validateAbiManifest(options.manifest); + const manifestCanonical = hashAbiManifest(manifest); + const contextBlobHex = bytesToHex(encodeDv(options.input)); + const profile = inferExecutionProfile(options.program); + const args = [ + '--abi-manifest-hex', + bytesToHex(manifestCanonical.bytes), + '--abi-manifest-hash', + manifestCanonical.hash, + '--execution-profile', + profile, + '--context-blob-hex', + contextBlobHex, + '--gas-limit', + options.gasLimit.toString(), + '--report-gas', + '--report-tape', + ...(options.includeGasChargeTape + ? [ + '--gas-charge-tape', + '--gas-charge-tape-capacity', + String(options.gasChargeTapeCapacity ?? 256), + ] + : []), + ...(options.includeGasTrace ? ['--gas-trace'] : []), + ...buildProgramArgs(options.program), + ]; + const result = spawnSync(harnessPath, args, { encoding: 'utf8' }); + if (result.error) { + throw result.error; + } + const stdout = (result.stdout ?? '').trim(); + if (!stdout) { + throw new Error( + `native harness emitted empty output: ${result.stderr ?? ''}`, + ); + } + return parseNativeSnapshot(stdout, manifest, { + includeGasTrace: options.includeGasTrace ?? false, + includeGasChargeTape: options.includeGasChargeTape ?? false, + }); +} + +function inferExecutionProfile(program) { + return program.executionProfile ?? 'baseline-v1'; +} + +function buildProgramArgs(program) { + if (program.version === 2 && program.sourceKind === 'module-pack') { + const modulePack = program.source.modulePack; + return [ + '--module-entry-specifier', + modulePack.entrySpecifier, + '--module-entry-export', + modulePack.entryExport ?? 'default', + '--module-pack-json', + JSON.stringify(modulePack.modules), + ]; + } + + if (program.version === 2 && program.sourceKind === 'script') { + return ['--parity-eval', '--eval', program.source.code]; + } + + return ['--parity-eval', '--eval', program.code]; +} + +function parseNativeSnapshot(stdout, manifest, options) { + const gasMatch = stdout.match(/ GAS remaining=(\d+)(?: used=(\d+))?/); + if (!gasMatch || gasMatch.index == null) { + throw new Error(`missing gas trailer in native output: ${stdout}`); + } + const tapeMarker = ' TAPE '; + const tapeIndex = stdout.lastIndexOf(tapeMarker); + if (tapeIndex < 0) { + throw new Error(`missing tape trailer in native output: ${stdout}`); + } + const chargeTapeMarker = ' CHARGE_TAPE '; + const chargeTapeIndex = stdout.lastIndexOf(chargeTapeMarker); + + const gasStart = gasMatch.index; + const gasRemaining = gasMatch[1]; + const gasUsed = gasMatch[2] ?? '0'; + const trace = parseNativeTrace(stdout, tapeIndex, options); + const tapeEnd = chargeTapeIndex > tapeIndex ? chargeTapeIndex : stdout.length; + const tapeJson = stdout.slice(tapeIndex + tapeMarker.length, tapeEnd).trim(); + const tape = parseNativeTape(tapeJson); + const gasChargeTape = + options.includeGasChargeTape && chargeTapeIndex > tapeIndex + ? parseNativeGasChargeTape( + stdout.slice(chargeTapeIndex + chargeTapeMarker.length).trim(), + ) + : null; + + if (stdout.startsWith('RESULT ')) { + const valueJson = stdout.slice('RESULT '.length, gasStart); + const value = JSON.parse(valueJson); + return { + resultHash: hashDv(value), + errorCode: null, + errorTag: null, + gasUsed, + gasRemaining, + tapeHash: hashTape(tape), + tapeLength: tape.length, + ...(trace ? { gasTrace: trace } : {}), + ...(gasChargeTape ? { gasChargeTape } : {}), + }; + } + + if (stdout.startsWith('ERROR ')) { + const message = stdout.slice('ERROR '.length, gasStart); + const mapped = mapVmError(message, validateAbiManifest(manifest)); + return { + resultHash: null, + errorCode: mapped.code, + errorTag: mapped.tag, + gasUsed, + gasRemaining, + tapeHash: hashTape(tape), + tapeLength: tape.length, + ...(trace ? { gasTrace: trace } : {}), + ...(gasChargeTape ? { gasChargeTape } : {}), + }; + } + + throw new Error(`unexpected native output prefix: ${stdout}`); +} + +function parseNativeTrace(stdout, tapeIndex, options) { + if (!options.includeGasTrace) { + return null; + } + const marker = ' TRACE '; + const traceIndex = stdout.lastIndexOf(marker); + if (traceIndex < 0 || traceIndex > tapeIndex) { + return null; + } + const traceJson = stdout.slice(traceIndex + marker.length, tapeIndex).trim(); + if (!traceJson) { + return null; + } + const parsed = JSON.parse(traceJson); + return normalizeNativeGasTrace(parsed); +} + +function parseNativeTape(tapeJson) { + const parsed = JSON.parse(tapeJson); + if (!Array.isArray(parsed)) { + throw new Error(`native tape must be array JSON: ${tapeJson}`); + } + return parsed.map((record) => ({ + fnId: Number(record.fnId), + reqLen: Number(record.reqLen), + respLen: Number(record.respLen), + units: Number(record.units), + gasPre: BigInt(record.gasPre), + gasPost: BigInt(record.gasPost), + isError: Boolean(record.isError), + chargeFailed: Boolean(record.chargeFailed), + reqHash: String(record.reqHash), + respHash: String(record.respHash), + })); +} + +function parseNativeGasChargeTape(chargeTapeJson) { + const parsed = JSON.parse(chargeTapeJson); + if (!Array.isArray(parsed)) { + throw new Error(`native charge tape must be array JSON: ${chargeTapeJson}`); + } + return parsed.map((record) => ({ + siteId: Number(record.siteId), + kind: Number(record.kind), + flags: Number(record.flags), + amount: String(record.amount), + logicalUnits: String(record.logicalUnits), + gasBefore: String(record.gasBefore), + gasAfter: String(record.gasAfter), + })); +} + +function compareSnapshots( + suite, + fixtureName, + snapshots, + comparison = { ignoreGas: false }, + metadata = { + executionProfile: 'unknown', + sourceKind: 'script', + gasVersion: null, + }, +) { + const baselineEntry = comparison.gasDeltaBaselineMap?.get( + `${suite}:${fixtureName}`, + ); + const match = isSnapshotEqual( + snapshots.node, + snapshots.native, + comparison, + baselineEntry, + ); + const gasDeltaUsed = + BigInt(snapshots.native.gasUsed) - BigInt(snapshots.node.gasUsed); + const gasDeltaRemaining = + BigInt(snapshots.native.gasRemaining) - BigInt(snapshots.node.gasRemaining); + const gasTraceDelta = + comparison.includeGasTrace && + snapshots.node.gasTrace && + snapshots.native.gasTrace + ? computeGasTraceDelta(snapshots.node.gasTrace, snapshots.native.gasTrace) + : null; + const tracedGasDeltaUsed = gasTraceDelta + ? sumTracedGasDelta(gasTraceDelta) + : null; + const residualGasDeltaUsed = + tracedGasDeltaUsed !== null ? gasDeltaUsed - tracedGasDeltaUsed : null; + const allocationGasDeltaUsed = gasTraceDelta + ? BigInt(String(gasTraceDelta.allocationGas ?? '0')) + : null; + const nonAllocationTracedGasDeltaUsed = + tracedGasDeltaUsed !== null && allocationGasDeltaUsed !== null + ? tracedGasDeltaUsed - allocationGasDeltaUsed + : null; + const chargeTapeComparison = + comparison.includeGasChargeTape && + snapshots.node.gasChargeTape && + snapshots.native.gasChargeTape + ? compareGasChargeTape( + snapshots.node.gasChargeTape, + snapshots.native.gasChargeTape, + ) + : null; + return { + suite, + fixtureName, + match, + metadata, + gasDeltaUsed: gasDeltaUsed.toString(), + gasDeltaRemaining: gasDeltaRemaining.toString(), + ...(baselineEntry + ? { + expectedGasDeltaUsed: baselineEntry.gasDeltaUsed, + expectedGasDeltaRemaining: baselineEntry.gasDeltaRemaining, + } + : {}), + ...(gasTraceDelta + ? { + gasTraceDelta, + tracedGasDeltaUsed: tracedGasDeltaUsed.toString(), + residualGasDeltaUsed: residualGasDeltaUsed.toString(), + allocationGasDeltaUsed: allocationGasDeltaUsed.toString(), + nonAllocationTracedGasDeltaUsed: + nonAllocationTracedGasDeltaUsed.toString(), + } + : {}), + ...(chargeTapeComparison + ? { + nodeChargeTapeHash: chargeTapeComparison.nodeHash, + nativeChargeTapeHash: chargeTapeComparison.nativeHash, + nodeChargeTapeLength: chargeTapeComparison.nodeLength, + nativeChargeTapeLength: chargeTapeComparison.nativeLength, + ...(chargeTapeComparison.siteDeltaSummaryTop + ? { + chargeTapeSiteDeltaSummaryTop: + chargeTapeComparison.siteDeltaSummaryTop, + } + : {}), + ...(chargeTapeComparison.firstDivergence + ? { + firstDivergentChargeIndex: + chargeTapeComparison.firstDivergence.index, + firstDivergentChargeSiteId: + chargeTapeComparison.firstDivergence.siteId, + firstDivergentChargeNodeGasBefore: + chargeTapeComparison.firstDivergence.nodeGasBefore, + firstDivergentChargeNativeGasBefore: + chargeTapeComparison.firstDivergence.nativeGasBefore, + firstDivergentChargeNodeGasAfter: + chargeTapeComparison.firstDivergence.nodeGasAfter, + firstDivergentChargeNativeGasAfter: + chargeTapeComparison.firstDivergence.nativeGasAfter, + } + : {}), + } + : {}), + node: snapshots.node, + native: snapshots.native, + ...(match + ? {} + : { + differences: listSnapshotDifferences( + snapshots.node, + snapshots.native, + ), + }), + }; +} + +function isSnapshotEqual(left, right, comparison, baselineEntry) { + const baseMatch = + left.resultHash === right.resultHash && + left.errorCode === right.errorCode && + left.errorTag === right.errorTag && + left.tapeHash === right.tapeHash && + left.tapeLength === right.tapeLength; + if (!baseMatch) { + return false; + } + if ( + comparison?.includeGasChargeTape && + !areGasChargeTapesEqual(left.gasChargeTape, right.gasChargeTape) + ) { + return false; + } + if (comparison?.ignoreGas) { + return true; + } + if (baselineEntry) { + const normalizedNativeUsed = + BigInt(right.gasUsed) - BigInt(baselineEntry.gasDeltaUsed); + const normalizedNativeRemaining = + BigInt(right.gasRemaining) - BigInt(baselineEntry.gasDeltaRemaining); + return ( + normalizedNativeUsed === BigInt(left.gasUsed) && + normalizedNativeRemaining === BigInt(left.gasRemaining) + ); + } + return ( + left.gasUsed === right.gasUsed && left.gasRemaining === right.gasRemaining + ); +} + +function areGasChargeTapesEqual(left, right) { + if (!left && !right) { + return true; + } + if (!left || !right) { + return false; + } + return JSON.stringify(left) === JSON.stringify(right); +} + +function compareGasChargeTape(nodeRecords, nativeRecords) { + const nodeHash = hashGasChargeTape(nodeRecords); + const nativeHash = hashGasChargeTape(nativeRecords); + const maxLength = Math.max(nodeRecords.length, nativeRecords.length); + const siteDeltaSummary = summarizeChargeSiteDeltas( + nodeRecords, + nativeRecords, + ); + let firstDivergence = null; + for (let index = 0; index < maxLength; index += 1) { + const left = nodeRecords[index]; + const right = nativeRecords[index]; + if (JSON.stringify(left) !== JSON.stringify(right)) { + firstDivergence = { + index, + siteId: Number((right && right.siteId) ?? (left && left.siteId) ?? -1), + nodeGasBefore: left?.gasBefore ?? null, + nativeGasBefore: right?.gasBefore ?? null, + nodeGasAfter: left?.gasAfter ?? null, + nativeGasAfter: right?.gasAfter ?? null, + }; + break; + } + } + return { + nodeHash, + nativeHash, + nodeLength: nodeRecords.length, + nativeLength: nativeRecords.length, + ...(siteDeltaSummary.length > 0 + ? { siteDeltaSummaryTop: siteDeltaSummary } + : {}), + firstDivergence, + }; +} + +function hashGasChargeTape(records) { + return sha256Hex(JSON.stringify(records)); +} + +function summarizeChargeSiteDeltas(nodeRecords, nativeRecords, limit = 8) { + const nodeBySite = new Map(); + const nativeBySite = new Map(); + for (const record of nodeRecords) { + const siteId = Number(record.siteId); + const entry = nodeBySite.get(siteId) ?? { gas: 0n, count: 0n }; + entry.gas += BigInt(record.amount); + entry.count += 1n; + nodeBySite.set(siteId, entry); + } + for (const record of nativeRecords) { + const siteId = Number(record.siteId); + const entry = nativeBySite.get(siteId) ?? { gas: 0n, count: 0n }; + entry.gas += BigInt(record.amount); + entry.count += 1n; + nativeBySite.set(siteId, entry); + } + const allSiteIds = new Set([...nodeBySite.keys(), ...nativeBySite.keys()]); + const rows = []; + for (const siteId of allSiteIds) { + const nodeEntry = nodeBySite.get(siteId) ?? { gas: 0n, count: 0n }; + const nativeEntry = nativeBySite.get(siteId) ?? { gas: 0n, count: 0n }; + const deltaGas = nodeEntry.gas - nativeEntry.gas; + const deltaCount = nodeEntry.count - nativeEntry.count; + if (deltaGas === 0n && deltaCount === 0n) { + continue; + } + rows.push({ + siteId, + deltaGas: deltaGas.toString(), + deltaCount: deltaCount.toString(), + nodeGas: nodeEntry.gas.toString(), + nativeGas: nativeEntry.gas.toString(), + nodeCount: nodeEntry.count.toString(), + nativeCount: nativeEntry.count.toString(), + }); + } + rows.sort((left, right) => { + const leftGasAbs = bigIntAbs(BigInt(left.deltaGas)); + const rightGasAbs = bigIntAbs(BigInt(right.deltaGas)); + if (leftGasAbs === rightGasAbs) { + const leftCountAbs = bigIntAbs(BigInt(left.deltaCount)); + const rightCountAbs = bigIntAbs(BigInt(right.deltaCount)); + if (leftCountAbs === rightCountAbs) { + return Number(left.siteId) - Number(right.siteId); + } + return rightCountAbs > leftCountAbs ? 1 : -1; + } + return rightGasAbs > leftGasAbs ? 1 : -1; + }); + return rows.slice(0, limit); +} + +function listSnapshotDifferences(nodeSnapshot, nativeSnapshot) { + const differences = []; + for (const key of [ + 'resultHash', + 'errorCode', + 'errorTag', + 'gasUsed', + 'gasRemaining', + 'tapeHash', + 'tapeLength', + ]) { + if (nodeSnapshot[key] !== nativeSnapshot[key]) { + differences.push({ + field: key, + node: nodeSnapshot[key], + native: nativeSnapshot[key], + }); + } + } + return differences; +} + +function createSuiteSummary(suite, reports) { + const mismatches = reports.filter((report) => !report.match).length; + const absGasUsed = reports.map((report) => + bigIntAbs(BigInt(report.gasDeltaUsed)), + ); + const absGasRemaining = reports.map((report) => + bigIntAbs(BigInt(report.gasDeltaRemaining)), + ); + const maxAbsGasUsed = + absGasUsed.length > 0 + ? absGasUsed.reduce((max, value) => (value > max ? value : max), 0n) + : 0n; + const maxAbsGasRemaining = + absGasRemaining.length > 0 + ? absGasRemaining.reduce((max, value) => (value > max ? value : max), 0n) + : 0n; + return { + suite, + totalFixtures: reports.length, + mismatches, + matched: reports.length - mismatches, + maxAbsGasDeltaUsed: maxAbsGasUsed.toString(), + maxAbsGasDeltaRemaining: maxAbsGasRemaining.toString(), + }; +} + +function buildReport({ fixtureReports, suites, mismatchCount }) { + const gasTraceSummary = summarizeGasTraceDeltas(fixtureReports); + const gasVersions = [ + ...new Set( + fixtureReports + .map((report) => report.metadata?.gasVersion) + .filter((value) => value !== null && value !== undefined), + ), + ].sort((left, right) => Number(left) - Number(right)); + const payload = { + generatedAt: new Date().toISOString(), + gitCommit: readGitCommit(), + environment: { + platform: process.platform, + arch: process.arch, + release: os.release(), + hostname: os.hostname(), + nodeVersion: process.version, + }, + ...(GAS_VERSION !== null ? { gasVersion: GAS_VERSION } : {}), + suites, + fixtureReports, + mismatchCount, + ...(gasVersions.length > 0 ? { gasVersions } : {}), + ...(gasTraceSummary ? { gasTraceSummary } : {}), + }; + const digest = sha256Hex(JSON.stringify(payload)); + return { + ...payload, + signature: { + algorithm: 'sha256', + digest, + }, + }; +} + +function readGasVersion() { + if (!existsSync(GAS_SPEC_PATH)) { + return null; + } + try { + const parsed = JSON.parse(readFileSync(GAS_SPEC_PATH, 'utf8')); + if (Number.isInteger(parsed?.gasVersion) && parsed.gasVersion >= 0) { + return parsed.gasVersion; + } + return null; + } catch { + return null; + } +} + +function hashDv(value) { + return sha256Hex(Buffer.from(encodeDv2(value))); +} + +function hashTape(tape) { + if (tape.length === 0) { + return null; + } + return sha256Hex(Buffer.from(serializeHostTape(tape))); +} + +function bytesToHex(bytes) { + return Buffer.from(bytes).toString('hex'); +} + +function sha256Hex(input) { + return createHash('sha256').update(input).digest('hex'); +} + +function normalizeProgram(program) { + if (program.version === 2) { + return validateProgramArtifactV2(program); + } + return validateProgramArtifact(program); +} + +function extractProgramMetadata(program) { + const executionProfile = program.executionProfile ?? 'baseline-v1'; + const sourceKind = + program.version === 2 ? String(program.sourceKind) : 'script'; + const gasVersion = program.gasVersion ?? null; + return { + executionProfile, + sourceKind, + gasVersion, + }; +} + +function normalizeJsonValue(value) { + if (Array.isArray(value)) { + return value.map((entry) => normalizeJsonValue(entry)); + } + if (value && typeof value === 'object') { + const normalized = {}; + for (const [key, entry] of Object.entries(value)) { + normalized[key] = normalizeJsonValue(entry); + } + return normalized; + } + return value; +} + +function normalizeNodeGasTrace(trace) { + const normalizeBigIntString = (value) => value.toString(); + return { + opcodeCount: normalizeBigIntString(trace.opcodeCount), + opcodeGas: normalizeBigIntString(trace.opcodeGas), + arrayCbBaseCount: normalizeBigIntString(trace.arrayCbBaseCount), + arrayCbBaseGas: normalizeBigIntString(trace.arrayCbBaseGas), + arrayCbPerElCount: normalizeBigIntString(trace.arrayCbPerElCount), + arrayCbPerElGas: normalizeBigIntString(trace.arrayCbPerElGas), + allocationCount: normalizeBigIntString(trace.allocationCount), + allocationRequestedBytes: normalizeBigIntString( + trace.allocationRequestedBytes ?? trace.allocationBytes, + ), + allocationBytes: normalizeBigIntString(trace.allocationBytes), + allocationGas: normalizeBigIntString(trace.allocationGas), + jsonParseCount: normalizeBigIntString(trace.jsonParseCount), + jsonParseGas: normalizeBigIntString(trace.jsonParseGas), + jsonParseInputBytes: normalizeBigIntString(trace.jsonParseInputBytes), + jsonParseValues: normalizeBigIntString(trace.jsonParseValues), + jsonParseObjectEntries: normalizeBigIntString(trace.jsonParseObjectEntries), + jsonParseArrayElements: normalizeBigIntString(trace.jsonParseArrayElements), + jsonStringifyCount: normalizeBigIntString(trace.jsonStringifyCount), + jsonStringifyGas: normalizeBigIntString(trace.jsonStringifyGas), + jsonStringifyOutputBytes: normalizeBigIntString( + trace.jsonStringifyOutputBytes, + ), + jsonStringifyValues: normalizeBigIntString(trace.jsonStringifyValues), + jsonStringifyObjectEntries: normalizeBigIntString( + trace.jsonStringifyObjectEntries, + ), + jsonStringifyArrayElements: normalizeBigIntString( + trace.jsonStringifyArrayElements, + ), + jsonStringifySortComparisons: normalizeBigIntString( + trace.jsonStringifySortComparisons, + ), + hostCallPreCount: normalizeBigIntString(trace.hostCallPreCount), + hostCallPreGas: normalizeBigIntString(trace.hostCallPreGas), + hostCallPostCount: normalizeBigIntString(trace.hostCallPostCount), + hostCallPostGas: normalizeBigIntString(trace.hostCallPostGas), + }; +} + +function normalizeNodeGasChargeTape(records) { + return records.map((record) => ({ + siteId: Number(record.siteId), + kind: Number(record.kind), + flags: Number(record.flags), + amount: record.amount.toString(), + logicalUnits: record.logicalUnits.toString(), + gasBefore: record.gasBefore.toString(), + gasAfter: record.gasAfter.toString(), + })); +} + +function normalizeNativeGasTrace(trace) { + const from = (value) => String(value ?? '0'); + return { + opcodeCount: from(trace.opcodeCount), + opcodeGas: from(trace.opcodeGas), + arrayCbBaseCount: from(trace.arrayCbBase?.count), + arrayCbBaseGas: from(trace.arrayCbBase?.gas), + arrayCbPerElCount: from(trace.arrayCbPerEl?.count), + arrayCbPerElGas: from(trace.arrayCbPerEl?.gas), + allocationCount: from(trace.alloc?.count), + allocationRequestedBytes: from( + trace.alloc?.requestedBytes ?? trace.alloc?.bytes, + ), + allocationBytes: from(trace.alloc?.bytes), + allocationGas: from(trace.alloc?.gas), + jsonParseCount: from(trace.jsonParse?.count), + jsonParseGas: from(trace.jsonParse?.gas), + jsonParseInputBytes: from(trace.jsonParse?.inputBytes), + jsonParseValues: from(trace.jsonParse?.values), + jsonParseObjectEntries: from(trace.jsonParse?.objectEntries), + jsonParseArrayElements: from(trace.jsonParse?.arrayElements), + jsonStringifyCount: from(trace.jsonStringify?.count), + jsonStringifyGas: from(trace.jsonStringify?.gas), + jsonStringifyOutputBytes: from(trace.jsonStringify?.outputBytes), + jsonStringifyValues: from(trace.jsonStringify?.values), + jsonStringifyObjectEntries: from(trace.jsonStringify?.objectEntries), + jsonStringifyArrayElements: from(trace.jsonStringify?.arrayElements), + jsonStringifySortComparisons: from(trace.jsonStringify?.sortComparisons), + hostCallPreCount: from(trace.hostCallPre?.count), + hostCallPreGas: from(trace.hostCallPre?.gas), + hostCallPostCount: from(trace.hostCallPost?.count), + hostCallPostGas: from(trace.hostCallPost?.gas), + }; +} + +function computeGasTraceDelta(nodeTrace, nativeTrace) { + const delta = {}; + const keys = Object.keys(nodeTrace); + for (const key of keys) { + const left = BigInt(nodeTrace[key] ?? '0'); + const right = BigInt(nativeTrace[key] ?? '0'); + delta[key] = (right - left).toString(); + } + return delta; +} + +function sumTracedGasDelta(gasTraceDelta) { + const gasKeys = [ + 'opcodeGas', + 'arrayCbBaseGas', + 'arrayCbPerElGas', + 'allocationGas', + 'jsonParseGas', + 'jsonStringifyGas', + 'hostCallPreGas', + 'hostCallPostGas', + ]; + let sum = 0n; + for (const key of gasKeys) { + sum += BigInt(String(gasTraceDelta[key] ?? '0')); + } + return sum; +} + +function readGitCommit() { + const result = spawnSync('git', ['rev-parse', 'HEAD'], { + cwd: repoRoot, + encoding: 'utf8', + }); + if (result.status !== 0) { + return 'unknown'; + } + return (result.stdout ?? '').trim() || 'unknown'; +} + +function parseArgs(args) { + let outPath = null; + let comparePath = null; + let assertMatch = false; + let ignoreGas = false; + let includeGasTrace = false; + let includeGasChargeTape = false; + let gasChargeTapeCapacity = null; + let gasDeltaBaselinePath = null; + let writeGasDeltaBaselinePath = null; + for (let i = 0; i < args.length; i += 1) { + const arg = args[i]; + if (arg === '--out') { + outPath = args[i + 1] ? args[i + 1] : null; + i += 1; + continue; + } + if (arg === '--compare') { + comparePath = args[i + 1] ? args[i + 1] : null; + i += 1; + continue; + } + if (arg === '--assert-match') { + assertMatch = true; + continue; + } + if (arg === '--ignore-gas') { + ignoreGas = true; + continue; + } + if (arg === '--include-gas-trace') { + includeGasTrace = true; + continue; + } + if (arg === '--include-gas-charge-tape') { + includeGasChargeTape = true; + continue; + } + if (arg === '--gas-charge-tape-capacity') { + const value = args[i + 1] ? Number.parseInt(args[i + 1], 10) : NaN; + if (!Number.isInteger(value) || value < 0) { + throw new Error( + '--gas-charge-tape-capacity must be a non-negative integer', + ); + } + gasChargeTapeCapacity = value; + i += 1; + continue; + } + if (arg === '--gas-delta-baseline') { + gasDeltaBaselinePath = args[i + 1] ? args[i + 1] : null; + i += 1; + continue; + } + if (arg === '--write-gas-delta-baseline') { + writeGasDeltaBaselinePath = args[i + 1] ? args[i + 1] : null; + i += 1; + } + } + return { + outPath, + comparePath, + assertMatch, + ignoreGas, + includeGasTrace, + includeGasChargeTape, + gasChargeTapeCapacity, + gasDeltaBaselinePath, + writeGasDeltaBaselinePath, + }; +} + +async function compareWithReport(currentReport, comparePath) { + const baselineText = await readFile(path.resolve(comparePath), 'utf8'); + const baseline = JSON.parse(baselineText); + + const baselineByFixture = new Map(); + for (const report of baseline.fixtureReports ?? []) { + baselineByFixture.set(`${report.suite}:${report.fixtureName}`, report); + } + + const differences = []; + for (const current of currentReport.fixtureReports) { + const key = `${current.suite}:${current.fixtureName}`; + const previous = baselineByFixture.get(key); + if (!previous) { + differences.push({ + suite: current.suite, + fixtureName: current.fixtureName, + reason: 'missing in comparison report', + }); + continue; + } + + const currentSnapshot = stableFixtureSnapshot(current); + const previousSnapshot = stableFixtureSnapshot(previous); + if (currentSnapshot !== previousSnapshot) { + differences.push({ + suite: current.suite, + fixtureName: current.fixtureName, + reason: 'snapshot differs', + }); + } + } + + return { + differenceCount: differences.length, + differences, + }; +} + +function stableFixtureSnapshot(report) { + return JSON.stringify({ + match: report.match, + node: report.node, + native: report.native, + }); +} + +function bigIntAbs(value) { + return value < 0n ? -value : value; +} + +function summarizeGasTraceDeltas(fixtureReports) { + const byCounter = new Map(); + const residualByFixture = []; + const allocationByFixture = []; + const residualHistogram = new Map(); + const residualByProfile = new Map(); + let fixturesWithTrace = 0; + + for (const report of fixtureReports) { + if (!report.gasTraceDelta || typeof report.gasTraceDelta !== 'object') { + continue; + } + fixturesWithTrace += 1; + const fixtureKey = `${report.suite}:${report.fixtureName}`; + if (report.residualGasDeltaUsed !== undefined) { + const residualValue = String(report.residualGasDeltaUsed); + residualByFixture.push({ + fixture: fixtureKey, + residualGasDeltaUsed: residualValue, + }); + + const histogramEntry = residualHistogram.get(residualValue) ?? { + residualGasDeltaUsed: residualValue, + count: 0, + fixtures: [], + }; + histogramEntry.count += 1; + if (histogramEntry.fixtures.length < 6) { + histogramEntry.fixtures.push(fixtureKey); + } + residualHistogram.set(residualValue, histogramEntry); + + const profile = String(report.metadata?.executionProfile ?? 'unknown'); + const profileEntry = residualByProfile.get(profile) ?? { + executionProfile: profile, + count: 0, + signedResidual: 0n, + totalAbsResidual: 0n, + maxAbsResidual: 0n, + maxAbsFixture: null, + }; + const residualBigInt = BigInt(residualValue); + profileEntry.count += 1; + profileEntry.signedResidual += residualBigInt; + profileEntry.totalAbsResidual += bigIntAbs(residualBigInt); + if (bigIntAbs(residualBigInt) > profileEntry.maxAbsResidual) { + profileEntry.maxAbsResidual = bigIntAbs(residualBigInt); + profileEntry.maxAbsFixture = fixtureKey; + } + residualByProfile.set(profile, profileEntry); + } + if (report.allocationGasDeltaUsed !== undefined) { + allocationByFixture.push({ + fixture: fixtureKey, + allocationGasDeltaUsed: String(report.allocationGasDeltaUsed), + }); + } + for (const [counter, rawDelta] of Object.entries(report.gasTraceDelta)) { + const delta = BigInt(String(rawDelta)); + const current = byCounter.get(counter) ?? { + counter, + signedDelta: 0n, + totalAbsDelta: 0n, + maxAbsDelta: 0n, + maxAbsFixture: null, + }; + current.signedDelta += delta; + current.totalAbsDelta += bigIntAbs(delta); + if (bigIntAbs(delta) > current.maxAbsDelta) { + current.maxAbsDelta = bigIntAbs(delta); + current.maxAbsFixture = fixtureKey; + } + byCounter.set(counter, current); + } + } + + if (fixturesWithTrace === 0) { + return null; + } + + const counters = [...byCounter.values()] + .sort((left, right) => { + if (left.totalAbsDelta === right.totalAbsDelta) { + return left.counter.localeCompare(right.counter); + } + return left.totalAbsDelta > right.totalAbsDelta ? -1 : 1; + }) + .map((entry) => ({ + counter: entry.counter, + signedDelta: entry.signedDelta.toString(), + totalAbsDelta: entry.totalAbsDelta.toString(), + maxAbsDelta: entry.maxAbsDelta.toString(), + maxAbsFixture: entry.maxAbsFixture, + })); + + const topResiduals = residualByFixture + .map((entry) => ({ + fixture: entry.fixture, + residualGasDeltaUsed: entry.residualGasDeltaUsed, + absResidualGasDeltaUsed: bigIntAbs( + BigInt(entry.residualGasDeltaUsed), + ).toString(), + })) + .sort((left, right) => { + const leftAbs = BigInt(left.absResidualGasDeltaUsed); + const rightAbs = BigInt(right.absResidualGasDeltaUsed); + if (leftAbs === rightAbs) { + return left.fixture.localeCompare(right.fixture); + } + return leftAbs > rightAbs ? -1 : 1; + }) + .slice(0, 10); + + const topAllocationGasDeltas = allocationByFixture + .map((entry) => ({ + fixture: entry.fixture, + allocationGasDeltaUsed: entry.allocationGasDeltaUsed, + absAllocationGasDeltaUsed: bigIntAbs( + BigInt(entry.allocationGasDeltaUsed), + ).toString(), + })) + .sort((left, right) => { + const leftAbs = BigInt(left.absAllocationGasDeltaUsed); + const rightAbs = BigInt(right.absAllocationGasDeltaUsed); + if (leftAbs === rightAbs) { + return left.fixture.localeCompare(right.fixture); + } + return leftAbs > rightAbs ? -1 : 1; + }) + .slice(0, 10); + + const residualSignatures = [...residualHistogram.values()] + .sort((left, right) => { + if (left.count === right.count) { + const leftResidual = BigInt(left.residualGasDeltaUsed); + const rightResidual = BigInt(right.residualGasDeltaUsed); + if (leftResidual === rightResidual) { + return 0; + } + return rightResidual > leftResidual ? 1 : -1; + } + return right.count - left.count; + }) + .map((entry) => ({ + residualGasDeltaUsed: entry.residualGasDeltaUsed, + count: entry.count, + fixtures: entry.fixtures, + })); + + const residualProfiles = [...residualByProfile.values()] + .sort((left, right) => { + if (left.totalAbsResidual === right.totalAbsResidual) { + return left.executionProfile.localeCompare(right.executionProfile); + } + return left.totalAbsResidual > right.totalAbsResidual ? -1 : 1; + }) + .map((entry) => ({ + executionProfile: entry.executionProfile, + count: entry.count, + signedResidual: entry.signedResidual.toString(), + totalAbsResidual: entry.totalAbsResidual.toString(), + maxAbsResidual: entry.maxAbsResidual.toString(), + maxAbsFixture: entry.maxAbsFixture, + })); + + return { + fixturesWithTrace, + counterCount: counters.length, + counters, + topAllocationGasDeltas, + topResiduals, + residualSignatures, + residualProfiles, + }; +} + +function buildGasDeltaBaseline(report) { + const entries = report.fixtureReports + .map((fixtureReport) => ({ + suite: fixtureReport.suite, + fixtureName: fixtureReport.fixtureName, + gasDeltaUsed: fixtureReport.gasDeltaUsed, + gasDeltaRemaining: fixtureReport.gasDeltaRemaining, + })) + .sort((left, right) => { + const leftKey = `${left.suite}:${left.fixtureName}`; + const rightKey = `${right.suite}:${right.fixtureName}`; + return leftKey.localeCompare(rightKey); + }); + + return { + version: 1, + entries, + }; +} + +async function loadGasDeltaBaselineMap(baselinePath) { + const baselineText = await readFile(path.resolve(baselinePath), 'utf8'); + const baseline = JSON.parse(baselineText); + const baselineEntries = Array.isArray(baseline.entries) + ? baseline.entries + : []; + const lookup = new Map(); + for (const entry of baselineEntries) { + lookup.set(`${entry.suite}:${entry.fixtureName}`, { + gasDeltaUsed: String(entry.gasDeltaUsed), + gasDeltaRemaining: String(entry.gasDeltaRemaining), + }); + } + return lookup; +} + +async function compareGasDeltaBaseline(currentReport, baselinePath) { + const baselineText = await readFile(path.resolve(baselinePath), 'utf8'); + const baseline = JSON.parse(baselineText); + const baselineEntries = Array.isArray(baseline.entries) + ? baseline.entries + : []; + + const baselineByFixture = new Map(); + for (const entry of baselineEntries) { + baselineByFixture.set(`${entry.suite}:${entry.fixtureName}`, entry); + } + + const differences = []; + for (const fixtureReport of currentReport.fixtureReports) { + const key = `${fixtureReport.suite}:${fixtureReport.fixtureName}`; + const expected = baselineByFixture.get(key); + if (!expected) { + differences.push({ + suite: fixtureReport.suite, + fixtureName: fixtureReport.fixtureName, + reason: 'missing fixture in gas delta baseline', + }); + continue; + } + if ( + String(expected.gasDeltaUsed) !== String(fixtureReport.gasDeltaUsed) || + String(expected.gasDeltaRemaining) !== + String(fixtureReport.gasDeltaRemaining) + ) { + differences.push({ + suite: fixtureReport.suite, + fixtureName: fixtureReport.fixtureName, + reason: 'gas delta mismatch', + expected: { + gasDeltaUsed: String(expected.gasDeltaUsed), + gasDeltaRemaining: String(expected.gasDeltaRemaining), + }, + actual: { + gasDeltaUsed: String(fixtureReport.gasDeltaUsed), + gasDeltaRemaining: String(fixtureReport.gasDeltaRemaining), + }, + }); + } + } + + return { + differenceCount: differences.length, + differences, + }; +} + +await main(); diff --git a/tools/quickjs-native-harness/scripts/test.sh b/tools/quickjs-native-harness/scripts/test.sh index 0b61b1f..60440b5 100755 --- a/tools/quickjs-native-harness/scripts/test.sh +++ b/tools/quickjs-native-harness/scripts/test.sh @@ -14,6 +14,9 @@ fi HOST_MANIFEST_HEX="$(tr -d '\r\n' < "${REPO_ROOT}/libs/test-harness/fixtures/abi-manifest/host-v1.bytes.hex")" HOST_MANIFEST_HASH="$(tr -d '\r\n' < "${REPO_ROOT}/libs/test-harness/fixtures/abi-manifest/host-v1.hash")" COMMON_ARGS=(--abi-manifest-hex "${HOST_MANIFEST_HEX}" --abi-manifest-hash "${HOST_MANIFEST_HASH}") +HOST_V2_MANIFEST_HEX="$(tr -d '\r\n' < "${REPO_ROOT}/libs/test-harness/fixtures/abi-manifest/host-v2.bytes.hex")" +HOST_V2_MANIFEST_HASH="$(tr -d '\r\n' < "${REPO_ROOT}/libs/test-harness/fixtures/abi-manifest/host-v2.hash")" +COMMON_ARGS_V2=(--abi-manifest-hex "${HOST_V2_MANIFEST_HEX}" --abi-manifest-hash "${HOST_V2_MANIFEST_HASH}") BAD_MANIFEST_HASH="0000000000000000000000000000000000000000000000000000000000000000" SHA_EMPTY="e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855" SHA_ABC="ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad" @@ -61,6 +64,23 @@ assert_host_call() { fi } +assert_output_v2() { + local name="$1" + local code="$2" + local expected="$3" + shift 3 + + local output + output="$("${BIN}" "${COMMON_ARGS_V2[@]}" "$@" --eval "${code}" || true)" + + if [[ "${output}" != "${expected}" ]]; then + echo "Harness output mismatch for '${name}'" >&2 + echo " expected: ${expected}" >&2 + echo " actual: ${output}" >&2 + exit 1 + fi +} + assert_sha() { local name="$1" local hex="$2" @@ -365,6 +385,7 @@ assert_output "Function ctor via arrow constructor" "(() => { const RealFunction assert_output "Function ctor via generator constructor" "(() => { const GenFunction = (function* () {}).constructor; return GenFunction('return 5')(); })()" "ERROR TypeError: Function constructor is disabled in deterministic mode" assert_output "RegExp constructor disabled" "new RegExp('a')" "ERROR TypeError: RegExp is disabled in deterministic mode" assert_output "RegExp literal disabled" "'abc'.match(/a/)" "ERROR TypeError: RegExp is disabled in deterministic mode" +assert_output "RegExp compat profile enabled" "'abc'.match(/a/) !== null" "RESULT true" --execution-profile compat-general-v1 assert_output "Proxy disabled" "new Proxy({}, {})" "ERROR TypeError: Proxy is disabled in deterministic mode" assert_output "Math.random disabled" "Math.random()" "ERROR TypeError: Math.random is disabled in deterministic mode" assert_output "ArrayBuffer disabled" "new ArrayBuffer(4)" "ERROR TypeError: ArrayBuffer is disabled in deterministic mode" @@ -392,16 +413,24 @@ assert_output "JSON.stringify invalid key" "(() => { const key = '\\ud800'; retu assert_output "JSON.stringify unsupported type" "JSON.stringify({ x: undefined })" "ERROR TypeError: JSON.stringify only supports null, booleans, strings, finite numbers, arrays, and plain objects" assert_output "JSON.stringify sparse array ignores prototype getters" "(() => { let getterCalls = 0; Object.defineProperty(Array.prototype, 0, { get() { getterCalls += 1; return 1; }, configurable: true }); try { return [JSON.stringify([,]), getterCalls]; } finally { delete Array.prototype[0]; } })()" "RESULT [\"[null]\",0]" assert_output "Array.sort disabled" "[3, 1, 2].sort()" "ERROR TypeError: Array.prototype.sort is disabled in deterministic mode" +assert_output "Array.sort compat-general stable" "(() => { const records = [{ id: 'a', group: 1 }, { id: 'b', group: 1 }, { id: 'c', group: 2 }, { id: 'd', group: 1 }]; records.sort((left, right) => left.group - right.group); return records.map((record) => record.id).join(','); })()" "RESULT \"a,b,d,c\"" --execution-profile compat-general-v1 assert_output "Date missing" "typeof Date" "RESULT \"undefined\"" assert_output "Timers missing" "typeof setTimeout" "RESULT \"undefined\"" assert_output "Promise disabled" "Promise.resolve(1)" "ERROR TypeError: Promise is disabled in deterministic mode" assert_output "queueMicrotask missing" "typeof queueMicrotask" "RESULT \"undefined\"" +assert_output "Promise compat-general enabled" "Promise.resolve(1).then((value) => value + 1)" "RESULT 2" --execution-profile compat-general-v1 +assert_output "queueMicrotask compat-general enabled" "(() => { const events = []; queueMicrotask(() => events.push('a')); queueMicrotask(() => events.push('b')); return Promise.resolve().then(() => events.join(',')); })()" "RESULT \"a,b\"" --execution-profile compat-general-v1 +assert_output "console compat-general enabled" "(() => { console.log('hello', 7); return null; })()" "RESULT null" --execution-profile compat-general-v1 +assert_output "Promise compat-general gas+tape" "(() => Promise.resolve(40).then((value) => value + 2))()" "RESULT 42 GAS remaining=49872 used=128 TAPE []" --execution-profile compat-general-v1 --gas-limit 50000 --report-gas --report-tape +assert_output "queueMicrotask host-call gas+tape" "(() => { queueMicrotask(() => Host.v1.emit({ phase: 'microtask' })); return Promise.resolve({ ok: true }); })()" "RESULT {\"ok\":true} GAS remaining=49832 used=168 TAPE [{\"fnId\":3,\"reqLen\":18,\"respLen\":12,\"units\":0,\"gasPre\":\"23\",\"gasPost\":\"0\",\"isError\":false,\"chargeFailed\":false,\"reqHash\":\"7c833f34b57bfcb9b78c49448e0506baec6e0cc31aecf5af02f6a8f24bb53fec\",\"respHash\":\"d4a80d0e37c72d337ea29cff53628612f13bd4d5269b86f393a02759d60307c0\"}]" --execution-profile compat-general-v1 --gas-limit 50000 --report-gas --report-tape +assert_output "Promise rejection deterministic error" "(() => Promise.reject(new Error('async-failure')))()" "ERROR Error: async-failure GAS remaining=49913 used=87 TAPE []" --execution-profile compat-general-v1 --gas-limit 50000 --report-gas --report-tape assert_output "Host descriptor" "${host_descriptor_js}" "RESULT {\"configurable\":false,\"enumerable\":false,\"writable\":false,\"hostType\":\"object\",\"v1Type\":\"object\",\"v1NullProto\":true}" assert_output "capability snapshot" "${capability_snapshot_js}" "RESULT {\"eval\":{\"ok\":false,\"error\":\"TypeError: eval is disabled in deterministic mode\"},\"Function\":{\"ok\":false,\"error\":\"TypeError: Function is disabled in deterministic mode\"},\"RegExp\":{\"ok\":false,\"error\":\"TypeError: RegExp is disabled in deterministic mode\"},\"Proxy\":{\"ok\":false,\"error\":\"TypeError: Proxy is disabled in deterministic mode\"},\"Promise\":{\"ok\":false,\"error\":\"TypeError: Promise is disabled in deterministic mode\"},\"MathRandom\":{\"ok\":false,\"error\":\"TypeError: Math.random is disabled in deterministic mode\"},\"Date\":{\"ok\":true,\"value\":\"undefined\"},\"setTimeout\":{\"ok\":true,\"value\":\"undefined\"},\"ArrayBuffer\":{\"ok\":false,\"error\":\"TypeError: ArrayBuffer is disabled in deterministic mode\"},\"SharedArrayBuffer\":{\"ok\":false,\"error\":\"TypeError: SharedArrayBuffer is disabled in deterministic mode\"},\"DataView\":{\"ok\":false,\"error\":\"TypeError: DataView is disabled in deterministic mode\"},\"Uint8Array\":{\"ok\":false,\"error\":\"TypeError: Typed arrays are disabled in deterministic mode\"},\"Atomics\":{\"ok\":false,\"error\":\"TypeError: Atomics is disabled in deterministic mode\"},\"WebAssembly\":{\"ok\":false,\"error\":\"TypeError: WebAssembly is disabled in deterministic mode\"},\"consoleLog\":{\"ok\":false,\"error\":\"TypeError: console is disabled in deterministic mode\"},\"print\":{\"ok\":false,\"error\":\"TypeError: print is disabled in deterministic mode\"},\"globalOrder\":{\"ok\":true,\"value\":[\"console\",\"print\",\"Host\"]},\"hostImmutable\":{\"ok\":true,\"value\":{\"sameRef\":true,\"hasV1\":true,\"added\":false,\"desc\":{\"value\":{},\"writable\":false,\"enumerable\":false,\"configurable\":false},\"protoNull\":true,\"v1ProtoNull\":true,\"hostIsExtensible\":false,\"hostV1Extensible\":false,\"overwrite\":{\"same\":true,\"threw\":true,\"writable\":false,\"configurable\":false}}}}" assert_output "ergonomic globals" "${ergonomic_globals_js}" "RESULT {\"document\":{\"value\":\"foo\",\"canonical\":\"bar\",\"desc\":{\"writable\":false,\"enumerable\":false,\"configurable\":false},\"canonicalDesc\":{\"writable\":false,\"enumerable\":false,\"configurable\":false},\"extensible\":false},\"context\":{\"event\":{\"foo\":1},\"eventCanonical\":{\"bar\":true},\"steps\":[\"s1\",\"s2\"],\"currentContract\":{\"id\":\"contract-1\"},\"currentContractCanonical\":{\"id\":{\"value\":\"contract-1\"}},\"frozen\":{\"event\":true,\"eventCanonical\":true,\"steps\":true,\"currentContract\":true,\"currentContractCanonical\":true}}}" --context-blob-hex "${CONTEXT_BLOB_HEX}" assert_output "Host.v1 document.get ok" "Host.v1.document.get('foo')" "RESULT \"foo\"" assert_output "Host.v1 document.getCanonical ok" "Host.v1.document.getCanonical('bar')" "RESULT \"bar\"" assert_output "Host.v1 emit" "Host.v1.emit({ a: 1 })" "RESULT null" +assert_output_v2 "Host.v2 bytes roundtrip" "(() => { const payload = Host.v2.document.get('bytes/payload'); Host.v2.emit(payload); return [payload.byteLength, payload[0], payload[payload.byteLength - 1]]; })()" "RESULT [4,222,239]" --execution-profile compat-binary-v1 assert_output "Host.v1 document missing" "Host.v1.document.get('missing')" "ERROR HostError: host/not_found" assert_output "Host.v1 document arg type" "Host.v1.document.get(123)" "ERROR TypeError: Host.v1.document.get argument 1 must be a string" assert_output "Host.v1 document arg utf8 limit" "Host.v1.document.get('x'.repeat(2050))" "ERROR TypeError: Host.v1.document.get argument 1 exceeds utf8 limit (2050 > 2048)" @@ -427,5 +456,16 @@ echo "Running host gas suite" node "${SCRIPT_DIR}/host-gas.mjs" echo "Running DV parity suite" node "${SCRIPT_DIR}/dv-parity.mjs" +echo "Running binary library parity suite" +node "${SCRIPT_DIR}/binary-library-parity.mjs" +echo "Running module-pack parity suite" +node "${SCRIPT_DIR}/module-pack-parity.mjs" +if [[ "${NATIVE_PARITY_STRICT:-0}" == "1" ]]; then + echo "Running cross-runtime strict parity report suite" + node "${SCRIPT_DIR}/parity-report.mjs" --assert-match +else + echo "Running cross-runtime diagnostic parity report suite" + node "${SCRIPT_DIR}/parity-report.mjs" +fi echo "quickjs-native-harness test passed" diff --git a/tools/quickjs-native-harness/src/harness.c b/tools/quickjs-native-harness/src/harness.c index 053cefa..43a2a7e 100644 --- a/tools/quickjs-native-harness/src/harness.c +++ b/tools/quickjs-native-harness/src/harness.c @@ -3,6 +3,7 @@ #include "quickjs-internal.h" #include #include +#include #include #include #include @@ -16,6 +17,7 @@ typedef struct { HostStubMode mode; int trigger_reentrancy; int trigger_exception; + int use_dv2_codec; } HostStubConfig; typedef struct { @@ -27,11 +29,19 @@ typedef struct { typedef struct { const char *code; + const char *module_pack_json; + const char *module_pack_file; + const char *module_entry_specifier; + const char *module_entry_export; uint64_t gas_limit; int report_gas; int report_trace; + int report_tape; + int report_charge_tape; + uint32_t charge_tape_capacity; const char *dump_global; int dv_encode; + int parity_eval; const char *dv_decode_hex; const char *abi_manifest_hex; const char *abi_manifest_file; @@ -47,6 +57,7 @@ typedef struct { int host_call_parse_envelope; uint32_t host_call_max_units; int host_call_max_units_provided; + const char *execution_profile; } HarnessOptions; typedef struct { @@ -60,9 +71,44 @@ typedef struct { size_t count; } HostErrorTable; +typedef struct { + char *specifier; + char *source; + size_t source_len; +} ModulePackEntry; + +typedef struct { + ModulePackEntry *entries; + uint32_t entry_count; +} ModulePack; + static int print_exception(JSContext *ctx, const HarnessOptions *options); static void free_runtime(HarnessRuntime *runtime); static int run_sha256(const HarnessOptions *options); +static int eval_module_pack(HarnessRuntime *runtime, const HarnessOptions *options); + +static uint32_t deterministic_feature_flags_for_profile(const char *profile) { + if (!profile || strcmp(profile, "baseline-v1") == 0) { + return 0; + } + if (strcmp(profile, "compat-regexp-v1") == 0) { + return JS_DETERMINISTIC_FEATURE_REGEXP; + } + if (strcmp(profile, "compat-general-v1") == 0) { + return JS_DETERMINISTIC_FEATURE_REGEXP | + JS_DETERMINISTIC_FEATURE_PROMISE_JOBS | + JS_DETERMINISTIC_FEATURE_CONSOLE_SHIM | + JS_DETERMINISTIC_FEATURE_STABLE_SORT; + } + if (strcmp(profile, "compat-binary-v1") == 0) { + return JS_DETERMINISTIC_FEATURE_REGEXP | + JS_DETERMINISTIC_FEATURE_PROMISE_JOBS | + JS_DETERMINISTIC_FEATURE_CONSOLE_SHIM | + JS_DETERMINISTIC_FEATURE_STABLE_SORT | + JS_DETERMINISTIC_FEATURE_TYPED_ARRAYS; + } + return UINT32_MAX; +} static int hex_value(char c) { if (c >= '0' && c <= '9') { @@ -137,6 +183,282 @@ static int parse_hex_string(const char *hex, uint8_t **out, size_t *out_len) { return 0; } +static int manifest_uses_host_v2(const uint8_t *bytes, size_t len) { + static const uint8_t needle[] = {'H', 'o', 's', 't', '.', 'v', '2'}; + if (!bytes || len < sizeof(needle)) { + return 0; + } + for (size_t i = 0; i + sizeof(needle) <= len; i++) { + if (memcmp(bytes + i, needle, sizeof(needle)) == 0) { + return 1; + } + } + return 0; +} + +static char *copy_cstring_len(const char *value, size_t length) { + char *out = malloc(length + 1); + if (!out) { + return NULL; + } + memcpy(out, value, length); + out[length] = '\0'; + return out; +} + +static char *hex_bytes(const uint8_t *bytes, size_t length) { + static const char *HEX = "0123456789abcdef"; + char *out; + + if (length > 0 && !bytes) { + return NULL; + } + + out = malloc((length * 2) + 1); + if (!out) { + return NULL; + } + + for (size_t i = 0; i < length; i++) { + out[i * 2] = HEX[(bytes[i] >> 4) & 0x0f]; + out[i * 2 + 1] = HEX[bytes[i] & 0x0f]; + } + out[length * 2] = '\0'; + return out; +} + +static int js_set_prop(JSContext *ctx, JSValue obj, const char *name, JSValue val) { + if (JS_IsException(val)) { + return -1; + } + if (JS_DefinePropertyValueStr(ctx, obj, name, val, JS_PROP_C_W_E) < 0) { + JS_FreeValue(ctx, val); + return -1; + } + return 0; +} + +static void free_module_pack(ModulePack *pack) { + if (!pack) { + return; + } + + if (pack->entries) { + for (uint32_t i = 0; i < pack->entry_count; i++) { + free(pack->entries[i].specifier); + free(pack->entries[i].source); + } + free(pack->entries); + } + pack->entries = NULL; + pack->entry_count = 0; +} + +static ModulePackEntry *find_module_pack_entry(ModulePack *pack, const char *specifier) { + if (!pack || !specifier) { + return NULL; + } + + for (uint32_t i = 0; i < pack->entry_count; i++) { + if (strcmp(pack->entries[i].specifier, specifier) == 0) { + return &pack->entries[i]; + } + } + return NULL; +} + +static int parse_module_pack_json(JSContext *ctx, const char *module_pack_json, ModulePack *out_pack) { + JSValue parsed = JS_UNDEFINED; + JSValue length_value = JS_UNDEFINED; + uint32_t module_count = 0; + + memset(out_pack, 0, sizeof(*out_pack)); + + parsed = JS_ParseJSON(ctx, module_pack_json, strlen(module_pack_json), ""); + if (JS_IsException(parsed)) { + goto fail; + } + + if (!JS_IsArray(ctx, parsed)) { + JS_ThrowTypeError(ctx, "module pack json must be an array"); + goto fail; + } + + length_value = JS_GetPropertyStr(ctx, parsed, "length"); + if (JS_IsException(length_value)) { + goto fail; + } + + if (JS_ToUint32(ctx, &module_count, length_value) != 0) { + goto fail; + } + JS_FreeValue(ctx, length_value); + length_value = JS_UNDEFINED; + + if (module_count == 0) { + JS_ThrowTypeError(ctx, "module pack must contain at least one module"); + goto fail; + } + + out_pack->entries = calloc(module_count, sizeof(*out_pack->entries)); + if (!out_pack->entries) { + JS_ThrowOutOfMemory(ctx); + goto fail; + } + out_pack->entry_count = module_count; + + for (uint32_t i = 0; i < module_count; i++) { + JSValue item = JS_GetPropertyUint32(ctx, parsed, i); + JSValue specifier_value = JS_UNDEFINED; + JSValue source_value = JS_UNDEFINED; + const char *specifier_cstr = NULL; + const char *source_cstr = NULL; + size_t source_len = 0; + + if (JS_IsException(item)) { + goto fail; + } + if (!JS_IsObject(item)) { + JS_FreeValue(ctx, item); + JS_ThrowTypeError(ctx, "module pack entry must be an object"); + goto fail; + } + + specifier_value = JS_GetPropertyStr(ctx, item, "specifier"); + source_value = JS_GetPropertyStr(ctx, item, "source"); + if (JS_IsException(specifier_value) || JS_IsException(source_value)) { + JS_FreeValue(ctx, specifier_value); + JS_FreeValue(ctx, source_value); + JS_FreeValue(ctx, item); + goto fail; + } + + specifier_cstr = JS_ToCString(ctx, specifier_value); + source_cstr = JS_ToCStringLen(ctx, &source_len, source_value); + if (!specifier_cstr || !source_cstr) { + JS_FreeCString(ctx, specifier_cstr); + JS_FreeCString(ctx, source_cstr); + JS_FreeValue(ctx, specifier_value); + JS_FreeValue(ctx, source_value); + JS_FreeValue(ctx, item); + goto fail; + } + + out_pack->entries[i].specifier = copy_cstring_len(specifier_cstr, strlen(specifier_cstr)); + out_pack->entries[i].source = copy_cstring_len(source_cstr, source_len); + out_pack->entries[i].source_len = source_len; + + JS_FreeCString(ctx, specifier_cstr); + JS_FreeCString(ctx, source_cstr); + JS_FreeValue(ctx, specifier_value); + JS_FreeValue(ctx, source_value); + JS_FreeValue(ctx, item); + + if (!out_pack->entries[i].specifier || !out_pack->entries[i].source) { + JS_ThrowOutOfMemory(ctx); + goto fail; + } + } + + JS_FreeValue(ctx, parsed); + return 0; + +fail: + if (!JS_IsUndefined(length_value)) { + JS_FreeValue(ctx, length_value); + } + if (!JS_IsUndefined(parsed)) { + JS_FreeValue(ctx, parsed); + } + free_module_pack(out_pack); + return -1; +} + +static JSModuleDef *module_pack_loader(JSContext *ctx, + const char *module_name, + void *opaque, + JSValueConst attributes) { + ModulePack *pack = (ModulePack *)opaque; + ModulePackEntry *entry = find_module_pack_entry(pack, module_name); + JSValue module_obj = JS_UNDEFINED; + + (void)attributes; + + if (!entry) { + JS_ThrowReferenceError(ctx, "ModuleResolutionError: module specifier not found: %s", module_name); + return NULL; + } + + module_obj = JS_Eval(ctx, + entry->source, + entry->source_len, + entry->specifier, + JS_EVAL_TYPE_MODULE | JS_EVAL_FLAG_COMPILE_ONLY); + if (JS_IsException(module_obj)) { + return NULL; + } + + JSModuleDef *module_def = (JSModuleDef *)JS_VALUE_GET_PTR(module_obj); + JS_FreeValue(ctx, module_obj); + return module_def; +} + +static char *escape_js_string(const char *input) { + size_t needed = 2; + for (const unsigned char *p = (const unsigned char *)input; *p; p++) { + switch (*p) { + case '\\': + case '"': + case '\n': + case '\r': + case '\t': + needed += 2; + break; + default: + needed += 1; + break; + } + } + + char *out = malloc(needed + 1); + if (!out) { + return NULL; + } + + char *cursor = out; + *cursor++ = '"'; + for (const unsigned char *p = (const unsigned char *)input; *p; p++) { + switch (*p) { + case '\\': + *cursor++ = '\\'; + *cursor++ = '\\'; + break; + case '"': + *cursor++ = '\\'; + *cursor++ = '"'; + break; + case '\n': + *cursor++ = '\\'; + *cursor++ = 'n'; + break; + case '\r': + *cursor++ = '\\'; + *cursor++ = 'r'; + break; + case '\t': + *cursor++ = '\\'; + *cursor++ = 't'; + break; + default: + *cursor++ = (char)*p; + break; + } + } + *cursor++ = '"'; + *cursor = '\0'; + return out; +} + static void free_default_host_errors(JSContext *ctx, HostErrorTable *table) { if (!table) { return; @@ -192,7 +514,8 @@ static uint32_t harness_manifest_host_call(JSContext *ctx, const uint8_t *req_ptr, uint32_t req_len, uint8_t *resp_ptr, - uint32_t resp_capacity) { + uint32_t resp_capacity, + int use_dv2_codec) { JSValue req = JS_UNDEFINED; JSValue arg0 = JS_UNDEFINED; JSValue envelope = JS_UNDEFINED; @@ -203,7 +526,9 @@ static uint32_t harness_manifest_host_call(JSContext *ctx, const char *error_code = NULL; uint32_t resp_len = JS_HOST_CALL_TRANSPORT_ERROR; - req = JS_DecodeDV(ctx, req_ptr, req_len, &JS_DV_LIMIT_DEFAULTS); + req = use_dv2_codec + ? JS_DecodeDV2(ctx, req_ptr, req_len, &JS_DV_LIMIT_DEFAULTS) + : JS_DecodeDV(ctx, req_ptr, req_len, &JS_DV_LIMIT_DEFAULTS); if (JS_IsException(req)) { goto done; } @@ -237,19 +562,29 @@ static uint32_t harness_manifest_host_call(JSContext *ctx, error_code = "LIMIT_EXCEEDED"; units = 3; } - JS_FreeCString(ctx, path); - if (error_code) { + if (!error_code && strcmp(path, "bytes/payload") == 0) { + const uint8_t payload_dv2[] = {0x44, 0xde, 0xad, 0xbe, 0xef}; + ok_val = JS_DecodeDV2(ctx, payload_dv2, sizeof(payload_dv2), &JS_DV_LIMIT_DEFAULTS); + if (JS_IsException(ok_val)) { + JS_FreeCString(ctx, path); + goto done; + } + units = 4; + } else if (error_code) { err_obj = JS_NewObjectProto(ctx, JS_NULL); if (JS_IsException(err_obj)) { + JS_FreeCString(ctx, path); goto done; } if (JS_SetPropertyStr(ctx, err_obj, "code", JS_NewString(ctx, error_code)) < 0) { + JS_FreeCString(ctx, path); goto done; } } else { ok_val = JS_DupValue(ctx, arg0); } + JS_FreeCString(ctx, path); } else if (fn_id == 3) { ok_val = JS_NULL; units = 0; @@ -273,7 +608,8 @@ static uint32_t harness_manifest_host_call(JSContext *ctx, goto done; } - if (JS_EncodeDV(ctx, envelope, &JS_DV_LIMIT_DEFAULTS, &resp) != 0) { + if ((use_dv2_codec ? JS_EncodeDV2(ctx, envelope, &JS_DV_LIMIT_DEFAULTS, &resp) + : JS_EncodeDV(ctx, envelope, &JS_DV_LIMIT_DEFAULTS, &resp)) != 0) { goto done; } @@ -337,7 +673,13 @@ static uint32_t harness_host_call(JSContext *ctx, } if (config && config->mode == HOST_STUB_MODE_MANIFEST) { - return harness_manifest_host_call(ctx, fn_id, req_ptr, req_len, resp_ptr, resp_capacity); + return harness_manifest_host_call(ctx, + fn_id, + req_ptr, + req_len, + resp_ptr, + resp_capacity, + config->use_dv2_codec); } if (req_len > resp_capacity) { @@ -384,6 +726,31 @@ static char *read_file_to_string(const char *path) { return buffer; } +static char *dup_printf(const char *fmt, ...) { + va_list args; + va_start(args, fmt); + int needed = vsnprintf(NULL, 0, fmt, args); + va_end(args); + if (needed < 0) { + return NULL; + } + + char *out = malloc((size_t)needed + 1); + if (!out) { + return NULL; + } + + va_start(args, fmt); + int written = vsnprintf(out, (size_t)needed + 1, fmt, args); + va_end(args); + if (written < 0) { + free(out); + return NULL; + } + + return out; +} + static void print_hex_buffer(const uint8_t *data, size_t len) { for (size_t i = 0; i < len; i++) { fprintf(stdout, "%02x", data[i]); @@ -414,10 +781,16 @@ static int init_runtime(HarnessRuntime *runtime, const HarnessOptions *options) uint8_t *context_blob = NULL; size_t context_blob_len = 0; char *manifest_hex_from_file = NULL; + uint32_t feature_flags = deterministic_feature_flags_for_profile(options->execution_profile); int rc = 0; - if (JS_NewDeterministicRuntime(&runtime->rt, &runtime->ctx) != 0) { - fprintf(stderr, "init: JS_NewDeterministicRuntime failed\n"); + if (feature_flags == UINT32_MAX) { + fprintf(stderr, "Unsupported --execution-profile: %s\n", options->execution_profile); + return 2; + } + + if (JS_NewDeterministicRuntimeWithFeatures(&runtime->rt, &runtime->ctx, feature_flags) != 0) { + fprintf(stderr, "init: JS_NewDeterministicRuntimeWithFeatures failed\n"); return 1; } @@ -475,6 +848,7 @@ static int init_runtime(HarnessRuntime *runtime, const HarnessOptions *options) .context_blob = context_blob, .context_blob_size = context_blob_len, .gas_limit = options->gas_limit, + .feature_flags = feature_flags, }; if (JS_InitDeterministicContext(runtime->ctx, &init_opts) != 0) { @@ -491,6 +865,11 @@ static int init_runtime(HarnessRuntime *runtime, const HarnessOptions *options) options->host_call_hex != NULL ? HOST_STUB_MODE_ECHO : HOST_STUB_MODE_MANIFEST; runtime->host_stub.trigger_reentrancy = options->host_call_reentrant; runtime->host_stub.trigger_exception = options->host_call_exception; + runtime->host_stub.use_dv2_codec = + runtime->host_stub.mode == HOST_STUB_MODE_MANIFEST && + manifest_uses_host_v2(manifest_bytes, manifest_len) + ? 1 + : 0; runtime->host_stub_enabled = 1; if (JS_SetHostCallDispatcher(runtime->rt, harness_host_call, &runtime->host_stub) != 0) { rc = 1; @@ -619,7 +998,9 @@ static void print_trace_suffix(const HarnessOptions *options, const HarnessSnaps "},\"jsonStringify\":{\"count\":%" PRIu64 ",\"gas\":%" PRIu64 ",\"outputBytes\":%" PRIu64 ",\"values\":%" PRIu64 ",\"objectEntries\":%" PRIu64 ",\"arrayElements\":%" PRIu64 - ",\"sortComparisons\":%" PRIu64 "}", + ",\"sortComparisons\":%" PRIu64 + "},\"hostCallPre\":{\"count\":%" PRIu64 ",\"gas\":%" PRIu64 + "},\"hostCallPost\":{\"count\":%" PRIu64 ",\"gas\":%" PRIu64 "}", snapshot->trace.opcode_count, snapshot->trace.opcode_gas, snapshot->trace.builtin_array_cb_base_count, snapshot->trace.builtin_array_cb_base_gas, snapshot->trace.builtin_array_cb_per_element_count, @@ -634,11 +1015,233 @@ static void print_trace_suffix(const HarnessOptions *options, const HarnessSnaps snapshot->trace.json_stringify_value_count, snapshot->trace.json_stringify_object_entry_count, snapshot->trace.json_stringify_array_element_count, - snapshot->trace.json_stringify_sort_comparison_count); + snapshot->trace.json_stringify_sort_comparison_count, + snapshot->trace.host_call_pre_count, + snapshot->trace.host_call_pre_gas, + snapshot->trace.host_call_post_count, + snapshot->trace.host_call_post_gas); fputc('}', stdout); } +static void print_tape_suffix(JSContext *ctx, const HarnessOptions *options) { + if (!options->report_tape) { + return; + } + + JSHostTapeRecord *records = NULL; + size_t count = JS_GetHostTapeLength(ctx); + size_t to_read = 0; + JSValue arr = JS_UNDEFINED; + JSValue json = JS_UNDEFINED; + const char *json_str = NULL; + int wrote = 0; + + if (count == 0) { + fprintf(stdout, " TAPE []"); + return; + } + + to_read = count > JS_HOST_TAPE_MAX_CAPACITY ? JS_HOST_TAPE_MAX_CAPACITY : count; + records = js_mallocz(ctx, sizeof(JSHostTapeRecord) * to_read); + if (!records) { + goto done; + } + + if (JS_ReadHostTape(ctx, records, to_read, &count) != 0) { + goto done; + } + + arr = JS_NewArray(ctx); + if (JS_IsException(arr)) { + goto done; + } + + for (size_t i = 0; i < count; i++) { + JSValue obj = JS_NewObjectProto(ctx, JS_NULL); + char *req_hex = NULL; + char *resp_hex = NULL; + char gas_pre_buf[32]; + char gas_post_buf[32]; + + if (JS_IsException(obj)) { + JS_FreeValue(ctx, obj); + goto done; + } + + if (js_set_prop(ctx, obj, "fnId", JS_NewUint32(ctx, records[i].fn_id)) < 0 || + js_set_prop(ctx, obj, "reqLen", JS_NewUint32(ctx, records[i].req_len)) < 0 || + js_set_prop(ctx, obj, "respLen", JS_NewUint32(ctx, records[i].resp_len)) < 0 || + js_set_prop(ctx, obj, "units", JS_NewUint32(ctx, records[i].units)) < 0) { + JS_FreeValue(ctx, obj); + goto done; + } + + snprintf(gas_pre_buf, sizeof(gas_pre_buf), "%" PRIu64, records[i].gas_pre); + snprintf(gas_post_buf, sizeof(gas_post_buf), "%" PRIu64, records[i].gas_post); + if (js_set_prop(ctx, obj, "gasPre", JS_NewString(ctx, gas_pre_buf)) < 0 || + js_set_prop(ctx, obj, "gasPost", JS_NewString(ctx, gas_post_buf)) < 0 || + js_set_prop(ctx, obj, "isError", JS_NewBool(ctx, records[i].is_error)) < 0 || + js_set_prop(ctx, obj, "chargeFailed", JS_NewBool(ctx, records[i].charge_failed)) < 0) { + JS_FreeValue(ctx, obj); + goto done; + } + + req_hex = hex_bytes(records[i].req_hash, sizeof(records[i].req_hash)); + resp_hex = hex_bytes(records[i].resp_hash, sizeof(records[i].resp_hash)); + if (!req_hex || !resp_hex) { + free(req_hex); + free(resp_hex); + JS_FreeValue(ctx, obj); + goto done; + } + + if (js_set_prop(ctx, obj, "reqHash", JS_NewString(ctx, req_hex)) < 0 || + js_set_prop(ctx, obj, "respHash", JS_NewString(ctx, resp_hex)) < 0) { + free(req_hex); + free(resp_hex); + JS_FreeValue(ctx, obj); + goto done; + } + free(req_hex); + free(resp_hex); + + if (JS_SetPropertyUint32(ctx, arr, (uint32_t)i, obj) < 0) { + JS_FreeValue(ctx, obj); + goto done; + } + } + + json = JS_JSONStringify(ctx, arr, JS_UNDEFINED, JS_UNDEFINED); + if (JS_IsException(json)) { + goto done; + } + + json_str = JS_ToCString(ctx, json); + if (!json_str) { + goto done; + } + + fprintf(stdout, " TAPE %s", json_str); + wrote = 1; + JS_FreeCString(ctx, json_str); + +done: + if (records) { + js_free(ctx, records); + } + if (!JS_IsUndefined(arr)) { + JS_FreeValue(ctx, arr); + } + if (!JS_IsUndefined(json)) { + JS_FreeValue(ctx, json); + } + if (!wrote) { + fprintf(stdout, " TAPE []"); + } +} + +static void print_charge_tape_suffix(JSContext *ctx, const HarnessOptions *options) { + if (!options->report_charge_tape) { + return; + } + + JSGasChargeRecord *records = NULL; + size_t count = JS_GetGasChargeTapeLength(ctx); + size_t to_read = 0; + JSValue arr = JS_UNDEFINED; + JSValue json = JS_UNDEFINED; + const char *json_str = NULL; + int wrote = 0; + + if (count == 0) { + fprintf(stdout, " CHARGE_TAPE []"); + return; + } + + to_read = + count > JS_GAS_CHARGE_TAPE_MAX_CAPACITY ? JS_GAS_CHARGE_TAPE_MAX_CAPACITY : count; + records = js_mallocz(ctx, sizeof(JSGasChargeRecord) * to_read); + if (!records) { + goto done; + } + + if (JS_ReadGasChargeTape(ctx, records, to_read, &count) != 0) { + goto done; + } + + arr = JS_NewArray(ctx); + if (JS_IsException(arr)) { + goto done; + } + + for (size_t i = 0; i < count; i++) { + JSValue obj = JS_NewObjectProto(ctx, JS_NULL); + char amount_buf[32]; + char logical_units_buf[32]; + char gas_before_buf[32]; + char gas_after_buf[32]; + + if (JS_IsException(obj)) { + JS_FreeValue(ctx, obj); + goto done; + } + + if (js_set_prop(ctx, obj, "siteId", JS_NewUint32(ctx, records[i].site_id)) < 0 || + js_set_prop(ctx, obj, "kind", JS_NewUint32(ctx, records[i].kind)) < 0 || + js_set_prop(ctx, obj, "flags", JS_NewUint32(ctx, records[i].flags)) < 0) { + JS_FreeValue(ctx, obj); + goto done; + } + + snprintf(amount_buf, sizeof(amount_buf), "%" PRIu64, records[i].amount); + snprintf(logical_units_buf, sizeof(logical_units_buf), "%" PRIu64, + records[i].logical_units); + snprintf(gas_before_buf, sizeof(gas_before_buf), "%" PRIu64, records[i].gas_before); + snprintf(gas_after_buf, sizeof(gas_after_buf), "%" PRIu64, records[i].gas_after); + if (js_set_prop(ctx, obj, "amount", JS_NewString(ctx, amount_buf)) < 0 || + js_set_prop(ctx, obj, "logicalUnits", JS_NewString(ctx, logical_units_buf)) < 0 || + js_set_prop(ctx, obj, "gasBefore", JS_NewString(ctx, gas_before_buf)) < 0 || + js_set_prop(ctx, obj, "gasAfter", JS_NewString(ctx, gas_after_buf)) < 0) { + JS_FreeValue(ctx, obj); + goto done; + } + + if (JS_SetPropertyUint32(ctx, arr, (uint32_t)i, obj) < 0) { + JS_FreeValue(ctx, obj); + goto done; + } + } + + json = JS_JSONStringify(ctx, arr, JS_UNDEFINED, JS_UNDEFINED); + if (JS_IsException(json)) { + goto done; + } + + json_str = JS_ToCString(ctx, json); + if (!json_str) { + goto done; + } + + fprintf(stdout, " CHARGE_TAPE %s", json_str); + wrote = 1; + JS_FreeCString(ctx, json_str); + +done: + if (records) { + js_free(ctx, records); + } + if (!JS_IsUndefined(arr)) { + JS_FreeValue(ctx, arr); + } + if (!JS_IsUndefined(json)) { + JS_FreeValue(ctx, json); + } + if (!wrote) { + fprintf(stdout, " CHARGE_TAPE []"); + } +} + static int print_exception(JSContext *ctx, const HarnessOptions *options) { HarnessSnapshot snapshot = {0}; JSValue exception = JS_GetException(ctx); @@ -650,6 +1253,8 @@ static int print_exception(JSContext *ctx, const HarnessOptions *options) { print_gas_suffix(options, &snapshot); print_state_suffix(ctx, options); print_trace_suffix(options, &snapshot); + print_tape_suffix(ctx, options); + print_charge_tape_suffix(ctx, options); fprintf(stdout, "\n"); JS_FreeCString(ctx, msg); } else { @@ -657,6 +1262,8 @@ static int print_exception(JSContext *ctx, const HarnessOptions *options) { print_gas_suffix(options, &snapshot); print_state_suffix(ctx, options); print_trace_suffix(options, &snapshot); + print_tape_suffix(ctx, options); + print_charge_tape_suffix(ctx, options); fprintf(stdout, "\n"); } JS_FreeValue(ctx, exception); @@ -671,6 +1278,47 @@ static int run_gc_checkpoint(JSContext *ctx, const HarnessOptions *options) { return print_exception(ctx, options); } +static int drain_pending_jobs(JSRuntime *rt, JSContext *ctx, JSContext **out_error_ctx) { + while (JS_IsJobPending(rt)) { + JSContext *job_ctx = NULL; + int rc = JS_ExecutePendingJob(rt, &job_ctx); + if (rc < 0) { + if (out_error_ctx) { + *out_error_ctx = job_ctx ? job_ctx : ctx; + } + return -1; + } + } + if (out_error_ctx) { + *out_error_ctx = ctx; + } + return 0; +} + +static int resolve_promise_result(JSContext *ctx, JSValue *value) { + int state = (int)JS_PromiseState(ctx, *value); + if (state < 0) { + return 0; + } + + if (state == JS_PROMISE_PENDING) { + JS_ThrowTypeError(ctx, "promise did not settle during deterministic job drain"); + return -1; + } + + JSValue settled = JS_PromiseResult(ctx, *value); + if (state == JS_PROMISE_REJECTED) { + JS_FreeValue(ctx, *value); + *value = JS_UNDEFINED; + JS_Throw(ctx, settled); + return -1; + } + + JS_FreeValue(ctx, *value); + *value = settled; + return 0; +} + static int encode_dv_source(JSContext *ctx, const HarnessOptions *options) { if (run_gc_checkpoint(ctx, options) != 0) { return 1; @@ -876,6 +1524,8 @@ static int run_host_call(HarnessRuntime *runtime, const HarnessOptions *options) print_gas_suffix(options, &snapshot); print_state_suffix(runtime->ctx, options); print_trace_suffix(options, &snapshot); + print_tape_suffix(runtime->ctx, options); + print_charge_tape_suffix(runtime->ctx, options); fprintf(stdout, "\n"); return 1; } @@ -888,6 +1538,8 @@ static int run_host_call(HarnessRuntime *runtime, const HarnessOptions *options) print_gas_suffix(options, &snapshot); print_state_suffix(runtime->ctx, options); print_trace_suffix(options, &snapshot); + print_tape_suffix(runtime->ctx, options); + print_charge_tape_suffix(runtime->ctx, options); fprintf(stdout, "\n"); free(req_bytes); return 0; @@ -902,6 +1554,8 @@ static int run_host_call(HarnessRuntime *runtime, const HarnessOptions *options) print_gas_suffix(options, &snapshot); print_state_suffix(runtime->ctx, options); print_trace_suffix(options, &snapshot); + print_tape_suffix(runtime->ctx, options); + print_charge_tape_suffix(runtime->ctx, options); fprintf(stdout, "\n"); free(req_bytes); @@ -909,6 +1563,11 @@ static int run_host_call(HarnessRuntime *runtime, const HarnessOptions *options) } static int eval_source(JSContext *ctx, const char *code, const HarnessOptions *options) { + JSRuntime *rt = JS_GetRuntime(ctx); + JSContext *job_error_ctx = NULL; + JSDvBuffer parity_dv = {0}; + JSValue parity_decoded = JS_UNDEFINED; + if (run_gc_checkpoint(ctx, options) != 0) { return 1; } @@ -916,14 +1575,36 @@ static int eval_source(JSContext *ctx, const char *code, const HarnessOptions *o JSValue result = JS_Eval(ctx, code, strlen(code), "", JS_EVAL_TYPE_GLOBAL); if (JS_IsException(result)) { JS_FreeValue(ctx, result); - if (run_gc_checkpoint(ctx, options) != 0) { + if (!options->parity_eval && run_gc_checkpoint(ctx, options) != 0) { return 1; } return print_exception(ctx, options); } + if (drain_pending_jobs(rt, ctx, &job_error_ctx) != 0) { + JS_FreeValue(ctx, result); + return print_exception(job_error_ctx ? job_error_ctx : ctx, options); + } + + if (resolve_promise_result(ctx, &result) != 0) { + JS_FreeValue(ctx, result); + return print_exception(ctx, options); + } + + if (options->parity_eval) { + if (JS_EncodeDV(ctx, result, NULL, &parity_dv) != 0) { + JS_FreeValue(ctx, result); + return print_exception(ctx, options); + } + JS_FreeValue(ctx, result); + result = JS_UNDEFINED; + } + if (run_gc_checkpoint(ctx, options) != 0) { JS_FreeValue(ctx, result); + if (parity_dv.data) { + JS_FreeDVBuffer(ctx, &parity_dv); + } return 1; } @@ -931,8 +1612,26 @@ static int eval_source(JSContext *ctx, const char *code, const HarnessOptions *o capture_snapshot(ctx, options, &snapshot); disable_gas_metering(ctx); - JSValue json = JS_JSONStringify(ctx, result, JS_UNDEFINED, JS_UNDEFINED); - JS_FreeValue(ctx, result); + if (options->parity_eval) { + parity_decoded = JS_DecodeDV(ctx, parity_dv.data, parity_dv.length, NULL); + JS_FreeDVBuffer(ctx, &parity_dv); + parity_dv.data = NULL; + if (JS_IsException(parity_decoded)) { + return print_exception(ctx, options); + } + } + + JSValue json = JS_JSONStringify( + ctx, + options->parity_eval ? parity_decoded : result, + JS_UNDEFINED, + JS_UNDEFINED); + if (options->parity_eval) { + JS_FreeValue(ctx, parity_decoded); + parity_decoded = JS_UNDEFINED; + } else { + JS_FreeValue(ctx, result); + } if (JS_IsException(json)) { if (run_gc_checkpoint(ctx, options) != 0) { @@ -952,6 +1651,8 @@ static int eval_source(JSContext *ctx, const char *code, const HarnessOptions *o print_gas_suffix(options, &snapshot); print_state_suffix(ctx, options); print_trace_suffix(options, &snapshot); + print_tape_suffix(ctx, options); + print_charge_tape_suffix(ctx, options); fprintf(stdout, "\n"); JS_FreeCString(ctx, json_str); @@ -959,28 +1660,265 @@ static int eval_source(JSContext *ctx, const char *code, const HarnessOptions *o return 0; } +static int eval_module_pack(HarnessRuntime *runtime, const HarnessOptions *options) { + JSContext *ctx = runtime->ctx; + JSRuntime *rt = runtime->rt; + JSContext *job_error_ctx = NULL; + JSContext *error_ctx = NULL; + ModulePack pack = {0}; + JSValue module_eval = JS_UNDEFINED; + JSValue global_obj = JS_UNDEFINED; + JSValue export_value = JS_UNDEFINED; + JSValue decoded_result = JS_UNDEFINED; + JSValue json = JS_UNDEFINED; + JSDvBuffer dv = {0}; + char *module_pack_from_file = NULL; + const char *module_pack_json = options->module_pack_json; + const char *entry_specifier = options->module_entry_specifier; + const char *target_export = NULL; + const char *json_str = NULL; + char *entry_specifier_escaped = NULL; + char *entry_export_escaped = NULL; + char *wrapper_source = NULL; + JSAtom result_atom = JS_ATOM_NULL; + const char *result_global_name = "__blue_module_pack_result"; + int rc = 1; + + if (options->module_pack_file) { + module_pack_from_file = read_file_to_string(options->module_pack_file); + if (!module_pack_from_file) { + return 1; + } + module_pack_json = module_pack_from_file; + } + + target_export = (options->module_entry_export && options->module_entry_export[0] != '\0') + ? options->module_entry_export + : "default"; + + if (run_gc_checkpoint(ctx, options) != 0) { + rc = 1; + goto cleanup; + } + + if (!module_pack_json || module_pack_json[0] == '\0') { + JS_ThrowReferenceError(ctx, "ModuleEvaluationError: empty module pack json"); + goto cleanup; + } + + if (!entry_specifier || entry_specifier[0] == '\0') { + JS_ThrowReferenceError(ctx, "ModuleSpecifierNotFound: empty entry specifier"); + goto cleanup; + } + + if (parse_module_pack_json(ctx, module_pack_json, &pack) != 0) { + goto cleanup; + } + + if (!find_module_pack_entry(&pack, entry_specifier)) { + JS_ThrowReferenceError(ctx, "ModuleSpecifierNotFound: entry module not found"); + goto cleanup; + } + + if (JS_AddIntrinsicPromise(ctx) != 0) { + goto cleanup; + } + + JS_SetModuleLoaderFunc2(rt, NULL, module_pack_loader, NULL, &pack); + + entry_specifier_escaped = escape_js_string(entry_specifier); + entry_export_escaped = escape_js_string(target_export); + if (!entry_specifier_escaped || !entry_export_escaped) { + JS_ThrowOutOfMemory(ctx); + goto cleanup; + } + + wrapper_source = dup_printf( + "import * as __blue_entry_ns from %s;\n" + "if (typeof __blue_entry_ns[%s] === 'undefined') {\n" + " throw new Error('ModuleExportMissing: export not found');\n" + "}\n" + "globalThis.%s = __blue_entry_ns[%s];\n", + entry_specifier_escaped, + entry_export_escaped, + result_global_name, + entry_export_escaped); + if (!wrapper_source) { + JS_ThrowOutOfMemory(ctx); + goto cleanup; + } + + module_eval = JS_Eval(ctx, + wrapper_source, + strlen(wrapper_source), + "./__module_pack_entry__.js", + JS_EVAL_TYPE_MODULE); + if (JS_IsException(module_eval)) { + goto cleanup; + } + + if (drain_pending_jobs(rt, ctx, &job_error_ctx) != 0) { + error_ctx = job_error_ctx ? job_error_ctx : ctx; + rc = 1; + goto cleanup; + } + + global_obj = JS_GetGlobalObject(ctx); + if (JS_IsException(global_obj)) { + goto cleanup; + } + + export_value = JS_GetPropertyStr(ctx, global_obj, result_global_name); + if (JS_IsException(export_value)) { + goto cleanup; + } + if (JS_IsUndefined(export_value)) { + JS_ThrowReferenceError(ctx, "ModuleExportMissing: export not found"); + goto cleanup; + } + + if (resolve_promise_result(ctx, &export_value) != 0) { + rc = 1; + goto cleanup; + } + + result_atom = JS_NewAtom(ctx, result_global_name); + if (result_atom != JS_ATOM_NULL) { + JS_DeleteProperty(ctx, global_obj, result_atom, 0); + } + + if (JS_EncodeDV(ctx, export_value, NULL, &dv) != 0) { + goto cleanup; + } + + if (run_gc_checkpoint(ctx, options) != 0) { + rc = 1; + goto cleanup; + } + + HarnessSnapshot snapshot = {0}; + capture_snapshot(ctx, options, &snapshot); + disable_gas_metering(ctx); + + decoded_result = JS_DecodeDV(ctx, dv.data, dv.length, NULL); + if (JS_IsException(decoded_result)) { + goto cleanup; + } + + json = JS_JSONStringify(ctx, decoded_result, JS_UNDEFINED, JS_UNDEFINED); + if (JS_IsException(json)) { + goto cleanup; + } + + json_str = JS_ToCString(ctx, json); + if (!json_str) { + fprintf(stdout, "ERROR "); + print_gas_suffix(options, &snapshot); + print_state_suffix(ctx, options); + print_trace_suffix(options, &snapshot); + print_tape_suffix(ctx, options); + print_charge_tape_suffix(ctx, options); + fprintf(stdout, "\n"); + rc = 1; + goto cleanup; + } + + fprintf(stdout, "RESULT %s", json_str); + print_gas_suffix(options, &snapshot); + print_state_suffix(ctx, options); + print_trace_suffix(options, &snapshot); + print_tape_suffix(ctx, options); + print_charge_tape_suffix(ctx, options); + fprintf(stdout, "\n"); + rc = 0; + +cleanup: + if (json_str) { + JS_FreeCString(ctx, json_str); + } + if (!JS_IsUndefined(json)) { + JS_FreeValue(ctx, json); + } + if (!JS_IsUndefined(decoded_result)) { + JS_FreeValue(ctx, decoded_result); + } + if (dv.data) { + JS_FreeDVBuffer(ctx, &dv); + } + + JS_SetModuleLoaderFunc2(rt, NULL, NULL, NULL, NULL); + if (result_atom != JS_ATOM_NULL) { + JS_FreeAtom(ctx, result_atom); + } + + if (!JS_IsUndefined(export_value)) { + JS_FreeValue(ctx, export_value); + } + if (!JS_IsUndefined(global_obj)) { + JS_FreeValue(ctx, global_obj); + } + if (!JS_IsUndefined(module_eval)) { + JS_FreeValue(ctx, module_eval); + } + + if (wrapper_source) { + free(wrapper_source); + } + if (entry_specifier_escaped) { + free(entry_specifier_escaped); + } + if (entry_export_escaped) { + free(entry_export_escaped); + } + + JS_FreeContextLoadedModules(ctx); + free_module_pack(&pack); + free(module_pack_from_file); + + if (rc != 0) { + JSContext *exception_ctx = error_ctx ? error_ctx : ctx; + if (!JS_HasException(exception_ctx)) { + JS_ThrowInternalError(ctx, "ModuleEvaluationError: module-pack execution failed"); + exception_ctx = ctx; + } + return print_exception(exception_ctx, options); + } + + return 0; +} + static void print_usage(const char *prog) { fprintf(stderr, "Usage:\n" - " %s [--gas-limit ] [--report-gas] [--gas-trace] [--dump-global ] [--abi-manifest-hex | --abi-manifest-hex-file ] [--abi-manifest-hash ] [--context-blob-hex ] --eval \"\"\n" + " %s [--gas-limit ] [--report-gas] [--report-tape] [--gas-charge-tape] [--gas-charge-tape-capacity ] [--gas-trace] [--dump-global ] [--execution-profile ] [--abi-manifest-hex | --abi-manifest-hex-file ] [--abi-manifest-hash ] [--context-blob-hex ] [--parity-eval] --eval \"\"\n" + " %s [--gas-limit ] [--report-gas] [--report-tape] [--gas-charge-tape] [--gas-charge-tape-capacity ] [--gas-trace] [--execution-profile ] [--abi-manifest-hex | --abi-manifest-hex-file ] [--abi-manifest-hash ] --module-entry-specifier [--module-entry-export ] (--module-pack-json \"\" | --module-pack-file )\n" " %s --dv-encode --eval \"\"\n" " %s --dv-decode \n" - " %s --host-call [--host-fn-id ] [--host-max-request ] [--host-max-response ] [--host-max-units ] [--host-parse-envelope] [--host-reentrant] [--host-exception] [--gas-limit ] [--report-gas] [--gas-trace] [--abi-manifest-hex | --abi-manifest-hex-file ] [--abi-manifest-hash ] [--context-blob-hex ]\n" + " %s --host-call [--host-fn-id ] [--host-max-request ] [--host-max-response ] [--host-max-units ] [--host-parse-envelope] [--host-reentrant] [--host-exception] [--gas-limit ] [--report-gas] [--report-tape] [--gas-charge-tape] [--gas-charge-tape-capacity ] [--gas-trace] [--execution-profile ] [--abi-manifest-hex | --abi-manifest-hex-file ] [--abi-manifest-hash ] [--context-blob-hex ]\n" " %s --sha256-hex \n", prog, prog, prog, prog, + prog, prog); } static int parse_args(int argc, char **argv, HarnessOptions *opts) { opts->code = NULL; + opts->module_pack_json = NULL; + opts->module_pack_file = NULL; + opts->module_entry_specifier = NULL; + opts->module_entry_export = NULL; opts->gas_limit = JS_GAS_UNLIMITED; opts->report_gas = 0; opts->report_trace = 0; + opts->report_tape = 0; + opts->report_charge_tape = 0; + opts->charge_tape_capacity = 256; opts->dump_global = NULL; opts->dv_encode = 0; + opts->parity_eval = 0; opts->dv_decode_hex = NULL; opts->abi_manifest_hex = NULL; opts->abi_manifest_file = NULL; @@ -996,6 +1934,7 @@ static int parse_args(int argc, char **argv, HarnessOptions *opts) { opts->host_call_parse_envelope = 0; opts->host_call_max_units = 0; opts->host_call_max_units_provided = 0; + opts->execution_profile = "baseline-v1"; for (int i = 1; i < argc; i++) { if (strcmp(argv[i], "--eval") == 0) { @@ -1029,6 +1968,33 @@ static int parse_args(int argc, char **argv, HarnessOptions *opts) { continue; } + if (strcmp(argv[i], "--report-tape") == 0) { + opts->report_tape = 1; + continue; + } + + if (strcmp(argv[i], "--gas-charge-tape") == 0) { + opts->report_charge_tape = 1; + continue; + } + + if (strcmp(argv[i], "--gas-charge-tape-capacity") == 0) { + if (i + 1 >= argc) { + print_usage(argv[0]); + return 2; + } + const char *value = argv[++i]; + char *endptr = NULL; + errno = 0; + unsigned long parsed = strtoul(value, &endptr, 10); + if (errno != 0 || endptr == value || *endptr != '\0' || parsed > UINT32_MAX) { + fprintf(stderr, "Invalid --gas-charge-tape-capacity: %s\n", value); + return 2; + } + opts->charge_tape_capacity = (uint32_t)parsed; + continue; + } + if (strcmp(argv[i], "--gas-trace") == 0) { opts->report_trace = 1; continue; @@ -1039,6 +2005,11 @@ static int parse_args(int argc, char **argv, HarnessOptions *opts) { continue; } + if (strcmp(argv[i], "--parity-eval") == 0) { + opts->parity_eval = 1; + continue; + } + if (strcmp(argv[i], "--dv-decode") == 0) { if (i + 1 >= argc) { print_usage(argv[0]); @@ -1084,6 +2055,15 @@ static int parse_args(int argc, char **argv, HarnessOptions *opts) { continue; } + if (strcmp(argv[i], "--execution-profile") == 0) { + if (i + 1 >= argc) { + print_usage(argv[0]); + return 2; + } + opts->execution_profile = argv[++i]; + continue; + } + if (strcmp(argv[i], "--sha256-hex") == 0) { if (i + 1 >= argc) { print_usage(argv[0]); @@ -1102,6 +2082,42 @@ static int parse_args(int argc, char **argv, HarnessOptions *opts) { continue; } + if (strcmp(argv[i], "--module-pack-json") == 0) { + if (i + 1 >= argc) { + print_usage(argv[0]); + return 2; + } + opts->module_pack_json = argv[++i]; + continue; + } + + if (strcmp(argv[i], "--module-pack-file") == 0) { + if (i + 1 >= argc) { + print_usage(argv[0]); + return 2; + } + opts->module_pack_file = argv[++i]; + continue; + } + + if (strcmp(argv[i], "--module-entry-specifier") == 0) { + if (i + 1 >= argc) { + print_usage(argv[0]); + return 2; + } + opts->module_entry_specifier = argv[++i]; + continue; + } + + if (strcmp(argv[i], "--module-entry-export") == 0) { + if (i + 1 >= argc) { + print_usage(argv[0]); + return 2; + } + opts->module_entry_export = argv[++i]; + continue; + } + if (strcmp(argv[i], "--host-call") == 0) { if (i + 1 >= argc) { print_usage(argv[0]); @@ -1203,9 +2219,13 @@ static int parse_args(int argc, char **argv, HarnessOptions *opts) { } const int host_call_mode = opts->host_call_hex != NULL || opts->host_call_parse_envelope; + const int module_pack_mode = opts->module_pack_json != NULL || opts->module_pack_file != NULL || + opts->module_entry_specifier != NULL || + opts->module_entry_export != NULL; if (opts->dv_decode_hex) { - if (opts->code != NULL || opts->dv_encode || host_call_mode || opts->sha256_hex) { + if (opts->code != NULL || opts->dv_encode || opts->parity_eval || host_call_mode || opts->sha256_hex || + module_pack_mode) { print_usage(argv[0]); return 2; } @@ -1213,8 +2233,8 @@ static int parse_args(int argc, char **argv, HarnessOptions *opts) { } if (opts->sha256_hex) { - if (opts->code != NULL || opts->dv_encode || opts->dv_decode_hex || - host_call_mode) { + if (opts->code != NULL || opts->dv_encode || opts->parity_eval || opts->dv_decode_hex || + host_call_mode || module_pack_mode) { print_usage(argv[0]); return 2; } @@ -1222,7 +2242,7 @@ static int parse_args(int argc, char **argv, HarnessOptions *opts) { } if (host_call_mode) { - if (opts->code != NULL || opts->dv_encode) { + if (opts->code != NULL || opts->dv_encode || opts->parity_eval || module_pack_mode) { print_usage(argv[0]); return 2; } @@ -1233,11 +2253,32 @@ static int parse_args(int argc, char **argv, HarnessOptions *opts) { return 0; } + if (module_pack_mode) { + if (opts->code != NULL || opts->dv_encode || opts->parity_eval) { + print_usage(argv[0]); + return 2; + } + if ((opts->module_pack_json != NULL) == (opts->module_pack_file != NULL)) { + print_usage(argv[0]); + return 2; + } + if (opts->module_entry_specifier == NULL) { + print_usage(argv[0]); + return 2; + } + return 0; + } + if (opts->code == NULL) { print_usage(argv[0]); return 2; } + if (opts->parity_eval && opts->dv_encode) { + print_usage(argv[0]); + return 2; + } + return 0; } @@ -1261,6 +2302,25 @@ int main(int argc, char **argv) { JS_SetGasLimit(runtime.ctx, options.gas_limit); + if (options.report_tape) { + if (JS_EnableHostTape(runtime.ctx, 64) != 0 || JS_ResetHostTape(runtime.ctx) != 0) { + fprintf(stderr, "init: failed to enable host tape\n"); + free_runtime(&runtime); + return 1; + } + } + + if (options.report_charge_tape) { + if (JS_EnableGasChargeTape(runtime.ctx, options.charge_tape_capacity) != 0 || + JS_ResetGasChargeTape(runtime.ctx) != 0) { + fprintf(stderr, "init: failed to enable gas charge tape\n"); + free_runtime(&runtime); + return 1; + } + } + + /* Keep trace counters aligned with wasm-node evaluate(): tape setup first, + then gas-trace enable/reset so setup charges are excluded from trace data. */ if (options.report_trace) { if (JS_EnableGasTrace(runtime.ctx, 1) != 0) { fprintf(stderr, "init: failed to enable gas trace\n"); @@ -1270,15 +2330,15 @@ int main(int argc, char **argv) { } int rc = 0; + const int module_pack_mode = options.module_pack_json != NULL || options.module_pack_file != NULL; if (options.dv_decode_hex) { rc = decode_dv_hex(runtime.ctx, &options); } else if (options.host_call_hex) { rc = run_host_call(&runtime, &options); + } else if (module_pack_mode) { + rc = eval_module_pack(&runtime, &options); } else { - if (run_gc_checkpoint(runtime.ctx, &options) != 0) { - free_runtime(&runtime); - return 1; - } + /* eval_source()/encode_dv_source() own their GC checkpoint sequencing. */ if (options.dv_encode) { rc = encode_dv_source(runtime.ctx, &options); } else { diff --git a/tools/release-evidence/_lib.mjs b/tools/release-evidence/_lib.mjs new file mode 100644 index 0000000..2f17473 --- /dev/null +++ b/tools/release-evidence/_lib.mjs @@ -0,0 +1,181 @@ +import { createHash, createPrivateKey, createPublicKey, sign, verify } from 'node:crypto'; +import { copyFile, mkdir, readFile, stat, writeFile } from 'node:fs/promises'; +import path from 'node:path'; + +export async function ensureDir(targetDir) { + await mkdir(targetDir, { recursive: true }); +} + +export function sha256Hex(input) { + return createHash('sha256').update(input).digest('hex'); +} + +export async function sha256FileHex(filePath) { + const content = await readFile(filePath); + return sha256Hex(content); +} + +export async function copyIntoEvidenceDir(sourcePath, targetDir, targetName) { + await ensureDir(targetDir); + const destinationPath = path.join(targetDir, targetName ?? path.basename(sourcePath)); + await copyFile(sourcePath, destinationPath); + return destinationPath; +} + +export async function createManifestEntry(filePath, evidenceRoot, category) { + const digest = await sha256FileHex(filePath); + const fileStat = await stat(filePath); + return { + category, + file: path.relative(evidenceRoot, filePath), + sha256: digest, + sizeBytes: fileStat.size, + }; +} + +export function createDetachedSignature(payloadBytes, options = {}) { + if (options.privateKeyPem) { + const key = createPrivateKey(options.privateKeyPem); + const signatureBytes = sign(null, payloadBytes, key); + return { + mode: 'ed25519', + algorithm: 'ed25519', + keyId: options.keyId ?? 'release-evidence', + signatureBase64: signatureBytes.toString('base64'), + }; + } + + return { + mode: 'digest-fallback', + algorithm: 'sha256', + keyId: options.keyId ?? 'digest-fallback', + signatureHex: sha256Hex(payloadBytes), + }; +} + +export function verifyDetachedSignature(payloadBytes, signaturePayload, options = {}) { + if (signaturePayload.mode === 'ed25519') { + if (!options.publicKeyPem) { + return { + ok: false, + reason: 'missing public key for ed25519 signature verification', + }; + } + const key = createPublicKey(options.publicKeyPem); + const signatureBytes = Buffer.from(signaturePayload.signatureBase64, 'base64'); + const isValid = verify(null, payloadBytes, key, signatureBytes); + return { + ok: isValid, + reason: isValid ? null : 'ed25519 signature mismatch', + }; + } + + const expectedDigest = sha256Hex(payloadBytes); + const isValid = signaturePayload.signatureHex === expectedDigest; + return { + ok: isValid, + reason: isValid ? null : 'sha256 digest signature mismatch', + }; +} + +export async function writeChecksumFile(filePath) { + const digest = await sha256FileHex(filePath); + const checksumPath = `${filePath}.sha256`; + await writeFile( + checksumPath, + `${digest} ${path.basename(filePath)}\n`, + 'utf8', + ); + return checksumPath; +} + +export async function writeSignatureFile(filePath, signaturePayload) { + const signaturePath = `${filePath}.sig`; + await writeFile( + signaturePath, + `${JSON.stringify(signaturePayload, null, 2)}\n`, + 'utf8', + ); + return signaturePath; +} + +export async function loadOptionalText(valueOrPath) { + if (!valueOrPath) { + return null; + } + const normalized = valueOrPath.trim(); + if (!normalized) { + return null; + } + if (normalized.includes('BEGIN') || normalized.includes('\n')) { + return normalized; + } + return readFile(path.resolve(process.cwd(), normalized), 'utf8'); +} + +export async function verifyManifestBundle(manifest, evidenceRoot, options = {}) { + const errors = []; + let verifiedCount = 0; + + for (const artifact of manifest.artifacts) { + const artifactPath = path.resolve(evidenceRoot, artifact.file); + let digest; + try { + digest = await sha256FileHex(artifactPath); + } catch (error) { + errors.push({ + type: 'missing-artifact', + file: artifact.file, + message: error instanceof Error ? error.message : String(error), + }); + continue; + } + if (digest !== artifact.sha256) { + errors.push({ + type: 'checksum-mismatch', + file: artifact.file, + expected: artifact.sha256, + actual: digest, + }); + continue; + } + + if (artifact.signatureFile) { + const signaturePath = path.resolve(evidenceRoot, artifact.signatureFile); + try { + const signaturePayload = JSON.parse(await readFile(signaturePath, 'utf8')); + const verification = verifyDetachedSignature( + await readFile(artifactPath), + signaturePayload, + options, + ); + if (!verification.ok) { + errors.push({ + type: 'signature-mismatch', + file: artifact.file, + signatureFile: artifact.signatureFile, + reason: verification.reason, + }); + continue; + } + } catch (error) { + errors.push({ + type: 'signature-read-failure', + file: artifact.file, + signatureFile: artifact.signatureFile, + message: error instanceof Error ? error.message : String(error), + }); + continue; + } + } + + verifiedCount += 1; + } + + return { + ok: errors.length === 0, + verifiedCount, + errorCount: errors.length, + errors, + }; +} diff --git a/tools/release-evidence/check-doc-links.mjs b/tools/release-evidence/check-doc-links.mjs new file mode 100644 index 0000000..30ba1f6 --- /dev/null +++ b/tools/release-evidence/check-doc-links.mjs @@ -0,0 +1,124 @@ +#!/usr/bin/env node + +import { access, readFile, readdir } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; + +const args = parseArgs(process.argv.slice(2)); +const repoRoot = process.cwd(); +const targets = + args.files.length > 0 ? args.files : await discoverDefaultTargets(repoRoot); + +const missingLinks = []; +const checkedLinks = []; + +for (const target of targets) { + const sourcePath = path.resolve(repoRoot, target); + const markdown = await readFile(sourcePath, 'utf8'); + const links = extractMarkdownLinks(markdown); + for (const link of links) { + if (isExternalOrAnchor(link.href)) { + continue; + } + const normalizedHref = normalizeHref(link.href); + const resolvedPath = path.resolve(path.dirname(sourcePath), normalizedHref); + checkedLinks.push({ + file: target, + href: link.href, + resolvedPath: path.relative(repoRoot, resolvedPath), + }); + try { + await access(resolvedPath); + } catch { + missingLinks.push({ + file: target, + href: link.href, + resolvedPath: path.relative(repoRoot, resolvedPath), + }); + } + } +} + +const output = { + checkedFileCount: targets.length, + checkedLinkCount: checkedLinks.length, + missingLinkCount: missingLinks.length, + missingLinks, +}; + +process.stdout.write(`${JSON.stringify(output, null, 2)}\n`); +if (missingLinks.length > 0) { + process.exitCode = 1; +} + +function parseArgs(argv) { + const files = []; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--file') { + const file = argv[index + 1]; + if (!file) { + throw new Error('--file requires a value'); + } + files.push(file); + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { files }; +} + +function extractMarkdownLinks(markdown) { + const links = []; + const pattern = /!?\[[^\]]*]\(([^)\s]+)(?:\s+"[^"]*")?\)/g; + let match = pattern.exec(markdown); + while (match) { + links.push({ href: match[1] }); + match = pattern.exec(markdown); + } + return links; +} + +function isExternalOrAnchor(href) { + return ( + href.startsWith('http://') || + href.startsWith('https://') || + href.startsWith('mailto:') || + href.startsWith('tel:') || + href.startsWith('#') + ); +} + +function normalizeHref(href) { + const withoutFragment = href.split('#', 1)[0]; + const withoutQuery = withoutFragment.split('?', 1)[0]; + return withoutQuery; +} + +async function discoverDefaultTargets(repoRoot) { + const docsDir = path.join(repoRoot, 'docs'); + const docsFiles = await walkMarkdownFiles(repoRoot, docsDir); + return ['README.md', ...docsFiles, 'examples/README.md']; +} + +async function walkMarkdownFiles(repoRoot, currentDir) { + const entries = await readdir(currentDir, { withFileTypes: true }); + const files = []; + + for (const entry of entries) { + const absolutePath = path.join(currentDir, entry.name); + if (entry.isDirectory()) { + files.push(...(await walkMarkdownFiles(repoRoot, absolutePath))); + continue; + } + if (entry.isFile() && entry.name.endsWith('.md')) { + files.push(path.relative(repoRoot, absolutePath)); + } + } + + return files.sort(); +} diff --git a/tools/release-evidence/check-release-doc-freshness.mjs b/tools/release-evidence/check-release-doc-freshness.mjs new file mode 100644 index 0000000..4f8489f --- /dev/null +++ b/tools/release-evidence/check-release-doc-freshness.mjs @@ -0,0 +1,93 @@ +#!/usr/bin/env node + +import { readFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { spawnSync } from 'node:child_process'; + +const args = parseArgs(process.argv.slice(2)); +const repoRoot = process.cwd(); +const reportPath = path.resolve( + repoRoot, + args.reportPath ?? 'docs/release-readiness-report.md', +); +const reportText = await readFile(reportPath, 'utf8'); + +const expectedBranch = args.expectedBranch ?? resolveCurrentBranch(repoRoot); +const expectedDate = args.expectedDate ?? new Date().toISOString().slice(0, 10); + +const branchMatch = reportText.match(/^Branch:\s*`([^`]+)`/m); +const dateMatch = reportText.match(/^Date:\s*(\d{4}-\d{2}-\d{2})/m); + +if (!branchMatch) { + throw new Error(`missing Branch line in ${path.relative(repoRoot, reportPath)}`); +} +if (!dateMatch) { + throw new Error(`missing Date line in ${path.relative(repoRoot, reportPath)}`); +} + +const actualBranch = branchMatch[1]; +const actualDate = dateMatch[1]; +const checks = { + branchMatches: actualBranch === expectedBranch, + dateMatches: actualDate === expectedDate, +}; + +const output = { + reportPath: path.relative(repoRoot, reportPath), + expected: { + branch: expectedBranch, + date: expectedDate, + }, + actual: { + branch: actualBranch, + date: actualDate, + }, + checks, +}; + +process.stdout.write(`${JSON.stringify(output, null, 2)}\n`); +if (!checks.branchMatches || !checks.dateMatches) { + process.exitCode = 1; +} + +function resolveCurrentBranch(cwd) { + const result = spawnSync('git', ['rev-parse', '--abbrev-ref', 'HEAD'], { + cwd, + encoding: 'utf8', + }); + if (result.status !== 0) { + const stderr = result.stderr?.trim() ?? ''; + throw new Error(`unable to resolve current git branch: ${stderr}`); + } + return result.stdout.trim(); +} + +function parseArgs(argv) { + let expectedBranch; + let expectedDate; + let reportPath; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--expected-branch') { + expectedBranch = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--expected-date') { + expectedDate = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--report-path') { + reportPath = argv[index + 1]; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { expectedBranch, expectedDate, reportPath }; +} diff --git a/tools/release-evidence/generate-license-report.mjs b/tools/release-evidence/generate-license-report.mjs new file mode 100644 index 0000000..e8c9d6f --- /dev/null +++ b/tools/release-evidence/generate-license-report.mjs @@ -0,0 +1,104 @@ +#!/usr/bin/env node + +import { mkdir, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { spawnSync } from 'node:child_process'; + +const args = parseArgs(process.argv.slice(2)); +const repoRoot = process.cwd(); +const outDir = path.resolve(repoRoot, args.outDir); +await mkdir(outDir, { recursive: true }); + +const run = spawnSync('pnpm', ['licenses', 'list', '--json'], { + cwd: repoRoot, + encoding: 'utf8', + env: process.env, + stdio: 'pipe', +}); +if (run.status !== 0) { + throw new Error(`license report generation failed: ${run.stderr ?? run.stdout}`); +} + +const parsed = JSON.parse(run.stdout); +const dependencies = []; +if (Array.isArray(parsed)) { + dependencies.push(...parsed); +} else if (parsed && typeof parsed === 'object') { + for (const [license, entries] of Object.entries(parsed)) { + if (!Array.isArray(entries)) { + continue; + } + for (const entry of entries) { + dependencies.push({ + ...entry, + license: entry.license ?? license, + }); + } + } +} + +const counts = new Map(); +for (const entry of dependencies) { + const license = entry.license ?? 'UNKNOWN'; + counts.set(license, (counts.get(license) ?? 0) + 1); +} +const summary = [...counts.entries()] + .map(([license, count]) => ({ license, count })) + .sort((left, right) => right.count - left.count); + +const report = { + generatedAt: new Date().toISOString(), + dependencyCount: dependencies.length, + licenseSummary: summary, + dependencies, +}; + +const jsonPath = path.join(outDir, 'license-report.json'); +const mdPath = path.join(outDir, 'license-report.md'); +await writeFile(jsonPath, `${JSON.stringify(report, null, 2)}\n`, 'utf8'); +await writeFile(mdPath, renderMarkdown(report), 'utf8'); + +process.stdout.write( + `${JSON.stringify( + { + jsonPath: path.relative(repoRoot, jsonPath), + mdPath: path.relative(repoRoot, mdPath), + dependencyCount: dependencies.length, + }, + null, + 2, + )}\n`, +); + +function renderMarkdown(report) { + const lines = [ + '# Dependency license report', + '', + `Generated: ${report.generatedAt}`, + `Dependencies: ${report.dependencyCount}`, + '', + '| License | Count |', + '| --- | ---: |', + ...report.licenseSummary.map((entry) => `| ${entry.license} | ${entry.count} |`), + '', + ]; + return `${lines.join('\n')}\n`; +} + +function parseArgs(argv) { + let outDir = 'artifacts/security'; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--out-dir') { + outDir = argv[index + 1] ?? outDir; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { outDir }; +} diff --git a/tools/release-evidence/generate-sbom.mjs b/tools/release-evidence/generate-sbom.mjs new file mode 100644 index 0000000..2df16c0 --- /dev/null +++ b/tools/release-evidence/generate-sbom.mjs @@ -0,0 +1,127 @@ +#!/usr/bin/env node + +import { mkdir } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { spawnSync } from 'node:child_process'; +import { writeFile } from 'node:fs/promises'; + +const args = parseArgs(process.argv.slice(2)); +const repoRoot = process.cwd(); +const outDir = path.resolve(repoRoot, args.outDir); +const outputPath = path.join(outDir, 'sbom.cdx.json'); + +await mkdir(outDir, { recursive: true }); + +const run = spawnSync( + 'pnpm', + ['ls', '--json', '--depth', 'Infinity'], + { + cwd: repoRoot, + encoding: 'utf8', + env: process.env, + stdio: 'pipe', + }, +); + +if (run.status !== 0) { + throw new Error(`SBOM generation failed: ${run.stderr || run.stdout}`); +} + +const parsed = JSON.parse(run.stdout); +const roots = Array.isArray(parsed) ? parsed : [parsed]; +const componentMap = new Map(); + +for (const root of roots) { + walkDependencies(root); +} + +const components = [...componentMap.values()].sort((left, right) => + `${left.name}@${left.version}`.localeCompare(`${right.name}@${right.version}`), +); +const sbom = { + bomFormat: 'CycloneDX', + specVersion: '1.5', + version: 1, + metadata: { + timestamp: new Date().toISOString(), + component: { + type: 'application', + name: '@blue-quickjs/source', + version: '0.0.0', + }, + tools: [ + { + vendor: 'blue-quickjs', + name: 'custom-pnpm-sbom-generator', + }, + ], + }, + components, +}; +await writeFile(outputPath, `${JSON.stringify(sbom, null, 2)}\n`, 'utf8'); + +process.stdout.write( + `${JSON.stringify( + { + outputPath: path.relative(repoRoot, outputPath), + componentCount: components.length, + }, + null, + 2, + )}\n`, +); + +function walkDependencies(node) { + if (!node || typeof node !== 'object') { + return; + } + for (const field of [ + 'dependencies', + 'devDependencies', + 'optionalDependencies', + 'peerDependencies', + ]) { + const dependencies = node[field]; + if (!dependencies || typeof dependencies !== 'object') { + continue; + } + for (const [name, dependency] of Object.entries(dependencies)) { + if (!dependency || typeof dependency !== 'object') { + continue; + } + const version = dependency.version ?? '0.0.0'; + const key = `${name}@${version}`; + if (!componentMap.has(key)) { + componentMap.set(key, { + type: 'library', + name, + version, + purl: `pkg:npm/${encodeComponent(name)}@${version}`, + }); + } + walkDependencies(dependency); + } + } +} + +function encodeComponent(name) { + return encodeURIComponent(name).replace('%2F', '/'); +} + +function parseArgs(argv) { + let outDir = 'artifacts/security'; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--out-dir') { + outDir = argv[index + 1] ?? outDir; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { outDir }; +} diff --git a/tools/release-evidence/release-evidence.test.mjs b/tools/release-evidence/release-evidence.test.mjs new file mode 100644 index 0000000..30977aa --- /dev/null +++ b/tools/release-evidence/release-evidence.test.mjs @@ -0,0 +1,74 @@ +import test from 'node:test'; +import assert from 'node:assert/strict'; +import { generateKeyPairSync } from 'node:crypto'; +import { mkdtemp, readFile, rm, writeFile } from 'node:fs/promises'; +import os from 'node:os'; +import path from 'node:path'; +import { + createDetachedSignature, + createManifestEntry, + verifyDetachedSignature, + verifyManifestBundle, + writeSignatureFile, +} from './_lib.mjs'; + +test('digest fallback signatures verify deterministically', async () => { + const payload = Buffer.from('release-evidence'); + const signature = createDetachedSignature(payload); + const verification = verifyDetachedSignature(payload, signature); + assert.equal(verification.ok, true); +}); + +test('ed25519 signatures verify with public key', async () => { + const { privateKey, publicKey } = generateKeyPairSync('ed25519'); + const payload = Buffer.from('consensus-evidence'); + const signature = createDetachedSignature(payload, { + privateKeyPem: privateKey.export({ format: 'pem', type: 'pkcs8' }), + keyId: 'test-key', + }); + const verification = verifyDetachedSignature(payload, signature, { + publicKeyPem: publicKey.export({ format: 'pem', type: 'spki' }), + }); + assert.equal(verification.ok, true); +}); + +test('manifest verification fails when artifact content is tampered', async () => { + const tempDir = await mkdtemp(path.join(os.tmpdir(), 'release-evidence-test-')); + try { + const artifactPath = path.join(tempDir, 'sample.json'); + await writeFile(artifactPath, '{"ok":true}\n', 'utf8'); + + const artifactEntry = await createManifestEntry( + artifactPath, + tempDir, + 'release-evidence', + ); + const signaturePayload = createDetachedSignature( + await readFile(artifactPath), + {}, + ); + const signaturePath = await writeSignatureFile(artifactPath, signaturePayload); + artifactEntry.signatureFile = path.relative(tempDir, signaturePath); + + const manifest = { + version: 1, + generatedAt: new Date().toISOString(), + branch: 'cursor/test', + date: '2026-03-18', + artifacts: [artifactEntry], + }; + + const valid = await verifyManifestBundle(manifest, tempDir, {}); + assert.equal(valid.ok, true); + + await writeFile(artifactPath, '{"ok":false}\n', 'utf8'); + const tampered = await verifyManifestBundle(manifest, tempDir, {}); + assert.equal(tampered.ok, false); + assert.equal( + tampered.errors.some((error) => error.type === 'checksum-mismatch'), + true, + ); + } finally { + await rm(tempDir, { recursive: true, force: true }); + } +}); diff --git a/tools/release-evidence/synthesize-release-evidence.mjs b/tools/release-evidence/synthesize-release-evidence.mjs new file mode 100644 index 0000000..2d5f895 --- /dev/null +++ b/tools/release-evidence/synthesize-release-evidence.mjs @@ -0,0 +1,582 @@ +#!/usr/bin/env node + +import { readFile, readdir, stat, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { spawnSync } from 'node:child_process'; +import { + copyIntoEvidenceDir, + createDetachedSignature, + createManifestEntry, + ensureDir, + loadOptionalText, + writeChecksumFile, + writeSignatureFile, +} from './_lib.mjs'; + +const args = parseArgs(process.argv.slice(2)); +const repoRoot = process.cwd(); +const artifactsRoot = path.resolve(repoRoot, args.artifactsDir); +const outDir = path.resolve(repoRoot, args.outDir); +const inputsDir = path.join(outDir, 'inputs'); + +await ensureDir(outDir); +await ensureDir(inputsDir); + +const branch = args.branch ?? resolveCurrentBranch(repoRoot); +const date = args.date ?? new Date().toISOString().slice(0, 10); +const existingSummaryPath = path.join(outDir, 'release-evidence-summary.json'); +const existingSummary = + args.check && (await pathExists(existingSummaryPath)) + ? JSON.parse(await readFile(existingSummaryPath, 'utf8')) + : null; +const generatedAt = existingSummary?.generatedAt ?? new Date().toISOString(); + +const consensusSource = path.resolve( + repoRoot, + args.consensusReport ?? + (await findNewestFile(artifactsRoot, (entry) => + /^consensus-parity-report-.*\.json$/.test(entry.name), + )), +); +const workloadSource = path.resolve( + repoRoot, + args.workloadReport ?? + (await findNewestFile( + path.join(artifactsRoot, 'workload-certification'), + (entry) => /^workload-certification-.*\.json$/.test(entry.name), + )), +); +const workloadOogSource = path.resolve( + repoRoot, + args.workloadOogReport ?? path.join(artifactsRoot, 'workload-certification', 'oog-boundaries.json'), +); +const consumerSource = path.resolve( + repoRoot, + args.consumerReport ?? 'e2e/consumer-proof-app/reports/reproducibility-report.json', +); +const repeatabilitySource = path.resolve( + repoRoot, + args.repeatabilityReport ?? + path.join(artifactsRoot, 'workload-certification', 'repeatability-report.json'), +); +const seededSource = path.resolve( + repoRoot, + args.seededReport ?? + path.join(artifactsRoot, 'workload-certification', 'seeded-property-corpus-report.json'), +); +const workloadDeltaSource = path.resolve( + repoRoot, + args.workloadDeltaReport ?? + path.join(artifactsRoot, 'workload-certification', 'compatibility-delta-report.json'), +); +const workloadMatrixSource = path.resolve( + repoRoot, + args.workloadMatrixReport ?? + (await findNewestFile( + path.join(artifactsRoot, 'workload-certification'), + (entry) => /^compatibility-matrix-.*\.json$/.test(entry.name), + )), +); +const nativeSource = args.nativeReport + ? path.resolve(repoRoot, args.nativeReport) + : await findNewestFileOptional( + path.join(artifactsRoot, 'reproducibility'), + (entry) => /^parity-report-.*\.json$/.test(entry.name), + ); + +const metadataSource = path.resolve( + repoRoot, + args.metadataPath ?? 'libs/quickjs-wasm-build/dist/quickjs-wasm-build.metadata.json', +); +const metadata = await readOptionalJson(metadataSource); +const signingKeyPem = + (await loadOptionalText(args.signingKeyPath ?? '')) ?? + process.env.RELEASE_EVIDENCE_SIGNING_KEY ?? + null; + +const copiedArtifacts = []; +copiedArtifacts.push( + await copyArtifact(consensusSource, 'consensus-report.json', 'consensus'), +); +copiedArtifacts.push( + await copyArtifact(workloadSource, 'workload-certification.json', 'workload'), +); +copiedArtifacts.push( + await copyArtifact(workloadOogSource, 'workload-oog-boundaries.json', 'workload'), +); +copiedArtifacts.push( + await copyArtifact(workloadMatrixSource, 'workload-compatibility-matrix.json', 'workload'), +); +copiedArtifacts.push( + await copyArtifact(consumerSource, 'consumer-reproducibility.json', 'consumer'), +); + +if (await pathExists(repeatabilitySource)) { + copiedArtifacts.push( + await copyArtifact(repeatabilitySource, 'workload-repeatability.json', 'workload'), + ); +} +if (await pathExists(seededSource)) { + copiedArtifacts.push( + await copyArtifact(seededSource, 'workload-seeded-corpus.json', 'workload'), + ); +} +if (await pathExists(workloadDeltaSource)) { + copiedArtifacts.push( + await copyArtifact(workloadDeltaSource, 'workload-compatibility-delta.json', 'workload'), + ); +} +if (nativeSource && (await pathExists(nativeSource))) { + copiedArtifacts.push( + await copyArtifact(nativeSource, 'native-diagnostic-report.json', 'native'), + ); +} + +const consensus = JSON.parse( + await readFile(path.join(inputsDir, 'consensus-report.json'), 'utf8'), +); +const workload = JSON.parse( + await readFile(path.join(inputsDir, 'workload-certification.json'), 'utf8'), +); +const workloadOog = JSON.parse( + await readFile(path.join(inputsDir, 'workload-oog-boundaries.json'), 'utf8'), +); +const consumer = JSON.parse( + await readFile(path.join(inputsDir, 'consumer-reproducibility.json'), 'utf8'), +); +const workloadDelta = (await pathExists(path.join(inputsDir, 'workload-compatibility-delta.json'))) + ? JSON.parse( + await readFile(path.join(inputsDir, 'workload-compatibility-delta.json'), 'utf8'), + ) + : null; + +const executionProfiles = [ + ...new Set( + (workload.records ?? []) + .map((record) => record.profile) + .filter((value) => typeof value === 'string' && value.length > 0), + ), +].sort(); + +const consensusBoundarySuite = (consensus.suites ?? []).find( + (suite) => suite.name === 'gas-boundary-fixtures', +); +const exactOogParity = + (consensusBoundarySuite?.mismatchCount ?? 0) === 0 && + (workloadOog.mismatchCount ?? 1) === 0 && + Boolean(consumer.parity?.oogEqual); + +const summary = { + generatedAt, + branch, + date, + engineBuildHash: + metadata?.engineBuildHash ?? + metadata?.variants?.wasm32?.release?.engineBuildHash ?? + null, + gasVersion: metadata?.gasVersion ?? null, + executionProfileCoverage: executionProfiles, + fixtureCounts: { + consensus: consensus.fixtureCount ?? 0, + workloadTotal: workload.summary?.total ?? 0, + workloadGreen: workload.summary?.greenCount ?? 0, + workloadRed: workload.summary?.redCount ?? 0, + workloadFlagship: workload.summary?.flagshipCount ?? 0, + }, + mismatchCounts: { + consensus: consensus.mismatchCount ?? 0, + workload: workload.summary?.mismatches ?? 0, + workloadOog: workloadOog.mismatchCount ?? 0, + consumerParity: + consumer.parity?.snapshotEqual && consumer.parity?.oogEqual ? 0 : 1, + }, + compatibilityDelta: workloadDelta + ? { + greenDelta: workloadDelta.deltas?.greenDelta ?? 0, + addedCount: workloadDelta.added?.length ?? 0, + removedCount: workloadDelta.removed?.length ?? 0, + } + : null, + exactOogParity, + consumerParity: { + snapshotEqual: Boolean(consumer.parity?.snapshotEqual), + oogEqual: Boolean(consumer.parity?.oogEqual), + }, +}; + +const summaryJsonPath = path.join(outDir, 'release-evidence-summary.json'); +await writeFile(`${summaryJsonPath}`, `${JSON.stringify(summary, null, 2)}\n`, 'utf8'); +const summaryMarkdown = renderSummaryMarkdown(summary, copiedArtifacts); +const summaryMdPath = path.join(outDir, 'release-evidence-summary.md'); +await writeFile(summaryMdPath, summaryMarkdown, 'utf8'); + +const generatedArtifacts = []; +generatedArtifacts.push( + await finalizeGeneratedArtifact(summaryJsonPath, 'release-evidence', signingKeyPem), +); +generatedArtifacts.push( + await finalizeGeneratedArtifact(summaryMdPath, 'release-evidence', signingKeyPem), +); + +const manifest = { + version: 1, + generatedAt, + branch, + date, + artifacts: [ + ...(await Promise.all( + copiedArtifacts.map(async (artifact) => + createManifestEntry(artifact.path, outDir, artifact.category), + ), + )), + ...(await Promise.all( + generatedArtifacts.map(async (artifact) => { + const baseEntry = await createManifestEntry( + artifact.path, + outDir, + artifact.category, + ); + return { + ...baseEntry, + checksumFile: path.relative(outDir, artifact.checksumPath), + signatureFile: path.relative(outDir, artifact.signaturePath), + }; + }), + )), + ], +}; + +const manifestPath = path.join(outDir, 'release-evidence-manifest.json'); +await writeFile(manifestPath, `${JSON.stringify(manifest, null, 2)}\n`, 'utf8'); +const manifestChecksumPath = await writeChecksumFile(manifestPath); +const manifestSignaturePath = await writeSignatureFile( + manifestPath, + createDetachedSignature(await readFile(manifestPath), { + privateKeyPem: signingKeyPem, + keyId: args.signingKeyId ?? 'release-evidence-manifest', + }), +); + +const docsPath = path.resolve(repoRoot, args.docsPath ?? 'docs/release-readiness-report.md'); +const generatedDocs = renderReleaseReadinessDoc(summary, manifest, outDir); +if (args.check) { + const existing = await readFile(docsPath, 'utf8'); + if (existing !== generatedDocs) { + throw new Error( + `${path.relative(repoRoot, docsPath)} is stale; run synthesize-release-evidence without --check`, + ); + } +} else if (!args.skipDocs) { + await writeFile(docsPath, generatedDocs, 'utf8'); +} + +process.stdout.write( + `${JSON.stringify( + { + outDir, + summaryJsonPath: path.relative(repoRoot, summaryJsonPath), + summaryMdPath: path.relative(repoRoot, summaryMdPath), + manifestPath: path.relative(repoRoot, manifestPath), + manifestChecksumPath: path.relative(repoRoot, manifestChecksumPath), + manifestSignaturePath: path.relative(repoRoot, manifestSignaturePath), + docsPath: path.relative(repoRoot, docsPath), + exactOogParity, + }, + null, + 2, + )}\n`, +); + +async function copyArtifact(sourcePath, targetName, category) { + if (!(await pathExists(sourcePath))) { + throw new Error(`required evidence source is missing: ${sourcePath}`); + } + const destination = await copyIntoEvidenceDir(sourcePath, inputsDir, targetName); + return { category, path: destination }; +} + +async function finalizeGeneratedArtifact(filePath, category, signingKeyPem) { + const checksumPath = await writeChecksumFile(filePath); + const signaturePayload = createDetachedSignature(await readFile(filePath), { + privateKeyPem: signingKeyPem, + keyId: args.signingKeyId ?? 'release-evidence', + }); + const signaturePath = await writeSignatureFile(filePath, signaturePayload); + return { + category, + path: filePath, + checksumPath, + signaturePath, + }; +} + +function renderSummaryMarkdown(summary, copiedArtifacts) { + const lines = [ + '# Release Evidence Summary (Generated)', + '', + `Generated at: ${summary.generatedAt}`, + `Branch: \`${summary.branch}\``, + `Date: ${summary.date}`, + '', + `- engineBuildHash: \`${summary.engineBuildHash ?? 'n/a'}\``, + `- gasVersion: \`${summary.gasVersion ?? 'n/a'}\``, + `- exact OOG parity: **${summary.exactOogParity ? 'pass' : 'fail'}**`, + '', + '## Coverage', + '', + `- execution profiles: ${summary.executionProfileCoverage.length > 0 ? summary.executionProfileCoverage.map((entry) => `\`${entry}\``).join(', ') : 'n/a'}`, + `- consensus fixtures: ${summary.fixtureCounts.consensus}`, + `- workload fixtures: ${summary.fixtureCounts.workloadTotal} (green ${summary.fixtureCounts.workloadGreen} / red ${summary.fixtureCounts.workloadRed} / flagship ${summary.fixtureCounts.workloadFlagship})`, + '', + '## Mismatches', + '', + `- consensus mismatches: ${summary.mismatchCounts.consensus}`, + `- workload mismatches: ${summary.mismatchCounts.workload}`, + `- workload OOG mismatches: ${summary.mismatchCounts.workloadOog}`, + `- consumer parity mismatches: ${summary.mismatchCounts.consumerParity}`, + `- compatibility green delta: ${summary.compatibilityDelta?.greenDelta ?? 'n/a'}`, + '', + '## Included source evidence files', + '', + '| Category | File |', + '| --- | --- |', + ]; + for (const artifact of copiedArtifacts) { + lines.push(`| ${artifact.category} | \`${path.basename(artifact.path)}\` |`); + } + lines.push(''); + return `${lines.join('\n')}\n`; +} + +function renderReleaseReadinessDoc(summary, manifest, evidenceDir) { + const lines = [ + '# Release-readiness report (current branch snapshot)', + '', + `Date: ${summary.date} `, + `Branch: \`${summary.branch}\``, + '', + '> This file is generated by `node tools/release-evidence/synthesize-release-evidence.mjs`.', + '', + '## Environment', + '', + `- engineBuildHash: \`${summary.engineBuildHash ?? 'n/a'}\``, + `- gasVersion: \`${summary.gasVersion ?? 'n/a'}\``, + '', + '## Consensus-safe vs diagnostic-only', + '', + '### Consensus-safe (release gate)', + '', + '- Executor pair: `wasm-node` vs `wasm-browser` (`wasm32` release artifacts).', + '- Gate requirements: exact value/error parity, exact gas parity, exact tape parity, exact OOG boundary parity.', + `- Consensus mismatch count: \`${summary.mismatchCounts.consensus}\``, + '', + '### Diagnostic-only', + '', + '- Native parity remains diagnostic-only unless explicitly promoted by release policy.', + '', + '## Certification and parity snapshot', + '', + `- Workload totals: \`${summary.fixtureCounts.workloadTotal}\` fixtures (\`${summary.fixtureCounts.workloadGreen}\` green / \`${summary.fixtureCounts.workloadRed}\` red / \`${summary.fixtureCounts.workloadFlagship}\` flagship)`, + `- Workload mismatch count: \`${summary.mismatchCounts.workload}\``, + `- Workload OOG mismatch count: \`${summary.mismatchCounts.workloadOog}\``, + `- Compatibility green delta vs baseline: \`${summary.compatibilityDelta?.greenDelta ?? 'n/a'}\``, + `- Consumer snapshot parity: \`${summary.consumerParity.snapshotEqual}\``, + `- Consumer OOG parity: \`${summary.consumerParity.oogEqual}\``, + `- Exact OOG parity status: \`${summary.exactOogParity}\``, + '', + '## Evidence manifest', + '', + `- Manifest file: \`${path.relative(process.cwd(), path.join(evidenceDir, 'release-evidence-manifest.json'))}\``, + `- Manifest artifact entries: \`${manifest.artifacts.length}\``, + '', + '## Included artifacts', + '', + '| Category | File | SHA256 |', + '| --- | --- | --- |', + ]; + for (const artifact of manifest.artifacts) { + lines.push(`| ${artifact.category} | \`${artifact.file}\` | \`${artifact.sha256}\` |`); + } + lines.push(''); + return `${lines.join('\n')}\n`; +} + +async function findNewestFile(rootDir, predicate) { + const found = await findNewestFileOptional(rootDir, predicate); + if (!found) { + throw new Error(`no matching files under ${rootDir}`); + } + return found; +} + +async function findNewestFileOptional(rootDir, predicate) { + if (!(await pathExists(rootDir))) { + return null; + } + const files = await walkFiles(rootDir); + let latest = null; + for (const file of files) { + if (!predicate({ name: path.basename(file), path: file })) { + continue; + } + const fileStat = await stat(file); + if (!latest || fileStat.mtimeMs > latest.mtimeMs) { + latest = { file, mtimeMs: fileStat.mtimeMs }; + } + } + return latest?.file ?? null; +} + +async function walkFiles(rootDir) { + const entries = await readdir(rootDir, { withFileTypes: true }); + const files = []; + for (const entry of entries) { + const fullPath = path.join(rootDir, entry.name); + if (entry.isDirectory()) { + files.push(...(await walkFiles(fullPath))); + } else { + files.push(fullPath); + } + } + return files; +} + +async function readOptionalJson(filePath) { + if (!(await pathExists(filePath))) { + return null; + } + return JSON.parse(await readFile(filePath, 'utf8')); +} + +async function pathExists(targetPath) { + try { + await stat(targetPath); + return true; + } catch { + return false; + } +} + +function resolveCurrentBranch(cwd) { + const result = spawnSync('git', ['rev-parse', '--abbrev-ref', 'HEAD'], { + cwd, + encoding: 'utf8', + }); + if (result.status !== 0) { + throw new Error(`unable to resolve current branch: ${result.stderr?.trim() ?? ''}`); + } + return result.stdout.trim(); +} + +function parseArgs(argv) { + const parsed = { + artifactsDir: 'artifacts', + outDir: 'artifacts/release-evidence', + docsPath: 'docs/release-readiness-report.md', + check: false, + skipDocs: false, + }; + + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--artifacts-dir') { + parsed.artifactsDir = argv[index + 1] ?? parsed.artifactsDir; + index += 1; + continue; + } + if (arg === '--out-dir') { + parsed.outDir = argv[index + 1] ?? parsed.outDir; + index += 1; + continue; + } + if (arg === '--docs-path') { + parsed.docsPath = argv[index + 1] ?? parsed.docsPath; + index += 1; + continue; + } + if (arg === '--consensus-report') { + parsed.consensusReport = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--workload-report') { + parsed.workloadReport = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--workload-oog-report') { + parsed.workloadOogReport = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--workload-matrix-report') { + parsed.workloadMatrixReport = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--consumer-report') { + parsed.consumerReport = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--repeatability-report') { + parsed.repeatabilityReport = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--seeded-report') { + parsed.seededReport = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--workload-delta-report') { + parsed.workloadDeltaReport = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--native-report') { + parsed.nativeReport = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--metadata-path') { + parsed.metadataPath = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--signing-key-path') { + parsed.signingKeyPath = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--signing-key-id') { + parsed.signingKeyId = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--branch') { + parsed.branch = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--date') { + parsed.date = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--check') { + parsed.check = true; + continue; + } + if (arg === '--skip-docs') { + parsed.skipDocs = true; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return parsed; +} diff --git a/tools/release-evidence/verify-learning-path.mjs b/tools/release-evidence/verify-learning-path.mjs new file mode 100644 index 0000000..a0f4dd2 --- /dev/null +++ b/tools/release-evidence/verify-learning-path.mjs @@ -0,0 +1,69 @@ +#!/usr/bin/env node + +import { readFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; + +const repoRoot = process.cwd(); + +const pages = [ + 'docs/learn/00-what-is-bluequickjs.md', + 'docs/learn/01-install-and-run-your-first-script.md', + 'docs/learn/02-understand-the-program-artifact.md', + 'docs/learn/03-module-packs-and-imports.md', + 'docs/learn/04-promises-async-and-microtasks.md', + 'docs/learn/05-binary-and-host-v2.md', + 'docs/learn/06-gas-oog-and-max-gas-policies.md', + 'docs/learn/07-verify-release-evidence.md', + 'docs/learn/08-build-a-real-example.md', + 'docs/learn/09-production-embedder-checklist.md', +]; + +const requiredSections = [ + '## Prerequisites', + '## Commands', + '## Expected output', + '## What you learned', + '## Continue', + '## Troubleshooting', +]; + +const problems = []; + +for (let index = 0; index < pages.length; index += 1) { + const relativePath = pages[index]; + const contents = await readFile(path.join(repoRoot, relativePath), 'utf8'); + + for (const section of requiredSections) { + if (!contents.includes(section)) { + problems.push(`${relativePath}: missing required section "${section}"`); + } + } + + if (index < pages.length - 1) { + const nextPagePath = pages[index + 1]; + const nextPageName = path.basename(nextPagePath); + if (!contents.includes(nextPageName)) { + problems.push( + `${relativePath}: continue section should reference ${nextPageName}`, + ); + } + } +} + +process.stdout.write( + `${JSON.stringify( + { + checkedPageCount: pages.length, + requiredSectionCount: requiredSections.length, + problemCount: problems.length, + problems, + }, + null, + 2, + )}\n`, +); + +if (problems.length > 0) { + process.exitCode = 1; +} diff --git a/tools/release-evidence/verify-readme-quickstart.mjs b/tools/release-evidence/verify-readme-quickstart.mjs new file mode 100644 index 0000000..013e5b6 --- /dev/null +++ b/tools/release-evidence/verify-readme-quickstart.mjs @@ -0,0 +1,175 @@ +#!/usr/bin/env node + +import { mkdtemp, readFile, rm } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import os from 'node:os'; +import { spawnSync } from 'node:child_process'; + +const args = parseArgs(process.argv.slice(2)); +const repoRoot = path.resolve(process.cwd()); +const readmePath = path.join(repoRoot, 'README.md'); +const readme = await readFile(readmePath, 'utf8'); + +const quickstartCommands = [ + 'pnpm install', + 'bash tools/scripts/setup-emsdk.sh', + 'source tools/emsdk/emsdk_env.sh', + 'pnpm exec playwright install --with-deps chromium', + 'pnpm nx test smoke-node', + 'pnpm nx run smoke-web:e2e', + 'node tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs --out-dir artifacts/reproducibility-consensus', + 'node apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs --out-dir artifacts/workload-certification', +]; + +const missingCommands = quickstartCommands.filter( + (command) => !readme.includes(command), +); +if (missingCommands.length > 0) { + throw new Error( + `README quickstart is missing expected commands:\n${missingCommands.join('\n')}`, + ); +} + +const tempRoot = await mkdtemp( + path.join(args.tempRoot ?? os.tmpdir(), 'bluequickjs-quickstart-'), +); +const clonePath = path.join(tempRoot, 'repo'); + +try { + run( + 'git', + ['clone', '--depth', '1', '--recurse-submodules', repoRoot, clonePath], + repoRoot, + ); + + if (!args.skipInstall) { + run('pnpm', ['install'], clonePath); + } + if (!args.skipEmsdkSetup) { + run('bash', ['tools/scripts/setup-emsdk.sh'], clonePath); + } + + if (!args.skipBrowserTasks) { + run('pnpm', ['exec', 'playwright', 'install', '--with-deps', 'chromium'], clonePath); + } + + if (!args.skipSmokeTests) { + runBash( + 'source tools/emsdk/emsdk_env.sh && pnpm nx test smoke-node', + clonePath, + ); + + if (!args.skipBrowserTasks) { + runBash( + 'source tools/emsdk/emsdk_env.sh && pnpm nx run smoke-web:e2e', + clonePath, + ); + } + } + + if (!args.skipEvidence) { + runBash( + 'source tools/emsdk/emsdk_env.sh && node tools/consensus-parity/scripts/archive-consensus-reproducibility-report.mjs --out-dir artifacts/reproducibility-consensus', + clonePath, + ); + runBash( + 'source tools/emsdk/emsdk_env.sh && node apps/ecosystem-certifier/scripts/archive-workload-certification-report.mjs --out-dir artifacts/workload-certification', + clonePath, + ); + } + + process.stdout.write( + `${JSON.stringify( + { + status: 'ok', + clonePath, + skipped: { + emsdkSetup: args.skipEmsdkSetup, + install: args.skipInstall, + browserTasks: args.skipBrowserTasks, + smokeTests: args.skipSmokeTests, + evidence: args.skipEvidence, + }, + }, + null, + 2, + )}\n`, + ); +} finally { + if (!args.keepTemp) { + await rm(tempRoot, { recursive: true, force: true }); + } +} + +function parseArgs(argv) { + let skipEmsdkSetup = false; + let skipInstall = false; + let skipBrowserTasks = false; + let skipSmokeTests = false; + let skipEvidence = false; + let keepTemp = false; + let tempRoot; + + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--skip-install') { + skipInstall = true; + continue; + } + if (arg === '--skip-emsdk-setup') { + skipEmsdkSetup = true; + continue; + } + if (arg === '--skip-smoke-tests') { + skipSmokeTests = true; + continue; + } + if (arg === '--skip-browser-tasks') { + skipBrowserTasks = true; + continue; + } + if (arg === '--skip-evidence') { + skipEvidence = true; + continue; + } + if (arg === '--keep-temp') { + keepTemp = true; + continue; + } + if (arg === '--temp-root') { + tempRoot = argv[index + 1]; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + + return { + skipInstall, + skipEmsdkSetup, + skipBrowserTasks, + skipSmokeTests, + skipEvidence, + keepTemp, + tempRoot, + }; +} + +function run(command, args, cwd) { + const result = spawnSync(command, args, { + cwd, + stdio: 'inherit', + env: process.env, + }); + if (result.status !== 0) { + throw new Error(`command failed: ${command} ${args.join(' ')}`); + } +} + +function runBash(command, cwd) { + run('bash', ['-lc', command], cwd); +} diff --git a/tools/release-evidence/verify-release-evidence.mjs b/tools/release-evidence/verify-release-evidence.mjs new file mode 100644 index 0000000..a34b80f --- /dev/null +++ b/tools/release-evidence/verify-release-evidence.mjs @@ -0,0 +1,111 @@ +#!/usr/bin/env node + +import { readFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { spawnSync } from 'node:child_process'; +import { loadOptionalText, verifyManifestBundle } from './_lib.mjs'; + +const args = parseArgs(process.argv.slice(2)); +const repoRoot = process.cwd(); +const evidenceDir = path.resolve(repoRoot, args.evidenceDir); +const manifestPath = path.resolve( + evidenceDir, + args.manifestPath ?? 'release-evidence-manifest.json', +); +const manifest = JSON.parse(await readFile(manifestPath, 'utf8')); + +const publicKeyPem = + (await loadOptionalText(args.publicKeyPath ?? '')) ?? + process.env.RELEASE_EVIDENCE_PUBLIC_KEY ?? + null; + +const verification = await verifyManifestBundle(manifest, evidenceDir, { + publicKeyPem, +}); + +const branchCheck = buildBranchCheck(manifest.branch, args.expectedBranch); +const dateCheck = buildDateCheck(manifest.date, args.expectedDate); + +const output = { + evidenceDir, + manifestPath: path.relative(repoRoot, manifestPath), + artifactCount: manifest.artifacts.length, + verification, + branchCheck, + dateCheck, +}; + +process.stdout.write(`${JSON.stringify(output, null, 2)}\n`); + +if (!verification.ok || !branchCheck.ok || !dateCheck.ok) { + process.exitCode = 1; +} + +function buildBranchCheck(actual, expectedBranchArg) { + const expectedBranch = expectedBranchArg ?? resolveCurrentBranch(process.cwd()); + return { + expected: expectedBranch, + actual, + ok: actual === expectedBranch, + }; +} + +function buildDateCheck(actual, expectedDateArg) { + const expectedDate = expectedDateArg ?? new Date().toISOString().slice(0, 10); + return { + expected: expectedDate, + actual, + ok: actual === expectedDate, + }; +} + +function resolveCurrentBranch(cwd) { + const result = spawnSync('git', ['rev-parse', '--abbrev-ref', 'HEAD'], { + cwd, + encoding: 'utf8', + }); + if (result.status !== 0) { + return null; + } + return result.stdout.trim(); +} + +function parseArgs(argv) { + const parsed = { + evidenceDir: 'artifacts/release-evidence', + }; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--evidence-dir') { + parsed.evidenceDir = argv[index + 1] ?? parsed.evidenceDir; + index += 1; + continue; + } + if (arg === '--manifest-path') { + parsed.manifestPath = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--public-key-path') { + parsed.publicKeyPath = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--expected-branch') { + parsed.expectedBranch = argv[index + 1]; + index += 1; + continue; + } + if (arg === '--expected-date') { + parsed.expectedDate = argv[index + 1]; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return parsed; +} diff --git a/tools/scripts/ensure-quickjs-submodule.sh b/tools/scripts/ensure-quickjs-submodule.sh new file mode 100644 index 0000000..843977a --- /dev/null +++ b/tools/scripts/ensure-quickjs-submodule.sh @@ -0,0 +1,33 @@ +#!/usr/bin/env bash +set -euo pipefail + +SCRIPT_DIR="$(cd -- "$(dirname -- "${BASH_SOURCE[0]}")" && pwd)" +REPO_ROOT="$(cd -- "${SCRIPT_DIR}/../.." && pwd)" +QJS_DIR="${REPO_ROOT}/vendor/quickjs" +QJS_VERSION_FILE="${QJS_DIR}/VERSION" + +if [ -f "${QJS_VERSION_FILE}" ]; then + exit 0 +fi + +echo "QuickJS submodule is missing or incomplete; attempting to initialize vendor/quickjs..." >&2 + +if ! command -v git >/dev/null 2>&1; then + echo "git is not available, so vendor/quickjs cannot be initialized automatically." >&2 + echo "Run: git submodule update --init --recursive vendor/quickjs" >&2 + exit 1 +fi + +( + cd "${REPO_ROOT}" + git submodule update --init --recursive vendor/quickjs +) + +if [ ! -f "${QJS_VERSION_FILE}" ]; then + echo "vendor/quickjs is still incomplete after submodule initialization." >&2 + echo "Expected file missing: ${QJS_VERSION_FILE}" >&2 + echo "Run: git submodule update --init --recursive vendor/quickjs" >&2 + exit 1 +fi + +echo "QuickJS submodule is ready." >&2 diff --git a/tools/scripts/setup-emsdk.sh b/tools/scripts/setup-emsdk.sh index 8d950c4..f357522 100755 --- a/tools/scripts/setup-emsdk.sh +++ b/tools/scripts/setup-emsdk.sh @@ -8,6 +8,98 @@ SCRIPT_DIR="$(cd -- "$(dirname -- "${BASH_SOURCE[0]}")" && pwd)" REPO_ROOT="$(cd -- "${SCRIPT_DIR}/../.." && pwd)" EMSDK_VERSION="$(cat "${SCRIPT_DIR}/emsdk-version.txt")" EMSDK_DIR="${REPO_ROOT}/tools/emsdk" +HOST_OS="$(uname -s)" +HOST_ARCH="$(uname -m)" + +resolve_host_python() { + if [ "${HOST_OS}" = "Darwin" ] && [ -x /usr/bin/python3 ]; then + echo /usr/bin/python3 + return 0 + fi + + if command -v python3 >/dev/null 2>&1; then + command -v python3 + return 0 + fi + + if command -v python >/dev/null 2>&1; then + command -v python + return 0 + fi + + echo "" +} + +HOST_PYTHON="$(resolve_host_python)" + +run_with_retry() { + local step_name="$1" + shift + + if "$@"; then + return 0 + fi + + if [ "${HOST_OS}" = "Darwin" ]; then + clear_quarantine_if_possible + fi + + echo "emsdk ${step_name} failed; retrying once..." >&2 + sleep 2 + + if "$@"; then + return 0 + fi + + if [ "${HOST_OS}" = "Darwin" ] && [ "${HOST_ARCH}" = "arm64" ] && [ -z "${EMSDK_ARCH:-}" ]; then + echo "emsdk ${step_name} still failed on macOS arm64; retrying with EMSDK_ARCH=x86_64..." >&2 + sleep 2 + if EMSDK_ARCH=x86_64 "$@"; then + cat >&2 <<'EOF' +emsdk setup succeeded using EMSDK_ARCH=x86_64. + +If this machine does not already have Rosetta installed, install it with: + softwareupdate --install-rosetta --agree-to-license +EOF + return 0 + fi + fi + + cat >&2 <<'EOF' +emsdk setup failed twice. + +If you saw a process get killed part-way through install, rerun: + bash tools/scripts/setup-emsdk.sh + +The script is idempotent and safe to retry after a partial install. +EOF + return 1 +} + +clear_quarantine_if_possible() { + if ! command -v xattr >/dev/null 2>&1; then + return 0 + fi + + xattr -dr com.apple.quarantine "${EMSDK_DIR}" >/dev/null 2>&1 || true +} + +run_emsdk() { + if [ -n "${HOST_PYTHON}" ] && [ -f "${EMSDK_DIR}/emsdk.py" ]; then + env \ + -u PYTHONHOME \ + -u PYTHONPATH \ + -u CONDA_PREFIX \ + -u CONDA_DEFAULT_ENV \ + -u CONDA_EXE \ + -u CONDA_PYTHON_EXE \ + EMSDK_PYTHON="${HOST_PYTHON}" \ + "${HOST_PYTHON}" "${EMSDK_DIR}/emsdk.py" "$@" + return $? + fi + + "${EMSDK_DIR}/emsdk" "$@" +} if [ ! -d "${EMSDK_DIR}" ]; then git clone https://github.com/emscripten-core/emsdk.git "${EMSDK_DIR}" @@ -18,8 +110,8 @@ cd "${EMSDK_DIR}" # Ensure we know about new tags/releases before installing. git fetch --tags origin -./emsdk install "${EMSDK_VERSION}" -./emsdk activate "${EMSDK_VERSION}" +run_with_retry "install" run_emsdk install "${EMSDK_VERSION}" +run_with_retry "activate" run_emsdk activate "${EMSDK_VERSION}" cat <<'EOF' Emscripten installed and activated. diff --git a/tools/workload-certification/check-pack-manifests.mjs b/tools/workload-certification/check-pack-manifests.mjs new file mode 100644 index 0000000..985d261 --- /dev/null +++ b/tools/workload-certification/check-pack-manifests.mjs @@ -0,0 +1,73 @@ +#!/usr/bin/env node + +import { mkdir, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { spawnSync } from 'node:child_process'; +import { PUBLIC_PACKAGES } from './public-packages.mjs'; + +const args = parseArgs(process.argv.slice(2)); +const repoRoot = process.cwd(); +const outDir = path.resolve(repoRoot, args.outDir); +await mkdir(outDir, { recursive: true }); + +const records = []; +for (const pkg of PUBLIC_PACKAGES) { + const run = spawnSync( + 'pnpm', + ['--filter', pkg, 'pack', '--json', '--pack-destination', outDir], + { + cwd: repoRoot, + encoding: 'utf8', + env: process.env, + }, + ); + if (run.status !== 0) { + throw new Error(`pack --json failed for ${pkg}: ${run.stderr ?? run.stdout}`); + } + + const raw = run.stdout.trim(); + const parsed = JSON.parse(raw); + const entries = Array.isArray(parsed) ? parsed : [parsed]; + records.push({ + package: pkg, + entries, + }); +} + +const manifest = { + generatedAt: new Date().toISOString(), + packageCount: PUBLIC_PACKAGES.length, + records, +}; +const manifestPath = path.join(outDir, 'pack-manifest.json'); +await writeFile(manifestPath, `${JSON.stringify(manifest, null, 2)}\n`, 'utf8'); + +process.stdout.write( + `${JSON.stringify( + { + outDir, + manifestPath, + packageCount: PUBLIC_PACKAGES.length, + }, + null, + 2, + )}\n`, +); + +function parseArgs(argv) { + let outDir = 'artifacts/consumer-proof/pack-manifests'; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--out-dir') { + outDir = argv[index + 1] ?? outDir; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { outDir }; +} diff --git a/tools/workload-certification/check-public-package-versions.mjs b/tools/workload-certification/check-public-package-versions.mjs new file mode 100644 index 0000000..d6d74f8 --- /dev/null +++ b/tools/workload-certification/check-public-package-versions.mjs @@ -0,0 +1,61 @@ +#!/usr/bin/env node + +import { readFile, stat } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { PUBLIC_PACKAGES } from './public-packages.mjs'; + +const repoRoot = process.cwd(); +const packageInfos = []; + +for (const pkg of PUBLIC_PACKAGES) { + const packageJsonPath = await resolveWorkspacePackageJsonPath(repoRoot, pkg); + const packageJson = JSON.parse(await readFile(packageJsonPath, 'utf8')); + packageInfos.push({ + name: packageJson.name, + version: packageJson.version, + private: Boolean(packageJson.private), + path: path.relative(repoRoot, packageJsonPath), + }); +} + +const versionSet = new Set(packageInfos.map((entry) => entry.version)); +const privatePackages = packageInfos.filter((entry) => entry.private); +const checks = { + alignedVersion: versionSet.size === 1, + noPrivatePackages: privatePackages.length === 0, +}; + +const output = { + packageCount: packageInfos.length, + targetVersion: versionSet.size === 1 ? [...versionSet][0] : null, + checks, + packages: packageInfos, + privatePackages, +}; + +process.stdout.write(`${JSON.stringify(output, null, 2)}\n`); +if (!checks.alignedVersion || !checks.noPrivatePackages) { + process.exitCode = 1; +} + +async function resolveWorkspacePackageJsonPath(root, packageName) { + const shortName = packageName.replace('@blue-quickjs/', ''); + const candidatePaths = [ + path.join(root, 'libs', shortName, 'package.json'), + path.join(root, 'tools', shortName, 'package.json'), + ]; + return findExistingPath(candidatePaths, packageName); +} + +async function findExistingPath(candidatePaths, packageName) { + for (const candidate of candidatePaths) { + try { + await stat(candidate); + return candidate; + } catch { + continue; + } + } + throw new Error(`unable to resolve package.json path for ${packageName}`); +} diff --git a/tools/workload-certification/compare-builder-determinism-matrix.mjs b/tools/workload-certification/compare-builder-determinism-matrix.mjs new file mode 100644 index 0000000..fa04932 --- /dev/null +++ b/tools/workload-certification/compare-builder-determinism-matrix.mjs @@ -0,0 +1,103 @@ +#!/usr/bin/env node + +import { readFile, readdir } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; + +const args = parseArgs(process.argv.slice(2)); +const inputDir = path.resolve(process.cwd(), args.inputDir); +const reportPaths = await findReports(inputDir); + +if (reportPaths.length === 0) { + throw new Error(`no builder-determinism-report.json files found under ${inputDir}`); +} + +const reports = []; +for (const reportPath of reportPaths) { + reports.push({ + path: reportPath, + payload: JSON.parse(await readFile(reportPath, 'utf8')), + }); +} + +const baseline = reports[0].payload; +const mismatches = []; +for (const report of reports.slice(1)) { + for (let index = 0; index < baseline.fixtures.length; index += 1) { + const baselineFixture = baseline.fixtures[index]; + const candidateFixture = report.payload.fixtures[index]; + if (!candidateFixture) { + mismatches.push({ + type: 'missing_fixture', + report: report.path, + fixtureIndex: index, + }); + continue; + } + if (baselineFixture.graphHash !== candidateFixture.graphHash) { + mismatches.push({ + type: 'graph_hash_mismatch', + report: report.path, + fixtureIndex: index, + baseline: baselineFixture.graphHash, + candidate: candidateFixture.graphHash, + }); + } + if (baselineFixture.canonicalHash !== candidateFixture.canonicalHash) { + mismatches.push({ + type: 'canonical_hash_mismatch', + report: report.path, + fixtureIndex: index, + baseline: baselineFixture.canonicalHash, + candidate: candidateFixture.canonicalHash, + }); + } + } +} + +const output = { + generatedAt: new Date().toISOString(), + inputDir, + reportCount: reports.length, + mismatchCount: mismatches.length, + reports: reports.map((report) => ({ + path: path.relative(inputDir, report.path), + checks: report.payload.checks, + })), + mismatches, +}; + +console.log(JSON.stringify(output, null, 2)); +if (mismatches.length > 0) { + process.exitCode = 1; +} + +async function findReports(targetDir) { + const entries = await readdir(targetDir, { withFileTypes: true }); + const reports = []; + for (const entry of entries) { + const entryPath = path.join(targetDir, entry.name); + if (entry.isDirectory()) { + reports.push(...(await findReports(entryPath))); + continue; + } + if (entry.name === 'builder-determinism-report.json') { + reports.push(entryPath); + } + } + return reports.sort(); +} + +function parseArgs(argv) { + let inputDir = 'artifacts'; + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--input-dir') { + inputDir = argv[index + 1] ?? inputDir; + index += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { inputDir }; +} diff --git a/tools/workload-certification/pack-public-tarballs.mjs b/tools/workload-certification/pack-public-tarballs.mjs new file mode 100644 index 0000000..2291a25 --- /dev/null +++ b/tools/workload-certification/pack-public-tarballs.mjs @@ -0,0 +1,75 @@ +#!/usr/bin/env node + +import { mkdir, readdir, unlink, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { spawn } from 'node:child_process'; +import { PUBLIC_PACKAGES } from './public-packages.mjs'; + +const repoRoot = process.cwd(); +const args = parseArgs(process.argv.slice(2)); +const outDir = path.resolve(repoRoot, args.outDir); +await mkdir(outDir, { recursive: true }); +for (const entry of await readdir(outDir)) { + if (entry.endsWith('.tgz')) { + await unlink(path.join(outDir, entry)); + } +} + +const packages = PUBLIC_PACKAGES; + +for (const pkg of packages) { + await run( + 'pnpm', + ['--filter', pkg, 'pack', '--pack-destination', outDir], + repoRoot, + ); +} + +const tarballs = await listTarballs(outDir); +const manifest = { + generatedAt: new Date().toISOString(), + outDir, + packages, + tarballs, +}; +const manifestPath = path.join(outDir, 'tarball-manifest.json'); +await writeFile(manifestPath, `${JSON.stringify(manifest, null, 2)}\n`, 'utf8'); + +console.log(JSON.stringify({ outDir, manifestPath, count: tarballs.length }, null, 2)); + +async function listTarballs(directory) { + const entries = await readdir(directory); + return entries.filter((entry) => entry.endsWith('.tgz')).sort(); +} + +async function run(command, argsList, cwd) { + await new Promise((resolve, reject) => { + const child = spawn(command, argsList, { + cwd, + stdio: 'inherit', + shell: false, + }); + child.on('exit', (code) => { + if (code === 0) { + resolve(undefined); + return; + } + reject(new Error(`command failed (${command} ${argsList.join(' ')}): ${code}`)); + }); + }); +} + +function parseArgs(argv) { + let outDir = 'artifacts/consumer-proof/tarballs'; + for (let i = 0; i < argv.length; i += 1) { + const arg = argv[i]; + if (arg === '--out-dir') { + outDir = argv[i + 1] ?? outDir; + i += 1; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return { outDir }; +} diff --git a/tools/workload-certification/public-packages.mjs b/tools/workload-certification/public-packages.mjs new file mode 100644 index 0000000..0e72757 --- /dev/null +++ b/tools/workload-certification/public-packages.mjs @@ -0,0 +1,9 @@ +export const PUBLIC_PACKAGES = [ + '@blue-quickjs/abi-manifest', + '@blue-quickjs/dv', + '@blue-quickjs/execution-profiles', + '@blue-quickjs/quickjs-wasm-constants', + '@blue-quickjs/quickjs-wasm', + '@blue-quickjs/quickjs-runtime', + '@blue-quickjs/deterministic-bundler', +]; diff --git a/tools/workload-certification/run-verdaccio-publish-rehearsal.mjs b/tools/workload-certification/run-verdaccio-publish-rehearsal.mjs new file mode 100644 index 0000000..c70d271 --- /dev/null +++ b/tools/workload-certification/run-verdaccio-publish-rehearsal.mjs @@ -0,0 +1,291 @@ +#!/usr/bin/env node + +import { mkdir, readFile, rm, writeFile } from 'node:fs/promises'; +import path from 'node:path'; +import process from 'node:process'; +import { spawn, spawnSync } from 'node:child_process'; +import { setTimeout as sleep } from 'node:timers/promises'; +import { URL } from 'node:url'; +import { PUBLIC_PACKAGES } from './public-packages.mjs'; + +const args = parseArgs(process.argv.slice(2)); +const repoRoot = process.cwd(); +const outDir = path.resolve(repoRoot, args.outDir); +const consumerAppDir = path.resolve(repoRoot, 'e2e/consumer-proof-app'); +const registryStoragePath = path.resolve(repoRoot, 'tmp/local-registry/storage'); +const listenAddress = resolveListenAddress(args.registryUrl); + +await rm(registryStoragePath, { recursive: true, force: true }); +await mkdir(outDir, { recursive: true }); + +const registryProcess = spawn( + 'pnpm', + [ + 'exec', + 'verdaccio', + '--config', + '.verdaccio/config.yml', + '--listen', + listenAddress, + ], + { + cwd: repoRoot, + stdio: 'pipe', + }, +); +let registryStdout = ''; +let registryStderr = ''; +registryProcess.stdout.on('data', (chunk) => { + registryStdout += chunk.toString(); +}); +registryProcess.stderr.on('data', (chunk) => { + registryStderr += chunk.toString(); +}); + +try { + await waitForRegistry(args.registryUrl, args.registryTimeoutMs); + + run( + 'pnpm', + [ + 'dlx', + 'npm-cli-login', + '-u', + 'ci-user', + '-p', + 'ci-password', + '-e', + 'ci@example.com', + '-r', + args.registryUrl, + ], + repoRoot, + ); + + run( + 'pnpm', + [ + 'nx', + 'run-many', + '-t', + 'build', + '-p', + 'dv,abi-manifest,execution-profiles,quickjs-wasm-constants,quickjs-runtime,deterministic-bundler', + ], + repoRoot, + ); + + const packageVersions = await resolvePublicPackageVersions(repoRoot); + const publishResults = []; + for (const pkg of PUBLIC_PACKAGES) { + const publish = run( + 'pnpm', + [ + '--filter', + pkg, + 'publish', + '--registry', + args.registryUrl, + '--no-git-checks', + '--access', + 'public', + '--tag', + 'rc', + '--force', + ], + repoRoot, + ); + publishResults.push({ + package: pkg, + version: packageVersions.get(pkg), + command: publish.command, + exitCode: publish.exitCode, + }); + } + + run('npm', ['install', '--no-fund', '--no-audit'], consumerAppDir); + run( + 'npm', + ['remove', '--no-save', ...PUBLIC_PACKAGES], + consumerAppDir, + { allowFailure: true }, + ); + run( + 'npm', + [ + 'install', + '--no-save', + '--force', + '--no-fund', + '--no-audit', + '--registry', + args.registryUrl, + ...PUBLIC_PACKAGES.map((pkg) => `${pkg}@${packageVersions.get(pkg)}`), + ], + consumerAppDir, + ); + + if (!args.skipPlaywrightInstall) { + run( + 'pnpm', + ['--dir', 'e2e/consumer-proof-app', 'exec', 'playwright', 'install', '--with-deps', 'chromium'], + repoRoot, + ); + } + + run( + 'pnpm', + ['--dir', 'e2e/consumer-proof-app', 'run', 'repro', '--', '--browser', 'chromium'], + repoRoot, + ); + + const reproReportPath = path.join( + consumerAppDir, + 'reports', + 'reproducibility-report.json', + ); + const reproReport = JSON.parse(await readFile(reproReportPath, 'utf8')); + + const output = { + generatedAt: new Date().toISOString(), + registryUrl: args.registryUrl, + packageCount: PUBLIC_PACKAGES.length, + publishedPackages: publishResults, + consumerReportPath: path.relative(repoRoot, reproReportPath), + consumerParity: reproReport.parity ?? null, + }; + + const outputPath = path.join(outDir, 'verdaccio-publish-rehearsal.json'); + await writeFile(outputPath, `${JSON.stringify(output, null, 2)}\n`, 'utf8'); + await writeFile(path.join(outDir, 'verdaccio-stdout.log'), registryStdout, 'utf8'); + await writeFile(path.join(outDir, 'verdaccio-stderr.log'), registryStderr, 'utf8'); + + process.stdout.write( + `${JSON.stringify( + { + outputPath: path.relative(repoRoot, outputPath), + registryUrl: args.registryUrl, + consumerParity: output.consumerParity, + }, + null, + 2, + )}\n`, + ); +} finally { + if (!registryProcess.killed) { + registryProcess.kill('SIGTERM'); + } + await waitForExit(registryProcess, 5000); + run('npm', ['config', 'set', 'registry', 'https://registry.npmjs.org/'], repoRoot, { + allowFailure: true, + }); + run('npm', ['config', 'delete', '//127.0.0.1:4873/:_authToken'], repoRoot, { + allowFailure: true, + }); +} + +async function resolvePublicPackageVersions(repoRootPath) { + const versionMap = new Map(); + for (const pkg of PUBLIC_PACKAGES) { + const packageJsonPath = path.resolve( + repoRootPath, + 'libs', + pkg.replace('@blue-quickjs/', ''), + 'package.json', + ); + const packageJson = JSON.parse(await readFile(packageJsonPath, 'utf8')); + versionMap.set(pkg, packageJson.version); + } + return versionMap; +} + +async function waitForRegistry(registryUrl, timeoutMs) { + const deadline = Date.now() + timeoutMs; + while (Date.now() < deadline) { + try { + const response = await fetch(`${registryUrl}/-/ping`); + if (response.ok) { + return; + } + } catch { + // ignore while waiting + } + await sleep(500); + } + throw new Error(`verdaccio did not become ready within ${timeoutMs}ms`); +} + +function run(command, args, cwd, options = {}) { + const result = spawnSync(command, args, { + cwd, + encoding: 'utf8', + stdio: 'pipe', + env: { + ...process.env, + ...(options.env ?? {}), + }, + input: options.input, + }); + if (result.status !== 0 && !options.allowFailure) { + throw new Error( + `command failed (${command} ${args.join(' ')}): ${result.stderr ?? result.stdout}`, + ); + } + return { + command: `${command} ${args.join(' ')}`, + exitCode: result.status, + stdout: result.stdout, + stderr: result.stderr, + }; +} + +async function waitForExit(child, timeoutMs) { + await Promise.race([ + new Promise((resolve) => { + child.once('exit', () => resolve(undefined)); + }), + sleep(timeoutMs), + ]); +} + +function parseArgs(argv) { + const parsed = { + outDir: 'artifacts/consumer-proof/verdaccio', + registryUrl: 'http://127.0.0.1:4873', + registryTimeoutMs: 60000, + skipPlaywrightInstall: false, + }; + + for (let index = 0; index < argv.length; index += 1) { + const arg = argv[index]; + if (arg === '--') { + continue; + } + if (arg === '--out-dir') { + parsed.outDir = argv[index + 1] ?? parsed.outDir; + index += 1; + continue; + } + if (arg === '--registry-url') { + parsed.registryUrl = argv[index + 1] ?? parsed.registryUrl; + index += 1; + continue; + } + if (arg === '--registry-timeout-ms') { + parsed.registryTimeoutMs = Number(argv[index + 1] ?? parsed.registryTimeoutMs); + index += 1; + continue; + } + if (arg === '--skip-playwright-install') { + parsed.skipPlaywrightInstall = true; + continue; + } + throw new Error(`unknown argument: ${arg}`); + } + return parsed; +} + +function resolveListenAddress(registryUrl) { + const parsed = new URL(registryUrl); + return `${parsed.hostname}:${parsed.port}`; +} diff --git a/tsconfig.json b/tsconfig.json index 433edb1..1486732 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -29,6 +29,24 @@ }, { "path": "./libs/quickjs-wasm-constants" + }, + { + "path": "./libs/deterministic-bundler" + }, + { + "path": "./libs/deterministic-builder" + }, + { + "path": "./libs/execution-profiles" + }, + { + "path": "./tools/blue-quickjs-cli" + }, + { + "path": "./apps/ecosystem-certifier" + }, + { + "path": "./apps/bluequickjs-playground" } ] } diff --git a/vendor/README.md b/vendor/README.md index cddd76e..f3055e4 100644 --- a/vendor/README.md +++ b/vendor/README.md @@ -1,6 +1,6 @@ # QuickJS submodule -This repo pins the QuickJS fork as a git submodule at `vendor/quickjs` with origin `git@blue.github.com:mjwebblue/quickjs.git`. +This repo pins the QuickJS fork as a git submodule at `vendor/quickjs` with origin `git@github.com:bluecontract/quickjs.git`. ## Clone / init - From a fresh clone run: `git submodule update --init --recursive` to populate `vendor/quickjs`. diff --git a/vendor/quickjs b/vendor/quickjs index 9d1eda6..8b3253b 160000 --- a/vendor/quickjs +++ b/vendor/quickjs @@ -1 +1 @@ -Subproject commit 9d1eda6e0d1ec36c279d87380db77fbcc3acbae8 +Subproject commit 8b3253bddf6a5a792dd098b1a8a154f534b88586
+

Use these docs to learn the current selection and verify its deterministic scope.

+
+