- CreateProjectFlow now defaults to setup/fresh mode; type selector never shown - FreshIdeaSetup simplified to just project name + Start button (removed description field, 6-phase explanation copy, SetupHeader) Made-with: Cursor
75 lines
2.3 KiB
TypeScript
75 lines
2.3 KiB
TypeScript
"use client";
|
||
|
||
import { useRef, useState } from "react";
|
||
import { useRouter } from "next/navigation";
|
||
import { toast } from "sonner";
|
||
import { FieldLabel, TextInput, PrimaryButton, type SetupProps } from "./setup-shared";
|
||
|
||
export function FreshIdeaSetup({ workspace, onClose }: SetupProps) {
|
||
const router = useRouter();
|
||
const [name, setName] = useState("");
|
||
const [loading, setLoading] = useState(false);
|
||
const nameRef = useRef<HTMLInputElement>(null);
|
||
|
||
const canCreate = name.trim().length > 0;
|
||
|
||
const handleCreate = async () => {
|
||
if (!canCreate) return;
|
||
setLoading(true);
|
||
try {
|
||
const res = await fetch("/api/projects/create", {
|
||
method: "POST",
|
||
headers: { "Content-Type": "application/json" },
|
||
body: JSON.stringify({
|
||
projectName: name.trim(),
|
||
projectType: "web-app",
|
||
slug: name.toLowerCase().replace(/[^a-z0-9]+/g, "-"),
|
||
product: { name: name.trim() },
|
||
creationMode: "fresh",
|
||
sourceData: {},
|
||
}),
|
||
});
|
||
if (!res.ok) {
|
||
const err = await res.json();
|
||
toast.error(err.error || "Failed to create project");
|
||
return;
|
||
}
|
||
const data = await res.json();
|
||
onClose();
|
||
router.push(`/${workspace}/project/${data.projectId}/overview`);
|
||
} catch {
|
||
toast.error("Something went wrong");
|
||
} finally {
|
||
setLoading(false);
|
||
}
|
||
};
|
||
|
||
return (
|
||
<div style={{ padding: "32px 36px 36px" }}>
|
||
<div style={{ display: "flex", alignItems: "center", justifyContent: "space-between", marginBottom: 28 }}>
|
||
<div style={{ fontSize: "1.15rem", fontWeight: 600, color: "#1a1a1a", fontFamily: "Newsreader, serif" }}>
|
||
New project
|
||
</div>
|
||
<button
|
||
onClick={onClose}
|
||
style={{ background: "none", border: "none", cursor: "pointer", color: "#a09a90", fontSize: "1.1rem", padding: "2px 6px", lineHeight: 1 }}
|
||
>×</button>
|
||
</div>
|
||
|
||
<FieldLabel>Project name</FieldLabel>
|
||
<TextInput
|
||
value={name}
|
||
onChange={setName}
|
||
placeholder="e.g. Foxglove, Meridian, OpsAI…"
|
||
onKeyDown={e => { if (e.key === "Enter" && canCreate) handleCreate(); }}
|
||
inputRef={nameRef}
|
||
autoFocus
|
||
/>
|
||
|
||
<PrimaryButton onClick={handleCreate} disabled={!canCreate} loading={loading}>
|
||
Start →
|
||
</PrimaryButton>
|
||
</div>
|
||
);
|
||
}
|