···22import { z } from "zod";
3344import { analytics, trackAnalytics } from "@openstatus/analytics";
55-import { and, eq, inArray } from "@openstatus/db";
55+import { and, eq, inArray, sql } from "@openstatus/db";
66import {
77 insertPageSchemaWithMonitors,
88 monitor,
···232232233233 // public if we use trpc hooks to get the page from the url
234234 getPageBySlug: publicProcedure
235235- .input(z.object({ slug: z.string() }))
235235+ .input(z.object({ slug: z.string().toLowerCase() }))
236236 .query(async (opts) => {
237237 const result = await opts.ctx.db.query.page.findFirst({
238238- where: eq(page.slug, opts.input.slug),
238238+ where: sql`lower(${page.slug}) = ${opts.input.slug}`,
239239 with: { incidents: true },
240240 });
241241···273273 }),
274274275275 getSlugUniqueness: protectedProcedure
276276- .input(z.object({ slug: z.string() }))
276276+ .input(z.object({ slug: z.string().toLowerCase() }))
277277 .query(async (opts) => {
278278 // had filter on some words we want to keep for us
279279 if (["api", "app", "www", "docs"].includes(opts.input.slug)) {
280280 return false;
281281 }
282282 const result = await opts.ctx.db.query.page.findMany({
283283- where: eq(page.slug, opts.input.slug),
283283+ where: sql`lower(${page.slug}) = ${opts.input.slug}`,
284284 });
285285 return result?.length > 0 ? false : true;
286286 }),
+1
packages/db/src/schema/page.ts
···5454 customDomain: z.string().optional().default(""),
5555 monitors: z.array(z.number()).optional(),
5656 workspaceSlug: z.string().optional(),
5757+ slug: z.string().toLowerCase(),
5758});
5859// Schema for selecting a Page - can be used to validate API responses
5960export const selectPageSchema = createSelectSchema(page);