npm package: @masters-ws/react-seo
Description: Professional high-performance SEO package for React/Next.js. Zero-dependency core for Next.js App Router, optional Helmet components for React.
Author: Masters WS
Latest version: 1.5.4

[![npm version](https://img.shields.io/npm/v/@masters-ws/react-seo.svg?style=flat-square)](https://www.npmjs.com/package/@masters-ws/react-seo)
[![Total Downloads](https://img.shields.io/npm/dt/@masters-ws/react-seo.svg?style=flat-square)](https://www.npmjs.com/package/@masters-ws/react-seo)
[![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg?style=flat-square)](https://opensource.org/licenses/MIT)

# @masters-ws/react-seo

> Professional SEO toolkit for React & Next.js — SSR-first, zero-dependency core, 30+ schema types, and built-in development auditor.

---

## Why @masters-ws/react-seo?

Most SEO packages inject metadata client-side — after JavaScript loads. Google crawls your page before that. This package fixes that.

| Feature | @masters-ws/react-seo | next-seo | react-helmet |
|---|---|---|---|
| Zero-dependency core | ✅ | ❌ | ❌ |
| SSR-first (App Router) | ✅ | ✅ | ❌ |
| `@graph` JSON-LD | ✅ | ❌ | ❌ |
| One-call page setup | ✅ | ❌ | ❌ |
| **Integrated SEO Auditor** | ✅ | ❌ | ❌ |
| Built-in pagination SEO | ✅ | partial | ❌ |

---

## Installation

```bash
# Next.js App Router (zero dependencies)
npm install @masters-ws/react-seo

# React / Next.js Pages Router
npm install @masters-ws/react-seo react-helmet-async
```

---

## 🔍 SEO Auditor (Development Only)

This library includes a built-in **SEO Auditor** component designed to speed up your development workflow by providing a real-time analysis of your page's SEO status directly in your browser.

- **Real-Time Analysis:** Scans for title/description lengths, H1 counts, missing alt tags, and more.
- **Visual Previews:** Live mockups for Google Search results and Social Media cards.
- **Production Safe:** Only renders when `process.env.NODE_ENV === 'development'`.

### Usage:

```tsx
// app/layout.tsx (Next.js App Router)
import { SEOAuditor } from '@masters-ws/react-seo';

export default function RootLayout({ children }) {
  return (
    <html>
      <body>
        {children}
        <SEOAuditor />
      </body>
    </html>
  );
}
```

---

## 🚀 Quick Start: Next.js App Router (Recommended)

### Product Page — One-Call Setup

```tsx
// app/products/[slug]/page.tsx
import { generateProductMetadata, JsonLd } from '@masters-ws/react-seo/core';

const siteConfig = {
  name: "My Store",
  url: "https://store.com",
  logo: "https://store.com/logo.png",
  description: "Best online store",
  language: "en_US",
};

export async function generateMetadata({ params }) {
  const product = await fetchProduct(params.slug);
  const { metadata } = generateProductMetadata({
    name: product.name,
    description: product.short_description,
    image: [product.main_image, ...product.gallery],
    price: product.price,
    currency: "USD",
    sku: product.sku,
    brand: product.brand?.name,
    availability: product.in_stock
      ? "https://schema.org/InStock"
      : "https://schema.org/OutOfStock",
    url: `https://store.com/products/${params.slug}`,
    breadcrumbs: [
      { name: "Home", item: "https://store.com" },
      { name: product.category?.name, item: `https://store.com/categories/${product.category?.slug}` },
      { name: product.name, item: `https://store.com/products/${params.slug}` },
    ],
  }, siteConfig);

  return metadata;
}

export default async function ProductPage({ params }) {
  const product = await fetchProduct(params.slug);
  const { schemas } = generateProductMetadata({ /* same options */ }, siteConfig);

  return (
    <>
      <JsonLd schema={schemas} graph />
      <ProductDetailClient product={product} />
    </>
  );
}
```

**What Google sees in the HTML source:**
```html
<title>Product Name | My Store</title>
<meta name="description" content="..." />
<meta property="og:title" content="Product Name" />
<meta property="og:image" content="https://store.com/product.jpg" />
<link rel="canonical" href="https://store.com/products/my-product" />
<script type="application/ld+json">
{
  "@context": "https://schema.org",
  "@graph": [
    { "@type": "Product", "name": "...", "offers": {...} },
    { "@type": "BreadcrumbList", "itemListElement": [...] },
    { "@type": "Organization", "name": "..." },
    { "@type": "WebSite", "potentialAction": {...} }
  ]
}
</script>
```

---

## Core Functions

### One-Call Helpers (Recommended)

| Function | Generates |
|---|---|
| `generateProductMetadata(product, config)` | Metadata + Product, Breadcrumb, Organization, WebSite schemas |
| `generateArticleMetadata(article, config)` | Metadata + NewsArticle, Breadcrumb, Organization, WebSite schemas |
| `generateCategoryMetadata(category, config)` | Metadata + CollectionPage, Breadcrumb, ItemList schemas |
| `generateHomepageMetadata(input, config)` | Metadata + WebPage, Organization, WebSite, optional LocalBusiness schemas |

### Schema Generators

| Function | Schema Type |
|---|---|
| `generateProductSchema(data)` | `Product` — multi-image, reviews, return policy, shipping, variants |
| `generateArticleSchema(data, config)` | `NewsArticle` |
| `generateFAQSchema(questions)` | `FAQPage` |
| `generateBreadcrumbSchema(items)` | `BreadcrumbList` |
| `generateLocalBusinessSchema(data)` | `LocalBusiness` |
| `generateOrganizationSchema(config)` | `Organization` |
| `generateWebSiteSchema(config)` | `WebSite` with `SearchAction` |
| `generateWebPageSchema(data, config)` | `WebPage` |
| `generateHowToSchema(data)` | `HowTo` |
| `generateRecipeSchema(data)` | `Recipe` |
| `generateJobPostingSchema(data)` | `JobPosting` |
| `generateEventSchema(data)` | `Event` |
| `generateVideoSchema(data)` | `VideoObject` |

### Utilities

| Function | Description |
|---|---|
| `toNextMetadata(data, config)` | Converts SEO data to Next.js Metadata object |
| `cleanSchema(obj)` | Removes `undefined`/`null` from schema objects |
| `validateSEO(type, data, fields)` | Dev-only warnings for missing required fields |

### `<JsonLd>` Component

```tsx
// Multiple separate <script> tags
<JsonLd schema={[productSchema, breadcrumbSchema]} />

// Single @graph block (Google recommended)
<JsonLd schema={[productSchema, breadcrumbSchema, orgSchema]} graph />
```

---

## Product Schema — Advanced Features

### Reviews + Ratings
```tsx
generateProductSchema({
  name: "T-Shirt",
  rating: 4.5,
  reviewCount: 128,
  reviews: [
    { author: "Alice", ratingValue: 5, reviewBody: "Amazing quality!", datePublished: "2024-01-15" },
    { author: "Bob",   ratingValue: 4, reviewBody: "Good value",       datePublished: "2024-02-01" },
  ],
});
```

### Return Policy
```tsx
generateProductSchema({
  returnPolicy: {
    returnPolicyCategory: "MerchantReturnFiniteReturnWindow",
    returnWithin: 30,
    returnMethod: "ReturnByMail",
    returnFees: "FreeReturn",
  },
});
```

### Shipping
```tsx
generateProductSchema({
  shipping: {
    shippingRate: { value: 5.99, currency: "USD" },
    shippingDestination: "US",
    deliveryTime: { minDays: 3, maxDays: 7 },
    freeShippingThreshold: 50,
  },
});
```

### Product Variants → AggregateOffer
```tsx
generateProductSchema({
  variants: [
    { name: "Small",  sku: "TS-S", price: 19.99 },
    { name: "Medium", sku: "TS-M", price: 22.99 },
    { name: "Large",  sku: "TS-L", price: 24.99 },
  ],
});
// → AggregateOffer { lowPrice: 19.99, highPrice: 24.99, offerCount: 3 }
```

---

## React / Pages Router

```tsx
// _app.tsx
import { SEOProvider } from '@masters-ws/react-seo';

export default function App({ Component, pageProps }) {
  return (
    <SEOProvider config={{ name: "My Site", url: "https://mysite.com", description: "..." }}>
      <Component {...pageProps} />
    </SEOProvider>
  );
}

// pages/products/[id].tsx
import { SeoProduct } from '@masters-ws/react-seo';

export default function ProductPage({ product }) {
  return (
    <>
      <SeoProduct item={{
        name: product.name,
        description: product.description,
        image: product.image,
        price: product.price,
        currency: "USD",
        sku: product.sku,
      }} />
      <main>...</main>
    </>
  );
}
```

---

## ⚠️ SSR vs CSR

```tsx
// ✅ Correct — Server Component, Google sees everything
import { generateProductMetadata, JsonLd } from '@masters-ws/react-seo/core';
export async function generateMetadata() { /* ... */ }
export default function Page() {
  return <JsonLd schema={schemas} graph />;
}

// ❌ Wrong — 'use client' means metadata loads after JS
'use client';
export default function Page() {
  return <SEO title="..." />; // Google may miss this
}
```

---

## Generating SEO-Optimized Content

This package handles technical SEO perfectly. For generating the **actual content** that ranks — blog posts, product descriptions, landing pages — pair it with **Outrank**, the AI platform built specifically for SEO content at scale.

🚀 **Get Started:** [outrank.so](https://outrank.so/?via=shadi)  
🎁 **Exclusive:** Use code **`SHADI`** for **10% off** your first month.

---

## License

MIT © [Shadi Shammaa](https://github.com/shammaa)