- Add 'Featured Examples' section with 6 popular repos (express, flask, zod, etc.) - Add browser window mockup in hero showing what generated docs look like - Fix all links: company.repi.fun → vectry.tech, github.com → gitea.repi.fun - Update stats: ~3 min generation, 10+ languages supported - New ExampleRepos client component with generate-on-click functionality
97 lines
3.1 KiB
TypeScript
97 lines
3.1 KiB
TypeScript
"use client";
|
|
|
|
import { useState } from "react";
|
|
import { useRouter } from "next/navigation";
|
|
import { ArrowRight, Loader2 } from "lucide-react";
|
|
|
|
interface ExampleRepo {
|
|
name: string;
|
|
description: string;
|
|
language: string;
|
|
languageColor: string;
|
|
}
|
|
|
|
interface ExampleRepoCardProps {
|
|
repo: ExampleRepo;
|
|
}
|
|
|
|
export function ExampleRepoCard({ repo }: ExampleRepoCardProps) {
|
|
const [isLoading, setIsLoading] = useState(false);
|
|
const router = useRouter();
|
|
|
|
const handleGenerate = async () => {
|
|
const repoUrl = `https://github.com/${repo.name}`;
|
|
setIsLoading(true);
|
|
|
|
try {
|
|
const response = await fetch("/api/generate", {
|
|
method: "POST",
|
|
headers: { "Content-Type": "application/json" },
|
|
body: JSON.stringify({ repoUrl }),
|
|
});
|
|
|
|
if (!response.ok) {
|
|
const data = await response.json();
|
|
throw new Error(data.error || "Failed to start generation");
|
|
}
|
|
|
|
const data = await response.json();
|
|
router.push(`/generate?repo=${encodeURIComponent(repoUrl)}&id=${data.id}`);
|
|
} catch (err) {
|
|
setIsLoading(false);
|
|
}
|
|
};
|
|
|
|
return (
|
|
<div className="group relative p-6 rounded-2xl glass hover:bg-white/[0.05] transition-all duration-300 hover:-translate-y-1 hover:shadow-2xl hover:shadow-blue-500/10">
|
|
<div className="absolute inset-0 rounded-2xl bg-gradient-to-r from-blue-500/20 via-indigo-500/20 to-purple-500/20 opacity-0 group-hover:opacity-100 transition-opacity -z-10 blur-xl" />
|
|
|
|
<div className="flex items-center justify-between mb-4">
|
|
<div
|
|
className="flex items-center gap-2 px-3 py-1 rounded-full text-xs font-medium"
|
|
style={{
|
|
backgroundColor: `${repo.languageColor}20`,
|
|
color: repo.languageColor,
|
|
border: `1px solid ${repo.languageColor}40`,
|
|
}}
|
|
>
|
|
<span
|
|
className="w-2 h-2 rounded-full"
|
|
style={{ backgroundColor: repo.languageColor }}
|
|
/>
|
|
{repo.language}
|
|
</div>
|
|
</div>
|
|
|
|
<h3 className="text-lg font-semibold text-white mb-2 group-hover:text-blue-300 transition-colors font-mono">
|
|
{repo.name}
|
|
</h3>
|
|
|
|
<p className="text-sm text-zinc-400 mb-6 leading-relaxed line-clamp-2">
|
|
{repo.description}
|
|
</p>
|
|
|
|
<button
|
|
onClick={handleGenerate}
|
|
disabled={isLoading}
|
|
className="w-full flex items-center justify-center gap-2 px-4 py-3 rounded-xl text-sm font-medium transition-all duration-200
|
|
bg-gradient-to-r from-blue-600/20 to-indigo-600/20 hover:from-blue-600 hover:to-indigo-600
|
|
border border-blue-500/30 hover:border-transparent text-blue-300 hover:text-white
|
|
disabled:opacity-50 disabled:cursor-not-allowed group/btn"
|
|
>
|
|
{isLoading ? (
|
|
<>
|
|
<Loader2 className="w-4 h-4 animate-spin" />
|
|
<span>Starting...</span>
|
|
</>
|
|
) : (
|
|
<>
|
|
<span>Generate Docs</span>
|
|
<ArrowRight className="w-4 h-4 group-hover/btn:translate-x-1 transition-transform" />
|
|
</>
|
|
)}
|
|
</button>
|
|
</div>
|
|
);
|
|
}
|