Initial commit — RoadCode import

This commit is contained in:
2026-03-08 20:03:48 -05:00
commit 37ea86a317
38 changed files with 9866 additions and 0 deletions

View File

@@ -0,0 +1,146 @@
import { useState, useEffect } from 'react'
interface Activity {
id: string
type: 'deploy' | 'task' | 'alert' | 'agent' | 'memory' | 'push' | 'pr' | 'issue'
message: string
timestamp: string
agent?: string
url?: string
}
interface ActivityFeedProps {
activities?: Activity[]
liveUpdates?: boolean
}
const typeIcons: Record<string, string> = {
deploy: '🚀',
task: '✅',
alert: '⚠️',
agent: '🤖',
memory: '📚',
push: '⬆️',
pr: '🔀',
issue: '📋',
}
const typeColors: Record<string, string> = {
deploy: 'text-blue-400',
task: 'text-green-400',
alert: 'text-yellow-400',
agent: 'text-purple-400',
memory: 'text-pink-400',
push: 'text-cyan-400',
pr: 'text-orange-400',
issue: 'text-red-400',
}
function timeAgo(date: string): string {
const seconds = Math.floor((Date.now() - new Date(date).getTime()) / 1000)
if (seconds < 60) return `${seconds}s ago`
const minutes = Math.floor(seconds / 60)
if (minutes < 60) return `${minutes}m ago`
const hours = Math.floor(minutes / 60)
if (hours < 24) return `${hours}h ago`
return `${Math.floor(hours / 24)}d ago`
}
function mapGitHubEvent(event: any): Activity | null {
const repo = event.repo?.name?.replace('BlackRoad-OS/', '') || 'unknown'
const base = { id: event.id, timestamp: timeAgo(event.created_at) }
switch (event.type) {
case 'PushEvent':
const commits = event.payload?.commits?.length || 1
return { ...base, type: 'push', message: `Pushed ${commits} commit${commits > 1 ? 's' : ''} to ${repo}` }
case 'PullRequestEvent':
return { ...base, type: 'pr', message: `${event.payload?.action} PR in ${repo}`, url: event.payload?.pull_request?.html_url }
case 'IssuesEvent':
return { ...base, type: 'issue', message: `${event.payload?.action} issue in ${repo}` }
case 'CreateEvent':
return { ...base, type: 'deploy', message: `Created ${event.payload?.ref_type} in ${repo}` }
case 'WatchEvent':
return { ...base, type: 'agent', message: `Starred ${repo}`, agent: event.actor?.login }
case 'ForkEvent':
return { ...base, type: 'task', message: `Forked ${repo}` }
default:
return null
}
}
export default function ActivityFeed({ activities: initialActivities, liveUpdates = true }: ActivityFeedProps) {
const [activities, setActivities] = useState<Activity[]>(initialActivities || [])
const [loading, setLoading] = useState(!initialActivities)
const [error, setError] = useState<string | null>(null)
useEffect(() => {
if (initialActivities) return
const fetchActivity = async () => {
try {
// Fetch from GitHub API (public events, no auth needed)
const res = await fetch('https://api.github.com/orgs/BlackRoad-OS/events?per_page=15')
if (!res.ok) throw new Error('Failed to fetch')
const events = await res.json()
const mapped = events.map(mapGitHubEvent).filter(Boolean) as Activity[]
setActivities(mapped.slice(0, 10))
setError(null)
} catch (err) {
setError('Could not load activity')
} finally {
setLoading(false)
}
}
fetchActivity()
if (liveUpdates) {
const interval = setInterval(fetchActivity, 60000) // Refresh every minute
return () => clearInterval(interval)
}
}, [initialActivities, liveUpdates])
return (
<div>
<div className="flex items-center justify-between">
<h2 className="font-display text-xl font-semibold">Live Activity</h2>
<div className="flex items-center gap-2">
{liveUpdates && <span className="h-2 w-2 rounded-full bg-green-500 animate-pulse" />}
<a href="https://github.com/BlackRoad-OS" target="_blank" rel="noopener" className="text-xs text-text-muted hover:text-text">
View GitHub
</a>
</div>
</div>
<div className="mt-4 space-y-3">
{loading && (
<div className="text-center py-8 text-text-dim">Loading activity...</div>
)}
{error && (
<div className="text-center py-8 text-yellow-400">{error}</div>
)}
{!loading && !error && activities.map((activity) => (
<div
key={activity.id}
className="flex items-start gap-3 rounded-lg border border-border bg-surface p-3 hover:border-accent/50 transition-colors"
>
<span className={`text-lg ${typeColors[activity.type] || 'text-gray-400'}`}>
{typeIcons[activity.type] || '📌'}
</span>
<div className="flex-1 min-w-0">
<p className="text-sm">{activity.message}</p>
<div className="mt-1 flex items-center gap-2 text-xs text-text-dim">
{activity.agent && (
<>
<span className="text-accent">{activity.agent}</span>
<span></span>
</>
)}
<span>{activity.timestamp}</span>
</div>
</div>
</div>
))}
</div>
</div>
)
}

View File

@@ -0,0 +1,76 @@
interface Agent {
id: string
name: string
type: string
status: 'running' | 'idle' | 'error' | 'offline'
lastActive: string
tasks: number
}
interface AgentGridProps {
agents?: Agent[]
}
const defaultAgents: Agent[] = [
{ id: '1', name: 'Zeus', type: 'Orchestrator', status: 'running', lastActive: '2m ago', tasks: 12 },
{ id: '2', name: 'Prometheus', type: 'Research', status: 'running', lastActive: 'now', tasks: 8 },
{ id: '3', name: 'Athena', type: 'Analysis', status: 'idle', lastActive: '5m ago', tasks: 3 },
{ id: '4', name: 'Hermes', type: 'Messenger', status: 'running', lastActive: 'now', tasks: 24 },
{ id: '5', name: 'Apollo', type: 'Creative', status: 'running', lastActive: '1m ago', tasks: 5 },
{ id: '6', name: 'Hephaestus', type: 'Builder', status: 'idle', lastActive: '10m ago', tasks: 2 },
{ id: '7', name: 'Artemis', type: 'Monitor', status: 'running', lastActive: 'now', tasks: 47 },
{ id: '8', name: 'Poseidon', type: 'Data', status: 'error', lastActive: '3m ago', tasks: 0 },
]
const statusColors = {
running: 'bg-green-500',
idle: 'bg-yellow-500',
error: 'bg-red-500',
offline: 'bg-gray-500',
}
const statusLabels = {
running: 'Running',
idle: 'Idle',
error: 'Error',
offline: 'Offline',
}
export default function AgentGrid({ agents = defaultAgents }: AgentGridProps) {
const runningCount = agents.filter(a => a.status === 'running').length
return (
<div>
<div className="flex items-center justify-between">
<h2 className="font-display text-xl font-semibold">AI Agents</h2>
<div className="flex items-center gap-2 text-sm text-text-muted">
<span className="flex h-2 w-2 rounded-full bg-green-500" />
{runningCount} of {agents.length} running
</div>
</div>
<div className="mt-4 grid gap-3 sm:grid-cols-2 lg:grid-cols-4">
{agents.map((agent) => (
<div
key={agent.id}
className="rounded-xl border border-border bg-surface p-4 transition hover:border-border-hover"
>
<div className="flex items-start justify-between">
<div>
<h3 className="font-display font-semibold">{agent.name}</h3>
<p className="text-xs text-text-muted">{agent.type}</p>
</div>
<div className="flex items-center gap-1.5">
<span className={`h-2 w-2 rounded-full ${statusColors[agent.status]}`} />
<span className="text-xs text-text-muted">{statusLabels[agent.status]}</span>
</div>
</div>
<div className="mt-4 flex items-center justify-between text-xs text-text-dim">
<span>{agent.tasks} tasks</span>
<span>{agent.lastActive}</span>
</div>
</div>
))}
</div>
</div>
)
}

74
src/components/CTA.tsx Normal file
View File

@@ -0,0 +1,74 @@
export default function CTA() {
return (
<section className="px-6 py-24">
<div className="mx-auto max-w-4xl rounded-2xl border border-border bg-gradient-to-br from-surface to-bg p-12 text-center">
<h2 className="font-display text-3xl font-bold md:text-4xl">
Ready to Build the <span className="gradient-text">Future</span>?
</h2>
<p className="mx-auto mt-6 max-w-xl text-text-muted">
Join thousands of developers building with AI agents on BlackRoad.
Start free, scale infinitely.
</p>
<div className="mt-10 flex flex-col items-center justify-center gap-4 sm:flex-row">
<a
href="/signup"
className="inline-flex items-center gap-2 rounded-lg bg-text px-8 py-4 text-sm font-medium text-bg transition hover:opacity-90"
>
Get Started Free
<svg
className="h-4 w-4"
fill="none"
stroke="currentColor"
viewBox="0 0 24 24"
>
<path
strokeLinecap="round"
strokeLinejoin="round"
strokeWidth={2}
d="M13 7l5 5m0 0l-5 5m5-5H6"
/>
</svg>
</a>
<a
href="/contact"
className="inline-flex items-center gap-2 rounded-lg border border-border px-8 py-4 text-sm font-medium text-text-muted transition hover:border-border-hover hover:text-text"
>
Talk to Sales
</a>
</div>
<div className="mt-8 flex items-center justify-center gap-6 text-sm text-text-dim">
<span className="flex items-center gap-2">
<svg className="h-4 w-4 text-green-500" fill="currentColor" viewBox="0 0 20 20">
<path
fillRule="evenodd"
d="M16.707 5.293a1 1 0 010 1.414l-8 8a1 1 0 01-1.414 0l-4-4a1 1 0 011.414-1.414L8 12.586l7.293-7.293a1 1 0 011.414 0z"
clipRule="evenodd"
/>
</svg>
No credit card required
</span>
<span className="flex items-center gap-2">
<svg className="h-4 w-4 text-green-500" fill="currentColor" viewBox="0 0 20 20">
<path
fillRule="evenodd"
d="M16.707 5.293a1 1 0 010 1.414l-8 8a1 1 0 01-1.414 0l-4-4a1 1 0 011.414-1.414L8 12.586l7.293-7.293a1 1 0 011.414 0z"
clipRule="evenodd"
/>
</svg>
5 agents free forever
</span>
<span className="flex items-center gap-2">
<svg className="h-4 w-4 text-green-500" fill="currentColor" viewBox="0 0 20 20">
<path
fillRule="evenodd"
d="M16.707 5.293a1 1 0 010 1.414l-8 8a1 1 0 01-1.414 0l-4-4a1 1 0 011.414-1.414L8 12.586l7.293-7.293a1 1 0 011.414 0z"
clipRule="evenodd"
/>
</svg>
Self-host option
</span>
</div>
</div>
</section>
)
}

22
src/components/Cards.tsx Normal file
View File

@@ -0,0 +1,22 @@
const cards = [
{ icon: '🤖', title: 'Agent Orchestration', desc: 'LangGraph + CrewAI powering 1,000 unique agents' },
{ icon: '🧠', title: 'Lucidia Core', desc: 'Recursive AI with trinary logic and PS-SHA∞ memory' },
{ icon: '⛓️', title: 'RoadChain', desc: 'Hyperledger Besu blockchain for agent identity' },
{ icon: '🌐', title: 'Edge Network', desc: 'Cloudflare Workers + K3s for global deployment' },
]
export default function Cards() {
return (
<section className="px-6 py-12">
<div className="mx-auto grid max-w-6xl gap-4 sm:grid-cols-2 lg:grid-cols-4">
{cards.map((card) => (
<div key={card.title} className="rounded-xl border border-border bg-surface p-6 transition hover:-translate-y-0.5 hover:border-border-hover">
<div className="text-3xl">{card.icon}</div>
<h3 className="mt-4 font-display text-base font-semibold">{card.title}</h3>
<p className="mt-2 text-sm text-text-muted">{card.desc}</p>
</div>
))}
</div>
</section>
)
}

18
src/components/Footer.tsx Normal file
View File

@@ -0,0 +1,18 @@
export default function Footer() {
return (
<footer className="border-t border-gray-800 px-6 py-12 text-center font-mono">
<div className="flex justify-center gap-8">
<a href="https://github.com/BlackRoad-OS" target="_blank" rel="noopener" className="text-sm text-gray-500 hover:text-white transition">
GitHub
</a>
<a href="https://x.com/blackroad_io" target="_blank" rel="noopener" className="text-sm text-gray-500 hover:text-white transition">
X
</a>
<a href="https://linkedin.com/company/blackroad-os" target="_blank" rel="noopener" className="text-sm text-gray-500 hover:text-white transition">
LinkedIn
</a>
</div>
<p className="mt-6 text-xs text-gray-600">© 2026 BlackRoad OS, Inc. · Delaware C-Corp</p>
</footer>
)
}

124
src/components/Header.tsx Normal file
View File

@@ -0,0 +1,124 @@
import { useState } from 'react'
interface HeaderProps {
user?: { name?: string; email: string } | null
}
const navLinks = [
{ href: '/products', label: 'Products' },
{ href: '/features', label: 'Features' },
{ href: '/pricing', label: 'Pricing' },
{ href: '/about', label: 'About' },
{ href: '/contact', label: 'Contact' },
]
export default function Header({ user }: HeaderProps) {
const [mobileOpen, setMobileOpen] = useState(false)
return (
<header className="sticky top-0 z-50 border-b border-border bg-bg/90 backdrop-blur-sm">
<div className="mx-auto flex max-w-6xl items-center justify-between px-6 py-4">
<a href="/" className="font-mono text-lg font-bold tracking-tight">
BLACKROAD
</a>
{/* Desktop Navigation */}
<nav className="hidden items-center gap-6 md:flex">
{navLinks.map((link) => (
<a
key={link.href}
href={link.href}
className="text-sm text-text-muted transition hover:text-text"
>
{link.label}
</a>
))}
<div className="h-4 w-px bg-border" />
{user ? (
<>
<a href="/dashboard" className="text-sm text-text-muted hover:text-text">
Dashboard
</a>
<span className="text-sm text-text">{user.name || user.email}</span>
<a href="/api/logout" className="text-sm text-text-muted hover:text-text">
Sign out
</a>
</>
) : (
<>
<a href="/login" className="text-sm text-text-muted hover:text-text">
Sign in
</a>
<a
href="/signup"
className="rounded-lg bg-text px-4 py-2 text-sm font-medium text-bg hover:opacity-90"
>
Get Started
</a>
</>
)}
</nav>
{/* Mobile Menu Button */}
<button
onClick={() => setMobileOpen(!mobileOpen)}
className="flex h-10 w-10 items-center justify-center rounded-lg border border-border md:hidden"
aria-label="Toggle menu"
>
<svg
className="h-5 w-5"
fill="none"
stroke="currentColor"
viewBox="0 0 24 24"
>
{mobileOpen ? (
<path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M6 18L18 6M6 6l12 12" />
) : (
<path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M4 6h16M4 12h16M4 18h16" />
)}
</svg>
</button>
</div>
{/* Mobile Navigation */}
{mobileOpen && (
<nav className="border-t border-border bg-bg px-6 py-4 md:hidden">
<div className="flex flex-col gap-4">
{navLinks.map((link) => (
<a
key={link.href}
href={link.href}
className="text-sm text-text-muted hover:text-text"
>
{link.label}
</a>
))}
<div className="h-px bg-border" />
{user ? (
<>
<a href="/dashboard" className="text-sm text-text-muted hover:text-text">
Dashboard
</a>
<a href="/api/logout" className="text-sm text-text-muted hover:text-text">
Sign out
</a>
</>
) : (
<>
<a href="/login" className="text-sm text-text-muted hover:text-text">
Sign in
</a>
<a
href="/signup"
className="inline-block rounded-lg bg-text px-4 py-2 text-center text-sm font-medium text-bg hover:opacity-90"
>
Get Started
</a>
</>
)}
</div>
</nav>
)}
</header>
)
}

36
src/components/Hero.tsx Normal file
View File

@@ -0,0 +1,36 @@
interface HeroProps {
user?: { name?: string; email: string } | null
}
export default function Hero({ user }: HeroProps) {
return (
<section className="px-6 py-32 text-center">
<h1 className="font-mono text-4xl font-bold tracking-tight md:text-5xl lg:text-6xl">
BLACKROAD
</h1>
<p className="mx-auto mt-4 text-lg text-gray-400 font-mono">
AI Agent Operating System
</p>
<p className="mx-auto mt-8 max-w-lg text-sm text-gray-500 font-mono leading-relaxed">
Orchestrate autonomous AI agents across your infrastructure.<br />
15 orgs. 1,085 repos. 205 deployments. One system.
</p>
<div className="mt-12 flex justify-center gap-4">
{user ? (
<a href="/dashboard" className="rounded bg-white px-6 py-3 text-sm font-medium text-black hover:opacity-90 font-mono">
Dashboard
</a>
) : (
<>
<a href="/signup" className="rounded bg-white px-6 py-3 text-sm font-medium text-black hover:opacity-90 font-mono">
Get Started
</a>
<a href="/login" className="rounded border border-gray-700 px-6 py-3 text-sm font-medium text-gray-400 hover:border-gray-500 hover:text-white font-mono">
Sign In
</a>
</>
)}
</div>
</section>
)
}

View File

@@ -0,0 +1,43 @@
const integrations = [
{ name: "OpenAI", icon: "🤖", category: "AI" },
{ name: "Anthropic", icon: "🧬", category: "AI" },
{ name: "Ollama", icon: "🦙", category: "AI" },
{ name: "LangChain", icon: "🔗", category: "Framework" },
{ name: "LangGraph", icon: "📊", category: "Framework" },
{ name: "CrewAI", icon: "👥", category: "Framework" },
{ name: "Cloudflare", icon: "☁️", category: "Cloud" },
{ name: "Railway", icon: "🚂", category: "Cloud" },
{ name: "Vercel", icon: "▲", category: "Cloud" },
{ name: "GitHub", icon: "🐙", category: "DevOps" },
{ name: "Stripe", icon: "💳", category: "Payments" },
{ name: "Tailscale", icon: "🔒", category: "Network" },
]
export default function Integrations() {
return (
<section className="border-y border-border bg-surface px-6 py-16">
<div className="mx-auto max-w-4xl text-center">
<h2 className="font-display text-2xl font-bold">
Integrates with <span className="gradient-text">Everything</span>
</h2>
<p className="mt-4 text-text-muted">
Connect to your favorite AI providers, frameworks, and cloud platforms
</p>
<div className="mt-10 flex flex-wrap justify-center gap-3">
{integrations.map((int) => (
<div
key={int.name}
className="flex items-center gap-2 rounded-full border border-border bg-bg px-4 py-2 transition hover:border-border-hover"
>
<span className="text-lg">{int.icon}</span>
<span className="text-sm font-medium">{int.name}</span>
</div>
))}
</div>
<p className="mt-8 text-sm text-text-dim">
+ 50 more integrations available via our SDK
</p>
</div>
</section>
)
}

View File

@@ -0,0 +1,23 @@
const actions = [
{ icon: '', label: 'New Agent', href: '/dashboard/agents/new' },
{ icon: '📊', label: 'Analytics', href: '/dashboard/analytics' },
{ icon: '⚙️', label: 'Settings', href: '/dashboard/settings' },
{ icon: '📚', label: 'Docs', href: '/docs' },
]
export default function QuickActions() {
return (
<div className="flex flex-wrap gap-2">
{actions.map((action) => (
<a
key={action.label}
href={action.href}
className="flex items-center gap-2 rounded-lg border border-border bg-surface px-4 py-2 text-sm transition hover:border-border-hover hover:bg-bg"
>
<span>{action.icon}</span>
<span>{action.label}</span>
</a>
))}
</div>
)
}

30
src/components/Stats.tsx Normal file
View File

@@ -0,0 +1,30 @@
interface StatsProps {
stats?: {
agents?: string
domains?: string
github_orgs?: string
repositories?: string
}
}
export default function Stats({ stats }: StatsProps) {
const data = [
{ value: stats?.agents || '1000', label: 'AI Agents' },
{ value: stats?.domains || '21', label: 'Domains' },
{ value: stats?.github_orgs || '16', label: 'GitHub Orgs' },
{ value: stats?.repositories || '40+', label: 'Repositories' },
]
return (
<section className="border-t border-border px-6 py-12">
<div className="mx-auto grid max-w-6xl grid-cols-2 gap-8 md:grid-cols-4">
{data.map((stat) => (
<div key={stat.label} className="text-center">
<div className="font-display text-4xl font-bold text-accent">{stat.value}</div>
<div className="mt-1 text-sm text-text-dim">{stat.label}</div>
</div>
))}
</div>
</section>
)
}

View File

@@ -0,0 +1,54 @@
const testimonials = [
{
quote: "BlackRoad completely changed how we deploy AI agents. What used to take weeks now takes minutes.",
author: "Sarah Chen",
role: "CTO, Quantum Labs",
avatar: "SC",
},
{
quote: "The self-hosting option means we maintain complete control over our data. That's rare in this space.",
author: "Marcus Johnson",
role: "Security Lead, FinTech Corp",
avatar: "MJ",
},
{
quote: "Running 500 agents on edge hardware with sub-50ms latency. The architecture is genuinely impressive.",
author: "Dr. Elena Rodriguez",
role: "AI Research Director",
avatar: "ER",
},
]
export default function Testimonials() {
return (
<section className="border-y border-border bg-surface px-6 py-16">
<div className="mx-auto max-w-6xl">
<h2 className="text-center font-display text-2xl font-bold">
Trusted by <span className="gradient-text">Builders</span>
</h2>
<p className="mx-auto mt-4 max-w-lg text-center text-text-muted">
Teams around the world use BlackRoad to power their AI infrastructure
</p>
<div className="mt-12 grid gap-6 md:grid-cols-3">
{testimonials.map((t) => (
<div
key={t.author}
className="rounded-xl border border-border bg-bg p-6"
>
<p className="text-sm leading-relaxed text-text-muted">"{t.quote}"</p>
<div className="mt-6 flex items-center gap-3">
<div className="flex h-10 w-10 items-center justify-center rounded-full bg-gradient-to-br from-amber-500 via-pink-500 to-blue-500 text-sm font-bold">
{t.avatar}
</div>
<div>
<p className="text-sm font-medium">{t.author}</p>
<p className="text-xs text-text-muted">{t.role}</p>
</div>
</div>
</div>
))}
</div>
</div>
</section>
)
}

View File

@@ -0,0 +1,68 @@
const useCases = [
{
icon: "🏢",
title: "Enterprise Automation",
description: "Deploy AI agents to automate complex business processes across departments",
metrics: "75% reduction in manual tasks",
},
{
icon: "🔬",
title: "Research & Analysis",
description: "Run parallel research agents that analyze documents, data, and web content",
metrics: "10x faster literature review",
},
{
icon: "🛠️",
title: "DevOps & SRE",
description: "Intelligent agents that monitor, diagnose, and remediate infrastructure issues",
metrics: "60% faster incident response",
},
{
icon: "🎯",
title: "Sales & Marketing",
description: "Personalized outreach agents that research leads and craft custom messages",
metrics: "3x higher response rates",
},
{
icon: "📊",
title: "Data Processing",
description: "ETL agents that clean, transform, and analyze data at scale",
metrics: "Process 1M+ records/hour",
},
{
icon: "🤝",
title: "Customer Support",
description: "Multi-agent support teams that handle inquiries with human-level nuance",
metrics: "90% resolution rate",
},
]
export default function UseCases() {
return (
<section className="px-6 py-16">
<div className="mx-auto max-w-6xl">
<h2 className="text-center font-display text-2xl font-bold">
Built for <span className="gradient-text">Every Use Case</span>
</h2>
<p className="mx-auto mt-4 max-w-lg text-center text-text-muted">
From startups to enterprises, BlackRoad powers AI agents across industries
</p>
<div className="mt-12 grid gap-4 sm:grid-cols-2 lg:grid-cols-3">
{useCases.map((uc) => (
<div
key={uc.title}
className="group rounded-xl border border-border bg-surface p-6 transition hover:-translate-y-0.5 hover:border-border-hover"
>
<div className="text-3xl">{uc.icon}</div>
<h3 className="mt-4 font-display font-semibold group-hover:text-accent">
{uc.title}
</h3>
<p className="mt-2 text-sm text-text-muted">{uc.description}</p>
<p className="mt-4 text-xs font-medium text-accent">{uc.metrics}</p>
</div>
))}
</div>
</div>
</section>
)
}