diff --git a/.env.example b/.env.example index f83207b..035c5ec 100644 --- a/.env.example +++ b/.env.example @@ -24,3 +24,6 @@ NEXT_PUBLIC_CALCOM_URL=https://cal.letsbe.biz # ── Site URL ── NEXT_PUBLIC_SITE_URL=https://staging.letsbe.biz + +# ── Google Analytics ── +NEXT_PUBLIC_GA_ID=G-XXXXXXXXXX diff --git a/docs/superpowers/specs/2026-04-07-seo-optimization-design.md b/docs/superpowers/specs/2026-04-07-seo-optimization-design.md new file mode 100644 index 0000000..8c626c3 --- /dev/null +++ b/docs/superpowers/specs/2026-04-07-seo-optimization-design.md @@ -0,0 +1,151 @@ +# SEO Optimization — Design Spec + +**Date:** 2026-04-07 +**Domain:** letsbe.biz +**Stack:** Next.js 16 App Router, next-intl (en/fr, `as-needed` prefix), Payload CMS + +## Current State + +The site has a single `metadata` export in the layout with a generic title/description. No robots.txt, no sitemap, no OG tags, no hreflang, no structured data, no analytics. The services page has a static English-only metadata export. Case study pages and the homepage have no metadata at all. + +## 1. Metadata Foundation + +### metadataBase +Add `metadataBase: new URL('https://letsbe.biz')` to `src/app/(frontend)/[locale]/layout.tsx`. Required for OG images and canonical URLs to resolve as absolute URLs. + +### i18n SEO keys +Add a `meta` section to both `en.json` and `fr.json`: +```json +{ + "meta": { + "home": { "title": "...", "description": "..." }, + "about": { "title": "...", "description": "..." }, + "services": { "title": "...", "description": "..." }, + "work": { + "monaco-ocean": { "title": "...", "description": "..." }, + "port-nimara": { "title": "...", "description": "..." }, + "port-amador": { "title": "...", "description": "..." } + } + } +} +``` + +### Per-page generateMetadata +Convert every page to use `generateMetadata({ params })`: +- Read locale from params +- Call `getTranslations({ locale, namespace: 'meta' })` for localized title/description +- Set `alternates.canonical` (e.g., `https://letsbe.biz/about` for en, `https://letsbe.biz/fr/about` for fr) +- Set `alternates.languages` for hreflang: + - `en` → unprefixed path + - `fr` → `/fr/` prefixed path + - `x-default` → unprefixed (English) + +### Layout metadata +Convert the layout's static `metadata` to `generateMetadata()` so it can set locale-aware defaults, `metadataBase`, and default OG/Twitter config. + +## 2. Social Sharing (Open Graph / Twitter) + +### Default OG in layout +```ts +openGraph: { + type: 'website', + siteName: 'LetsBe.', + locale: locale === 'fr' ? 'fr_FR' : 'en_US', + images: [{ url: '/images/og-default.png', width: 1200, height: 630 }], +} +twitter: { + card: 'summary_large_image', +} +``` + +### OG image +Create a 1200x630 OG default image using sharp — the logo centered on a branded background (the site's surface color with the blue accent). Place at `public/images/og-default.png`. + +### Per-page OG +Case study pages override with their hero image. Other pages use the default. + +## 3. Crawl Infrastructure + +### robots.ts +`src/app/robots.ts`: +- Allow all user agents +- Disallow `/admin/`, `/api/` +- Sitemap: `https://letsbe.biz/sitemap.xml` + +### sitemap.ts +`src/app/sitemap.ts`: +- Static routes: `/`, `/about`, `/services` +- Dynamic routes: `/work/monaco-ocean`, `/work/port-nimara`, `/work/port-amador` +- Each entry includes both locale variants in `alternates.languages` +- `lastModified` set to build date +- `changeFrequency` and `priority` set appropriately + +## 4. Structured Data (JSON-LD) + +Inject via ` + + {/* Google tag (gtag.js) */} + + + ) +} diff --git a/src/i18n/messages/en.json b/src/i18n/messages/en.json index 5abb40f..3667ed8 100644 --- a/src/i18n/messages/en.json +++ b/src/i18n/messages/en.json @@ -1,4 +1,33 @@ { + "meta": { + "siteName": "LetsBe.", + "home": { + "title": "LetsBe. | Custom Web Design, Software & Digital Infrastructure", + "description": "Bespoke websites, purpose-built software, AI integration, and private infrastructure — designed, built, and managed by one dedicated team." + }, + "about": { + "title": "About LetsBe. | Our Story & Approach", + "description": "An American-founded digital studio building custom websites, software, and platforms for businesses that care about quality." + }, + "services": { + "title": "Services | LetsBe. — Web Design, Software & Infrastructure", + "description": "Custom web design, purpose-built software, AI automation, and private infrastructure — three pillars of digital excellence under one roof." + }, + "work": { + "monaco-ocean": { + "title": "Monaco Ocean Protection Challenge | LetsBe.", + "description": "AI-powered judging and analytics platform for one of the Mediterranean's leading conservation events." + }, + "port-nimara": { + "title": "Port Nimara — Maritime Digital Hub | LetsBe.", + "description": "Custom website and full CRM for lead management, berth assignment, and marina operations." + }, + "port-amador": { + "title": "Port Amador — Premium Nautical Experience | LetsBe.", + "description": "Website and private digital infrastructure for a premium marina — cloud storage, email, and file management." + } + } + }, "nav": { "services": "Services", "configure": "Get Started", diff --git a/src/i18n/messages/fr.json b/src/i18n/messages/fr.json index ee60b1a..a03b408 100644 --- a/src/i18n/messages/fr.json +++ b/src/i18n/messages/fr.json @@ -1,4 +1,33 @@ { + "meta": { + "siteName": "LetsBe.", + "home": { + "title": "LetsBe. | Design Web Sur Mesure, Logiciels & Infrastructure Digitale", + "description": "Sites web sur mesure, logiciels dédiés, intégration IA et infrastructure privée — conçus, développés et gérés par une seule équipe." + }, + "about": { + "title": "À Propos de LetsBe. | Notre Histoire & Approche", + "description": "Un studio digital fondé aux États-Unis, créant des sites web, logiciels et plateformes sur mesure pour les entreprises exigeantes." + }, + "services": { + "title": "Services | LetsBe. — Design Web, Logiciels & Infrastructure", + "description": "Design web sur mesure, logiciels dédiés, automatisation IA et infrastructure privée — trois piliers d'excellence digitale sous un même toit." + }, + "work": { + "monaco-ocean": { + "title": "Monaco Ocean Protection Challenge | LetsBe.", + "description": "Plateforme de jugement et d'analyse propulsée par l'IA pour l'un des événements de conservation majeurs de la Méditerranée." + }, + "port-nimara": { + "title": "Port Nimara — Hub Digital Maritime | LetsBe.", + "description": "Site web sur mesure et CRM complet pour la gestion des prospects, l'attribution des places et les opérations de la marina." + }, + "port-amador": { + "title": "Port Amador — Expérience Nautique Premium | LetsBe.", + "description": "Site web et infrastructure digitale privée pour une marina premium — stockage cloud, email et gestion de fichiers." + } + } + }, "nav": { "services": "Services", "configure": "Démarrer",