技术Github ActionAstro

在 Astro 实现链接预览

· 4min

起因

在 twitter 上看到 cali castle 大佬直播实现了一个有趣的功能,这个功能的来源是 uiwtf。 在博客中通常包含许多链接以提供额外的上下文或进一步阅读。但是,打开外部链接可能会打乱专注的阅读,导致我们被其他所吸引走。 如果可以在悬停和时显示链接的预览,应该能更加专注于内容本身吧! 我觉得这会让阅读带来一个不错体验的功能,大佬使用的 next.js 那一套。我刚用 astro 也就没法直接拿来用了,就尝试看能否在我的博客上也加上这个功能!

实现

大佬的实现方式是,在服务端部署了一个接口,在使用者需要的时候发送请求。然后服务端通过无头浏览器去截取对应链接的内容! 首先我的是一个纯静态,就没办法动态的去抓去链接的预览图了。 咋办呢?想到一个方式,既然是一个纯静态的内容,那么是不是可以在生成静态内容中分析出链接,然后预先生成内容呢?
do it。

获取 astro 中的超链接

在 Astro Integration API 文档中发现了 astro:build:done 这个 hooks 根据 pages 、 dir 这两个参数就可以找到所有生成出来的页面了。

'astro:build:done'?: (options: { dir: URL; routes: RouteData[];  pages: { pathname: string; }[]; }) => void | Promise<void>;

复制成功!

'astro:build:done'?: (options: { dir: URL; routes: RouteData[];  pages: { pathname: string; }[]; }) => void | Promise<void>;

复制成功!

那接下里我们就可以通过解析这些内容,从而拿到页面中的超链接了。当然自己写 html parse 是不可能的!直接就上 npm 上开找! htmlparser2 是一个能快速解析 html 的包,我们熟知的 cheerio 就是用的这个。
有了解析库那就简单了,这个库也有提供简易的 DOM 操作相关的api。就类似平时操作原生 DOM 一样过滤出我们需要的内容能拿到页面中所有的超链接了。

获取截图

获取截图也比较容易实现通过一些无头的浏览器,目前主流的是 Playwright、Puppeteer,我这里里直接用的 capture-website 使用也比较容易

展示内容

对于前面收集的链接可能需要一些处理,比如哪些是需要预览的链接。生成出来的预览图片如何关联页面的链接等 在 astro 组件中,可以直接使用 astro 编写一个显示的UI组件即可。在 .md 文件中的链接就需要自定义插件( todo )处理了

example google & myblog

google szqingt blog
<fancy-link href='https://google.com'>google</fancy-link>

<fancy-link href='https://szqingt.github.io'>szqingt</fancy-link>

复制成功!

<fancy-link href='https://google.com'>google</fancy-link>

<fancy-link href='https://szqingt.github.io'>szqingt</fancy-link>

复制成功!

more todo

  • markdown plugin
  • github action scheduled task (done)
  • lazy load(img lading laze)
  • capture dark preview (done)