diff --git a/astro.config.mjs b/astro.config.mjs
index 347b6fd..9fb1778 100644
--- a/astro.config.mjs
+++ b/astro.config.mjs
@@ -3,6 +3,7 @@ import { defineConfig } from 'astro/config';
import pagefind from 'astro-pagefind';
import sitemap from '@astrojs/sitemap';
import { execSync } from 'node:child_process';
+import rehypeLinkCards, { linkCardsReport } from './src/lib/rehype-link-cards';
// 构建透明(T7):commit/时间经 vite.define 注入,页脚与 /about 引用。
// 四重回退:CI 环境变量优先(GITEA_ACTIONS/GITHUB_SHA)→ 本地 git → dev 占位。
@@ -17,7 +18,11 @@ const date =
export default defineConfig({
site: 'https://wait4x.online',
- integrations: [pagefind(), sitemap()],
+ integrations: [pagefind(), sitemap(), linkCardsReport()],
+ markdown: {
+ // 独立成段的裸链接 → OG 预览卡(构建期抓取,失败回落普通链接;见 src/lib/rehype-link-cards.ts)
+ rehypePlugins: [rehypeLinkCards],
+ },
i18n: {
defaultLocale: 'zh',
locales: ['zh', 'en'],
diff --git a/content/.link-cache.json b/content/.link-cache.json
new file mode 100644
index 0000000..e7eec4a
--- /dev/null
+++ b/content/.link-cache.json
@@ -0,0 +1,31 @@
+{
+ "_readme": "链接卡片抓取缓存(构建确定性需求,入仓)。键=URL,值={title,desc,image,favicon,ts};ts 超 30 天刷新。手工改动安全:删条目即下次构建重抓。",
+ "https://www.cnblogs.com/Lenbrother/p/18673403": {
+ "title": "Debian 安装 Docker - 神奇小宝 - 博客园",
+ "desc": "卸载已有 Docker 如果你之前安装过 Docker Engine 之前,你需要卸载旧版本,避免冲突: for pkg in docker.io docker-doc docker-compose podman-docker containerd runc; do sudo apt-get rem",
+ "image": "https://assets.cnblogs.com/images/wechat-share.jpg",
+ "favicon": "https://assets.cnblogs.com/favicon_v3_3.ico",
+ "ts": 1793593758751
+ },
+ "https://wait4x.online/": {
+ "title": "wait4x",
+ "desc": "wait4x 的博客:阅读 · 技术 · 摄影",
+ "image": "",
+ "favicon": "https://wait4x.online/favicon.svg",
+ "ts": 1793593759184
+ },
+ "https://blog.csdn.net/qq_40605167/article/details/122888580": {
+ "title": "Docker版 E5续订的E5调用API续订服务:Microsoft 365 E5 Renew X_e5 docker",
+ "desc": "文章浏览阅读2.7w次,点赞10次,收藏43次。本文介绍了如何使用Docker轻松部署Microsoft365E5续订服务,包括提供小巧的镜像、一键部署命令及邮箱通知功能。用户需要具备Docker基础,并按照步骤修改邮箱和密码等参数。此外,还提供了不同CPU架构的支持。注意,已有部分账号出现被关停的情况。文章附带了Docker环境搭建教程和相关资源链接。",
+ "image": "https://i-blog.csdnimg.cn/blog_migrate/cover/dc9f6540d4d4330e797f1ebd0261f736.png",
+ "favicon": "https://g.csdnimg.cn/static/logo/favicon32.ico",
+ "ts": 1793593759739
+ },
+ "https://astro.build/": {
+ "title": "Astro",
+ "desc": "Astro builds fast content sites, powerful web applications, dynamic server APIs, and everything in-between.",
+ "image": "https://astro.build/og/astro.jpg",
+ "favicon": "https://astro.build/favicon.svg",
+ "ts": 1793593759816
+ }
+}
diff --git a/content/posts/link-cards-test.md b/content/posts/link-cards-test.md
new file mode 100644
index 0000000..e7d332b
--- /dev/null
+++ b/content/posts/link-cards-test.md
@@ -0,0 +1,30 @@
+---
+title: "链接卡片样例"
+pubDate: 2026-11-02
+category: tech
+tags: [test, hidden]
+# 链接卡片(OG 预览)测试样张:hidden 不列出,构建验证用;保留为活样例
+draft: false
+---
+
+本篇验证链接卡片:独立成段的裸链接转 OG 预览卡,内联链接保持普通样式。
+
+## 正例:有 OG 的站点
+
+https://wait4x.online/
+
+https://astro.build/
+
+## 反例:404 与无 OG 站点(应回落普通链接,构建不报错)
+
+https://wait4x.online/definitely-not-a-real-page-404/
+
+https://example.com/
+
+## 内联链接保持普通样式(不应变卡)
+
+这里有一个内联链接 [Astro 官网](https://astro.build/) 夹在句子中间,它必须保持普通链接样式,不能整篇变卡片墙。
+
+## 卡片首行文字(markdown 链接形态同样触发)
+
+[wait4x.online 首页](https://wait4x.online/)
diff --git a/package.json b/package.json
index 6f2a931..9937dcf 100644
--- a/package.json
+++ b/package.json
@@ -23,6 +23,7 @@
"sharp": "^0.35.5"
},
"devDependencies": {
+ "@astrojs/markdown-remark": "^7.3.5",
"@fontsource/noto-serif-sc": "^5.3.1",
"playwright": "^1.64.1"
}
diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml
index 7053d36..8af9da9 100644
--- a/pnpm-lock.yaml
+++ b/pnpm-lock.yaml
@@ -28,10 +28,10 @@ importers:
version: 5.3.1
astro:
specifier: ^7.3.8
- version: 7.3.8(@types/node@24.19.2)(yaml@2.9.1)
+ version: 7.3.8(@astrojs/markdown-remark@7.3.5)(@types/node@24.19.2)(yaml@2.9.1)
astro-pagefind:
specifier: ^2.0.1
- version: 2.0.1(astro@7.3.8(@types/node@24.19.2)(yaml@2.9.1))
+ version: 2.0.1(astro@7.3.8(@astrojs/markdown-remark@7.3.5)(@types/node@24.19.2)(yaml@2.9.1))
exifr:
specifier: ^7.1.3
version: 7.1.3
@@ -42,6 +42,9 @@ importers:
specifier: ^0.35.5
version: 0.35.5(@types/node@24.19.2)
devDependencies:
+ '@astrojs/markdown-remark':
+ specifier: ^7.3.5
+ version: 7.3.5
'@fontsource/noto-serif-sc':
specifier: ^5.3.1
version: 5.3.1
@@ -125,6 +128,12 @@ packages:
'@astrojs/internal-helpers@0.12.0':
resolution: {integrity: sha512-pKPuwCDtO0L7zgmt1JGd9X4Aes1+0SX3IEBSqBNPHsScYdPMlfmed3Y7DTbXyF7E+8ylnb563o/0OzGQPOFehw==}
+ '@astrojs/internal-helpers@0.13.0':
+ resolution: {integrity: sha512-20jxQqnSmpskcGyad7N5l6Xf1gz0UCa6lNde44bEBdaXGpncEYfAZJ142r2ZgzBaG4dUyzGmhqZWv1INU2eiHQ==}
+
+ '@astrojs/markdown-remark@7.3.5':
+ resolution: {integrity: sha512-Xk0gvOMEpBul2zj5jZXS5WH2Gng/6dW7c3WWLXgip+LZGpY64frwTvBChznMtpnNIqVgFXSsu44RYrISojcodQ==}
+
'@astrojs/markdown-satteri@0.4.3':
resolution: {integrity: sha512-PFbEHPnwUlLvpXd7RXrrKM+j12akF4bG+DSuNuoN+3eiwjOwp4HaPi+QQdbkBV7QEYXmzyKca50OJsmGxhNIUA==}
@@ -132,6 +141,10 @@ packages:
resolution: {integrity: sha512-KTivpmnz6lDsC6o9H4+DNm2SrE/GHzw8cNAvEJwAvUT+eoaEnn/4NtbDNfRRaxaJHdp15gf+tfHAWiXR4wB3BA==}
engines: {node: '>=22.12.0'}
+ '@astrojs/prism@4.1.2':
+ resolution: {integrity: sha512-jMrUEpFDarDO1KWPvVc9eSa8DSfwBlwEOHwX+8zvZQpiqXRGDxFnOXHsYqV6DP7w+0qIgTr98gS1GdQlm8ypWg==}
+ engines: {node: '>=22.23.4'}
+
'@astrojs/rss@4.0.19':
resolution: {integrity: sha512-e+z5wYeYtffQdHQO8c2tkSd2JEBdAuRXJV4ZEU5IxkYeE6e39woDd7nw1PH1Kk2tEYNCYuKdylnnbhGmt61awA==}
@@ -418,6 +431,9 @@ packages:
'@jridgewell/sourcemap-codec@1.6.0':
resolution: {integrity: sha512-T7jf+5zgsZHwNJ4lvQ7/aezbyk0nNX+zJVWpmHA7VYsEx7a7qr5Rg5IbtJFqkgze5Y2sruq1RUY8Q837Od7iFw==}
+ '@mdx-js/mdx@3.1.1':
+ resolution: {integrity: sha512-f6ZO2ifpwAQIpzGWaBQT2TXxPv6z3RBzQKpVftEWN78Vl/YweF1uwussDx8ECAXVtr3Rs89fKyG9YlzUs9DyGQ==}
+
'@napi-rs/wasm-runtime@1.2.5':
resolution: {integrity: sha512-HshSvXzmBxNzqejd3k/KemgQ3hdREUYFRRrgxOZ+gPljDIsO2SDZrVZMd4Z/HsxudQbE62OVyVFE8z9BCurfjA==}
engines: {node: ^20.19.0 || ^22.13.0 || >=23.5.0}
@@ -608,6 +624,9 @@ packages:
'@tybys/wasm-util@0.10.4':
resolution: {integrity: sha512-W3c4gRigFS0T/Ma4qIYF3GDAc5AQdHb1yL5znJT1Zv1YaD9Kitx656wBjvr19qbiosmZT8lWDM5BEMynUqX65A==}
+ '@types/debug@4.1.13':
+ resolution: {integrity: sha512-KSVgmQmzMwPlmtljOomayoR89W4FynCAi3E8PPs7vmDVPe84hT+vGPKkJfThkmXs0x0jAaa9U8uW8bbfyS2fWw==}
+
'@types/estree-jsx@1.0.5':
resolution: {integrity: sha512-52CcUVNFyfb1A2ALocQw/Dd1BQFNmSdkuC3BkZ6iqhdMfQz7JWOFRuJFloOzjk+6WijU56m9oKXFAXc7o3Towg==}
@@ -620,6 +639,12 @@ packages:
'@types/mdast@4.0.4':
resolution: {integrity: sha512-kGaNbPh1k7AFzgpud/gMdvIm5xuECykRR+JnWKQno9TAXVa6WIVCGTPvYGekIDL4uwCZQSYbUxNBSb1aUo79oA==}
+ '@types/mdx@2.0.14':
+ resolution: {integrity: sha512-T48PeuJtvLosNTPVhfnIp3i/n3a4g4Bad7YCq5k64D4u7NwDrAotikQ+5+sjtUvBmxCMlbo3dVL+C2dP0rWHzg==}
+
+ '@types/ms@2.1.0':
+ resolution: {integrity: sha512-GsCCIZDE/p3i96vtEqx+7dBUGXrc7zeSK3wwPHIaRThS+9OhWIXRqzs4d6k1SVU8g91DrNRWxWUGhp5KXQb2VA==}
+
'@types/nlcst@2.0.3':
resolution: {integrity: sha512-vSYNSDe6Ix3q+6Z7ri9lyWqgGhJTmzRjZRqyq15N0Z/1/UnVsno9G/N40NBijoYx2seFDIl0+B2mgAb9mezUCA==}
@@ -629,12 +654,25 @@ packages:
'@types/sax@1.2.7':
resolution: {integrity: sha512-rO73L89PJxeYM3s3pPPjiPgVVcymqU490g0YO5n5By0k2Erzj6tay/4lr1CHAAU4JyOWd1rpQ8bCf6cZfHU96A==}
+ '@types/unist@2.0.11':
+ resolution: {integrity: sha512-CmBKiL6NNo/OqgmMn95Fk9Whlp2mtvIv+KNpQKN2F4SjvrEesubTRWGYSg+BnWZOnlCaSTU1sMpsBOzgbYhnsA==}
+
'@types/unist@3.0.3':
resolution: {integrity: sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==}
'@ungap/structured-clone@1.4.0':
resolution: {integrity: sha512-1mEZtMKPM09vDmQt5y7YvmN2+DFTP7Tg0EWXdic8/C6VRnpb33e4ghisCIE3WZjsE2N8mf+QV1Zqh7ZFYLWInQ==}
+ acorn-jsx@5.3.2:
+ resolution: {integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==}
+ peerDependencies:
+ acorn: ^6.0.0 || ^7.0.0 || ^8.0.0
+
+ acorn@8.19.0:
+ resolution: {integrity: sha512-oJlA3XiRm7Cyk6qFD2Jn8ak9B7jSy0qy00ADO3+8dpT0LSjFihQYv4C02LFCSYJV3Q37xYwwRy5m+IpIiUzqWw==}
+ engines: {node: '>=0.4.0'}
+ hasBin: true
+
adequate-little-templates@1.0.2:
resolution: {integrity: sha512-d0tFFG538l3Y4CElRKtticzrMr/OGohs32/nf3Ewn8rbTMBYwkVNe8mPdXWrDnMlz+ZVUFQjsTmsBD5zCtU4wg==}
engines: {node: '>=14'}
@@ -657,6 +695,13 @@ packages:
resolution: {integrity: sha512-COROpnaoap1E2F000S62r6A60uHZnmlvomhfyT2DlTcrY1OrBKn2UhH7qn5wTC9zMvD0AY7csdPSNwKP+7WiQw==}
engines: {node: '>= 0.4'}
+ array-iterate@2.0.1:
+ resolution: {integrity: sha512-I1jXZMjAgCMmxT4qxXfPXa6SthSoE8h6gkSI9BGGNv8mP8G/v0blc+qFnZu6K42vTOiuME596QaLO0TP3Lk0xg==}
+
+ astring@1.9.0:
+ resolution: {integrity: sha512-LElXdjswlqjWrPpJFg1Fx4wpkOCxj1TDHlSV4PlaRxHGWko024xICaa97ZkMfs6DRKlCguiAI+rbXv5GWwXIkg==}
+ hasBin: true
+
astro-pagefind@2.0.1:
resolution: {integrity: sha512-zhMTctuVuKrYH1C0Xl+p8mhexEuxVrqfT8paQOAbKZFtgUIWAMtR2nCeU11ti4Rfeit16LhiCxZFwjOqYoiaNQ==}
peerDependencies:
@@ -694,6 +739,12 @@ packages:
character-entities-legacy@3.0.0:
resolution: {integrity: sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==}
+ character-entities@2.0.2:
+ resolution: {integrity: sha512-shx7oQ0Awen/BRIdkjkvz54PnEEI/EjwXDSIZp86/KKdbafHh1Df/RYGBhn4hbe2+uKC9FnT5UCEdyPz3ai9hQ==}
+
+ character-reference-invalid@2.0.1:
+ resolution: {integrity: sha512-iBZ4F4wRbyORVsu0jPV7gXkOsGYjGHPmAyv+HiHG8gi5PtC9KI2j1+v8/tlibRvjoWX027ypmG/n0HtO5t7unw==}
+
chokidar@5.0.0:
resolution: {integrity: sha512-TQMmc3w+5AxjpL8iIiwebF73dRDF4fBIieAqGn9RGCWaEVwQ6Fb2cGe31Yns0RRIzii5goJ1Y7xbMwo1TxMplw==}
engines: {node: '>= 20.19.0'}
@@ -706,6 +757,9 @@ packages:
resolution: {integrity: sha512-eYm0QWBtUrBWZWG0d386OGAw16Z995PiOVo2B7bjWSbHedGl5e0ZWaq65kOGgUSNesEIDkB9ISbTg/JK9dhCZA==}
engines: {node: '>=6'}
+ collapse-white-space@2.1.0:
+ resolution: {integrity: sha512-loKTxY1zCOuG4j9f6EPnuyyYkf58RnhhWTvRoZEokgB+WbdXehfjFviyOVYkqzEWz1Q5kRiZdBYS5SwxbQYwzw==}
+
comma-separated-tokens@2.0.3:
resolution: {integrity: sha512-Fu4hJdvzeylCfQPp9SGWidpzrMs7tTrlu6Vb8XGaRGck8QSNZJJp538Wrb60Lax4fPwR64ViY468OIUTbRlGZg==}
@@ -746,6 +800,18 @@ packages:
resolution: {integrity: sha512-0LrrStPOdJj+SPCCrGhzryycLjwcgUSHBtxNA8aIDxf0GLsRh1cKYhB00Gd1lDOS4yGH69+SNn13+TWbVHETFQ==}
engines: {node: ^10 || ^12.20.0 || ^14.13.0 || >=15.0.0, npm: '>=7.0.0'}
+ debug@4.4.3:
+ resolution: {integrity: sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==}
+ engines: {node: '>=6.0'}
+ peerDependencies:
+ supports-color: '*'
+ peerDependenciesMeta:
+ supports-color:
+ optional: true
+
+ decode-named-character-reference@1.3.0:
+ resolution: {integrity: sha512-GtpQYB283KrPp6nRw50q3U9/VfOutZOe103qlN7BPP6Ad27xYnOIWv4lPzo8HCAL+mMZofJ9KEy30fq6MfaK6Q==}
+
defu@6.1.7:
resolution: {integrity: sha512-7z22QmUWiQ/2d0KkdYmANbRUVABpZ9SNYyH5vx6PZ+nE5bcC0l7uFvEfHlyld/HcGBFTL536ClDt3DEcSlEJAQ==}
@@ -791,9 +857,44 @@ packages:
resolution: {integrity: sha512-wEJa03bJgqEwPnkUqYdgmcfUXfm6+4hePQhntIvRy/1/+C4dFuhYHsgKBRjbQ6OWBh42P+VhAoCDO77DUh0e/Q==}
engines: {node: '>=0.12'}
+ entities@4.3.0:
+ resolution: {integrity: sha512-/iP1rZrSEJ0DTlPiX+jbzlA3eVkY/e8L8SozroF395fIqE3TYF/Nz7YOMAawta+vLmyJ/hkGNNPcSbMADCCXbg==}
+ engines: {node: '>=0.12'}
+
es-module-lexer@3.0.4:
resolution: {integrity: sha512-BldNY5mwkVu+cQ5Ymn3e6hB9Sx8XHx4ZevWbiUyZbfKxJxYO27Hf0wfzkxIaD5CAJMaGl3YspKELj0ff/7nCMA==}
+ esast-util-from-estree@2.0.0:
+ resolution: {integrity: sha512-4CyanoAudUSBAn5K13H4JhsMH6L9ZP7XbLVe/dKybkxMO7eDyLsT8UHl9TRNrU2Gr9nz+FovfSIjuXWJ81uVwQ==}
+
+ esast-util-from-js@2.0.1:
+ resolution: {integrity: sha512-8Ja+rNJ0Lt56Pcf3TAmpBZjmx8ZcK5Ts4cAzIOjsjevg9oSXJnl6SUQ2EevU8tv3h6ZLWmoKL5H4fgWvdvfETw==}
+
+ escape-string-regexp@5.0.0:
+ resolution: {integrity: sha512-/veY75JbMK4j1yjvuUxuVsiS/hr/4iHs9FTT6cgTexxdE0Ly/glccBAkloH/DofkjRbZU3bnoj38mOmhkZ0lHw==}
+ engines: {node: '>=12'}
+
+ estree-util-attach-comments@3.0.0:
+ resolution: {integrity: sha512-cKUwm/HUcTDsYh/9FgnuFqpfquUbwIqwKM26BVCGDPVgvaCl/nDCCjUfiLlx6lsEZ3Z4RFxNbOQ60pkaEwFxGw==}
+
+ estree-util-build-jsx@3.0.1:
+ resolution: {integrity: sha512-8U5eiL6BTrPxp/CHbs2yMgP8ftMhR5ww1eIKoWRMlqvltHF8fZn5LRDvTKuxD3DUn+shRbLGqXemcP51oFCsGQ==}
+
+ estree-util-is-identifier-name@3.0.0:
+ resolution: {integrity: sha512-hFtqIDZTIUZ9BXLb8y4pYGyk6+wekIivNVTcmvk8NoOh+VeRn5y6cEHzbURrWbfp1fIqdVipilzj+lfaadNZmg==}
+
+ estree-util-scope@1.0.1:
+ resolution: {integrity: sha512-B0np3dcdxqILX5e9nEi5/Fr4K7gL4oYFVPV1zRa2e9wRCbQoZZNWOZFYyoInvXUPJXBXjss+QXlWLJChDEHDkA==}
+
+ estree-util-to-js@2.0.0:
+ resolution: {integrity: sha512-WDF+xj5rRWmD5tj6bIqRi6CkLIXbbNQUcxQHzGysQzvHmdYG2G7p/Tf0J0gpxGgkeMZNTIjT/AoSvC9Xehcgdg==}
+
+ estree-util-visit@2.0.0:
+ resolution: {integrity: sha512-m5KgiH85xAhhW8Wta0vShLcUvOsh3LLPI2YVwcbio1l7E09NTLL1EyMZFM1OyWowoH0skScNbhOPl4kcBgzTww==}
+
+ estree-walker@3.0.3:
+ resolution: {integrity: sha512-7RUKfXgSMMkzt6ZuXmqapOurLGPPfgj6l9uRZ7lRGolvk0y2yocc35LdcxKC5PQZdn2DMqioAQ2NoWcrTKmm6g==}
+
eventemitter3@5.0.4:
resolution: {integrity: sha512-mlsTRyGaPBjPedk6Bvw+aqbsXDtoAyAzm5MO7JgU+yVRyMQ5O8bD4Kcci7BS85f93veegeCPkL8R4GLClnjLFw==}
@@ -858,12 +959,39 @@ packages:
h3@1.15.11:
resolution: {integrity: sha512-L3THSe2MPeBwgIZVSH5zLdBBU90TOxarvhK9d04IDY2AmVS8j2Jz2LIWtwsGOU3lu2I5jCN7FNvVfY2+XyF+mg==}
- hast-util-to-html@9.0.5:
- resolution: {integrity: sha512-OguPdidb+fbHQSU4Q4ZiLKnzWo8Wwsf5bZfbvu7//a9oTYoqD/fWpe96NuHkoS9h0ccGOTe0C4NGXdtS0iObOw==}
+ hast-util-from-html@2.0.3:
+ resolution: {integrity: sha512-CUSRHXyKjzHov8yKsQjGOElXy/3EKpyX56ELnkHH34vDVw1N1XSQ1ZcAvTyAPtGqLTuKP/uxM+aLkSPqF/EtMw==}
+
+ hast-util-from-parse5@8.0.4:
+ resolution: {integrity: sha512-Yq7XlXor0Cpb71sI2E0zpv8QxQ5a6rfhDEETk4bcgrFX2SvJAY2PHocWwFtL6U9qyfiyByW3wZ6sZEfP2kW81g==}
+
+ hast-util-parse-selector@4.0.0:
+ resolution: {integrity: sha512-wkQCkSYoOGCRKERFWcxMVMOcYE2K1AaNLU8DXS9arxnLOUEWbOXKXiJUNzEpqZ3JOKpnha3jkFrumEjVliDe7A==}
+
+ hast-util-raw@9.1.0:
+ resolution: {integrity: sha512-Y8/SBAHkZGoNkpzqqfCldijcuUKh7/su31kEBp67cFY09Wy0mTRgtsLYsiIxMJxlu0f6AA5SUTbDR8K0rxnbUw==}
+
+ hast-util-to-estree@3.1.3:
+ resolution: {integrity: sha512-48+B/rJWAp0jamNbAAf9M7Uf//UVqAoMmgXhBdxTDJLGKY+LRnZ99qcG+Qjl5HfMpYNzS5v4EAwVEF34LeAj7w==}
+
+ hast-util-to-html@9.0.6:
+ resolution: {integrity: sha512-1SZUxCN3TtJAE7e2BQN2MBHsoZ1gnmi9GoCP5Di59CSWptIezSAW09yDZyVbanb78V9eCwrKqdQsjtfVTxYHWA==}
+
+ hast-util-to-jsx-runtime@2.3.7:
+ resolution: {integrity: sha512-F7DNV2NMcTxA4GqPVHnXzX+mpoPHAIY9rJAVH3CZ1FdBZOcBUEjUuvMkMpHVs/sicEtznh9tMGj5WUR9S4E2rg==}
+
+ hast-util-to-parse5@8.0.1:
+ resolution: {integrity: sha512-MlWT6Pjt4CG9lFCjiz4BH7l9wmrMkfkJYCxFwKQic8+RTZgWPuWxwAfjJElsXkex7DJjfSJsQIt931ilUgmwdA==}
+
+ hast-util-to-text@4.0.3:
+ resolution: {integrity: sha512-5yrlWOvGFs6CqHriUpSsNrjzT/Tdo+IOQudbznxOn8K5qblp18MJyzOg8IgDOKQ8MYgQcJA7SusuCjSpDr8mSA==}
hast-util-whitespace@3.0.0:
resolution: {integrity: sha512-88JUN06ipLwsnv+dVn+OIYOvAuvBMy/Qoi6O7mQHxdPXpjy+Cd6xRkWwux7DKO+4sYILtLBRIKgsdpS2gQc7qw==}
+ hastscript@9.0.3:
+ resolution: {integrity: sha512-1ALZXSmCGmW3h8AMz4R4+QKSKFi7sNgXLVwmwB8FYVtl1CwQ3WDkSAEY/d5tp1g/vbQgq2s1WlHgfO3jbw1TsA==}
+
html-escaper@3.0.3:
resolution: {integrity: sha512-RuMffC89BOWQoY0WKGpIhn5gX3iI54O6nRA0yC124NYVtzjmFWBIiFd8M0x+ZdX0P9R4lADg1mgP8C7PxGOWuQ==}
@@ -873,6 +1001,12 @@ packages:
http-cache-semantics@4.3.0:
resolution: {integrity: sha512-M5t5LlJpS1UHMjvwRQVdFHvPISGeLAxNcrWuJkeGh0KxsqCHZ1O3NXZU/8x7cD0BDcGW8kapxMKTvwlqrNkHkA==}
+ inline-style-parser@0.1.1:
+ resolution: {integrity: sha512-7NXolsK4CAS5+xvdj5OMMbI962hU/wvwoxk+LWR9Ek9bVtyuuYScDN6eS0rUm6TxApFpw7CX1o4uJzcd4AyD3Q==}
+
+ inline-style-parser@0.2.9:
+ resolution: {integrity: sha512-IttN8BqKLxzUrnTqHI+/hwAJQItBAUjdoHERCDv+oOuX48VP6bzW8+QjOXSfoevzq3YrYAwX1uLHp8TqO9yIeg==}
+
iron-webcrypto@1.2.1:
resolution: {integrity: sha512-feOM6FaSr6rEABp/eDfVseKyTMDt+KGpeB35SkVn9Tyn0CqvVsY3EwI0v5i8nMHyJnzCIQf7nsy3p41TPkJZhg==}
@@ -890,6 +1024,9 @@ packages:
engines: {node: '>=20'}
hasBin: true
+ is-hexadecimal@2.0.1:
+ resolution: {integrity: sha512-DgZQp241c8oO6cA1SbTEWiXeoxV42vlcJxgH+B3hi1AiqqKruZR3ZGF8In3fj4+/y/7rHvlOZLZtgJ/4ttYGZg==}
+
is-plain-obj@4.1.0:
resolution: {integrity: sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg==}
engines: {node: '>=12'}
@@ -974,6 +1111,9 @@ packages:
resolution: {integrity: sha512-WkUDrojuJs0xkgGf2udWxa3yGBRxPtxUkB79i6aCZLRgc7PM8fZe9TosfPDcvEpQZbuFASnHYmRLBLUbmLOIIA==}
engines: {node: '>= 12.0.0'}
+ longest-streak@3.1.0:
+ resolution: {integrity: sha512-9Ri+o0JYgehTaVBBDoMqIl8GXtbWg711O3srftcHhZ0dqnETqLaoIK0x17fUw9rFSlK/0NlsKe0Ahhyl5pXE2g==}
+
lru-cache@11.5.3:
resolution: {integrity: sha512-U4N8FgzmWxc8k1VH8Kr6lQg18U7Fjvby6wXHVRX/ZZ7IwWbRMgrRbP0Wrb5q5NVinryp4SQampHKdvtecItxUg==}
engines: {node: 20 || >=22}
@@ -987,34 +1127,185 @@ packages:
magicast@0.5.5:
resolution: {integrity: sha512-UicdXN8zQ3JHlxVq+28afMXPr1z7WNY6+7EJnzTdQWkTAlMLF5fNCCKxJHBQwGaNGR11581EiQmQzx73+MvszA==}
+ markdown-extensions@2.0.0:
+ resolution: {integrity: sha512-o5vL7aDWatOTX8LzaS1WMoaoxIiLRQJuIKKe2wAw6IeULDHaqbiqiggmx+pKvZDb1Sj+pE46Sn1T7lCqfFtg1Q==}
+ engines: {node: '>=16'}
+
+ markdown-table@3.0.4:
+ resolution: {integrity: sha512-wiYz4+JrLyb/DqW2hkFJxP7Vd7JuTDm77fvbM8VfEQdmSMqcImWeeRbHwZjBjIFki/VaMK2BhFi7oUUZeM5bqw==}
+
+ mdast-util-definitions@6.0.0:
+ resolution: {integrity: sha512-scTllyX6pnYNZH/AIp/0ePz6s4cZtARxImwoPJ7kS42n+MnVsI4XbnG6d4ibehRIldYMWM2LD7ImQblVhUejVQ==}
+
+ mdast-util-find-and-replace@3.0.4:
+ resolution: {integrity: sha512-z4B5c6jrnJ1ltOQemhWYPBSAo6y42Z8Gt2yEgfgNTMcLSU59B8bfj8Z8AnAlJrBGLnqkdAUZ7jdDEqQw3KuipQ==}
+
+ mdast-util-from-markdown@2.1.0:
+ resolution: {integrity: sha512-KRLgmPaP2H1ul2bpoJkOS+9pAcDAAj9Nu1mqLnh8NLeJG5tlvj42TH80PIGBpROWlRXLk0lDrWNuZCFy/tsB4A==}
+
+ mdast-util-gfm-autolink-literal@2.0.1:
+ resolution: {integrity: sha512-5HVP2MKaP6L+G6YaxPNjuL0BPrq9orG3TsrZ9YXbA3vDw/ACI4MEsnoDpn6ZNm7GnZgtAcONJyPhOP8tNJQavQ==}
+
+ mdast-util-gfm-footnote@2.1.0:
+ resolution: {integrity: sha512-sqpDWlsHn7Ac9GNZQMeUzPQSMzR6Wv0WKRNvQRg0KqHh02fpTz69Qc1QSseNX29bhz1ROIyNyxExfawVKTm1GQ==}
+
+ mdast-util-gfm-strikethrough@2.0.1:
+ resolution: {integrity: sha512-OuJHqvr455pwu2OaOrir7dbzqs4jlWKOtlu9L6GjcIjjQwNyw02VntQsr/Ek6/A13vgnXfUhBekWRUP1OkNivw==}
+
+ mdast-util-gfm-table@2.0.0:
+ resolution: {integrity: sha512-78UEvebzz/rJIxLvE7ZtDd/vIQ0RHv+3Mh5DR96p7cS7HsBhYIICDBCu8csTNWNO6tBWfqXPWekRuj2FNOGOZg==}
+
+ mdast-util-gfm-task-list-item@2.0.0:
+ resolution: {integrity: sha512-IrtvNvjxC1o06taBAVJznEnkiHxLFTzgonUdy8hzFVeDun0uTjxxrRGVaNFqkU1wJR3RBPEfsxmU6jDWPofrTQ==}
+
+ mdast-util-gfm@3.1.0:
+ resolution: {integrity: sha512-0ulfdQOM3ysHhCJ1p06l0b0VKlhU0wuQs3thxZQagjcjPrlFRqY215uZGHHJan9GEAXd9MbfPjFJz+qMkVR6zQ==}
+
+ mdast-util-mdx-expression@2.0.1:
+ resolution: {integrity: sha512-J6f+9hUp+ldTZqKRSg7Vw5V6MqjATc+3E4gf3CFNcuZNWD8XdyI6zQ8GqH7f8169MM6P7hMBRDVGnn7oHB9kXQ==}
+
+ mdast-util-mdx-jsx@3.2.0:
+ resolution: {integrity: sha512-lj/z8v0r6ZtsN/cGNNtemmmfoLAFZnjMbNyLzBafjzikOM+glrjNHPlf6lQDOTccj9n5b0PPihEBbhneMyGs1Q==}
+
+ mdast-util-mdx@3.0.0:
+ resolution: {integrity: sha512-JfbYLAW7XnYTTbUsmpu0kdBUVe+yKVJZBItEjwyYJiDJuZ9w4eeaqks4HQO+R7objWgS2ymV60GYpI14Ug554w==}
+
+ mdast-util-mdxjs-esm@2.0.1:
+ resolution: {integrity: sha512-EcmOpxsZ96CvlP03NghtH1EsLtr0n9Tm4lPUJUBccV9RwUOneqSycg19n5HGzCf+10LozMRSObtVr3ee1WoHtg==}
+
+ mdast-util-phrasing@4.1.0:
+ resolution: {integrity: sha512-TqICwyvJJpBwvGAMZjj4J2n0X8QWp21b9l0o7eXyVJ25YNWYbJDVIyD1bZXE6WtV6RmKJVYmQAKWa0zWOABz2w==}
+
mdast-util-to-hast@13.2.1:
resolution: {integrity: sha512-cctsq2wp5vTsLIcaymblUriiTcZd0CwWtCbLvrOzYCDZoWyMNV8sZ7krj09FSnsiJi3WVsHLM4k6Dq/yaPyCXA==}
+ mdast-util-to-markdown@2.2.1:
+ resolution: {integrity: sha512-ThatlCBxG2GE+mljhNSfZPv56d3QrGiRh97jjYgIk80IzS4uU6d7cHAaexCYSAmUCCcOs3grJ07kX3oTGsFUOw==}
+
+ mdast-util-to-string@4.0.0:
+ resolution: {integrity: sha512-0H44vDimn51F0YwvxSJSm0eCDOJTRlmN0R1yBh4HLj9wiV1Dn0QoXGbvFAWj2hSItVTlCmBF1hqKlIyUBVFLPg==}
+
mdn-data@2.0.28:
resolution: {integrity: sha512-aylIc7Z9y4yzHYAJNuESG3hfhC+0Ibp/MAMiaOZgNv4pmEdFyfZhhhny4MNiAfWdBQ1RQ2mfDWmM1x8SvGyp8g==}
mdn-data@2.27.1:
resolution: {integrity: sha512-9Yubnt3e8A0OKwxYSXyhLymGW4sCufcLG6VdiDdUGVkPhpqLxlvP5vl1983gQjJl3tqbrM731mjaZaP68AgosQ==}
+ micromark-core-commonmark@2.0.4:
+ resolution: {integrity: sha512-wxEeE8v8XVvOrxn1TZj74qYhAtTQsSqufHVS3uNVyT1MupXxhyaHk8/9xDNPh9BmL77QNDgWTkZ3RsYHB2ry7w==}
+
+ micromark-extension-gfm-autolink-literal@2.1.0:
+ resolution: {integrity: sha512-oOg7knzhicgQ3t4QCjCWgTmfNhvQbDDnJeVu9v81r7NltNCVmhPy1fJRX27pISafdjL+SVc4d3l48Gb6pbRypw==}
+
+ micromark-extension-gfm-footnote@2.1.0:
+ resolution: {integrity: sha512-/yPhxI1ntnDNsiHtzLKYnE3vf9JZ6cAisqVDauhp4CEHxlb4uoOTxOCJ+9s51bIB8U1N1FJ1RXOKTIlD5B/gqw==}
+
+ micromark-extension-gfm-strikethrough@2.1.0:
+ resolution: {integrity: sha512-ADVjpOOkjz1hhkZLlBiYA9cR2Anf8F4HqZUO6e5eDcPQd0Txw5fxLzzxnEkSkfnD0wziSGiv7sYhk/ktvbf1uw==}
+
+ micromark-extension-gfm-table@2.1.2:
+ resolution: {integrity: sha512-pRzm4kDTu0MjlmBkxmS9yYhw60nncfcEwu9NNdPFSQEFXS95ZKyIIyTSHu/o3ReBUrLKYEq+7YaXCRn/bPB4MA==}
+
+ micromark-extension-gfm-tagfilter@2.0.0:
+ resolution: {integrity: sha512-xHlTOmuCSotIA8TW1mDIM6X2O1SiX5P9IuDtqGonFhEK0qgRI4yeC6vMxEV2dgyr2TiD+2PQ10o+cOhdVAcwfg==}
+
+ micromark-extension-gfm-task-list-item@2.1.0:
+ resolution: {integrity: sha512-qIBZhqxqI6fjLDYFTBIa4eivDMnP+OZqsNwmQ3xNLE4Cxwc+zfQEfbs6tzAo2Hjq+bh6q5F+Z8/cksrLFYWQQw==}
+
+ micromark-extension-gfm@3.0.0:
+ resolution: {integrity: sha512-vsKArQsicm7t0z2GugkCKtZehqUm31oeGBV/KVSorWSy8ZlNAv7ytjFhvaryUiCUJYqs+NoE6AFhpQvBTM6Q4w==}
+
+ micromark-extension-mdx-expression@3.0.0:
+ resolution: {integrity: sha512-sI0nwhUDz97xyzqJAbHQhp5TfaxEvZZZ2JDqUo+7NvyIYG6BZ5CPPqj2ogUoPJlmXHBnyZUzISg9+oUmU6tUjQ==}
+
+ micromark-extension-mdx-jsx@3.0.2:
+ resolution: {integrity: sha512-e5+q1DjMh62LZAJOnDraSSbDMvGJ8x3cbjygy2qFEi7HCeUT4BDKCvMozPozcD6WmOt6sVvYDNBKhFSz3kjOVQ==}
+
+ micromark-extension-mdx-md@2.0.0:
+ resolution: {integrity: sha512-EpAiszsB3blw4Rpba7xTOUptcFeBFi+6PY8VnJ2hhimH+vCQDirWgsMpz7w1XcZE7LVrSAUGb9VJpG9ghlYvYQ==}
+
+ micromark-extension-mdxjs-esm@3.0.0:
+ resolution: {integrity: sha512-DJFl4ZqkErRpq/dAPyeWp15tGrcrrJho1hKK5uBS70BCtfrIFg81sqcTVu3Ta+KD1Tk5vAtBNElWxtAa+m8K9A==}
+
+ micromark-extension-mdxjs@3.0.0:
+ resolution: {integrity: sha512-A873fJfhnJ2siZyUrJ31l34Uqwy4xIFmvPY1oj+Ean5PHcPBYzEsvqvWGaWcfEIr11O5Dlw3p2y0tZWpKHDejQ==}
+
+ micromark-factory-destination@2.0.0:
+ resolution: {integrity: sha512-j9DGrQLm/Uhl2tCzcbLhy5kXsgkHUrjJHg4fFAeoMRwJmJerT9aw4FEhIbZStWN8A3qMwOp1uzHr4UL8AInxtA==}
+
+ micromark-factory-label@2.0.0:
+ resolution: {integrity: sha512-RR3i96ohZGde//4WSe/dJsxOX6vxIg9TimLAS3i4EhBAFx8Sm5SmqVfR8E87DPSR31nEAjZfbt91OMZWcNgdZw==}
+
+ micromark-factory-mdx-expression@2.0.0:
+ resolution: {integrity: sha512-2Q5+jhTBhtMdNDN9aQb9WWhpmO3ALY+eNTPfZZpDRdbK5m/bywnexvvNrP5EKdIg83udifcxpB0jyJOGKuMA9Q==}
+
+ micromark-factory-space@2.1.0:
+ resolution: {integrity: sha512-fS8hnLIjnjvdQIj39Geug8wWsR0HrYZ43KShKxNfwT7t2LOHo/LbWZEzEaSOjwtjdCsjoE6syHhonEzW0zv0+Q==}
+
+ micromark-factory-title@2.0.0:
+ resolution: {integrity: sha512-jY8CSxmpWLOxS+t8W+FG3Xigc0RDQA9bKMY/EwILvsesiRniiVMejYTE4wumNc2f4UbAa4WsHqe3J1QS1sli+A==}
+
+ micromark-factory-whitespace@2.0.0:
+ resolution: {integrity: sha512-28kbwaBjc5yAI1XadbdPYHX/eDnqaUFVikLwrO7FDnKG7lpgxnvk/XGRhX/PN0mOZ+dBSZ+LgunHS+6tYQAzhA==}
+
micromark-util-character@2.0.0:
resolution: {integrity: sha512-DtHHqgTRz32ylwiGSZwoK+BTx4gaq//ig71g20pwBwRLxo3CfInyD+NyTrriLOhPz5WQOfAOSLLbKOaaGXWz9Q==}
+ micromark-util-chunked@2.0.0:
+ resolution: {integrity: sha512-anK8SWmNphkXdaKgz5hJvGa7l00qmcaUQoMYsBwDlSKFKjc6gjGXPDw3FNL3Nbwq5L8gE+RCbGqTw49FK5Qyvg==}
+
+ micromark-util-classify-character@2.0.0:
+ resolution: {integrity: sha512-S0ze2R9GH+fu41FA7pbSqNWObo/kzwf8rN/+IGlW/4tC6oACOs8B++bh+i9bVyNnwCcuksbFwsBme5OCKXCwIw==}
+
+ micromark-util-combine-extensions@2.0.0:
+ resolution: {integrity: sha512-vZZio48k7ON0fVS3CUgFatWHoKbbLTK/rT7pzpJ4Bjp5JjkZeasRfrS9wsBdDJK2cJLHMckXZdzPSSr1B8a4oQ==}
+
+ micromark-util-decode-numeric-character-reference@2.0.0:
+ resolution: {integrity: sha512-pIgcsGxpHEtTG/rPJRz/HOLSqp5VTuIIjXlPI+6JSDlK2oljApusG6KzpS8AF0ENUMCHlC/IBb5B9xdFiVlm5Q==}
+
+ micromark-util-decode-string@2.0.1:
+ resolution: {integrity: sha512-nDV/77Fj6eH1ynwscYTOsbK7rR//Uj0bZXBwJZRfaLEJ1iGBR6kIfNmlNqaqJf649EP0F3NWNdeJi03elllNUQ==}
+
+ micromark-util-edit-map@1.0.0:
+ resolution: {integrity: sha512-Pa2ljlsEL6sVwFaYeyrOLSYbQt73JvGbPOYFq+9AElXiSnfI5Q4465RRZ1sHv7lDjDOnGRDDaqPXqClqWK/q1Q==}
+
micromark-util-encode@2.0.0:
resolution: {integrity: sha512-pS+ROfCXAGLWCOc8egcBvT0kf27GoWMqtdarNfDcjb6YLuV5cM3ioG45Ys2qOVqeqSbjaKg72vU+Wby3eddPsA==}
+ micromark-util-events-to-acorn@2.0.3:
+ resolution: {integrity: sha512-jmsiEIiZ1n7X1Rr5k8wVExBQCg5jy4UXVADItHmNk1zkwEVhBuIUKRu3fqv+hs4nxLISi2DQGlqIOGiFxgbfHg==}
+
+ micromark-util-html-tag-name@2.0.0:
+ resolution: {integrity: sha512-xNn4Pqkj2puRhKdKTm8t1YHC/BAjx6CEwRFXntTaRf/x16aqka6ouVoutm+QdkISTlT7e2zU7U4ZdlDLJd2Mcw==}
+
+ micromark-util-normalize-identifier@2.0.0:
+ resolution: {integrity: sha512-2xhYT0sfo85FMrUPtHcPo2rrp1lwbDEEzpx7jiH2xXJLqBuy4H0GgXk5ToU8IEwoROtXuL8ND0ttVa4rNqYK3w==}
+
+ micromark-util-resolve-all@2.0.0:
+ resolution: {integrity: sha512-6KU6qO7DZ7GJkaCgwBNtplXCvGkJToU86ybBAUdavvgsCiG8lSSvYxr9MhwmQ+udpzywHsl4RpGJsYWG1pDOcA==}
+
micromark-util-sanitize-uri@2.0.0:
resolution: {integrity: sha512-WhYv5UEcZrbAtlsnPuChHUAsu/iBPOVaEVsntLBIdpibO0ddy8OzavZz3iL2xVvBZOpolujSliP65Kq0/7KIYw==}
+ micromark-util-subtokenize@2.0.0:
+ resolution: {integrity: sha512-vc93L1t+gpR3p8jxeVdaYlbV2jTYteDje19rNSS/H5dlhxUYll5Fy6vJ2cDwP8RnsXi818yGty1ayP55y3W6fg==}
+
micromark-util-symbol@2.0.0:
resolution: {integrity: sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw==}
micromark-util-types@2.0.3:
resolution: {integrity: sha512-oxB2Ik03hI0gv+VNn9tnh1t1YEe9MDPptViAEgfdf3YQHsn0pzGTgCdlSCJXcwhqm8phaEuM7zeEu3QQzVBrPg==}
+ micromark@4.0.3:
+ resolution: {integrity: sha512-oGYfQzHSG5dOMovQcJ3fyTmZlWAWpi0XA0sJwJs+i6OT88o1+Jtw/8z0CmdowSLxGhhFK89rQ/oXph/wN02PNw==}
+
mrmime@2.0.1:
resolution: {integrity: sha512-Y3wQdFg2Va6etvQ5I82yUhGdsKrcYox6p7FfL1LbK2J4V01F9TGlepTIhnK24t7koZibmg82KGglhA1XK5IsLQ==}
engines: {node: '>=10'}
+ ms@2.1.3:
+ resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==}
+
nanoid@3.3.20:
resolution: {integrity: sha512-uKdg2G3GNCKQn9byYOpxbGqrT2fGO5KRt5J/8b3pok8rT6qxGWF6hxMyJiEYtAf+FVyYuD9hRaDqX5uPFYJ4ZQ==}
engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1}
@@ -1075,6 +1366,15 @@ packages:
resolution: {integrity: sha512-XTUaK0hXMCu2jszWE584JGQT7y284TmMV9l/HX3rnG5uo3rHI/uHU56XTyyyPFjeWEBxECbAi0CaFDJOONtG0Q==}
hasBin: true
+ parse-entities@4.0.2:
+ resolution: {integrity: sha512-GG2AQYWoLgL877gQIKeRPGO1xF9+eG1ujIb5soS5gPvLQ1y2o8FL90w2QWNdf9I361Mpp7726c+lj3U0qK1uGw==}
+
+ parse-latin@7.0.0:
+ resolution: {integrity: sha512-mhHgobPPua5kZ98EF4HWiH167JWBfl4pvAIXXdbaVohtK7a6YBOy56kvhCqduqyo/f3yrHFWmqmiMg/BkBkYYQ==}
+
+ parse5@7.0.0:
+ resolution: {integrity: sha512-y/t8IXSPWTuRZqXc0ajH/UwDj4mnqLEbSttNbThcFhGrZuOyoyvNBO85PBp2jQa55wY9d07PBNjsK8ZP3K5U6g==}
+
path-expression-matcher@1.6.2:
resolution: {integrity: sha512-enSlaiat05iasnzmgNxRj8reFdj3puY2QpNgP1aPIaVfT6nn9ICuPoFlKHk8EN22HcwewshO+mN2DGbkCEOtqQ==}
engines: {node: '>=14.0.0'}
@@ -1125,6 +1425,20 @@ packages:
resolution: {integrity: sha512-Kko+Y5XQ6fM+Ce3dq3m9YGxnacYZYl9cA1wZjaF3Vbry2L3i1qVg8+CAgNPsXRArPMUMCaOR7oa9Nqntc43JKA==}
engines: {node: '>= 20.19.0'}
+ recma-build-jsx@1.0.0:
+ resolution: {integrity: sha512-8GtdyqaBcDfva+GUKDr3nev3VpKAhup1+RvkMvUxURHpW7QyIvk9F5wz7Vzo06CEMSilw6uArgRqhpiUcWp8ew==}
+
+ recma-jsx@1.0.1:
+ resolution: {integrity: sha512-huSIy7VU2Z5OLv6oFLosQGGDqPqdO1iq6bWNAdhzMxSJP7RAso4fCZ1cKu8j9YHCZf3TPrq4dw3okhrylgcd7w==}
+ peerDependencies:
+ acorn: ^6.0.0 || ^7.0.0 || ^8.0.0
+
+ recma-parse@1.0.0:
+ resolution: {integrity: sha512-OYLsIGBB5Y5wjnSnQW6t3Xg7q3fQ7FWbw/vcXtORTnyaSFscOtABg+7Pnz6YZ6c27fG1/aN8CjfwoUEUIdwqWQ==}
+
+ recma-stringify@1.0.0:
+ resolution: {integrity: sha512-cjwII1MdIIVloKvC9ErQ+OgAtwHBmcZ0Bg4ciz78FtbT8In39aAYbaA7zvxQ61xVMSPE8WxhLwLbhif4Js2C+g==}
+
regex-recursion@6.0.2:
resolution: {integrity: sha512-0YCaSCq2VRIebiaUviZNs0cBz1kg5kVS2UKUfNIx8YVs1cN3AV7NTctO5FOKBA+UT2BPJIWZauYHPqJODG50cg==}
@@ -1134,12 +1448,49 @@ packages:
regex@6.1.0:
resolution: {integrity: sha512-6VwtthbV4o/7+OaAF9I5L5V3llLEsoPyq9P1JVXkedTP33c7MfCG0/5NOPcSJn0TzXcG9YUrR0gQSWioew3LDg==}
+ rehype-raw@7.0.0:
+ resolution: {integrity: sha512-/aE8hCfKlQeA8LmyeyQvQF3eBiLRGNlfBJEvWH7ivp9sBqs7TNqBL5X3v157rM4IFETqDnIOO+z5M/biZbo9Ww==}
+
+ rehype-recma@1.0.0:
+ resolution: {integrity: sha512-lqA4rGUf1JmacCNWWZx0Wv1dHqMwxzsDWYMTowuplHF3xH0N/MmrZ/G3BDZnzAkRmxDadujCjaKM2hqYdCBOGw==}
+
+ rehype-stringify@10.0.1:
+ resolution: {integrity: sha512-k9ecfXHmIPuFVI61B9DeLPN0qFHfawM6RsuX48hoqlaKSF61RskNjSm1lI8PhBEM0MRdLxVVm4WmTqJQccH9mA==}
+
+ remark-gfm@4.0.1:
+ resolution: {integrity: sha512-1quofZ2RQ9EWdeN34S79+KExV1764+wCUGop5CPL1WGdD0ocPpu91lzPGbwWMECpEpd42kJGQwzRfyov9j4yNg==}
+
+ remark-mdx@3.0.0:
+ resolution: {integrity: sha512-O7yfjuC6ra3NHPbRVxfflafAj3LTwx3b73aBvkEFU5z4PsD6FD4vrqJAkE5iNGLz71GdjXfgRqm3SQ0h0VuE7g==}
+
+ remark-parse@11.0.0:
+ resolution: {integrity: sha512-FCxlKLNGknS5ba/1lmpYijMUzX2esxW5xQqjWxw2eHFfS2MSdaHVINFmhjo+qN1WhZhNimq0dZATN9pH0IDrpA==}
+
+ remark-rehype@11.1.2:
+ resolution: {integrity: sha512-Dh7l57ianaEoIpzbp0PC9UKAdCSVklD8E5Rpw7ETfbTl3FqcOOgq5q2LVDhgGCkaBv7p24JXikPdvhhmHvKMsw==}
+
+ remark-smartypants@3.0.3:
+ resolution: {integrity: sha512-gCaK+ndZ0hYezlqFegHFCVh2CQemsi0Npdh1qVM9bxlUFknjkbP6VmojWhddOCrbK0PbbacmYLWfTULRiT1eWA==}
+ engines: {node: '>=16.0.0'}
+
+ remark-stringify@11.0.0:
+ resolution: {integrity: sha512-1OSmLd3awB/t8qdoEOMazZkNsfVTeY4fTsgzcQFdXNq8ToTN4ZGwrMnlda4K6smTFKD+GRV6O48i6Z4iKgPPpw==}
+
resolve-pkg-maps@1.0.0:
resolution: {integrity: sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw==}
+ retext-latin@4.0.0:
+ resolution: {integrity: sha512-hv9woG7Fy0M9IlRQloq/N6atV82NxLGveq+3H2WOi79dtIYWN8OaxogDm77f8YnVXJL2VD3bbqowu5E3EMhBYA==}
+
retext-smartypants@6.2.0:
resolution: {integrity: sha512-kk0jOU7+zGv//kfjXEBjdIryL1Acl4i9XNkHxtM7Tm5lFiCog576fjNC9hjoR7LTKQ0DsPWy09JummSsH1uqfQ==}
+ retext-stringify@4.0.0:
+ resolution: {integrity: sha512-rtfN/0o8kL1e+78+uxPTqu1Klt0yPzKuQ2BfWwwfgIUSayyzxpM1PJzkKt4V8803uB9qSy32MvI7Xep9khTpiA==}
+
+ retext@9.0.0:
+ resolution: {integrity: sha512-sbMDcpHCNjvlheSgMfEcVrZko3cDzdbe1x/e7G66dFp0Ff7Mldvi2uv6JkJQzdRcvLYE8CA8Oe8siQx8ZOgTcA==}
+
rolldown@1.2.15:
resolution: {integrity: sha512-6odND+fel5zVw3I4Yc2e69gvguDnX0CAAGiNDZSq4ik5WUcaLrkD2GLuog0XcODbor31hZ5ayEMgVDno+KPV5g==}
engines: {node: ^20.19.0 || >=22.12.0}
@@ -1190,6 +1541,14 @@ packages:
resolution: {integrity: sha512-KGj/8Y43x35aZVDtt+J4mK1hoLGHULMYfSkODJNQjNDC3oW1PqPoxMwo0pLUsWM/UEGzON/NxeHywEfNXNP3Vw==}
engines: {node: '>=0.10.0'}
+ source-map@0.7.0:
+ resolution: {integrity: sha512-JsXsCYrKzxA5kU8LanQJHIPoEY3fEH5WYSMJ8Z77ESByI18VFEoxB46H2eNHqK2nVqTRjUe5DYvNHmyT3JOd1w==}
+ engines: {node: '>= 8'}
+
+ source-map@0.8.0:
+ resolution: {integrity: sha512-d8EqvL+k/SOXCreS/SUzg2ciyHqBBLcN/yuRjFsbvVhHTE2pgei7oAhmPM7kWFbkX6OSMQfUq4KbkF3au9lhYQ==}
+ engines: {node: '>= 12'}
+
space-separated-tokens@2.0.2:
resolution: {integrity: sha512-PEGlAwrG8yXGXRjW32fGbg66JAlOAwbObuqVoJpv/mRgoWDQfgH1wDPvtzWyUSNAXBGSk8h755YDbbcEy3SH2Q==}
@@ -1199,6 +1558,15 @@ packages:
strnum@2.5.1:
resolution: {integrity: sha512-UM4nTLWzQiDBseVxUGxN0wJzIk0UU89Qi7pKXz9qISo+lhviJikTuikBsK/oFRlpvYHvSdz0TVoLyQ+sEpYwxA==}
+ style-to-js@1.0.0:
+ resolution: {integrity: sha512-OiaJVLD+ybcul+6oAdwTOKLFewvYapPLG4H3JiYBYUS0yoi29Ag1IiqprbVARaxiAXvkk+4B8aNcG7lyEDKebg==}
+
+ style-to-object@0.3.0:
+ resolution: {integrity: sha512-CzFnRRXhzWIdItT3OmF8SQfWyahHhjq3HwcMNCNLn+N7klOOqPjMeG/4JSu77D7ypZdGvSzvkrbyeTMizz2VrA==}
+
+ style-to-object@2.0.2:
+ resolution: {integrity: sha512-QmbXPUylqU80HAgTOJeEOdbA40W9KtxmjMhQy+tq+b8F2aoh3aQLuy82hh2jm2qsC9hR9eI0+eQidTMydKcqRA==}
+
svgo@4.1.0:
resolution: {integrity: sha512-bkxnTg1kSU0guhIBmibA6UUhrQmPVA1XsQLN+ylCd+UWzbnLkySOcXpyk1mrl05f+pcaCx2eHb+sp6BgMZWX+Q==}
engines: {node: '>=16'}
@@ -1257,14 +1625,29 @@ packages:
unist-util-is@6.0.1:
resolution: {integrity: sha512-LsiILbtBETkDz8I9p1dQ0uyRUWuaQzd/cuEeS1hoRSyW5E5XGmTzlwY1OrNzzakGowI9Dr/I8HVaw4hTtnxy8g==}
+ unist-util-modify-children@4.0.0:
+ resolution: {integrity: sha512-+tdN5fGNddvsQdIzUF3Xx82CU9sMM+fA0dLgR9vOmT0oPT2jH+P1nd5lSqfCfXAw+93NhcXNY2qqvTUtE4cQkw==}
+
+ unist-util-position-from-estree@1.1.2:
+ resolution: {integrity: sha512-poZa0eXpS+/XpoQwGwl79UUdea4ol2ZuCYguVaJS4qzIOMDzbqz8a3erUCOmubSZkaOuGamb3tX790iwOIROww==}
+
+ unist-util-position-from-estree@2.0.0:
+ resolution: {integrity: sha512-KaFVRjoqLyF6YXCbVLNad/eS4+OfPQQn2yOd7zF/h5T/CSL2v8NpN6a5TPvtbXthAGw5nG+PuTtq+DdIZr+cRQ==}
+
unist-util-position@5.0.0:
resolution: {integrity: sha512-fucsC7HjXvkB5R3kTCO7kUjRdrS0BJt3M/FPxmHMBOm8JQi2BsHAHFsy27E0EolP8rp0NzXsJ+jNPyDWvOJZPA==}
+ unist-util-remove-position@5.0.0:
+ resolution: {integrity: sha512-Hp5Kh3wLxv0PHj9m2yZhhLt58KzPtEYKQQ4yxfYFEO7EvHwzyDYnduhHnY1mDxoqr7VUwVuHXk9RXKIiYS1N8Q==}
+
unist-util-stringify-position@4.0.0:
resolution: {integrity: sha512-0ASV06AAoKCDkS2+xw5RXJywruurpbC4JZSm7nr7MOt1ojAzvyyaO+UxZf18j8FCF6kmzCZKcAgN/yu2gm2XgQ==}
- unist-util-visit-parents@6.0.2:
- resolution: {integrity: sha512-goh1s1TBrqSqukSc8wrjwWhL0hiJxgA8m4kFxGlQ+8FYQ3C/m11FcTs4YYem7V664AhHVvgoQLk890Ssdsr2IQ==}
+ unist-util-visit-children@3.0.0:
+ resolution: {integrity: sha512-RgmdTfSBOg04sdPcpTSD1jzoNBjt9a80/ZCzp5cI9n1qPzLZWF9YdvWGN2zmTumP1HWhXKdUWexjy/Wy/lJ7tA==}
+
+ unist-util-visit-parents@6.1.0:
+ resolution: {integrity: sha512-vKXxz6O38sKDj1mtx/k2cWvkkFBuYGx6uGrlzBkVeWCRF/F8sdI0j3Wbkz/5rVNRRuVc8UrgRdbCxNhmYXgP3w==}
unist-util-visit@5.1.0:
resolution: {integrity: sha512-m+vIdyeCOpdr/QeQCu2EzxX/ohgS8KbnPDgFni4dQsfSCtpz8UqDyY5GjRru8PDKuYn7Fq19j1CQ+nJSsGKOzg==}
@@ -1335,6 +1718,9 @@ packages:
resolution: {integrity: sha512-u4J1hr6Y+C/hit34GwL3eIcUf3wngT8TlYUjK7tk0jxydKLAq3sYvifjdTDA6U3KCKRcQCQDGf/srjxfZF3l7g==}
engines: {node: '>=18.12.0'}
+ vfile-location@5.0.3:
+ resolution: {integrity: sha512-5yXvWDEgqeiYiBe1lbxYF7UMAIm/IcopxMHrMQDq3nvKcjPKIhZklUKL+AE7J7uApI4kwe2snsK+eI6UTj9EHg==}
+
vfile-message@4.0.3:
resolution: {integrity: sha512-QTHzsGd1EhbZs4AsQ20JX1rC3cOlt/IWJruk893DfLRr57lcnOeMaWG4K0JrRta4mIJZKth2Au3mM3u03/JWKw==}
@@ -1392,6 +1778,9 @@ packages:
vite:
optional: true
+ web-namespaces@2.0.1:
+ resolution: {integrity: sha512-bKr1DkiNa2krS7qxNtdrtHAmzuYGFQLiQ13TsorsdT6ULTkPLKuu5+GsFpDlg6JFjUTwX2DyhMPG2be8uPrqsQ==}
+
xml-naming@0.3.0:
resolution: {integrity: sha512-ghig2TBE/H11aOVgmahA3MhimvkBr6JIYknH/Dhdk10nXwdbIqBJsbfMxpvFPG8bAw77gN29aQWvKpmVoPlvPQ==}
engines: {node: '>=16.0.0'}
@@ -1482,6 +1871,44 @@ snapshots:
unified: 11.0.5
yaml: 2.9.1
+ '@astrojs/internal-helpers@0.13.0':
+ dependencies:
+ '@types/hast': 3.0.5
+ '@types/mdast': 4.0.4
+ picomatch: 4.0.7
+ retext-smartypants: 6.2.0
+ shiki: 4.5.0
+ smol-toml: 1.9.1
+ unified: 11.0.5
+ yaml: 2.9.1
+
+ '@astrojs/markdown-remark@7.3.5':
+ dependencies:
+ '@astrojs/internal-helpers': 0.13.0
+ '@astrojs/prism': 4.1.2
+ '@mdx-js/mdx': 3.1.1
+ acorn: 8.19.0
+ estree-util-visit: 2.0.0
+ github-slugger: 2.0.0
+ hast-util-from-html: 2.0.3
+ hast-util-to-html: 9.0.6
+ hast-util-to-text: 4.0.3
+ mdast-util-definitions: 6.0.0
+ rehype-raw: 7.0.0
+ rehype-stringify: 10.0.1
+ remark-gfm: 4.0.1
+ remark-parse: 11.0.0
+ remark-rehype: 11.1.2
+ remark-smartypants: 3.0.3
+ source-map: 0.8.0
+ unified: 11.0.5
+ unist-util-remove-position: 5.0.0
+ unist-util-visit: 5.1.0
+ unist-util-visit-parents: 6.1.0
+ vfile: 6.0.3
+ transitivePeerDependencies:
+ - supports-color
+
'@astrojs/markdown-satteri@0.4.3':
dependencies:
'@astrojs/internal-helpers': 0.12.0
@@ -1493,6 +1920,10 @@ snapshots:
dependencies:
prismjs: 1.30.0
+ '@astrojs/prism@4.1.2':
+ dependencies:
+ prismjs: 1.30.0
+
'@astrojs/rss@4.0.19':
dependencies:
fast-xml-parser: 5.11.2
@@ -1721,6 +2152,36 @@ snapshots:
'@jridgewell/sourcemap-codec@1.6.0': {}
+ '@mdx-js/mdx@3.1.1':
+ dependencies:
+ '@types/estree': 1.0.9
+ '@types/estree-jsx': 1.0.5
+ '@types/hast': 3.0.5
+ '@types/mdx': 2.0.14
+ acorn: 8.19.0
+ collapse-white-space: 2.1.0
+ devlop: 1.1.0
+ estree-util-is-identifier-name: 3.0.0
+ estree-util-scope: 1.0.1
+ estree-walker: 3.0.3
+ hast-util-to-jsx-runtime: 2.3.7
+ markdown-extensions: 2.0.0
+ recma-build-jsx: 1.0.0
+ recma-jsx: 1.0.1(acorn@8.19.0)
+ recma-stringify: 1.0.0
+ rehype-recma: 1.0.0
+ remark-mdx: 3.0.0
+ remark-parse: 11.0.0
+ remark-rehype: 11.1.2
+ source-map: 0.7.0
+ unified: 11.0.5
+ unist-util-position-from-estree: 2.0.0
+ unist-util-stringify-position: 4.0.0
+ unist-util-visit: 5.1.0
+ vfile: 6.0.3
+ transitivePeerDependencies:
+ - supports-color
+
'@napi-rs/wasm-runtime@1.2.5(@emnapi/core@1.11.1)(@emnapi/runtime@1.11.1)':
dependencies:
'@emnapi/core': 1.11.1
@@ -1822,7 +2283,7 @@ snapshots:
'@shikijs/types': 4.5.0
'@shikijs/vscode-textmate': 10.1.0
'@types/hast': 3.0.5
- hast-util-to-html: 9.0.5
+ hast-util-to-html: 9.0.6
'@shikijs/engine-javascript@4.5.0':
dependencies:
@@ -1861,6 +2322,10 @@ snapshots:
tslib: 2.8.1
optional: true
+ '@types/debug@4.1.13':
+ dependencies:
+ '@types/ms': 2.1.0
+
'@types/estree-jsx@1.0.5':
dependencies:
'@types/estree': 1.0.9
@@ -1875,6 +2340,10 @@ snapshots:
dependencies:
'@types/unist': 3.0.3
+ '@types/mdx@2.0.14': {}
+
+ '@types/ms@2.1.0': {}
+
'@types/nlcst@2.0.3':
dependencies:
'@types/unist': 3.0.3
@@ -1887,10 +2356,18 @@ snapshots:
dependencies:
'@types/node': 24.19.2
+ '@types/unist@2.0.11': {}
+
'@types/unist@3.0.3': {}
'@ungap/structured-clone@1.4.0': {}
+ acorn-jsx@5.3.2(acorn@8.19.0):
+ dependencies:
+ acorn: 8.19.0
+
+ acorn@8.19.0: {}
+
adequate-little-templates@1.0.2: {}
am-i-vibing@0.5.0:
@@ -1908,14 +2385,18 @@ snapshots:
aria-query@5.3.2: {}
- astro-pagefind@2.0.1(astro@7.3.8(@types/node@24.19.2)(yaml@2.9.1)):
+ array-iterate@2.0.1: {}
+
+ astring@1.9.0: {}
+
+ astro-pagefind@2.0.1(astro@7.3.8(@astrojs/markdown-remark@7.3.5)(@types/node@24.19.2)(yaml@2.9.1)):
dependencies:
'@pagefind/component-ui': 1.5.2
- astro: 7.3.8(@types/node@24.19.2)(yaml@2.9.1)
+ astro: 7.3.8(@astrojs/markdown-remark@7.3.5)(@types/node@24.19.2)(yaml@2.9.1)
pagefind: 1.5.2
sirv: 3.0.2
- astro@7.3.8(@types/node@24.19.2)(yaml@2.9.1):
+ astro@7.3.8(@astrojs/markdown-remark@7.3.5)(@types/node@24.19.2)(yaml@2.9.1):
dependencies:
'@astrojs/compiler-rs': 0.5.2
'@astrojs/internal-helpers': 0.12.0
@@ -1970,6 +2451,7 @@ snapshots:
yargs-parser: 22.0.0
zod: 4.6.7
optionalDependencies:
+ '@astrojs/markdown-remark': 7.3.5
sharp: 0.35.5(@types/node@24.19.2)
transitivePeerDependencies:
- '@azure/app-configuration'
@@ -2022,6 +2504,10 @@ snapshots:
character-entities-legacy@3.0.0: {}
+ character-entities@2.0.2: {}
+
+ character-reference-invalid@2.0.1: {}
+
chokidar@5.0.0:
dependencies:
readdirp: 5.1.1
@@ -2030,6 +2516,8 @@ snapshots:
clsx@2.1.1: {}
+ collapse-white-space@2.1.0: {}
+
comma-separated-tokens@2.0.3: {}
commander@11.1.0: {}
@@ -2068,6 +2556,14 @@ snapshots:
dependencies:
css-tree: 2.2.0
+ debug@4.4.3:
+ dependencies:
+ ms: 2.1.3
+
+ decode-named-character-reference@1.3.0:
+ dependencies:
+ character-entities: 2.0.2
+
defu@6.1.7: {}
dequal@2.0.3: {}
@@ -2106,8 +2602,59 @@ snapshots:
entities@4.2.0: {}
+ entities@4.3.0: {}
+
es-module-lexer@3.0.4: {}
+ esast-util-from-estree@2.0.0:
+ dependencies:
+ '@types/estree-jsx': 1.0.5
+ devlop: 1.1.0
+ estree-util-visit: 2.0.0
+ unist-util-position-from-estree: 2.0.0
+
+ esast-util-from-js@2.0.1:
+ dependencies:
+ '@types/estree-jsx': 1.0.5
+ acorn: 8.19.0
+ esast-util-from-estree: 2.0.0
+ vfile-message: 4.0.3
+
+ escape-string-regexp@5.0.0: {}
+
+ estree-util-attach-comments@3.0.0:
+ dependencies:
+ '@types/estree': 1.0.9
+
+ estree-util-build-jsx@3.0.1:
+ dependencies:
+ '@types/estree-jsx': 1.0.5
+ devlop: 1.1.0
+ estree-util-is-identifier-name: 3.0.0
+ estree-walker: 3.0.3
+
+ estree-util-is-identifier-name@3.0.0: {}
+
+ estree-util-scope@1.0.1:
+ dependencies:
+ '@types/estree': 1.0.9
+ devlop: 1.1.0
+
+ estree-util-to-js@2.0.0:
+ dependencies:
+ '@types/estree-jsx': 1.0.5
+ astring: 1.9.0
+ source-map: 0.7.0
+
+ estree-util-visit@2.0.0:
+ dependencies:
+ '@types/estree-jsx': 1.0.5
+ '@types/unist': 3.0.3
+
+ estree-walker@3.0.3:
+ dependencies:
+ '@types/estree': 1.0.9
+
eventemitter3@5.0.4: {}
exifr@7.1.3: {}
@@ -2175,7 +2722,68 @@ snapshots:
ufo: 1.6.4
uncrypto: 0.1.3
- hast-util-to-html@9.0.5:
+ hast-util-from-html@2.0.3:
+ dependencies:
+ '@types/hast': 3.0.5
+ devlop: 1.1.0
+ hast-util-from-parse5: 8.0.4
+ parse5: 7.0.0
+ vfile: 6.0.3
+ vfile-message: 4.0.3
+
+ hast-util-from-parse5@8.0.4:
+ dependencies:
+ '@types/hast': 3.0.5
+ '@types/unist': 3.0.3
+ devlop: 1.1.0
+ hastscript: 9.0.3
+ property-information: 7.2.0
+ vfile: 6.0.3
+ vfile-location: 5.0.3
+ web-namespaces: 2.0.1
+
+ hast-util-parse-selector@4.0.0:
+ dependencies:
+ '@types/hast': 3.0.5
+
+ hast-util-raw@9.1.0:
+ dependencies:
+ '@types/hast': 3.0.5
+ '@types/unist': 3.0.3
+ '@ungap/structured-clone': 1.4.0
+ hast-util-from-parse5: 8.0.4
+ hast-util-to-parse5: 8.0.1
+ html-void-elements: 3.0.0
+ mdast-util-to-hast: 13.2.1
+ parse5: 7.0.0
+ unist-util-position: 5.0.0
+ unist-util-visit: 5.1.0
+ vfile: 6.0.3
+ web-namespaces: 2.0.1
+ zwitch: 2.0.4
+
+ hast-util-to-estree@3.1.3:
+ dependencies:
+ '@types/estree': 1.0.9
+ '@types/estree-jsx': 1.0.5
+ '@types/hast': 3.0.5
+ comma-separated-tokens: 2.0.3
+ devlop: 1.1.0
+ estree-util-attach-comments: 3.0.0
+ estree-util-is-identifier-name: 3.0.0
+ hast-util-whitespace: 3.0.0
+ mdast-util-mdx-expression: 2.0.1
+ mdast-util-mdx-jsx: 3.2.0
+ mdast-util-mdxjs-esm: 2.0.1
+ property-information: 7.2.0
+ space-separated-tokens: 2.0.2
+ style-to-js: 1.0.0
+ unist-util-position: 5.0.0
+ zwitch: 2.0.4
+ transitivePeerDependencies:
+ - supports-color
+
+ hast-util-to-html@9.0.6:
dependencies:
'@types/hast': 3.0.5
'@types/unist': 3.0.3
@@ -2189,16 +2797,62 @@ snapshots:
stringify-entities: 4.0.4
zwitch: 2.0.4
+ hast-util-to-jsx-runtime@2.3.7:
+ dependencies:
+ '@types/estree': 1.0.9
+ '@types/hast': 3.0.5
+ '@types/unist': 3.0.3
+ comma-separated-tokens: 2.0.3
+ devlop: 1.1.0
+ estree-util-is-identifier-name: 3.0.0
+ hast-util-whitespace: 3.0.0
+ mdast-util-mdx-expression: 2.0.1
+ mdast-util-mdx-jsx: 3.2.0
+ mdast-util-mdxjs-esm: 2.0.1
+ property-information: 7.2.0
+ space-separated-tokens: 2.0.2
+ style-to-object: 2.0.2
+ unist-util-position: 5.0.0
+ vfile-message: 4.0.3
+ transitivePeerDependencies:
+ - supports-color
+
+ hast-util-to-parse5@8.0.1:
+ dependencies:
+ '@types/hast': 3.0.5
+ comma-separated-tokens: 2.0.3
+ devlop: 1.1.0
+ property-information: 7.2.0
+ space-separated-tokens: 2.0.2
+ web-namespaces: 2.0.1
+ zwitch: 2.0.4
+
+ hast-util-to-text@4.0.3:
+ dependencies:
+ '@types/hast': 3.0.5
+
hast-util-whitespace@3.0.0:
dependencies:
'@types/hast': 3.0.5
+ hastscript@9.0.3:
+ dependencies:
+ '@types/hast': 3.0.5
+ comma-separated-tokens: 2.0.3
+ hast-util-parse-selector: 4.0.0
+ property-information: 7.2.0
+ space-separated-tokens: 2.0.2
+
html-escaper@3.0.3: {}
html-void-elements@3.0.0: {}
http-cache-semantics@4.3.0: {}
+ inline-style-parser@0.1.1: {}
+
+ inline-style-parser@0.2.9: {}
+
iron-webcrypto@1.2.1: {}
is-alphabetical@2.0.1: {}
@@ -2212,6 +2866,8 @@ snapshots:
is-docker@4.0.0: {}
+ is-hexadecimal@2.0.1: {}
+
is-plain-obj@4.1.0: {}
is-unsafe@2.0.2: {}
@@ -2267,6 +2923,8 @@ snapshots:
lightningcss-win32-arm64-msvc: 1.33.0
lightningcss-win32-x64-msvc: 1.33.0
+ longest-streak@3.1.0: {}
+
lru-cache@11.5.3: {}
lxgw-wenkai-screen-webfont@1.7.0: {}
@@ -2281,6 +2939,151 @@ snapshots:
'@babel/types': 7.29.8
source-map-js: 1.2.2
+ markdown-extensions@2.0.0: {}
+
+ markdown-table@3.0.4: {}
+
+ mdast-util-definitions@6.0.0:
+ dependencies:
+ '@types/mdast': 4.0.4
+ '@types/unist': 3.0.3
+ unist-util-visit: 5.1.0
+
+ mdast-util-find-and-replace@3.0.4:
+ dependencies:
+ '@types/mdast': 4.0.4
+ escape-string-regexp: 5.0.0
+ unist-util-is: 6.0.1
+ unist-util-visit-parents: 6.1.0
+
+ mdast-util-from-markdown@2.1.0:
+ dependencies:
+ '@types/mdast': 4.0.4
+ '@types/unist': 3.0.3
+ decode-named-character-reference: 1.3.0
+ devlop: 1.1.0
+ mdast-util-to-string: 4.0.0
+ micromark: 4.0.3
+ micromark-util-decode-numeric-character-reference: 2.0.0
+ micromark-util-decode-string: 2.0.1
+ micromark-util-normalize-identifier: 2.0.0
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+ unist-util-stringify-position: 4.0.0
+ transitivePeerDependencies:
+ - supports-color
+
+ mdast-util-gfm-autolink-literal@2.0.1:
+ dependencies:
+ '@types/mdast': 4.0.4
+ ccount: 2.0.1
+ devlop: 1.1.0
+ mdast-util-find-and-replace: 3.0.4
+ micromark-util-character: 2.0.0
+
+ mdast-util-gfm-footnote@2.1.0:
+ dependencies:
+ '@types/mdast': 4.0.4
+ devlop: 1.1.0
+ mdast-util-from-markdown: 2.1.0
+ mdast-util-to-markdown: 2.2.1
+ micromark-util-normalize-identifier: 2.0.0
+ transitivePeerDependencies:
+ - supports-color
+
+ mdast-util-gfm-strikethrough@2.0.1:
+ dependencies:
+ '@types/mdast': 4.0.4
+ mdast-util-from-markdown: 2.1.0
+ mdast-util-to-markdown: 2.2.1
+ transitivePeerDependencies:
+ - supports-color
+
+ mdast-util-gfm-table@2.0.0:
+ dependencies:
+ '@types/mdast': 4.0.4
+ devlop: 1.1.0
+ markdown-table: 3.0.4
+ mdast-util-from-markdown: 2.1.0
+ mdast-util-to-markdown: 2.2.1
+ transitivePeerDependencies:
+ - supports-color
+
+ mdast-util-gfm-task-list-item@2.0.0:
+ dependencies:
+ '@types/mdast': 4.0.4
+ devlop: 1.1.0
+ mdast-util-from-markdown: 2.1.0
+ mdast-util-to-markdown: 2.2.1
+ transitivePeerDependencies:
+ - supports-color
+
+ mdast-util-gfm@3.1.0:
+ dependencies:
+ mdast-util-from-markdown: 2.1.0
+ mdast-util-gfm-autolink-literal: 2.0.1
+ mdast-util-gfm-footnote: 2.1.0
+ mdast-util-gfm-strikethrough: 2.0.1
+ mdast-util-gfm-table: 2.0.0
+ mdast-util-gfm-task-list-item: 2.0.0
+ mdast-util-to-markdown: 2.2.1
+ transitivePeerDependencies:
+ - supports-color
+
+ mdast-util-mdx-expression@2.0.1:
+ dependencies:
+ '@types/estree-jsx': 1.0.5
+ '@types/hast': 3.0.5
+ '@types/mdast': 4.0.4
+ devlop: 1.1.0
+ mdast-util-from-markdown: 2.1.0
+ mdast-util-to-markdown: 2.2.1
+ transitivePeerDependencies:
+ - supports-color
+
+ mdast-util-mdx-jsx@3.2.0:
+ dependencies:
+ '@types/estree-jsx': 1.0.5
+ '@types/hast': 3.0.5
+ '@types/mdast': 4.0.4
+ '@types/unist': 3.0.3
+ ccount: 2.0.1
+ devlop: 1.1.0
+ mdast-util-from-markdown: 2.1.0
+ mdast-util-to-markdown: 2.2.1
+ parse-entities: 4.0.2
+ stringify-entities: 4.0.4
+ unist-util-stringify-position: 4.0.0
+ vfile-message: 4.0.3
+ transitivePeerDependencies:
+ - supports-color
+
+ mdast-util-mdx@3.0.0:
+ dependencies:
+ mdast-util-from-markdown: 2.1.0
+ mdast-util-mdx-expression: 2.0.1
+ mdast-util-mdx-jsx: 3.2.0
+ mdast-util-mdxjs-esm: 2.0.1
+ mdast-util-to-markdown: 2.2.1
+ transitivePeerDependencies:
+ - supports-color
+
+ mdast-util-mdxjs-esm@2.0.1:
+ dependencies:
+ '@types/estree-jsx': 1.0.5
+ '@types/hast': 3.0.5
+ '@types/mdast': 4.0.4
+ devlop: 1.1.0
+ mdast-util-from-markdown: 2.1.0
+ mdast-util-to-markdown: 2.2.1
+ transitivePeerDependencies:
+ - supports-color
+
+ mdast-util-phrasing@4.1.0:
+ dependencies:
+ '@types/mdast': 4.0.4
+ unist-util-is: 6.0.1
+
mdast-util-to-hast@13.2.1:
dependencies:
'@types/hast': 3.0.5
@@ -2293,29 +3096,301 @@ snapshots:
unist-util-visit: 5.1.0
vfile: 6.0.3
+ mdast-util-to-markdown@2.2.1:
+ dependencies:
+ '@types/mdast': 4.0.4
+ '@types/unist': 3.0.3
+ longest-streak: 3.1.0
+ mdast-util-phrasing: 4.1.0
+ mdast-util-to-string: 4.0.0
+ micromark-util-character: 2.0.0
+ micromark-util-classify-character: 2.0.0
+ micromark-util-decode-string: 2.0.1
+ micromark-util-html-tag-name: 2.0.0
+ unist-util-visit: 5.1.0
+ zwitch: 2.0.4
+
+ mdast-util-to-string@4.0.0:
+ dependencies:
+ '@types/mdast': 4.0.4
+
mdn-data@2.0.28: {}
mdn-data@2.27.1: {}
+ micromark-core-commonmark@2.0.4:
+ dependencies:
+ decode-named-character-reference: 1.3.0
+ devlop: 1.1.0
+ micromark-factory-destination: 2.0.0
+ micromark-factory-label: 2.0.0
+ micromark-factory-space: 2.1.0
+ micromark-factory-title: 2.0.0
+ micromark-factory-whitespace: 2.0.0
+ micromark-util-character: 2.0.0
+ micromark-util-chunked: 2.0.0
+ micromark-util-classify-character: 2.0.0
+ micromark-util-edit-map: 1.0.0
+ micromark-util-html-tag-name: 2.0.0
+ micromark-util-normalize-identifier: 2.0.0
+ micromark-util-resolve-all: 2.0.0
+ micromark-util-subtokenize: 2.0.0
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+
+ micromark-extension-gfm-autolink-literal@2.1.0:
+ dependencies:
+ micromark-util-character: 2.0.0
+ micromark-util-sanitize-uri: 2.0.0
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+
+ micromark-extension-gfm-footnote@2.1.0:
+ dependencies:
+ devlop: 1.1.0
+ micromark-core-commonmark: 2.0.4
+ micromark-factory-space: 2.1.0
+ micromark-util-character: 2.0.0
+ micromark-util-normalize-identifier: 2.0.0
+ micromark-util-sanitize-uri: 2.0.0
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+
+ micromark-extension-gfm-strikethrough@2.1.0:
+ dependencies:
+ devlop: 1.1.0
+ micromark-util-chunked: 2.0.0
+ micromark-util-classify-character: 2.0.0
+ micromark-util-resolve-all: 2.0.0
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+
+ micromark-extension-gfm-table@2.1.2:
+ dependencies:
+ devlop: 1.1.0
+ micromark-factory-space: 2.1.0
+ micromark-util-character: 2.0.0
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+
+ micromark-extension-gfm-tagfilter@2.0.0:
+ dependencies:
+ micromark-util-types: 2.0.3
+
+ micromark-extension-gfm-task-list-item@2.1.0:
+ dependencies:
+ devlop: 1.1.0
+ micromark-factory-space: 2.1.0
+ micromark-util-character: 2.0.0
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+
+ micromark-extension-gfm@3.0.0:
+ dependencies:
+ micromark-extension-gfm-autolink-literal: 2.1.0
+ micromark-extension-gfm-footnote: 2.1.0
+ micromark-extension-gfm-strikethrough: 2.1.0
+ micromark-extension-gfm-table: 2.1.2
+ micromark-extension-gfm-tagfilter: 2.0.0
+ micromark-extension-gfm-task-list-item: 2.1.0
+ micromark-util-combine-extensions: 2.0.0
+ micromark-util-types: 2.0.3
+
+ micromark-extension-mdx-expression@3.0.0:
+ dependencies:
+ '@types/estree': 1.0.9
+ devlop: 1.1.0
+ micromark-factory-mdx-expression: 2.0.0
+ micromark-factory-space: 2.1.0
+ micromark-util-character: 2.0.0
+ micromark-util-events-to-acorn: 2.0.3
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+
+ micromark-extension-mdx-jsx@3.0.2:
+ dependencies:
+ '@types/estree': 1.0.9
+ devlop: 1.1.0
+ estree-util-is-identifier-name: 3.0.0
+ micromark-factory-mdx-expression: 2.0.0
+ micromark-factory-space: 2.1.0
+ micromark-util-character: 2.0.0
+ micromark-util-events-to-acorn: 2.0.3
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+ vfile-message: 4.0.3
+
+ micromark-extension-mdx-md@2.0.0:
+ dependencies:
+ micromark-util-types: 2.0.3
+
+ micromark-extension-mdxjs-esm@3.0.0:
+ dependencies:
+ '@types/estree': 1.0.9
+ devlop: 1.1.0
+ micromark-core-commonmark: 2.0.4
+ micromark-util-character: 2.0.0
+ micromark-util-events-to-acorn: 2.0.3
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+ unist-util-position-from-estree: 2.0.0
+ vfile-message: 4.0.3
+
+ micromark-extension-mdxjs@3.0.0:
+ dependencies:
+ acorn: 8.19.0
+ acorn-jsx: 5.3.2(acorn@8.19.0)
+ micromark-extension-mdx-expression: 3.0.0
+ micromark-extension-mdx-jsx: 3.0.2
+ micromark-extension-mdx-md: 2.0.0
+ micromark-extension-mdxjs-esm: 3.0.0
+ micromark-util-combine-extensions: 2.0.0
+ micromark-util-types: 2.0.3
+
+ micromark-factory-destination@2.0.0:
+ dependencies:
+ micromark-util-character: 2.0.0
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+
+ micromark-factory-label@2.0.0:
+ dependencies:
+ devlop: 1.1.0
+ micromark-util-character: 2.0.0
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+
+ micromark-factory-mdx-expression@2.0.0:
+ dependencies:
+ '@types/estree': 1.0.9
+ devlop: 1.1.0
+ micromark-util-character: 2.0.0
+ micromark-util-events-to-acorn: 2.0.3
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+ unist-util-position-from-estree: 1.1.2
+ vfile-message: 4.0.3
+
+ micromark-factory-space@2.1.0:
+ dependencies:
+ micromark-util-character: 2.0.0
+ micromark-util-types: 2.0.3
+
+ micromark-factory-title@2.0.0:
+ dependencies:
+ micromark-factory-space: 2.1.0
+ micromark-util-character: 2.0.0
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+
+ micromark-factory-whitespace@2.0.0:
+ dependencies:
+ micromark-factory-space: 2.1.0
+ micromark-util-character: 2.0.0
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+
micromark-util-character@2.0.0:
dependencies:
micromark-util-symbol: 2.0.0
micromark-util-types: 2.0.3
+ micromark-util-chunked@2.0.0:
+ dependencies:
+ micromark-util-symbol: 2.0.0
+
+ micromark-util-classify-character@2.0.0:
+ dependencies:
+ micromark-util-character: 2.0.0
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+
+ micromark-util-combine-extensions@2.0.0:
+ dependencies:
+ micromark-util-chunked: 2.0.0
+ micromark-util-types: 2.0.3
+
+ micromark-util-decode-numeric-character-reference@2.0.0:
+ dependencies:
+ micromark-util-symbol: 2.0.0
+
+ micromark-util-decode-string@2.0.1:
+ dependencies:
+ decode-named-character-reference: 1.3.0
+ micromark-util-character: 2.0.0
+ micromark-util-decode-numeric-character-reference: 2.0.0
+ micromark-util-symbol: 2.0.0
+
+ micromark-util-edit-map@1.0.0:
+ dependencies:
+ micromark-util-types: 2.0.3
+
micromark-util-encode@2.0.0: {}
+ micromark-util-events-to-acorn@2.0.3:
+ dependencies:
+ '@types/estree': 1.0.9
+ '@types/unist': 3.0.3
+ devlop: 1.1.0
+ estree-util-visit: 2.0.0
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+ vfile-message: 4.0.3
+
+ micromark-util-html-tag-name@2.0.0: {}
+
+ micromark-util-normalize-identifier@2.0.0:
+ dependencies:
+ micromark-util-symbol: 2.0.0
+
+ micromark-util-resolve-all@2.0.0:
+ dependencies:
+ micromark-util-types: 2.0.3
+
micromark-util-sanitize-uri@2.0.0:
dependencies:
micromark-util-character: 2.0.0
micromark-util-encode: 2.0.0
micromark-util-symbol: 2.0.0
+ micromark-util-subtokenize@2.0.0:
+ dependencies:
+ devlop: 1.1.0
+ micromark-util-chunked: 2.0.0
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+
micromark-util-symbol@2.0.0: {}
micromark-util-types@2.0.3: {}
+ micromark@4.0.3:
+ dependencies:
+ '@types/debug': 4.1.13
+ debug: 4.4.3
+ decode-named-character-reference: 1.3.0
+ devlop: 1.1.0
+ micromark-core-commonmark: 2.0.4
+ micromark-factory-space: 2.1.0
+ micromark-util-character: 2.0.0
+ micromark-util-chunked: 2.0.0
+ micromark-util-combine-extensions: 2.0.0
+ micromark-util-decode-numeric-character-reference: 2.0.0
+ micromark-util-edit-map: 1.0.0
+ micromark-util-encode: 2.0.0
+ micromark-util-normalize-identifier: 2.0.0
+ micromark-util-resolve-all: 2.0.0
+ micromark-util-sanitize-uri: 2.0.0
+ micromark-util-subtokenize: 2.0.0
+ micromark-util-symbol: 2.0.0
+ micromark-util-types: 2.0.3
+ transitivePeerDependencies:
+ - supports-color
+
mrmime@2.0.1: {}
+ ms@2.1.3: {}
+
nanoid@3.3.20: {}
neotraverse@1.0.1: {}
@@ -2375,6 +3450,29 @@ snapshots:
'@pagefind/windows-arm64': 1.5.2
'@pagefind/windows-x64': 1.5.2
+ parse-entities@4.0.2:
+ dependencies:
+ '@types/unist': 2.0.11
+ character-entities-legacy: 3.0.0
+ character-reference-invalid: 2.0.1
+ decode-named-character-reference: 1.3.0
+ is-alphanumerical: 2.0.1
+ is-decimal: 2.0.1
+ is-hexadecimal: 2.0.1
+
+ parse-latin@7.0.0:
+ dependencies:
+ '@types/nlcst': 2.0.3
+ '@types/unist': 3.0.3
+ nlcst-to-string: 4.0.0
+ unist-util-modify-children: 4.0.0
+ unist-util-visit-children: 3.0.0
+ vfile: 6.0.3
+
+ parse5@7.0.0:
+ dependencies:
+ entities: 4.3.0
+
path-expression-matcher@1.6.2: {}
piccolore@0.1.3: {}
@@ -2407,6 +3505,35 @@ snapshots:
readdirp@5.1.1: {}
+ recma-build-jsx@1.0.0:
+ dependencies:
+ '@types/estree': 1.0.9
+ estree-util-build-jsx: 3.0.1
+ vfile: 6.0.3
+
+ recma-jsx@1.0.1(acorn@8.19.0):
+ dependencies:
+ acorn: 8.19.0
+ acorn-jsx: 5.3.2(acorn@8.19.0)
+ estree-util-to-js: 2.0.0
+ recma-parse: 1.0.0
+ recma-stringify: 1.0.0
+ unified: 11.0.5
+
+ recma-parse@1.0.0:
+ dependencies:
+ '@types/estree': 1.0.9
+ esast-util-from-js: 2.0.1
+ unified: 11.0.5
+ vfile: 6.0.3
+
+ recma-stringify@1.0.0:
+ dependencies:
+ '@types/estree': 1.0.9
+ estree-util-to-js: 2.0.0
+ unified: 11.0.5
+ vfile: 6.0.3
+
regex-recursion@6.0.2:
dependencies:
regex-utilities: 2.3.0
@@ -2417,14 +3544,101 @@ snapshots:
dependencies:
regex-utilities: 2.3.0
+ rehype-raw@7.0.0:
+ dependencies:
+ '@types/hast': 3.0.5
+ hast-util-raw: 9.1.0
+ vfile: 6.0.3
+
+ rehype-recma@1.0.0:
+ dependencies:
+ '@types/estree': 1.0.9
+ '@types/hast': 3.0.5
+ hast-util-to-estree: 3.1.3
+ transitivePeerDependencies:
+ - supports-color
+
+ rehype-stringify@10.0.1:
+ dependencies:
+ '@types/hast': 3.0.5
+ hast-util-to-html: 9.0.6
+ unified: 11.0.5
+
+ remark-gfm@4.0.1:
+ dependencies:
+ '@types/mdast': 4.0.4
+ mdast-util-gfm: 3.1.0
+ micromark-extension-gfm: 3.0.0
+ remark-parse: 11.0.0
+ remark-stringify: 11.0.0
+ unified: 11.0.5
+ transitivePeerDependencies:
+ - supports-color
+
+ remark-mdx@3.0.0:
+ dependencies:
+ mdast-util-mdx: 3.0.0
+ micromark-extension-mdxjs: 3.0.0
+ transitivePeerDependencies:
+ - supports-color
+
+ remark-parse@11.0.0:
+ dependencies:
+ '@types/mdast': 4.0.4
+ mdast-util-from-markdown: 2.1.0
+ micromark-util-types: 2.0.3
+ unified: 11.0.5
+ transitivePeerDependencies:
+ - supports-color
+
+ remark-rehype@11.1.2:
+ dependencies:
+ '@types/hast': 3.0.5
+ '@types/mdast': 4.0.4
+ mdast-util-to-hast: 13.2.1
+ unified: 11.0.5
+ vfile: 6.0.3
+
+ remark-smartypants@3.0.3:
+ dependencies:
+ retext: 9.0.0
+ retext-smartypants: 6.2.0
+ unified: 11.0.5
+ unist-util-visit: 5.1.0
+
+ remark-stringify@11.0.0:
+ dependencies:
+ '@types/mdast': 4.0.4
+ mdast-util-to-markdown: 2.2.1
+ unified: 11.0.5
+
resolve-pkg-maps@1.0.0: {}
+ retext-latin@4.0.0:
+ dependencies:
+ '@types/nlcst': 2.0.3
+ parse-latin: 7.0.0
+ unified: 11.0.5
+
retext-smartypants@6.2.0:
dependencies:
'@types/nlcst': 2.0.3
nlcst-to-string: 4.0.0
unist-util-visit: 5.1.0
+ retext-stringify@4.0.0:
+ dependencies:
+ '@types/nlcst': 2.0.3
+ nlcst-to-string: 4.0.0
+ unified: 11.0.5
+
+ retext@9.0.0:
+ dependencies:
+ '@types/nlcst': 2.0.3
+ retext-latin: 4.0.0
+ retext-stringify: 4.0.0
+ unified: 11.0.5
+
rolldown@1.2.15:
dependencies:
'@oxc-project/types': 0.155.0
@@ -2530,6 +3744,10 @@ snapshots:
source-map-js@1.2.2: {}
+ source-map@0.7.0: {}
+
+ source-map@0.8.0: {}
+
space-separated-tokens@2.0.2: {}
stringify-entities@4.0.4:
@@ -2541,6 +3759,18 @@ snapshots:
dependencies:
anynum: 1.0.1
+ style-to-js@1.0.0:
+ dependencies:
+ style-to-object: 0.3.0
+
+ style-to-object@0.3.0:
+ dependencies:
+ inline-style-parser: 0.1.1
+
+ style-to-object@2.0.2:
+ dependencies:
+ inline-style-parser: 0.2.9
+
svgo@4.1.0:
dependencies:
commander: 11.1.0
@@ -2601,15 +3831,37 @@ snapshots:
dependencies:
'@types/unist': 3.0.3
+ unist-util-modify-children@4.0.0:
+ dependencies:
+ '@types/unist': 3.0.3
+ array-iterate: 2.0.1
+
+ unist-util-position-from-estree@1.1.2:
+ dependencies:
+ '@types/unist': 2.0.11
+
+ unist-util-position-from-estree@2.0.0:
+ dependencies:
+ '@types/unist': 3.0.3
+
unist-util-position@5.0.0:
dependencies:
'@types/unist': 3.0.3
+ unist-util-remove-position@5.0.0:
+ dependencies:
+ '@types/unist': 3.0.3
+ unist-util-visit: 5.1.0
+
unist-util-stringify-position@4.0.0:
dependencies:
'@types/unist': 3.0.3
- unist-util-visit-parents@6.0.2:
+ unist-util-visit-children@3.0.0:
+ dependencies:
+ '@types/unist': 3.0.3
+
+ unist-util-visit-parents@6.1.0:
dependencies:
'@types/unist': 3.0.3
unist-util-is: 6.0.1
@@ -2618,7 +3870,7 @@ snapshots:
dependencies:
'@types/unist': 3.0.3
unist-util-is: 6.0.1
- unist-util-visit-parents: 6.0.2
+ unist-util-visit-parents: 6.1.0
unstorage@1.17.6:
dependencies:
@@ -2633,6 +3885,11 @@ snapshots:
verkit@0.5.0: {}
+ vfile-location@5.0.3:
+ dependencies:
+ '@types/unist': 3.0.3
+ vfile: 6.0.3
+
vfile-message@4.0.3:
dependencies:
'@types/unist': 3.0.3
@@ -2659,6 +3916,8 @@ snapshots:
optionalDependencies:
vite: 8.3.5(@types/node@24.19.2)(yaml@2.9.1)
+ web-namespaces@2.0.1: {}
+
xml-naming@0.3.0: {}
xxhash-wasm@1.1.0: {}
diff --git a/src/components/geek/LinkCardStyles.astro b/src/components/geek/LinkCardStyles.astro
new file mode 100644
index 0000000..a4f57f4
--- /dev/null
+++ b/src/components/geek/LinkCardStyles.astro
@@ -0,0 +1,76 @@
+---
+// 链接卡片样式(构建期由 rehype 插件产出 .link-card 节点,元素无 astro cid):
+// 样式必须全局。灰阶克制 + 纯 CSS(hover 微浮、reduced-motion 豁免)。
+---
+
+
diff --git a/src/lib/rehype-link-cards.ts b/src/lib/rehype-link-cards.ts
new file mode 100644
index 0000000..235d354
--- /dev/null
+++ b/src/lib/rehype-link-cards.ts
@@ -0,0 +1,285 @@
+/**
+ * rehype 链接卡片:独立成段的裸链接 → OG 预览卡(构建期抓取 + 仓内缓存)。
+ *
+ * 触发:段落 children 去掉空白后恰为一个 时转卡(内联链接保持普通样式)。
+ * 抓取:UA 伪装、4s 超时、仅读 HTML 前 200KB、解析 og/twitter 系列的标题描述图 + favicon;
+ * 任何失败回落普通链接——构建绝不因外部站点失败。
+ * 缓存:content/.link-cache.json(入仓,保证构建确定性);30 天 TTL 后再抓。
+ * 安全:标题/描述一律走 hast text 节点(序列化时自动转义,杜绝注入);
+ * og:image / favicon 仅接受 http(s) URL。
+ * 护栏:每篇最多 MAX_CARDS 张卡,超出回落;全局并发 4。
+ */
+import fs from 'node:fs';
+import path from 'node:path';
+
+const CACHE_PATH = path.join(process.cwd(), 'content', '.link-cache.json');
+const CACHE_TTL = 30 * 24 * 3600 * 1000;
+const MAX_CARDS = 10;
+const CONCURRENCY = 4;
+const TIMEOUT_MS = 4000;
+const MAX_BYTES = 200 * 1024;
+const UA =
+ 'Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0 Safari/537.36';
+
+interface CardMeta {
+ title: string;
+ desc: string;
+ image: string;
+ favicon: string;
+ ts: number;
+}
+
+type Cache = Record;
+
+const stats = { cards: 0, fallback: 0 };
+
+function readCache(): Cache {
+ try {
+ const raw = JSON.parse(fs.readFileSync(CACHE_PATH, 'utf8')) as Record;
+ const out: Cache = {};
+ for (const [url, v] of Object.entries(raw)) {
+ if (url.startsWith('_')) continue; // 文件头说明字段
+ if (v && typeof v === 'object') out[url] = v as CardMeta;
+ }
+ return out;
+ } catch {
+ return {};
+ }
+}
+
+const cache: Cache = readCache();
+let cacheDirty = false;
+
+function writeCache(): void {
+ if (!cacheDirty) return;
+ const payload = {
+ _readme:
+ '链接卡片抓取缓存(构建确定性需求,入仓)。键=URL,值={title,desc,image,favicon,ts};ts 超 30 天刷新。手工改动安全:删条目即下次构建重抓。',
+ ...cache,
+ };
+ try {
+ fs.writeFileSync(CACHE_PATH, JSON.stringify(payload, null, 2) + '\n');
+ cacheDirty = false;
+ } catch {
+ /* 缓存写失败不阻断构建 */
+ }
+}
+
+// 并发闸:全局最多 4 个在途抓取
+let active = 0;
+const queue: (() => void)[] = [];
+async function withSlot(fn: () => Promise): Promise {
+ if (active >= CONCURRENCY) await new Promise((r) => queue.push(r));
+ active++;
+ try {
+ return await fn();
+ } finally {
+ active--;
+ queue.shift()?.();
+ }
+}
+
+/** 只允许 http(s):og:image/favicon 来自外部站点,协议白名单挡住 data:/javascript: 等 */
+function safeUrl(raw: string, base: string): string {
+ if (!raw) return '';
+ try {
+ const u = new URL(raw, base);
+ return u.protocol === 'http:' || u.protocol === 'https:' ? u.href : '';
+ } catch {
+ return '';
+ }
+}
+
+/** 读流并截断到 MAX_BYTES:外部页面可能很大,只看头部足够拿到 meta */
+async function readHead(res: Response): Promise {
+ const body = res.body;
+ if (!body) return (await res.text()).slice(0, MAX_BYTES);
+ const reader = body.getReader();
+ const chunks: Uint8Array[] = [];
+ let total = 0;
+ while (total < MAX_BYTES) {
+ const { done, value } = await reader.read();
+ if (done || !value) break;
+ chunks.push(value);
+ total += value.byteLength;
+ }
+ try { await reader.cancel(); } catch { /* 已结束 */ }
+ return new TextDecoder('utf-8', { fatal: false }).decode(
+ Buffer.concat(chunks).subarray(0, MAX_BYTES),
+ );
+}
+
+function extractMeta(html: string, base: string): Omit | null {
+ const metas = html.match(/]*>/gi) ?? [];
+ const pick: Record = {};
+ for (const tag of metas) {
+ const key = /(?:property|name)\s*=\s*["']([^"']+)["']/i.exec(tag)?.[1]?.toLowerCase();
+ const val = /content\s*=\s*["']([^"']*)["']/i.exec(tag)?.[1];
+ if (key && val && !(key in pick)) pick[key] = val;
+ }
+ // 契约门槛:仅当站点显式提供 OG/Twitter 标题才建卡;只有 的无 OG 站回落普通链接
+ const title = pick['og:title'] || pick['twitter:title'] || '';
+ const desc = pick['og:description'] || pick['twitter:description'] || pick['description'] || '';
+ const image = safeUrl(pick['og:image'] || pick['twitter:image'] || '', base);
+ // favicon: 优先,/favicon.ico 兜底(不依赖第三方 s2 服务)
+ const iconHref =
+ (/]*rel\s*=\s*["'][^"']*icon[^"']*["'][^>]*>/i.exec(html) ?? [])
+ .map((t) => /href\s*=\s*["']([^"']+)["']/i.exec(t)?.[1] ?? '')[0] ?? '';
+ const favicon = safeUrl(iconHref || '/favicon.ico', base);
+ if (!title) return null; // 无 OG/Twitter 标题=无预览语义,回落普通链接(契约反例)
+ return {
+ title: decodeEntities(title).slice(0, 200),
+ desc: decodeEntities(desc).slice(0, 300),
+ image,
+ favicon,
+ };
+}
+
+/** 常见 HTML 实体还原(og 字段常有 & 等;最终仍走 text 节点再转义一次) */
+function decodeEntities(s: string): string {
+ return s
+ .replace(/&/g, '&')
+ .replace(/</g, '<')
+ .replace(/>/g, '>')
+ .replace(/"/g, '"')
+ .replace(/'/g, "'")
+ .replace(/ /g, ' ')
+ .replace(/\s+/g, ' ')
+ .trim();
+}
+
+async function fetchMeta(url: string): Promise {
+ const hit = cache[url];
+ if (hit && Date.now() - hit.ts < CACHE_TTL) return hit;
+ try {
+ const meta = await withSlot(async () => {
+ const res = await fetch(url, {
+ headers: { 'User-Agent': UA, Accept: 'text/html,application/xhtml+xml' },
+ signal: AbortSignal.timeout(TIMEOUT_MS),
+ redirect: 'follow',
+ });
+ if (!res.ok) return null;
+ const html = await readHead(res);
+ const m = extractMeta(html, url);
+ return m ? { ...m, ts: Date.now() } : null;
+ });
+ if (meta) {
+ cache[url] = meta;
+ cacheDirty = true;
+ writeCache();
+ }
+ return meta;
+ } catch {
+ return null; // 超时/网络/证书失败:一律回落
+ }
+}
+
+// ── hast 构造(text 节点天然转义) ──
+const el = (tagName: string, properties: Record, children: unknown[] = []) =>
+ ({ type: 'element', tagName, properties, children }) as const;
+const txt = (value: string) => ({ type: 'text', value }) as const;
+
+function buildCard(url: string, meta: CardMeta) {
+ const href = safeUrl(url, url);
+ const host = (() => {
+ try { return new URL(href).hostname.replace(/^www\./, ''); } catch { return ''; }
+ })();
+ const body = el('div', { className: ['lc-body'] }, [
+ el('div', { className: ['lc-title'] }, [txt(meta.title)]),
+ ...(meta.desc ? [el('div', { className: ['lc-desc'] }, [txt(meta.desc)])] : []),
+ el('div', { className: ['lc-host'] }, [
+ ...(meta.favicon
+ ? [el('img', { className: ['lc-favicon'], src: meta.favicon, alt: '', loading: 'lazy', decoding: 'async', width: 16, height: 16 })]
+ : []),
+ txt(host),
+ ]),
+ ]);
+ return el(
+ 'a',
+ {
+ className: ['link-card'],
+ href,
+ target: '_blank',
+ rel: 'noopener noreferrer',
+ },
+ [...(meta.image
+ ? [el('img', { className: ['lc-thumb'], src: meta.image, alt: '', loading: 'lazy', decoding: 'async' })]
+ : []),
+ body],
+ );
+}
+
+/** 段落内「只有一个链接」判定:忽略空白 text */
+function loneLink(node: any): any | null {
+ const kids = (node.children ?? []).filter(
+ (c: any) => !(c.type === 'text' && !c.value.trim()),
+ );
+ if (kids.length !== 1) return null;
+ const only = kids[0];
+ if (only.type !== 'element' || only.tagName !== 'a') return null;
+ return only;
+}
+
+export default function rehypeLinkCards() {
+ return async (tree: any) => {
+ const jobs: { parent: any; index: number; url: string }[] = [];
+ let count = 0;
+ const walk = (node: any) => {
+ const kids: any[] = node.children ?? [];
+ for (let i = 0; i < kids.length; i++) {
+ const child = kids[i];
+ if (child.type === 'element' && child.tagName === 'p') {
+ const link = loneLink(child);
+ const rawHref = link?.properties?.href;
+ if (link && typeof rawHref === 'string' && /^https?:\/\//.test(rawHref)) {
+ if (count < MAX_CARDS) {
+ jobs.push({ parent: node, index: i, url: rawHref });
+ count++;
+ } else {
+ stats.fallback++; // 超护栏:保留普通链接
+ }
+ }
+ }
+ if (child.children) walk(child);
+ }
+ };
+ walk(tree);
+ if (jobs.length === 0) return;
+
+ const results = await Promise.all(jobs.map((j) => fetchMeta(j.url)));
+ // 从后往前替换,避免下标偏移(同父内多个卡片)
+ const byParent = new Map();
+ results.forEach((meta, k) => {
+ const job = jobs[k]!;
+ if (!meta) { stats.fallback++; return; }
+ if (!byParent.has(job.parent)) byParent.set(job.parent, []);
+ byParent.get(job.parent)!.push({ index: job.index, card: buildCard(job.url, meta) });
+ });
+ for (const [parent, list] of byParent) {
+ list.sort((a, b) => b.index - a.index).forEach(({ index, card }) => {
+ parent.children[index] = card;
+ stats.cards++;
+ });
+ }
+ writeCache();
+ };
+}
+
+// 构建收尾汇总(单进程 build):N 卡片 / M 回落
+/**
+ * 汇总日志集成:rehype 插件无法感知"最后一个文件",Astro CLI 末尾 `process.exit` 又会跳过
+ * beforeExit/exit 钩子——用 build:done 阶段汇报(契约要求「N 卡片 / M 回落」)。
+ */
+export function linkCardsReport() {
+ return {
+ name: 'link-cards-report',
+ hooks: {
+ 'astro:build:done': () => {
+ if (stats.cards || stats.fallback) {
+ console.log(`[link-cards] ${stats.cards} 卡片 / ${stats.fallback} 回落`);
+ }
+ writeCache();
+ },
+ },
+ };
+}