# Invite pour ajouter un sitemap et un robots.txt

> Invite pour agent IA afin d'ajouter un sitemap.xml généré dynamiquement et un robots.txt correct à un projet Next.js ou Astro pour un meilleur référencement.

**Type:** Prompt  
**Tools:** Cursor, Claude Code, Codex, Windsurf  
**Stack:** Next.js, Astro, TypeScript  
**Difficulty:** easy  
**Updated:** 2026-06-08

---

Donnez cette invite à votre agent pour ajouter un `sitemap.xml` et un `robots.txt` conformes aux normes — gérant les routes dynamiques, les valeurs de priorité et les dates de dernière modification sans utiliser de service tiers payant.

## Invite principale

```txt title="Main Prompt"
You are working in a Next.js 15 App Router project with TypeScript.
The site has static pages (/, /about, /pricing) and dynamic blog posts in `src/content/blog/`.

Task: add sitemap.xml and robots.txt using only Next.js built-in file conventions.

Requirements:
- Create `src/app/sitemap.ts` (NOT `.xml`) using the Next.js `MetadataRoute.Sitemap` return type.
  - Static URLs: `/`, `/about`, `/pricing` with `priority: 1.0` and `changeFrequency: 'monthly'`.
  - Dynamic URLs: read all MDX files from `src/content/blog/` using `getCollection('blog')` from
    `astro:content` — wait, this is Next.js, so use `fs` + `gray-matter` to read frontmatter.
  - For each post, return `{ url, lastModified, changeFrequency: 'weekly', priority: 0.8 }`.
  - `url` must be an absolute URL using the `NEXT_PUBLIC_SITE_URL` environment variable.
- Create `src/app/robots.ts` (NOT `.txt`) using the `MetadataRoute.Robots` return type.
  - Allow all crawlers for `/*`.
  - Disallow `/api/*` and `/admin/*` for all crawlers.
  - Set `sitemap` to the absolute sitemap URL.
- Add `NEXT_PUBLIC_SITE_URL=https://example.com` to `.env.example`.
- Do NOT install `next-sitemap` or any sitemap package.

Stop and list all files before writing code.
```

## Notes d'implémentation

- `sitemap.ts` et `robots.ts` dans le répertoire `app/` sont des conventions de fichiers Next.js 13.3+ ; ils doivent exporter une fonction par défaut qui retourne l'objet metadata typé — pas un objet Response ou une chaîne.
- Si `NEXT_PUBLIC_SITE_URL` n'est pas défini au moment de la construction, le sitemap contiendra des URLs relatives qui sont invalides selon le protocole Sitemap — validez avec une vérification au démarrage.
- `lastModified` doit être un objet `Date`, pas une chaîne ; Next.js le sérialise en ISO 8601.

## Modifications de fichiers attendues

```txt
src/app/sitemap.ts              (new)
src/app/robots.ts               (new)
src/lib/blog.ts                 (new or edited — getAllPosts helper)
.env.example                    (edited)
```

## Critères d'acceptation

- `GET /sitemap.xml` retourne du XML valide avec toutes les URLs statiques et dynamiques sous forme d'URLs absolues.
- `GET /robots.txt` inclut `Disallow: /api/` et `Sitemap: https://example.com/sitemap.xml`.
- L'ajout d'un nouveau fichier MDX d'article de blog fait apparaître son URL dans le sitemap après `bun run build`.
- Le sitemap est validé sur https://www.xml-sitemaps.com/validate-xml-sitemap.html.

## Commandes de test

```bash
bun run build && bun run start
curl http://localhost:3000/sitemap.xml | xmllint --format - | head -40
curl http://localhost:3000/robots.txt
# confirm /api/ is disallowed and sitemap URL is absolute
bun run typecheck
```

## Erreurs courantes de l'IA

- Créer un fichier statique `public/sitemap.xml` au lieu de la convention dynamique `src/app/sitemap.ts`.
- Utiliser des URLs relatives dans le sitemap (par ex. `/blog/my-post`) — les sitemaps nécessitent des URLs absolues.
- Installer `next-sitemap` alors que l'invite l'interdit explicitement.
- Configurer `robots.txt` pour interdire tous les robots (`Disallow: /`), ce qui désindexe tout le site.

## Invite de correction

```txt title="Fix Prompt"
The sitemap contains relative URLs or robots.txt disallows too much. Fix in order:
1. In `src/app/sitemap.ts`, construct every URL as:
   `const base = process.env.NEXT_PUBLIC_SITE_URL ?? 'https://example.com'; url: \`\${base}/blog/\${post.slug}\``
2. In `src/app/robots.ts`, verify the rules object:
   `{ userAgent: '*', allow: '/', disallow: ['/api/', '/admin/'] }`.
3. Confirm `sitemap.ts` exports a default async function (not a named export).
Show only the corrected diff.
```