Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 4 additions & 2 deletions lib/ranking.ts
Original file line number Diff line number Diff line change
Expand Up @@ -118,6 +118,7 @@ export async function getTrendingStorylines(
supabase: SupabaseClient,
limit = 20,
writerType?: number,
offset = 0,
): Promise<RankedStoryline[]> {
const { storylines, ratingMap } = await fetchCandidatesAndRatings(supabase, writerType);
if (storylines.length === 0) return [];
Expand All @@ -141,7 +142,7 @@ export async function getTrendingStorylines(
);

enriched.sort((a, b) => b.trendScore - a.trendScore);
return enriched.slice(0, limit);
return enriched.slice(offset, offset + limit);
}

/**
Expand All @@ -157,6 +158,7 @@ export async function getRisingStorylines(
supabase: SupabaseClient,
limit = 20,
writerType?: number,
offset = 0,
): Promise<RankedStoryline[]> {
const { storylines } = await fetchCandidatesAndRatings(supabase, writerType);
if (storylines.length === 0) return [];
Expand Down Expand Up @@ -260,5 +262,5 @@ export async function getRisingStorylines(
});

enriched.sort((a, b) => b.trendScore - a.trendScore);
return enriched.filter((s) => s.trendScore > 1).slice(0, limit);
return enriched.filter((s) => s.trendScore > 1).slice(offset, offset + limit);
}
51 changes: 44 additions & 7 deletions src/app/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,27 +12,30 @@

const WRITER_VALUES: WriterFilterValue[] = ["all", "human", "agent"];

type SearchParams = Promise<{ tab?: string; writer?: string }>;
const PAGE_SIZE = 24;

type SearchParams = Promise<{ tab?: string; writer?: string; page?: string }>;

export default async function Home({
searchParams,
}: {
searchParams: SearchParams;
}) {
const { tab: rawTab, writer: rawWriter } = await searchParams;
const { tab: rawTab, writer: rawWriter, page: rawPage } = await searchParams;
const tab: Tab = TABS.includes(rawTab as Tab) ? (rawTab as Tab) : "new";
const writer: WriterFilterValue = WRITER_VALUES.includes(
rawWriter as WriterFilterValue,
)
? (rawWriter as WriterFilterValue)
: "all";
const page = Math.max(1, parseInt(rawPage ?? "1", 10) || 1);

const supabase = createServerClient();

let storylines: Storyline[] = [];
const previews: Record<number, string> = {};
if (supabase) {
storylines = await queryTab(supabase, tab, writer);
storylines = await queryTab(supabase, tab, writer, page);
// Fetch genesis plot previews
if (storylines.length > 0) {
// eslint-disable-next-line @typescript-eslint/no-explicit-any
Expand All @@ -48,7 +51,7 @@
}
}

const extraParams = writer !== "all" ? { writer } : undefined;

Check warning on line 54 in src/app/page.tsx

View workflow job for this annotation

GitHub Actions / lint-and-typecheck

'extraParams' is assigned a value but never used

return (
<div className="mx-auto max-w-5xl px-6 py-10">
Expand All @@ -75,6 +78,29 @@
))}
</div>

{/* Pagination */}
{(page > 1 || storylines.length === PAGE_SIZE) && (
<div className="mt-8 flex items-center justify-center gap-4">
{page > 1 && (
<Link
href={buildPageHref(tab, writer, page - 1)}
className="border-border text-muted hover:text-foreground rounded border px-4 py-2 text-xs transition-colors"
>
&larr; Previous
</Link>
)}
<span className="text-muted text-xs">Page {page}</span>
{storylines.length === PAGE_SIZE && (
<Link
href={buildPageHref(tab, writer, page + 1)}
className="border-border text-muted hover:text-foreground rounded border px-4 py-2 text-xs transition-colors"
>
Next &rarr;
</Link>
)}
</div>
)}

{storylines.length === 0 && (
<section className="flex flex-col items-center gap-4 py-16 text-center">
<div className="border-border text-muted rounded border px-4 py-3 text-xs">
Expand All @@ -95,11 +121,22 @@
);
}

function buildPageHref(tab: string, writer: string, page: number): string {
const params = new URLSearchParams({ tab });
if (writer !== "all") params.set("writer", writer);
if (page > 1) params.set("page", String(page));
return `/?${params.toString()}`;
}

async function queryTab(
supabase: ReturnType<typeof createServerClient> & object,
tab: Tab,
writer: WriterFilterValue,
page: number,
): Promise<Storyline[]> {
const from = (page - 1) * PAGE_SIZE;
const to = from + PAGE_SIZE - 1;

switch (tab) {
case "new": {
let q = supabase
Expand All @@ -111,7 +148,7 @@
if (writer === "agent") q = q.eq("writer_type", 1);
const { data } = await q
.order("block_timestamp", { ascending: false })
.limit(50)
.range(from, to)
.returns<Storyline[]>();
return data ?? [];
}
Expand All @@ -126,19 +163,19 @@
if (writer === "agent") q = q.eq("writer_type", 1);
const { data } = await q
.order("plot_count", { ascending: false })
.limit(50)
.range(from, to)
.returns<Storyline[]>();
return data ?? [];
}

case "trending": {
const wt = writer === "human" ? 0 : writer === "agent" ? 1 : undefined;
return getTrendingStorylines(supabase, 20, wt);
return getTrendingStorylines(supabase, PAGE_SIZE, wt, from);
}

case "rising": {
const wt = writer === "human" ? 0 : writer === "agent" ? 1 : undefined;
return getRisingStorylines(supabase, 20, wt);
return getRisingStorylines(supabase, PAGE_SIZE, wt, from);
}
}
}
Loading