89 lines
2.8 KiB
TypeScript
89 lines
2.8 KiB
TypeScript
"use client";
|
|
|
|
import { useState } from "react";
|
|
import { useRouter } from "next/navigation";
|
|
import { ArrowLeft, Send, Loader2 } from "lucide-react";
|
|
import Link from "next/link";
|
|
import { useToast } from "@/components/Toast";
|
|
|
|
export default function NewSessionPage() {
|
|
const router = useRouter();
|
|
const { toast } = useToast();
|
|
const [message, setMessage] = useState("");
|
|
const [sending, setSending] = useState(false);
|
|
|
|
const create = async () => {
|
|
if (!message.trim() || sending) return;
|
|
setSending(true);
|
|
try {
|
|
const res = await fetch("/api/sessions", {
|
|
method: "POST",
|
|
headers: { "Content-Type": "application/json" },
|
|
body: JSON.stringify({ source: "web" }),
|
|
});
|
|
const data = await res.json();
|
|
const sessionId = data.session?.id;
|
|
if (!sessionId) throw new Error("No session ID");
|
|
|
|
await fetch("/api/sessions/" + sessionId + "/chat", {
|
|
method: "POST",
|
|
headers: { "Content-Type": "application/json" },
|
|
body: JSON.stringify({ message: message.trim() }),
|
|
});
|
|
|
|
router.push("/history/" + sessionId);
|
|
} catch (e) {
|
|
toast("Failed to create session", "error");
|
|
setSending(false);
|
|
}
|
|
};
|
|
|
|
return (
|
|
<div className="space-y-4">
|
|
<div className="flex items-center gap-3">
|
|
<Link href="/history" className="p-1 -ml-1 rounded-lg active:bg-white/[0.04]">
|
|
<ArrowLeft size={20} style={{ color: "var(--text-2)" }} />
|
|
</Link>
|
|
<h1 className="text-[15px] font-medium" style={{ color: "var(--text-1)" }}>New Session</h1>
|
|
</div>
|
|
|
|
<p className="text-[12px]" style={{ color: "var(--text-3)" }}>
|
|
Creates a new web session and sends your first message.
|
|
</p>
|
|
|
|
<textarea
|
|
value={message}
|
|
onChange={(e) => setMessage(e.target.value)}
|
|
placeholder="What do you need?"
|
|
className="w-full min-h-[140px] p-4 rounded-2xl text-[14px] resize-none outline-none transition-colors leading-relaxed"
|
|
style={{
|
|
background: "var(--bg-raised)",
|
|
border: "1px solid var(--border)",
|
|
color: "var(--text-1)",
|
|
}}
|
|
autoFocus
|
|
disabled={sending}
|
|
onKeyDown={(e) => { if (e.key === "Enter" && e.metaKey) create(); }}
|
|
/>
|
|
|
|
<button
|
|
onClick={create}
|
|
disabled={!message.trim() || sending}
|
|
className="btn-accent w-full flex items-center justify-center gap-2"
|
|
>
|
|
{sending ? (
|
|
<><Loader2 size={16} className="animate-spin" /> Creating session...</>
|
|
) : (
|
|
<><Send size={16} /> Send</>
|
|
)}
|
|
</button>
|
|
|
|
{sending && (
|
|
<p className="text-[12px] text-center" style={{ color: "var(--text-3)" }}>
|
|
This may take a moment — Hermes is processing your message.
|
|
</p>
|
|
)}
|
|
</div>
|
|
);
|
|
}
|