nyuchimzizi
Mzizi — an open-architecture project of the Bundu Foundation, operated and developed by Nyuchi. Built on the Five African Minerals palette.
Built by Nyuchi Africav4.0.39
SEO metadata component for Next.js App Router. Generates head metadata, Open Graph tags, Twitter Cards, Schema.org JSON-LD structured data, and canonical URLs. Server component — runs at build/request time. Supports all Schema.org types used by the platform: JobPosting, VideoObject, MedicalWebPage, RentalCarReservation, Product, Event, Article, Recipe, etc.
View the full component source code below.
import type { Metadata } from "next"
/* ═══════════════════════════════════════════════════════════════
NYUCHI SEO — Layer 6 Page Composition
Server-side metadata generation for Next.js App Router.
═══════════════════════════════════════════════════════════════ */
interface NyuchiSEOConfig {
title: string
description?: string
canonicalUrl?: string
ogImage?: string
ogType?: "website" | "article" | "profile" | "product"
twitterCard?: "summary" | "summary_large_image" | "player"
noIndex?: boolean
locale?: string
alternateLocales?: string[]
/** Schema.org structured data */
schema?: SchemaOrgData | SchemaOrgData[]
}
interface SchemaOrgData {
"@type": string
[key: string]: unknown
}
const BASE_URL = "https://mukoko.com"
const SITE_NAME = "Mukoko"
const DEFAULT_OG_IMAGE = "/og-default.png"
/**
* Generate Next.js Metadata object from NyuchiSEOConfig.
* Use in page.tsx: export const metadata = generateMetadata({ title: "..." })
*/
export function generateMetadata(config: NyuchiSEOConfig): Metadata {
const { title, description, canonicalUrl, ogImage, ogType = "website", twitterCard = "summary_large_image", noIndex = false, locale = "en", alternateLocales = [] } = config
const fullTitle = `${title} — ${SITE_NAME}`
const image = ogImage || DEFAULT_OG_IMAGE
const url = canonicalUrl ? `${BASE_URL}${canonicalUrl}` : undefined
return {
title: fullTitle,
description,
...(noIndex && { robots: { index: false, follow: false } }),
alternates: { canonical: url, languages: Object.fromEntries(alternateLocales.map((l) => [l, `${BASE_URL}/${l}${canonicalUrl || ""}`])) },
openGraph: { title: fullTitle, description, url, siteName: SITE_NAME, type: ogType, locale, images: [{ url: image, width: 1200, height: 630, alt: title }] },
twitter: { card: twitterCard, title: fullTitle, description, images: [image] },
}
}
/**
* Generate Schema.org JSON-LD script tag content.
* Use in layout.tsx: <script type="application/ld+json" dangerouslySetInnerHTML={{ __html: generateSchemaLD(schema) }} />
*/
export function generateSchemaLD(schema: SchemaOrgData | SchemaOrgData[]): string {
const items = Array.isArray(schema) ? schema : [schema]
const graph = items.map((item) => ({ "@context": "https://schema.org", ...item }))
return JSON.stringify(graph.length === 1 ? graph[0] : { "@context": "https://schema.org", "@graph": graph })
}
/** Pre-built Schema.org templates for common Mukoko content types */
export const schemaTemplates = {
jobPosting: (job: { title: string; company: string; location: string; description: string; datePosted: string; salary?: { min: number; max: number; currency: string } }): SchemaOrgData => ({
"@type": "JobPosting", title: job.title, hiringOrganization: { "@type": "Organization", name: job.company },
jobLocation: { "@type": "Place", address: job.location }, description: job.description, datePosted: job.datePosted,
...(job.salary && { baseSalary: { "@type": "MonetaryAmount", currency: job.salary.currency, value: { "@type": "QuantitativeValue", minValue: job.salary.min, maxValue: job.salary.max, unitText: "MONTH" } } }),
}),
article: (a: { title: string; author: string; datePublished: string; image?: string }): SchemaOrgData => ({
"@type": "Article", headline: a.title, author: { "@type": "Person", name: a.author }, datePublished: a.datePublished, ...(a.image && { image: a.image }),
}),
event: (e: { name: string; startDate: string; endDate?: string; location: string; description?: string }): SchemaOrgData => ({
"@type": "Event", name: e.name, startDate: e.startDate, ...(e.endDate && { endDate: e.endDate }),
location: { "@type": "Place", name: e.location }, ...(e.description && { description: e.description }),
}),
product: (p: { name: string; price: number; currency: string; image?: string; description?: string }): SchemaOrgData => ({
"@type": "Product", name: p.name, ...(p.description && { description: p.description }), ...(p.image && { image: p.image }),
offers: { "@type": "Offer", price: p.price, priceCurrency: p.currency, availability: "https://schema.org/InStock" },
}),
}
export type { NyuchiSEOConfig, SchemaOrgData }
npx shadcn@latest add https://mzizi.dev/api/v1/ui/nyuchi-seoFetch this component's metadata and source code from the registry API.
/api/v1/ui/nyuchi-seo