indxel

When the user wants to set up, configure, or fix SEO in a Next.js project using the indxel SDK and CLI. Also use when the user mentions "SEO setup," "meta tags," "structured data," "JSON-LD," "seo config," "seo check," "broken SEO," "metadata validation," "OG image," "canonical URL," or "defineSEO." For live site crawling, keyword research, or indexation, see indxel-pro.

Safety Notice

This listing is imported from skills.sh public index metadata. Review upstream SKILL.md and repository scripts before running.

Copy this and send it to your AI assistant to learn

Install skill "indxel" with this command: npx skills add indxel/indxel-skill/indxel-indxel-skill-indxel

Indxel — SEO infrastructure for developers

You are an expert in using the indxel npm package and CLI to set up bulletproof SEO in Next.js projects. Indxel is "ESLint for SEO" — it validates metadata at build time so broken SEO never ships to production.

Knowledge Base: Before making SEO recommendations, consult references/seo-knowledge-base.md for the complete set of SEO best practices, critical rules, structured data patterns (@graph, sameAs), GEO optimization (AI-readiness, semantic HTML, llms.txt), rendering strategies, and Core Web Vitals thresholds. This ensures your advice goes beyond tool usage and reflects what actually matters for ranking in 2026.

Before Starting

Check if indxel is already set up:

  1. Look for seo.config.ts (or seo.config.js) at the project root
  2. Check if indxel is in package.json dependencies
  3. Check if pages already use createMetadata() or generateMetadata()

If not set up, start with initialization. If already set up, skip to the relevant section.


1. Installation & Init

Install the package

npm install indxel

Initialize the project

npx indxel init

This generates:

  • seo.config.ts — Global SEO configuration
  • app/sitemap.ts — Dynamic sitemap
  • app/robots.ts — robots.txt configuration
  • public/<key>.txt — IndexNow verification key

With git hook guard:

npx indxel init --hook

2. defineSEO() — Global Configuration

Create seo.config.ts at the project root:

import { defineSEO } from 'indxel'

export default defineSEO({
  siteName: 'MonSaaS',
  siteUrl: 'https://monsaas.fr',
  titleTemplate: '%s | MonSaaS',
  defaultOGImage: '/og-default.png',
  locale: 'fr_FR',
  twitter: {
    handle: '@monsaas',
    cardType: 'summary_large_image',
  },
  organization: {
    name: 'MonSaaS',
    logo: 'https://monsaas.fr/logo.png',
    url: 'https://monsaas.fr',
  },
  verification: {
    google: 'google-site-verification-code',
  },
})

SEOConfig fields

FieldTypeRequiredDescription
siteNamestringYesDisplay name (titles, structured data)
siteUrlstringYesCanonical base URL (no trailing slash)
defaultTitlestringNoFallback page title
titleTemplatestringNoTemplate with %s placeholder
defaultOGImagestringNoDefault OG image URL
localestringNoLocale (e.g. fr_FR, en_US)
twitterobjectNo{ handle, cardType }
organizationobjectNo{ name, logo, url }
verificationobjectNo{ google?, yandex?, bing? }

3. createMetadata() — Per-Page Metadata

In each page.tsx or layout.tsx, export metadata using createMetadata():

import { createMetadata } from 'indxel'
import seoConfig from '@/seo.config'

export function generateMetadata() {
  return createMetadata({
    title: 'Pricing',
    description: 'Simple, transparent pricing. Start free.',
    path: '/pricing',
  }, seoConfig)
}

PageSEO fields

FieldTypeRequiredDescription
titlestringYesPage title
descriptionstringYesMeta description
pathstringYesURL path (e.g. /blog/my-post)
ogImagestringNoOverride default OG image
noindexbooleanNoAdd noindex directive
canonicalstringNoOverride canonical URL
alternatesRecord<string, string>Nohreflang alternates
articleobjectNoArticle metadata (publishedTime, author, tags)
structuredDataarrayNoJSON-LD entries for this page

Article pages

export function generateMetadata() {
  return createMetadata({
    title: 'How to Fix Broken Meta Tags',
    description: 'A guide to catching SEO regressions before they ship.',
    path: '/blog/fix-broken-meta-tags',
    ogImage: '/blog/fix-broken-meta-tags/og.png',
    article: {
      publishedTime: '2026-01-15',
      author: 'Jane Doe',
      section: 'Engineering',
      tags: ['SEO', 'Next.js', 'CI/CD'],
    },
  }, seoConfig)
}

Multilingual pages

export function generateMetadata() {
  return createMetadata({
    title: 'Accueil',
    description: 'Infrastructure SEO pour developpeurs.',
    path: '/fr',
    alternates: {
      en: '/en',
      fr: '/fr',
      de: '/de',
    },
  }, seoConfig)
}

4. generateLD() — Structured Data (JSON-LD)

Generate type-safe JSON-LD for rich results:

import { generateLD } from 'indxel'

// In your component or page:
const faqLD = generateLD('FAQ', {
  questions: [
    { question: 'What is indxel?', answer: 'ESLint for SEO.' },
    { question: 'Is it free?', answer: 'The CLI and SDK are open-source.' },
  ],
})

// Render:
<script
  type="application/ld+json"
  dangerouslySetInnerHTML={{ __html: JSON.stringify(faqLD) }}
/>

Supported types

TypeKey fieldsUse case
Articleheadline, datePublished, authorBlog posts
Productname, price, currency, brandProduct pages
FAQquestions: [{ question, answer }]FAQ sections
HowToname, steps: [{ name, text }]Tutorials
Breadcrumbitems: [{ name, url }]Navigation breadcrumbs
Organizationname, url, logoAbout pages
WebPagename, description, urlGeneric pages
SoftwareApplicationname, category, priceApp/tool pages
WebSitename, url, searchUrlSite-level schema

Examples

Product:

generateLD('Product', {
  name: 'Indxel Pro',
  description: 'SEO monitoring dashboard.',
  price: '19',
  currency: 'EUR',
  brand: 'Indxel',
  url: 'https://indxel.com/pricing',
})

Breadcrumb:

generateLD('Breadcrumb', {
  items: [
    { name: 'Home', url: 'https://indxel.com' },
    { name: 'Blog', url: 'https://indxel.com/blog' },
    { name: 'Post Title', url: 'https://indxel.com/blog/post' },
  ],
})

HowTo:

generateLD('HowTo', {
  name: 'Set up indxel in 3 steps',
  steps: [
    { name: 'Install', text: 'Run npm install indxel' },
    { name: 'Init', text: 'Run npx indxel init' },
    { name: 'Check', text: 'Run npx indxel check' },
  ],
})

5. validateMetadata() — Programmatic Validation

Validate metadata in code (used internally by the CLI):

import { createMetadata, validateMetadata } from 'indxel'
import seoConfig from '@/seo.config'

const metadata = createMetadata({
  title: 'Home',
  description: 'Welcome.',
  path: '/',
}, seoConfig)

const result = validateMetadata(metadata)

console.log(result.score)   // 85
console.log(result.grade)   // "B"
console.log(result.errors)  // [{ id: 'og-image', message: '...' }]

Options

validateMetadata(metadata, {
  strict: true,           // Treat warnings as errors
  disabledRules: ['alternates'], // Skip specific rules
})

6. CLI — npx indxel check

Basic check

npx indxel check

Scans all page.tsx files, extracts static metadata, validates against 17 rules, outputs a score per page.

CI/CD mode

npx indxel check --ci

Strict mode. Exit code 1 on any error. Use in GitHub Actions or Vercel build.

Diff mode

npx indxel check --diff

Compare with previous run. Shows score changes per page.

Minimum score

npx indxel check --min-score 80

Fail only if average score drops below threshold.

Fix suggestions

npx indxel check --fix

Show code snippets to fix detected errors.

JSON output

npx indxel check --json

Machine-readable output for integrations.


7. Validation Rules (17 rules, 100 points)

RulePointsSeverityWhat it checks
title-present5criticalPage has a title
title-length10optionalTitle is 30-60 characters
description-present5criticalPage has meta description
description-length10optionalDescription is 120-160 chars
og-image10optionalOpen Graph image is set
og-title5optionalOG title is set
og-description5optionalOG description is set
canonical10criticalCanonical URL is set
structured-data-present8optionalHas JSON-LD
structured-data-valid2optionalJSON-LD is valid
structured-data-complete5optionalJSON-LD has required fields
robots5optionalRobots directives present
twitter-card5optionalTwitter card is configured
alternates5optionalhreflang alternates set
viewport3optionalViewport meta present
favicon2optionalFavicon exists
image-alt5optionalImages have alt text

Scoring:

  • Pass = full points
  • Warning = half points
  • Error = 0 points
  • Grade: A (90+), B (80+), C (70+), D (60+), F (<60)

8. CI/CD Integration

GitHub Actions

# .github/workflows/seo.yml
name: SEO Check
on: [push, pull_request]
jobs:
  seo:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - uses: actions/setup-node@v4
        with:
          node-version: 20
      - run: npm ci
      - run: npx indxel check --ci

Vercel Build

In package.json:

{
  "scripts": {
    "build": "npx indxel check --ci && next build"
  }
}

Git pre-push hook

npx indxel init --hook

Blocks git push if critical SEO errors are found.


9. Configuration File

Create .indxelrc.json at the project root for persistent CLI settings:

{
  "minScore": 80,
  "disabledRules": ["alternates"],
  "ignoreRoutes": ["/dashboard/*", "/api/*"],
  "baseUrl": "https://monsaas.fr"
}

Verification

After making changes, always verify:

  1. Run the check: npx indxel check
  2. Confirm score is acceptable: Look for grade A or B (80+)
  3. No critical errors: Title, description, and canonical must pass
  4. Structured data present: Pages should have relevant JSON-LD

If errors remain, read the error messages — they tell you exactly what's missing and what to add.


Common Patterns

Layout metadata (shared across routes)

// app/blog/layout.tsx
import { createMetadata } from 'indxel'
import seoConfig from '@/seo.config'

export function generateMetadata() {
  return createMetadata({
    title: 'Blog',
    description: 'Engineering insights and product updates.',
    path: '/blog',
  }, seoConfig)
}

Dynamic pages (from CMS/database)

// app/blog/[slug]/page.tsx
import { createMetadata, generateLD } from 'indxel'
import seoConfig from '@/seo.config'

export async function generateMetadata({ params }) {
  const post = await getPost(params.slug)
  return createMetadata({
    title: post.title,
    description: post.excerpt,
    path: `/blog/${post.slug}`,
    ogImage: post.coverImage,
    article: {
      publishedTime: post.publishedAt,
      author: post.author.name,
      tags: post.tags,
    },
  }, seoConfig)
}

noindex for authenticated pages

export function generateMetadata() {
  return createMetadata({
    title: 'Dashboard',
    description: 'Your SEO dashboard.',
    path: '/dashboard',
    noindex: true,
  }, seoConfig)
}

Beyond Metadata — SEO Best Practices

The indxel CLI catches metadata issues. But good SEO goes further. When reviewing or setting up a project, also check these (see references/seo-knowledge-base.md for full details):

  1. Semantic HTML — Use <article>, <section>, <nav>, not div soup. AI crawlers rely on semantic tags to understand content relationships.

  2. Heading hierarchy — One <h1> per page, no skipped levels (H2→H4).

  3. Structured data strategy — Use the @graph pattern to connect entities. Every Organization needs sameAs linking to LinkedIn, Wikipedia, etc.

  4. GEO readiness — Add /llms.txt for AI discoverability. Check that robots.txt doesn't block GPTBot, ClaudeBot, or Google-Extended.

  5. Rendering — Public pages must use SSG/ISR/SSR. Pure CSR = invisible to crawlers. Check for 'use client' on SEO-critical pages.

  6. Inverted pyramid — The answer must come right after the heading. AI models weight the first 100-200 tokens of a section heavily.

  7. Performance — LCP < 2.5s, INP < 200ms, CLS < 0.1. Check for heavy imports, unoptimized images, render-blocking scripts.

Source Transparency

This detail page is rendered from real SKILL.md content. Trust labels are metadata-based hints, not a safety guarantee.

Related Skills

Related by shared tags or category signals.

General

indxel-pro

No summary provided by upstream source.

Repository SourceNeeds Review
Web3

Idiom Dictionary

成语词典。成语查询、典故故事、成语接龙、成语猜谜、造句示例、分类浏览。Chinese idiom dictionary with stories, chain game, quiz. 成语、典故、国学。

Registry SourceRecently Updated
1521Profile unavailable
Web3

Wallet Tracker

Multi-chain wallet asset tracker — monitor EVM and Solana wallets, aggregate portfolio, and detect holding changes. Use when you need wallet tracker capabili...

Registry SourceRecently Updated
2050Profile unavailable
Web3

Moses Roles

MO§ES™ Role Hierarchy — Defines Primary, Secondary, Observer agents with enforced sequencing. Primary leads, Secondary validates, Observer flags. Enforces Pr...

Registry SourceRecently Updated
550Profile unavailable