/ Agent Compat Fixes / Agent Navigation

How to Fix Navigation Agents Can't Follow

Agents discover your site structure through navigation. If your nav uses JS-only click handlers, mega-menus that only open on hover, or lazy-loaded submenus, agents see top-level items and dead ends. They can't traverse to your category pages, product pages, or knowledge-base articles. The fix is progressive enhancement: real anchor links that work without JS, enhanced by JS for interactivity.

1. The pattern

Bad: button with click handler

<button onClick={() => router.push('/products')}>
  Products
</button>
<!-- Agents see: a button with no destination. Dead end. -->

Good: anchor with real href

<a href="/audit-tools.html" onClick={interceptForSPA}>
  Products
</a>
<!-- Agents see: link to /products. Follow it. -->
<!-- Humans get JS-intercepted SPA navigation. -->

2. Framework patterns

Next.js

import Link from 'next/link';

<Link href="/audit-tools.html">Products</Link>
// Renders <a href="/audit-tools.html">Products</a> — agent-friendly
// JS intercepts clicks for client-side routing

Nuxt

<NuxtLink to="/products">Products</NuxtLink>
<!-- Renders <a href="/audit-tools.html"> -->

Astro

<a href="/audit-tools.html">Products</a>
<!-- Plain HTML by default; no JS needed -->

React Router (CSR-only)

// react-router-dom v6+
import { Link } from 'react-router-dom';
<Link to="/products">Products</Link>
// Renders <a href="/audit-tools.html">

// BUT: if the rest of the page is CSR, agent still sees empty shell.
// See how-to-fix-js-only-content for the underlying issue.

3. Mega-menus and dropdowns

Bad: hover-only, children injected via JS

<nav>
  <li onMouseEnter={loadSubmenu}>
    Products
    {/* Submenu loads here on hover, JS only */}
  </li>
</nav>

Good: server-rendered submenu, JS controls visibility

<nav>
  <li>
    <a href="/audit-tools.html">Products</a>
    <ul class="submenu">
      <li><a href="/audit-tools.html">Shoes</a></li>
      <li><a href="/audit-tools.html">Bags</a></li>
      <li><a href="/audit-tools.html">Accessories</a></li>
    </ul>
  </li>
</nav>

<style>
  /* Hidden until parent hovered/focused */
  .submenu { display: none; }
  li:hover .submenu, li:focus-within .submenu { display: block; }
</style>
<!-- All links in initial HTML. Agents see and follow them. -->

4. Mobile menus / hamburgers

<!-- Render the full menu in HTML, CSS-hidden until JS toggle -->
<button aria-controls="mobile-nav" aria-expanded="false">Menu</button>
<nav id="mobile-nav" hidden>
  <a href="/audit-tools.html">Products</a>
  <a href="/seo-audit-platform.html">About</a>
  <a href="/support.html">Contact</a>
</nav>

<!-- Agents read the nav regardless of hidden attribute -->
<!-- Humans toggle visibility via JS -->

5. Sitemap as backup nav

Even with perfect nav, link to an HTML sitemap. Single page listing all important URLs, hierarchically organised. Agents (and users with weird browsers) get a fallback discovery path:

<a href="/sitemap.xml">Site Map</a> <!-- in footer -->

<!-- /sitemap.html -->
<main>
  <h1>Site Map</h1>
  <section>
    <h2>Products</h2>
    <ul>
      <li><a href="/audit-tools.html">Shoes</a></li>
      <li><a href="/audit-tools.html">Bags</a></li>
    </ul>
  </section>
  <!-- ... -->
</main>

6. Test by disabling JS

Step 1
Browser DevTools
Chrome DevTools → Cmd/Ctrl+Shift+P → "Disable JavaScript" → reload. Can you navigate to every important page from the homepage using only links?
Step 2
curl crawl test
# Get all links from homepage
curl -s https://example.com/ | grep -oE 'href="[^"]+"' | sort -u | head -50

# Should include your main category and product pages
# If you only see static pages (about, contact, blog), nav is JS-only
💡 Hamburger menus on mobile and mega-menus on desktop are agent-friendly IF the links live in the HTML and CSS controls visibility. The mistake is loading them with JS on interaction — agents never interact, so they never see the menu.

🤖 Re-run Agent Compat audit

Verify agents can traverse every important page.

Run Agent Compat →
Related Guides: Agent Compat Fixes  ·  Fix JS-Only Content  ·  Fix Keyboard Nav
💬 Got a problem?