Building a static site search with Pagefind

Introduction

Hey there, web wizards and code conjurers! Today, I’m here to spill the beans on a magical tool that’ll have you searching through your static site like a pro without sacrificing your users’ data to the digital overlords. Say goodbye to the snooping eyes of Algolia and Google, and say hello to Pagefind – the hero we need in the wild world of web development!

Pagefind

So, what’s the deal with Pagefind? Well, it’s like having your own personal search genie, but without the need for complex setups or sacrificing your site’s performance. Here’s a quick rundown of its enchanting features straight from the Pagefind spellbook:

  • Multilingual Magic: Zero-config support for sites that speak many tongues.
  • Filtering Sorcery: A powerful filtering engine for organizing your knowledge bases.
  • Custom Sorting Spells: Tailor your search results with custom sort attributes.
  • Metadata Mysticism: Keep track of custom metadata for your pages.
  • Weighted Wand Wielding: Adjust the importance of content in your search results.
  • Section Spellcasting: Fetch results from specific – sections of your pages.
  • Domain Diving: Search across multiple domains with ease.
  • Index Anything Incantation: From PDFs to JSON files, if it’s digital, Pagefind can find it!
  • Low-Bandwidth Brilliance: All this magic with minimal bandwidth consumption – now that’s some serious wizardry!

Summoning Pagefind

Now, let’s talk about summoning this mystical tool onto your Astro-powered site. It’s as easy as waving your wand and chanting npx pagefind --site "dist. Poof! Your site’s now equipped with the power of search!

With a flick of your build script wand, you’ll integrate Pagefind seamlessly into your deployment pipeline. Just like adding a secret ingredient to a potion, modify your package.json build script to include Pagefind’s magic words.

JSON
  "scripts": {
    "dev": "astro dev",
    "start": "astro dev",
    "build": "astro build && pagefind --site dist && rm dist/pagefind/*.css && cp -r dist/pagefind public/",
    "preview": "astro preview",
    "astro": "astro"
  },

If you are not using Astro.js you will have to replace distwith your build directory. I will also explain why I am making the CSS dissapear.

Running the command should automagically build your index like so:

Bash
[Building search indexes]
Total:
  Indexed 1 language
  Indexed 19 pages
  Indexed 1328 words
  Indexed 0 filters
  Indexed 0 sorts

Finished in 0.043 seconds

Now my site is not that big, yet but 0.043 seconds is still very fast and if you are pying for build time, also next to nothing. Pagefind being written in Rust is very efficient.

Getting Cozy with Pagefind’s UI

Alright, so now you’ve got this powerful search engine at your fingertips. But wait, what’s this? Pagefind’s UI is a bit… opinionated. Fear not, fellow sorcerers! With a dash of JavaScript and a sprinkle of CSS, we’ll make it dance to our tune!

Weaving a custom UI spell involves a bit of JavaScript incantation to tweak placeholders and buttons just the way we like them. Plus, with a bit of CSS wizardry, we can transform Pagefind’s UI into something straight out of our own enchanting design dreams!

Astro
---import"../style/pagefind.css";---<divclass="max-w-96 flex"><divid="search"></div></div><scriptsrc="/pagefind/pagefind-ui.js"is:inline></script><script>document.addEventListener("astro:page-load",()=>{newPagefindUI({element:"#search",debounceTimeoutMs:500,resetStyles:!0,showEmptyFilters:!1,excerptLength:15,showImages:!1,addStyles:!1,});constsearchInput=document.querySelector<HTMLInputElement>(".pagefind-ui__search-input");constclearButton=document.querySelector<HTMLDivElement>(".pagefind-ui__search-clear");if(searchInput){searchInput.placeholder="Site Search";}if(clearButton){clearButton.innerText="Clear";}});</script>
  • /pagefind/pagefind-ui.js is Pagefind specific JavaScript.In the future I plan to reverse it as there is a lot of uneccessary code in there.
  • I am using astro:page-load as an event listener since I am using view transitions.

Embrace Your Inner Stylist

Ah,but crafting a unique style for your search UI is where the real fun begins!With the power of TailwindCSS (or your trusty CSS wand),you can mold Pagefind’s UI to fit your site’s aesthetic like a bespoke wizard robe.

With a little imagination and a lot of creativity,you’ll end up with a search UI that’s as unique as your magical incantations.

CSS
.pagefind-ui__results-area{@applyborderborder-pink-500dark:text-white text-black p-4;@applyabsolutez-50dark:bg-gray-900 bg-white;@applymax-h-96overflow-y-automr-10;}.pagefind-ui__result{@applyborder-tmy-4dark:text-white text-black;}.pagefind-ui__resultmark{@applybg-fuchsia-700text-fuchsia-300;}.pagefind-ui__form{@applyborderdark:border-white border-black;}.pagefind-ui__search-input{@applydark:text-white text-black bg-transparent;}.pagefind-ui__search-input{@applyplaceholder:italicplaceholder:text-slate-400 p-2 border-r border-black;}.pagefind-ui__form{@applymin-w-full;}.pagefind-ui__message{@applyfont-semiboldfirst-letter:text-pink-500;}.pagefind-ui__result-link{@applyfont-boldunderlinetext-blue-500;}.pagefind-ui__result-title{@applymb-1;}.pagefind-ui__result-inner{@applymy-3;}.pagefind-ui__button{@applyborderborder-blackpy-1px-2hover:underlinemt-4;}.pagefind-ui__search-clear{@applymr-2;}

(@apply is TailwindCSS specific,you can use regular CSS if you please)

And there you have it,folks – the mystical journey of integrating Pagefind into your static site,complete with a touch of your own wizardly flair!

custom search ui

Now go forth,weave your web spells,and may your users’ search journeys be as magical as your coding adventures!🧙✨

Where to go from here

I gave you a quick look into building a simple static site search.In my opinion the JavaSript files from Pagefind should be slimmed down to work,in my case for Astro,the CSS should be applied by you and Pagefind should just leave you a simple unstyled search,I am sure they would be happy if someone helped them out by doing this.

I was thinking about hosting my index on a Cloudflare Worker,then styling my search form however I want and just hooking up the Worker endpoint with the form,basically like a self hosted Algolia.An alternative to Pagefind could be Fuse.js,the drawback is that you would have to build your own index.

Bonus:

You can try out my search here: Exploit.to Search

This post was originally posted on 17 Mar 2024 at on myCybersecurity blog.

Comments

Leave a Reply

Your email address will not be published.Required fields are marked*