Skip to content

搞英语 → 看世界

翻译英文优质信息和名人推特

Menu
  • 首页
  • 作者列表
  • 独立博客
  • 专业媒体
  • 名人推特
  • 邮件列表
  • 关于本站
Menu

在 Astro 中创建 Jekyll 风格的博客文章 URL

Posted on 2023-03-08

网站图标.png

在将我的Jekyll博客转换为Astro时,最棘手的部分之一是确保所有 URL 保持不变。我的博客已经存在将近 20 年了,它已经从不同的框架多次转换,最终导致了一些不同的 URL 格式。然而,我最近使用的是熟悉的/blog/year/month/title格式。在这篇文章中,我将描述如何在 Astro 中创建这种 URL 格式。

第一步:创建帖子页面

假设您的博客模板位于src/pages/blog中,创建src/pages/blog/[...slug].astro 。 ...slug周围的方括号是故意的,让 Astro 知道这个页面有动态路线。在这种情况下,您将用您帖子的 URL 路径替换..slug 。 ...表示slug的值可能包含斜杠。当您定义getStaticPaths()方法时,Astro 知道如何替换slug 。

第 2 步:导出getStaticPaths()

Astro 调用getStaticPaths()函数来确定如何呈现动态路线。该函数必须返回一个对象数组,每个对象至少包含一个params键,指示如何填写文件名的动态部分,以及可选的props键,该键包含页面呈现时在Astro.props中可用的数据。

要为每篇博文创建合适的 URL,您需要为您收藏中的每篇博文导出一个slug 。这是执行此操作的代码:

 import { getCollection } from 'astro:content' ; export async function getStaticPaths () {	const posts = await getCollection ( 'blog' );    return posts . map ( post => {            const date = post.data.pubDate;            const year = post. getFullYear ();            const month = (post. getMonth () + 1 ). padStart ( 2 , "0" );            return { params: { slug: `${ year }/${ month }/${ post . slug }` }, props: { post } } }); };

此代码的第一步是获取blog集合中的所有博客文章。然后检查每个帖子以构建正确的 URL 格式。

如果您使用推荐的 Astro 设置,您将拥有一个包含帖子发布日期的post.data.pubDate属性(属性的名称是可配置的——唯一重要的是它是一个日期对象。)对于方便起见,年和月被分配给变量。年份使用getFullYear()保证四位数;月份是从 0 开始的,因此添加一个以获得日历年,然后调用padStart(2 "0")以确保始终至少有两位数(即7变为07 )。

对于每个帖子,代码返回一个包含params键的对象,该键包含带有 URL 路径的slug属性(重要的是 URL 路径不以斜杠结尾,因为这将导致页面无法呈现)和一个props包含帖子本身的键。

第 3 步:访问要渲染的params和props

在同一个src/pages/blog/[...slug].astro文件中,在getStaticPaths()之后,您可以从渲染每个页面的代码开始。首先,您需要收集有关从Astro.params和Astro.props呈现的页面的信息,如下所示:

 const post = Astro.props; const { Content } = await post. render ();

现在你有了年份和那一年的帖子,所以你需要做的就是渲染帖子。这是一个例子:

 < main > < h1 > { post.data.title } </ h1 > < Content /> </ main >

奖励步骤:重构以便于重用

虽然上面的代码作为示例效果很好,但实际上您不希望仅在src/pages/blog/[...slug].astro中构造您的 URL,因为您还想在其他地方引用这些 URL(即,在您的博客索引页面上)。与其在各处复制该逻辑,不如创建一个将为您格式化 URL 的辅助函数,例如:

 import { getCollection } from 'astro:content' ; export async function loadAndFormatCollection ( name ) {	const posts = await getCollection (name); posts. forEach ( post => {        const date = post.data.pubDate;        const year = post. getFullYear ();        const month = (post. getMonth () + 1 ). padStart ( 2 , "0" ); post.slug = `${ year }/${ month }/${ post . slug }` ; });    return posts; };

然后在src/pages/blog/[...slug].astro你可以将代码简化为:

 import { loadAndFormatCollection } from '../../lib/util.js' ; export async function getStaticPaths () {	const posts = await loadAndFormatCollection ( 'blog' );    return posts . map ( post => {            return { params: { slug: post.slug }, props: { post } } }); };

任何时候你以前使用内置的getCollection() ,你现在应该使用自定义的loadAndFormatCollection()来确保post.slug是正确的值。

奖励步骤:支持 Jekyll 永久链接

Jekyll 允许您通过在 frontmatter 中指定permalink键来覆盖任何给定帖子的默认 URL,例如:

 --- title : "Hello world!" permalink : "/blog/2013/12/my-special-post/" --- Hello world content!

关于permalink键,首先要注意的是,它是一个以斜杠开头和结尾的绝对 URL。它还以“博客”开头,这很可能是您收藏的名称。因此,如果您想确认permalink密钥覆盖默认的博客文章 URL,您需要将这些考虑在内并像这样更新loadAndFormatCollection()函数:

 import { getCollection } from 'astro:content' ; export async function loadAndFormatCollection ( name ) {	const posts = await getCollection (name); posts. forEach ( post => {        const permalink = post.data.permalink;        if (permalink) {            const urlParts = permalink. split ( "/" ); urlParts. shift (); // remove first empty space urlParts. shift (); // remove "blog"            if (permalink. endsWith ( "/" )) { urlParts. pop (); // remove last empty space } post.slug = urlParts. join ( "/" );            return ; }        const date = post.data.pubDate;        const year = post. getFullYear ();        const month = (post. getMonth () + 1 ). padStart ( 2 , "0" ); post.slug = `${ year }/${ month }/${ post . slug }` ; });    return posts; };

现在,如果帖子的前言中有permalink ,它将优先于默认的 URL 格式。

(注意:如果您正在尝试将 Jekyll 博客转换为 Astro,并且不想完成所有这些手动操作,请查看我的astro-jekyll项目,它会为您完成所有这些工作。)

结论

这是 Jekyll 默认包含一些功能的另一个例子,Astro 让您跳过几个环节来实现,但最终并没有那么多额外的工作。由于集合项的slug属性,修改博客文章的 URL 非常简单,同时又不会偏离 Astro 的做事方式太远。毕竟,这就是 Astro 的优势:它完全灵活,您可以让它做任何您想做的事情,只是可能比您习惯于从 Jekyll 获得更多的工作。

原文: https://humanwhocodes.com/blog/2023/03/astro-jekyll-blog-post-url/

本站文章系自动翻译,站长会周期检查,如果有不当内容,请点此留言,非常感谢。
  • Abhinav
  • Abigail Pain
  • Adam Fortuna
  • Alberto Gallego
  • Alex Wlchan
  • Answer.AI
  • Arne Bahlo
  • Ben Carlson
  • Ben Kuhn
  • Bert Hubert
  • Bits about Money
  • Brian Krebs
  • ByteByteGo
  • Chip Huyen
  • Chips and Cheese
  • Christopher Butler
  • Cool Infographics
  • Dan Sinker
  • David Walsh
  • Dmitry Dolzhenko
  • Elad Gil
  • Ellie Huxtable
  • Ethan Marcotte
  • Exponential View
  • FAIL Blog
  • Founder Weekly
  • Geoffrey Huntley
  • Geoffrey Litt
  • Greg Mankiw
  • Henrique Dias
  • Hypercritical
  • IEEE Spectrum
  • Investment Talk
  • Jaz
  • Jeff Geerling
  • Jonas Hietala
  • Josh Comeau
  • Lenny Rachitsky
  • Lou Plummer
  • Luke Wroblewski
  • Matt Stoller
  • Mert Bulan
  • Mostly metrics
  • News Letter
  • NextDraft
  • Non_Interactive
  • Not Boring
  • One Useful Thing
  • Phil Eaton
  • Product Market Fit
  • Readwise
  • ReedyBear
  • Robert Heaton
  • Ruben Schade
  • Sage Economics
  • Sam Altman
  • Sam Rose
  • selfh.st
  • Shtetl-Optimized
  • Simon schreibt
  • Slashdot
  • Small Good Things
  • Taylor Troesh
  • Telegram Blog
  • The Macro Compass
  • The Pomp Letter
  • thesephist
  • Thinking Deep & Wide
  • Tim Kellogg
  • 英文媒体
  • 英文推特
  • 英文独立博客
©2025 搞英语 → 看世界 | Design: Newspaperly WordPress Theme