/// import { action, computed, Default, NAME, pattern, Stream, UI, type VNode, Writable, } from "commontools"; export type ItemType = "book" | "article" | "paper" | "video"; export type ItemStatus = "want" | "reading" | "finished" | "abandoned"; /** Input for creating a new reading item detail piece */ interface ReadingItemDetailInput { title?: Writable>; author?: Writable>; url?: Writable>; type?: Writable>; status?: Writable>; rating?: Writable>; notes?: Writable>; addedAt?: Default; finishedAt?: Default; } /** Output shape of the reading item piece - this is what gets stored in lists * #book #article #reading */ interface ReadingItemDetailOutput { [NAME]: string; [UI]: VNode; title: string; author: string; url: string; type: ItemType; status: ItemStatus; rating: number | null; notes: string; summary: string; addedAt: number; finishedAt: number | null; // Actions to update properties setStatus: Stream<{ status: ItemStatus }>; setRating: Stream<{ rating: number | null }>; setNotes: Stream<{ notes: string }>; } // Re-export the Output type as ReadingItemPiece for use in collections export type ReadingItemPiece = ReadingItemDetailOutput; export default pattern( ( { title, author, url, type, status, rating, notes, addedAt, finishedAt }, ) => { // Actions to modify properties const setStatus = action( ({ status: newStatus }: { status: ItemStatus }) => { status.set(newStatus); }, ); const setRating = action( ({ rating: newRating }: { rating: number | null }) => { rating.set(newRating); }, ); const setNotes = action(({ notes: newNotes }: { notes: string }) => { notes.set(newNotes); }); return { [NAME]: computed(() => `Reading: ${title.get() || "New Item"}`), [UI]: ( {computed(() => title.get() || "New Item")} ), title, author, url, type, status, rating, notes, summary: computed(() => { const parts = [title.get()]; if (author.get()) parts.push(`by ${author.get()}`); parts.push(`(${status.get()})`); if (notes.get()) parts.push(notes.get().slice(0, 150)); return parts.join(" "); }), addedAt, finishedAt, setStatus, setRating, setNotes, }; }, );