Adding Journal Search Feature in My Astro JS Project with Pagefind

Tags: Astro JS, Pagefind JS

Context or Problem

Now I have good enough journal listing and views time to add search feature.

I have tried Pagefind before but not really using it in correct way. Now that I believe Astro JS docs also using it on Starlight project, I may just peek their source codes and gain some inspiration from it and make it happen on this website.

Experiment

Again, as typical professional software engineer I will go to official docs especially from Astro JS Pagefind Recipes.

But I couldn’t find it on official Astro JS docs seems like the remove it and move it to other domain https://astro-tips.dev/external-resources .

And yeah, I think it is better to have separate web for it because there will be so many recipe and guides from communities.

There are so many guides on that page makes me want to implement all of them 🤣 but of course I tried to be as pragmatic as possible and straight back to my main target “creating search feature”.

Anyways the tips list seems too old (around 2023) and make me don’t want to view or read them anymore. So I just to official Pagefind docs https://pagefind.app/docs/ and try build it myself.

From https://pagefind.app/docs/installation/ page, it said I can just use and run pagefind through npx command. Then I need to build the site first so I will get /dist folder. Now I can try to run it like this:

npx pagefind --site "dist"{:sh}

And it’s kinda work I guess…

Terminal window
Running Pagefind v1.3.0 (Extended)
Running from: "C:\\Users\\Administrator\\wsa"
Source: "dist"
Output: "dist\\pagefind"
[Walking source directory]
Found 7 files matching **/*.{html}
[Parsing files]
Did not find a data-pagefind-body element on the site.
↳ Indexing all <body> elements on the site.
[Reading languages]
Discovered 1 language: en
[Building search indexes]
Total:
Indexed 1 language
Indexed 7 pages
Indexed 558 words
Indexed 0 filters
Indexed 0 sorts
Finished in 0.146 seconds

So now I can using it by following starter codes like this.

sample.html
<link href="/pagefind/pagefind-ui.css" rel="stylesheet">
<script src="/pagefind/pagefind-ui.js"></script>
<div id="search"></div>
<script>
window.addEventListener('DOMContentLoaded', (event) => {
new PagefindUI({ element: "#search", showSubResults: true });
});
</script>

Of course I got error it said something about Please add the "is:inline" directive to keep this asset from being bundled. But still got same error.

Well I am running it on dev maybe I should run it with npm run preview{:sh} instead. Btw I need to place that script on the bottom to make sure the build is works then re-run the pagefind command.

It seems work, let me see the preview again.

YES! It works!

So in conclusion I need to

Well I deployed it to Vercel and got error Uncaught ReferenceError: PagefindUI is not defined maybe because I forgot to set Vercel adapter ? then I will just try to add that.

BUT! That docs directly wrote this

If you’re using Astro as a static site builder, you only need this adapter if you are using additional Vercel services (e.g. Vercel Web Analytics, Vercel Image Optimization). Otherwise, you do not need an adapter to deploy your static site.

Which is good and now I need to figure out why that Pagefind didn’t work in production.

Now I tried to check in Vercel deployment history and project settings. Seemslike I forgot to set the framework type used in this project and leave it set in to “other” rather than to “Astro”, so I tried to change it to astro and redeploy again.

AGAIN! The Pagefind still not shown. This is led to other assumption because when I inspect the deployment logs it still same and also not running pagefind command which is required. To fix that I will add it to build script hope it will works.

First I am doing it like this

package.json
"scripts": {
"dev": "astro dev",
"build": "astro build && npx pagefind --site 'dist'",
"preview": "astro preview",
"astro": "astro"
}

but it didn’t work LOL, pagefind command need to run only after build. So I read that information from https://otterlord.dev/posts/astro-search/ to add separate postbuild script which is make sense.

So now I tried with this script, also remove the quotes

package.json (modified)
"scripts": {
"build": "astro build",
"dev": "astro dev",
"postbuild": "npx pagefind --site 'dist'",
"postbuild": "npx pagefind --site dist",
"preview": "astro preview",
"astro": "astro"
}

and it works. Now seems like I will also need that postbuild script to Vercel and override the build command.

Vercel Custom Build Command
# they just call astro build, not npm run build
astro build && npm run postbuild

Alright, I will commit this post and see the new build.

Update! well now it works.

Outcome

Search bar are there with default css and default configuration. I can search content actually it’s anything inside <body>{:html} LOL

Possible Next Steps

Adjust configuration on which part should be indexed and searchable. Possibly make automated script to do this pagefind indexing workflow for Astro.

References