Kyoo/api/src/controllers/movies.ts
2025-01-10 12:16:32 +01:00

75 lines
1.8 KiB
TypeScript

import { Elysia, t } from "elysia";
import { Movie, MovieTranslation } from "../models/movie";
import { db } from "../db";
import { shows, showTranslations } from "../db/schema/shows";
import { eq, and, sql, or, inArray } from "drizzle-orm";
import { getColumns } from "../db/schema/utils";
import { bubble } from "../models/examples";
const translations = db
.selectDistinctOn([showTranslations.language])
.from(showTranslations)
.where(
or(
inArray(showTranslations.language, sql.placeholder("langs")),
eq(showTranslations.language, shows.originalLanguage),
),
)
.orderBy(
sql`array_position(${showTranslations.language}, ${sql.placeholder("langs")})`,
)
.as("t");
const { pk: _, kind, startAir, endAir, ...moviesCol } = getColumns(shows);
const { pk, language, ...translationsCol } = getColumns(translations);
const findMovie = db
.select({
...moviesCol,
airDate: startAir,
translations: translationsCol,
})
.from(shows)
.innerJoin(translations, eq(shows.pk, translations.pk))
.where(
and(
eq(shows.kind, "movie"),
or(
eq(shows.id, sql.placeholder("id")),
eq(shows.slug, sql.placeholder("id")),
),
),
)
.orderBy()
.limit(1)
.prepare("findMovie");
export const movies = new Elysia({ prefix: "/movies", tags: ["movies"] })
.model({
movie: Movie,
"movie-translation": MovieTranslation,
error: t.Object({}),
})
.guard({
params: t.Object({
id: t.String({
description: "The id or slug of the movie to retrieve",
examples: [bubble.slug],
}),
}),
response: { 200: "movie", 404: "error" },
})
.get(
"/:id",
async ({ params: { id }, error }) => {
const ret = await findMovie.execute({ id });
if (ret.length !== 1) return error(404, {});
return ret[0];
},
{
detail: {
description: "Get a movie by id or slug",
},
},
);