Skip to content

Vanilla JS / Static HTML

aeo.js works on any project that produces static HTML. Use the CLI directly — no plugin, no module, no framework.

Terminal window
npx aeo.js generate --url https://mysite.com --title "My Site" --out public

generate walks your output directory, extracts page content, and emits robots.txt, llms.txt, sitemap.xml, ai-index.json, and schema.json next to your HTML.

SourceHow to setUse when
Built HTML in outDir--out public (CLI)You have a built static site with *.html files
contentDirprogrammatic only — see belowYou have handwritten .md / .mdx files
pages arrayprogrammatic only — see belowExplicit control for runtime-only routes

The CLI exposes --out for outDir. For the richer options (contentDir, pages), call the package’s API directly:

scripts/aeo.mjs
import { generateAEOFiles, resolveConfig } from 'aeo.js';
await generateAEOFiles(resolveConfig({
title: 'My Site',
url: 'https://mysite.com',
contentDir: 'content',
outDir: 'public',
pages: [{ pathname: '/', title: 'Home' }],
}));
package.json
{
"scripts": {
"build:aeo": "aeo.js generate --url https://mysite.com --title \"My Site\" --out ."
}
}
package.json
{
"scripts": {
"build": "eleventy",
"postbuild": "aeo.js generate --url https://mysite.com --title \"My Site\" --out _site"
}
}

For Hugo use --out public; for Jekyll --out _site. The postbuild script runs automatically after npm run build.

The CLI’s --out flag covers built HTML; to also pull .md front-matter and bodies from a contentDir, use the programmatic API:

scripts/aeo.mjs
import { generateAEOFiles, resolveConfig } from 'aeo.js';
await generateAEOFiles(resolveConfig({
title: 'My Blog',
url: 'https://myblog.dev',
contentDir: 'content', // pull post bodies from here
outDir: 'public', // write generated files here
}));
package.json
{
"scripts": {
"build:aeo": "node scripts/aeo.mjs"
}
}
<script type="module">
import { AeoWidget } from 'https://esm.sh/aeo.js/widget';
new AeoWidget({
config: {
title: 'My Site',
url: 'https://mysite.com',
widget: { enabled: true, position: 'bottom-right', size: 'small' },
},
});
</script>

Or install and bundle locally with import { AeoWidget } from 'aeo.js/widget'.

- run: npx aeo.js check --json | tee audit.json
- run: |
SCORE=$(jq '.audit.score' audit.json)
[ "$SCORE" -ge 70 ] || { echo "GEO score $SCORE below 70"; exit 1; }