import { type CommonReservedFields, type NoReservedFields, defaultGqlPermission, defaultPermission, } from "@tailor-platform/erp-kit/core"; import { db, type TailorAnyDBField, type TailorAnyDBType } from "@tailor-platform/sdk"; import { notificationCategory } from "./notificationCategory"; import { notificationChannel } from "./notificationChannel"; const builtins = (params: { userType?: TailorAnyDBType }) => { const userId = db.uuid().description("Foreign key to User who owns this preference row"); return { userId: params.userType ? userId.relation({ type: "n-1", toward: { type: params.userType, as: "user" }, backward: "notificationPreferences", }) : userId, categoryId: db .uuid() .relation({ type: "n-1", toward: { type: notificationCategory, as: "category" }, backward: "notificationPreferences", }) .description("Foreign key to NotificationCategory bucket"), channelId: db .uuid() .relation({ type: "n-1", toward: { type: notificationChannel, as: "channel" }, backward: "notificationPreferences", }) .description("Foreign key to NotificationChannel"), allowed: db .bool() .description("User opt-in flag for the (category, channel) pair; false means opted out"), }; }; type ReservedFields = keyof ReturnType | CommonReservedFields; export interface CreateNotificationPreferenceTypeParams< F extends Record, > { fields?: NoReservedFields; userType?: TailorAnyDBType; } export function createNotificationPreferenceType>( params: CreateNotificationPreferenceTypeParams, ) { return db .table("NotificationPreference", { ...builtins(params), ...((params.fields ?? {}) as F), ...db.fields.timestamps(), }) .indexes({ fields: ["userId", "categoryId", "channelId"], unique: true, name: "notification_preference_unique_idx", }) .permission(defaultPermission) .gqlPermission(defaultGqlPermission); } export const notificationPreference = createNotificationPreferenceType({});