44 lines
1.5 KiB
TypeScript
44 lines
1.5 KiB
TypeScript
import { and, eq } from "drizzle-orm";
|
|
import { playbackProgress, type PlaybackProgress } from "@app/models";
|
|
import { db } from "@app/db";
|
|
|
|
export const playbackProgressDao = {
|
|
async get(userId: string, mediaItemId: string): Promise<PlaybackProgress | null> {
|
|
const [row] = await db
|
|
.select()
|
|
.from(playbackProgress)
|
|
.where(
|
|
and(
|
|
eq(playbackProgress.userId, userId),
|
|
eq(playbackProgress.mediaItemId, mediaItemId),
|
|
),
|
|
)
|
|
.limit(1);
|
|
return row ?? null;
|
|
},
|
|
async upsert(
|
|
userId: string,
|
|
mediaItemId: string,
|
|
positionMs: number,
|
|
durationMs: number,
|
|
): Promise<PlaybackProgress> {
|
|
const existing = await this.get(userId, mediaItemId);
|
|
if (existing) {
|
|
const [row] = await db
|
|
.update(playbackProgress)
|
|
.set({ positionMs, durationMs, updatedAt: new Date() })
|
|
.where(eq(playbackProgress.id, existing.id))
|
|
.returning();
|
|
if (!row) throw new Error("Failed to update progress");
|
|
return row;
|
|
}
|
|
const rows = await db
|
|
.insert(playbackProgress)
|
|
.values({ userId, mediaItemId, positionMs, durationMs })
|
|
.returning();
|
|
const row = rows[0];
|
|
if (!row) throw new Error("Failed to insert progress");
|
|
return row;
|
|
},
|
|
};
|