Astro v2.0
In my continuing Astro saga, here’s the latest chapter. This post marks the completion of this site’s Astro v2 upgrade. Rather than explain how to upgrade because that already exists, this is more of my thoughts and impressions on how the upgrade went.
Since that last post where I said “I should work on a plugin for Astro + MiniSearch”,
I went ahead and did that.
At the end of January 2023, Astro v2 launched.
One of the headline features was Content collections, something similar to Nuxt Content.
If you consider .md
files to be data and .astro
files to be presentation, then keeping them separated makes tons of sense.
Although I didn’t have to use the new content collections, part of this site’s raison d’être is to understand and extend Astro, so I went for it. If it wasn’t for my search plugin, upgrading probably would have been fairly smooth. I think the Astro team did a phenomenal job once again of documenting how to do it and keeping breaking changes to a minimum. In particular, the “Migrating from File-Based Routing” section was clutch.
For the most part, things Just Worked. Things I like about Astro v2:
- Markdown and MDX plugin configuration is improved.
- Using content collections is just cleaner than file-based routing — for example, you don’t have to specify layout in the frontmatter of every blog post anymore.
- Upgrades to Vite 4, which increases my confidence that Astro will continue to stay modern.
Not so great:
- I had a lot of trouble porting my search indexer endpoint.
I got the cryptic error
ReferenceError: Cannot access '_page9' before initialization
at first, and the “generating static routes” step would just die silently. I finally figured out that all content fetching code had to exist inside of theget()
function, not just at the top of the file like before. - Relative links and images in markdown files that were migrated to content collections were initially broken.
- If you use schemas but you don’t define a particular property, when you try to output the undefined property in a component, Astro will hide it instead. That is the Zod library’s default behavior and can be overridden.
- A weird error from an old workaround in astro-icon took a while to find and remove.
- Content collections schemas get very odd if you color outside the lines.
More detail about that last one.
It’s cool to define collection schemas, but they are sort of generated at build time I guess?
The documentation is still a little sparse, or maybe my use case is extreme.
For this site, I have two content collections, blog
and articles
that I want to index for search.
Both collections have a mandatory title
attribute and an optional description
.
The documentation describes CollectionEntry
class but it’s not clear how to use it.
In the end I sort of figured it out, but it’s not ideal.
I used CollectionEntry<any>
in my search indexer and defined a base search item schema with Zod.
I used Zod’s extend
method to “inherit” from a common set of searchable document fields.
Instead, I wish there was a ContentEntry<"search">
type without requiring an empty “search” collection.
Since I’m ignoring the type anyway there’s little purpose to the fancy schema.
That may be a microcosm of TypeScript’s overall failures though.