Technical SEO & GEO: A Complete Step-by-Step Guide to a Fast, AI-Discoverable Website

Use this technical SEO and GEO checklist to make your website fast, crawlable, indexable, and discoverable in Google and AI answer engines.

Q Zhao
Q Zhao18 min readJuly 20, 2026
Technical SEO & GEO: A Complete Step-by-Step Guide to a Fast, AI-Discoverable Website
TL;DR: This technical SEO and GEO guide covers the largely one-time setup behind a fast, searchable, AI-discoverable website: clean URLs, structured data, sensible caching, crawl access, and a few signals that are cheap to add and easy to get wrong. Part I shows you how to audit and implement that foundation on any website — with a separate step for the extra decisions blogs bring. Part II, the Content Guide, will cover what to publish and how to make it worth finding.
⚡ Turn this guide into an audit

If you use Claude or Codex, give it this article plus access to your website or codebase and ask it to produce a technical SEO and AI-discoverability report. A useful prompt:

Run a technical SEO and GEO audit of my website against every
relevant check in this article.
For each item, return Pass, Fail, or Could not verify; cite the
evidence; and rank any fixes by impact. Do not change anything yet.

This technical SEO checklist came from building WeBreeze, an AI-agent platform that automates much of the work traditionally handled by an SEO and GEO agency: research, content creation, optimization, publishing, and measurement. We first applied the setup below to client blogs, but it works for any public website; the final section covers the few choices that are blog-specific.

For about a decade, "getting found" meant one thing: rank on Google. That's still true, but it's no longer the whole game. A growing share of people now ask a question and get an answer — synthesized by an AI — instead of a list of blue links. If your website isn't set up so those systems can crawl it, understand it, and trust it, you're invisible to a channel that barely existed a few years ago.

This work goes by several overlapping names: AI search optimization; GEO, or Generative Engine Optimization; AEO, or Answer Engine Optimization; and sometimes LLMO, or Large Language Model Optimization. In this guide, technical GEO means making your site accessible and understandable to AI answer engines, then measuring whether they mention and cite it.

The good news: most technical SEO and GEO setup is shared. Google confirms that its foundational SEO guidance also applies to its generative AI search features. The same clean foundations often help other answer engines too — and a lot of it (fast pages, clear titles, accessible markup) makes the website better for visitors. Most of it is a one-time job: configure it correctly once, and every page you publish inherits it.

Contents

We'll take these one at a time: plain language first, code where it helps, and a clear distinction between documented practice and experimental GEO bets. WeBreeze applies this foundation automatically to the content its agents publish, but the same checklist works for product sites, company sites, documentation, directories, and other public websites.

Start here — if you only do a few things

The two biggest levers — genuinely useful content and the links it earns — are outside this technical audit. Within the setup below, the highest-value pieces are:

  1. Get the basics right — one web address per page, a real title on each, and a proper "not found" page. (Steps 1 & 6)
  2. Let the AI engines in and hand search a map — allow the answer-engine crawlers, publish a sitemap, verify Search Console. (Steps 4 & 6)
  3. Make it fast — put your public pages behind an edge cache. (Step 5)

Everything else is refinement. Structured data helps, but less — don't let it hold up publishing.

Step 1 — Get the page basics right

Bottom line — four boring things have to be right before anything clever matters: one web address per page, one main headline, a unique title, and clean underlying HTML.

Canonical URLs

Every page should have one preferred address. Without a canonical, trailing slashes, www variants, and tracking parameters can look like separate pages and split their signals. Google's canonicalization guide treats redirects and rel="canonical" as strong signals.

Choose one hostname, make both the bare and www domains resolve, redirect the duplicate host, and emit an absolute canonical on every indexable page. WeBreeze generates these canonicals for agent-published content automatically.

🛠 For your developer

Redirect duplicate hosts with 301/308, preserving path and query. Emit <link rel="canonical" href="…"> for parameter variants that remain 200. If the site's default-language redirect is permanent, use 301/308; use a temporary redirect only when that destination can change.

Common mistake: letting example.com and www.example.com (or the trailing-slash and non-slash versions) both resolve with a 200. Pick one, redirect the rest.

The <h1> tag

Give each page one clear <h1>. This is a maintainability convention, not a hard Google rule, but it removes ambiguity. A common CMS bug renders both the template title and a leading Markdown heading as <h1>; WeBreeze detects and demotes the body heading at render time.

Titles and meta descriptions

Give every important page a unique <title> and meta description. Check the rendered output, not just the CMS fields. Google generates title links algorithmically and may rewrite snippets, so treat both as strong suggestions rather than guaranteed display text.

Semantic HTML

Use real <main>, <nav>, and heading tags for what they mean, plus <article> where the page genuinely contains an article. The clearest, proven win is accessibility. Google's AI guidance also recommends semantic HTML where possible; a page built entirely from <div>s is harder for people and machines to parse.

✓ Foundations checklist
  • one URL per page (canonical set)
  • one <h1>
  • unique title + description per page
  • semantic landmarks
  • www/slash variants redirect, don't duplicate

Step 2 — Support multiple languages

Bottom line — is your website only in one language? Skip this step. Otherwise, give every language its own web address from day one — never one page that swaps languages in place.

Google recommends a distinct URL for every language version, such as /en/services and /zh/services. Connect them with hreflang. A language menu is fine; swapping text with JavaScript at the same URL is not, because crawlers may not discover every translation.

Your default language can stay at the root while others use prefixes, or every language can use a prefix. Both work. WeBreeze uses prefixes for every language because uniform URL, canonical, sitemap, and hreflang logic is easier to maintain.

🛠 For your developer

Distinct URL per language. hreflang tags must be self-referential and reciprocal (every version lists every version, including itself), use valid language(-region) codes, and add an x-default (recommended, not required) where you have a meaningful fallback for users whose language you don't target. Advertise only translations that actually exist.

<link rel="alternate" hreflang="en"        href="https://example.com/en/services">
<link rel="alternate" hreflang="zh"        href="https://example.com/zh/services">
<link rel="alternate" hreflang="x-default" href="https://example.com/en/services">
✓ Checklist
  • one URL per language (a menu that navigates is fine; never a same-URL swap)
  • self-referential + reciprocal hreflang
  • valid codes
  • x-default where you have a fallback
  • advertise only languages that actually exist

Step 3 — Help machines understand your pages (structured data)

Bottom line — add a small hidden block of code that tells search and AI what your site is, who runs it, and what each page represents — so they don't have to guess from the visible HTML.

Everything so far helps a machine read your page. Structured data helps it understand the entities on it: this is the website, this is the organization behind it, and this page is a product, article, event, local business, or something else.

You add that information as JSON-LD in the page's head. It's invisible to visitors. Google recommends JSON-LD and documents how structured data can enable rich results; for AI answer engines, the benefit is plausible but not proven. Use the most specific Schema.org type that honestly matches the page, and follow Google's rule that marked-up claims must be supported by visible content.

🛠 For your developer

Start with stable WebSite and Organization entities, give them durable @ids, and reference those same IDs from page-specific markup. Add BreadcrumbList where the page has a real hierarchy. Validate Google-eligible types with Google's Rich Results Test and general Schema.org with the Schema Markup Validator.

<script type="application/ld+json">
{
  "@context": "https://schema.org",
  "@graph": [
    {
      "@type": "WebSite",
      "@id": "https://example.com/#website",
      "url": "https://example.com/",
      "name": "Example Co"
    },
    {
      "@type": "Organization",
      "@id": "https://example.com/#organization",
      "name": "Example Co",
      "url": "https://example.com/"
    }
  ]
}
</script>
Common mistake: invalid JSON-LD that silently fails, or letting a </script> in your content break the block. Escape it, and validate.

Optional: connect your profiles with sameAs

sameAs lists your organization's official profiles so search engines can tell your brand from others with a similar name. Add only profiles you control, ideally ones that link back to your site. This is cheap but low priority: it won't create authority or a Knowledge Panel, and if you don't have established profiles, leave it out.

🛠 For your developer

Add sameAs to your existing Organization JSON-LD. Use real profile URLs, not homepages for the platforms themselves.

{
  "@context": "https://schema.org",
  "@type": "Organization",
  "@id": "https://example.com/#organization",
  "name": "Example Co",
  "url": "https://example.com",
  "sameAs": [
    "https://www.linkedin.com/company/example",
    "https://www.crunchbase.com/organization/example"
  ]
}
✓ Checklist
  • stable WebSite + Organization entities
  • the most specific honest type for each page
  • visible content supports every marked-up claim
  • valid JSON-LD (validate it)
  • (optional) official sameAs profiles

Step 4 — Help AI answer engines find your site

Bottom line — let answer-engine crawlers in, give them a sitemap, and notify Bing when pages change. Google has no equivalent instant-submit mechanism for ordinary pages.

This section mixes GEO (AI crawler access) with classic SEO (Bing, Google, and IndexNow) because the systems still overlap.

AI crawlers & robots.txt

robots.txt tells crawlers what they may fetch. Separate the bots by purpose:

  • Answer crawlers: OAI-SearchBot, PerplexityBot, Claude-SearchBot. Allow these if you want direct access for AI answers.
  • User-triggered fetchers: ChatGPT-User, Claude-User. These fetch a page at a person's request.
  • Training crawlers: GPTBot, ClaudeBot, CCBot. Allowing training is a separate policy decision; it does not determine whether you can be cited today.

The bot names and roles above come from the publishers' current documentation: OpenAI, Anthropic, and Perplexity. Recheck them periodically; crawler policies change.

WeBreeze allows answer crawlers on the public content its agents publish while keeping the training choice separate.

🛠 For your developer

Allow the answer user-agents you want and include your sitemap. Then check the CDN or firewall: it can block a bot even when robots.txt allows it.

User-agent: *
Allow: /

# Answer engines
User-agent: OAI-SearchBot
User-agent: PerplexityBot
User-agent: Claude-SearchBot
Allow: /

Sitemap: https://example.com/sitemap.xml
# llms: https://example.com/llms.txt
Common mistake: checking robots.txt but missing an upstream AI-bot block at the host, CDN, or firewall.

llms.txt

An llms.txt is a plain-text file at your root that lists your key pages for AI — think of it as a sitemap written for language models.

🛠 For your developer

A minimal llms.txt at your root:

# Example Co
> Software and services for X.

## Key pages
- [Product](https://example.com/product): what it does and who it is for
- [Documentation](https://example.com/docs): setup and reference guides

llms.txt is an emerging convention, not a proven ranking lever. Google says it ignores llms.txt for Search visibility and ranking. WeBreeze publishes one because it is cheap to maintain and other systems may use it; treat it as an experiment.

Google vs Bing submission (IndexNow)

Bing remains a cheap hedge for wider AI discovery because Microsoft says Copilot Search is grounded on Bing search results. Its publishing workflow differs from Google's:

WeBreeze publishes the sitemap and sends IndexNow notifications when its agents create or update eligible content. Clients connect Search Console to inspect Google's data.

🛠 For your developer

IndexNow requires a key file at the site root and a POST to api.indexnow.org when an eligible URL changes.

Common mistake: assuming IndexNow covers Google. It doesn't — Google isn't a participant.
✓ Checklist
  • allow the answer crawlers you want (and check no CDN firewall blocks them)
  • ship llms.txt (experimental — a cheap bet)
  • fire IndexNow when eligible URLs change
  • verify + submit your sitemap for Google

Step 5 — Make your website fast (speed & caching)

Bottom line — put your pages behind an edge cache so a visitor anywhere gets a ready-made copy fast — but only cache what's public and identical for everyone; keep anything private or personalized dynamic.

Slow pages hurt visitors, conversion, Core Web Vitals, and crawler reliability. Speed is not a simple ranking dial, but it is table stakes.

Edge caching

An edge cache keeps ready-made copies of public pages near visitors instead of rebuilding them at the origin. It removes server delay, though images, scripts, and page weight still matter.

WeBreeze edge-caches the public content its agents publish and purges it after every update. We verify the behavior rather than trusting the configuration:

What to testWhat you want to see
A public page, fetched twicefirst MISS, then HIT
A 404 or error pageBYPASS or a very short TTL
A personalized pagealways DYNAMIC
The same page, bot vs humanbyte-identical HTML — no cloaking
Publish an edit, then refetchthe new version appears immediately
🛠 For your developer

Set a high edge TTL with s-maxage or a CDN rule, keep the browser copy revalidating, and purge by path or tag when content changes. Exclude authenticated traffic from the cache key. Use the official Core Web Vitals thresholds: target LCP ≤ 2.5s, INP ≤ 200ms, CLS ≤ 0.1 at the 75th percentile.

You do not need a static-site generator to get this benefit. A dynamic site behind a correctly configured edge cache serves the same ready-made response on a cache hit.

What you must never cache

Only cache responses that are public and identical for everyone. A response that varies by login, session, or token must remain dynamic.

✅ Safe to cache

Public pages that are identical for everyone, plus indexes and sitemaps

⛔ Keep dynamic
  • Anything that varies by session, login, or token
  • error pages and redirects
  • API responses
  • the framework's internal "router" payloads (not real pages)
  • already-fingerprinted static assets (they use their own long cache)

A 200 status alone is not enough: personalized pages and soft 404s can also return 200. WeBreeze also lets answer crawlers bypass the cache so its crawler analytics remain accurate; bots and people still receive identical HTML.

Common mistake: a blanket "cache everything" rule that swallows your 404s, your logged-in pages, or a checkout flow.

Images on a CDN

Serve large uploaded or generated images through a CDN and resize them to the dimensions visitors need. Leave already-fast, fingerprinted brand assets alone; moving them adds complexity without solving a bottleneck.

✓ Checklist
  • edge-cache public HTML that is identical for everyone
  • never cache user-specific responses
  • keep errors and redirects on a short TTL
  • put heavy images on a CDN
  • leave already-fast static assets where they are

Step 6 — Sitemaps, error pages & Search Console

Bottom line — give crawlers a current list of your pages, return a real "not found" for missing ones, and sign up for Google's and Bing's free dashboards so you can actually see how you're doing.

XML sitemaps

A sitemap is a machine-readable list of the pages you want found, so crawlers don't have to discover them by luck. Every public website should have one, kept current automatically. Google's sitemap guide supports localized alternates for multilingual sites.

🛠 For your developer

Generate sitemap.xml from your actual indexable pages with a meaningful <lastmod> (reflect a real content change, not every render). For multilingual sites, declare the XHTML namespace on the root and give every language its own <url> entry that repeats the full alternate set. Reference the sitemap in robots.txt.

<url>
  <loc>https://example.com/en/services</loc>
  <lastmod>2026-07-01</lastmod>
  <xhtml:link rel="alternate" hreflang="en" href="https://example.com/en/services"/>
  <xhtml:link rel="alternate" hreflang="zh" href="https://example.com/zh/services"/>
  <xhtml:link rel="alternate" hreflang="x-default" href="https://example.com/en/services"/>
</url>
Common mistake: a hand-maintained sitemap that drifts out of sync with reality. Generate it from your actual content.

404s done right

A missing page should return 404 (or 410 when deliberately removed). A "not found" screen that returns 200 is a soft 404 and can linger as a phantom page; 403 incorrectly says the page exists but is forbidden. Test the actual status code.

Search Console & Bing Webmaster

These free dashboards show queries, indexing, and crawl problems:

WeBreeze automates the technical setup and reporting inputs; clients connect their own properties when they want direct access to the raw search data.

✓ Checklist
  • verify Google Search Console + submit sitemap
  • verify Bing Webmaster
  • connect analytics
  • set up an AI-visibility check

Step 7 — Measure your AI search visibility

Bottom line — measure three things: what the AI chats say when asked, how those answers change over time, and whether people actually click through to your site.

1. Check the AI chats manually

Start with the phrases a potential customer would actually type into ChatGPT, Perplexity, or Gemini. Use neutral discovery questions such as "What are the best tools for X?" or "How should a company solve Y?" Don't mention your brand, paste your URL, or ask why the engine failed to include you; those prompts lead the answer.

Consumer results can vary between runs. ChatGPT Search, for example, can use memory and location when forming a response. Other products have their own personalization controls. For a cleaner comparison:

  • Use a fresh or temporary conversation for every run; turn off memory or personalization where the product allows it.
  • Use the exact same prompt in each engine and record the date, answer, citations, competitors, and where and how your brand appears.
  • As a practical rule of thumb, run each prompt at least three times per engine. Use five separate conversations for a stronger baseline.
  • Repeat on a schedule — monthly for a small site, weekly for competitive or fast-changing topics.

A single favorable answer is not visibility; it is one sample. Look for repeated mentions and citations across engines and runs.

2. Check Google's free attribution and visibility reports

Citations are useful, but a click is stronger evidence. GA4's default AI Assistants channel groups visits from sources such as ChatGPT, Gemini, DeepSeek, Copilot, and Grok. Open Acquisition → Traffic acquisition, select the AI Assistants channel, then add dimensions such as session source and landing page to see which assistant sent people to which content.

Treat that number as a floor. Some AI clicks arrive without a referrer and appear as Direct; Google's own AI Overviews and AI Mode appear under Organic Search. Google is gradually rolling out a separate Generative AI performance report in Search Console that shows impressions from AI Overviews and AI Mode. GA4 measures visits, while Search Console, manual checks, and monitors provide different views of visibility.

3. Subscribe to an automated visibility monitor

Manual checks become tedious once you track more than a few prompts. Paid AI-visibility services automate the runs, preserve the answers, and chart mentions, citations, and changes over time. As of July 2026, the self-serve plans checked for this guide span roughly $29–$489 per month, depending on prompt volume and engine coverage (Otterly pricing; Semrush pricing). Enterprise plans can cost more.

Before subscribing, ask whether the monitor queries model APIs or the consumer chat products. API results are useful for consistent trend tracking, but they may not match a personalized chat exactly. Compare direction over time instead of treating any one score as absolute truth.

WeBreeze includes citation monitoring for every client. It runs weekly checks across Perplexity, OpenAI, and Gemini, surfaces the results in the client's Reports area, and feeds citation gaps back into the content agents so they can decide what to research, update, or create next. The same monitor is also available as a standalone public product for teams that want visibility tracking without the full WeBreeze platform.

✓ Checklist
  • start with neutral manual checks
  • inspect Google's free GA4 and Search Console data
  • add paid monitoring when you need repeatable tracking
  • measure trends, not one-off answers

Step 8 — Extra setup for blogs

Bottom line — everything above applies to blogs, but blogs add four recurring decisions: where the blog lives, how article pages are marked up, who gets credited as the author, and whether FAQ markup is worth adding.

This section comes from building the blog publishing layer used by WeBreeze's content agents. Treat it as an add-on to the website-wide checklist, not a separate SEO system.

Where the blog lives: subfolder or subdomain?

Your two common choices are yourdomain.com/blog (a subfolder) and blog.yourdomain.com (a subdomain). Both architectures are indexable. Google says its site-diversity system generally treats a subdomain as part of the root domain, but it does not promise a ranking advantage for either structure. Many experienced practitioners still prefer a subfolder for a new blog because it sits directly under the established root domain, but the evidence isn't clean enough to call that a guaranteed advantage.

My practical rule: starting fresh with a free choice? Use a subfolder. Already running a healthy blog on a subdomain? Leave it there. A migration means mapping every URL to a one-for-one 301, and the small possible upside rarely justifies moving a blog that already ranks.

For WeBreeze's own blog you're reading now, I deliberately chose a subdomain (blog.webreeze.ai) rather than a subfolder — because I want to dogfood our own product, running this blog on the exact platform we ship to clients.

🛠 For your developer

An externally managed publishing system can appear under /blog through a reverse proxy, but its canonicals, hreflang, sitemap URLs, JSON-LD IDs, assets, and internal links must all be base-path aware. If the platform cannot do that natively, the proxy must rewrite them.

Use BlogPosting for article pages

Article pages can extend the website-wide structured data from Step 3 with BlogPosting. Include the headline, real publication and modification dates, language, primary image, author, publisher, and canonical page URL. Reference the same organization ID used elsewhere on the site.

🛠 For your developer

Emit one block per article and validate it. The values must match what a visitor can see on the page.

<script type="application/ld+json">
{
  "@context": "https://schema.org",
  "@type": "BlogPosting",
  "headline": "How Virtual Doctor Visits Work",
  "datePublished": "2026-07-01",
  "dateModified": "2026-07-01",
  "inLanguage": "en",
  "image": "https://example.com/hero.jpg",
  "author": {
    "@type": "Person",
    "name": "Dr. Jane Smith",
    "url": "https://example.com/authors/jane-smith"
  },
  "publisher": {
    "@id": "https://example.com/#organization"
  },
  "mainEntityOfPage": "https://example.com/en/post"
}
</script>

Credit a real author where trust matters

For health, finance, legal, and other accuracy-sensitive topics, use an accurate byline and a real author page with relevant credentials; add a "reviewed by" line where it genuinely applies. Google's people-first content guidance explains that E-E-A-T is not a single ranking factor, but clear sourcing and demonstrable expertise still help readers assess trust.

FAQ schema is optional

If an article genuinely answers distinct questions, FAQPage markup can make that structure explicit. Google retired FAQ rich results from Search in May 2026, so it no longer earns expandable Q&As. Its remaining appeal is AI extractability, which is plausible but not a measured win. Add it only where the Q&A already exists on the visible page; never manufacture questions just for schema.

🛠 Developer aside — skip unless you're technical

A dead end I hit: separate Markdown copies

We experimented with serving a clean .md version beside each HTML article for machines that prefer plain text. Marking that copy noindex seemed like a neat way to prevent duplication, but OpenAI and Anthropic also document noindex as a way to keep content out of AI search. That can hide the Markdown from the engines it was meant to help.

The least ambiguous option is to skip the duplicate Markdown page. If you keep one, don't casually add noindex; handle duplication with an HTTP canonical header and test how the crawlers you care about respond.

✓ Blog checklist
  • choose subfolder vs subdomain before launch, but don't migrate a healthy blog casually
  • one canonical URL and one <h1> per article
  • valid BlogPosting markup
  • real authors for sensitive topics
  • FAQ schema only for genuine visible Q&A
  • update the sitemap, purge the cache, and notify IndexNow when an article changes

What comes next: Part II, the Content Guide

Most of the technical SEO and GEO work above is infrastructure: configure it once and every page can inherit it. We built these checks into WeBreeze so its agents can research, create, optimize, publish, and measure content as one continuous system.

Part II is the harder half: content. None of this makes a thin product page, generic service page, or weak article rank or get cited. The technical setup makes you eligible; the content and experience are what actually win — original evidence, claims worth quoting, satisfying the real intent behind a search, clear internal links, current information, and expertise people can trust.

And there's one more layer beyond both: authority you earn off your own site — other reputable sites linking to and mentioning you. You don't "set that up" in an afternoon; you build it over time. It's the slowest lever, and often the highest.

So, what do you actually do?

Turning all of the above into a to-do list, split by who owns it:

If you don't code — ask your developer or host for:

  • One web address per page, with www and the bare domain both working and one redirecting to the other
  • A real "not found" (404) page for dead links
  • The AI answer-engine crawlers allowed in, and a sitemap published
  • Public pages put behind an edge cache (CDN) so they load fast
  • Google Search Console + Bing Webmaster verified so you can see how you're doing

Then do the free, no-code part yourself: open GA4's AI Assistants channel, check Search Console's AI report if your property has it, and spot-check ChatGPT / Perplexity / Gemini to see if they mention you.

If you're the developer — the ticket list:

  • Canonical host + 301s; self-referential canonical tags; language on its own URL with reciprocal hreflang + x-default
  • Exactly one <h1>; unique <title> + description per page; semantic landmarks
  • WebSite + Organization JSON-LD, plus the honest page-specific type; blogs add BlogPosting
  • robots.txt allowing the answer crawlers (check the CDN firewall too); llms.txt (experimental); IndexNow on changes; verified GSC sitemap
  • Edge-cache public, identical HTML only (s-maxage + revalidating browser copy + purge-on-change); real 404/410; generated sitemap with per-language alternates

We open-sourced this checklist as a tool. Every check above is packaged as an open-source agent skill — point it at a site and it runs all 44 checks and hands back one table: what passed, what failed, the evidence, and the fix. It fetches your pages as OAI-SearchBot, PerplexityBot and Claude-SearchBot, so you see what the answer engines actually receive. MIT licensed, free, no signup.

If you'd rather turn this technical SEO and GEO audit into an ongoing content system, WeBreeze is your AI agent team that automates the research, creation, optimization, publishing, and measurement work traditionally split across an SEO and GEO agency.

See where your website stands right now. Run a free scan — drop in your URL and we'll send you a report on exactly these signals. Or book a consultation and we'll walk your site together.

WeBreeze · Technical SEO & GEO: A Complete Step-by-Step Guide to a Fast, AI-Discoverable Website · Part I · References checked July 2026