diff --git a/src/lib/getUniqueMonths.ts b/src/lib/getUniqueMonths.ts new file mode 100644 index 0000000..eb2ed49 --- /dev/null +++ b/src/lib/getUniqueMonths.ts @@ -0,0 +1,17 @@ +import db from "../config/db"; +import redis from "../config/redis"; + +const CACHE_TTL = 60 * 60 * 24; // 1 day in seconds + +export const getUniqueMonths = async (collection, key = "month") => { + const CACHE_KEY = `${collection}:months`; + + let months: string[] = await redis.smembers(CACHE_KEY); + if (months.length === 0) { + months = await db.collection(collection).distinct(key); + await redis.sadd(CACHE_KEY, ...months); + await redis.expire(CACHE_KEY, CACHE_TTL); + } + + return months.sort((a, b) => b.localeCompare(a)); +}; diff --git a/src/types/index.ts b/src/types/index.ts index 0911bdf..bf6bc2d 100644 --- a/src/types/index.ts +++ b/src/types/index.ts @@ -36,7 +36,6 @@ export interface LatestMonth { } export type Make = Car["make"]; -export type Month = Car["month"]; export enum Collection { Cars = "cars", diff --git a/src/v1/routes/cars.ts b/src/v1/routes/cars.ts index 180de3a..fa675c0 100644 --- a/src/v1/routes/cars.ts +++ b/src/v1/routes/cars.ts @@ -2,12 +2,15 @@ import { Hono } from "hono"; import db from "../../config/db"; import redis from "../../config/redis"; import type { Car, Make } from "../../types"; +import { Collection } from "../../types"; import { HYBRID_REGEX } from "../../config"; import type { WithId } from "mongodb"; +import { getUniqueMonths } from "../../lib/getUniqueMonths"; +import { groupMonthsByYear } from "../../lib/groupMonthsByYear"; const app = new Hono(); -const collection = db.collection("cars"); +const collection = db.collection(Collection.Cars); interface QueryParams { month?: string; @@ -69,6 +72,17 @@ app.get("/", async (c) => { return c.json(cars); }); +app.get("/months", async (c) => { + const { grouped } = c.req.query(); + + const months = await getUniqueMonths(Collection.Cars); + if (grouped) { + return c.json(groupMonthsByYear(months)); + } + + return c.json(months); +}); + app.get("/makes", async (c) => { const CACHE_KEY = "makes"; const CACHE_TTL = 60 * 60 * 24; // 1 day in seconds diff --git a/src/v1/routes/coe.ts b/src/v1/routes/coe.ts index a0964b0..1bd41c2 100644 --- a/src/v1/routes/coe.ts +++ b/src/v1/routes/coe.ts @@ -6,6 +6,8 @@ import { Collection, OrderBy } from "../../types"; import redis from "../../config/redis"; import { getLatestMonth } from "../../lib/getLatestMonth"; import { isValid, parse } from "date-fns"; +import { getUniqueMonths } from "../../lib/getUniqueMonths"; +import { groupMonthsByYear } from "../../lib/groupMonthsByYear"; type QueryParams = { sort?: string; @@ -85,6 +87,17 @@ app.get("/", async (c) => { return c.json(result); }); +app.get("/months", async (c) => { + const { grouped } = c.req.query(); + + const months = await getUniqueMonths(Collection.COE); + if (grouped) { + return c.json(groupMonthsByYear(months)); + } + + return c.json(months); +}); + app.get("/latest", async (c) => { const CACHE_KEY = `coe:latest`; const cachedData = await getCachedData(CACHE_KEY); diff --git a/src/v1/routes/months.ts b/src/v1/routes/months.ts index a3aec5b..4323762 100644 --- a/src/v1/routes/months.ts +++ b/src/v1/routes/months.ts @@ -1,34 +1,8 @@ import { Hono } from "hono"; -import db from "../../config/db"; import { getLatestMonth } from "../../lib/getLatestMonth"; -import { groupMonthsByYear } from "../../lib/groupMonthsByYear"; -import type { Car, Month } from "../../types"; -import redis from "../../config/redis"; const app = new Hono(); -app.get("/", async (c) => { - const CACHE_KEY = "months"; - const CACHE_TTL = 60 * 60 * 24; // 1 day in seconds - - const grouped = c.req.query("grouped"); - - let months: Month[] = await redis.smembers(CACHE_KEY); - if (months.length === 0) { - months = await db.collection("cars").distinct("month"); - await redis.sadd(CACHE_KEY, ...months); - await redis.expire(CACHE_KEY, CACHE_TTL); - } - - months.sort((a, b) => b.localeCompare(a)); - - if (grouped) { - return c.json(groupMonthsByYear(months)); - } - - return c.json(months); -}); - app.get("/latest", async (c) => { const collection = c.req.query("collection"); const dbCollections = ["cars", "coe"];