AgentStack
Browse Sign in
Browse Why AgentStack Sell Docs
Sign in
SKILL verified MIT Self-run

Seo Crawlability

skill-mvstepanek-nextjs-ecommerce-seo-skills-seo-crawlability · by mvstepanek

Crawlability, indexing, robots directives, and sitemap rules. Use when working with robots.txt, XML sitemaps, noindex/nofollow directives, pagination crawling, or server-side rendering for SEO.

No reviews yet
0 installs
27 views
0.0% view→install

Install

$ agentstack add skill-mvstepanek-nextjs-ecommerce-seo-skills-seo-crawlability

✓ scanned · ✓ verified, works with Claude Code, Cursor, and more.

Security review

✓ Passed

No issues found. Passed automated security review. · v0.1.0 How review works →

  • Prompt-injection patterns
  • Secret / credential exfiltration
  • Dangerous shell & filesystem operations
  • Untrusted network calls
  • Known-malicious package signatures

What it can access

  • Network access No
  • Filesystem access No
  • Shell / process execution No
  • Environment & secrets No
  • Dynamic code execution No

From automated source analysis of v0.1.0. “Used” means the capability is present in the source — more access means more to trust, not that it’s unsafe.

View the full security report →

Verified badge

Passed review? Show it. Paste this badge into your README, it links to the public security report.

AgentStack Verified badge Links to your public security report.
[![AgentStack Verified](https://agentstack.voostack.com/badges/verified.svg)](https://agentstack.voostack.com/security/report/skill-mvstepanek-nextjs-ecommerce-seo-skills-seo-crawlability)

Reliability & compatibility

Security review passed
0 installs to date
no reviews yet
5mo ago

Declared compatibility

Claude CodeClaude Desktop

Compatibility is declared by the source manifest. End-to-end runtime verification is coming, see below.

Preview Execution monitoring

We're building live execution health for every listing: tool-call success rate, median latency, uptime, and last-checked timestamps, measured, not self-reported. It isn't live yet, so we don't show numbers we can't stand behind.

How agent discovery & health will work →
Are you the author of Seo Crawlability? Claim this listing to set pricing, connect Stripe payouts, and keep 70% of every sale.
Sign up to claim

About

Crawlability & Indexing SEO Guidelines

Follow these rules to ensure search engines can discover, crawl, and index all important pages on the site.

For current robots.txt and sitemap structure details, see [reference.md](reference.md).

robots.txt

Example e-commerce robots.txt (adapt paths to your project):

User-agent: *
Disallow: /*/search/
Disallow: /*/search

Sitemap: ${SITE_URL}/sitemap.xml

robots.txt vs noindex

  • robots.txt blocks crawling, not indexing — Google may still index a blocked URL (with no snippet) if external sites link to it
  • Use robots.txt only for pages that generate massive URL combinations — search results are the primary example, as they create near-infinite crawlable URLs that waste crawl budget
  • Use noindex for finite pages that shouldn't be indexed — cart, checkout, account, wishlist, login, register. These have minimal crawl budget impact, and noindex properly prevents indexing

Rules for Modifying robots.txt

  • Always reference the sitemapSitemap: directive pointing to your sitemap URL
  • Keep robots.txt minimal — only block pages that genuinely waste crawl budget (e.g. search results with infinite URL combinations)
  • Prefer noindex over robots.txt for pages you want to prevent from appearing in search results — noindex is the correct tool for preventing indexing
  • Never block CSS/JS files — search engines need these to render pages
  • Never block product or category pages — these are the pages you want ranked
  • Test changes — use Google Search Console's robots.txt tester before deploying

In Next.js, you can generate robots.txt dynamically (App Router example; for Pages Router, use public/robots.txt or an API route):

// robots.ts (App Router) — for Pages Router, use public/robots.txt or an API route
import { MetadataRoute } from 'next';
// Example import — use your project's actual config
import { siteConfig } from '@/config/site';

export default function robots(): MetadataRoute.Robots {
  return {
    rules: {
      userAgent: '*',
      disallow: ['/*/search/', '/*/search'],
    },
    sitemap: `${siteConfig.url}/sitemap_index.xml`,
  };
}

Noindex Directives

Use noindex on pages that should be crawlable but NOT appear in search results:

| Page Type | Directive | Reason | |-----------|-----------|--------| | Search results | noindex, follow | Infinite URL combinations, thin content | | Granular filter combinations | noindex, follow | Thin/duplicate content — but keep useful single-filter pages (e.g. ?type=wireless) indexable if they match real search intent | | User account pages | noindex, nofollow | Private, no SEO value | | Cart / Checkout | noindex, nofollow | Private, no SEO value | | Thank you / confirmation | noindex, nofollow | No SEO value | | Internal error pages | noindex, nofollow | No SEO value | | Login / Register | noindex, follow | No SEO value, but follow links | | Print views | noindex, nofollow | Duplicate of main page |

Implementation:

// In page metadata
export const metadata: Metadata = {
  robots: {
    index: false,
    follow: true, // or false depending on page type
  },
};

// In generateMetadata for dynamic pages
export async function generateMetadata(): Promise {
  return {
    robots: { index: false, follow: true },
  };
}

Important: Use noindex in the metadata, not in robots.txt. robots.txt blocks crawling entirely (search engines can't even see the noindex tag), while noindex allows crawling but prevents indexing.

XML Sitemaps

Sitemap Rules

  • Only include canonical, indexable URLs — no noindex pages, no non-canonical URLs, no paginated URLs (except if self-canonical)
  • Include all locale variants — every page in every locale it's available in
  • Use lastmod — accurate last modified date helps search engines prioritize crawling
  • Include hreflang in sitemaps — use `` (see seo-hreflang skill)
  • Max 50,000 URLs per sitemap — split into sub-sitemaps if needed
  • Max 50MB per sitemap file — monitor file sizes
  • Keep sitemaps fresh — regenerate on content changes, not just at build time

Next.js sitemap generation (App Router example; for Pages Router, use an API route or build-time generation):

// sitemap.ts (App Router) — for Pages Router, generate via API route or at build time
import { MetadataRoute } from 'next';
// Example imports — use your project's actual config
import { siteConfig, ALL_LOCALES } from '@/config/site';

export default async function sitemap(): Promise {
  const products = await getAllProducts();

  return products.flatMap(product =>
    ALL_LOCALES.map(locale => ({
      url: `${siteConfig.url}/${locale}/products/${product.id}/${product.slug}`,
      lastModified: product.updatedAt,
      alternates: {
        languages: Object.fromEntries(
          ALL_LOCALES.map(loc => [loc, `${siteConfig.url}/${loc}/products/${product.id}/${product.slug}`])
        ),
      },
    }))
  );
}

Note: Google ignores changeFrequency and priority fields in sitemaps — omit them. The lastmod field is the only optional field Google uses, and only when it's consistently accurate and reflects significant content changes.

Server-Side Rendering for SEO

  • Critical content must be server-rendered — product names, descriptions, prices, specs
  • Google can render JavaScript, but it introduces a delay (typically hours to days for initial indexing)
  • Server-rendered content (Server Components in App Router, or getServerSideProps/getStaticProps in Pages Router) appears in the initial HTML — use this to your advantage
  • Never hide critical content behind client-side fetch — if a product name only appears after a useEffect fetch, it may not be indexed promptly
// GOOD — content is in the initial HTML
export default async function ProductPage({ params }: Props) {
  const product = await getProduct(params.id); // Server-side
  return {product.name}; // In initial HTML
}

// BAD — content requires client-side JS to appear
"use client";
export default function ProductPage({ params }: Props) {
  const [product, setProduct] = useState(null);
  useEffect(() => { fetchProduct(params.id).then(setProduct); }, []);
  return {product?.name}; // Not in initial HTML!
}

Orphan Pages

Every indexable page must be:

  1. Reachable from internal links — at least one link from another page on the site
  2. In the sitemap — listed in one of the XML sitemaps
  3. Not blocked by robots.txt — must be crawlable

If you create a new page, verify it has at least one internal link pointing to it (from navigation, category listing, related products, or footer).

Crawl Budget

For a large multi-locale site (many locales x many products), crawl budget matters:

  • Don't waste it on non-valuable pages — noindex search, granular filter combos, account pages
  • Use hreflang correctly — helps Google crawl locale variants efficiently
  • Fresh sitemaps — helps Google prioritize changed pages
  • Fast server response — slow responses waste crawl budget (aim for <500ms TTFB)

Common Mistakes to Avoid

  1. Using robots.txt to "hide" pages — use noindex instead; robots.txt prevents crawling, so Google can't see the noindex
  2. Sitemap with non-canonical URLs — only canonical URLs belong in sitemaps
  3. Missing sitemap reference in robots.txt — always include Sitemap: directive
  4. Client-side rendered critical content — search engines may miss content that requires JS execution
  5. Orphan product pages — new products must be linked from category pages
  6. Stale sitemaps — regenerate when content changes, not just at deploy time

Source & license

This open-source skill is cataloged on AgentStack and links to its original source — we do not rehost the code.

Install and usage instructions live in the source repository linked above.

Reviews

No reviews yet, be the first.

Versions

  • v0.1.0 Imported from the upstream source.