diff --git a/src/app/(dashboard)/jobs/[jobId]/page.tsx b/src/app/(dashboard)/jobs/[jobId]/page.tsx index 75a0004..5eab726 100644 --- a/src/app/(dashboard)/jobs/[jobId]/page.tsx +++ b/src/app/(dashboard)/jobs/[jobId]/page.tsx @@ -7,6 +7,7 @@ import { Button } from "@/components/ui/button"; import { Card, CardContent, CardDescription, CardHeader, CardTitle } from "@/components/ui/card"; import { listJobFiles } from "@/lib/appwrite/job-file-queries"; import { listJobHistory } from "@/lib/appwrite/job-history-queries"; +import { toPlain } from "@/lib/appwrite/serialize"; import { JOB_STATUS_LABELS, JOB_STEP_LABELS, @@ -57,7 +58,7 @@ export default async function JobDetailPage({ let job: Job; try { const row = await tablesDB.getRow(DATABASE_ID, TABLES.jobs, jobId); - job = row as unknown as Job; + job = toPlain(row as unknown as Job); } catch { notFound(); } diff --git a/src/lib/appwrite/connection-queries.ts b/src/lib/appwrite/connection-queries.ts index 31ad8f5..91185f7 100644 --- a/src/lib/appwrite/connection-queries.ts +++ b/src/lib/appwrite/connection-queries.ts @@ -10,6 +10,7 @@ import { type TenantSettings, } from "./schema"; import { createAdminClient } from "./server"; +import { toPlain } from "./serialize"; export type CounterpartTenant = { tenantId: string; @@ -54,10 +55,12 @@ async function enrich( new Set(rows.map((r) => counterpartTenantId(r, selfTenantId))), ); const map = await fetchCounterparts(counterpartIds); - return rows.map((r) => ({ - ...r, - counterpart: map.get(counterpartTenantId(r, selfTenantId)) ?? null, - })); + return toPlain( + rows.map((r) => ({ + ...r, + counterpart: map.get(counterpartTenantId(r, selfTenantId)) ?? null, + })), + ); } async function listConnectionsByStatus( diff --git a/src/lib/appwrite/dashboard-queries.ts b/src/lib/appwrite/dashboard-queries.ts index 2f61a30..a203e3c 100644 --- a/src/lib/appwrite/dashboard-queries.ts +++ b/src/lib/appwrite/dashboard-queries.ts @@ -12,6 +12,7 @@ import { type TenantSettings, } from "./schema"; import { createAdminClient } from "./server"; +import { toPlain } from "./serialize"; export type DashboardJob = Job & { counterpartName: string | null; @@ -140,7 +141,7 @@ export async function getDashboardData( if (e.type === "payable") payablePending += e.amount; } - return { + return toPlain({ openJobsCount: openJobsRes.total, pendingActionCount: pendingActionRes.total, unreadCount: unreadRes.total, @@ -154,5 +155,5 @@ export async function getDashboardData( counterpartMap.get(isLab ? j.clinicTenantId : j.labTenantId) ?? null, })), recentNotifications: notifRes.rows as unknown as Notification[], - }; + }); } diff --git a/src/lib/appwrite/finance-queries.ts b/src/lib/appwrite/finance-queries.ts index 1df10cd..e8b980f 100644 --- a/src/lib/appwrite/finance-queries.ts +++ b/src/lib/appwrite/finance-queries.ts @@ -10,6 +10,7 @@ import { type TenantSettings, } from "./schema"; import { createAdminClient } from "./server"; +import { toPlain } from "./serialize"; export type FinanceCounterpart = { tenantId: string; @@ -40,7 +41,7 @@ export async function listFinanceEntries( new Set(rows.map((r) => r.counterpartTenantId).filter((v): v is string => Boolean(v))), ); if (counterpartIds.length === 0) { - return rows.map((r) => ({ ...r, counterpart: null })); + return toPlain(rows.map((r) => ({ ...r, counterpart: null }))); } const counterpartsRes = await tablesDB.listRows({ @@ -57,10 +58,12 @@ export async function listFinanceEntries( }); } - return rows.map((r) => ({ - ...r, - counterpart: r.counterpartTenantId ? map.get(r.counterpartTenantId) ?? null : null, - })); + return toPlain( + rows.map((r) => ({ + ...r, + counterpart: r.counterpartTenantId ? map.get(r.counterpartTenantId) ?? null : null, + })), + ); } export function summarizeFinance( diff --git a/src/lib/appwrite/job-file-queries.ts b/src/lib/appwrite/job-file-queries.ts index b43113e..5884000 100644 --- a/src/lib/appwrite/job-file-queries.ts +++ b/src/lib/appwrite/job-file-queries.ts @@ -4,6 +4,7 @@ import { Query } from "node-appwrite"; import { BUCKETS, DATABASE_ID, TABLES, type JobFile } from "./schema"; import { createAdminClient } from "./server"; +import { toPlain } from "./serialize"; import { getFileViewUrl } from "./storage"; export type JobFileWithUrl = JobFile & { @@ -22,8 +23,10 @@ export async function listJobFiles(jobId: string): Promise { ], }); const rows = result.rows as unknown as JobFile[]; - return rows.map((r) => ({ - ...r, - url: getFileViewUrl(BUCKETS.jobFiles, r.fileId), - })); + return toPlain( + rows.map((r) => ({ + ...r, + url: getFileViewUrl(BUCKETS.jobFiles, r.fileId), + })), + ); } diff --git a/src/lib/appwrite/job-history-queries.ts b/src/lib/appwrite/job-history-queries.ts index 0256cf7..0cd334c 100644 --- a/src/lib/appwrite/job-history-queries.ts +++ b/src/lib/appwrite/job-history-queries.ts @@ -4,6 +4,7 @@ import { Query } from "node-appwrite"; import { DATABASE_ID, TABLES, type JobStatusHistory } from "./schema"; import { createAdminClient } from "./server"; +import { toPlain } from "./serialize"; export async function listJobHistory(jobId: string): Promise { const { tablesDB } = createAdminClient(); @@ -16,5 +17,5 @@ export async function listJobHistory(jobId: string): Promise Query.limit(100), ], }); - return result.rows as unknown as JobStatusHistory[]; + return toPlain(result.rows as unknown as JobStatusHistory[]); } diff --git a/src/lib/appwrite/job-queries.ts b/src/lib/appwrite/job-queries.ts index cea378b..2dc8e13 100644 --- a/src/lib/appwrite/job-queries.ts +++ b/src/lib/appwrite/job-queries.ts @@ -10,6 +10,7 @@ import { type TenantSettings, } from "./schema"; import { createAdminClient } from "./server"; +import { toPlain } from "./serialize"; export type JobCounterpart = { tenantId: string; @@ -58,7 +59,7 @@ export async function listInboundJobs(labTenantId: string): Promise j.clinicTenantId)))); - return jobs.map((j) => enrichJob(j, j.clinicTenantId, map)); + return toPlain(jobs.map((j) => enrichJob(j, j.clinicTenantId, map))); } /** Outbound for a clinic tenant — jobs the clinic has sent. */ @@ -75,7 +76,7 @@ export async function listOutboundJobs(clinicTenantId: string): Promise j.labTenantId)))); - return jobs.map((j) => enrichJob(j, j.labTenantId, map)); + return toPlain(jobs.map((j) => enrichJob(j, j.labTenantId, map))); } /** For clinic's "Yeni İş Yayınla" form: list approved labs they can send to. */ @@ -96,7 +97,9 @@ export async function listApprovedLabsForClinic( (r) => r.labTenantId, ); const map = await fetchTenants(labIds); - return labIds - .map((id) => map.get(id)) - .filter((v): v is JobCounterpart => Boolean(v)); + return toPlain( + labIds + .map((id) => map.get(id)) + .filter((v): v is JobCounterpart => Boolean(v)), + ); } diff --git a/src/lib/appwrite/notification-helpers.ts b/src/lib/appwrite/notification-helpers.ts index e11ab4a..8c67e9a 100644 --- a/src/lib/appwrite/notification-helpers.ts +++ b/src/lib/appwrite/notification-helpers.ts @@ -4,6 +4,7 @@ import { ID, Permission, Query, Role } from "node-appwrite"; import { DATABASE_ID, TABLES, type Notification } from "./schema"; import { createAdminClient } from "./server"; +import { toPlain } from "./serialize"; type CreateNotificationInput = { tenantId: string; @@ -76,5 +77,5 @@ export async function listNotifications( Query.limit(limit), ], }); - return result.rows as unknown as Notification[]; + return toPlain(result.rows as unknown as Notification[]); } diff --git a/src/lib/appwrite/prosthetic-queries.ts b/src/lib/appwrite/prosthetic-queries.ts index bdbc6fc..8df77fd 100644 --- a/src/lib/appwrite/prosthetic-queries.ts +++ b/src/lib/appwrite/prosthetic-queries.ts @@ -4,6 +4,7 @@ import { Query } from "node-appwrite"; import { DATABASE_ID, TABLES, type Prosthetic } from "./schema"; import { createAdminClient } from "./server"; +import { toPlain } from "./serialize"; export async function listProsthetics(tenantId: string): Promise { const { tablesDB } = createAdminClient(); @@ -16,7 +17,7 @@ export async function listProsthetics(tenantId: string): Promise { Query.limit(200), ], }); - return result.rows as unknown as Prosthetic[]; + return toPlain(result.rows as unknown as Prosthetic[]); } export async function listActiveProsthetics(tenantId: string): Promise { @@ -31,5 +32,5 @@ export async function listActiveProsthetics(tenantId: string): Promise(value: T): T { + return JSON.parse(JSON.stringify(value)) as T; +}