https://github.com/coana-tech/next-plugin-metadata-extractor
Next.js plugin to automatically extract metadata from pages
https://github.com/coana-tech/next-plugin-metadata-extractor
extractor metadata nextjs plugin searchindex webpack
Last synced: 5 months ago
JSON representation
Next.js plugin to automatically extract metadata from pages
- Host: GitHub
- URL: https://github.com/coana-tech/next-plugin-metadata-extractor
- Owner: coana-tech
- License: mit
- Created: 2025-02-06T13:37:17.000Z (over 1 year ago)
- Default Branch: main
- Last Pushed: 2025-02-17T10:00:14.000Z (over 1 year ago)
- Last Synced: 2025-09-20T03:01:58.274Z (10 months ago)
- Topics: extractor, metadata, nextjs, plugin, searchindex, webpack
- Language: TypeScript
- Homepage:
- Size: 82 KB
- Stars: 0
- Watchers: 3
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
# @coana-tech/next-plugin-metadata-extractor
A Next.js plugin that automatically extracts page metadata to a JSON file for site-wide search functionality.
## Features
- Automatically collects static metadata from Next.js pages during development and build
- Updates metadata in real-time during development
- TypeScript support
- Zero configuration required
## Example Metadata Output
```json
// metadata.json
[
{
"pathname": "/home",
"metadata": {
"title": "Home Page",
"description": "Home Page Description"
}
},
{
"pathname": "/about",
"metadata": {
"title": "About Page",
"description": "About Page Description",
"keywords": ["about", "page", "description"]
}
}
]
```
## Installation
```bash
npm install @coana-tech/next-plugin-metadata-extractor
# or
pnpm add @coana-tech/next-plugin-metadata-extractor
# or
yarn add @coana-tech/next-plugin-metadata-extractor
```
## Usage
1. Add the plugin to your `next.config.js`:
```js
// next.config.js
const { MetadataCollectorPlugin } = require('@coana-tech/next-plugin-metadata-extractor');
/** @type {import('next').NextConfig} */
const nextConfig = {
webpack: (config, { isServer, dev }) => {
if (isServer) {
config.plugins.push(new MetadataCollectorPlugin({ dev }));
}
return config;
}
};
module.exports = nextConfig;
```
2. Define static metadata in your pages:
```tsx
// app/page.tsx
import type { Metadata } from 'next';
export const metadata: Metadata = {
title: "My Page",
description: "My Page Description",
};
```
See the [Next.js documentation](https://nextjs.org/docs/app/building-your-application/optimizing/metadata) for more information about defining metadata.
**NOTE:** The plugin does not support dynamically computed metadata.
3. Start the development server:
```bash
npm run dev
```
4. Fetch the `metadata.json` file from the `public` directory:
```tsx
// app/components/Metadata.tsx
import { useState, useEffect } from 'react';
import type { PageMetadata } from '@coana-tech/next-plugin-metadata-extractor';
function Component() {
const [metadata, setMetadata] = useState([]);
useEffect(() => {
fetch('/metadata.json')
.then(res => res.json())
.then(setMetadata);
}, []);
return (
{metadata.map(item => (
{item.metadata.title}
))}
);
}
```
## Configuration
The MetadataCollectorPlugin accepts the following configuration options:
| Option | Description | Default |
|--------|-------------|---------|
| `outputPath` | Set output path for the metadata file, must end with `.json` | `public/metadata.json` |
| `dir` | Set directory to search for page files | `app` |
| `files` | Set files to collect from metadata, supports glob patterns | `["**/page.tsx", "**/page.ts", "**/page.jsx", "**/page.js"]` |
| `keys` | Set keys to collect from metadata | `['title', 'description', 'keywords', 'category']` |
| `dev` | Enable development mode with debouncing | `false` |
| `debounceTime` | Debounce time in milliseconds for dev mode updates | `1000` |
## Advanced Usage
### Server-side usage
If you don't want the metadata file to be public, set the `outputPath` to a server directory and create a server action to fetch the metadata.
Here's an example:
```tsx
// next.config.js
const nextConfig = {
webpack: (config, { isServer, dev }) => {
isServer && config.plugins.push(new MetadataCollectorPlugin(
{
dev,
outputPath: 'src/actions/metadata.json', // <-- output path
}
));
return config;
}
};
// src/actions/metadata.ts
import metadata from './metadata.json';
export async function getMetadata() {
const { userId } = auth();
if (!userId) {
throw new Error('Unauthorized');
}
return metadata;
}
```
### Adding Fuzzy Search
You can enhance the search functionality with fuzzy matching using libraries like Fuse.js. Here's an example:
```typescript
import Fuse from 'fuse.js';
import type { PageMetadata } from '@coana-tech/next-plugin-metadata-extractor';
function FuzzySearch() {
const [fuse, setFuse] = useState | null>(null);
const [results, setResults] = useState([]);
useEffect(() => {
// Load metadata and initialize Fuse.js
fetch('/metadata.json')
.then(res => res.json())
.then(data => {
setFuse(new Fuse(data, {
keys: ['metadata.title', 'metadata.description'],
threshold: 0.3,
distance: 100
}));
});
}, []);
const handleSearch = useCallback((term: string) => {
if (!fuse || !term.trim()) {
setResults([]);
return;
}
setResults(fuse.search(term).map(result => result.item));
}, [fuse]);
return (
handleSearch(e.target.value)} />
{results.map(result => (
- {result.metadata.title}
))}
);
}
```
See [Fuse.js documentation](https://fusejs.io/) for more configuration options.
## Compatibility
This plugin is tested with Next.js 14.
## License
MIT