'use client'; import { useEffect, useState, useCallback } from 'react'; import { useParams, useRouter } from 'next/navigation'; import Link from 'next/link'; import { NoteCard } from '@/components/NoteCard'; import { CanvasEmbed } from '@/components/CanvasEmbed'; import { OpenNotebookEmbed } from '@/components/OpenNotebookEmbed'; import { UserMenu } from '@/components/UserMenu'; import { authFetch } from '@/lib/authFetch'; import type { CanvasShapeMessage } from '@/lib/canvas-sync'; interface NoteData { id: string; title: string; type: string; contentPlain: string | null; isPinned: boolean; updatedAt: string; url: string | null; tags: { tag: { id: string; name: string; color: string | null } }[]; } interface NotebookData { id: string; title: string; description: string | null; coverColor: string; canvasSlug: string | null; isPublic: boolean; notes: NoteData[]; _count: { notes: number }; } export default function NotebookDetailPage() { const params = useParams(); const router = useRouter(); const [notebook, setNotebook] = useState(null); const [loading, setLoading] = useState(true); const [showCanvas, setShowCanvas] = useState(false); const [creatingCanvas, setCreatingCanvas] = useState(false); const [tab, setTab] = useState<'notes' | 'pinned' | 'ai'>('notes'); const fetchNotebook = useCallback(() => { fetch(`/api/notebooks/${params.id}`) .then((res) => res.json()) .then(setNotebook) .catch(console.error) .finally(() => setLoading(false)); }, [params.id]); useEffect(() => { fetchNotebook(); }, [fetchNotebook]); const handleShapeUpdate = useCallback(async (message: CanvasShapeMessage) => { try { await fetch('/api/sync', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ shapeId: message.shapeId, type: message.type, data: message.data, }), }); fetchNotebook(); } catch (err) { console.error('Canvas sync error:', err); } }, [fetchNotebook]); const handleCreateCanvas = async () => { if (creatingCanvas) return; setCreatingCanvas(true); try { const res = await authFetch(`/api/notebooks/${params.id}/canvas`, { method: 'POST' }); if (res.ok) { fetchNotebook(); setShowCanvas(true); } } catch (error) { console.error('Failed to create canvas:', error); } finally { setCreatingCanvas(false); } }; const handleDelete = async () => { if (!confirm('Delete this notebook and all its notes?')) return; await authFetch(`/api/notebooks/${params.id}`, { method: 'DELETE' }); router.push('/notebooks'); }; if (loading) { return (
); } if (!notebook) { return (
Notebook not found
); } const filteredNotes = tab === 'pinned' ? notebook.notes.filter((n) => n.isPinned) : notebook.notes; return (
{/* Notes panel */}
{/* Header */}

{notebook.title}

{notebook.description && (

{notebook.description}

)}

{notebook._count.notes} notes

{/* Tabs */}
{/* Tab content */} {tab === 'ai' ? ( ) : filteredNotes.length === 0 ? (
{tab === 'pinned' ? 'No pinned notes' : 'No notes yet. Add one!'}
) : (
{filteredNotes.map((note) => ( ({ id: nt.tag.id, name: nt.tag.name, color: nt.tag.color, }))} /> ))}
)}
{/* Canvas sidebar — full screen on mobile, split on desktop */} {showCanvas && notebook.canvasSlug && (
Canvas
)}
); }