Some checks failed
Deploy to Production / deploy (push) Failing after 46s
Ported and adapted from the BuildMyDiscord SEO setup: - lib/seo.ts — single source for site constants, the FAQ data (shared by the rendered FAQ and the FAQPage schema so they never drift) and JSON-LD builders. - Rich root metadata: title template, keywords, Open Graph, Twitter card, robots directives, canonical. - JSON-LD: Organization + WebSite + SoftwareApplication sitewide, FAQPage on the landing page. No AggregateRating — there are no real reviews yet. - app/robots.ts — allow all, explicit allow-list for AI answer-engine crawlers (GPTBot, ClaudeBot, PerplexityBot, …), disallow private routes. - app/sitemap.ts — every public marketing + docs route. - app/opengraph-image.tsx — monochrome on-brand 1200x630 share card. - app/manifest.ts + public/llms.txt. - Per-page metadata for pricing, changelog, security, privacy, terms, docs, templates and status. - opengraph-image + apple-icon pinned to the edge runtime — next/og crashes during a Node-runtime prerender. Verified: next build passes; /robots.txt, /sitemap.xml, /manifest.webmanifest and /opengraph-image all generate. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
109 lines
4.5 KiB
TypeScript
109 lines
4.5 KiB
TypeScript
import { CodeBlock } from '@/components/code-block';
|
||
import { pageMetadata } from '@/lib/seo';
|
||
|
||
export const metadata = pageMetadata({
|
||
title: 'Changelog',
|
||
description:
|
||
'Product updates and release notes for BuildMyMCPServer — new features, fixes and improvements to the MCP server platform.',
|
||
path: '/changelog',
|
||
});
|
||
|
||
interface Release {
|
||
version: string;
|
||
date: string;
|
||
tag: 'launch' | 'feature' | 'fix';
|
||
title: string;
|
||
items: string[];
|
||
}
|
||
|
||
const RELEASES: Release[] = [
|
||
{
|
||
version: '0.2.0',
|
||
date: '2026-05-19',
|
||
tag: 'feature',
|
||
title: '3-step wizard + filled-in pages',
|
||
items: [
|
||
'Real 3-step wizard: prompt → confirm parsed spec → build. Step 2 shows the tools Claude actually parsed and only asks for the credentials it identified.',
|
||
'Preview endpoint: POST /v1/servers/preview runs Claude once, caches the spec 5 min, build worker reuses it. Saves a second Claude round-trip (~30s).',
|
||
'Shared @bmm/llm package — system prompt + generateSpec live in one place, used by api and generator.',
|
||
'Audit log: writes for login, logout, server.create, server.iterate, server.delete. /v1/audit endpoint + /audit page.',
|
||
'Real /settings page (org info, plan & usage, members, encryption status).',
|
||
'Full /docs site: quickstart, MCP concepts, OAuth flow, authoring, self-hosting, API reference, FAQ.',
|
||
'Changelog, /security, /privacy, /terms, /pricing, /status pages — all marketing links work.',
|
||
],
|
||
},
|
||
{
|
||
version: '0.1.0',
|
||
date: '2026-05-18',
|
||
tag: 'launch',
|
||
title: 'Sprints 1–3 — initial public dev build',
|
||
items: [
|
||
'Monorepo: Next.js 15 + Fastify + BullMQ generator + runner-template.',
|
||
'Drizzle schema for orgs, servers, builds, secrets, oauth, metrics, audit.',
|
||
'Magic-link auth, 30-day sessions, AES-256-GCM secret encryption.',
|
||
'OAuth 2.1 Authorization Server: PKCE, RFC 7591 dynamic registration, RFC 8707 resource indicators, RS256 JWKS.',
|
||
'Runner template with Streamable HTTP + OAuth 2.1 Resource Server.',
|
||
'WebSocket build stream: queued → generating → building → deploying → live.',
|
||
'Install snippet generator for Claude Desktop, Cursor, ChatGPT.',
|
||
'docker-compose dev environment, pnpm dev bootstraps everything.',
|
||
],
|
||
},
|
||
];
|
||
|
||
const tagStyle: Record<Release['tag'], string> = {
|
||
launch: 'border-[--color-accent]/40 bg-[--color-accent]/10 text-[--color-accent]',
|
||
feature: 'border-emerald-400/40 bg-emerald-400/10 text-emerald-300',
|
||
fix: 'border-amber-400/40 bg-amber-400/10 text-amber-300',
|
||
};
|
||
|
||
export default function Changelog() {
|
||
return (
|
||
<div className="mx-auto max-w-3xl px-6 py-16">
|
||
<header className="mb-12">
|
||
<div className="text-[11px] uppercase tracking-[0.16em] text-[--color-fg-subtle]">
|
||
Release notes
|
||
</div>
|
||
<h1 className="mt-2 text-[32px] font-semibold tracking-tight">Changelog</h1>
|
||
<p className="mt-3 text-[14px] leading-relaxed text-[--color-fg-muted]">
|
||
What shipped, when, and why.
|
||
</p>
|
||
</header>
|
||
|
||
<div className="space-y-12">
|
||
{RELEASES.map((r) => (
|
||
<article key={r.version} className="relative pl-6">
|
||
<div className="absolute left-0 top-2 size-2 rounded-full border border-[--color-border-strong] bg-[--color-bg-elevated]" />
|
||
<div className="flex items-baseline gap-3">
|
||
<span className="mono text-[13px] text-[--color-fg]">v{r.version}</span>
|
||
<span className="text-[12px] text-[--color-fg-subtle]">{r.date}</span>
|
||
<span
|
||
className={`mono rounded-full border px-2 py-0.5 text-[10.5px] uppercase tracking-wider ${tagStyle[r.tag]}`}
|
||
>
|
||
{r.tag}
|
||
</span>
|
||
</div>
|
||
<h2 className="mt-2 text-[16px] font-semibold tracking-tight">{r.title}</h2>
|
||
<ul className="mt-3 space-y-1.5">
|
||
{r.items.map((item) => (
|
||
<li
|
||
key={item}
|
||
className="relative pl-4 text-[13px] leading-relaxed text-[--color-fg-muted] before:absolute before:left-0 before:top-2 before:size-1 before:rounded-full before:bg-[--color-fg-subtle]"
|
||
>
|
||
{item}
|
||
</li>
|
||
))}
|
||
</ul>
|
||
</article>
|
||
))}
|
||
</div>
|
||
|
||
<footer className="mt-16">
|
||
<CodeBlock
|
||
label="subscribe"
|
||
code={`Follow @buildmymcp on Mastodon — or watch the GitHub repo for tagged releases.`}
|
||
/>
|
||
</footer>
|
||
</div>
|
||
);
|
||
}
|