### Enhancing Search with Astro Actions and Fuse.js
Static websites are fantastic, and I’m a huge fan. However, they come with certain limitations. Most static site generators either remain entirely static or lose the benefits of true static generation when introducing server routes.
Astro is taking a unique approach by maintaining a strong foundation in static generation while incorporating powerful server-side capabilities. One of these features is **Astro Actions**, which allows sites to leverage server functionality while remaining mostly static. A great example of this is implementing search functionality.
For content-driven sites, search is often handled on the front end, through a third-party service, or by converting the entire site into a server-side application. With Astro, we can generate most of the site at build time while using a small server-side function to handle search using **Fuse.js**.
In this guide, we’ll build a search feature using Astro Actions and Fuse.js, allowing users to search through a set of bookmarks generated at build time.
—
## Setting Up the Project
To begin, create a new Astro project by running:
“`sh
npm create astro@latest
“`
Astro will prompt you with a few setup questions:
– **Project location**: Choose a directory (e.g., `./astro-search`).
– **Starter template**: Select the **basic** minimalist starter.
– **Install dependencies?** Yes.
– **Initialize a Git repository?** Recommended.
Once the setup is complete, navigate to your project directory and start the development server:
“`sh
npm run dev
“`
You should see the default Astro homepage.
—
## Basic Setup
First, remove the default content from `src/pages/index.astro` by deleting the `
“`sh
npx astro add tailwind
“`
Follow the CLI instructions to complete the setup. Next, update `index.astro` with some basic markup:
“`astro
—
import Layout from ‘../layouts/Layout.astro’;
—
My Latest Bookmarks
Displaying 10 of many bookmarks
“`
Now, let’s load our bookmarks.
—
## Adding Bookmark Data with Astro Content Layer
We’ll use a JSON file to store bookmark data. Create `src/data/bookmarks.json` and add some sample bookmarks:
“`json
[
{
“pageTitle”: “Our Favorite Sandwich Bread | King Arthur Baking”,
“url”: “https://www.kingarthurbaking.com/recipes/our-favorite-sandwich-bread-recipe”,
“description”: “Classic American sandwich loaf, perfect for French toast and sandwiches.”,
“id”: “007y8pmEOvhwldfT3wx1MW”
}
]
“`
To make this data available in Astro, create `src/content.config.ts`:
“`ts
import { defineCollection, z } from “astro:content”;
import { file } from ‘astro/loaders’;
const bookmarks = defineCollection({
schema: z.object({
pageTitle: z.string(),
url: z.string(),
description: z.string().optional(),
}),
loader: file(“src/data/bookmarks.json”),
});
export const collections = { bookmarks };
“`
Restart the Astro server (`npm run dev`) to apply the changes.
—
## Displaying Bookmarks on the Homepage
Modify `src/pages/index.astro` to fetch and display bookmarks:
“`astro
—
import Layout from ‘../layouts/Layout.astro’;
import { getCollection } from ‘astro:content’;
const bookmarks = await getCollection(‘bookmarks’);
—
My Latest Bookmarks
Displaying 10 of {bookmarks.length}
Latest Bookmarks
-
{bookmarks.slice(0, 10).map((item) => (
-
{item.data?.pageTitle}
{item.data?.description}
))}
“`
Now, let’s build the search functionality.
—
## Implementing