@m1212e/rumble 0.23.14 → 0.23.15
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/out/index.cjs +2 -2
- package/out/index.cjs.map +1 -1
- package/out/index.mjs +2 -2
- package/out/index.mjs.map +1 -1
- package/package.json +1 -1
package/out/index.mjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.mjs","names":["EmptyFilter","makeDefaultName","packagejson.version","createYoga","nativeCreateYoga"],"sources":["../lib/types/rumbleError.ts","../lib/helpers/asserts.ts","../lib/helpers/mapNullFieldsToUndefined.ts","../package.json","../lib/helpers/mergeFilters.ts","../lib/helpers/sanitizeFilterValue.ts","../lib/helpers/sqlTypes/types.ts","../lib/helpers/sqlTypes/distinctValuesFromSQLType.ts","../lib/helpers/tableHelpers.ts","../lib/abilityBuilder.ts","../lib/args/orderArg.ts","../lib/enum.ts","../lib/helpers/sqlTypes/mapSQLTypeToTSType.ts","../lib/args/whereArg.ts","../lib/client/client.ts","../lib/context.ts","../lib/helpers/protoMapper.ts","../lib/countQuery.ts","../lib/helpers/sofaOpenAPIWebhookDocs.ts","../lib/helpers/errorLogging.ts","../lib/helpers/tracing.ts","../lib/helpers/sqlTypes/mapDrizzleTypeToGraphQlType.ts","../lib/helpers/determineDialectFromSchema.ts","../lib/search.ts","../lib/object.ts","../lib/pubsub.ts","../lib/query.ts","../lib/args/whereArgsImplementer.ts","../lib/runtimeFiltersPlugin/filterTypes.ts","../lib/runtimeFiltersPlugin/runtimeFiltersPlugin.ts","../lib/schemaBuilder.ts","../lib/rumble.ts"],"sourcesContent":["import { GraphQLError } from \"graphql\";\n/**\n * An error that gets raised by rumble whenever something does not go according to plan.\n * Mostly internals, configuration errors or other unexpected things.\n */\nexport class RumbleError extends Error {\n constructor(message: string) {\n super(message);\n this.name = \"RumbleError\";\n }\n}\n\n/**\n * An error that gets raised by rumble whenever an error occurs in a resolver, containing\n * information safely exposeable to the user.\n * E.g. the assert helpers issue these.\n */\nexport class RumbleErrorSafe extends GraphQLError {}\n","import { RumbleErrorSafe } from \"../types/rumbleError\";\n\n/**\n *\n * Helper function to map a drizzle findFirst query result,\n * which may be optional, to a correct drizzle type.\n *\n * @throws RumbleError\n *\n * @example\n *\n * ```ts\n * schemaBuilder.queryFields((t) => {\n return {\n findFirstUser: t.drizzleField({\n type: UserRef,\n resolve: (query, root, args, ctx, info) => {\n return (\n db.query.users\n .findFirst({\n ...query,\n where: ctx.abilities.users.filter(\"read\").single.where,\n })\n // note that we need to manually raise an error if the value is not found\n .then(assertFindFirstExists)\n );\n },\n }),\n };\n });\n * ```\n */\nexport const assertFindFirstExists = <T>(value: T | undefined): T => {\n if (!value) {\n throw new RumbleErrorSafe(\"Value not found but required (findFirst)\");\n }\n return value;\n};\n\n/**\n *\n * Helper function to map a drizzle findFirst query result,\n * which may be optional, to a correct drizzle type.\n *\n * @throws RumbleError\n *\n * @example\n *\n * ```ts\n schemaBuilder.mutationFields((t) => {\n return {\n updateUsername: t.drizzleField({\n type: UserRef,\n args: {\n userId: t.arg.int({ required: true }),\n newName: t.arg.string({ required: true }),\n },\n resolve: (query, root, args, ctx, info) => {\n return db\n .update(schema.users)\n .set({\n name: args.newName,\n })\n .where(\n and(\n eq(schema.users.id, args.userId),\n ctx.abilities.users.filter(\"update\").single.where\n )\n )\n .returning({ id: schema.users.id, name: schema.users.name })\n // note that we need to manually raise an error if the value is not found\n .then(assertFirstEntryExists);\n },\n }),\n };\n });\n * ```\n */\nexport const assertFirstEntryExists = <T>(value: T[]): T => {\n const v = value.at(0);\n if (!v)\n throw new RumbleErrorSafe(\"Value not found but required (firstEntry)\");\n return v;\n};\n","/**\n * Helper to map null fields to undefined\n * @param obj The object to map\n * @returns The mapped object with all fields of 'null' transformed to 'undefined'\n * \n * This becomes useful for update mutations where you do not want to pass null (unset value in db)\n * but undefined (do not touch value in db) in case of a value not beeing set in the args of said mutation\n * @example\n * ```ts\n * updateUser: t.drizzleField({\n type: User,\n args: {\n id: t.arg.string({ required: true }),\n email: t.arg.string(),\n lastName: t.arg.string(),\n firstName: t.arg.string(),\n },\n resolve: async (query, root, args, ctx, info) => {\n const mappedArgs = mapNullFieldsToUndefined(args);\n const user = await db.transaction(async (tx) => {\n const user = await tx\n .update(schema.user)\n .set({\n\n // email: args.email ?? undefined,\n // lastName: args.lastName ?? undefined,\n // firstName: args.firstName ?? undefined,\n\n // becomes this\n\n email: mappedArgs.email,\n lastName: mappedArgs.lastName,\n firstName: mappedArgs.firstName,\n })\n .returning()\n .then(assertFirstEntryExists);\n return user;\n });\n\n pubsub.updated(user.id);\n\n return db.query.user\n .findFirst(\n query(\n ctx.abilities.user.filter('read').merge(\n {\n where: { id: user.id },\n }\n 1).query.single,\n ),\n )\n .then(assertFindFirstExists);\n },\n }),\n * \n * \n * ```\n */\nexport function mapNullFieldsToUndefined<T extends object>(obj: T) {\n return Object.fromEntries(\n Object.entries(obj).map(([key, value]) => [\n key,\n value === null ? undefined : value,\n ]),\n ) as {\n [K in keyof T]: T[K] extends null ? undefined : Exclude<T[K], null>;\n };\n}\n","","import { toMerged } from \"es-toolkit\";\n\n// See the comment on `EmptyFilter` in `./sanitizeFilterValue.ts` for why this\n// is recreated locally instead of imported from drizzle-orm.\nconst EmptyFilter = Symbol.for(\"drizzle:EmptyFilter\");\n\n/**\n * Normalizes drizzle-orm's `EmptyFilter` sentinel to `undefined` so it's\n * treated as \"no filter\" rather than a real filter value to combine with\n * AND/OR — otherwise merging an unrestricted (EmptyFilter) base filter with\n * a real `where` would needlessly wrap it as `{ AND: [EmptyFilter, where] }`\n * instead of just `where`.\n */\nfunction realWhere(where: unknown) {\n return where === EmptyFilter ? undefined : where;\n}\n\nexport function mergeFilters<\n FilterA extends Record<string, any>,\n FilterB extends Record<string, any>,\n>(\n filterA?: Partial<FilterA>,\n filterB?: Partial<FilterB>,\n mode: \"AND\" | \"OR\" = \"AND\",\n) {\n const filterAWhere = realWhere(filterA?.where);\n const filterBWhere = realWhere(filterB?.where);\n\n const where =\n filterAWhere && filterBWhere\n ? mode === \"OR\"\n ? { OR: [filterAWhere, filterBWhere] }\n : { AND: [filterAWhere, filterBWhere] }\n : (filterAWhere ?? filterBWhere);\n\n const columns =\n filterA?.columns || filterB?.columns\n ? new Set(\n [\n Object.entries(filterA?.columns ?? {}),\n Object.entries(filterB?.columns ?? {}),\n ]\n .flat()\n .filter(([, v]) => v === true)\n .map(([k]) => k),\n )\n .entries()\n .reduce(\n (acc, [key]) => {\n acc[key] = true;\n return acc;\n },\n {} as Record<string, true>,\n )\n : undefined;\n\n const extras =\n filterA?.extras || filterB?.extras\n ? toMerged(filterA?.extras ?? {}, filterB?.extras ?? {})\n : undefined;\n\n const orderBy =\n filterA?.orderBy || filterB?.orderBy\n ? toMerged(filterA?.orderBy ?? {}, filterB?.orderBy ?? {})\n : undefined;\n\n const limit =\n mode === \"OR\"\n ? filterA?.limit === undefined || filterB?.limit === undefined\n ? undefined\n : Math.max(filterA.limit, filterB.limit)\n : filterA?.limit || filterB?.limit\n ? Math.min(filterA?.limit ?? Infinity, filterB?.limit ?? Infinity)\n : undefined;\n\n const offset =\n mode === \"OR\"\n ? filterA?.offset === undefined || filterB?.offset === undefined\n ? undefined\n : Math.min(filterA.offset, filterB.offset)\n : filterA?.offset || filterB?.offset\n ? Math.min(filterA?.offset ?? Infinity, filterB?.offset ?? Infinity)\n : undefined;\n\n const with_ =\n filterA?.with || filterB?.with\n ? toMerged(filterA?.with ?? {}, filterB?.with ?? {})\n : undefined;\n\n return {\n where,\n columns,\n extras,\n orderBy,\n limit,\n offset,\n with: with_,\n } as unknown as FilterA & FilterB;\n}\n","const EmptyFilter = Symbol.for(\"drizzle:EmptyFilter\");\n\nfunction isPlainObject(value: unknown): value is Record<string, unknown> {\n if (typeof value !== \"object\" || value === null) return false;\n const proto = Object.getPrototypeOf(value);\n return proto === Object.prototype || proto === null;\n}\n\nexport function sanitizeFilterValue(value: unknown): unknown {\n if (value === undefined) return EmptyFilter;\n if (Array.isArray(value)) return value.map(sanitizeFilterValue);\n if (isPlainObject(value)) {\n return Object.fromEntries(\n Object.entries(value).map(([key, entry]) => [\n key,\n sanitizeFilterValue(entry),\n ]),\n );\n }\n return value;\n}\n","import { RumbleError } from \"../../types/rumbleError\";\n\n/**\n * Strips parameter suffixes like `(256)`, `(10,2)` and timezone modifiers\n * (`with time zone`, `without time zone`) from raw getSQLType() output so\n * every classifier works on the base type name only.\n */\nexport function normalizeSQLType(raw: string): string {\n return raw\n .replace(/\\s*with(?:out)?\\s+time\\s+zone/i, \"\")\n .replace(/\\s*\\([^)]*\\)/, \"\")\n .trim()\n .toLowerCase();\n}\n\nconst intLikeSQLTypeStrings = [\n \"serial\",\n \"int\",\n \"integer\",\n \"tinyint\",\n \"smallint\",\n \"mediumint\",\n \"int2\",\n \"int4\",\n \"smallserial\",\n] as const;\n\nexport function isIntLikeSQLTypeString(sqlType: string): boolean {\n return intLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst bigIntLikeSQLTypeStrings = [\n \"bigint\",\n \"bigserial\",\n \"int8\",\n \"bigint unsigned\",\n] as const;\n\nexport function isBigIntLikeSQLTypeString(sqlType: string): boolean {\n return bigIntLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst floatLikeSQLTypeStrings = [\n \"real\",\n \"decimal\",\n \"double\",\n \"float\",\n \"numeric\",\n \"double precision\",\n \"float4\",\n \"float8\",\n \"money\",\n] as const;\n\nexport function isFloatLikeSQLTypeString(sqlType: string): boolean {\n return floatLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst stringLikeSQLTypeStrings = [\n \"string\",\n \"text\",\n \"varchar\",\n \"char\",\n \"character varying\",\n \"character\",\n \"inet\",\n \"cidr\",\n \"macaddr\",\n \"macaddr8\",\n \"interval\",\n \"time\",\n \"year\",\n \"binary\",\n \"varbinary\",\n \"tinytext\",\n \"mediumtext\",\n \"longtext\",\n] as const;\n\nexport function isStringLikeSQLTypeString(sqlType: string): boolean {\n return stringLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst IDLikeSQLTypeStrings = [\"uuid\"] as const;\n\nexport function isIDLikeSQLTypeString(sqlType: string): boolean {\n return IDLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst booleanSQLTypeStrings = [\"boolean\", \"bool\"] as const;\n\nexport function isBooleanSQLTypeString(sqlType: string): boolean {\n return booleanSQLTypeStrings.includes(sqlType as any);\n}\n\nconst dateTimeLikeSQLTypeStrings = [\"timestamp\", \"datetime\"] as const;\n\nexport function isDateTimeLikeSQLTypeString(sqlType: string): boolean {\n return dateTimeLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst dateLikeSQLTypeStrings = [\"date\"] as const;\n\nexport function isDateLikeSQLTypeString(sqlType: string): boolean {\n return dateLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst jsonLikeSQLTypeStrings = [\"json\", \"jsonb\"] as const;\n\nexport function isJSONLikeSQLTypeString(sqlType: string): boolean {\n return jsonLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst jsonFallbackSQLTypeStrings = [\n \"point\",\n \"line\",\n \"lseg\",\n \"box\",\n \"path\",\n \"polygon\",\n \"circle\",\n \"geometry\",\n] as const;\n\nexport function isJSONFallbackSQLTypeString(sqlType: string): boolean {\n return (\n jsonFallbackSQLTypeStrings.includes(sqlType as any) ||\n sqlType.startsWith(\"geometry\")\n );\n}\n\nconst bytesSQLTypeStrings = [\"bytea\", \"blob\"] as const;\n\nexport function isBytesSQLTypeString(sqlType: string): boolean {\n return bytesSQLTypeStrings.includes(sqlType as any);\n}\n\n// PossibleSQLType is intentionally broad — classifiers receive normalized\n// strings and use runtime includes() checks.\nexport type PossibleSQLType = string & {};\n\nexport const UnknownTypeRumbleError = (\n sqlType: string,\n additionalInfo?: string,\n) =>\n new RumbleError(\n `RumbleError: Unknown SQL type '${sqlType}'. Please open an issue (https://github.com/m1212e/rumble/issues) so it can be added. (${additionalInfo})`,\n );\n","import {\n isBooleanSQLTypeString,\n isDateLikeSQLTypeString,\n isDateTimeLikeSQLTypeString,\n isFloatLikeSQLTypeString,\n isIDLikeSQLTypeString,\n isIntLikeSQLTypeString,\n isJSONLikeSQLTypeString,\n isStringLikeSQLTypeString,\n type PossibleSQLType,\n UnknownTypeRumbleError,\n} from \"./types\";\n\nexport function createDistinctValuesFromSQLType(sqlType: PossibleSQLType): {\n value1: any;\n value2: any;\n} {\n if (isIntLikeSQLTypeString(sqlType)) {\n return {\n value1: 1,\n value2: 2,\n };\n }\n\n if (isFloatLikeSQLTypeString(sqlType)) {\n return {\n value1: 1.1,\n value2: 2.2,\n };\n }\n\n if (isStringLikeSQLTypeString(sqlType)) {\n return {\n value1: \"a\",\n value2: \"b\",\n };\n }\n\n if (isIDLikeSQLTypeString(sqlType)) {\n return {\n value1: \"fba31870-5528-42d7-b27e-2e5ee657aea5\",\n value2: \"fc65db81-c2d1-483d-8a25-a30e2cf6e02d\",\n };\n }\n\n if (isBooleanSQLTypeString(sqlType)) {\n return {\n value1: true,\n value2: false,\n };\n }\n\n if (isDateTimeLikeSQLTypeString(sqlType)) {\n return {\n value1: new Date(2022, 1, 1),\n value2: new Date(2022, 1, 2),\n };\n }\n\n if (isDateLikeSQLTypeString(sqlType)) {\n return {\n value1: new Date(2022, 1, 1),\n value2: new Date(2022, 1, 2),\n };\n }\n\n if (isJSONLikeSQLTypeString(sqlType)) {\n return {\n value1: { a: 1 },\n value2: { b: 2 },\n };\n }\n\n throw UnknownTypeRumbleError(sqlType, \"Distinct\");\n}\n","import {\n type Column,\n getTableColumns,\n getTableName,\n is,\n isTable,\n type Many,\n type One,\n type Table,\n} from \"drizzle-orm\";\nimport type { DrizzleInstance } from \"../types/drizzleInstanceType\";\nimport { RumbleError } from \"../types/rumbleError\";\n\ntype RelationEntry = {\n /** TS-level key in db._.relations (i.e. the export name) */\n name: string;\n /** runtime DB table name as returned by getTableName(table) */\n dbName: string;\n /** the underlying drizzle Table object */\n table: any;\n /** columns map for the table */\n columns: Record<string, Column>;\n /** primary key columns, keyed by column ts-name */\n primaryKey: Record<string, Column>;\n /** named relations record (one/many) for this table */\n relations: Record<string, One<any, any> | Many<any>>;\n /**\n * Whether the underlying entity is a genuine drizzle Table (as opposed to a\n * View/MaterializedView)\n */\n isTable: boolean;\n /**\n * The raw entry from db._.relations — preserved for callers that previously\n * read `foundRelation` off tableHelper().\n */\n foundRelation: any;\n};\n\ntype TableIndex = {\n byTsName: Map<string, RelationEntry>;\n byDbName: Map<string, RelationEntry>;\n byTableRef: Map<any, RelationEntry>;\n};\n\nconst indexCache = new WeakMap<object, TableIndex>();\n\nfunction buildIndex<DB extends DrizzleInstance>(db: DB): TableIndex {\n const byTsName = new Map<string, RelationEntry>();\n const byDbName = new Map<string, RelationEntry>();\n const byTableRef = new Map<any, RelationEntry>();\n\n for (const [tsName, rawEntry] of Object.entries(db._.relations ?? {})) {\n const entry = rawEntry as any;\n const tableObj = entry.table;\n if (!tableObj) continue;\n\n const columns = (\n isTable(tableObj) ? getTableColumns(tableObj as Table) : {}\n ) as Record<string, Column>;\n\n const primaryKey = Object.fromEntries(\n Object.entries(columns).filter(([, col]) => (col as any).primary),\n ) as Record<string, Column>;\n\n const dbName = isTable(tableObj)\n ? (getTableName(tableObj as Table) as string)\n : ((entry.name as string) ?? tsName);\n\n const resolved: RelationEntry = {\n name: entry.name ?? tsName,\n dbName,\n table: tableObj,\n columns,\n primaryKey,\n relations: entry.relations ?? {},\n isTable: isTable(tableObj),\n foundRelation: entry,\n };\n\n byTsName.set(resolved.name, resolved);\n byDbName.set(resolved.dbName, resolved);\n byTableRef.set(tableObj, resolved);\n }\n\n return { byTsName, byDbName, byTableRef };\n}\n\nfunction getIndex<DB extends DrizzleInstance>(db: DB): TableIndex {\n let idx = indexCache.get(db as unknown as object);\n if (!idx) {\n idx = buildIndex(db);\n indexCache.set(db as unknown as object, idx);\n }\n return idx;\n}\n\nexport function tableHelper<\n DB extends DrizzleInstance,\n TableIdentifier extends\n | string\n | DB[\"_\"][\"relations\"][keyof DB[\"_\"][\"relations\"]],\n>({ db, table }: { db: DB; table: TableIdentifier }) {\n const idx = getIndex(db);\n\n let entry: RelationEntry | undefined;\n\n if (typeof table === \"string\") {\n // Lookup by TS-level relation name first (the common case), then by DB name.\n entry = idx.byTsName.get(table) ?? idx.byDbName.get(table);\n } else if (table && typeof table === \"object\") {\n const t = table as any;\n\n // Case 1: caller passed an entry from db._.relations directly:resolve by\n // table identity via its `.table` property.\n if (t.table) {\n entry = idx.byTableRef.get(t.table);\n if (!entry && t.name) {\n entry = idx.byTsName.get(t.name) ?? idx.byDbName.get(t.name);\n }\n }\n\n // Case 2: caller passed a raw Table object: resolve by identity.\n if (!entry) {\n entry = idx.byTableRef.get(t);\n }\n\n // Case 3: last resort lookup via the public getTableName() helper.\n if (!entry && isTable(t)) {\n const dbName = getTableName(t as Table) as string;\n entry = idx.byDbName.get(dbName);\n }\n }\n\n if (!entry) {\n throw new RumbleError(\n `Could not find schema for ${JSON.stringify(\n typeof table === \"string\" ? table : \"<table-object>\",\n )}`,\n );\n }\n\n return {\n columns: entry.columns,\n primaryKey: entry.primaryKey,\n relations: entry.relations,\n dbName: entry.dbName,\n tsName: entry.name,\n table: entry.table,\n isTable: entry.isTable,\n foundRelation: entry.foundRelation,\n };\n}\n\n/**\n * Looks up a relation entry by its TS-level name — i.e. the key in\n * db._.relations, which is also what `Relation.targetTableName` carries.\n * Prefer this for cross-relation navigation over re-resolving via the raw\n * `targetTable` object.\n */\nexport function tableHelperByTsName<DB extends DrizzleInstance>(\n db: DB,\n tsName: string,\n) {\n return tableHelper({ db, table: tsName });\n}\n\nexport { is };\n","import type { Span } from \"@opentelemetry/api\";\nimport { relationsFilterToSQL } from \"drizzle-orm\";\nimport { debounce } from \"es-toolkit\";\nimport { lazy } from \"./helpers/lazy\";\nimport { mergeFilters } from \"./helpers/mergeFilters\";\nimport { sanitizeFilterValue } from \"./helpers/sanitizeFilterValue\";\nimport { createDistinctValuesFromSQLType } from \"./helpers/sqlTypes/distinctValuesFromSQLType\";\nimport { tableHelper } from \"./helpers/tableHelpers\";\nimport type {\n Filter,\n FilterPrefetchCombo,\n Prefetch,\n} from \"./runtimeFiltersPlugin/filterTypes\";\nimport type {\n DrizzleInstance,\n DrizzleQueryFunction,\n DrizzleQueryFunctionInput,\n DrizzleTableValueType,\n TableRelationNames,\n} from \"./types/drizzleInstanceType\";\nimport { RumbleError } from \"./types/rumbleError\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n RumbleLogger,\n} from \"./types/rumbleInput\";\n\n//TODO: optimize this for v8 & refactor\n\nexport type AbilityBuilderType<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n> = ReturnType<\n typeof createAbilityBuilder<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >\n>;\n\n/**\n * Static, non changing query filter input type for a specific table\n */\ntype StaticQueryFilter<\n DB extends DrizzleInstance,\n Table extends keyof DrizzleQueryFunction<DB>,\n Filter extends DrizzleQueryFunctionInput<DB, Table>,\n> = Filter;\n\n/**\n * Dynamic, context based query filter input type for a specific table\n */\ntype DynamicQueryFilter<\n DB extends DrizzleInstance,\n Table extends keyof DrizzleQueryFunction<DB>,\n Filter extends DrizzleQueryFunctionInput<DB, Table>,\n Context,\n> = (\n context: Context,\n) => StaticQueryFilter<DB, Table, Filter> | undefined | \"allow\";\n\n/**\n * Combined query filter type for a specific table. May be static or dynamic.\n */\ntype QueryFilter<\n DB extends DrizzleInstance,\n Table extends keyof DrizzleQueryFunction<DB>,\n Filter extends DrizzleQueryFunctionInput<DB, Table>,\n Context,\n> =\n | StaticQueryFilter<DB, Table, Filter>\n | DynamicQueryFilter<DB, Table, Filter, Context>;\n\nfunction isDynamicQueryFilter<\n DB extends DrizzleInstance,\n Table extends keyof DrizzleQueryFunction<DB>,\n Filter extends DrizzleQueryFunctionInput<DB, Table>,\n Context,\n>(\n filter: QueryFilter<DB, Table, Filter, Context>,\n): filter is DynamicQueryFilter<DB, Table, Filter, Context> {\n return (\n typeof filter === \"function\" && filter.constructor.name !== \"AsyncFunction\"\n );\n}\n\nfunction isStaticQueryFilter<\n DB extends DrizzleInstance,\n Table extends keyof DrizzleQueryFunction<DB>,\n Filter extends DrizzleQueryFunctionInput<DB, Table>,\n Context,\n>(\n filter: QueryFilter<DB, Table, Filter, Context>,\n): filter is StaticQueryFilter<DB, Table, Filter> {\n return typeof filter !== \"function\";\n}\n\nconst makeNothingRegisteredWarner = (logger?: RumbleLogger) =>\n debounce((model: string, action: string) => {\n const msg = `No abilities registered for ${model}/${action} — blocking everything. Register the ability or ignore this warning if intentional.`;\n if (logger) {\n logger.warn({ \"rumble.table\": model, \"rumble.action\": action }, msg);\n } else {\n console.warn(msg);\n }\n }, 1000);\n\nexport const createAbilityBuilder = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>({\n db,\n actions,\n defaultLimit,\n otel,\n logger: loggerConfig,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig>) => {\n const log = loggerConfig?.enabled ? loggerConfig.logger : undefined;\n const nothingRegisteredWarningLogger = makeNothingRegisteredWarner(log);\n type TableNames = TableRelationNames<DB>;\n\n // Views/materialized views can appear in db.query (if the caller's schema\n // includes them)\n const tableRelationNames = (\n Object.keys(db.query) as (keyof DrizzleQueryFunction<DB>)[]\n ).filter(\n (name) => tableHelper({ db, table: name as any }).isTable,\n ) as TableNames[];\n\n let hasBeenBuilt = false;\n\n const createBuilderForTable = <TableName extends TableNames>() => {\n const queryFilters = new Map<\n Action,\n | QueryFilter<\n DB,\n TableName,\n DrizzleQueryFunctionInput<DB, TableName>,\n UserContext\n >[]\n | \"unrestricted\"\n >();\n\n const runtimeFilters = new Map<\n Action,\n //TODO add a run all helper\n FilterPrefetchCombo<UserContext, any, any>[]\n >();\n\n // we want to init all possible runtime filters since we want to ensure\n // that the implementaiton helpers pass an object by reference when creating\n // the implementation, instead of a copy like it would be the case with undefined\n for (const action of actions!) {\n if (!runtimeFilters.has(action)) {\n runtimeFilters.set(action, []);\n }\n }\n\n return {\n /**\n * Allows to perform a specific action on a specific entity\n */\n allow: (action: Action | Action[]) => {\n if (hasBeenBuilt) {\n throw new RumbleError(\n \"You can't call allow() after the ability builder has been built. Please ensure that you register all abilities before accessing them.\",\n );\n }\n\n const actions = Array.isArray(action) ? action : [action];\n // Track which actions this specific allow() call initialized as \"unrestricted\",\n // so .when() can distinguish chained use (allow().when()) from a later separate call\n // that finds a pre-existing \"unrestricted\" from a prior bare allow().\n const setUnrestrictedByThisCall = new Set<(typeof actions)[number]>();\n for (const action of actions) {\n let filters = queryFilters.get(action);\n if (!filters) {\n filters = \"unrestricted\";\n queryFilters.set(action, filters);\n setUnrestrictedByThisCall.add(action);\n }\n }\n\n return {\n /**\n * Restricts the allowed actions to a filter\n * @example\n * ```ts\n * abilityBuilder.users.allow([\"read\", \"update\", \"delete\"]).when(({ userId }) => ({\n * where: {\n * id: userId,\n * },\n * }));\n * ```\n */\n when: (\n queryFilter: QueryFilter<\n DB,\n TableName,\n DrizzleQueryFunctionInput<DB, TableName>,\n UserContext\n >,\n ) => {\n for (const action of actions) {\n if (queryFilters.get(action) === \"unrestricted\") {\n if (setUnrestrictedByThisCall.has(action)) {\n // Chained directly on this allow() call — override unrestricted with specific filter\n queryFilters.set(action, []);\n } else {\n // A previous separate bare allow() already set unrestricted\n // skip this filter\n continue;\n }\n }\n const filters = queryFilters.get(action)!;\n (filters as Exclude<typeof filters, \"unrestricted\">).push(\n queryFilter,\n );\n }\n },\n };\n },\n /**\n * Allows to register an application level filter to restrict some results\n * which were returned by a query\n */\n filter: (action: Action | Action[]) => {\n const actions = Array.isArray(action) ? action : [action];\n return {\n /**\n * Allows to register an application level prefetch to fetch some data\n * which could be useful for later filtering the results. The prefetch\n * function will be called with the user context but unlike the actual\n * filter function, it will not have access to the result of the query\n * and therefore can be run in parallel with underlying query resolver.\n * A typical use case is to fetch some data which is not directly\n * related to the query but to the context only. So e.g. fetching the\n * user's permissions from an external system and then later applying\n * the filter based on those permissions.\n */\n prefetch: <PrefetchReturnType>(\n prefetch: Prefetch<UserContext, PrefetchReturnType>,\n ) => {\n return {\n /**\n * The actual filter function to apply. Returns the allowed values\n */\n by: (\n explicitFilter: Filter<\n UserContext,\n DrizzleTableValueType<DB, TableName>,\n PrefetchReturnType\n >,\n ) => {\n for (const action of actions) {\n // we initialized all possible actions when creating the builder\n runtimeFilters.get(action)!.push({\n filter: explicitFilter,\n prefetch: prefetch,\n });\n }\n },\n };\n },\n /**\n * The actual filter function to apply. Returns the allowed values\n */\n by: (\n explicitFilter: Filter<\n UserContext,\n DrizzleTableValueType<DB, TableName>\n >,\n ) => {\n for (const action of actions) {\n // we initialized all possible actions when creating the builder\n runtimeFilters.get(action)!.push({\n filter: explicitFilter as Filter<UserContext, any, any>,\n });\n }\n },\n };\n },\n _: {\n runtimeFilters,\n queryFilters,\n },\n };\n };\n\n const buildersPerTable = Object.fromEntries(\n tableRelationNames.map((tableName) => [\n tableName,\n createBuilderForTable<typeof tableName>(),\n ]),\n ) as {\n [key in TableNames]: ReturnType<typeof createBuilderForTable<key>>;\n };\n\n return {\n ...buildersPerTable,\n /**\n * @internal\n * @ignore\n */\n _: {\n registeredFilters({\n action,\n table,\n }: {\n table: TableNames;\n action: Action;\n }) {\n return (buildersPerTable[table] as any)._.runtimeFilters.get(\n action,\n )! as Filter<UserContext, DrizzleTableValueType<DB, TableNames>>[];\n },\n build() {\n const createFilterForTable = <TableName extends TableNames>(\n tableName: TableName,\n ) => {\n const queryFilters = buildersPerTable[tableName]._.queryFilters;\n\n const simpleQueryFilters = Object.fromEntries(\n actions!.map((action) => {\n const filters = queryFilters.get(action);\n\n if (!filters || filters === \"unrestricted\") return [action, []];\n\n return [action, filters.filter(isStaticQueryFilter)];\n }),\n ) as {\n [key in Action]: StaticQueryFilter<\n DB,\n TableName,\n DrizzleQueryFunctionInput<DB, TableName>\n >[];\n };\n\n const dynamicQueryFilters = Object.fromEntries(\n actions!.map((action) => {\n const filters = queryFilters.get(action);\n\n if (!filters || filters === \"unrestricted\") return [action, []];\n\n return [action, filters.filter(isDynamicQueryFilter)];\n }),\n ) as {\n [key in Action]: DynamicQueryFilter<\n DB,\n TableName,\n DrizzleQueryFunctionInput<DB, TableName>,\n UserContext\n >[];\n };\n\n const tableSchema = tableHelper({\n db,\n table: tableName,\n });\n\n if (Object.keys(tableSchema.primaryKey).length === 0) {\n throw new RumbleError(\n `No primary key found for entity ${String(tableName)}`,\n );\n }\n\n const primaryKeyField: any = Object.values(tableSchema.primaryKey)[0];\n // we want a filter that excludes everything\n const distinctValues = createDistinctValuesFromSQLType(\n primaryKeyField.getSQLType() as any,\n );\n\n const blockEverythingFilter = {\n where: {\n AND: [\n {\n [primaryKeyField.name]: distinctValues.value1,\n },\n {\n [primaryKeyField.name]: distinctValues.value2,\n },\n ],\n },\n };\n\n /**\n * Packs the filters into a response object that can be applied for queries by the user\n */\n function transformToResponse(\n queryFilters?: DrizzleQueryFunctionInput<DB, TableName>,\n ) {\n const internalTransformer = (\n filters?: DrizzleQueryFunctionInput<DB, TableName>,\n mergedLimit?: number,\n ) => {\n const limit = lazy(() => {\n if (\n // got a merge injection\n mergedLimit !== undefined\n ) {\n if (!filters?.limit) {\n // there is not ability limit\n return mergedLimit;\n }\n\n if ((filters.limit as number) > mergedLimit) {\n // there is an ability limit and it is higher that the injected merge limit\n return mergedLimit;\n }\n }\n\n let limit = filters?.limit as number | undefined;\n\n if (\n defaultLimit &&\n (limit === undefined || limit > defaultLimit)\n ) {\n limit = defaultLimit;\n }\n\n // ensure that null is converted to undefined\n return limit ?? undefined;\n });\n\n const sqlTransformedWhere = lazy(() => {\n const casing = (db._ as any).session?.dialect?.casing;\n\n return filters?.where\n ? relationsFilterToSQL(\n tableSchema.foundRelation.table,\n sanitizeFilterValue(filters.where) as any,\n tableSchema.relations,\n db._.relations,\n casing,\n )\n : undefined;\n });\n\n // we acutally need to define multiple return objects since we do not want to use delete for\n // performance reasons and an undefined columns field on a drizzle filter will prevent any\n // column from being selected at all\n if (filters?.columns) {\n return {\n /**\n * Query filters for the drizzle query API.\n * @example\n * ```ts\n * author: t.relation(\"author\", {\n * query: (_args, ctx) => ctx.abilities.users.filter(\"read\").query.single,\n * }),\n * ´´´\n */\n query: {\n /**\n * For find first calls\n */\n single: {\n extras: filters?.extras,\n where: sanitizeFilterValue(filters?.where),\n columns: filters?.columns,\n } as Pick<\n NonNullable<\n NonNullable<\n Parameters<DB[\"query\"][TableName][\"findFirst\"]>[0]\n >\n >,\n \"columns\" | \"where\"\n >,\n /**\n * For find many calls\n */\n many: {\n extras: filters?.extras,\n where: sanitizeFilterValue(filters?.where),\n columns: filters?.columns,\n get limit() {\n return limit();\n },\n } as Pick<\n NonNullable<\n NonNullable<\n Parameters<DB[\"query\"][TableName][\"findMany\"]>[0]\n >\n >,\n \"columns\" | \"where\" | \"limit\"\n >,\n },\n /**\n * Query filters for the drizzle SQL API as used in e.g. updates.\n * @example\n *\n * ```ts\n * await db\n *\t.update(schema.users)\n *\t.set({\n *\t name: args.newName,\n * \t})\n *\t.where(\n *\t and(\n *\t eq(schema.users.id, args.userId),\n *\t ctx.abilities.users.filter(\"update\").sql.where,\n *\t ),\n *\t);\n * ```\n *\n */\n sql: {\n get where() {\n return sqlTransformedWhere();\n },\n },\n };\n } else {\n return {\n /**\n * Query filters for the drizzle query API.\n * @example\n * ```ts\n * author: t.relation(\"author\", {\n * query: (_args, ctx) => ctx.abilities.users.filter(\"read\").query.single,\n * }),\n * ´´´\n */\n query: {\n /**\n * For find first calls\n */\n single: {\n extras: filters?.extras,\n where: sanitizeFilterValue(filters?.where),\n } as Pick<\n NonNullable<\n NonNullable<\n Parameters<DB[\"query\"][TableName][\"findFirst\"]>[0]\n >\n >,\n \"where\"\n >,\n /**\n * For find many calls\n */\n many: {\n extras: filters?.extras,\n where: sanitizeFilterValue(filters?.where),\n get limit() {\n return limit();\n },\n } as Pick<\n NonNullable<\n NonNullable<\n Parameters<DB[\"query\"][TableName][\"findMany\"]>[0]\n >\n >,\n \"where\" | \"limit\"\n >,\n },\n /**\n * Query filters for the drizzle SQL API as used in e.g. updates.\n * @example\n *\n * ```ts\n * await db\n *\t.update(schema.users)\n *\t.set({\n *\t name: args.newName,\n * \t})\n *\t.where(\n *\t and(\n *\t eq(schema.users.id, args.userId),\n *\t ctx.abilities.users.filter(\"update\").sql.where,\n *\t ),\n *\t);\n * ```\n *\n */\n sql: {\n get where() {\n return sqlTransformedWhere();\n },\n },\n };\n }\n };\n\n const ret = internalTransformer(queryFilters);\n\n /**\n * Merges the current query filters with the provided filters for this call only\n */\n function merge(\n p: NonNullable<DrizzleQueryFunctionInput<DB, TableName>>,\n ) {\n const merged = mergeFilters(ret.query.many, p);\n return internalTransformer(\n merged,\n // in case the user wants to inject a limit, we need to ensure that it is applied\n // and not the potential default limit will be used\n // this is important for functions of the default query pagination implementation\n p.limit as number | undefined,\n );\n }\n\n (ret as any).merge = merge;\n\n return ret as typeof ret & {\n merge: typeof merge;\n };\n }\n\n return {\n withContext: (userContext: UserContext) => {\n return {\n filter: (action: Action) => {\n const assembleAbilities = (span?: Span) => {\n const filters = queryFilters.get(action);\n\n // in case we have a wildcard ability, skip the rest and return no filters at all\n if (filters === \"unrestricted\") {\n span?.setAttribute(\"abilities.status\", \"unrestricted\");\n return transformToResponse();\n }\n\n // if nothing has been allowed, block everything\n if (!filters) {\n span?.setAttribute(\n \"abilities.status\",\n \"blocked_everything\",\n );\n nothingRegisteredWarningLogger(String(tableName), action);\n return transformToResponse(blockEverythingFilter);\n }\n\n // run all dynamic filters\n const dynamicResults = new Array<\n DrizzleQueryFunctionInput<DB, TableName>\n >(dynamicQueryFilters[action].length);\n let filtersReturned = 0;\n for (\n let i = 0;\n i < dynamicQueryFilters[action].length;\n i++\n ) {\n const func = dynamicQueryFilters[action][i];\n const result = func(userContext);\n // if one of the dynamic filters returns \"allow\", we want to allow everything\n if (result === \"allow\") {\n return transformToResponse();\n }\n // if nothing is returned, nothing is allowed by this filter\n if (result === undefined) continue;\n\n dynamicResults[filtersReturned++] = result;\n }\n dynamicResults.length = filtersReturned;\n\n span?.setAttribute(\n \"abilities.dynamic\",\n dynamicResults.length,\n );\n span?.setAttribute(\n \"abilities.static\",\n simpleQueryFilters[action].length,\n );\n\n const allQueryFilters = [\n ...simpleQueryFilters[action],\n ...dynamicResults,\n ];\n\n span?.setAttribute(\n \"abilities.total\",\n allQueryFilters.length,\n );\n\n // if we don't have any permitted filters then block everything\n if (allQueryFilters.length === 0) {\n span?.setAttribute(\n \"abilities.status\",\n \"blocked_everything\",\n );\n\n return transformToResponse(blockEverythingFilter);\n }\n\n const mergedFilters =\n allQueryFilters.length === 1\n ? allQueryFilters[0]\n : allQueryFilters.reduce((a, b) => {\n return mergeFilters(a, b, \"OR\");\n });\n\n span?.setAttribute(\"abilities.status\", \"applied\");\n return transformToResponse(mergedFilters as any);\n };\n\n if (otel?.enabled && otel.tracer) {\n return otel.tracer.startActiveSpan(\n `rumble.abilities.prepare`,\n (span) => {\n span.setAttribute(\"rumble.action\", action);\n span.setAttribute(\"rumble.table\", String(tableName));\n try {\n // assembleAbilities sets abilities.* attributes on the span;\n // we capture them in parallel for logging via a lightweight proxy\n const attrs: Record<string, unknown> = {\n \"rumble.table\": String(tableName),\n \"rumble.action\": action,\n };\n const proxy = new Proxy(span, {\n get(target, prop) {\n if (prop === \"setAttribute\") {\n return (k: string, v: unknown) => {\n attrs[k] = v;\n return target.setAttribute(k, v as any);\n };\n }\n return (target as any)[prop];\n },\n });\n const result = assembleAbilities(proxy);\n log?.debug(attrs, \"abilities prepared\");\n return result;\n } finally {\n span.end();\n }\n },\n );\n } else {\n const attrs: Record<string, unknown> = {\n \"rumble.table\": String(tableName),\n \"rumble.action\": action,\n };\n const spy = log\n ? ({\n setAttribute: (k: string, v: unknown) => {\n attrs[k] = v;\n },\n } as unknown as Span)\n : undefined;\n const result = assembleAbilities(spy);\n log?.debug(attrs, \"abilities prepared\");\n return result;\n }\n },\n };\n },\n };\n };\n\n const abilitiesPerTable = Object.fromEntries(\n tableRelationNames.map((tableName) => [\n tableName,\n createFilterForTable(tableName),\n ]),\n ) as {\n [key in TableNames]: ReturnType<typeof createFilterForTable<key>>;\n };\n\n hasBeenBuilt = true;\n\n return (ctx: UserContext) => {\n return Object.fromEntries(\n tableRelationNames.map((tableName) => [\n tableName,\n abilitiesPerTable[tableName].withContext(ctx),\n ]),\n ) as {\n [key in TableNames]: ReturnType<\n ReturnType<typeof createFilterForTable<key>>[\"withContext\"]\n >;\n };\n };\n },\n },\n };\n};\n","import { toCamelCase } from \"drizzle-orm/casing\";\nimport { capitalize } from \"es-toolkit\";\nimport { lazy } from \"../helpers/lazy\";\nimport { tableHelper } from \"../helpers/tableHelpers\";\nimport type {\n DrizzleInstance,\n DrizzleQueryFunction,\n} from \"../types/drizzleInstanceType\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"../types/rumbleInput\";\nimport type { SchemaBuilderType } from \"../types/schemaBuilderType\";\n\nexport type OrderArgImplementerType<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n> = ReturnType<\n typeof createOrderArgImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >\n>;\n\nconst makeDefaultName = (dbName: string) =>\n `${capitalize(toCamelCase(dbName.toString()))}OrderInputArgument`;\n\nexport const createOrderArgImplementer = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>({\n db,\n schemaBuilder,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig> & {\n schemaBuilder: SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n}) => {\n const referenceStorage = new Map<string, any>();\n\n const sortingParameterEnumRef = lazy(() =>\n schemaBuilder.enumType(\"SortingParameter\", {\n values: [\"asc\", \"desc\"] as const,\n }),\n );\n\n const orderArgImplementer = <\n RefName extends string,\n TableName extends keyof DrizzleQueryFunction<DB>,\n >({\n table,\n refName,\n dbName,\n }: Partial<{\n table: TableName;\n refName: RefName | undefined;\n dbName: string;\n }> &\n (\n | {\n table: TableName;\n }\n | {\n dbName: string;\n }\n )) => {\n const tableSchema = tableHelper({\n db,\n table: dbName ?? table!,\n });\n\n const inputTypeName = refName ?? makeDefaultName(tableSchema.tsName);\n\n let ret: ReturnType<typeof implement> | undefined =\n referenceStorage.get(inputTypeName);\n if (ret) {\n return ret;\n }\n\n const implement = () => {\n return schemaBuilder.inputType(inputTypeName, {\n fields: (t) => {\n // Drizzle's relationsOrderToSQL treats every key as a column on the\n // current table, so exposing relation keys would generate invalid SQL.\n const fields = Object.entries(tableSchema.columns).reduce(\n (acc, [key]) => {\n // GraphQL reserves names starting with \"__\" for introspection.\n if (key.startsWith(\"__\")) return acc;\n\n acc[key] = t.field({\n type: sortingParameterEnumRef(),\n required: false,\n });\n\n return acc;\n },\n {} as Record<string, ReturnType<typeof t.field>>,\n );\n\n return fields;\n },\n });\n };\n\n ret = implement();\n referenceStorage.set(inputTypeName, ret);\n return ret;\n };\n\n return orderArgImplementer;\n};\n","import { type Column, getTableName, is, isTable } from \"drizzle-orm\";\nimport { toCamelCase } from \"drizzle-orm/casing\";\nimport { MySqlEnumColumn, MySqlEnumObjectColumn } from \"drizzle-orm/mysql-core\";\nimport {\n isPgEnum,\n type PgEnum,\n PgEnumColumn,\n type PgEnumObject,\n PgEnumObjectColumn,\n} from \"drizzle-orm/pg-core\";\nimport { capitalize } from \"es-toolkit\";\nimport type { DrizzleInstance } from \"./types/drizzleInstanceType\";\nimport { RumbleError } from \"./types/rumbleError\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\nimport type { SchemaBuilderType } from \"./types/schemaBuilderType\";\n\n/**\n * Checks if a column is a database enum column (Postgres or MySQL).\n */\nexport function isEnumSchema(\n schemaType: any,\n): schemaType is\n | PgEnumColumn<any>\n | PgEnumObjectColumn<any>\n | MySqlEnumColumn<any>\n | MySqlEnumObjectColumn<any> {\n return (\n is(schemaType, PgEnumColumn) ||\n is(schemaType, PgEnumObjectColumn) ||\n is(schemaType, MySqlEnumColumn) ||\n is(schemaType, MySqlEnumObjectColumn)\n );\n}\n\n// TODO make this compatible with other db drivers\ntype EnumTypes = PgEnum<any> | PgEnumObject<any>;\n\nexport type NonEnumFields<T> = {\n [K in keyof T as T[K] extends EnumTypes ? never : K]: T[K];\n};\n\n/**\n * Picks the keys of a schema object that are pgEnum definitions\n */\nexport type EnumFieldKeys<S> = keyof {\n [K in keyof S as S[K] extends EnumTypes ? K : never]: S[K];\n};\n\n/**\n * Fallback value tuple used whenever the concrete enum members cannot be\n * recovered from the drizzle types (e.g. an object-enum whose values were\n * widened to `string`, or a `tsName` that does not resolve against `Schema`).\n */\ntype UnknownEnumValues = readonly [string, ...string[]];\n\n/**\n * Extracts the literal value tuple carried by a drizzle enum definition.\n */\ntype EnumValuesOf<E> =\n E extends PgEnum<infer V>\n ? V\n : E extends PgEnumObject<infer O>\n ? ReadonlyArray<O[keyof O] & string>\n : UnknownEnumValues;\n\n/**\n * The GraphQL enum member union for a single `enum_(...)` call, resolved from\n * whichever of the three per-call generics the caller populated (`tsName` /\n * `enum` / `enumColumn`). The unused generics default to `never`, so\n * `[X] extends [never]` tells us which identification form was used.\n *\n * Anything we can't recover from the drizzle types (an object-enum widened to\n * `string`, or a `tsName` that doesn't resolve against `Schema`) falls back to\n * `string`, matching Pothos' own enum member type.\n */\ntype EnumMembers<Schema, TsName, EnumArg, EnumColumn> = [EnumColumn] extends [\n never,\n]\n ? [EnumArg] extends [never]\n ? [TsName] extends [never]\n ? string\n : TsName extends keyof Schema\n ? EnumValuesOf<Schema[TsName]>[number]\n : string\n : EnumValuesOf<EnumArg>[number]\n : EnumColumn extends { enumValues: infer CV extends UnknownEnumValues }\n ? CV[number]\n : string;\n\n/**\n * The strongly typed Pothos enum ref returned by a single `enum_(...)` call.\n *\n * Kept as a named, exported alias on purpose: the `.d.ts` emitter prints type\n * aliases by reference rather than expanding their bodies, so the (otherwise\n * very deep) `SchemaBuilder` / `EnumRef` types never get inlined into the\n * declaration output. Two details keep this printable without the emitter\n * recursing: referencing `SchemaBuilderType<...>` (a named alias) rather than\n * `typeof schemaBuilder` (a value), and inlining the member resolution so the\n * cyclic drizzle `Schema[TsName]` access never surfaces as its own symbol.\n */\nexport type EnumImplementationRef<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n Schema,\n TsName,\n EnumArg,\n EnumColumn,\n> =\n SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n > extends PothosSchemaTypes.SchemaBuilder<infer Types>\n ? PothosSchemaTypes.EnumRef<\n Types,\n EnumMembers<Schema, TsName, EnumArg, EnumColumn>\n >\n : never;\n\nexport type EnumImplementerType<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n AvailableEnums extends string,\n Schema extends Record<string, any> = Record<string, any>,\n> = ReturnType<\n typeof createEnumImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n AvailableEnums,\n Schema\n >\n>;\n\nexport const createEnumImplementer = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n AvailableEnums extends string,\n Schema extends Record<string, any> = Record<string, any>,\n>({\n schema,\n schemaBuilder,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig> & {\n schemaBuilder: SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n}) => {\n const referenceStorage = new Map<string, any>();\n\n /**\n * Registers a Postgres enum as a GraphQL enum type.\n *\n * You can identify the enum in three ways:\n * - `tsName`: the exported TypeScript identifier from your schema module. This is the\n * most typesafe form, only valid enum keys autocomplete, typos are caught at compile time.\n * - `enum`: pass the pgEnum object directly.\n * - `enumColumn`: pass a column that uses the enum.\n *\n * Use `refName` to override the auto-generated GraphQL type name.\n */\n const enumImplementer = <\n TsName extends AvailableEnums = never,\n EnumArg extends PgEnum<any> | PgEnumObject<any> = never,\n EnumColumn extends Column = never,\n RefName extends string = string,\n >(\n args: {\n refName?: RefName;\n } & (\n | { tsName: TsName; enum?: never; enumColumn?: never }\n | { enum: EnumArg; tsName?: never; enumColumn?: never }\n | { enumColumn: EnumColumn; tsName?: never; enum?: never }\n ),\n ): EnumImplementationRef<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n Schema,\n TsName,\n EnumArg,\n EnumColumn\n > => {\n const { refName } = args;\n const tsName = (args as { tsName?: string }).tsName;\n const enumObjectArg = (args as { enum?: PgEnum<any> | PgEnumObject<any> })\n .enum;\n const enumColumn = (args as { enumColumn?: Column }).enumColumn;\n\n let enumObject: PgEnum<any> | PgEnumObject<any> | undefined = enumObjectArg;\n\n if (tsName) {\n const candidate = (schema as Record<string, unknown>)[tsName];\n if (!candidate || !isPgEnum(candidate as any)) {\n throw new RumbleError(\n `Could not find a pgEnum exported as ${JSON.stringify(\n tsName,\n )} in the provided schema. ` +\n `Make sure the identifier exists and refers to a value created with \\`pgEnum(...)\\`.`,\n );\n }\n enumObject = candidate as PgEnum<any> | PgEnumObject<any>;\n }\n\n if (!enumObject && !enumColumn) {\n throw new RumbleError(\n `Could not determine enum structure! Pass one of 'tsName' (requires \\`schema\\` on rumble()), ` +\n `'enum' (the pgEnum object), or 'enumColumn' (a column that uses the enum).`,\n );\n }\n\n let enumSchemaName: string | undefined;\n let enumValues: any[] | undefined;\n\n if (enumObject) {\n enumSchemaName = enumObject.enumName;\n enumValues = enumObject.enumValues as unknown as any[];\n } else if (enumColumn) {\n // MySQL enum columns carry their values directly; there is no standalone\n // enum object. Derive a stable name from table + column name.\n if (\n is(enumColumn, MySqlEnumColumn) ||\n is(enumColumn, MySqlEnumObjectColumn)\n ) {\n enumValues = (enumColumn as any).enumValues as unknown as any[];\n const colTable = (enumColumn as any).table;\n const tableName =\n colTable && isTable(colTable) ? getTableName(colTable) : undefined;\n enumSchemaName = tableName\n ? `${tableName}_${enumColumn.name}`\n : enumColumn.name;\n } else {\n const pgEnum = (enumColumn as any).enum as\n | PgEnum<any>\n | PgEnumObject<any>\n | undefined;\n\n if (!pgEnum) {\n throw new RumbleError(\n `Could not find enum definition on column. Make sure the column is a pgEnum column.`,\n );\n }\n\n enumSchemaName = pgEnum.enumName;\n enumValues = enumColumn.enumValues as unknown as any[];\n }\n }\n\n if (!enumSchemaName || !enumValues) {\n throw new RumbleError(\"Could not determine enum structure!\");\n }\n\n const graphqlImplementationName =\n refName ?? `${capitalize(toCamelCase(enumSchemaName))}Enum`;\n\n // The runtime always produces a plain Pothos enum ref; the strong typing\n // lives entirely in the (explicit, named) return type, so we cast on the\n // way out. The named return alias is what keeps the `.d.ts` emitter from\n // recursing on the inlined SchemaBuilder/EnumRef types.\n type Ret = EnumImplementationRef<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n Schema,\n TsName,\n EnumArg,\n EnumColumn\n >;\n\n const cached = referenceStorage.get(graphqlImplementationName);\n if (cached) {\n return cached as Ret;\n }\n\n const ret = schemaBuilder.enumType(graphqlImplementationName, {\n values: enumValues,\n });\n referenceStorage.set(graphqlImplementationName, ret);\n return ret as unknown as Ret;\n };\n\n return enumImplementer;\n};\n","import {\n isBigIntLikeSQLTypeString,\n isBooleanSQLTypeString,\n isBytesSQLTypeString,\n isDateLikeSQLTypeString,\n isDateTimeLikeSQLTypeString,\n isFloatLikeSQLTypeString,\n isIDLikeSQLTypeString,\n isIntLikeSQLTypeString,\n isJSONFallbackSQLTypeString,\n isJSONLikeSQLTypeString,\n isStringLikeSQLTypeString,\n normalizeSQLType,\n type PossibleSQLType,\n UnknownTypeRumbleError,\n} from \"./types\";\n\nexport type GraphQLTypeName =\n | \"Int\"\n | \"Float\"\n | \"String\"\n | \"ID\"\n | \"Boolean\"\n | \"DateTime\"\n | \"Date\"\n | \"JSON\"\n | \"BigInt\"\n | \"Bytes\";\n\nexport function mapSQLTypeToGraphQLType({\n sqlType,\n fieldName,\n}: {\n sqlType: PossibleSQLType;\n fieldName?: string;\n}): GraphQLTypeName {\n // MySQL raw enum columns expose their values in the SQL type string.\n // Handle before normalization since normalization would strip the parens.\n if (/^enum\\(/.test(sqlType)) {\n return \"String\";\n }\n\n const normalized = normalizeSQLType(sqlType);\n\n let ret: GraphQLTypeName | undefined;\n\n if (isIntLikeSQLTypeString(normalized)) {\n ret = \"Int\";\n }\n\n if (isBigIntLikeSQLTypeString(normalized)) {\n ret = \"BigInt\";\n }\n\n if (isFloatLikeSQLTypeString(normalized)) {\n ret = \"Float\";\n }\n\n if (isStringLikeSQLTypeString(normalized)) {\n if (\n fieldName &&\n (fieldName.toLowerCase().endsWith(\"_id\") ||\n fieldName.toLowerCase().endsWith(\"id\"))\n ) {\n ret = \"ID\";\n } else {\n ret = \"String\";\n }\n }\n\n if (isIDLikeSQLTypeString(normalized)) {\n ret = \"ID\";\n }\n\n if (isBooleanSQLTypeString(normalized)) {\n ret = \"Boolean\";\n }\n\n if (isDateTimeLikeSQLTypeString(normalized)) {\n ret = \"DateTime\";\n }\n\n if (isDateLikeSQLTypeString(normalized)) {\n ret = \"Date\";\n }\n\n if (isJSONLikeSQLTypeString(normalized)) {\n ret = \"JSON\";\n }\n\n if (isJSONFallbackSQLTypeString(normalized)) {\n ret = \"JSON\";\n }\n\n if (isBytesSQLTypeString(normalized)) {\n ret = \"Bytes\";\n }\n\n if (ret !== undefined) {\n return ret;\n }\n\n throw UnknownTypeRumbleError(sqlType, \"SQL to GQL\");\n}\n","import { is } from \"drizzle-orm\";\nimport { toCamelCase } from \"drizzle-orm/casing\";\nimport { PgColumn } from \"drizzle-orm/pg-core\";\nimport { capitalize } from \"es-toolkit\";\nimport { type EnumImplementerType, isEnumSchema } from \"../enum\";\nimport { mapSQLTypeToGraphQLType } from \"../helpers/sqlTypes/mapSQLTypeToTSType\";\nimport type { PossibleSQLType } from \"../helpers/sqlTypes/types\";\nimport { tableHelper } from \"../helpers/tableHelpers\";\nimport type {\n DrizzleInstance,\n DrizzleQueryFunction,\n} from \"../types/drizzleInstanceType\";\nimport { RumbleError } from \"../types/rumbleError\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"../types/rumbleInput\";\nimport type { SchemaBuilderType } from \"../types/schemaBuilderType\";\n\n// TODO: in general, several of the filter methods should be more\n// restrictive in case of explicitly allowed columns\n// search, order and filter should be restricted to allowed cols\n// and should completely ignore other fields since one might be ably\n// to narrow down and guess the actual values behind forbidden columns by\n// using the provided args. This way one could guess, e.g. secrets which are forbidden by\n// the column abilitiy settings but will be respected in searches, etc.\n\nexport type WhereArgImplementerType<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n> = ReturnType<\n typeof createWhereArgImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >\n>;\n\nconst makeDefaultName = (dbName: string) =>\n `${capitalize(toCamelCase(dbName.toString()))}WhereInputArgument`;\n\nexport const createWhereArgImplementer = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>({\n db,\n schemaBuilder,\n enumImplementer,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig> & {\n enumImplementer: EnumImplementerType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n any\n >;\n schemaBuilder: SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n}) => {\n const referenceStorage = new Map<string, any>();\n const enumArrayWhereInputStorage = new Map<string, any>();\n const scalarArrayWhereInputStorage = new Map<string, any>();\n\n const scalarArrayWhereInputName = (gqlType: string) =>\n `${gqlType}ArrayWhereInputArgument`;\n\n const getScalarArrayWhereInput = (gqlType: string) => {\n const typeName = scalarArrayWhereInputName(gqlType);\n const existing = scalarArrayWhereInputStorage.get(typeName);\n if (existing) return existing;\n\n const ret = schemaBuilder.inputRef(typeName);\n scalarArrayWhereInputStorage.set(typeName, ret);\n\n ret.implement({\n fields: (t: any) => ({\n eq: t.field({ type: [gqlType], required: false }),\n ne: t.field({ type: [gqlType], required: false }),\n in: t.field({ type: [[gqlType]], required: false }),\n notIn: t.field({ type: [[gqlType]], required: false }),\n isNull: t.boolean({ required: false }),\n isNotNull: t.boolean({ required: false }),\n arrayOverlaps: t.field({ type: [gqlType], required: false }),\n arrayContained: t.field({ type: [gqlType], required: false }),\n arrayContains: t.field({ type: [gqlType], required: false }),\n AND: t.field({ type: [ret], required: false }),\n OR: t.field({ type: [ret], required: false }),\n NOT: t.field({ type: ret, required: false }),\n }),\n });\n\n return ret;\n };\n\n const getEnumArrayWhereInput = (enumImpl: any) => {\n const typeName = `${enumImpl.name}WhereInputArgument`;\n\n const existing = enumArrayWhereInputStorage.get(typeName);\n if (existing) {\n return existing;\n }\n\n const ret = schemaBuilder.inputRef(typeName);\n enumArrayWhereInputStorage.set(typeName, ret);\n\n ret.implement({\n fields: (t: any) => ({\n // the column holds an array, so eq/ne compare against a whole\n // array value and in/notIn against a list of array values\n eq: t.field({ type: [enumImpl], required: false }),\n ne: t.field({ type: [enumImpl], required: false }),\n in: t.field({ type: [[enumImpl]], required: false }),\n notIn: t.field({ type: [[enumImpl]], required: false }),\n isNull: t.boolean({ required: false }),\n isNotNull: t.boolean({ required: false }),\n arrayOverlaps: t.field({ type: [enumImpl], required: false }),\n arrayContained: t.field({ type: [enumImpl], required: false }),\n arrayContains: t.field({ type: [enumImpl], required: false }),\n AND: t.field({ type: [ret], required: false }),\n OR: t.field({ type: [ret], required: false }),\n NOT: t.field({ type: ret, required: false }),\n }),\n });\n\n return ret;\n };\n\n const whereArgImplementer = <\n TableName extends keyof DrizzleQueryFunction<DB>,\n RefName extends string,\n >({\n table,\n refName,\n dbName,\n }: Partial<{\n table: TableName;\n refName: RefName | undefined;\n dbName: string;\n }> &\n (\n | {\n table: TableName;\n }\n | {\n dbName: string;\n }\n )) => {\n const tableSchema = tableHelper({\n db,\n table: dbName ?? table!,\n });\n\n const inputTypeName = refName ?? makeDefaultName(tableSchema.tsName);\n\n const existing = referenceStorage.get(inputTypeName);\n if (existing) {\n return existing;\n }\n\n const ret = schemaBuilder.inputRef(inputTypeName);\n referenceStorage.set(inputTypeName, ret);\n\n ret.implement({\n fields: (t: any) => {\n const mapSQLTypeStringToInputPothosType = (\n sqlType: PossibleSQLType,\n fieldName: string,\n isArray: boolean,\n ) => {\n const gqlType = mapSQLTypeToGraphQLType({\n sqlType,\n fieldName,\n });\n\n if (isArray) {\n return t.field({\n type: getScalarArrayWhereInput(gqlType),\n required: false,\n });\n }\n\n switch (gqlType) {\n case \"Int\":\n return t.field({\n type: \"IntWhereInputArgument\",\n required: false,\n });\n case \"BigInt\":\n return t.field({\n type: \"BigIntWhereInputArgument\",\n required: false,\n });\n case \"String\":\n return t.field({\n type: \"StringWhereInputArgument\",\n required: false,\n });\n case \"Boolean\":\n return t.field({\n type: \"BooleanWhereInputArgument\",\n required: false,\n });\n case \"Date\":\n return t.field({\n type: \"DateWhereInputArgument\",\n required: false,\n });\n case \"DateTime\":\n return t.field({\n type: \"DateTimeWhereInputArgument\",\n required: false,\n });\n case \"Float\":\n return t.field({\n type: \"FloatWhereInputArgument\",\n required: false,\n });\n case \"ID\":\n return t.field({\n type: \"IDWhereInputArgument\",\n required: false,\n });\n case \"JSON\":\n return t.field({\n type: \"JSONWhereInputArgument\",\n required: false,\n });\n case \"Bytes\":\n // No meaningful filter operators for byte columns — skip.\n return null;\n default:\n throw new RumbleError(\n `Unsupported argument type ${gqlType} for column ${sqlType}`,\n );\n }\n };\n const fields = Object.entries(tableSchema.columns).reduce(\n (acc, [key, value]) => {\n // GraphQL reserves names starting with \"__\" for introspection.\n if (key.startsWith(\"__\")) return acc;\n\n // Detect pg array columns via the `dimensions` runtime property.\n let isArray = false;\n if (is(value, PgColumn)) {\n const dims = (value as PgColumn & { dimensions?: number })\n .dimensions;\n if (dims && dims > 0) isArray = true;\n }\n\n if (isEnumSchema(value)) {\n const enumImpl = enumImplementer({\n enumColumn: value,\n });\n\n acc[key] = t.field({\n type: isArray ? getEnumArrayWhereInput(enumImpl) : enumImpl,\n required: false,\n });\n } else {\n const field = mapSQLTypeStringToInputPothosType(\n value.getSQLType() as PossibleSQLType,\n key,\n isArray,\n );\n if (field !== null) {\n acc[key] = field;\n }\n }\n\n return acc;\n },\n {} as Record<string, ReturnType<typeof t.field>>,\n );\n\n const relations = Object.entries(tableSchema.relations ?? {}).reduce(\n (acc, [key, value]) => {\n // `targetTableName` is the publicly typed TS-key of the target\n // relation in db._.relations, prefer it over re-resolving via\n // the `targetTable` object.\n const targetTsName = (value as any).targetTableName as string;\n const relationSchema = tableHelper({\n db,\n table: targetTsName,\n });\n const referenceModel = whereArgImplementer({\n dbName: relationSchema.dbName,\n });\n\n acc[key] = t.field({\n type: referenceModel,\n required: false,\n });\n\n return acc;\n },\n {} as Record<\n keyof typeof tableSchema.columns,\n ReturnType<typeof mapSQLTypeStringToInputPothosType>\n >,\n );\n\n return {\n ...fields,\n ...relations,\n AND: t.field({ type: [ret], required: false }),\n OR: t.field({ type: [ret], required: false }),\n NOT: t.field({ type: ret, required: false }),\n };\n },\n });\n\n return ret;\n };\n\n return whereArgImplementer;\n};\n","import type { DrizzleInstance } from \"../types/drizzleInstanceType\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"../types/rumbleInput\";\nimport type { SchemaBuilderType } from \"../types/schemaBuilderType\";\nimport { generateFromSchema } from \"./generate/generate\";\n\nexport const clientCreatorImplementer = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>({\n builtSchema,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig> & {\n builtSchema: () => ReturnType<\n SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >[\"toSchema\"]\n >;\n}) => {\n const clientCreator = async ({\n apiUrl,\n outputPath,\n rumbleImportPath,\n useExternalUrqlClient,\n removeExisting,\n forceReactivity,\n autoIncludeIdField = false,\n }: {\n /**\n * Path to the output directory where the client files will be generated.\n */\n outputPath: string;\n /**\n * The base URL of the Rumble API.\n */\n apiUrl?: string;\n /**\n * The import path for the rumble library, defaults to \"@m1212e/rumble/client\".\n */\n rumbleImportPath?: string;\n /**\n * Set this to use an external urql client exported from a module.\n * If a string, uses the provided path to the urql client for importing the client.\n * If false, creates a new urql client with the provided apiUrl.\n */\n useExternalUrqlClient?: string;\n /**\n * Whether to remove existing generated files in the output directory before generating new ones.\n */\n removeExisting?: boolean;\n /**\n * Whether to force reactivity for generated queries and mutations. This will prevent the actual response fields of the awaited response from being populated\n * and requires you to subscribe to the response to access the data. Useful to prevent forgetting to subscribe to the response to utilize reactive data.\n */\n forceReactivity?: boolean;\n /**\n * Whether to automatically include the `id` field in generated queries and mutations.\n * This might be helpful to ensure that caching works correctly since all object will always be identifiable by their `id`.\n * Can be set to `true` to always include the `id` field, or to `false` to never include it.\n * Can also be set to a string to include a custom named field as Id field in case you have a different naming convention like `_id`.\n *\n * @default false\n */\n autoIncludeIdField?: boolean | string;\n }) => {\n if (process.env.NODE_ENV !== \"development\") {\n console.warn(\n `Running rumble client generation in non development mode. Are you sure this is correct? Called with arguments: ${JSON.stringify(\n {\n outputPath,\n apiUrl,\n rumbleImportPath,\n useExternalUrqlClient,\n removeExisting,\n },\n )}`,\n );\n }\n const schema = builtSchema();\n await generateFromSchema({\n schema,\n outputPath,\n rumbleImportPath,\n apiUrl,\n useExternalUrqlClient,\n removeExisting,\n forceReactivity,\n autoIncludeIdField,\n });\n };\n\n return clientCreator;\n};\n","import type { AbilityBuilderType } from \"./abilityBuilder\";\nimport { lazy } from \"./helpers/lazy\";\nimport type { DrizzleInstance } from \"./types/drizzleInstanceType\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\n\nexport type ContextFunctionType<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n> = ReturnType<\n typeof createContextFunction<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >\n>;\n\nexport type ContextType<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n> = Awaited<\n ReturnType<\n ContextFunctionType<UserContext, DB, RequestEvent, Action, PothosConfig>\n >\n>;\n\nexport const createContextFunction = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>({\n context: makeUserContext,\n abilityBuilder,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig> & {\n abilityBuilder: AbilityBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n}) => {\n const builtAbilityBuilder = lazy(() => abilityBuilder._.build());\n\n return async (req: RequestEvent) => {\n const userContext = makeUserContext\n ? await makeUserContext(req)\n : ({} as UserContext);\n\n return {\n ...userContext,\n abilities: builtAbilityBuilder()(userContext),\n };\n };\n};\n","export function deepSetProto(\n obj: any,\n proto = Object.prototype,\n seen = new WeakSet(),\n) {\n if (obj === null || typeof obj !== \"object\") return;\n if (seen.has(obj)) return;\n seen.add(obj);\n\n if (Array.isArray(obj)) {\n for (const item of obj) {\n deepSetProto(item, proto, seen);\n }\n return;\n }\n\n const currentProto = Object.getPrototypeOf(obj);\n if (currentProto !== Object.prototype && currentProto !== null) {\n return;\n }\n Object.setPrototypeOf(obj, proto);\n for (const key of Object.keys(obj)) {\n deepSetProto(obj[key], proto, seen);\n }\n}\n","import { count } from \"drizzle-orm\";\nimport pluralize from \"pluralize\";\nimport type { WhereArgImplementerType } from \"./args/whereArg\";\nimport { assertFirstEntryExists } from \"./helpers/asserts\";\nimport { mapNullFieldsToUndefined } from \"./helpers/mapNullFieldsToUndefined\";\nimport { deepSetProto } from \"./helpers/protoMapper\";\nimport { tableHelper } from \"./helpers/tableHelpers\";\nimport type { MakePubSubInstanceType } from \"./pubsub\";\nimport type {\n DrizzleInstance,\n DrizzleQueryFunction,\n TableRelationNames,\n} from \"./types/drizzleInstanceType\";\nimport { RumbleErrorSafe } from \"./types/rumbleError\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\nimport type { SchemaBuilderType } from \"./types/schemaBuilderType\";\n\nexport const createCountQueryImplementer = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n Schema extends Record<string, any>,\n>({\n db,\n schemaBuilder,\n whereArgImplementer,\n makePubSubInstance,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig, Schema> & {\n schemaBuilder: SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n whereArgImplementer: WhereArgImplementerType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n makePubSubInstance: MakePubSubInstanceType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n}) => {\n return <TableName extends TableRelationNames<DB>>({\n table,\n listAction = \"read\" as Action,\n isAllowed,\n }: {\n /**\n * The table for which to implement the count query\n */\n table: TableName;\n /**\n * Which action should be used for listing many entities\n * @default \"read\"\n */\n listAction?: Action;\n /**\n * Optional function to check if the query is allowed\n */\n isAllowed?: (context: UserContext) => boolean | Promise<boolean>;\n }) => {\n const WhereArg = whereArgImplementer({\n table: table,\n });\n const { registerOnInstance } = makePubSubInstance({ table: table });\n\n const tableSchema = tableHelper({\n db,\n table,\n });\n\n return schemaBuilder.queryFields((t) => {\n return {\n [`${pluralize.plural(String(table))}Count`]: t.field({\n type: \"Int\",\n nullable: false,\n smartSubscription: true,\n description: `Count all ${pluralize.plural(String(table))}`,\n subscribe: (subscriptions, _root, _args, _ctx, _info) => {\n registerOnInstance({\n instance: subscriptions,\n action: \"created\",\n });\n registerOnInstance({\n instance: subscriptions,\n action: \"removed\",\n });\n },\n args: {\n where: t.arg({ type: WhereArg, required: false }),\n },\n resolve: async (_root, args, ctx, _info) => {\n if (isAllowed && !(await isAllowed(ctx))) {\n throw new RumbleErrorSafe(\"Not allowed to perform this action\");\n }\n\n deepSetProto(args);\n\n return (db as any)\n .select({ count: count() })\n .from(tableSchema.table)\n .where(\n ctx.abilities[table]\n .filter(listAction)\n .merge(mapNullFieldsToUndefined(args) as any).sql.where,\n )\n .then(assertFirstEntryExists)\n .then((r: any) => r.count);\n },\n }),\n };\n });\n };\n};\n","import type { useSofa } from \"sofa-api\";\n\nexport const sofaOpenAPIWebhookDocs: NonNullable<\n Parameters<typeof useSofa>[0][\"openAPI\"]\n> = {\n paths: {\n \"/webhook\": {\n post: {\n operationId: \"webhook_create\",\n description: \"Creates a webhook subscription.\",\n tags: [],\n parameters: [],\n requestBody: {\n content: {\n \"application/json\": {\n schema: {\n $ref: \"#/components/schemas/WebhookCreateBody\",\n },\n },\n },\n },\n responses: {\n \"200\": {\n description: \"\",\n content: {\n \"application/json\": {\n schema: {\n $ref: \"#/components/schemas/WebhookDetailResponse\",\n },\n },\n },\n },\n },\n },\n },\n \"/webhook/{id}\": {\n post: {\n operationId: \"webhook_update\",\n description: \"Updates a webhook subscription.\",\n parameters: [\n {\n name: \"id\",\n in: \"path\",\n description: \"The ID of the webhook to update\",\n required: true,\n schema: {\n type: \"string\",\n },\n } as any,\n ],\n requestBody: {\n content: {\n \"application/json\": {\n schema: {\n $ref: \"#/components/schemas/WebhookCreateBody\",\n },\n },\n },\n },\n responses: {\n \"200\": {\n description: \"\",\n content: {\n \"application/json\": {\n schema: {\n $ref: \"#/components/schemas/WebhookDetailResponse\",\n },\n },\n },\n },\n },\n },\n delete: {\n operationId: \"webhook_delete\",\n description: \"Removes a webhook subscription.\",\n tags: [],\n parameters: [\n {\n name: \"id\",\n in: \"path\",\n description: \"The ID of the webhook to delete\",\n required: true,\n schema: {\n type: \"string\",\n },\n } as any,\n ],\n responses: {\n \"200\": {\n description: \"\",\n content: {\n \"application/json\": {\n schema: {\n $ref: \"#/components/schemas/WebhookDetailResponse\",\n },\n },\n },\n },\n },\n },\n },\n },\n components: {\n schemas: {\n WebhookCreateBody: {\n type: \"object\",\n properties: {\n subscription: {\n description:\n \"The subscription to subscribe to. In many cases, these match the available query IDs without the '_query' suffix. E.g., 'users_query' -> 'users'. See the graphql schema for more details on what subscriptions are available.\",\n type: \"string\",\n },\n variables: {\n description: \"The variables to pass to the subscription.\",\n type: \"object\",\n },\n url: {\n description: \"The URL to send the webhook to.\",\n type: \"string\",\n },\n },\n },\n WebhookDetailResponse: {\n type: \"object\",\n properties: {\n id: {\n description:\n \"The ID of the webhook. Can be used as reference in update or delete calls.\",\n type: \"string\",\n },\n },\n },\n DateTime: {\n type: \"string\",\n format: \"date-time\",\n },\n Date: {\n type: \"string\",\n format: \"date\",\n },\n },\n },\n};\n","import type { GraphQLError } from \"graphql\";\n\n/**\n * Shape of a single error entry in a log's `errors` array, following\n * OpenTelemetry's exception semantic conventions\n * (https://opentelemetry.io/docs/specs/semconv/exceptions/exceptions-logs/).\n */\nexport interface LoggedException {\n \"exception.type\": string;\n \"exception.message\": string;\n \"exception.stacktrace\"?: string;\n path?: ReadonlyArray<string | number>;\n extensions?: Record<string, unknown>;\n}\n\nfunction hasMessage(error: unknown): error is { message: unknown } {\n return typeof error === \"object\" && error !== null && \"message\" in error;\n}\n\nfunction toLoggedException(error: unknown): LoggedException {\n if (hasMessage(error)) {\n const gqlError = error as Partial<GraphQLError> & Error;\n return {\n \"exception.type\": gqlError.constructor?.name ?? gqlError.name ?? \"Error\",\n \"exception.message\": String(gqlError.message),\n ...(gqlError.stack ? { \"exception.stacktrace\": gqlError.stack } : {}),\n ...(gqlError.path ? { path: gqlError.path } : {}),\n ...(gqlError.extensions && Object.keys(gqlError.extensions).length > 0\n ? { extensions: gqlError.extensions }\n : {}),\n };\n }\n return {\n \"exception.type\": \"UnknownError\",\n \"exception.message\": String(error),\n };\n}\n\n/**\n * Every erroneous rumble log carries the same `errors` array shape,\n * whether it originates from a thrown exception (single-element array)\n * or a GraphQL `ExecutionResult.errors` list (multi-element array).\n */\nexport function errorsLogField(errors: readonly unknown[]): {\n errors: LoggedException[];\n} {\n return { errors: errors.map(toLoggedException) };\n}\n\nexport function errorLogField(error: unknown): { errors: LoggedException[] } {\n return errorsLogField([error]);\n}\n","import { type Span, SpanStatusCode } from \"@opentelemetry/api\";\nimport { AttributeNames, SpanNames } from \"@pothos/tracing-opentelemetry\";\nimport {\n execute as defaultExecute,\n subscribe as defaultSubscribe,\n type ExecutionArgs,\n type ExecutionResult,\n getOperationAST,\n print,\n} from \"graphql\";\nimport type { DrizzleInstance } from \"../types/drizzleInstanceType\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n RumbleLogger,\n} from \"../types/rumbleInput\";\nimport { errorLogField, errorsLogField } from \"./errorLogging\";\n\n// @pothos/tracing-opentelemetry's SpanNames enum has no subscribe member.\nconst SUBSCRIBE_SPAN_NAME = \"graphql.subscribe\";\n\nfunction getOperationType(options: ExecutionArgs) {\n return getOperationAST(options.document, options.operationName)?.operation;\n}\n\nfunction operationLogFields(operationName: string, operationType?: string) {\n return {\n \"graphql.operation.name\": operationName,\n ...(operationType ? { \"graphql.operation.type\": operationType } : {}),\n };\n}\n\nfunction traceIdLogFields(span: Span) {\n const { traceId, spanId, traceFlags } = span.spanContext();\n return {\n trace_id: traceId,\n span_id: spanId,\n trace_flags: traceFlags.toString(16).padStart(2, \"0\"),\n };\n}\n\nexport function isAsyncIterable(\n value: unknown,\n): value is AsyncIterable<unknown> {\n return (\n typeof value === \"object\" && value !== null && Symbol.asyncIterator in value\n );\n}\n\nexport async function* wrapSubscriptionIterator(\n iterator: AsyncIterable<ExecutionResult>,\n log: RumbleLogger,\n operationName: string,\n operationType?: string,\n): AsyncGenerator<ExecutionResult> {\n let eventCount = 0;\n try {\n for await (const event of iterator) {\n eventCount++;\n if (event.errors?.length) {\n log.error(\n {\n ...operationLogFields(operationName, operationType),\n event_count: eventCount,\n ...errorsLogField(event.errors),\n },\n \"graphql subscription event error\",\n );\n }\n yield event;\n }\n log.info(\n {\n ...operationLogFields(operationName, operationType),\n event_count: eventCount,\n },\n \"graphql subscription completed\",\n );\n } catch (error) {\n log.error(\n {\n ...operationLogFields(operationName, operationType),\n event_count: eventCount,\n ...errorLogField(error),\n },\n \"graphql subscription threw\",\n );\n throw error;\n }\n}\n\nexport function buildTracedExecute<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>(\n executeFn: (\n args: ExecutionArgs,\n ) => Promise<ExecutionResult> | ExecutionResult,\n rumbleInput: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig>,\n): (args: ExecutionArgs) => Promise<ExecutionResult> {\n return async (options: ExecutionArgs): Promise<ExecutionResult> => {\n let log = rumbleInput.logger?.enabled\n ? rumbleInput.logger.logger\n : undefined;\n const operationName = options.operationName ?? \"anonymous\";\n const operationType = getOperationType(options);\n const start = Date.now();\n\n log?.info(\n operationLogFields(operationName, operationType),\n \"graphql execute start\",\n );\n\n const run = async () => {\n const result = await executeFn(options);\n if (result && \"errors\" in result && result.errors?.length) {\n log?.error(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n ...errorsLogField(result.errors),\n },\n \"graphql execute completed with errors\",\n );\n } else {\n log?.info(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n },\n \"graphql execute completed\",\n );\n }\n return result;\n };\n\n if (rumbleInput.otel?.enabled) {\n return rumbleInput.otel.tracer!.startActiveSpan(\n SpanNames.EXECUTE,\n {\n attributes: {\n [AttributeNames.OPERATION_NAME]: operationName,\n ...(operationType\n ? { [AttributeNames.OPERATION_TYPE]: operationType }\n : {}),\n \"graphql.document\": print(options.document),\n },\n },\n async (span: Span) => {\n if (log && rumbleInput.logger?.injectTraceId !== false) {\n log = log.child(traceIdLogFields(span));\n }\n try {\n const result = await run();\n if (result && \"errors\" in result && result.errors?.length) {\n for (const error of result.errors) span.recordException(error);\n span.setStatus({ code: SpanStatusCode.ERROR });\n }\n return result;\n } catch (error) {\n if (error instanceof Error) span.recordException(error);\n log?.error(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n ...errorLogField(error),\n },\n \"graphql execute threw\",\n );\n span.setStatus({ code: SpanStatusCode.ERROR });\n throw error;\n } finally {\n span.end();\n }\n },\n );\n }\n\n try {\n return await run();\n } catch (error) {\n log?.error(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n ...errorLogField(error),\n },\n \"graphql execute threw\",\n );\n throw error;\n }\n };\n}\n\nexport function buildTracedSubscribe<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>(\n subscribeFn: (\n args: ExecutionArgs,\n ) =>\n | Promise<AsyncIterable<ExecutionResult> | ExecutionResult>\n | AsyncIterable<ExecutionResult>\n | ExecutionResult,\n rumbleInput: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig>,\n): (\n args: ExecutionArgs,\n) => Promise<AsyncIterable<ExecutionResult> | ExecutionResult> {\n return async (\n options: ExecutionArgs,\n ): Promise<AsyncIterable<ExecutionResult> | ExecutionResult> => {\n let log = rumbleInput.logger?.enabled\n ? rumbleInput.logger.logger\n : undefined;\n const operationName = options.operationName ?? \"anonymous\";\n const operationType = getOperationType(options);\n const start = Date.now();\n\n const doSubscribe = async (): Promise<\n AsyncIterable<ExecutionResult> | ExecutionResult\n > => {\n log?.info(\n operationLogFields(operationName, operationType),\n \"graphql subscribe start\",\n );\n\n const result = await subscribeFn(options);\n\n if (!isAsyncIterable(result)) {\n const execResult = result as ExecutionResult;\n if (execResult.errors?.length) {\n log?.error(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n ...errorsLogField(execResult.errors),\n },\n \"graphql subscribe completed with errors\",\n );\n }\n return execResult;\n }\n\n log?.info(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n },\n \"graphql subscription established\",\n );\n\n if (log) {\n return wrapSubscriptionIterator(\n result as AsyncIterable<ExecutionResult>,\n log,\n operationName,\n operationType,\n );\n }\n return result;\n };\n\n if (rumbleInput.otel?.enabled) {\n return rumbleInput.otel.tracer!.startActiveSpan(\n SUBSCRIBE_SPAN_NAME,\n {\n attributes: {\n [AttributeNames.OPERATION_NAME]: operationName,\n ...(operationType\n ? { [AttributeNames.OPERATION_TYPE]: operationType }\n : {}),\n \"graphql.document\": print(options.document),\n },\n },\n async (span: Span) => {\n if (log && rumbleInput.logger?.injectTraceId !== false) {\n log = log.child(traceIdLogFields(span));\n }\n try {\n const result = await doSubscribe();\n if (!isAsyncIterable(result)) {\n const execResult = result as ExecutionResult;\n if (execResult.errors?.length) {\n for (const error of execResult.errors)\n span.recordException(error);\n span.setStatus({ code: SpanStatusCode.ERROR });\n }\n }\n return result;\n } catch (error) {\n if (error instanceof Error) span.recordException(error);\n log?.error(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n ...errorLogField(error),\n },\n \"graphql subscribe threw\",\n );\n span.setStatus({ code: SpanStatusCode.ERROR });\n throw error;\n } finally {\n span.end();\n }\n },\n );\n }\n\n try {\n return await doSubscribe();\n } catch (error) {\n log?.error(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n ...errorLogField(error),\n },\n \"graphql subscribe threw\",\n );\n throw error;\n }\n };\n}\n\nexport { defaultExecute, defaultSubscribe };\n","import type { DrizzleObjectFieldBuilder } from \"@pothos/plugin-drizzle\";\nimport { RumbleError } from \"../../types/rumbleError\";\nimport { mapSQLTypeToGraphQLType } from \"./mapSQLTypeToTSType\";\nimport type { PossibleSQLType } from \"./types\";\n\nexport function buildPothosResponseTypeFromGraphQLType<\n Builder extends DrizzleObjectFieldBuilder<any, any, any, any>,\n>({\n builder,\n sqlType,\n fieldName,\n nullable,\n isArray,\n}: {\n builder: Builder;\n sqlType: PossibleSQLType;\n fieldName: string;\n nullable: boolean;\n isArray: boolean;\n}) {\n const gqlType = mapSQLTypeToGraphQLType({\n sqlType,\n fieldName,\n });\n switch (gqlType) {\n case \"Int\":\n return isArray\n ? builder.exposeIntList(fieldName, { nullable: nullable as any })\n : builder.exposeInt(fieldName, { nullable });\n case \"BigInt\":\n return builder.field({\n type: isArray ? [\"BigInt\"] : \"BigInt\",\n resolve: (element: any) => element[fieldName],\n nullable,\n });\n case \"String\":\n return isArray\n ? builder.exposeStringList(fieldName, { nullable: nullable as any })\n : builder.exposeString(fieldName, { nullable });\n case \"Boolean\":\n return isArray\n ? builder.exposeBooleanList(fieldName, { nullable: nullable as any })\n : builder.exposeBoolean(fieldName, { nullable });\n case \"Date\":\n return builder.field({\n type: isArray ? [\"Date\"] : \"Date\",\n resolve: (element: any) => element[fieldName],\n nullable,\n });\n case \"DateTime\":\n return builder.field({\n type: isArray ? [\"DateTime\"] : \"DateTime\",\n // Drizzle's timestamp({ mode: \"string\" }) returns a string; the\n // DateTimeISO scalar expects a Date object, so coerce when needed.\n resolve: (element: any) => {\n const v = element[fieldName];\n if (v == null) return v;\n return v instanceof Date ? v : new Date(v);\n },\n nullable,\n });\n case \"Float\":\n return isArray\n ? builder.exposeFloatList(fieldName, { nullable: nullable as any })\n : builder.exposeFloat(fieldName, { nullable });\n case \"ID\":\n return isArray\n ? builder.exposeIDList(fieldName, { nullable: nullable as any })\n : builder.exposeID(fieldName, { nullable });\n case \"JSON\":\n return builder.field({\n type: isArray ? [\"JSON\"] : \"JSON\",\n resolve: (element: any) => element[fieldName],\n nullable,\n });\n case \"Bytes\":\n return builder.field({\n type: \"Bytes\",\n resolve: (element: any) => {\n const v = element[fieldName];\n if (v == null) return v;\n return Buffer.isBuffer(v) ? v.toString(\"base64\") : String(v);\n },\n nullable,\n });\n default:\n throw new RumbleError(\n `Unsupported object type ${gqlType} for column ${fieldName}`,\n );\n }\n}\n","import { is } from \"drizzle-orm\";\nimport type { MySqlAsyncDatabase } from \"drizzle-orm/mysql-core\";\nimport { MySqlTable } from \"drizzle-orm/mysql-core\";\nimport type { PgAsyncDatabase } from \"drizzle-orm/pg-core\";\nimport { PgTable } from \"drizzle-orm/pg-core\";\nimport type { SQLiteAsyncDatabase } from \"drizzle-orm/sqlite-core\";\nimport { SQLiteTable } from \"drizzle-orm/sqlite-core\";\nimport type { DrizzleInstance } from \"../types/drizzleInstanceType\";\n\nexport type DBDialect = \"mysql\" | \"postgres\" | \"sqlite\";\n\nconst dialectCache = new WeakMap<object, DBDialect>();\n\nexport function determineDBDialectFromSchema<DB extends DrizzleInstance>(\n schema: DB[\"_\"][\"relations\"],\n): DBDialect {\n const cached = dialectCache.get(schema as unknown as object);\n if (cached) return cached;\n\n const found = new Set<DBDialect>();\n\n for (const table of Object.values(schema).map((t: any) => t.table)) {\n if (!table || typeof table !== \"object\") {\n continue;\n }\n\n // `is()` survives duplicate drizzle-orm copies in node_modules where\n // `instanceof` silently returns false against the \"wrong\" class identity.\n if (is(table, PgTable)) {\n found.add(\"postgres\");\n } else if (is(table, MySqlTable)) {\n found.add(\"mysql\");\n } else if (is(table, SQLiteTable)) {\n found.add(\"sqlite\");\n }\n }\n\n const dialects = Array.from(found);\n\n if (dialects.length === 1) {\n const only = dialects[0]!;\n dialectCache.set(schema as unknown as object, only);\n return only;\n }\n\n if (dialects.length === 0) {\n throw new Error(\"No tables found in schema, could not determine dialect\");\n }\n\n throw new Error(`Multiple dialects found in schema: ${dialects.join(\", \")}`);\n}\n\nexport function isPostgresDB<\n Narrowed extends PgAsyncDatabase<any, any> = PgAsyncDatabase<any, any>,\n>(db: any): db is Narrowed {\n return determineDBDialectFromSchema(db._.relations) === \"postgres\";\n}\n\nexport function isMySQLDB<\n Narrowed extends MySqlAsyncDatabase<any, any> = MySqlAsyncDatabase<any, any>,\n>(db: any): db is Narrowed {\n return determineDBDialectFromSchema(db._.relations) === \"mysql\";\n}\n\nexport function isSQLiteDB<\n Narrowed extends SQLiteAsyncDatabase<any, any, any> = SQLiteAsyncDatabase<\n any,\n any,\n any\n >,\n>(db: any): db is Narrowed {\n return determineDBDialectFromSchema(db._.relations) === \"sqlite\";\n}\n","import { sql } from \"drizzle-orm\";\nimport { cloneDeep } from \"es-toolkit\";\nimport { isPostgresDB } from \"./helpers/determineDialectFromSchema\";\nimport { errorLogField } from \"./helpers/errorLogging\";\nimport {\n isIDLikeSQLTypeString,\n isStringLikeSQLTypeString,\n} from \"./helpers/sqlTypes/types\";\nimport type { tableHelper } from \"./helpers/tableHelpers\";\nimport type { RumbleInput } from \"./types/rumbleInput\";\n\nexport async function initSearchIfApplicable(\n input: RumbleInput<any, any, any, any, any, any>,\n) {\n const log = input.logger?.enabled ? input.logger.logger : undefined;\n\n if (!isPostgresDB(input.db)) {\n const msg =\n \"Database dialect is not compatible with search, skipping search initialization. Only PostgreSQL is supported.\";\n log ? log.info({}, msg) : console.info(msg);\n return;\n }\n\n try {\n await input.db.execute(sql`CREATE EXTENSION IF NOT EXISTS pg_trgm;`);\n } catch (error) {\n const msg =\n \"Failed to create pg_trgm extension. Search functionality may not work. Ensure the database user has CREATE privilege or the extension is pre-installed.\";\n log ? log.error(errorLogField(error), msg) : console.error(msg, error);\n return;\n }\n if (input.search?.threshold) {\n // make absolutely sure the threshold is a number\n const threshold = Number(input.search.threshold);\n\n if (threshold < 0 || threshold > 1) {\n throw new Error(`Search threshold must be between 0 and 1`);\n }\n\n const result = await input.db.execute(sql`SELECT current_database()`);\n const dbName = result.rows[0].current_database;\n\n try {\n await input.db.execute(\n sql.raw(\n `ALTER DATABASE ${dbName} SET pg_trgm.similarity_threshold = ${threshold};`,\n ),\n );\n } catch (error: any) {\n // XX000 = tuple concurrently updated: multiple workers racing to set the same\n // idempotent value at startup. Safe to ignore — one of them will win.\n if (error?.cause?.code !== \"XX000\" && error?.code !== \"XX000\")\n throw error;\n }\n }\n\n if (input.search?.cpu_operator_cost) {\n if (typeof input.search.cpu_operator_cost !== \"number\") {\n throw new Error(`CPU operator cost must be a number`);\n }\n\n if (input.search.cpu_operator_cost <= 0) {\n throw new Error(`CPU operator cost must be a positive number`);\n }\n }\n}\n\n/**\n * Performs adjustments to the query args to issue a full text search in case the\n * respective feature is enabled and a search term was provided.\n */\nexport function adjustQueryArgsForSearch({\n search,\n args,\n tableSchema,\n abilities,\n}: Pick<RumbleInput<any, any, any, any, any, any>, \"search\"> & {\n //TODO types\n args: any;\n tableSchema: ReturnType<typeof tableHelper>;\n //TODO types\n abilities: any;\n}) {\n if (search?.enabled && args.search && args.search.length > 0) {\n // this prevents columns beeing searched which are not accessible to the user\n // if the abilities defined the user not to be allowed to read something, we need\n // to prevent it from beeing included in the search since this could\n // leak information\n const columnsToSearch = (\n abilities.query.many.columns\n ? Object.entries(tableSchema.columns).filter(\n ([key]) => abilities.query.many.columns[key],\n )\n : Object.entries(tableSchema.columns)\n ).filter(\n ([_key, col]) =>\n isStringLikeSQLTypeString(col.getSQLType()) ||\n isIDLikeSQLTypeString(col.getSQLType()),\n );\n\n const searchParam = sql`${args.search}`;\n\n args.extras = {\n search_distance: (table: any) =>\n sql`${sql.join(\n columnsToSearch.map(([key]) => {\n return sql`COALESCE((${table[key]}::TEXT <-> ${searchParam}), 1)`;\n }),\n sql.raw(\" + \"),\n )}`,\n };\n\n const originalOrderBy = cloneDeep(args.orderBy);\n (args as any).orderBy = (table: any) => {\n const argsOrderBySQL = sql.join(\n Object.entries(originalOrderBy ?? {}).map(([key, value]) => {\n // value is \"asc\" or \"desc\"\n if (value === \"asc\") {\n return sql`${table[key]} ASC`;\n } else if (value === \"desc\") {\n return sql`${table[key]} DESC`;\n } else {\n throw new Error(`Invalid value ${value} for orderBy`);\n }\n }),\n sql.raw(\", \"),\n );\n\n const searchSQL = sql`search_distance ASC`;\n\n const ret = originalOrderBy\n ? sql.join([argsOrderBySQL, searchSQL], sql.raw(\", \"))\n : searchSQL;\n\n return ret;\n };\n\n const originalWhere = cloneDeep(args.where);\n\n // this limits the search to the rows which at least match the threshold score\n (args as any).where = {\n AND: [\n originalWhere ?? {},\n {\n RAW: (table: any) =>\n sql`(${sql.join(\n columnsToSearch.map(([key]) => {\n return sql`${table[key]} % ${searchParam}`;\n }),\n sql.raw(\" OR \"),\n )})`,\n },\n ],\n };\n }\n}\n","import type { FieldMap } from \"@pothos/core\";\nimport type { DrizzleObjectFieldBuilder } from \"@pothos/plugin-drizzle\";\nimport { is, One } from \"drizzle-orm\";\nimport { PgColumn } from \"drizzle-orm/pg-core\";\nimport { capitalize } from \"es-toolkit\";\nimport pluralize from \"pluralize\";\nimport type { AbilityBuilderType } from \"./abilityBuilder\";\nimport type { OrderArgImplementerType } from \"./args/orderArg\";\nimport type { WhereArgImplementerType } from \"./args/whereArg\";\nimport { type EnumImplementerType, isEnumSchema } from \"./enum\";\nimport { buildPothosResponseTypeFromGraphQLType } from \"./helpers/sqlTypes/mapDrizzleTypeToGraphQlType\";\nimport type { PossibleSQLType } from \"./helpers/sqlTypes/types\";\nimport { tableHelper } from \"./helpers/tableHelpers\";\nimport type { MakePubSubInstanceType } from \"./pubsub\";\nimport { adjustQueryArgsForSearch } from \"./search\";\nimport type {\n DrizzleInstance,\n DrizzleQueryFunction,\n DrizzleTableValueType,\n TableRelationNames,\n} from \"./types/drizzleInstanceType\";\nimport { RumbleError } from \"./types/rumbleError\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\nimport type { SchemaBuilderType } from \"./types/schemaBuilderType\";\n\n// TODO remove as many as any types as possible here\n\n//TODO this is a bit flaky, we should check if we can determine the config object more reliably\n//TODO maybe a plugin can place some marker field on these objects?\n// like this?\n// if (t instanceof DrizzleObjectOptions) {\n// return true;\n// }\n\nconst isProbablyAConfigObject = (t: any) => {\n if (typeof t !== \"object\") {\n return false;\n }\n\n if (\n Object.keys(t).some((k) =>\n [\n \"args\",\n \"nullable\",\n \"query\",\n \"subscribe\",\n \"description\",\n \"type\",\n \"resolve\",\n ].find((e) => e === k),\n )\n )\n return true;\n return false;\n};\n\nexport const createObjectImplementer = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n Schema extends Record<string, any>,\n>({\n db,\n search,\n logger: loggerConfig,\n schemaBuilder,\n makePubSubInstance,\n whereArgImplementer,\n orderArgImplementer,\n enumImplementer,\n abilityBuilder,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig, Schema> & {\n schemaBuilder: SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n whereArgImplementer: WhereArgImplementerType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n orderArgImplementer: OrderArgImplementerType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n enumImplementer: EnumImplementerType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n any\n >;\n makePubSubInstance: MakePubSubInstanceType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n abilityBuilder: AbilityBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n}) => {\n type SchemaBuilder = SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n return <TableName extends TableRelationNames<DB>, RefName extends string>({\n table,\n refName,\n readAction = \"read\" as Action,\n adjust,\n }: {\n /**\n * The table you want to be used as reference for the object creation.\n */\n table: TableName;\n /**\n * The name you want this object to have in your graphql schema.\n * Rumble will create a reasonable default if not specified.\n */\n refName?: RefName;\n /**\n * The action used for read access to the table.\n * Defaults to \"read\".\n */\n readAction?: Action;\n /**\n * A function which can be used to adjust the fields of the object.\n * You can extend the object by specifying fields that do not exist as\n * per your db schema, or overwrite existing fields with the same name.\n * In case you do overwrite, rumble will set proper nullability and\n * subscription properties if you do not specify them explicitly.\n */\n adjust?:\n | ((\n t: DrizzleObjectFieldBuilder<\n SchemaBuilder[\"$inferSchemaTypes\"],\n SchemaBuilder[\"$inferSchemaTypes\"][\"DrizzleRelations\"][TableName],\n DrizzleTableValueType<DB, TableName>\n >,\n ) => FieldMap)\n | undefined;\n }) => {\n const tableSchema = tableHelper({ db, table });\n\n if (Object.keys(tableSchema.primaryKey).length === 0) {\n const log = loggerConfig?.enabled ? loggerConfig.logger : undefined;\n const msg = `Could not find primary key for ${String(table)}. Cannot register subscriptions!`;\n log\n ? log.warn({ \"rumble.table\": String(table) }, msg)\n : console.warn(msg);\n }\n const primaryKey = Object.values(tableSchema.primaryKey)[0];\n\n const { registerOnInstance } = makePubSubInstance({ table: table });\n\n return schemaBuilder.drizzleObject(table, {\n name: refName ?? capitalize(String(table)),\n subscribe: (subscriptions, element, _context) => {\n if (!primaryKey) return;\n const primaryKeyValue = (element as any)[primaryKey.name];\n if (!primaryKeyValue) {\n const log = loggerConfig?.enabled ? loggerConfig.logger : undefined;\n const msg = `Could not find primary key value for element on ${String(table)}. Cannot register subscription!`;\n log\n ? log.warn({ \"rumble.table\": String(table) }, msg)\n : console.warn(msg);\n return;\n }\n\n //TODO maybe register non specific update calls aswell?\n registerOnInstance({\n instance: subscriptions,\n action: \"updated\",\n primaryKeyValue: primaryKeyValue,\n });\n },\n applyFilters: abilityBuilder?._.registeredFilters({\n table,\n action: readAction,\n }),\n fields: (t) => {\n const columns = tableSchema.columns;\n\n // in case the user makes adjustments we want to store away which\n // pothos function was called with what config\n // this is mapped to the ref which later can be used to\n // reference these parameters while iterating over the fields\n // and checking against the userAdjustments object\n // this is necessary to e.g. merge nullability info from the database schema\n // or register subscriptions on relations\n const configMap = new Map<\n any,\n {\n creatorFunction: (...p: any[]) => any;\n params: any[];\n configObject: any;\n }\n >();\n // stores the results of the user adjustments\n // also stores all the used pothos functions and the configs\n // provided by the user so we can extend that if necessary\n const userAdjustments =\n adjust?.(\n new Proxy(t, {\n get: (target, prop, _receiver) => {\n if (\n // we only care for field/relation functions\n typeof (target as any)[prop] !== \"function\" ||\n prop === \"arg\" ||\n prop === \"builder\" ||\n prop === \"graphqlKind\" ||\n prop === \"kind\" ||\n prop === \"listRef\" ||\n prop === \"table\" ||\n prop === \"typename\" ||\n prop === \"variant\" ||\n prop.toString().startsWith(\"boolean\") ||\n prop.toString().startsWith(\"float\") ||\n prop.toString().startsWith(\"id\") ||\n prop.toString().startsWith(\"int\") ||\n prop.toString().startsWith(\"string\") ||\n prop.toString().startsWith(\"expose\")\n ) {\n return (target as any)[prop];\n }\n\n return (...params: any[]) => {\n const ref = (target as any)[prop](...params);\n const configObject = params.find(isProbablyAConfigObject);\n if (!configObject)\n throw new RumbleError(\n \"Expected config object to be passed to adjust field\",\n );\n\n configMap.set(ref, {\n params,\n creatorFunction: (target as any)[prop],\n configObject,\n });\n return ref;\n };\n },\n }) as any,\n ) ?? {};\n\n const fields = Object.entries(columns).reduce(\n (acc, [key, column]) => {\n // GraphQL reserves all names beginning with \"__\" for introspection.\n // Skip such columns silently — the user must expose them manually\n // via `adjust` if they truly need them.\n if (key.startsWith(\"__\")) {\n console.warn(\n `Skipping column \"${key}\" on table \"${tableSchema.tsName}\": names starting with \"__\" are reserved by GraphQL introspection. Use a custom adjust() call if you really need to expose this column.`,\n );\n return acc;\n }\n\n // in case the user wants to overwrite a field\n // we want to merge with our stuff in case the user\n // did not specify it themselves\n if (userAdjustments[key]) {\n const { params, creatorFunction, configObject } = configMap.get(\n userAdjustments[key],\n )!;\n\n if (typeof configObject.nullable !== \"boolean\") {\n configObject.nullable = !column.notNull;\n }\n\n userAdjustments[key] = creatorFunction.bind(t)(...params);\n return acc;\n }\n\n // Array columns only exist on Postgres; `dimensions` is a runtime\n // property of PgColumn instances. Gate via is() so MySQL/SQLite\n // columns aren't probed for a field they don't have.\n let isArray = false;\n if (is(column, PgColumn)) {\n const dimensions = (column as PgColumn & { dimensions?: number })\n .dimensions;\n if (dimensions && dimensions > 0) {\n if (dimensions !== 1) {\n throw new RumbleError(\n \"Only one-dimensional arrays are supported for default object implementation\",\n );\n }\n isArray = true;\n }\n }\n\n if (isEnumSchema(column)) {\n const enumImpl = enumImplementer({\n enumColumn: column,\n });\n\n acc[key] = t.field({\n type: isArray ? [enumImpl] : enumImpl,\n resolve: (element) => (element as any)[key],\n nullable: !column.notNull,\n });\n } else {\n acc[key] = buildPothosResponseTypeFromGraphQLType({\n builder: t,\n sqlType: column.getSQLType() as PossibleSQLType,\n fieldName: key,\n nullable: !column.notNull,\n isArray,\n });\n }\n return acc;\n },\n {} as Record<\n keyof typeof columns,\n | ReturnType<typeof buildPothosResponseTypeFromGraphQLType>\n | ReturnType<typeof t.field>\n >,\n );\n\n const relations = Object.entries(tableSchema.relations ?? {}).reduce(\n (acc, [key, value]) => {\n const targetTsName = (value as any).targetTableName as string;\n const relationSchema = tableHelper({\n db,\n table: targetTsName,\n });\n const WhereArg = whereArgImplementer({\n dbName: relationSchema.dbName,\n });\n const OrderArg = orderArgImplementer({\n dbName: relationSchema.dbName,\n });\n const relationTablePubSub = makePubSubInstance({\n table: relationSchema.tsName as any,\n });\n\n // many relations will return an empty array so we just don't set them nullable\n let nullable = false;\n let isMany = true;\n let filterSpecifier = \"many\";\n if (is(value, One)) {\n isMany = false;\n nullable =\n value.optional ||\n !value.sourceColumns.every((column) => column.notNull);\n filterSpecifier = \"single\";\n }\n\n const subscribe = (subscriptions: any, _element: any) => {\n relationTablePubSub.registerOnInstance({\n instance: subscriptions,\n action: \"created\",\n });\n relationTablePubSub.registerOnInstance({\n instance: subscriptions,\n action: \"removed\",\n });\n };\n\n // in case the user wants to overwrite a field\n // we want to merge with our stuff in case the user\n // did not specify it themselves\n if (userAdjustments[key]) {\n const { params, creatorFunction, configObject } = configMap.get(\n userAdjustments[key],\n )!;\n\n if (typeof configObject.nullable !== \"boolean\") {\n configObject.nullable = nullable;\n }\n\n if (typeof configObject.subscribe !== \"function\") {\n configObject.subscribe = subscribe;\n }\n\n userAdjustments[key] = creatorFunction.bind(t)(...params);\n return acc;\n }\n\n const args = {\n where: t.arg({ type: WhereArg, required: false }),\n orderBy: t.arg({ type: OrderArg, required: false }),\n ...(isMany\n ? {\n offset: t.arg.int({ required: false }),\n limit: t.arg.int({ required: false }),\n }\n : {}),\n search: t.arg.string({ required: false }),\n };\n\n if (!search?.enabled || !isMany) {\n delete (args as any).search;\n }\n\n (acc as any)[key] = t.relation(\n key as any,\n {\n args,\n subscribe,\n nullable,\n description: `Get the ${pluralize.plural(relationSchema.tsName)} related to this ${pluralize.singular(tableSchema.tsName)}`,\n query: (args: any, ctx: any) => {\n // transform null prototyped object\n args = JSON.parse(JSON.stringify(args));\n\n if (isMany) {\n adjustQueryArgsForSearch({\n search,\n args,\n tableSchema: relationSchema,\n abilities:\n ctx.abilities[relationSchema.tsName].filter(readAction),\n });\n }\n\n const filter = ctx.abilities[relationSchema.tsName]\n .filter(readAction)\n .merge({\n where: args.where,\n limit: args.limit,\n extras: args.extras,\n }).query[filterSpecifier];\n\n if (args.offset) {\n (filter as any).offset = args.offset;\n }\n\n if (args.orderBy) {\n (filter as any).orderBy = args.orderBy;\n }\n\n return filter;\n },\n } as any,\n ) as any;\n return acc;\n },\n {} as Record<\n keyof typeof tableSchema.relations,\n ReturnType<typeof buildPothosResponseTypeFromGraphQLType>\n >,\n );\n\n if (search?.enabled) {\n if (fields.search_distance) {\n throw new Error(\n \"Reserved field name 'search_distance' found on \" +\n tableSchema.tsName +\n \". If search is enabled, the 'search_distance' field is automatically added and cannot be defined manually.\",\n );\n }\n\n fields.search_distance = t.float({\n description:\n \"The search distance of the object. If a search is provided, this field will be populated with the search distance.\",\n nullable: true,\n resolve: (parent, _args, _ctx, _info) =>\n (parent as any).search_distance,\n });\n }\n\n return {\n ...fields,\n ...relations,\n ...userAdjustments,\n };\n },\n });\n };\n};\n","import { createPubSub } from \"graphql-yoga\";\nimport type {\n DrizzleInstance,\n DrizzleQueryFunction,\n} from \"./types/drizzleInstanceType\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\n\ntype PubSubAction = \"created\" | \"removed\" | \"updated\";\n\nconst SUBSCRIPTION_NOTIFIER_RUMBLE_PREFIX = \"RUMBLE_SUBSCRIPTION_NOTIFICATION\";\nconst SUBSCRIPTION_NOTIFIER_REMOVED = \"REMOVED\";\nconst SUBSCRIPTION_NOTIFIER_UPDATED = \"UPDATED\";\nconst SUBSCRIPTION_NOTIFIER_CREATED = \"CREATED\";\n\nexport type MakePubSubInstanceType<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n> = ReturnType<\n typeof createPubSubInstance<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >\n>[\"makePubSubInstance\"];\n\nexport const createPubSubInstance = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>({\n subscriptions,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig>) => {\n const pubsub = subscriptions\n ? createPubSub(...subscriptions)\n : createPubSub();\n\n const makePubSubInstance = <\n TableName extends keyof DrizzleQueryFunction<DB>,\n >({\n table,\n }: {\n table: TableName;\n }) => {\n type PrimaryKeyType = any;\n\n function makePubSubKey({\n action,\n tableName,\n primaryKeyValue,\n }: {\n tableName: string;\n action: PubSubAction;\n primaryKeyValue?: PrimaryKeyType;\n }) {\n let actionKey: string;\n\n switch (action) {\n case \"created\":\n actionKey = SUBSCRIPTION_NOTIFIER_CREATED;\n break;\n case \"removed\":\n actionKey = SUBSCRIPTION_NOTIFIER_REMOVED;\n break;\n case \"updated\":\n actionKey = SUBSCRIPTION_NOTIFIER_UPDATED;\n break;\n default:\n throw new Error(`Unknown action: ${action}`);\n }\n\n return `${SUBSCRIPTION_NOTIFIER_RUMBLE_PREFIX}/${tableName}${\n primaryKeyValue ? `/${primaryKeyValue}` : \"\"\n }/${actionKey}`;\n }\n\n // TODO does caching these make sense?\n return {\n /**\n * Call this when you want to register a subscription on an instance to this table\n */\n registerOnInstance({\n instance,\n action,\n primaryKeyValue,\n }: {\n instance: { register: (id: string) => void };\n action: PubSubAction;\n primaryKeyValue?: string;\n }) {\n const key = makePubSubKey({\n tableName: table.toString(),\n action,\n primaryKeyValue,\n });\n instance.register(key);\n },\n /**\n * Call this when you created an entity of this table\n */\n created() {\n const key = makePubSubKey({\n tableName: table.toString(),\n action: \"created\",\n });\n return pubsub.publish(key);\n },\n /**\n * Call this when you removed one or more entities of this table\n */\n // removed(primaryKeyValue?: PrimaryKeyType | PrimaryKeyType[]) {\n removed() {\n const key = makePubSubKey({\n tableName: table.toString(),\n action: \"removed\",\n //TODO would it make sense to use specific sub topics here?\n // primaryKeyValue,\n });\n return pubsub.publish(key);\n },\n /**\n * Call this when you updated one or more entities of this table\n */\n updated(primaryKeyValue?: PrimaryKeyType | PrimaryKeyType[]) {\n const primaryKeys = Array.isArray(primaryKeyValue)\n ? primaryKeyValue\n : [primaryKeyValue];\n const keys = primaryKeys.map((primaryKeyValue) =>\n makePubSubKey({\n tableName: table.toString(),\n action: \"updated\",\n primaryKeyValue,\n }),\n );\n const uniqueKeys = Array.from(new Set(keys));\n for (const key of uniqueKeys) {\n pubsub.publish(key);\n }\n },\n };\n };\n\n return {\n pubsub,\n makePubSubInstance,\n };\n};\n","import { sql } from \"drizzle-orm\";\nimport pluralize from \"pluralize\";\nimport type { OrderArgImplementerType } from \"./args/orderArg\";\nimport type { WhereArgImplementerType } from \"./args/whereArg\";\nimport { assertFindFirstExists } from \"./helpers/asserts\";\nimport { isPostgresDB } from \"./helpers/determineDialectFromSchema\";\nimport { mapNullFieldsToUndefined } from \"./helpers/mapNullFieldsToUndefined\";\nimport { deepSetProto } from \"./helpers/protoMapper\";\nimport { tableHelper } from \"./helpers/tableHelpers\";\nimport type { MakePubSubInstanceType } from \"./pubsub\";\nimport { adjustQueryArgsForSearch } from \"./search\";\nimport type {\n DrizzleInstance,\n DrizzleQueryFunction,\n TableRelationNames,\n} from \"./types/drizzleInstanceType\";\nimport { RumbleError } from \"./types/rumbleError\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\nimport type { SchemaBuilderType } from \"./types/schemaBuilderType\";\n\nexport const createQueryImplementer = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n Schema extends Record<string, any>,\n>({\n db,\n schemaBuilder,\n search,\n logger: loggerConfig,\n whereArgImplementer,\n orderArgImplementer,\n makePubSubInstance,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig, Schema> & {\n schemaBuilder: SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n whereArgImplementer: WhereArgImplementerType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n orderArgImplementer: OrderArgImplementerType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n makePubSubInstance: MakePubSubInstanceType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n}) => {\n const registeredQueryFieldNames = new Set<string>();\n\n return <TableName extends TableRelationNames<DB>>({\n table,\n readAction = \"read\" as Action,\n listAction = \"read\" as Action,\n findFirst,\n findMany,\n }: {\n /**\n * The table for which to implement the query\n */\n table: TableName;\n /**\n * Which action should be used for reading single entities\n * @default \"read\"\n */\n readAction?: Action;\n /**\n * Which action should be used for listing many entities\n * @default \"read\"\n */\n listAction?: Action;\n\n findMany?: (p: {\n tx: DB | Parameters<Parameters<DB[\"transaction\"]>[0]>[0];\n filter: Parameters<DrizzleQueryFunction<DB>[TableName][\"findMany\"]>[0];\n queryArgs: Parameters<DrizzleQueryFunction<DB>[TableName][\"findMany\"]>[0];\n }) => ReturnType<DrizzleQueryFunction<DB>[TableName][\"findMany\"]>;\n\n findFirst?: (p: {\n tx: DB;\n filter: Parameters<DrizzleQueryFunction<DB>[TableName][\"findFirst\"]>[0];\n queryArgs: Parameters<\n DrizzleQueryFunction<DB>[TableName][\"findFirst\"]\n >[0];\n }) => ReturnType<DrizzleQueryFunction<DB>[TableName][\"findFirst\"]>;\n }) => {\n const WhereArg = whereArgImplementer({\n table: table,\n });\n const OrderArg = orderArgImplementer({\n table: table,\n });\n const tableSchema = tableHelper({\n db,\n table,\n });\n const primaryKeyField = Object.values(tableSchema.primaryKey)[0];\n\n const { registerOnInstance } = makePubSubInstance({ table: table });\n\n const pluralName = pluralize.plural(String(table));\n const singularName = pluralize.singular(String(table));\n for (const name of [pluralName, singularName]) {\n if (registeredQueryFieldNames.has(name)) {\n throw new RumbleError(\n `Duplicate query field \"${name}\": the table \"${String(table)}\" generates a ` +\n `query field that collides with one already registered. Use unique table names ` +\n `(or refNames) to avoid plural/singular collisions (e.g. \"post\" and \"posts\").`,\n );\n }\n registeredQueryFieldNames.add(name);\n }\n\n return schemaBuilder.queryFields((t) => {\n const manyArgs = {\n where: t.arg({ type: WhereArg, required: false }),\n orderBy: t.arg({ type: OrderArg, required: false }),\n limit: t.arg.int({ required: false }),\n offset: t.arg.int({ required: false }),\n search: t.arg.string({ required: false }),\n };\n\n if (!search?.enabled) {\n delete (manyArgs as any).search;\n }\n\n return {\n [pluralName]: t.drizzleField({\n type: [table],\n nullable: false,\n smartSubscription: true,\n description: `List all ${pluralName}`,\n subscribe: (subscriptions, _root, _args, _ctx, _info) => {\n registerOnInstance({\n instance: subscriptions,\n action: \"created\",\n });\n registerOnInstance({\n instance: subscriptions,\n action: \"removed\",\n });\n },\n args: manyArgs,\n resolve: (query, _root, args, ctx, _info) => {\n // args does not have Object.prototype as prototype, so we need to set it\n // otherwise some libraries (like drizzle-orm) might have issues with it\n deepSetProto(args);\n\n adjustQueryArgsForSearch({\n search,\n args,\n tableSchema,\n abilities: ctx.abilities[table].filter(listAction),\n });\n\n const mappedArgs = mapNullFieldsToUndefined(args);\n const filter = ctx.abilities[table]\n .filter(listAction)\n .merge(mappedArgs as any).query.many;\n\n if (mappedArgs.offset) {\n (filter as any).offset = mappedArgs.offset;\n }\n\n if (mappedArgs.orderBy) {\n (filter as any).orderBy = mappedArgs.orderBy;\n }\n\n const queryArgs = query(filter as any);\n\n if ((filter as any).columns) {\n queryArgs.columns = (filter as any).columns;\n }\n\n const run = findMany\n ? (tx: DB) => findMany({ tx, filter: filter as any, queryArgs })\n : (tx: any) => (tx.query as any)[table].findMany(queryArgs);\n\n if (\n search?.enabled &&\n args.search &&\n args.search.length > 0 &&\n search?.cpu_operator_cost\n ) {\n return db.transaction(async (tx: any) => {\n if (isPostgresDB(tx)) {\n await tx.execute(\n sql.raw(\n `SET cpu_operator_cost = ${search.cpu_operator_cost};`,\n ),\n );\n } else {\n const msg =\n \"Database dialect is not postgresql, cannot set cpu_operator_cost.\";\n const log = loggerConfig?.enabled\n ? loggerConfig.logger\n : undefined;\n log ? log.info({}, msg) : console.info(msg);\n }\n\n return run(tx);\n });\n }\n\n return run(db);\n },\n }),\n [singularName]: t.drizzleField({\n type: table,\n nullable: false,\n smartSubscription: true,\n description: `Get a single ${singularName} by ID`,\n args: {\n id: t.arg.id({ required: true }),\n },\n resolve: (query, _root, args, ctx, _info) => {\n deepSetProto(args);\n\n const filter = (ctx.abilities as any)[table]\n .filter(readAction)\n .merge({ where: { [primaryKeyField.name]: args.id } })\n .query.single;\n const queryArgs = query(filter);\n\n if (filter.columns) {\n queryArgs.columns = filter.columns;\n }\n\n return findFirst\n ? findFirst({ tx: db, filter: filter as any, queryArgs })\n : (db.query as any)[table]\n .findFirst(queryArgs)\n .then(assertFindFirstExists);\n },\n }),\n };\n });\n };\n};\n","export type NumberWhereInputArgument = {\n eq?: number;\n ne?: number;\n gt?: number;\n gte?: number;\n lt?: number;\n lte?: number;\n in?: number[];\n notIn?: number[];\n like?: string;\n ilike?: string;\n notLike?: string;\n notIlike?: string;\n isNull?: boolean;\n isNotNull?: boolean;\n arrayOverlaps?: number[];\n arrayContained?: number[];\n arrayContains?: number[];\n AND?: NumberWhereInputArgument[];\n OR?: NumberWhereInputArgument[];\n NOT?: NumberWhereInputArgument;\n};\n\nexport type StringWhereInputArgument = {\n eq?: string;\n ne?: string;\n gt?: string;\n gte?: string;\n lt?: string;\n lte?: string;\n in?: string[];\n notIn?: string[];\n like?: string;\n ilike?: string;\n notLike?: string;\n notIlike?: string;\n isNull?: boolean;\n isNotNull?: boolean;\n arrayOverlaps?: string[];\n arrayContained?: string[];\n arrayContains?: string[];\n AND?: StringWhereInputArgument[];\n OR?: StringWhereInputArgument[];\n NOT?: StringWhereInputArgument;\n};\n\nexport type DateWhereInputArgument = {\n eq?: Date;\n ne?: Date;\n gt?: Date;\n gte?: Date;\n lt?: Date;\n lte?: Date;\n in?: Date[];\n notIn?: Date[];\n like?: string;\n ilike?: string;\n notLike?: string;\n notIlike?: string;\n isNull?: boolean;\n isNotNull?: boolean;\n arrayOverlaps?: Date[];\n arrayContained?: Date[];\n arrayContains?: Date[];\n AND?: DateWhereInputArgument[];\n OR?: DateWhereInputArgument[];\n NOT?: DateWhereInputArgument;\n};\n\nexport type BooleanWhereInputArgument = {\n eq?: boolean;\n ne?: boolean;\n in?: boolean[];\n notIn?: boolean[];\n isNull?: boolean;\n isNotNull?: boolean;\n arrayOverlaps?: boolean[];\n arrayContained?: boolean[];\n arrayContains?: boolean[];\n AND?: BooleanWhereInputArgument[];\n OR?: BooleanWhereInputArgument[];\n NOT?: BooleanWhereInputArgument;\n};\n\nexport type IDWhereInputArgument = {\n eq?: string;\n ne?: string;\n gt?: string;\n gte?: string;\n lt?: string;\n lte?: string;\n in?: string[];\n notIn?: string[];\n like?: string;\n ilike?: string;\n notLike?: string;\n notIlike?: string;\n isNull?: boolean;\n isNotNull?: boolean;\n arrayOverlaps?: string[];\n arrayContained?: string[];\n arrayContains?: string[];\n AND?: IDWhereInputArgument[];\n OR?: IDWhereInputArgument[];\n NOT?: IDWhereInputArgument;\n};\n\nexport type JSONWhereInputArgument = {\n eq?: unknown;\n ne?: unknown;\n in?: unknown[];\n notIn?: unknown[];\n isNull?: boolean;\n isNotNull?: boolean;\n arrayOverlaps?: unknown[];\n arrayContained?: unknown[];\n arrayContains?: unknown[];\n AND?: JSONWhereInputArgument[];\n OR?: JSONWhereInputArgument[];\n NOT?: JSONWhereInputArgument;\n};\n\nexport type BigIntWhereInputArgument = {\n eq?: bigint | number;\n ne?: bigint | number;\n gt?: bigint | number;\n gte?: bigint | number;\n lt?: bigint | number;\n lte?: bigint | number;\n in?: (bigint | number)[];\n notIn?: (bigint | number)[];\n isNull?: boolean;\n isNotNull?: boolean;\n AND?: BigIntWhereInputArgument[];\n OR?: BigIntWhereInputArgument[];\n NOT?: BigIntWhereInputArgument;\n};\n\nexport type DateTimeWhereInputArgument = {\n eq?: Date;\n ne?: Date;\n gt?: Date;\n gte?: Date;\n lt?: Date;\n lte?: Date;\n in?: Date[];\n notIn?: Date[];\n isNull?: boolean;\n isNotNull?: boolean;\n arrayOverlaps?: Date[];\n arrayContained?: Date[];\n arrayContains?: Date[];\n AND?: DateTimeWhereInputArgument[];\n OR?: DateTimeWhereInputArgument[];\n NOT?: DateTimeWhereInputArgument;\n};\n\n// TODO: Add proper type for schemaBuilder\n\nexport function implementDefaultWhereInputArgs(schemaBuilder: any) {\n const IntWhereInputArgument = schemaBuilder\n .inputRef(\"IntWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.int(),\n ne: t.int(),\n gt: t.int(),\n gte: t.int(),\n lt: t.int(),\n lte: t.int(),\n in: t.intList(),\n notIn: t.intList(),\n like: t.string(),\n ilike: t.string(),\n notLike: t.string(),\n notIlike: t.string(),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.intList(),\n arrayContained: t.intList(),\n arrayContains: t.intList(),\n AND: t.field({\n type: [IntWhereInputArgument],\n }),\n OR: t.field({\n type: [IntWhereInputArgument],\n }),\n NOT: t.field({\n type: IntWhereInputArgument,\n }),\n }),\n });\n\n const FloatWhereInputArgument = schemaBuilder\n .inputRef(\"FloatWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.float(),\n ne: t.float(),\n gt: t.float(),\n gte: t.float(),\n lt: t.float(),\n lte: t.float(),\n in: t.floatList(),\n notIn: t.floatList(),\n like: t.string(),\n ilike: t.string(),\n notLike: t.string(),\n notIlike: t.string(),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.floatList(),\n arrayContained: t.floatList(),\n arrayContains: t.floatList(),\n AND: t.field({\n type: [FloatWhereInputArgument],\n }),\n OR: t.field({\n type: [FloatWhereInputArgument],\n }),\n NOT: t.field({\n type: FloatWhereInputArgument,\n }),\n }),\n });\n\n const StringWhereInputArgument = schemaBuilder\n .inputRef(\"StringWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.string(),\n ne: t.string(),\n gt: t.string(),\n gte: t.string(),\n lt: t.string(),\n lte: t.string(),\n in: t.stringList(),\n notIn: t.stringList(),\n like: t.string(),\n ilike: t.string(),\n notLike: t.string(),\n notIlike: t.string(),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.stringList(),\n arrayContained: t.stringList(),\n arrayContains: t.stringList(),\n AND: t.field({\n type: [StringWhereInputArgument],\n }),\n OR: t.field({\n type: [StringWhereInputArgument],\n }),\n NOT: t.field({\n type: StringWhereInputArgument,\n }),\n }),\n });\n\n const DateWhereInputArgument = schemaBuilder\n .inputRef(\"DateWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.field({ type: \"Date\" }),\n ne: t.field({ type: \"Date\" }),\n gt: t.field({ type: \"Date\" }),\n gte: t.field({ type: \"Date\" }),\n lt: t.field({ type: \"Date\" }),\n lte: t.field({ type: \"Date\" }),\n in: t.field({ type: [\"Date\"] }),\n notIn: t.field({ type: [\"Date\"] }),\n like: t.string(),\n ilike: t.string(),\n notLike: t.string(),\n notIlike: t.string(),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.field({ type: [\"Date\"] }),\n arrayContained: t.field({ type: [\"Date\"] }),\n arrayContains: t.field({ type: [\"Date\"] }),\n AND: t.field({\n type: [DateWhereInputArgument],\n }),\n OR: t.field({\n type: [DateWhereInputArgument],\n }),\n NOT: t.field({\n type: DateWhereInputArgument,\n }),\n }),\n });\n\n const BooleanWhereInputArgument = schemaBuilder\n .inputRef(\"BooleanWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.boolean(),\n ne: t.boolean(),\n in: t.booleanList(),\n notIn: t.booleanList(),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.booleanList(),\n arrayContained: t.booleanList(),\n arrayContains: t.booleanList(),\n AND: t.field({\n type: [BooleanWhereInputArgument],\n }),\n OR: t.field({\n type: [BooleanWhereInputArgument],\n }),\n NOT: t.field({\n type: BooleanWhereInputArgument,\n }),\n }),\n });\n\n const IDWhereInputArgument = schemaBuilder\n .inputRef(\"IDWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.id(),\n ne: t.id(),\n gt: t.id(),\n gte: t.id(),\n lt: t.id(),\n lte: t.id(),\n in: t.idList(),\n notIn: t.idList(),\n like: t.string(),\n ilike: t.string(),\n notLike: t.string(),\n notIlike: t.string(),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.idList(),\n arrayContained: t.idList(),\n arrayContains: t.idList(),\n AND: t.field({\n type: [IDWhereInputArgument],\n }),\n OR: t.field({\n type: [IDWhereInputArgument],\n }),\n NOT: t.field({\n type: IDWhereInputArgument,\n }),\n }),\n });\n\n const JSONWhereInputArgument = schemaBuilder\n .inputRef(\"JSONWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.field({ type: \"JSON\", required: false }),\n ne: t.field({ type: \"JSON\", required: false }),\n in: t.field({ type: [\"JSON\"], required: false }),\n notIn: t.field({ type: [\"JSON\"], required: false }),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.field({ type: [\"JSON\"], required: false }),\n arrayContained: t.field({ type: [\"JSON\"], required: false }),\n arrayContains: t.field({ type: [\"JSON\"], required: false }),\n AND: t.field({\n type: [JSONWhereInputArgument],\n }),\n OR: t.field({\n type: [JSONWhereInputArgument],\n }),\n NOT: t.field({\n type: JSONWhereInputArgument,\n }),\n }),\n });\n\n const BigIntWhereInputArgument = schemaBuilder\n .inputRef(\"BigIntWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.field({ type: \"BigInt\", required: false }),\n ne: t.field({ type: \"BigInt\", required: false }),\n gt: t.field({ type: \"BigInt\", required: false }),\n gte: t.field({ type: \"BigInt\", required: false }),\n lt: t.field({ type: \"BigInt\", required: false }),\n lte: t.field({ type: \"BigInt\", required: false }),\n in: t.field({ type: [\"BigInt\"], required: false }),\n notIn: t.field({ type: [\"BigInt\"], required: false }),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n AND: t.field({ type: [BigIntWhereInputArgument] }),\n OR: t.field({ type: [BigIntWhereInputArgument] }),\n NOT: t.field({ type: BigIntWhereInputArgument }),\n }),\n });\n\n const DateTimeWhereInputArgument = schemaBuilder\n .inputRef(\"DateTimeWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.field({ type: \"DateTime\", required: false }),\n ne: t.field({ type: \"DateTime\", required: false }),\n gt: t.field({ type: \"DateTime\", required: false }),\n gte: t.field({ type: \"DateTime\", required: false }),\n lt: t.field({ type: \"DateTime\", required: false }),\n lte: t.field({ type: \"DateTime\", required: false }),\n in: t.field({ type: [\"DateTime\"], required: false }),\n notIn: t.field({ type: [\"DateTime\"], required: false }),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.field({ type: [\"DateTime\"], required: false }),\n arrayContained: t.field({ type: [\"DateTime\"], required: false }),\n arrayContains: t.field({ type: [\"DateTime\"], required: false }),\n AND: t.field({ type: [DateTimeWhereInputArgument] }),\n OR: t.field({ type: [DateTimeWhereInputArgument] }),\n NOT: t.field({ type: DateTimeWhereInputArgument }),\n }),\n });\n}\n","export type Prefetch<Context, ReturnType> = (params: {\n context: Context;\n}) => Promise<ReturnType>;\n\nexport type Filter<\n Context,\n FilteredEntityType,\n PrefetchReturnType = never,\n> = (p: {\n context: Context;\n entities: FilteredEntityType[];\n prefetched: PrefetchReturnType;\n}) => FilteredEntityType[] | Promise<FilteredEntityType[]>;\n\nexport type FilterPrefetchCombo<\n Context,\n FilteredEntityType,\n PrefetchReturnType = never,\n> = {\n filter: Filter<Context, FilteredEntityType, PrefetchReturnType>;\n prefetch?: Prefetch<Context, PrefetchReturnType>;\n};\n\nexport type ApplyFiltersField<Context, T> =\n | FilterPrefetchCombo<Context, T>\n | FilterPrefetchCombo<Context, T>[]\n | undefined;\n\nexport const pluginName = \"RuntimeFiltersPlugin\" as const;\n","import type { Span, Tracer } from \"@opentelemetry/api\";\nimport SchemaBuilder, {\n BasePlugin,\n type PothosOutputFieldConfig,\n type PothosTypeConfig,\n type SchemaTypes,\n} from \"@pothos/core\";\nimport DataLoader from \"dataloader\";\nimport type { GraphQLFieldResolver } from \"graphql\";\nimport { errorLogField } from \"../helpers/errorLogging\";\nimport type { RumbleLogger } from \"../types/rumbleInput\";\nimport {\n type ApplyFiltersField,\n type FilterPrefetchCombo,\n pluginName,\n} from \"./filterTypes\";\n\nexport const applyFiltersKey = \"applyFilters\";\n\ntype AnyFilterCombo = FilterPrefetchCombo<any, any, any>;\n\nexport class RuntimeFiltersPlugin<\n Types extends SchemaTypes,\n> extends BasePlugin<Types> {\n private tracer?: Tracer;\n private tracerEnabled?: boolean;\n private logger?: RumbleLogger;\n\n // graphql-js resolves a relation field once per sibling in a list, concurrently,\n // so without this a filter like \"can read user\" would fire once per row instead\n // of once for the whole list. Keying loaders by context means they get garbage\n // collected once the request is done, no manual cleanup needed.\n private filterLoaders = new WeakMap<\n object,\n Map<AnyFilterCombo, DataLoader<any, any>>\n >();\n\n private getLoader(\n context: Types[\"Context\"],\n filter: AnyFilterCombo,\n ): DataLoader<any, any> {\n let perContext = this.filterLoaders.get(context as object);\n if (!perContext) {\n perContext = new Map();\n this.filterLoaders.set(context as object, perContext);\n }\n\n let loader = perContext.get(filter);\n if (!loader) {\n // not awaited here on purpose, so it runs alongside the resolver instead of after it\n const prefetchPromise = filter.prefetch\n ? filter.prefetch({ context })\n : undefined;\n\n loader = new DataLoader<any, any>(\n async (entities) => {\n const prefetched = prefetchPromise\n ? await prefetchPromise\n : undefined;\n const allowed = await filter.filter({\n context,\n entities: entities as any[],\n prefetched,\n } as any);\n const allowedSet = new Set(allowed);\n return entities.map((entity) =>\n allowedSet.has(entity) ? entity : null,\n );\n },\n // cache off on purpose, we only want the batching, filters should still\n // run fresh every time like before\n { cache: false },\n );\n perContext.set(filter, loader);\n }\n\n return loader;\n }\n\n override onTypeConfig(typeConfig: PothosTypeConfig) {\n this.tracer = this.builder.options.otel?.tracer;\n this.tracerEnabled = this.builder.options.otel?.enabled;\n this.logger = this.builder.options.logger?.enabled\n ? this.builder.options.logger.logger\n : undefined;\n return typeConfig;\n }\n\n override wrapResolve(\n resolver: GraphQLFieldResolver<unknown, Types[\"Context\"], object>,\n fieldConfig: PothosOutputFieldConfig<Types>,\n ): GraphQLFieldResolver<unknown, Types[\"Context\"], object> {\n return async (parent, args, context, info) => {\n let filters: ApplyFiltersField<Types[\"Context\"], any> | undefined;\n const fieldType = fieldConfig?.type as any;\n\n if (fieldType.kind === \"List\") {\n filters =\n fieldType.type?.ref.currentConfig.pothosOptions[applyFiltersKey];\n } else if (fieldType.kind === \"Object\") {\n filters = fieldType.ref.currentConfig.pothosOptions[applyFiltersKey];\n }\n\n if (!filters || !Array.isArray(filters) || filters.length === 0) {\n // if no filter should be applied, just continue\n return resolver(parent, args, context, info);\n }\n\n const runFilters = async (span?: Span) => {\n const allFilters = Array.isArray(filters) ? filters : [filters];\n span?.setAttribute(\"filters.total\", allFilters.length);\n\n const loaders = allFilters.map((filter) =>\n this.getLoader(context, filter as AnyFilterCombo),\n );\n\n let resolved: any;\n\n if (this.tracer && this.tracerEnabled) {\n resolved = await this.tracer.startActiveSpan(\n `rumble.filter.resolve`,\n async (span) => {\n span.setAttribute(\"graphql.field.name\", fieldConfig.name);\n try {\n return await resolver(parent, args, context, info);\n } finally {\n span.end();\n }\n },\n );\n } else {\n resolved = await resolver(parent, args, context, info);\n }\n\n const entities: any[] = Array.isArray(resolved) ? resolved : [resolved];\n\n // load() instead of loadMany() so a thrown filter still rejects here\n // instead of getting swallowed into an Error value\n const perFilterResults = await Promise.all(\n loaders.map((loader) =>\n Promise.all(entities.map((entity) => loader.load(entity))),\n ),\n );\n\n const allowed = entities.filter((_, index) =>\n perFilterResults.some((results) => results[index] != null),\n );\n\n span?.setAttribute(\"filters.allowed\", allowed.length);\n this.logger?.debug(\n {\n \"graphql.field.name\": fieldConfig.name,\n \"filters.total\": allFilters.length,\n \"filters.allowed\": allowed.length,\n },\n \"runtime filters applied\",\n );\n\n // if the original value was an array, return an array\n if (Array.isArray(resolved)) {\n return allowed;\n }\n\n // if the original value was a single value, return the first allowed\n // or null if not allowed\n return allowed[0] ?? null;\n };\n\n if (this.tracer && this.tracerEnabled) {\n return this.tracer.startActiveSpan(\n `rumble.filter.apply`,\n async (span) => {\n span.setAttribute(\"graphql.field.name\", fieldConfig.name);\n try {\n return await runFilters(span);\n } catch (error) {\n this.logger?.error(\n {\n \"graphql.field.name\": fieldConfig.name,\n ...errorLogField(error),\n },\n \"runtime filter threw\",\n );\n throw error;\n } finally {\n span.end();\n }\n },\n );\n } else {\n try {\n return await runFilters();\n } catch (error) {\n this.logger?.error(\n {\n \"graphql.field.name\": fieldConfig.name,\n ...errorLogField(error),\n },\n \"runtime filter threw\",\n );\n throw error;\n }\n }\n };\n }\n}\n\nlet registered = false;\nexport function registerRuntimeFiltersPlugin() {\n if (!registered) {\n SchemaBuilder.registerPlugin(pluginName, RuntimeFiltersPlugin);\n registered = true;\n }\n}\n","import SchemaBuilder from \"@pothos/core\";\nimport DrizzlePlugin from \"@pothos/plugin-drizzle\";\nimport SmartSubscriptionsPlugin, {\n subscribeOptionsFromIterator,\n} from \"@pothos/plugin-smart-subscriptions\";\nimport TracingPlugin, {\n isRootField,\n wrapResolver,\n} from \"@pothos/plugin-tracing\";\nimport { createOpenTelemetryWrapper } from \"@pothos/tracing-opentelemetry\";\nimport { getTableColumns, isTable, type Table } from \"drizzle-orm\";\nimport {\n BigIntResolver,\n ByteResolver,\n DateResolver,\n DateTimeISOResolver,\n JSONResolver,\n} from \"graphql-scalars\";\nimport type { createPubSub } from \"graphql-yoga\";\nimport {\n type BigIntWhereInputArgument,\n type BooleanWhereInputArgument,\n type DateTimeWhereInputArgument,\n type DateWhereInputArgument,\n type IDWhereInputArgument,\n implementDefaultWhereInputArgs,\n type JSONWhereInputArgument,\n type NumberWhereInputArgument,\n type StringWhereInputArgument,\n} from \"./args/whereArgsImplementer\";\nimport type { ContextType } from \"./context\";\nimport { errorLogField } from \"./helpers/errorLogging\";\nimport { pluginName } from \"./runtimeFiltersPlugin/filterTypes\";\nimport { registerRuntimeFiltersPlugin } from \"./runtimeFiltersPlugin/runtimeFiltersPlugin\";\nimport type { DrizzleInstance } from \"./types/drizzleInstanceType\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\n\nexport const createSchemaBuilder = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>({\n db,\n pubsub,\n pothosConfig,\n otel,\n logger,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig> & {\n pubsub: ReturnType<typeof createPubSub>;\n}) => {\n const createSpan =\n otel?.enabled && otel.tracer\n ? createOpenTelemetryWrapper(otel.tracer, otel.options)\n : undefined;\n\n registerRuntimeFiltersPlugin();\n const schemaBuilder = new SchemaBuilder<{\n Context: ContextType<UserContext, DB, RequestEvent, Action, PothosConfig>;\n DrizzleRelations: DB[\"_\"][\"relations\"];\n Scalars: {\n JSON: {\n Input: unknown;\n Output: unknown;\n };\n Date: {\n Input: Date;\n Output: Date;\n };\n DateTime: {\n Input: Date;\n Output: Date | string;\n };\n BigInt: {\n Input: bigint | number;\n Output: bigint | number | string;\n };\n Bytes: {\n Input: string;\n Output: string;\n };\n };\n Inputs: {\n IntWhereInputArgument: NumberWhereInputArgument;\n FloatWhereInputArgument: NumberWhereInputArgument;\n StringWhereInputArgument: StringWhereInputArgument;\n DateWhereInputArgument: DateWhereInputArgument;\n DateTimeWhereInputArgument: DateTimeWhereInputArgument;\n BigIntWhereInputArgument: BigIntWhereInputArgument;\n BooleanWhereInputArgument: BooleanWhereInputArgument;\n IDWhereInputArgument: IDWhereInputArgument;\n JSONWhereInputArgument: JSONWhereInputArgument;\n };\n DefaultFieldNullability: false;\n }>({\n ...pothosConfig,\n plugins: [\n pluginName,\n DrizzlePlugin,\n SmartSubscriptionsPlugin,\n TracingPlugin,\n ...(pothosConfig?.plugins ?? []),\n ],\n drizzle: {\n client: db,\n relations: db._.relations,\n getTableConfig(table) {\n //TODO support composite primary keys\n const columns = isTable(table)\n ? Object.values(getTableColumns(table as Table))\n : [];\n return {\n columns,\n primaryKeys: columns.filter((v: any) => v.primary),\n } as any;\n },\n },\n smartSubscriptions: {\n ...subscribeOptionsFromIterator((name, _context) => {\n return pubsub.subscribe(name);\n }),\n },\n defaultFieldNullability: false,\n tracing: {\n default:\n otel?.enabled || logger?.enabled\n ? (config) => isRootField(config)\n : () => false,\n wrap: (resolver, options, config) => {\n let r = createSpan ? createSpan(resolver, options) : resolver;\n if (logger?.enabled) {\n const log = logger.logger;\n r = wrapResolver(r, (error, duration) => {\n if (error) {\n log.error(\n {\n \"graphql.field.name\": config.name,\n \"graphql.parent.type\": config.parentType,\n duration_ms: duration,\n ...errorLogField(error),\n },\n \"resolver failed\",\n );\n } else {\n log.debug(\n {\n \"graphql.field.name\": config.name,\n \"graphql.parent.type\": config.parentType,\n duration_ms: duration,\n },\n \"resolver completed\",\n );\n }\n });\n }\n return r;\n },\n },\n otel,\n logger,\n });\n\n schemaBuilder.addScalarType(\"JSON\", JSONResolver);\n schemaBuilder.addScalarType(\"Date\", DateResolver);\n schemaBuilder.addScalarType(\"DateTime\", DateTimeISOResolver);\n schemaBuilder.addScalarType(\"BigInt\", BigIntResolver);\n schemaBuilder.addScalarType(\"Bytes\", ByteResolver);\n implementDefaultWhereInputArgs(schemaBuilder);\n\n schemaBuilder.queryType({});\n schemaBuilder.subscriptionType({});\n schemaBuilder.mutationType({});\n\n return { schemaBuilder };\n};\n","import { EnvelopArmorPlugin } from \"@escape.tech/graphql-armor\";\nimport { useDisableIntrospection } from \"@graphql-yoga/plugin-disable-introspection\";\nimport { SpanStatusCode, trace } from \"@opentelemetry/api\";\nimport { merge } from \"es-toolkit\";\nimport { GraphQLSchema } from \"graphql\";\nimport type { ServerOptions } from \"graphql-ws\";\nimport {\n createYoga as nativeCreateYoga,\n type Plugin,\n type YogaServerOptions,\n} from \"graphql-yoga\";\nimport type { useSofa } from \"sofa-api\";\nimport packagejson from \"../package.json\";\nimport { createAbilityBuilder } from \"./abilityBuilder\";\nimport { createOrderArgImplementer } from \"./args/orderArg\";\nimport { createWhereArgImplementer } from \"./args/whereArg\";\nimport { clientCreatorImplementer } from \"./client/client\";\nimport { createContextFunction } from \"./context\";\nimport { createCountQueryImplementer } from \"./countQuery\";\nimport { createEnumImplementer, type EnumFieldKeys } from \"./enum\";\nimport { lazy } from \"./helpers/lazy\";\nimport { sofaOpenAPIWebhookDocs } from \"./helpers/sofaOpenAPIWebhookDocs\";\nimport {\n buildTracedExecute,\n buildTracedSubscribe,\n defaultExecute,\n defaultSubscribe,\n} from \"./helpers/tracing\";\nimport { createObjectImplementer } from \"./object\";\nimport { createPubSubInstance } from \"./pubsub\";\nimport { createQueryImplementer } from \"./query\";\nimport { createSchemaBuilder } from \"./schemaBuilder\";\nimport { initSearchIfApplicable } from \"./search\";\nimport type { DrizzleInstance } from \"./types/drizzleInstanceType\";\nimport { RumbleError } from \"./types/rumbleError\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\n\nexport const rumble = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n PothosConfig extends CustomRumblePothosConfig,\n Schema extends Record<string, any>,\n Action extends string = \"read\" | \"update\" | \"delete\",\n>(\n rumbleInput: RumbleInput<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n > & {\n schema: Schema;\n },\n) => {\n if (!rumbleInput.db._.relations) {\n throw new RumbleError(`\nrumble could not find any relations in the provided drizzle instance.\nMake sure you import the relations and pass them to the drizzle instance:\n\nexport const db = drizzle(\n \"postgres://postgres:postgres@localhost:5432/postgres\",\n {\n relations, // <--- add this line\n },\n);\n\n`);\n }\n\n if (\n !rumbleInput.schema ||\n typeof rumbleInput.schema !== \"object\" ||\n Object.keys(rumbleInput.schema).length === 0\n ) {\n throw new RumbleError(`\nrumble requires the drizzle schema object to be passed when initializing.\nImport your schema module and pass it alongside \\`db\\`:\n\nimport * as schema from \"./db/schema\";\n\nexport const r = rumble({\n db,\n schema, // <--- add this line\n});\n\n`);\n }\n\n // to be able to iterate over the actions, we populate the actions array in case the user does not\n if (!rumbleInput.actions) {\n rumbleInput.actions = [\"read\", \"update\", \"delete\"] as Action[];\n }\n\n if (rumbleInput.defaultLimit === undefined) {\n rumbleInput.defaultLimit = 100;\n }\n\n if (rumbleInput.search?.enabled) {\n initSearchIfApplicable(rumbleInput);\n }\n\n if (rumbleInput.otel?.enabled && !rumbleInput.otel.tracer) {\n rumbleInput.otel.tracer = trace.getTracer(\n \"@m1212e/rumble\",\n packagejson.version,\n );\n }\n\n const abilityBuilder = createAbilityBuilder<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >(rumbleInput);\n\n const context = createContextFunction<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >({\n ...rumbleInput,\n abilityBuilder,\n });\n\n const { makePubSubInstance, pubsub } = createPubSubInstance<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >({\n ...rumbleInput,\n });\n\n const { schemaBuilder } = createSchemaBuilder<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >({ ...rumbleInput, pubsub });\n\n const enum_ = createEnumImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n EnumFieldKeys<Schema>,\n Schema\n >({\n ...rumbleInput,\n schemaBuilder,\n });\n\n const whereArg = createWhereArgImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >({\n ...rumbleInput,\n schemaBuilder,\n enumImplementer: enum_,\n });\n\n const orderArg = createOrderArgImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >({\n ...rumbleInput,\n schemaBuilder,\n });\n\n const object = createObjectImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n Schema\n >({\n ...rumbleInput,\n schemaBuilder,\n makePubSubInstance,\n whereArgImplementer: whereArg,\n orderArgImplementer: orderArg,\n enumImplementer: enum_,\n abilityBuilder,\n });\n\n const query = createQueryImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n Schema\n >({\n ...rumbleInput,\n schemaBuilder,\n whereArgImplementer: whereArg,\n orderArgImplementer: orderArg,\n makePubSubInstance,\n });\n\n const countQuery = createCountQueryImplementer({\n ...rumbleInput,\n schemaBuilder,\n whereArgImplementer: whereArg,\n makePubSubInstance,\n });\n\n const builtSchema = lazy(() => {\n let raw: ReturnType<typeof schemaBuilder.toSchema>;\n try {\n raw = schemaBuilder.toSchema();\n } catch (e: any) {\n const msg: string = e?.message ?? String(e);\n const unimplMatch = msg.match(\n /ObjectRef<(.+?)> has not been implemented/,\n );\n if (unimplMatch) {\n throw new RumbleError(\n `Could not build GraphQL schema: the table \"${unimplMatch[1]}\" is referenced ` +\n `in a relation but has not been registered. Call rumble.object({ table: \"${unimplMatch[1]}\" }) ` +\n `before building the schema.`,\n );\n }\n throw e;\n }\n\n const mutation = raw.getMutationType();\n const subscription = raw.getSubscriptionType();\n const emptyMutation =\n mutation && Object.keys(mutation.getFields()).length === 0;\n const emptySubscription =\n subscription && Object.keys(subscription.getFields()).length === 0;\n\n if (!emptyMutation && !emptySubscription) return raw;\n\n const config = raw.toConfig();\n const filteredTypes = config.types.filter((t) => {\n if (emptyMutation && t === mutation) return false;\n if (emptySubscription && t === subscription) return false;\n return true;\n });\n return new GraphQLSchema({\n ...config,\n mutation: emptyMutation ? undefined : config.mutation,\n subscription: emptySubscription ? undefined : config.subscription,\n types: filteredTypes,\n });\n });\n\n const createYoga = (\n args?:\n | (Omit<YogaServerOptions<RequestEvent, any>, \"schema\" | \"context\"> & {\n /**\n * Determines if the API should disclose various things about its structure.\n * Defaults to `process.env.NODE_ENV === \"development\"`.\n * If enabled, the api will allow introspection requests, provide the graphiql\n * explorer and will not apply the additional envelop armor plugin.\n */\n enableApiDocs?: boolean;\n /**\n * Optional configuration passed to the auto-installed graphql-armor\n * EnvelopArmorPlugin. Only applied when `enableApiDocs` is false\n * (i.e. in production). Useful for relaxing the default depth/alias/\n * directive/token limits when the generated schema legitimately exceeds\n * them. See https://github.com/Escape-Technologies/graphql-armor for available options.\n *\n * @example\n * createYoga({ armorConfig: { maxDepth: { n: 20 } } })\n */\n armorConfig?: Parameters<typeof EnvelopArmorPlugin>[0];\n })\n | undefined,\n ) => {\n const enableApiDocs =\n args?.enableApiDocs ?? process?.env?.NODE_ENV === \"development\";\n\n return nativeCreateYoga<RequestEvent>({\n ...args,\n graphiql: enableApiDocs,\n schema: builtSchema(),\n context,\n plugins: [\n ...(args?.plugins ?? []),\n ...(enableApiDocs\n ? []\n : [useDisableIntrospection(), EnvelopArmorPlugin(args?.armorConfig)]),\n rumbleInput.otel?.enabled || rumbleInput.logger?.enabled\n ? ({\n // TODO: add trace header per default in http response\n // TODO: Automatic Persisted Queries\n onExecute: ({ setExecuteFn, executeFn }) => {\n setExecuteFn(\n buildTracedExecute(\n executeFn,\n rumbleInput,\n ) as typeof executeFn,\n );\n },\n } as Plugin)\n : false,\n ].filter(Boolean),\n });\n };\n\n const createSofa = async (\n args: Omit<Parameters<typeof useSofa>[0], \"schema\" | \"context\">,\n ) => {\n const { useSofa: useSofaFn } = await import(\"sofa-api\");\n if (args.openAPI) {\n merge(args.openAPI, sofaOpenAPIWebhookDocs);\n }\n if (args.errorHandler) {\n const originalHandler = args.errorHandler;\n args.errorHandler = (errors) => {\n const span = trace.getActiveSpan();\n\n for (const error of errors) {\n span?.recordException(error);\n }\n span?.setStatus({ code: SpanStatusCode.ERROR });\n return originalHandler(errors);\n };\n }\n return useSofaFn({\n ...args,\n schema: builtSchema(),\n context,\n execute: buildTracedExecute(\n args.execute ?? defaultExecute,\n rumbleInput,\n ) as any,\n subscribe: buildTracedSubscribe(\n args.subscribe ?? defaultSubscribe,\n rumbleInput,\n ) as any,\n errorHandler(errors) {\n const span = trace.getActiveSpan();\n\n for (const error of errors) {\n span?.recordException(error);\n }\n span?.setStatus({ code: SpanStatusCode.ERROR });\n\n return new Response(errors[0].message, {\n status: 500,\n }) as any;\n },\n });\n };\n\n const createWs = <\n Options extends ServerOptions<any, any>,\n Rest extends unknown[],\n Return,\n >(\n implementation: (options: Options, ...rest: Rest) => Return,\n args: Omit<Options, \"schema\" | \"context\">,\n ...rest: Rest\n ): Return => {\n return implementation(\n {\n ...args,\n schema: builtSchema(),\n context,\n execute: buildTracedExecute(\n (args as any).execute ?? defaultExecute,\n rumbleInput,\n ) as any,\n subscribe: buildTracedSubscribe(\n (args as any).subscribe ?? defaultSubscribe,\n rumbleInput,\n ) as any,\n } as Options,\n ...rest,\n );\n };\n\n const clientCreator = clientCreatorImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >({\n ...rumbleInput,\n builtSchema,\n });\n\n return {\n /**\n * The ability builder. Use it to declare whats allowed for each entity in your DB.\n *\n * @example\n *\n * ```ts\n * // users can edit themselves\n abilityBuilder.users\n .allow([\"read\", \"update\", \"delete\"])\n .when(({ userId }) => ({ where: eq(schema.users.id, userId) }));\n\n // everyone can read posts\n abilityBuilder.posts.allow(\"read\");\n *\n * ```\n */\n abilityBuilder,\n /**\n * The pothos schema builder. See https://pothos-graphql.dev/docs/plugins/drizzle\n */\n schemaBuilder,\n /**\n * Creates the native yoga instance. Can be used to run an actual HTTP server.\n *\n * @example\n *\n * ```ts\n * import { createServer } from \"node:http\";\n * const server = createServer(createYoga());\n * server.listen(3000, () => {\n * console.info(\"Visit http://localhost:3000/graphql\");\n * });\n * ```\n * https://the-guild.dev/graphql/yoga-server/docs#server\n */\n createYoga,\n /**\n * Creates a sofa instance to offer a REST API.\n *\n * ```ts\n * import express from \"express\";\n *\n * const app = express();\n * const sofa = createSofa(...);\n *\n * app.use(\"/api\", useSofa({ schema }));\n * ```\n * https://the-guild.dev/graphql/sofa-api/docs#usage\n */\n createSofa,\n /**\n * Creates a WebSocket server handler for GraphQL subscriptions.\n * Pass the ws implementation function as the first argument and rumble will\n * inject the schema and context automatically.\n *\n * @example\n *\n * ```ts\n * // ws\n * import { useServer } from \"graphql-ws/use/ws\";\n * import { WebSocketServer } from \"ws\";\n * const wss = new WebSocketServer({ port: 4000 });\n * const disposable = createWs(useServer, { ... }, wss);\n *\n * // bun\n * import { makeHandler } from \"graphql-ws/use/bun\";\n * Bun.serve({ websocket: createWs(makeHandler, { ... }), ... });\n * ```\n */\n createWs,\n /**\n * A function for creating default objects for your schema\n */\n object,\n /**\n * A function for creating where args to filter entities\n */\n whereArg,\n /**\n * A function for creating order args to sort entities\n */\n orderArg,\n /**\n * A function for creating default READ queries.\n * Make sure the objects for the table you are creating the queries for are implemented\n */\n query,\n /**\n * A function for creating a pubsub instance for a table. Use this to publish or subscribe events\n */\n pubsub: makePubSubInstance,\n /**\n * A function to implement enums for graphql usage.\n * The other helpers use this helper internally so in most cases you do not have to\n * call this helper directly, unless you need the reference to an enum type\n */\n enum_,\n /**\n * Create a client to consume a rumble graphql api at the specified location.\n * Requires GraphQL, does not work with the SOFA REST API.\n */\n clientCreator,\n /**\n * A function for creating count queries for your tables\n */\n countQuery,\n /**\n * The generated GraphQL schema. You can use this for example to create a GraphQL server with a different library than Yoga or to generate types with codegen.\n * When calling this function, the schema will be built for the first time and cached for later usage. So you can call this function multiple times without performance issues.\n * After calling, you cannot adjust the schema via the schema builder\n */\n buildSchema: builtSchema,\n };\n};\n"],"mappings":"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ACR,EACF,EACF,EACF;GACA,WAAW,EACT,OAAO;IACL,aAAa;IACb,SAAS,EACP,oBAAoB,EAClB,QAAQ,EACN,MAAM,6CACR,EACF,EACF;GACF,EACF;EACF,EACF;EACA,iBAAiB;GACf,MAAM;IACJ,aAAa;IACb,aAAa;IACb,YAAY,CACV;KACE,MAAM;KACN,IAAI;KACJ,aAAa;KACb,UAAU;KACV,QAAQ,EACN,MAAM,SACR;IACF,CACF;IACA,aAAa,EACX,SAAS,EACP,oBAAoB,EAClB,QAAQ,EACN,MAAM,yCACR,EACF,EACF,EACF;IACA,WAAW,EACT,OAAO;KACL,aAAa;KACb,SAAS,EACP,oBAAoB,EAClB,QAAQ,EACN,MAAM,6CACR,EACF,EACF;IACF,EACF;GACF;GACA,QAAQ;IACN,aAAa;IACb,aAAa;IACb,MAAM,CAAC;IACP,YAAY,CACV;KACE,MAAM;KACN,IAAI;KACJ,aAAa;KACb,UAAU;KACV,QAAQ,EACN,MAAM,SACR;IACF,CACF;IACA,WAAW,EACT,OAAO;KACL,aAAa;KACb,SAAS,EACP,oBAAoB,EAClB,QAAQ,EACN,MAAM,6CACR,EACF,EACF;IACF,EACF;GACF;EACF;CACF;CACA,YAAY,EACV,SAAS;EACP,mBAAmB;GACjB,MAAM;GACN,YAAY;IACV,cAAc;KACZ,aACE;KACF,MAAM;IACR;IACA,WAAW;KACT,aAAa;KACb,MAAM;IACR;IACA,KAAK;KACH,aAAa;KACb,MAAM;IACR;GACF;EACF;EACA,uBAAuB;GACrB,MAAM;GACN,YAAY,EACV,IAAI;IACF,aACE;IACF,MAAM;GACR,EACF;EACF;EACA,UAAU;GACR,MAAM;GACN,QAAQ;EACV;EACA,MAAM;GACJ,MAAM;GACN,QAAQ;EACV;CACF,EACF;AACF;;;AC/HA,SAAS,WAAW,OAA+C;CACjE,OAAO,OAAO,UAAU,YAAY,UAAU,QAAQ,aAAa;AACrE;AAEA,SAAS,kBAAkB,OAAiC;CAC1D,IAAI,WAAW,KAAK,GAAG;EACrB,MAAM,WAAW;EACjB,OAAO;GACL,kBAAkB,SAAS,aAAa,QAAQ,SAAS,QAA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"}
|
|
1
|
+
{"version":3,"file":"index.mjs","names":["EmptyFilter","makeDefaultName","packagejson.version","createYoga","nativeCreateYoga"],"sources":["../lib/types/rumbleError.ts","../lib/helpers/asserts.ts","../lib/helpers/mapNullFieldsToUndefined.ts","../package.json","../lib/helpers/mergeFilters.ts","../lib/helpers/sanitizeFilterValue.ts","../lib/helpers/sqlTypes/types.ts","../lib/helpers/sqlTypes/distinctValuesFromSQLType.ts","../lib/helpers/tableHelpers.ts","../lib/abilityBuilder.ts","../lib/args/orderArg.ts","../lib/enum.ts","../lib/helpers/sqlTypes/mapSQLTypeToTSType.ts","../lib/args/whereArg.ts","../lib/client/client.ts","../lib/context.ts","../lib/helpers/protoMapper.ts","../lib/countQuery.ts","../lib/helpers/sofaOpenAPIWebhookDocs.ts","../lib/helpers/errorLogging.ts","../lib/helpers/tracing.ts","../lib/helpers/sqlTypes/mapDrizzleTypeToGraphQlType.ts","../lib/helpers/determineDialectFromSchema.ts","../lib/search.ts","../lib/object.ts","../lib/pubsub.ts","../lib/query.ts","../lib/args/whereArgsImplementer.ts","../lib/runtimeFiltersPlugin/filterTypes.ts","../lib/runtimeFiltersPlugin/runtimeFiltersPlugin.ts","../lib/schemaBuilder.ts","../lib/rumble.ts"],"sourcesContent":["import { GraphQLError } from \"graphql\";\n/**\n * An error that gets raised by rumble whenever something does not go according to plan.\n * Mostly internals, configuration errors or other unexpected things.\n */\nexport class RumbleError extends Error {\n constructor(message: string) {\n super(message);\n this.name = \"RumbleError\";\n }\n}\n\n/**\n * An error that gets raised by rumble whenever an error occurs in a resolver, containing\n * information safely exposeable to the user.\n * E.g. the assert helpers issue these.\n */\nexport class RumbleErrorSafe extends GraphQLError {}\n","import { RumbleErrorSafe } from \"../types/rumbleError\";\n\n/**\n *\n * Helper function to map a drizzle findFirst query result,\n * which may be optional, to a correct drizzle type.\n *\n * @throws RumbleError\n *\n * @example\n *\n * ```ts\n * schemaBuilder.queryFields((t) => {\n return {\n findFirstUser: t.drizzleField({\n type: UserRef,\n resolve: (query, root, args, ctx, info) => {\n return (\n db.query.users\n .findFirst({\n ...query,\n where: ctx.abilities.users.filter(\"read\").single.where,\n })\n // note that we need to manually raise an error if the value is not found\n .then(assertFindFirstExists)\n );\n },\n }),\n };\n });\n * ```\n */\nexport const assertFindFirstExists = <T>(value: T | undefined): T => {\n if (!value) {\n throw new RumbleErrorSafe(\"Value not found but required (findFirst)\");\n }\n return value;\n};\n\n/**\n *\n * Helper function to map a drizzle findFirst query result,\n * which may be optional, to a correct drizzle type.\n *\n * @throws RumbleError\n *\n * @example\n *\n * ```ts\n schemaBuilder.mutationFields((t) => {\n return {\n updateUsername: t.drizzleField({\n type: UserRef,\n args: {\n userId: t.arg.int({ required: true }),\n newName: t.arg.string({ required: true }),\n },\n resolve: (query, root, args, ctx, info) => {\n return db\n .update(schema.users)\n .set({\n name: args.newName,\n })\n .where(\n and(\n eq(schema.users.id, args.userId),\n ctx.abilities.users.filter(\"update\").single.where\n )\n )\n .returning({ id: schema.users.id, name: schema.users.name })\n // note that we need to manually raise an error if the value is not found\n .then(assertFirstEntryExists);\n },\n }),\n };\n });\n * ```\n */\nexport const assertFirstEntryExists = <T>(value: T[]): T => {\n const v = value.at(0);\n if (!v)\n throw new RumbleErrorSafe(\"Value not found but required (firstEntry)\");\n return v;\n};\n","/**\n * Helper to map null fields to undefined\n * @param obj The object to map\n * @returns The mapped object with all fields of 'null' transformed to 'undefined'\n * \n * This becomes useful for update mutations where you do not want to pass null (unset value in db)\n * but undefined (do not touch value in db) in case of a value not beeing set in the args of said mutation\n * @example\n * ```ts\n * updateUser: t.drizzleField({\n type: User,\n args: {\n id: t.arg.string({ required: true }),\n email: t.arg.string(),\n lastName: t.arg.string(),\n firstName: t.arg.string(),\n },\n resolve: async (query, root, args, ctx, info) => {\n const mappedArgs = mapNullFieldsToUndefined(args);\n const user = await db.transaction(async (tx) => {\n const user = await tx\n .update(schema.user)\n .set({\n\n // email: args.email ?? undefined,\n // lastName: args.lastName ?? undefined,\n // firstName: args.firstName ?? undefined,\n\n // becomes this\n\n email: mappedArgs.email,\n lastName: mappedArgs.lastName,\n firstName: mappedArgs.firstName,\n })\n .returning()\n .then(assertFirstEntryExists);\n return user;\n });\n\n pubsub.updated(user.id);\n\n return db.query.user\n .findFirst(\n query(\n ctx.abilities.user.filter('read').merge(\n {\n where: { id: user.id },\n }\n 1).query.single,\n ),\n )\n .then(assertFindFirstExists);\n },\n }),\n * \n * \n * ```\n */\nexport function mapNullFieldsToUndefined<T extends object>(obj: T) {\n return Object.fromEntries(\n Object.entries(obj).map(([key, value]) => [\n key,\n value === null ? undefined : value,\n ]),\n ) as {\n [K in keyof T]: T[K] extends null ? undefined : Exclude<T[K], null>;\n };\n}\n","","import { toMerged } from \"es-toolkit\";\n\n// See the comment on `EmptyFilter` in `./sanitizeFilterValue.ts` for why this\n// is recreated locally instead of imported from drizzle-orm.\nconst EmptyFilter = Symbol.for(\"drizzle:EmptyFilter\");\n\n/**\n * Normalizes drizzle-orm's `EmptyFilter` sentinel to `undefined` so it's\n * treated as \"no filter\" rather than a real filter value to combine with\n * AND/OR — otherwise merging an unrestricted (EmptyFilter) base filter with\n * a real `where` would needlessly wrap it as `{ AND: [EmptyFilter, where] }`\n * instead of just `where`.\n */\nfunction realWhere(where: unknown) {\n return where === EmptyFilter ? undefined : where;\n}\n\nexport function mergeFilters<\n FilterA extends Record<string, any>,\n FilterB extends Record<string, any>,\n>(\n filterA?: Partial<FilterA>,\n filterB?: Partial<FilterB>,\n mode: \"AND\" | \"OR\" = \"AND\",\n) {\n const filterAWhere = realWhere(filterA?.where);\n const filterBWhere = realWhere(filterB?.where);\n\n const where =\n filterAWhere && filterBWhere\n ? mode === \"OR\"\n ? { OR: [filterAWhere, filterBWhere] }\n : { AND: [filterAWhere, filterBWhere] }\n : (filterAWhere ?? filterBWhere);\n\n const columns =\n filterA?.columns || filterB?.columns\n ? new Set(\n [\n Object.entries(filterA?.columns ?? {}),\n Object.entries(filterB?.columns ?? {}),\n ]\n .flat()\n .filter(([, v]) => v === true)\n .map(([k]) => k),\n )\n .entries()\n .reduce(\n (acc, [key]) => {\n acc[key] = true;\n return acc;\n },\n {} as Record<string, true>,\n )\n : undefined;\n\n const extras =\n filterA?.extras || filterB?.extras\n ? toMerged(filterA?.extras ?? {}, filterB?.extras ?? {})\n : undefined;\n\n const orderBy =\n filterA?.orderBy || filterB?.orderBy\n ? toMerged(filterA?.orderBy ?? {}, filterB?.orderBy ?? {})\n : undefined;\n\n const limit =\n mode === \"OR\"\n ? filterA?.limit === undefined || filterB?.limit === undefined\n ? undefined\n : Math.max(filterA.limit, filterB.limit)\n : filterA?.limit || filterB?.limit\n ? Math.min(filterA?.limit ?? Infinity, filterB?.limit ?? Infinity)\n : undefined;\n\n const offset =\n mode === \"OR\"\n ? filterA?.offset === undefined || filterB?.offset === undefined\n ? undefined\n : Math.min(filterA.offset, filterB.offset)\n : filterA?.offset || filterB?.offset\n ? Math.min(filterA?.offset ?? Infinity, filterB?.offset ?? Infinity)\n : undefined;\n\n const with_ =\n filterA?.with || filterB?.with\n ? toMerged(filterA?.with ?? {}, filterB?.with ?? {})\n : undefined;\n\n return {\n where,\n columns,\n extras,\n orderBy,\n limit,\n offset,\n with: with_,\n } as unknown as FilterA & FilterB;\n}\n","const EmptyFilter = Symbol.for(\"drizzle:EmptyFilter\");\n\nfunction isPlainObject(value: unknown): value is Record<string, unknown> {\n if (typeof value !== \"object\" || value === null) return false;\n const proto = Object.getPrototypeOf(value);\n return proto === Object.prototype || proto === null;\n}\n\nexport function sanitizeFilterValue(value: unknown): unknown {\n if (value === undefined || value === null) return EmptyFilter;\n if (Array.isArray(value)) return value.map(sanitizeFilterValue);\n if (isPlainObject(value)) {\n return Object.fromEntries(\n Object.entries(value).map(([key, entry]) => [\n key,\n sanitizeFilterValue(entry),\n ]),\n );\n }\n return value;\n}\n","import { RumbleError } from \"../../types/rumbleError\";\n\n/**\n * Strips parameter suffixes like `(256)`, `(10,2)` and timezone modifiers\n * (`with time zone`, `without time zone`) from raw getSQLType() output so\n * every classifier works on the base type name only.\n */\nexport function normalizeSQLType(raw: string): string {\n return raw\n .replace(/\\s*with(?:out)?\\s+time\\s+zone/i, \"\")\n .replace(/\\s*\\([^)]*\\)/, \"\")\n .trim()\n .toLowerCase();\n}\n\nconst intLikeSQLTypeStrings = [\n \"serial\",\n \"int\",\n \"integer\",\n \"tinyint\",\n \"smallint\",\n \"mediumint\",\n \"int2\",\n \"int4\",\n \"smallserial\",\n] as const;\n\nexport function isIntLikeSQLTypeString(sqlType: string): boolean {\n return intLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst bigIntLikeSQLTypeStrings = [\n \"bigint\",\n \"bigserial\",\n \"int8\",\n \"bigint unsigned\",\n] as const;\n\nexport function isBigIntLikeSQLTypeString(sqlType: string): boolean {\n return bigIntLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst floatLikeSQLTypeStrings = [\n \"real\",\n \"decimal\",\n \"double\",\n \"float\",\n \"numeric\",\n \"double precision\",\n \"float4\",\n \"float8\",\n \"money\",\n] as const;\n\nexport function isFloatLikeSQLTypeString(sqlType: string): boolean {\n return floatLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst stringLikeSQLTypeStrings = [\n \"string\",\n \"text\",\n \"varchar\",\n \"char\",\n \"character varying\",\n \"character\",\n \"inet\",\n \"cidr\",\n \"macaddr\",\n \"macaddr8\",\n \"interval\",\n \"time\",\n \"year\",\n \"binary\",\n \"varbinary\",\n \"tinytext\",\n \"mediumtext\",\n \"longtext\",\n] as const;\n\nexport function isStringLikeSQLTypeString(sqlType: string): boolean {\n return stringLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst IDLikeSQLTypeStrings = [\"uuid\"] as const;\n\nexport function isIDLikeSQLTypeString(sqlType: string): boolean {\n return IDLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst booleanSQLTypeStrings = [\"boolean\", \"bool\"] as const;\n\nexport function isBooleanSQLTypeString(sqlType: string): boolean {\n return booleanSQLTypeStrings.includes(sqlType as any);\n}\n\nconst dateTimeLikeSQLTypeStrings = [\"timestamp\", \"datetime\"] as const;\n\nexport function isDateTimeLikeSQLTypeString(sqlType: string): boolean {\n return dateTimeLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst dateLikeSQLTypeStrings = [\"date\"] as const;\n\nexport function isDateLikeSQLTypeString(sqlType: string): boolean {\n return dateLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst jsonLikeSQLTypeStrings = [\"json\", \"jsonb\"] as const;\n\nexport function isJSONLikeSQLTypeString(sqlType: string): boolean {\n return jsonLikeSQLTypeStrings.includes(sqlType as any);\n}\n\nconst jsonFallbackSQLTypeStrings = [\n \"point\",\n \"line\",\n \"lseg\",\n \"box\",\n \"path\",\n \"polygon\",\n \"circle\",\n \"geometry\",\n] as const;\n\nexport function isJSONFallbackSQLTypeString(sqlType: string): boolean {\n return (\n jsonFallbackSQLTypeStrings.includes(sqlType as any) ||\n sqlType.startsWith(\"geometry\")\n );\n}\n\nconst bytesSQLTypeStrings = [\"bytea\", \"blob\"] as const;\n\nexport function isBytesSQLTypeString(sqlType: string): boolean {\n return bytesSQLTypeStrings.includes(sqlType as any);\n}\n\n// PossibleSQLType is intentionally broad — classifiers receive normalized\n// strings and use runtime includes() checks.\nexport type PossibleSQLType = string & {};\n\nexport const UnknownTypeRumbleError = (\n sqlType: string,\n additionalInfo?: string,\n) =>\n new RumbleError(\n `RumbleError: Unknown SQL type '${sqlType}'. Please open an issue (https://github.com/m1212e/rumble/issues) so it can be added. (${additionalInfo})`,\n );\n","import {\n isBooleanSQLTypeString,\n isDateLikeSQLTypeString,\n isDateTimeLikeSQLTypeString,\n isFloatLikeSQLTypeString,\n isIDLikeSQLTypeString,\n isIntLikeSQLTypeString,\n isJSONLikeSQLTypeString,\n isStringLikeSQLTypeString,\n type PossibleSQLType,\n UnknownTypeRumbleError,\n} from \"./types\";\n\nexport function createDistinctValuesFromSQLType(sqlType: PossibleSQLType): {\n value1: any;\n value2: any;\n} {\n if (isIntLikeSQLTypeString(sqlType)) {\n return {\n value1: 1,\n value2: 2,\n };\n }\n\n if (isFloatLikeSQLTypeString(sqlType)) {\n return {\n value1: 1.1,\n value2: 2.2,\n };\n }\n\n if (isStringLikeSQLTypeString(sqlType)) {\n return {\n value1: \"a\",\n value2: \"b\",\n };\n }\n\n if (isIDLikeSQLTypeString(sqlType)) {\n return {\n value1: \"fba31870-5528-42d7-b27e-2e5ee657aea5\",\n value2: \"fc65db81-c2d1-483d-8a25-a30e2cf6e02d\",\n };\n }\n\n if (isBooleanSQLTypeString(sqlType)) {\n return {\n value1: true,\n value2: false,\n };\n }\n\n if (isDateTimeLikeSQLTypeString(sqlType)) {\n return {\n value1: new Date(2022, 1, 1),\n value2: new Date(2022, 1, 2),\n };\n }\n\n if (isDateLikeSQLTypeString(sqlType)) {\n return {\n value1: new Date(2022, 1, 1),\n value2: new Date(2022, 1, 2),\n };\n }\n\n if (isJSONLikeSQLTypeString(sqlType)) {\n return {\n value1: { a: 1 },\n value2: { b: 2 },\n };\n }\n\n throw UnknownTypeRumbleError(sqlType, \"Distinct\");\n}\n","import {\n type Column,\n getTableColumns,\n getTableName,\n is,\n isTable,\n type Many,\n type One,\n type Table,\n} from \"drizzle-orm\";\nimport type { DrizzleInstance } from \"../types/drizzleInstanceType\";\nimport { RumbleError } from \"../types/rumbleError\";\n\ntype RelationEntry = {\n /** TS-level key in db._.relations (i.e. the export name) */\n name: string;\n /** runtime DB table name as returned by getTableName(table) */\n dbName: string;\n /** the underlying drizzle Table object */\n table: any;\n /** columns map for the table */\n columns: Record<string, Column>;\n /** primary key columns, keyed by column ts-name */\n primaryKey: Record<string, Column>;\n /** named relations record (one/many) for this table */\n relations: Record<string, One<any, any> | Many<any>>;\n /**\n * Whether the underlying entity is a genuine drizzle Table (as opposed to a\n * View/MaterializedView)\n */\n isTable: boolean;\n /**\n * The raw entry from db._.relations — preserved for callers that previously\n * read `foundRelation` off tableHelper().\n */\n foundRelation: any;\n};\n\ntype TableIndex = {\n byTsName: Map<string, RelationEntry>;\n byDbName: Map<string, RelationEntry>;\n byTableRef: Map<any, RelationEntry>;\n};\n\nconst indexCache = new WeakMap<object, TableIndex>();\n\nfunction buildIndex<DB extends DrizzleInstance>(db: DB): TableIndex {\n const byTsName = new Map<string, RelationEntry>();\n const byDbName = new Map<string, RelationEntry>();\n const byTableRef = new Map<any, RelationEntry>();\n\n for (const [tsName, rawEntry] of Object.entries(db._.relations ?? {})) {\n const entry = rawEntry as any;\n const tableObj = entry.table;\n if (!tableObj) continue;\n\n const columns = (\n isTable(tableObj) ? getTableColumns(tableObj as Table) : {}\n ) as Record<string, Column>;\n\n const primaryKey = Object.fromEntries(\n Object.entries(columns).filter(([, col]) => (col as any).primary),\n ) as Record<string, Column>;\n\n const dbName = isTable(tableObj)\n ? (getTableName(tableObj as Table) as string)\n : ((entry.name as string) ?? tsName);\n\n const resolved: RelationEntry = {\n name: entry.name ?? tsName,\n dbName,\n table: tableObj,\n columns,\n primaryKey,\n relations: entry.relations ?? {},\n isTable: isTable(tableObj),\n foundRelation: entry,\n };\n\n byTsName.set(resolved.name, resolved);\n byDbName.set(resolved.dbName, resolved);\n byTableRef.set(tableObj, resolved);\n }\n\n return { byTsName, byDbName, byTableRef };\n}\n\nfunction getIndex<DB extends DrizzleInstance>(db: DB): TableIndex {\n let idx = indexCache.get(db as unknown as object);\n if (!idx) {\n idx = buildIndex(db);\n indexCache.set(db as unknown as object, idx);\n }\n return idx;\n}\n\nexport function tableHelper<\n DB extends DrizzleInstance,\n TableIdentifier extends\n | string\n | DB[\"_\"][\"relations\"][keyof DB[\"_\"][\"relations\"]],\n>({ db, table }: { db: DB; table: TableIdentifier }) {\n const idx = getIndex(db);\n\n let entry: RelationEntry | undefined;\n\n if (typeof table === \"string\") {\n // Lookup by TS-level relation name first (the common case), then by DB name.\n entry = idx.byTsName.get(table) ?? idx.byDbName.get(table);\n } else if (table && typeof table === \"object\") {\n const t = table as any;\n\n // Case 1: caller passed an entry from db._.relations directly:resolve by\n // table identity via its `.table` property.\n if (t.table) {\n entry = idx.byTableRef.get(t.table);\n if (!entry && t.name) {\n entry = idx.byTsName.get(t.name) ?? idx.byDbName.get(t.name);\n }\n }\n\n // Case 2: caller passed a raw Table object: resolve by identity.\n if (!entry) {\n entry = idx.byTableRef.get(t);\n }\n\n // Case 3: last resort lookup via the public getTableName() helper.\n if (!entry && isTable(t)) {\n const dbName = getTableName(t as Table) as string;\n entry = idx.byDbName.get(dbName);\n }\n }\n\n if (!entry) {\n throw new RumbleError(\n `Could not find schema for ${JSON.stringify(\n typeof table === \"string\" ? table : \"<table-object>\",\n )}`,\n );\n }\n\n return {\n columns: entry.columns,\n primaryKey: entry.primaryKey,\n relations: entry.relations,\n dbName: entry.dbName,\n tsName: entry.name,\n table: entry.table,\n isTable: entry.isTable,\n foundRelation: entry.foundRelation,\n };\n}\n\n/**\n * Looks up a relation entry by its TS-level name — i.e. the key in\n * db._.relations, which is also what `Relation.targetTableName` carries.\n * Prefer this for cross-relation navigation over re-resolving via the raw\n * `targetTable` object.\n */\nexport function tableHelperByTsName<DB extends DrizzleInstance>(\n db: DB,\n tsName: string,\n) {\n return tableHelper({ db, table: tsName });\n}\n\nexport { is };\n","import type { Span } from \"@opentelemetry/api\";\nimport { relationsFilterToSQL } from \"drizzle-orm\";\nimport { debounce } from \"es-toolkit\";\nimport { lazy } from \"./helpers/lazy\";\nimport { mergeFilters } from \"./helpers/mergeFilters\";\nimport { sanitizeFilterValue } from \"./helpers/sanitizeFilterValue\";\nimport { createDistinctValuesFromSQLType } from \"./helpers/sqlTypes/distinctValuesFromSQLType\";\nimport { tableHelper } from \"./helpers/tableHelpers\";\nimport type {\n Filter,\n FilterPrefetchCombo,\n Prefetch,\n} from \"./runtimeFiltersPlugin/filterTypes\";\nimport type {\n DrizzleInstance,\n DrizzleQueryFunction,\n DrizzleQueryFunctionInput,\n DrizzleTableValueType,\n TableRelationNames,\n} from \"./types/drizzleInstanceType\";\nimport { RumbleError } from \"./types/rumbleError\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n RumbleLogger,\n} from \"./types/rumbleInput\";\n\n//TODO: optimize this for v8 & refactor\n\nexport type AbilityBuilderType<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n> = ReturnType<\n typeof createAbilityBuilder<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >\n>;\n\n/**\n * Static, non changing query filter input type for a specific table\n */\ntype StaticQueryFilter<\n DB extends DrizzleInstance,\n Table extends keyof DrizzleQueryFunction<DB>,\n Filter extends DrizzleQueryFunctionInput<DB, Table>,\n> = Filter;\n\n/**\n * Dynamic, context based query filter input type for a specific table\n */\ntype DynamicQueryFilter<\n DB extends DrizzleInstance,\n Table extends keyof DrizzleQueryFunction<DB>,\n Filter extends DrizzleQueryFunctionInput<DB, Table>,\n Context,\n> = (\n context: Context,\n) => StaticQueryFilter<DB, Table, Filter> | undefined | \"allow\";\n\n/**\n * Combined query filter type for a specific table. May be static or dynamic.\n */\ntype QueryFilter<\n DB extends DrizzleInstance,\n Table extends keyof DrizzleQueryFunction<DB>,\n Filter extends DrizzleQueryFunctionInput<DB, Table>,\n Context,\n> =\n | StaticQueryFilter<DB, Table, Filter>\n | DynamicQueryFilter<DB, Table, Filter, Context>;\n\nfunction isDynamicQueryFilter<\n DB extends DrizzleInstance,\n Table extends keyof DrizzleQueryFunction<DB>,\n Filter extends DrizzleQueryFunctionInput<DB, Table>,\n Context,\n>(\n filter: QueryFilter<DB, Table, Filter, Context>,\n): filter is DynamicQueryFilter<DB, Table, Filter, Context> {\n return (\n typeof filter === \"function\" && filter.constructor.name !== \"AsyncFunction\"\n );\n}\n\nfunction isStaticQueryFilter<\n DB extends DrizzleInstance,\n Table extends keyof DrizzleQueryFunction<DB>,\n Filter extends DrizzleQueryFunctionInput<DB, Table>,\n Context,\n>(\n filter: QueryFilter<DB, Table, Filter, Context>,\n): filter is StaticQueryFilter<DB, Table, Filter> {\n return typeof filter !== \"function\";\n}\n\nconst makeNothingRegisteredWarner = (logger?: RumbleLogger) =>\n debounce((model: string, action: string) => {\n const msg = `No abilities registered for ${model}/${action} — blocking everything. Register the ability or ignore this warning if intentional.`;\n if (logger) {\n logger.warn({ \"rumble.table\": model, \"rumble.action\": action }, msg);\n } else {\n console.warn(msg);\n }\n }, 1000);\n\nexport const createAbilityBuilder = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>({\n db,\n actions,\n defaultLimit,\n otel,\n logger: loggerConfig,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig>) => {\n const log = loggerConfig?.enabled ? loggerConfig.logger : undefined;\n const nothingRegisteredWarningLogger = makeNothingRegisteredWarner(log);\n type TableNames = TableRelationNames<DB>;\n\n // Views/materialized views can appear in db.query (if the caller's schema\n // includes them)\n const tableRelationNames = (\n Object.keys(db.query) as (keyof DrizzleQueryFunction<DB>)[]\n ).filter(\n (name) => tableHelper({ db, table: name as any }).isTable,\n ) as TableNames[];\n\n let hasBeenBuilt = false;\n\n const createBuilderForTable = <TableName extends TableNames>() => {\n const queryFilters = new Map<\n Action,\n | QueryFilter<\n DB,\n TableName,\n DrizzleQueryFunctionInput<DB, TableName>,\n UserContext\n >[]\n | \"unrestricted\"\n >();\n\n const runtimeFilters = new Map<\n Action,\n //TODO add a run all helper\n FilterPrefetchCombo<UserContext, any, any>[]\n >();\n\n // we want to init all possible runtime filters since we want to ensure\n // that the implementaiton helpers pass an object by reference when creating\n // the implementation, instead of a copy like it would be the case with undefined\n for (const action of actions!) {\n if (!runtimeFilters.has(action)) {\n runtimeFilters.set(action, []);\n }\n }\n\n return {\n /**\n * Allows to perform a specific action on a specific entity\n */\n allow: (action: Action | Action[]) => {\n if (hasBeenBuilt) {\n throw new RumbleError(\n \"You can't call allow() after the ability builder has been built. Please ensure that you register all abilities before accessing them.\",\n );\n }\n\n const actions = Array.isArray(action) ? action : [action];\n // Track which actions this specific allow() call initialized as \"unrestricted\",\n // so .when() can distinguish chained use (allow().when()) from a later separate call\n // that finds a pre-existing \"unrestricted\" from a prior bare allow().\n const setUnrestrictedByThisCall = new Set<(typeof actions)[number]>();\n for (const action of actions) {\n let filters = queryFilters.get(action);\n if (!filters) {\n filters = \"unrestricted\";\n queryFilters.set(action, filters);\n setUnrestrictedByThisCall.add(action);\n }\n }\n\n return {\n /**\n * Restricts the allowed actions to a filter\n * @example\n * ```ts\n * abilityBuilder.users.allow([\"read\", \"update\", \"delete\"]).when(({ userId }) => ({\n * where: {\n * id: userId,\n * },\n * }));\n * ```\n */\n when: (\n queryFilter: QueryFilter<\n DB,\n TableName,\n DrizzleQueryFunctionInput<DB, TableName>,\n UserContext\n >,\n ) => {\n for (const action of actions) {\n if (queryFilters.get(action) === \"unrestricted\") {\n if (setUnrestrictedByThisCall.has(action)) {\n // Chained directly on this allow() call — override unrestricted with specific filter\n queryFilters.set(action, []);\n } else {\n // A previous separate bare allow() already set unrestricted\n // skip this filter\n continue;\n }\n }\n const filters = queryFilters.get(action)!;\n (filters as Exclude<typeof filters, \"unrestricted\">).push(\n queryFilter,\n );\n }\n },\n };\n },\n /**\n * Allows to register an application level filter to restrict some results\n * which were returned by a query\n */\n filter: (action: Action | Action[]) => {\n const actions = Array.isArray(action) ? action : [action];\n return {\n /**\n * Allows to register an application level prefetch to fetch some data\n * which could be useful for later filtering the results. The prefetch\n * function will be called with the user context but unlike the actual\n * filter function, it will not have access to the result of the query\n * and therefore can be run in parallel with underlying query resolver.\n * A typical use case is to fetch some data which is not directly\n * related to the query but to the context only. So e.g. fetching the\n * user's permissions from an external system and then later applying\n * the filter based on those permissions.\n */\n prefetch: <PrefetchReturnType>(\n prefetch: Prefetch<UserContext, PrefetchReturnType>,\n ) => {\n return {\n /**\n * The actual filter function to apply. Returns the allowed values\n */\n by: (\n explicitFilter: Filter<\n UserContext,\n DrizzleTableValueType<DB, TableName>,\n PrefetchReturnType\n >,\n ) => {\n for (const action of actions) {\n // we initialized all possible actions when creating the builder\n runtimeFilters.get(action)!.push({\n filter: explicitFilter,\n prefetch: prefetch,\n });\n }\n },\n };\n },\n /**\n * The actual filter function to apply. Returns the allowed values\n */\n by: (\n explicitFilter: Filter<\n UserContext,\n DrizzleTableValueType<DB, TableName>\n >,\n ) => {\n for (const action of actions) {\n // we initialized all possible actions when creating the builder\n runtimeFilters.get(action)!.push({\n filter: explicitFilter as Filter<UserContext, any, any>,\n });\n }\n },\n };\n },\n _: {\n runtimeFilters,\n queryFilters,\n },\n };\n };\n\n const buildersPerTable = Object.fromEntries(\n tableRelationNames.map((tableName) => [\n tableName,\n createBuilderForTable<typeof tableName>(),\n ]),\n ) as {\n [key in TableNames]: ReturnType<typeof createBuilderForTable<key>>;\n };\n\n return {\n ...buildersPerTable,\n /**\n * @internal\n * @ignore\n */\n _: {\n registeredFilters({\n action,\n table,\n }: {\n table: TableNames;\n action: Action;\n }) {\n return (buildersPerTable[table] as any)._.runtimeFilters.get(\n action,\n )! as Filter<UserContext, DrizzleTableValueType<DB, TableNames>>[];\n },\n build() {\n const createFilterForTable = <TableName extends TableNames>(\n tableName: TableName,\n ) => {\n const queryFilters = buildersPerTable[tableName]._.queryFilters;\n\n const simpleQueryFilters = Object.fromEntries(\n actions!.map((action) => {\n const filters = queryFilters.get(action);\n\n if (!filters || filters === \"unrestricted\") return [action, []];\n\n return [action, filters.filter(isStaticQueryFilter)];\n }),\n ) as {\n [key in Action]: StaticQueryFilter<\n DB,\n TableName,\n DrizzleQueryFunctionInput<DB, TableName>\n >[];\n };\n\n const dynamicQueryFilters = Object.fromEntries(\n actions!.map((action) => {\n const filters = queryFilters.get(action);\n\n if (!filters || filters === \"unrestricted\") return [action, []];\n\n return [action, filters.filter(isDynamicQueryFilter)];\n }),\n ) as {\n [key in Action]: DynamicQueryFilter<\n DB,\n TableName,\n DrizzleQueryFunctionInput<DB, TableName>,\n UserContext\n >[];\n };\n\n const tableSchema = tableHelper({\n db,\n table: tableName,\n });\n\n if (Object.keys(tableSchema.primaryKey).length === 0) {\n throw new RumbleError(\n `No primary key found for entity ${String(tableName)}`,\n );\n }\n\n const primaryKeyField: any = Object.values(tableSchema.primaryKey)[0];\n // we want a filter that excludes everything\n const distinctValues = createDistinctValuesFromSQLType(\n primaryKeyField.getSQLType() as any,\n );\n\n const blockEverythingFilter = {\n where: {\n AND: [\n {\n [primaryKeyField.name]: distinctValues.value1,\n },\n {\n [primaryKeyField.name]: distinctValues.value2,\n },\n ],\n },\n };\n\n /**\n * Packs the filters into a response object that can be applied for queries by the user\n */\n function transformToResponse(\n queryFilters?: DrizzleQueryFunctionInput<DB, TableName>,\n ) {\n const internalTransformer = (\n filters?: DrizzleQueryFunctionInput<DB, TableName>,\n mergedLimit?: number,\n ) => {\n const limit = lazy(() => {\n if (\n // got a merge injection\n mergedLimit !== undefined\n ) {\n if (!filters?.limit) {\n // there is not ability limit\n return mergedLimit;\n }\n\n if ((filters.limit as number) > mergedLimit) {\n // there is an ability limit and it is higher that the injected merge limit\n return mergedLimit;\n }\n }\n\n let limit = filters?.limit as number | undefined;\n\n if (\n defaultLimit &&\n (limit === undefined || limit > defaultLimit)\n ) {\n limit = defaultLimit;\n }\n\n // ensure that null is converted to undefined\n return limit ?? undefined;\n });\n\n const sqlTransformedWhere = lazy(() => {\n const casing = (db._ as any).session?.dialect?.casing;\n\n return filters?.where\n ? relationsFilterToSQL(\n tableSchema.foundRelation.table,\n sanitizeFilterValue(filters.where) as any,\n tableSchema.relations,\n db._.relations,\n casing,\n )\n : undefined;\n });\n\n // we acutally need to define multiple return objects since we do not want to use delete for\n // performance reasons and an undefined columns field on a drizzle filter will prevent any\n // column from being selected at all\n if (filters?.columns) {\n return {\n /**\n * Query filters for the drizzle query API.\n * @example\n * ```ts\n * author: t.relation(\"author\", {\n * query: (_args, ctx) => ctx.abilities.users.filter(\"read\").query.single,\n * }),\n * ´´´\n */\n query: {\n /**\n * For find first calls\n */\n single: {\n extras: filters?.extras,\n where: sanitizeFilterValue(filters?.where),\n columns: filters?.columns,\n } as Pick<\n NonNullable<\n NonNullable<\n Parameters<DB[\"query\"][TableName][\"findFirst\"]>[0]\n >\n >,\n \"columns\" | \"where\"\n >,\n /**\n * For find many calls\n */\n many: {\n extras: filters?.extras,\n where: sanitizeFilterValue(filters?.where),\n columns: filters?.columns,\n get limit() {\n return limit();\n },\n } as Pick<\n NonNullable<\n NonNullable<\n Parameters<DB[\"query\"][TableName][\"findMany\"]>[0]\n >\n >,\n \"columns\" | \"where\" | \"limit\"\n >,\n },\n /**\n * Query filters for the drizzle SQL API as used in e.g. updates.\n * @example\n *\n * ```ts\n * await db\n *\t.update(schema.users)\n *\t.set({\n *\t name: args.newName,\n * \t})\n *\t.where(\n *\t and(\n *\t eq(schema.users.id, args.userId),\n *\t ctx.abilities.users.filter(\"update\").sql.where,\n *\t ),\n *\t);\n * ```\n *\n */\n sql: {\n get where() {\n return sqlTransformedWhere();\n },\n },\n };\n } else {\n return {\n /**\n * Query filters for the drizzle query API.\n * @example\n * ```ts\n * author: t.relation(\"author\", {\n * query: (_args, ctx) => ctx.abilities.users.filter(\"read\").query.single,\n * }),\n * ´´´\n */\n query: {\n /**\n * For find first calls\n */\n single: {\n extras: filters?.extras,\n where: sanitizeFilterValue(filters?.where),\n } as Pick<\n NonNullable<\n NonNullable<\n Parameters<DB[\"query\"][TableName][\"findFirst\"]>[0]\n >\n >,\n \"where\"\n >,\n /**\n * For find many calls\n */\n many: {\n extras: filters?.extras,\n where: sanitizeFilterValue(filters?.where),\n get limit() {\n return limit();\n },\n } as Pick<\n NonNullable<\n NonNullable<\n Parameters<DB[\"query\"][TableName][\"findMany\"]>[0]\n >\n >,\n \"where\" | \"limit\"\n >,\n },\n /**\n * Query filters for the drizzle SQL API as used in e.g. updates.\n * @example\n *\n * ```ts\n * await db\n *\t.update(schema.users)\n *\t.set({\n *\t name: args.newName,\n * \t})\n *\t.where(\n *\t and(\n *\t eq(schema.users.id, args.userId),\n *\t ctx.abilities.users.filter(\"update\").sql.where,\n *\t ),\n *\t);\n * ```\n *\n */\n sql: {\n get where() {\n return sqlTransformedWhere();\n },\n },\n };\n }\n };\n\n const ret = internalTransformer(queryFilters);\n\n /**\n * Merges the current query filters with the provided filters for this call only\n */\n function merge(\n p: NonNullable<DrizzleQueryFunctionInput<DB, TableName>>,\n ) {\n const merged = mergeFilters(ret.query.many, p);\n return internalTransformer(\n merged,\n // in case the user wants to inject a limit, we need to ensure that it is applied\n // and not the potential default limit will be used\n // this is important for functions of the default query pagination implementation\n p.limit as number | undefined,\n );\n }\n\n (ret as any).merge = merge;\n\n return ret as typeof ret & {\n merge: typeof merge;\n };\n }\n\n return {\n withContext: (userContext: UserContext) => {\n return {\n filter: (action: Action) => {\n const assembleAbilities = (span?: Span) => {\n const filters = queryFilters.get(action);\n\n // in case we have a wildcard ability, skip the rest and return no filters at all\n if (filters === \"unrestricted\") {\n span?.setAttribute(\"abilities.status\", \"unrestricted\");\n return transformToResponse();\n }\n\n // if nothing has been allowed, block everything\n if (!filters) {\n span?.setAttribute(\n \"abilities.status\",\n \"blocked_everything\",\n );\n nothingRegisteredWarningLogger(String(tableName), action);\n return transformToResponse(blockEverythingFilter);\n }\n\n // run all dynamic filters\n const dynamicResults = new Array<\n DrizzleQueryFunctionInput<DB, TableName>\n >(dynamicQueryFilters[action].length);\n let filtersReturned = 0;\n for (\n let i = 0;\n i < dynamicQueryFilters[action].length;\n i++\n ) {\n const func = dynamicQueryFilters[action][i];\n const result = func(userContext);\n // if one of the dynamic filters returns \"allow\", we want to allow everything\n if (result === \"allow\") {\n return transformToResponse();\n }\n // if nothing is returned, nothing is allowed by this filter\n if (result === undefined) continue;\n\n dynamicResults[filtersReturned++] = result;\n }\n dynamicResults.length = filtersReturned;\n\n span?.setAttribute(\n \"abilities.dynamic\",\n dynamicResults.length,\n );\n span?.setAttribute(\n \"abilities.static\",\n simpleQueryFilters[action].length,\n );\n\n const allQueryFilters = [\n ...simpleQueryFilters[action],\n ...dynamicResults,\n ];\n\n span?.setAttribute(\n \"abilities.total\",\n allQueryFilters.length,\n );\n\n // if we don't have any permitted filters then block everything\n if (allQueryFilters.length === 0) {\n span?.setAttribute(\n \"abilities.status\",\n \"blocked_everything\",\n );\n\n return transformToResponse(blockEverythingFilter);\n }\n\n const mergedFilters =\n allQueryFilters.length === 1\n ? allQueryFilters[0]\n : allQueryFilters.reduce((a, b) => {\n return mergeFilters(a, b, \"OR\");\n });\n\n span?.setAttribute(\"abilities.status\", \"applied\");\n return transformToResponse(mergedFilters as any);\n };\n\n if (otel?.enabled && otel.tracer) {\n return otel.tracer.startActiveSpan(\n `rumble.abilities.prepare`,\n (span) => {\n span.setAttribute(\"rumble.action\", action);\n span.setAttribute(\"rumble.table\", String(tableName));\n try {\n // assembleAbilities sets abilities.* attributes on the span;\n // we capture them in parallel for logging via a lightweight proxy\n const attrs: Record<string, unknown> = {\n \"rumble.table\": String(tableName),\n \"rumble.action\": action,\n };\n const proxy = new Proxy(span, {\n get(target, prop) {\n if (prop === \"setAttribute\") {\n return (k: string, v: unknown) => {\n attrs[k] = v;\n return target.setAttribute(k, v as any);\n };\n }\n return (target as any)[prop];\n },\n });\n const result = assembleAbilities(proxy);\n log?.debug(attrs, \"abilities prepared\");\n return result;\n } finally {\n span.end();\n }\n },\n );\n } else {\n const attrs: Record<string, unknown> = {\n \"rumble.table\": String(tableName),\n \"rumble.action\": action,\n };\n const spy = log\n ? ({\n setAttribute: (k: string, v: unknown) => {\n attrs[k] = v;\n },\n } as unknown as Span)\n : undefined;\n const result = assembleAbilities(spy);\n log?.debug(attrs, \"abilities prepared\");\n return result;\n }\n },\n };\n },\n };\n };\n\n const abilitiesPerTable = Object.fromEntries(\n tableRelationNames.map((tableName) => [\n tableName,\n createFilterForTable(tableName),\n ]),\n ) as {\n [key in TableNames]: ReturnType<typeof createFilterForTable<key>>;\n };\n\n hasBeenBuilt = true;\n\n return (ctx: UserContext) => {\n return Object.fromEntries(\n tableRelationNames.map((tableName) => [\n tableName,\n abilitiesPerTable[tableName].withContext(ctx),\n ]),\n ) as {\n [key in TableNames]: ReturnType<\n ReturnType<typeof createFilterForTable<key>>[\"withContext\"]\n >;\n };\n };\n },\n },\n };\n};\n","import { toCamelCase } from \"drizzle-orm/casing\";\nimport { capitalize } from \"es-toolkit\";\nimport { lazy } from \"../helpers/lazy\";\nimport { tableHelper } from \"../helpers/tableHelpers\";\nimport type {\n DrizzleInstance,\n DrizzleQueryFunction,\n} from \"../types/drizzleInstanceType\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"../types/rumbleInput\";\nimport type { SchemaBuilderType } from \"../types/schemaBuilderType\";\n\nexport type OrderArgImplementerType<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n> = ReturnType<\n typeof createOrderArgImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >\n>;\n\nconst makeDefaultName = (dbName: string) =>\n `${capitalize(toCamelCase(dbName.toString()))}OrderInputArgument`;\n\nexport const createOrderArgImplementer = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>({\n db,\n schemaBuilder,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig> & {\n schemaBuilder: SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n}) => {\n const referenceStorage = new Map<string, any>();\n\n const sortingParameterEnumRef = lazy(() =>\n schemaBuilder.enumType(\"SortingParameter\", {\n values: [\"asc\", \"desc\"] as const,\n }),\n );\n\n const orderArgImplementer = <\n RefName extends string,\n TableName extends keyof DrizzleQueryFunction<DB>,\n >({\n table,\n refName,\n dbName,\n }: Partial<{\n table: TableName;\n refName: RefName | undefined;\n dbName: string;\n }> &\n (\n | {\n table: TableName;\n }\n | {\n dbName: string;\n }\n )) => {\n const tableSchema = tableHelper({\n db,\n table: dbName ?? table!,\n });\n\n const inputTypeName = refName ?? makeDefaultName(tableSchema.tsName);\n\n let ret: ReturnType<typeof implement> | undefined =\n referenceStorage.get(inputTypeName);\n if (ret) {\n return ret;\n }\n\n const implement = () => {\n return schemaBuilder.inputType(inputTypeName, {\n fields: (t) => {\n // Drizzle's relationsOrderToSQL treats every key as a column on the\n // current table, so exposing relation keys would generate invalid SQL.\n const fields = Object.entries(tableSchema.columns).reduce(\n (acc, [key]) => {\n // GraphQL reserves names starting with \"__\" for introspection.\n if (key.startsWith(\"__\")) return acc;\n\n acc[key] = t.field({\n type: sortingParameterEnumRef(),\n required: false,\n });\n\n return acc;\n },\n {} as Record<string, ReturnType<typeof t.field>>,\n );\n\n return fields;\n },\n });\n };\n\n ret = implement();\n referenceStorage.set(inputTypeName, ret);\n return ret;\n };\n\n return orderArgImplementer;\n};\n","import { type Column, getTableName, is, isTable } from \"drizzle-orm\";\nimport { toCamelCase } from \"drizzle-orm/casing\";\nimport { MySqlEnumColumn, MySqlEnumObjectColumn } from \"drizzle-orm/mysql-core\";\nimport {\n isPgEnum,\n type PgEnum,\n PgEnumColumn,\n type PgEnumObject,\n PgEnumObjectColumn,\n} from \"drizzle-orm/pg-core\";\nimport { capitalize } from \"es-toolkit\";\nimport type { DrizzleInstance } from \"./types/drizzleInstanceType\";\nimport { RumbleError } from \"./types/rumbleError\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\nimport type { SchemaBuilderType } from \"./types/schemaBuilderType\";\n\n/**\n * Checks if a column is a database enum column (Postgres or MySQL).\n */\nexport function isEnumSchema(\n schemaType: any,\n): schemaType is\n | PgEnumColumn<any>\n | PgEnumObjectColumn<any>\n | MySqlEnumColumn<any>\n | MySqlEnumObjectColumn<any> {\n return (\n is(schemaType, PgEnumColumn) ||\n is(schemaType, PgEnumObjectColumn) ||\n is(schemaType, MySqlEnumColumn) ||\n is(schemaType, MySqlEnumObjectColumn)\n );\n}\n\n// TODO make this compatible with other db drivers\ntype EnumTypes = PgEnum<any> | PgEnumObject<any>;\n\nexport type NonEnumFields<T> = {\n [K in keyof T as T[K] extends EnumTypes ? never : K]: T[K];\n};\n\n/**\n * Picks the keys of a schema object that are pgEnum definitions\n */\nexport type EnumFieldKeys<S> = keyof {\n [K in keyof S as S[K] extends EnumTypes ? K : never]: S[K];\n};\n\n/**\n * Fallback value tuple used whenever the concrete enum members cannot be\n * recovered from the drizzle types (e.g. an object-enum whose values were\n * widened to `string`, or a `tsName` that does not resolve against `Schema`).\n */\ntype UnknownEnumValues = readonly [string, ...string[]];\n\n/**\n * Extracts the literal value tuple carried by a drizzle enum definition.\n */\ntype EnumValuesOf<E> =\n E extends PgEnum<infer V>\n ? V\n : E extends PgEnumObject<infer O>\n ? ReadonlyArray<O[keyof O] & string>\n : UnknownEnumValues;\n\n/**\n * The GraphQL enum member union for a single `enum_(...)` call, resolved from\n * whichever of the three per-call generics the caller populated (`tsName` /\n * `enum` / `enumColumn`). The unused generics default to `never`, so\n * `[X] extends [never]` tells us which identification form was used.\n *\n * Anything we can't recover from the drizzle types (an object-enum widened to\n * `string`, or a `tsName` that doesn't resolve against `Schema`) falls back to\n * `string`, matching Pothos' own enum member type.\n */\ntype EnumMembers<Schema, TsName, EnumArg, EnumColumn> = [EnumColumn] extends [\n never,\n]\n ? [EnumArg] extends [never]\n ? [TsName] extends [never]\n ? string\n : TsName extends keyof Schema\n ? EnumValuesOf<Schema[TsName]>[number]\n : string\n : EnumValuesOf<EnumArg>[number]\n : EnumColumn extends { enumValues: infer CV extends UnknownEnumValues }\n ? CV[number]\n : string;\n\n/**\n * The strongly typed Pothos enum ref returned by a single `enum_(...)` call.\n *\n * Kept as a named, exported alias on purpose: the `.d.ts` emitter prints type\n * aliases by reference rather than expanding their bodies, so the (otherwise\n * very deep) `SchemaBuilder` / `EnumRef` types never get inlined into the\n * declaration output. Two details keep this printable without the emitter\n * recursing: referencing `SchemaBuilderType<...>` (a named alias) rather than\n * `typeof schemaBuilder` (a value), and inlining the member resolution so the\n * cyclic drizzle `Schema[TsName]` access never surfaces as its own symbol.\n */\nexport type EnumImplementationRef<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n Schema,\n TsName,\n EnumArg,\n EnumColumn,\n> =\n SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n > extends PothosSchemaTypes.SchemaBuilder<infer Types>\n ? PothosSchemaTypes.EnumRef<\n Types,\n EnumMembers<Schema, TsName, EnumArg, EnumColumn>\n >\n : never;\n\nexport type EnumImplementerType<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n AvailableEnums extends string,\n Schema extends Record<string, any> = Record<string, any>,\n> = ReturnType<\n typeof createEnumImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n AvailableEnums,\n Schema\n >\n>;\n\nexport const createEnumImplementer = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n AvailableEnums extends string,\n Schema extends Record<string, any> = Record<string, any>,\n>({\n schema,\n schemaBuilder,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig> & {\n schemaBuilder: SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n}) => {\n const referenceStorage = new Map<string, any>();\n\n /**\n * Registers a Postgres enum as a GraphQL enum type.\n *\n * You can identify the enum in three ways:\n * - `tsName`: the exported TypeScript identifier from your schema module. This is the\n * most typesafe form, only valid enum keys autocomplete, typos are caught at compile time.\n * - `enum`: pass the pgEnum object directly.\n * - `enumColumn`: pass a column that uses the enum.\n *\n * Use `refName` to override the auto-generated GraphQL type name.\n */\n const enumImplementer = <\n TsName extends AvailableEnums = never,\n EnumArg extends PgEnum<any> | PgEnumObject<any> = never,\n EnumColumn extends Column = never,\n RefName extends string = string,\n >(\n args: {\n refName?: RefName;\n } & (\n | { tsName: TsName; enum?: never; enumColumn?: never }\n | { enum: EnumArg; tsName?: never; enumColumn?: never }\n | { enumColumn: EnumColumn; tsName?: never; enum?: never }\n ),\n ): EnumImplementationRef<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n Schema,\n TsName,\n EnumArg,\n EnumColumn\n > => {\n const { refName } = args;\n const tsName = (args as { tsName?: string }).tsName;\n const enumObjectArg = (args as { enum?: PgEnum<any> | PgEnumObject<any> })\n .enum;\n const enumColumn = (args as { enumColumn?: Column }).enumColumn;\n\n let enumObject: PgEnum<any> | PgEnumObject<any> | undefined = enumObjectArg;\n\n if (tsName) {\n const candidate = (schema as Record<string, unknown>)[tsName];\n if (!candidate || !isPgEnum(candidate as any)) {\n throw new RumbleError(\n `Could not find a pgEnum exported as ${JSON.stringify(\n tsName,\n )} in the provided schema. ` +\n `Make sure the identifier exists and refers to a value created with \\`pgEnum(...)\\`.`,\n );\n }\n enumObject = candidate as PgEnum<any> | PgEnumObject<any>;\n }\n\n if (!enumObject && !enumColumn) {\n throw new RumbleError(\n `Could not determine enum structure! Pass one of 'tsName' (requires \\`schema\\` on rumble()), ` +\n `'enum' (the pgEnum object), or 'enumColumn' (a column that uses the enum).`,\n );\n }\n\n let enumSchemaName: string | undefined;\n let enumValues: any[] | undefined;\n\n if (enumObject) {\n enumSchemaName = enumObject.enumName;\n enumValues = enumObject.enumValues as unknown as any[];\n } else if (enumColumn) {\n // MySQL enum columns carry their values directly; there is no standalone\n // enum object. Derive a stable name from table + column name.\n if (\n is(enumColumn, MySqlEnumColumn) ||\n is(enumColumn, MySqlEnumObjectColumn)\n ) {\n enumValues = (enumColumn as any).enumValues as unknown as any[];\n const colTable = (enumColumn as any).table;\n const tableName =\n colTable && isTable(colTable) ? getTableName(colTable) : undefined;\n enumSchemaName = tableName\n ? `${tableName}_${enumColumn.name}`\n : enumColumn.name;\n } else {\n const pgEnum = (enumColumn as any).enum as\n | PgEnum<any>\n | PgEnumObject<any>\n | undefined;\n\n if (!pgEnum) {\n throw new RumbleError(\n `Could not find enum definition on column. Make sure the column is a pgEnum column.`,\n );\n }\n\n enumSchemaName = pgEnum.enumName;\n enumValues = enumColumn.enumValues as unknown as any[];\n }\n }\n\n if (!enumSchemaName || !enumValues) {\n throw new RumbleError(\"Could not determine enum structure!\");\n }\n\n const graphqlImplementationName =\n refName ?? `${capitalize(toCamelCase(enumSchemaName))}Enum`;\n\n // The runtime always produces a plain Pothos enum ref; the strong typing\n // lives entirely in the (explicit, named) return type, so we cast on the\n // way out. The named return alias is what keeps the `.d.ts` emitter from\n // recursing on the inlined SchemaBuilder/EnumRef types.\n type Ret = EnumImplementationRef<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n Schema,\n TsName,\n EnumArg,\n EnumColumn\n >;\n\n const cached = referenceStorage.get(graphqlImplementationName);\n if (cached) {\n return cached as Ret;\n }\n\n const ret = schemaBuilder.enumType(graphqlImplementationName, {\n values: enumValues,\n });\n referenceStorage.set(graphqlImplementationName, ret);\n return ret as unknown as Ret;\n };\n\n return enumImplementer;\n};\n","import {\n isBigIntLikeSQLTypeString,\n isBooleanSQLTypeString,\n isBytesSQLTypeString,\n isDateLikeSQLTypeString,\n isDateTimeLikeSQLTypeString,\n isFloatLikeSQLTypeString,\n isIDLikeSQLTypeString,\n isIntLikeSQLTypeString,\n isJSONFallbackSQLTypeString,\n isJSONLikeSQLTypeString,\n isStringLikeSQLTypeString,\n normalizeSQLType,\n type PossibleSQLType,\n UnknownTypeRumbleError,\n} from \"./types\";\n\nexport type GraphQLTypeName =\n | \"Int\"\n | \"Float\"\n | \"String\"\n | \"ID\"\n | \"Boolean\"\n | \"DateTime\"\n | \"Date\"\n | \"JSON\"\n | \"BigInt\"\n | \"Bytes\";\n\nexport function mapSQLTypeToGraphQLType({\n sqlType,\n fieldName,\n}: {\n sqlType: PossibleSQLType;\n fieldName?: string;\n}): GraphQLTypeName {\n // MySQL raw enum columns expose their values in the SQL type string.\n // Handle before normalization since normalization would strip the parens.\n if (/^enum\\(/.test(sqlType)) {\n return \"String\";\n }\n\n const normalized = normalizeSQLType(sqlType);\n\n let ret: GraphQLTypeName | undefined;\n\n if (isIntLikeSQLTypeString(normalized)) {\n ret = \"Int\";\n }\n\n if (isBigIntLikeSQLTypeString(normalized)) {\n ret = \"BigInt\";\n }\n\n if (isFloatLikeSQLTypeString(normalized)) {\n ret = \"Float\";\n }\n\n if (isStringLikeSQLTypeString(normalized)) {\n if (\n fieldName &&\n (fieldName.toLowerCase().endsWith(\"_id\") ||\n fieldName.toLowerCase().endsWith(\"id\"))\n ) {\n ret = \"ID\";\n } else {\n ret = \"String\";\n }\n }\n\n if (isIDLikeSQLTypeString(normalized)) {\n ret = \"ID\";\n }\n\n if (isBooleanSQLTypeString(normalized)) {\n ret = \"Boolean\";\n }\n\n if (isDateTimeLikeSQLTypeString(normalized)) {\n ret = \"DateTime\";\n }\n\n if (isDateLikeSQLTypeString(normalized)) {\n ret = \"Date\";\n }\n\n if (isJSONLikeSQLTypeString(normalized)) {\n ret = \"JSON\";\n }\n\n if (isJSONFallbackSQLTypeString(normalized)) {\n ret = \"JSON\";\n }\n\n if (isBytesSQLTypeString(normalized)) {\n ret = \"Bytes\";\n }\n\n if (ret !== undefined) {\n return ret;\n }\n\n throw UnknownTypeRumbleError(sqlType, \"SQL to GQL\");\n}\n","import { is } from \"drizzle-orm\";\nimport { toCamelCase } from \"drizzle-orm/casing\";\nimport { PgColumn } from \"drizzle-orm/pg-core\";\nimport { capitalize } from \"es-toolkit\";\nimport { type EnumImplementerType, isEnumSchema } from \"../enum\";\nimport { mapSQLTypeToGraphQLType } from \"../helpers/sqlTypes/mapSQLTypeToTSType\";\nimport type { PossibleSQLType } from \"../helpers/sqlTypes/types\";\nimport { tableHelper } from \"../helpers/tableHelpers\";\nimport type {\n DrizzleInstance,\n DrizzleQueryFunction,\n} from \"../types/drizzleInstanceType\";\nimport { RumbleError } from \"../types/rumbleError\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"../types/rumbleInput\";\nimport type { SchemaBuilderType } from \"../types/schemaBuilderType\";\n\n// TODO: in general, several of the filter methods should be more\n// restrictive in case of explicitly allowed columns\n// search, order and filter should be restricted to allowed cols\n// and should completely ignore other fields since one might be ably\n// to narrow down and guess the actual values behind forbidden columns by\n// using the provided args. This way one could guess, e.g. secrets which are forbidden by\n// the column abilitiy settings but will be respected in searches, etc.\n\nexport type WhereArgImplementerType<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n> = ReturnType<\n typeof createWhereArgImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >\n>;\n\nconst makeDefaultName = (dbName: string) =>\n `${capitalize(toCamelCase(dbName.toString()))}WhereInputArgument`;\n\nexport const createWhereArgImplementer = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>({\n db,\n schemaBuilder,\n enumImplementer,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig> & {\n enumImplementer: EnumImplementerType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n any\n >;\n schemaBuilder: SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n}) => {\n const referenceStorage = new Map<string, any>();\n const enumArrayWhereInputStorage = new Map<string, any>();\n const scalarArrayWhereInputStorage = new Map<string, any>();\n\n const scalarArrayWhereInputName = (gqlType: string) =>\n `${gqlType}ArrayWhereInputArgument`;\n\n const getScalarArrayWhereInput = (gqlType: string) => {\n const typeName = scalarArrayWhereInputName(gqlType);\n const existing = scalarArrayWhereInputStorage.get(typeName);\n if (existing) return existing;\n\n const ret = schemaBuilder.inputRef(typeName);\n scalarArrayWhereInputStorage.set(typeName, ret);\n\n ret.implement({\n fields: (t: any) => ({\n eq: t.field({ type: [gqlType], required: false }),\n ne: t.field({ type: [gqlType], required: false }),\n in: t.field({ type: [[gqlType]], required: false }),\n notIn: t.field({ type: [[gqlType]], required: false }),\n isNull: t.boolean({ required: false }),\n isNotNull: t.boolean({ required: false }),\n arrayOverlaps: t.field({ type: [gqlType], required: false }),\n arrayContained: t.field({ type: [gqlType], required: false }),\n arrayContains: t.field({ type: [gqlType], required: false }),\n AND: t.field({ type: [ret], required: false }),\n OR: t.field({ type: [ret], required: false }),\n NOT: t.field({ type: ret, required: false }),\n }),\n });\n\n return ret;\n };\n\n const getEnumArrayWhereInput = (enumImpl: any) => {\n const typeName = `${enumImpl.name}WhereInputArgument`;\n\n const existing = enumArrayWhereInputStorage.get(typeName);\n if (existing) {\n return existing;\n }\n\n const ret = schemaBuilder.inputRef(typeName);\n enumArrayWhereInputStorage.set(typeName, ret);\n\n ret.implement({\n fields: (t: any) => ({\n // the column holds an array, so eq/ne compare against a whole\n // array value and in/notIn against a list of array values\n eq: t.field({ type: [enumImpl], required: false }),\n ne: t.field({ type: [enumImpl], required: false }),\n in: t.field({ type: [[enumImpl]], required: false }),\n notIn: t.field({ type: [[enumImpl]], required: false }),\n isNull: t.boolean({ required: false }),\n isNotNull: t.boolean({ required: false }),\n arrayOverlaps: t.field({ type: [enumImpl], required: false }),\n arrayContained: t.field({ type: [enumImpl], required: false }),\n arrayContains: t.field({ type: [enumImpl], required: false }),\n AND: t.field({ type: [ret], required: false }),\n OR: t.field({ type: [ret], required: false }),\n NOT: t.field({ type: ret, required: false }),\n }),\n });\n\n return ret;\n };\n\n const whereArgImplementer = <\n TableName extends keyof DrizzleQueryFunction<DB>,\n RefName extends string,\n >({\n table,\n refName,\n dbName,\n }: Partial<{\n table: TableName;\n refName: RefName | undefined;\n dbName: string;\n }> &\n (\n | {\n table: TableName;\n }\n | {\n dbName: string;\n }\n )) => {\n const tableSchema = tableHelper({\n db,\n table: dbName ?? table!,\n });\n\n const inputTypeName = refName ?? makeDefaultName(tableSchema.tsName);\n\n const existing = referenceStorage.get(inputTypeName);\n if (existing) {\n return existing;\n }\n\n const ret = schemaBuilder.inputRef(inputTypeName);\n referenceStorage.set(inputTypeName, ret);\n\n ret.implement({\n fields: (t: any) => {\n const mapSQLTypeStringToInputPothosType = (\n sqlType: PossibleSQLType,\n fieldName: string,\n isArray: boolean,\n ) => {\n const gqlType = mapSQLTypeToGraphQLType({\n sqlType,\n fieldName,\n });\n\n if (isArray) {\n return t.field({\n type: getScalarArrayWhereInput(gqlType),\n required: false,\n });\n }\n\n switch (gqlType) {\n case \"Int\":\n return t.field({\n type: \"IntWhereInputArgument\",\n required: false,\n });\n case \"BigInt\":\n return t.field({\n type: \"BigIntWhereInputArgument\",\n required: false,\n });\n case \"String\":\n return t.field({\n type: \"StringWhereInputArgument\",\n required: false,\n });\n case \"Boolean\":\n return t.field({\n type: \"BooleanWhereInputArgument\",\n required: false,\n });\n case \"Date\":\n return t.field({\n type: \"DateWhereInputArgument\",\n required: false,\n });\n case \"DateTime\":\n return t.field({\n type: \"DateTimeWhereInputArgument\",\n required: false,\n });\n case \"Float\":\n return t.field({\n type: \"FloatWhereInputArgument\",\n required: false,\n });\n case \"ID\":\n return t.field({\n type: \"IDWhereInputArgument\",\n required: false,\n });\n case \"JSON\":\n return t.field({\n type: \"JSONWhereInputArgument\",\n required: false,\n });\n case \"Bytes\":\n // No meaningful filter operators for byte columns — skip.\n return null;\n default:\n throw new RumbleError(\n `Unsupported argument type ${gqlType} for column ${sqlType}`,\n );\n }\n };\n const fields = Object.entries(tableSchema.columns).reduce(\n (acc, [key, value]) => {\n // GraphQL reserves names starting with \"__\" for introspection.\n if (key.startsWith(\"__\")) return acc;\n\n // Detect pg array columns via the `dimensions` runtime property.\n let isArray = false;\n if (is(value, PgColumn)) {\n const dims = (value as PgColumn & { dimensions?: number })\n .dimensions;\n if (dims && dims > 0) isArray = true;\n }\n\n if (isEnumSchema(value)) {\n const enumImpl = enumImplementer({\n enumColumn: value,\n });\n\n acc[key] = t.field({\n type: isArray ? getEnumArrayWhereInput(enumImpl) : enumImpl,\n required: false,\n });\n } else {\n const field = mapSQLTypeStringToInputPothosType(\n value.getSQLType() as PossibleSQLType,\n key,\n isArray,\n );\n if (field !== null) {\n acc[key] = field;\n }\n }\n\n return acc;\n },\n {} as Record<string, ReturnType<typeof t.field>>,\n );\n\n const relations = Object.entries(tableSchema.relations ?? {}).reduce(\n (acc, [key, value]) => {\n // `targetTableName` is the publicly typed TS-key of the target\n // relation in db._.relations, prefer it over re-resolving via\n // the `targetTable` object.\n const targetTsName = (value as any).targetTableName as string;\n const relationSchema = tableHelper({\n db,\n table: targetTsName,\n });\n const referenceModel = whereArgImplementer({\n dbName: relationSchema.dbName,\n });\n\n acc[key] = t.field({\n type: referenceModel,\n required: false,\n });\n\n return acc;\n },\n {} as Record<\n keyof typeof tableSchema.columns,\n ReturnType<typeof mapSQLTypeStringToInputPothosType>\n >,\n );\n\n return {\n ...fields,\n ...relations,\n AND: t.field({ type: [ret], required: false }),\n OR: t.field({ type: [ret], required: false }),\n NOT: t.field({ type: ret, required: false }),\n };\n },\n });\n\n return ret;\n };\n\n return whereArgImplementer;\n};\n","import type { DrizzleInstance } from \"../types/drizzleInstanceType\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"../types/rumbleInput\";\nimport type { SchemaBuilderType } from \"../types/schemaBuilderType\";\nimport { generateFromSchema } from \"./generate/generate\";\n\nexport const clientCreatorImplementer = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>({\n builtSchema,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig> & {\n builtSchema: () => ReturnType<\n SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >[\"toSchema\"]\n >;\n}) => {\n const clientCreator = async ({\n apiUrl,\n outputPath,\n rumbleImportPath,\n useExternalUrqlClient,\n removeExisting,\n forceReactivity,\n autoIncludeIdField = false,\n }: {\n /**\n * Path to the output directory where the client files will be generated.\n */\n outputPath: string;\n /**\n * The base URL of the Rumble API.\n */\n apiUrl?: string;\n /**\n * The import path for the rumble library, defaults to \"@m1212e/rumble/client\".\n */\n rumbleImportPath?: string;\n /**\n * Set this to use an external urql client exported from a module.\n * If a string, uses the provided path to the urql client for importing the client.\n * If false, creates a new urql client with the provided apiUrl.\n */\n useExternalUrqlClient?: string;\n /**\n * Whether to remove existing generated files in the output directory before generating new ones.\n */\n removeExisting?: boolean;\n /**\n * Whether to force reactivity for generated queries and mutations. This will prevent the actual response fields of the awaited response from being populated\n * and requires you to subscribe to the response to access the data. Useful to prevent forgetting to subscribe to the response to utilize reactive data.\n */\n forceReactivity?: boolean;\n /**\n * Whether to automatically include the `id` field in generated queries and mutations.\n * This might be helpful to ensure that caching works correctly since all object will always be identifiable by their `id`.\n * Can be set to `true` to always include the `id` field, or to `false` to never include it.\n * Can also be set to a string to include a custom named field as Id field in case you have a different naming convention like `_id`.\n *\n * @default false\n */\n autoIncludeIdField?: boolean | string;\n }) => {\n if (process.env.NODE_ENV !== \"development\") {\n console.warn(\n `Running rumble client generation in non development mode. Are you sure this is correct? Called with arguments: ${JSON.stringify(\n {\n outputPath,\n apiUrl,\n rumbleImportPath,\n useExternalUrqlClient,\n removeExisting,\n },\n )}`,\n );\n }\n const schema = builtSchema();\n await generateFromSchema({\n schema,\n outputPath,\n rumbleImportPath,\n apiUrl,\n useExternalUrqlClient,\n removeExisting,\n forceReactivity,\n autoIncludeIdField,\n });\n };\n\n return clientCreator;\n};\n","import type { AbilityBuilderType } from \"./abilityBuilder\";\nimport { lazy } from \"./helpers/lazy\";\nimport type { DrizzleInstance } from \"./types/drizzleInstanceType\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\n\nexport type ContextFunctionType<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n> = ReturnType<\n typeof createContextFunction<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >\n>;\n\nexport type ContextType<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n> = Awaited<\n ReturnType<\n ContextFunctionType<UserContext, DB, RequestEvent, Action, PothosConfig>\n >\n>;\n\nexport const createContextFunction = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>({\n context: makeUserContext,\n abilityBuilder,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig> & {\n abilityBuilder: AbilityBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n}) => {\n const builtAbilityBuilder = lazy(() => abilityBuilder._.build());\n\n return async (req: RequestEvent) => {\n const userContext = makeUserContext\n ? await makeUserContext(req)\n : ({} as UserContext);\n\n return {\n ...userContext,\n abilities: builtAbilityBuilder()(userContext),\n };\n };\n};\n","export function deepSetProto(\n obj: any,\n proto = Object.prototype,\n seen = new WeakSet(),\n) {\n if (obj === null || typeof obj !== \"object\") return;\n if (seen.has(obj)) return;\n seen.add(obj);\n\n if (Array.isArray(obj)) {\n for (const item of obj) {\n deepSetProto(item, proto, seen);\n }\n return;\n }\n\n const currentProto = Object.getPrototypeOf(obj);\n if (currentProto !== Object.prototype && currentProto !== null) {\n return;\n }\n Object.setPrototypeOf(obj, proto);\n for (const key of Object.keys(obj)) {\n deepSetProto(obj[key], proto, seen);\n }\n}\n","import { count } from \"drizzle-orm\";\nimport pluralize from \"pluralize\";\nimport type { WhereArgImplementerType } from \"./args/whereArg\";\nimport { assertFirstEntryExists } from \"./helpers/asserts\";\nimport { mapNullFieldsToUndefined } from \"./helpers/mapNullFieldsToUndefined\";\nimport { deepSetProto } from \"./helpers/protoMapper\";\nimport { tableHelper } from \"./helpers/tableHelpers\";\nimport type { MakePubSubInstanceType } from \"./pubsub\";\nimport type {\n DrizzleInstance,\n DrizzleQueryFunction,\n TableRelationNames,\n} from \"./types/drizzleInstanceType\";\nimport { RumbleErrorSafe } from \"./types/rumbleError\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\nimport type { SchemaBuilderType } from \"./types/schemaBuilderType\";\n\nexport const createCountQueryImplementer = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n Schema extends Record<string, any>,\n>({\n db,\n schemaBuilder,\n whereArgImplementer,\n makePubSubInstance,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig, Schema> & {\n schemaBuilder: SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n whereArgImplementer: WhereArgImplementerType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n makePubSubInstance: MakePubSubInstanceType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n}) => {\n return <TableName extends TableRelationNames<DB>>({\n table,\n listAction = \"read\" as Action,\n isAllowed,\n }: {\n /**\n * The table for which to implement the count query\n */\n table: TableName;\n /**\n * Which action should be used for listing many entities\n * @default \"read\"\n */\n listAction?: Action;\n /**\n * Optional function to check if the query is allowed\n */\n isAllowed?: (context: UserContext) => boolean | Promise<boolean>;\n }) => {\n const WhereArg = whereArgImplementer({\n table: table,\n });\n const { registerOnInstance } = makePubSubInstance({ table: table });\n\n const tableSchema = tableHelper({\n db,\n table,\n });\n\n return schemaBuilder.queryFields((t) => {\n return {\n [`${pluralize.plural(String(table))}Count`]: t.field({\n type: \"Int\",\n nullable: false,\n smartSubscription: true,\n description: `Count all ${pluralize.plural(String(table))}`,\n subscribe: (subscriptions, _root, _args, _ctx, _info) => {\n registerOnInstance({\n instance: subscriptions,\n action: \"created\",\n });\n registerOnInstance({\n instance: subscriptions,\n action: \"removed\",\n });\n },\n args: {\n where: t.arg({ type: WhereArg, required: false }),\n },\n resolve: async (_root, args, ctx, _info) => {\n if (isAllowed && !(await isAllowed(ctx))) {\n throw new RumbleErrorSafe(\"Not allowed to perform this action\");\n }\n\n deepSetProto(args);\n\n return (db as any)\n .select({ count: count() })\n .from(tableSchema.table)\n .where(\n ctx.abilities[table]\n .filter(listAction)\n .merge(mapNullFieldsToUndefined(args) as any).sql.where,\n )\n .then(assertFirstEntryExists)\n .then((r: any) => r.count);\n },\n }),\n };\n });\n };\n};\n","import type { useSofa } from \"sofa-api\";\n\nexport const sofaOpenAPIWebhookDocs: NonNullable<\n Parameters<typeof useSofa>[0][\"openAPI\"]\n> = {\n paths: {\n \"/webhook\": {\n post: {\n operationId: \"webhook_create\",\n description: \"Creates a webhook subscription.\",\n tags: [],\n parameters: [],\n requestBody: {\n content: {\n \"application/json\": {\n schema: {\n $ref: \"#/components/schemas/WebhookCreateBody\",\n },\n },\n },\n },\n responses: {\n \"200\": {\n description: \"\",\n content: {\n \"application/json\": {\n schema: {\n $ref: \"#/components/schemas/WebhookDetailResponse\",\n },\n },\n },\n },\n },\n },\n },\n \"/webhook/{id}\": {\n post: {\n operationId: \"webhook_update\",\n description: \"Updates a webhook subscription.\",\n parameters: [\n {\n name: \"id\",\n in: \"path\",\n description: \"The ID of the webhook to update\",\n required: true,\n schema: {\n type: \"string\",\n },\n } as any,\n ],\n requestBody: {\n content: {\n \"application/json\": {\n schema: {\n $ref: \"#/components/schemas/WebhookCreateBody\",\n },\n },\n },\n },\n responses: {\n \"200\": {\n description: \"\",\n content: {\n \"application/json\": {\n schema: {\n $ref: \"#/components/schemas/WebhookDetailResponse\",\n },\n },\n },\n },\n },\n },\n delete: {\n operationId: \"webhook_delete\",\n description: \"Removes a webhook subscription.\",\n tags: [],\n parameters: [\n {\n name: \"id\",\n in: \"path\",\n description: \"The ID of the webhook to delete\",\n required: true,\n schema: {\n type: \"string\",\n },\n } as any,\n ],\n responses: {\n \"200\": {\n description: \"\",\n content: {\n \"application/json\": {\n schema: {\n $ref: \"#/components/schemas/WebhookDetailResponse\",\n },\n },\n },\n },\n },\n },\n },\n },\n components: {\n schemas: {\n WebhookCreateBody: {\n type: \"object\",\n properties: {\n subscription: {\n description:\n \"The subscription to subscribe to. In many cases, these match the available query IDs without the '_query' suffix. E.g., 'users_query' -> 'users'. See the graphql schema for more details on what subscriptions are available.\",\n type: \"string\",\n },\n variables: {\n description: \"The variables to pass to the subscription.\",\n type: \"object\",\n },\n url: {\n description: \"The URL to send the webhook to.\",\n type: \"string\",\n },\n },\n },\n WebhookDetailResponse: {\n type: \"object\",\n properties: {\n id: {\n description:\n \"The ID of the webhook. Can be used as reference in update or delete calls.\",\n type: \"string\",\n },\n },\n },\n DateTime: {\n type: \"string\",\n format: \"date-time\",\n },\n Date: {\n type: \"string\",\n format: \"date\",\n },\n },\n },\n};\n","import type { GraphQLError } from \"graphql\";\n\n/**\n * Shape of a single error entry in a log's `errors` array, following\n * OpenTelemetry's exception semantic conventions\n * (https://opentelemetry.io/docs/specs/semconv/exceptions/exceptions-logs/).\n */\nexport interface LoggedException {\n \"exception.type\": string;\n \"exception.message\": string;\n \"exception.stacktrace\"?: string;\n path?: ReadonlyArray<string | number>;\n extensions?: Record<string, unknown>;\n}\n\nfunction hasMessage(error: unknown): error is { message: unknown } {\n return typeof error === \"object\" && error !== null && \"message\" in error;\n}\n\nfunction toLoggedException(error: unknown): LoggedException {\n if (hasMessage(error)) {\n const gqlError = error as Partial<GraphQLError> & Error;\n return {\n \"exception.type\": gqlError.constructor?.name ?? gqlError.name ?? \"Error\",\n \"exception.message\": String(gqlError.message),\n ...(gqlError.stack ? { \"exception.stacktrace\": gqlError.stack } : {}),\n ...(gqlError.path ? { path: gqlError.path } : {}),\n ...(gqlError.extensions && Object.keys(gqlError.extensions).length > 0\n ? { extensions: gqlError.extensions }\n : {}),\n };\n }\n return {\n \"exception.type\": \"UnknownError\",\n \"exception.message\": String(error),\n };\n}\n\n/**\n * Every erroneous rumble log carries the same `errors` array shape,\n * whether it originates from a thrown exception (single-element array)\n * or a GraphQL `ExecutionResult.errors` list (multi-element array).\n */\nexport function errorsLogField(errors: readonly unknown[]): {\n errors: LoggedException[];\n} {\n return { errors: errors.map(toLoggedException) };\n}\n\nexport function errorLogField(error: unknown): { errors: LoggedException[] } {\n return errorsLogField([error]);\n}\n","import { type Span, SpanStatusCode } from \"@opentelemetry/api\";\nimport { AttributeNames, SpanNames } from \"@pothos/tracing-opentelemetry\";\nimport {\n execute as defaultExecute,\n subscribe as defaultSubscribe,\n type ExecutionArgs,\n type ExecutionResult,\n getOperationAST,\n print,\n} from \"graphql\";\nimport type { DrizzleInstance } from \"../types/drizzleInstanceType\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n RumbleLogger,\n} from \"../types/rumbleInput\";\nimport { errorLogField, errorsLogField } from \"./errorLogging\";\n\n// @pothos/tracing-opentelemetry's SpanNames enum has no subscribe member.\nconst SUBSCRIBE_SPAN_NAME = \"graphql.subscribe\";\n\nfunction getOperationType(options: ExecutionArgs) {\n return getOperationAST(options.document, options.operationName)?.operation;\n}\n\nfunction operationLogFields(operationName: string, operationType?: string) {\n return {\n \"graphql.operation.name\": operationName,\n ...(operationType ? { \"graphql.operation.type\": operationType } : {}),\n };\n}\n\nfunction traceIdLogFields(span: Span) {\n const { traceId, spanId, traceFlags } = span.spanContext();\n return {\n trace_id: traceId,\n span_id: spanId,\n trace_flags: traceFlags.toString(16).padStart(2, \"0\"),\n };\n}\n\nexport function isAsyncIterable(\n value: unknown,\n): value is AsyncIterable<unknown> {\n return (\n typeof value === \"object\" && value !== null && Symbol.asyncIterator in value\n );\n}\n\nexport async function* wrapSubscriptionIterator(\n iterator: AsyncIterable<ExecutionResult>,\n log: RumbleLogger,\n operationName: string,\n operationType?: string,\n): AsyncGenerator<ExecutionResult> {\n let eventCount = 0;\n try {\n for await (const event of iterator) {\n eventCount++;\n if (event.errors?.length) {\n log.error(\n {\n ...operationLogFields(operationName, operationType),\n event_count: eventCount,\n ...errorsLogField(event.errors),\n },\n \"graphql subscription event error\",\n );\n }\n yield event;\n }\n log.info(\n {\n ...operationLogFields(operationName, operationType),\n event_count: eventCount,\n },\n \"graphql subscription completed\",\n );\n } catch (error) {\n log.error(\n {\n ...operationLogFields(operationName, operationType),\n event_count: eventCount,\n ...errorLogField(error),\n },\n \"graphql subscription threw\",\n );\n throw error;\n }\n}\n\nexport function buildTracedExecute<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>(\n executeFn: (\n args: ExecutionArgs,\n ) => Promise<ExecutionResult> | ExecutionResult,\n rumbleInput: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig>,\n): (args: ExecutionArgs) => Promise<ExecutionResult> {\n return async (options: ExecutionArgs): Promise<ExecutionResult> => {\n let log = rumbleInput.logger?.enabled\n ? rumbleInput.logger.logger\n : undefined;\n const operationName = options.operationName ?? \"anonymous\";\n const operationType = getOperationType(options);\n const start = Date.now();\n\n log?.info(\n operationLogFields(operationName, operationType),\n \"graphql execute start\",\n );\n\n const run = async () => {\n const result = await executeFn(options);\n if (result && \"errors\" in result && result.errors?.length) {\n log?.error(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n ...errorsLogField(result.errors),\n },\n \"graphql execute completed with errors\",\n );\n } else {\n log?.info(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n },\n \"graphql execute completed\",\n );\n }\n return result;\n };\n\n if (rumbleInput.otel?.enabled) {\n return rumbleInput.otel.tracer!.startActiveSpan(\n SpanNames.EXECUTE,\n {\n attributes: {\n [AttributeNames.OPERATION_NAME]: operationName,\n ...(operationType\n ? { [AttributeNames.OPERATION_TYPE]: operationType }\n : {}),\n \"graphql.document\": print(options.document),\n },\n },\n async (span: Span) => {\n if (log && rumbleInput.logger?.injectTraceId !== false) {\n log = log.child(traceIdLogFields(span));\n }\n try {\n const result = await run();\n if (result && \"errors\" in result && result.errors?.length) {\n for (const error of result.errors) span.recordException(error);\n span.setStatus({ code: SpanStatusCode.ERROR });\n }\n return result;\n } catch (error) {\n if (error instanceof Error) span.recordException(error);\n log?.error(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n ...errorLogField(error),\n },\n \"graphql execute threw\",\n );\n span.setStatus({ code: SpanStatusCode.ERROR });\n throw error;\n } finally {\n span.end();\n }\n },\n );\n }\n\n try {\n return await run();\n } catch (error) {\n log?.error(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n ...errorLogField(error),\n },\n \"graphql execute threw\",\n );\n throw error;\n }\n };\n}\n\nexport function buildTracedSubscribe<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>(\n subscribeFn: (\n args: ExecutionArgs,\n ) =>\n | Promise<AsyncIterable<ExecutionResult> | ExecutionResult>\n | AsyncIterable<ExecutionResult>\n | ExecutionResult,\n rumbleInput: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig>,\n): (\n args: ExecutionArgs,\n) => Promise<AsyncIterable<ExecutionResult> | ExecutionResult> {\n return async (\n options: ExecutionArgs,\n ): Promise<AsyncIterable<ExecutionResult> | ExecutionResult> => {\n let log = rumbleInput.logger?.enabled\n ? rumbleInput.logger.logger\n : undefined;\n const operationName = options.operationName ?? \"anonymous\";\n const operationType = getOperationType(options);\n const start = Date.now();\n\n const doSubscribe = async (): Promise<\n AsyncIterable<ExecutionResult> | ExecutionResult\n > => {\n log?.info(\n operationLogFields(operationName, operationType),\n \"graphql subscribe start\",\n );\n\n const result = await subscribeFn(options);\n\n if (!isAsyncIterable(result)) {\n const execResult = result as ExecutionResult;\n if (execResult.errors?.length) {\n log?.error(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n ...errorsLogField(execResult.errors),\n },\n \"graphql subscribe completed with errors\",\n );\n }\n return execResult;\n }\n\n log?.info(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n },\n \"graphql subscription established\",\n );\n\n if (log) {\n return wrapSubscriptionIterator(\n result as AsyncIterable<ExecutionResult>,\n log,\n operationName,\n operationType,\n );\n }\n return result;\n };\n\n if (rumbleInput.otel?.enabled) {\n return rumbleInput.otel.tracer!.startActiveSpan(\n SUBSCRIBE_SPAN_NAME,\n {\n attributes: {\n [AttributeNames.OPERATION_NAME]: operationName,\n ...(operationType\n ? { [AttributeNames.OPERATION_TYPE]: operationType }\n : {}),\n \"graphql.document\": print(options.document),\n },\n },\n async (span: Span) => {\n if (log && rumbleInput.logger?.injectTraceId !== false) {\n log = log.child(traceIdLogFields(span));\n }\n try {\n const result = await doSubscribe();\n if (!isAsyncIterable(result)) {\n const execResult = result as ExecutionResult;\n if (execResult.errors?.length) {\n for (const error of execResult.errors)\n span.recordException(error);\n span.setStatus({ code: SpanStatusCode.ERROR });\n }\n }\n return result;\n } catch (error) {\n if (error instanceof Error) span.recordException(error);\n log?.error(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n ...errorLogField(error),\n },\n \"graphql subscribe threw\",\n );\n span.setStatus({ code: SpanStatusCode.ERROR });\n throw error;\n } finally {\n span.end();\n }\n },\n );\n }\n\n try {\n return await doSubscribe();\n } catch (error) {\n log?.error(\n {\n ...operationLogFields(operationName, operationType),\n duration_ms: Date.now() - start,\n ...errorLogField(error),\n },\n \"graphql subscribe threw\",\n );\n throw error;\n }\n };\n}\n\nexport { defaultExecute, defaultSubscribe };\n","import type { DrizzleObjectFieldBuilder } from \"@pothos/plugin-drizzle\";\nimport { RumbleError } from \"../../types/rumbleError\";\nimport { mapSQLTypeToGraphQLType } from \"./mapSQLTypeToTSType\";\nimport type { PossibleSQLType } from \"./types\";\n\nexport function buildPothosResponseTypeFromGraphQLType<\n Builder extends DrizzleObjectFieldBuilder<any, any, any, any>,\n>({\n builder,\n sqlType,\n fieldName,\n nullable,\n isArray,\n}: {\n builder: Builder;\n sqlType: PossibleSQLType;\n fieldName: string;\n nullable: boolean;\n isArray: boolean;\n}) {\n const gqlType = mapSQLTypeToGraphQLType({\n sqlType,\n fieldName,\n });\n switch (gqlType) {\n case \"Int\":\n return isArray\n ? builder.exposeIntList(fieldName, { nullable: nullable as any })\n : builder.exposeInt(fieldName, { nullable });\n case \"BigInt\":\n return builder.field({\n type: isArray ? [\"BigInt\"] : \"BigInt\",\n resolve: (element: any) => element[fieldName],\n nullable,\n });\n case \"String\":\n return isArray\n ? builder.exposeStringList(fieldName, { nullable: nullable as any })\n : builder.exposeString(fieldName, { nullable });\n case \"Boolean\":\n return isArray\n ? builder.exposeBooleanList(fieldName, { nullable: nullable as any })\n : builder.exposeBoolean(fieldName, { nullable });\n case \"Date\":\n return builder.field({\n type: isArray ? [\"Date\"] : \"Date\",\n resolve: (element: any) => element[fieldName],\n nullable,\n });\n case \"DateTime\":\n return builder.field({\n type: isArray ? [\"DateTime\"] : \"DateTime\",\n // Drizzle's timestamp({ mode: \"string\" }) returns a string; the\n // DateTimeISO scalar expects a Date object, so coerce when needed.\n resolve: (element: any) => {\n const v = element[fieldName];\n if (v == null) return v;\n return v instanceof Date ? v : new Date(v);\n },\n nullable,\n });\n case \"Float\":\n return isArray\n ? builder.exposeFloatList(fieldName, { nullable: nullable as any })\n : builder.exposeFloat(fieldName, { nullable });\n case \"ID\":\n return isArray\n ? builder.exposeIDList(fieldName, { nullable: nullable as any })\n : builder.exposeID(fieldName, { nullable });\n case \"JSON\":\n return builder.field({\n type: isArray ? [\"JSON\"] : \"JSON\",\n resolve: (element: any) => element[fieldName],\n nullable,\n });\n case \"Bytes\":\n return builder.field({\n type: \"Bytes\",\n resolve: (element: any) => {\n const v = element[fieldName];\n if (v == null) return v;\n return Buffer.isBuffer(v) ? v.toString(\"base64\") : String(v);\n },\n nullable,\n });\n default:\n throw new RumbleError(\n `Unsupported object type ${gqlType} for column ${fieldName}`,\n );\n }\n}\n","import { is } from \"drizzle-orm\";\nimport type { MySqlAsyncDatabase } from \"drizzle-orm/mysql-core\";\nimport { MySqlTable } from \"drizzle-orm/mysql-core\";\nimport type { PgAsyncDatabase } from \"drizzle-orm/pg-core\";\nimport { PgTable } from \"drizzle-orm/pg-core\";\nimport type { SQLiteAsyncDatabase } from \"drizzle-orm/sqlite-core\";\nimport { SQLiteTable } from \"drizzle-orm/sqlite-core\";\nimport type { DrizzleInstance } from \"../types/drizzleInstanceType\";\n\nexport type DBDialect = \"mysql\" | \"postgres\" | \"sqlite\";\n\nconst dialectCache = new WeakMap<object, DBDialect>();\n\nexport function determineDBDialectFromSchema<DB extends DrizzleInstance>(\n schema: DB[\"_\"][\"relations\"],\n): DBDialect {\n const cached = dialectCache.get(schema as unknown as object);\n if (cached) return cached;\n\n const found = new Set<DBDialect>();\n\n for (const table of Object.values(schema).map((t: any) => t.table)) {\n if (!table || typeof table !== \"object\") {\n continue;\n }\n\n // `is()` survives duplicate drizzle-orm copies in node_modules where\n // `instanceof` silently returns false against the \"wrong\" class identity.\n if (is(table, PgTable)) {\n found.add(\"postgres\");\n } else if (is(table, MySqlTable)) {\n found.add(\"mysql\");\n } else if (is(table, SQLiteTable)) {\n found.add(\"sqlite\");\n }\n }\n\n const dialects = Array.from(found);\n\n if (dialects.length === 1) {\n const only = dialects[0]!;\n dialectCache.set(schema as unknown as object, only);\n return only;\n }\n\n if (dialects.length === 0) {\n throw new Error(\"No tables found in schema, could not determine dialect\");\n }\n\n throw new Error(`Multiple dialects found in schema: ${dialects.join(\", \")}`);\n}\n\nexport function isPostgresDB<\n Narrowed extends PgAsyncDatabase<any, any> = PgAsyncDatabase<any, any>,\n>(db: any): db is Narrowed {\n return determineDBDialectFromSchema(db._.relations) === \"postgres\";\n}\n\nexport function isMySQLDB<\n Narrowed extends MySqlAsyncDatabase<any, any> = MySqlAsyncDatabase<any, any>,\n>(db: any): db is Narrowed {\n return determineDBDialectFromSchema(db._.relations) === \"mysql\";\n}\n\nexport function isSQLiteDB<\n Narrowed extends SQLiteAsyncDatabase<any, any, any> = SQLiteAsyncDatabase<\n any,\n any,\n any\n >,\n>(db: any): db is Narrowed {\n return determineDBDialectFromSchema(db._.relations) === \"sqlite\";\n}\n","import { sql } from \"drizzle-orm\";\nimport { cloneDeep } from \"es-toolkit\";\nimport { isPostgresDB } from \"./helpers/determineDialectFromSchema\";\nimport { errorLogField } from \"./helpers/errorLogging\";\nimport {\n isIDLikeSQLTypeString,\n isStringLikeSQLTypeString,\n} from \"./helpers/sqlTypes/types\";\nimport type { tableHelper } from \"./helpers/tableHelpers\";\nimport type { RumbleInput } from \"./types/rumbleInput\";\n\nexport async function initSearchIfApplicable(\n input: RumbleInput<any, any, any, any, any, any>,\n) {\n const log = input.logger?.enabled ? input.logger.logger : undefined;\n\n if (!isPostgresDB(input.db)) {\n const msg =\n \"Database dialect is not compatible with search, skipping search initialization. Only PostgreSQL is supported.\";\n log ? log.info({}, msg) : console.info(msg);\n return;\n }\n\n try {\n await input.db.execute(sql`CREATE EXTENSION IF NOT EXISTS pg_trgm;`);\n } catch (error) {\n const msg =\n \"Failed to create pg_trgm extension. Search functionality may not work. Ensure the database user has CREATE privilege or the extension is pre-installed.\";\n log ? log.error(errorLogField(error), msg) : console.error(msg, error);\n return;\n }\n if (input.search?.threshold) {\n // make absolutely sure the threshold is a number\n const threshold = Number(input.search.threshold);\n\n if (threshold < 0 || threshold > 1) {\n throw new Error(`Search threshold must be between 0 and 1`);\n }\n\n const result = await input.db.execute(sql`SELECT current_database()`);\n const dbName = result.rows[0].current_database;\n\n try {\n await input.db.execute(\n sql.raw(\n `ALTER DATABASE ${dbName} SET pg_trgm.similarity_threshold = ${threshold};`,\n ),\n );\n } catch (error: any) {\n // XX000 = tuple concurrently updated: multiple workers racing to set the same\n // idempotent value at startup. Safe to ignore — one of them will win.\n if (error?.cause?.code !== \"XX000\" && error?.code !== \"XX000\")\n throw error;\n }\n }\n\n if (input.search?.cpu_operator_cost) {\n if (typeof input.search.cpu_operator_cost !== \"number\") {\n throw new Error(`CPU operator cost must be a number`);\n }\n\n if (input.search.cpu_operator_cost <= 0) {\n throw new Error(`CPU operator cost must be a positive number`);\n }\n }\n}\n\n/**\n * Performs adjustments to the query args to issue a full text search in case the\n * respective feature is enabled and a search term was provided.\n */\nexport function adjustQueryArgsForSearch({\n search,\n args,\n tableSchema,\n abilities,\n}: Pick<RumbleInput<any, any, any, any, any, any>, \"search\"> & {\n //TODO types\n args: any;\n tableSchema: ReturnType<typeof tableHelper>;\n //TODO types\n abilities: any;\n}) {\n if (search?.enabled && args.search && args.search.length > 0) {\n // this prevents columns beeing searched which are not accessible to the user\n // if the abilities defined the user not to be allowed to read something, we need\n // to prevent it from beeing included in the search since this could\n // leak information\n const columnsToSearch = (\n abilities.query.many.columns\n ? Object.entries(tableSchema.columns).filter(\n ([key]) => abilities.query.many.columns[key],\n )\n : Object.entries(tableSchema.columns)\n ).filter(\n ([_key, col]) =>\n isStringLikeSQLTypeString(col.getSQLType()) ||\n isIDLikeSQLTypeString(col.getSQLType()),\n );\n\n const searchParam = sql`${args.search}`;\n\n args.extras = {\n search_distance: (table: any) =>\n sql`${sql.join(\n columnsToSearch.map(([key]) => {\n return sql`COALESCE((${table[key]}::TEXT <-> ${searchParam}), 1)`;\n }),\n sql.raw(\" + \"),\n )}`,\n };\n\n const originalOrderBy = cloneDeep(args.orderBy);\n (args as any).orderBy = (table: any) => {\n const argsOrderBySQL = sql.join(\n Object.entries(originalOrderBy ?? {}).map(([key, value]) => {\n // value is \"asc\" or \"desc\"\n if (value === \"asc\") {\n return sql`${table[key]} ASC`;\n } else if (value === \"desc\") {\n return sql`${table[key]} DESC`;\n } else {\n throw new Error(`Invalid value ${value} for orderBy`);\n }\n }),\n sql.raw(\", \"),\n );\n\n const searchSQL = sql`search_distance ASC`;\n\n const ret = originalOrderBy\n ? sql.join([argsOrderBySQL, searchSQL], sql.raw(\", \"))\n : searchSQL;\n\n return ret;\n };\n\n const originalWhere = cloneDeep(args.where);\n\n // this limits the search to the rows which at least match the threshold score\n (args as any).where = {\n AND: [\n originalWhere ?? {},\n {\n RAW: (table: any) =>\n sql`(${sql.join(\n columnsToSearch.map(([key]) => {\n return sql`${table[key]} % ${searchParam}`;\n }),\n sql.raw(\" OR \"),\n )})`,\n },\n ],\n };\n }\n}\n","import type { FieldMap } from \"@pothos/core\";\nimport type { DrizzleObjectFieldBuilder } from \"@pothos/plugin-drizzle\";\nimport { is, One } from \"drizzle-orm\";\nimport { PgColumn } from \"drizzle-orm/pg-core\";\nimport { capitalize } from \"es-toolkit\";\nimport pluralize from \"pluralize\";\nimport type { AbilityBuilderType } from \"./abilityBuilder\";\nimport type { OrderArgImplementerType } from \"./args/orderArg\";\nimport type { WhereArgImplementerType } from \"./args/whereArg\";\nimport { type EnumImplementerType, isEnumSchema } from \"./enum\";\nimport { buildPothosResponseTypeFromGraphQLType } from \"./helpers/sqlTypes/mapDrizzleTypeToGraphQlType\";\nimport type { PossibleSQLType } from \"./helpers/sqlTypes/types\";\nimport { tableHelper } from \"./helpers/tableHelpers\";\nimport type { MakePubSubInstanceType } from \"./pubsub\";\nimport { adjustQueryArgsForSearch } from \"./search\";\nimport type {\n DrizzleInstance,\n DrizzleQueryFunction,\n DrizzleTableValueType,\n TableRelationNames,\n} from \"./types/drizzleInstanceType\";\nimport { RumbleError } from \"./types/rumbleError\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\nimport type { SchemaBuilderType } from \"./types/schemaBuilderType\";\n\n// TODO remove as many as any types as possible here\n\n//TODO this is a bit flaky, we should check if we can determine the config object more reliably\n//TODO maybe a plugin can place some marker field on these objects?\n// like this?\n// if (t instanceof DrizzleObjectOptions) {\n// return true;\n// }\n\nconst isProbablyAConfigObject = (t: any) => {\n if (typeof t !== \"object\") {\n return false;\n }\n\n if (\n Object.keys(t).some((k) =>\n [\n \"args\",\n \"nullable\",\n \"query\",\n \"subscribe\",\n \"description\",\n \"type\",\n \"resolve\",\n ].find((e) => e === k),\n )\n )\n return true;\n return false;\n};\n\nexport const createObjectImplementer = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n Schema extends Record<string, any>,\n>({\n db,\n search,\n logger: loggerConfig,\n schemaBuilder,\n makePubSubInstance,\n whereArgImplementer,\n orderArgImplementer,\n enumImplementer,\n abilityBuilder,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig, Schema> & {\n schemaBuilder: SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n whereArgImplementer: WhereArgImplementerType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n orderArgImplementer: OrderArgImplementerType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n enumImplementer: EnumImplementerType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n any\n >;\n makePubSubInstance: MakePubSubInstanceType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n abilityBuilder: AbilityBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n}) => {\n type SchemaBuilder = SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n return <TableName extends TableRelationNames<DB>, RefName extends string>({\n table,\n refName,\n readAction = \"read\" as Action,\n adjust,\n }: {\n /**\n * The table you want to be used as reference for the object creation.\n */\n table: TableName;\n /**\n * The name you want this object to have in your graphql schema.\n * Rumble will create a reasonable default if not specified.\n */\n refName?: RefName;\n /**\n * The action used for read access to the table.\n * Defaults to \"read\".\n */\n readAction?: Action;\n /**\n * A function which can be used to adjust the fields of the object.\n * You can extend the object by specifying fields that do not exist as\n * per your db schema, or overwrite existing fields with the same name.\n * In case you do overwrite, rumble will set proper nullability and\n * subscription properties if you do not specify them explicitly.\n */\n adjust?:\n | ((\n t: DrizzleObjectFieldBuilder<\n SchemaBuilder[\"$inferSchemaTypes\"],\n SchemaBuilder[\"$inferSchemaTypes\"][\"DrizzleRelations\"][TableName],\n DrizzleTableValueType<DB, TableName>\n >,\n ) => FieldMap)\n | undefined;\n }) => {\n const tableSchema = tableHelper({ db, table });\n\n if (Object.keys(tableSchema.primaryKey).length === 0) {\n const log = loggerConfig?.enabled ? loggerConfig.logger : undefined;\n const msg = `Could not find primary key for ${String(table)}. Cannot register subscriptions!`;\n log\n ? log.warn({ \"rumble.table\": String(table) }, msg)\n : console.warn(msg);\n }\n const primaryKey = Object.values(tableSchema.primaryKey)[0];\n\n const { registerOnInstance } = makePubSubInstance({ table: table });\n\n return schemaBuilder.drizzleObject(table, {\n name: refName ?? capitalize(String(table)),\n subscribe: (subscriptions, element, _context) => {\n if (!primaryKey) return;\n const primaryKeyValue = (element as any)[primaryKey.name];\n if (!primaryKeyValue) {\n const log = loggerConfig?.enabled ? loggerConfig.logger : undefined;\n const msg = `Could not find primary key value for element on ${String(table)}. Cannot register subscription!`;\n log\n ? log.warn({ \"rumble.table\": String(table) }, msg)\n : console.warn(msg);\n return;\n }\n\n //TODO maybe register non specific update calls aswell?\n registerOnInstance({\n instance: subscriptions,\n action: \"updated\",\n primaryKeyValue: primaryKeyValue,\n });\n },\n applyFilters: abilityBuilder?._.registeredFilters({\n table,\n action: readAction,\n }),\n fields: (t) => {\n const columns = tableSchema.columns;\n\n // in case the user makes adjustments we want to store away which\n // pothos function was called with what config\n // this is mapped to the ref which later can be used to\n // reference these parameters while iterating over the fields\n // and checking against the userAdjustments object\n // this is necessary to e.g. merge nullability info from the database schema\n // or register subscriptions on relations\n const configMap = new Map<\n any,\n {\n creatorFunction: (...p: any[]) => any;\n params: any[];\n configObject: any;\n }\n >();\n // stores the results of the user adjustments\n // also stores all the used pothos functions and the configs\n // provided by the user so we can extend that if necessary\n const userAdjustments =\n adjust?.(\n new Proxy(t, {\n get: (target, prop, _receiver) => {\n if (\n // we only care for field/relation functions\n typeof (target as any)[prop] !== \"function\" ||\n prop === \"arg\" ||\n prop === \"builder\" ||\n prop === \"graphqlKind\" ||\n prop === \"kind\" ||\n prop === \"listRef\" ||\n prop === \"table\" ||\n prop === \"typename\" ||\n prop === \"variant\" ||\n prop.toString().startsWith(\"boolean\") ||\n prop.toString().startsWith(\"float\") ||\n prop.toString().startsWith(\"id\") ||\n prop.toString().startsWith(\"int\") ||\n prop.toString().startsWith(\"string\") ||\n prop.toString().startsWith(\"expose\")\n ) {\n return (target as any)[prop];\n }\n\n return (...params: any[]) => {\n const ref = (target as any)[prop](...params);\n const configObject = params.find(isProbablyAConfigObject);\n if (!configObject)\n throw new RumbleError(\n \"Expected config object to be passed to adjust field\",\n );\n\n configMap.set(ref, {\n params,\n creatorFunction: (target as any)[prop],\n configObject,\n });\n return ref;\n };\n },\n }) as any,\n ) ?? {};\n\n const fields = Object.entries(columns).reduce(\n (acc, [key, column]) => {\n // GraphQL reserves all names beginning with \"__\" for introspection.\n // Skip such columns silently — the user must expose them manually\n // via `adjust` if they truly need them.\n if (key.startsWith(\"__\")) {\n console.warn(\n `Skipping column \"${key}\" on table \"${tableSchema.tsName}\": names starting with \"__\" are reserved by GraphQL introspection. Use a custom adjust() call if you really need to expose this column.`,\n );\n return acc;\n }\n\n // in case the user wants to overwrite a field\n // we want to merge with our stuff in case the user\n // did not specify it themselves\n if (userAdjustments[key]) {\n const { params, creatorFunction, configObject } = configMap.get(\n userAdjustments[key],\n )!;\n\n if (typeof configObject.nullable !== \"boolean\") {\n configObject.nullable = !column.notNull;\n }\n\n userAdjustments[key] = creatorFunction.bind(t)(...params);\n return acc;\n }\n\n // Array columns only exist on Postgres; `dimensions` is a runtime\n // property of PgColumn instances. Gate via is() so MySQL/SQLite\n // columns aren't probed for a field they don't have.\n let isArray = false;\n if (is(column, PgColumn)) {\n const dimensions = (column as PgColumn & { dimensions?: number })\n .dimensions;\n if (dimensions && dimensions > 0) {\n if (dimensions !== 1) {\n throw new RumbleError(\n \"Only one-dimensional arrays are supported for default object implementation\",\n );\n }\n isArray = true;\n }\n }\n\n if (isEnumSchema(column)) {\n const enumImpl = enumImplementer({\n enumColumn: column,\n });\n\n acc[key] = t.field({\n type: isArray ? [enumImpl] : enumImpl,\n resolve: (element) => (element as any)[key],\n nullable: !column.notNull,\n });\n } else {\n acc[key] = buildPothosResponseTypeFromGraphQLType({\n builder: t,\n sqlType: column.getSQLType() as PossibleSQLType,\n fieldName: key,\n nullable: !column.notNull,\n isArray,\n });\n }\n return acc;\n },\n {} as Record<\n keyof typeof columns,\n | ReturnType<typeof buildPothosResponseTypeFromGraphQLType>\n | ReturnType<typeof t.field>\n >,\n );\n\n const relations = Object.entries(tableSchema.relations ?? {}).reduce(\n (acc, [key, value]) => {\n const targetTsName = (value as any).targetTableName as string;\n const relationSchema = tableHelper({\n db,\n table: targetTsName,\n });\n const WhereArg = whereArgImplementer({\n dbName: relationSchema.dbName,\n });\n const OrderArg = orderArgImplementer({\n dbName: relationSchema.dbName,\n });\n const relationTablePubSub = makePubSubInstance({\n table: relationSchema.tsName as any,\n });\n\n // many relations will return an empty array so we just don't set them nullable\n let nullable = false;\n let isMany = true;\n let filterSpecifier = \"many\";\n if (is(value, One)) {\n isMany = false;\n nullable =\n value.optional ||\n !value.sourceColumns.every((column) => column.notNull);\n filterSpecifier = \"single\";\n }\n\n const subscribe = (subscriptions: any, _element: any) => {\n relationTablePubSub.registerOnInstance({\n instance: subscriptions,\n action: \"created\",\n });\n relationTablePubSub.registerOnInstance({\n instance: subscriptions,\n action: \"removed\",\n });\n };\n\n // in case the user wants to overwrite a field\n // we want to merge with our stuff in case the user\n // did not specify it themselves\n if (userAdjustments[key]) {\n const { params, creatorFunction, configObject } = configMap.get(\n userAdjustments[key],\n )!;\n\n if (typeof configObject.nullable !== \"boolean\") {\n configObject.nullable = nullable;\n }\n\n if (typeof configObject.subscribe !== \"function\") {\n configObject.subscribe = subscribe;\n }\n\n userAdjustments[key] = creatorFunction.bind(t)(...params);\n return acc;\n }\n\n const args = {\n where: t.arg({ type: WhereArg, required: false }),\n orderBy: t.arg({ type: OrderArg, required: false }),\n ...(isMany\n ? {\n offset: t.arg.int({ required: false }),\n limit: t.arg.int({ required: false }),\n }\n : {}),\n search: t.arg.string({ required: false }),\n };\n\n if (!search?.enabled || !isMany) {\n delete (args as any).search;\n }\n\n (acc as any)[key] = t.relation(\n key as any,\n {\n args,\n subscribe,\n nullable,\n description: `Get the ${pluralize.plural(relationSchema.tsName)} related to this ${pluralize.singular(tableSchema.tsName)}`,\n query: (args: any, ctx: any) => {\n // transform null prototyped object\n args = JSON.parse(JSON.stringify(args));\n\n if (isMany) {\n adjustQueryArgsForSearch({\n search,\n args,\n tableSchema: relationSchema,\n abilities:\n ctx.abilities[relationSchema.tsName].filter(readAction),\n });\n }\n\n const filter = ctx.abilities[relationSchema.tsName]\n .filter(readAction)\n .merge({\n where: args.where,\n limit: args.limit,\n extras: args.extras,\n }).query[filterSpecifier];\n\n if (args.offset) {\n (filter as any).offset = args.offset;\n }\n\n if (args.orderBy) {\n (filter as any).orderBy = args.orderBy;\n }\n\n return filter;\n },\n } as any,\n ) as any;\n return acc;\n },\n {} as Record<\n keyof typeof tableSchema.relations,\n ReturnType<typeof buildPothosResponseTypeFromGraphQLType>\n >,\n );\n\n if (search?.enabled) {\n if (fields.search_distance) {\n throw new Error(\n \"Reserved field name 'search_distance' found on \" +\n tableSchema.tsName +\n \". If search is enabled, the 'search_distance' field is automatically added and cannot be defined manually.\",\n );\n }\n\n fields.search_distance = t.float({\n description:\n \"The search distance of the object. If a search is provided, this field will be populated with the search distance.\",\n nullable: true,\n resolve: (parent, _args, _ctx, _info) =>\n (parent as any).search_distance,\n });\n }\n\n return {\n ...fields,\n ...relations,\n ...userAdjustments,\n };\n },\n });\n };\n};\n","import { createPubSub } from \"graphql-yoga\";\nimport type {\n DrizzleInstance,\n DrizzleQueryFunction,\n} from \"./types/drizzleInstanceType\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\n\ntype PubSubAction = \"created\" | \"removed\" | \"updated\";\n\nconst SUBSCRIPTION_NOTIFIER_RUMBLE_PREFIX = \"RUMBLE_SUBSCRIPTION_NOTIFICATION\";\nconst SUBSCRIPTION_NOTIFIER_REMOVED = \"REMOVED\";\nconst SUBSCRIPTION_NOTIFIER_UPDATED = \"UPDATED\";\nconst SUBSCRIPTION_NOTIFIER_CREATED = \"CREATED\";\n\nexport type MakePubSubInstanceType<\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n> = ReturnType<\n typeof createPubSubInstance<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >\n>[\"makePubSubInstance\"];\n\nexport const createPubSubInstance = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>({\n subscriptions,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig>) => {\n const pubsub = subscriptions\n ? createPubSub(...subscriptions)\n : createPubSub();\n\n const makePubSubInstance = <\n TableName extends keyof DrizzleQueryFunction<DB>,\n >({\n table,\n }: {\n table: TableName;\n }) => {\n type PrimaryKeyType = any;\n\n function makePubSubKey({\n action,\n tableName,\n primaryKeyValue,\n }: {\n tableName: string;\n action: PubSubAction;\n primaryKeyValue?: PrimaryKeyType;\n }) {\n let actionKey: string;\n\n switch (action) {\n case \"created\":\n actionKey = SUBSCRIPTION_NOTIFIER_CREATED;\n break;\n case \"removed\":\n actionKey = SUBSCRIPTION_NOTIFIER_REMOVED;\n break;\n case \"updated\":\n actionKey = SUBSCRIPTION_NOTIFIER_UPDATED;\n break;\n default:\n throw new Error(`Unknown action: ${action}`);\n }\n\n return `${SUBSCRIPTION_NOTIFIER_RUMBLE_PREFIX}/${tableName}${\n primaryKeyValue ? `/${primaryKeyValue}` : \"\"\n }/${actionKey}`;\n }\n\n // TODO does caching these make sense?\n return {\n /**\n * Call this when you want to register a subscription on an instance to this table\n */\n registerOnInstance({\n instance,\n action,\n primaryKeyValue,\n }: {\n instance: { register: (id: string) => void };\n action: PubSubAction;\n primaryKeyValue?: string;\n }) {\n const key = makePubSubKey({\n tableName: table.toString(),\n action,\n primaryKeyValue,\n });\n instance.register(key);\n },\n /**\n * Call this when you created an entity of this table\n */\n created() {\n const key = makePubSubKey({\n tableName: table.toString(),\n action: \"created\",\n });\n return pubsub.publish(key);\n },\n /**\n * Call this when you removed one or more entities of this table\n */\n // removed(primaryKeyValue?: PrimaryKeyType | PrimaryKeyType[]) {\n removed() {\n const key = makePubSubKey({\n tableName: table.toString(),\n action: \"removed\",\n //TODO would it make sense to use specific sub topics here?\n // primaryKeyValue,\n });\n return pubsub.publish(key);\n },\n /**\n * Call this when you updated one or more entities of this table\n */\n updated(primaryKeyValue?: PrimaryKeyType | PrimaryKeyType[]) {\n const primaryKeys = Array.isArray(primaryKeyValue)\n ? primaryKeyValue\n : [primaryKeyValue];\n const keys = primaryKeys.map((primaryKeyValue) =>\n makePubSubKey({\n tableName: table.toString(),\n action: \"updated\",\n primaryKeyValue,\n }),\n );\n const uniqueKeys = Array.from(new Set(keys));\n for (const key of uniqueKeys) {\n pubsub.publish(key);\n }\n },\n };\n };\n\n return {\n pubsub,\n makePubSubInstance,\n };\n};\n","import { sql } from \"drizzle-orm\";\nimport pluralize from \"pluralize\";\nimport type { OrderArgImplementerType } from \"./args/orderArg\";\nimport type { WhereArgImplementerType } from \"./args/whereArg\";\nimport { assertFindFirstExists } from \"./helpers/asserts\";\nimport { isPostgresDB } from \"./helpers/determineDialectFromSchema\";\nimport { mapNullFieldsToUndefined } from \"./helpers/mapNullFieldsToUndefined\";\nimport { deepSetProto } from \"./helpers/protoMapper\";\nimport { tableHelper } from \"./helpers/tableHelpers\";\nimport type { MakePubSubInstanceType } from \"./pubsub\";\nimport { adjustQueryArgsForSearch } from \"./search\";\nimport type {\n DrizzleInstance,\n DrizzleQueryFunction,\n TableRelationNames,\n} from \"./types/drizzleInstanceType\";\nimport { RumbleError } from \"./types/rumbleError\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\nimport type { SchemaBuilderType } from \"./types/schemaBuilderType\";\n\nexport const createQueryImplementer = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n Schema extends Record<string, any>,\n>({\n db,\n schemaBuilder,\n search,\n logger: loggerConfig,\n whereArgImplementer,\n orderArgImplementer,\n makePubSubInstance,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig, Schema> & {\n schemaBuilder: SchemaBuilderType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n whereArgImplementer: WhereArgImplementerType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n orderArgImplementer: OrderArgImplementerType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n makePubSubInstance: MakePubSubInstanceType<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >;\n}) => {\n const registeredQueryFieldNames = new Set<string>();\n\n return <TableName extends TableRelationNames<DB>>({\n table,\n readAction = \"read\" as Action,\n listAction = \"read\" as Action,\n findFirst,\n findMany,\n }: {\n /**\n * The table for which to implement the query\n */\n table: TableName;\n /**\n * Which action should be used for reading single entities\n * @default \"read\"\n */\n readAction?: Action;\n /**\n * Which action should be used for listing many entities\n * @default \"read\"\n */\n listAction?: Action;\n\n findMany?: (p: {\n tx: DB | Parameters<Parameters<DB[\"transaction\"]>[0]>[0];\n filter: Parameters<DrizzleQueryFunction<DB>[TableName][\"findMany\"]>[0];\n queryArgs: Parameters<DrizzleQueryFunction<DB>[TableName][\"findMany\"]>[0];\n }) => ReturnType<DrizzleQueryFunction<DB>[TableName][\"findMany\"]>;\n\n findFirst?: (p: {\n tx: DB;\n filter: Parameters<DrizzleQueryFunction<DB>[TableName][\"findFirst\"]>[0];\n queryArgs: Parameters<\n DrizzleQueryFunction<DB>[TableName][\"findFirst\"]\n >[0];\n }) => ReturnType<DrizzleQueryFunction<DB>[TableName][\"findFirst\"]>;\n }) => {\n const WhereArg = whereArgImplementer({\n table: table,\n });\n const OrderArg = orderArgImplementer({\n table: table,\n });\n const tableSchema = tableHelper({\n db,\n table,\n });\n const primaryKeyField = Object.values(tableSchema.primaryKey)[0];\n\n const { registerOnInstance } = makePubSubInstance({ table: table });\n\n const pluralName = pluralize.plural(String(table));\n const singularName = pluralize.singular(String(table));\n for (const name of [pluralName, singularName]) {\n if (registeredQueryFieldNames.has(name)) {\n throw new RumbleError(\n `Duplicate query field \"${name}\": the table \"${String(table)}\" generates a ` +\n `query field that collides with one already registered. Use unique table names ` +\n `(or refNames) to avoid plural/singular collisions (e.g. \"post\" and \"posts\").`,\n );\n }\n registeredQueryFieldNames.add(name);\n }\n\n return schemaBuilder.queryFields((t) => {\n const manyArgs = {\n where: t.arg({ type: WhereArg, required: false }),\n orderBy: t.arg({ type: OrderArg, required: false }),\n limit: t.arg.int({ required: false }),\n offset: t.arg.int({ required: false }),\n search: t.arg.string({ required: false }),\n };\n\n if (!search?.enabled) {\n delete (manyArgs as any).search;\n }\n\n return {\n [pluralName]: t.drizzleField({\n type: [table],\n nullable: false,\n smartSubscription: true,\n description: `List all ${pluralName}`,\n subscribe: (subscriptions, _root, _args, _ctx, _info) => {\n registerOnInstance({\n instance: subscriptions,\n action: \"created\",\n });\n registerOnInstance({\n instance: subscriptions,\n action: \"removed\",\n });\n },\n args: manyArgs,\n resolve: (query, _root, args, ctx, _info) => {\n // args does not have Object.prototype as prototype, so we need to set it\n // otherwise some libraries (like drizzle-orm) might have issues with it\n deepSetProto(args);\n\n adjustQueryArgsForSearch({\n search,\n args,\n tableSchema,\n abilities: ctx.abilities[table].filter(listAction),\n });\n\n const mappedArgs = mapNullFieldsToUndefined(args);\n const filter = ctx.abilities[table]\n .filter(listAction)\n .merge(mappedArgs as any).query.many;\n\n if (mappedArgs.offset) {\n (filter as any).offset = mappedArgs.offset;\n }\n\n if (mappedArgs.orderBy) {\n (filter as any).orderBy = mappedArgs.orderBy;\n }\n\n const queryArgs = query(filter as any);\n\n if ((filter as any).columns) {\n queryArgs.columns = (filter as any).columns;\n }\n\n const run = findMany\n ? (tx: DB) => findMany({ tx, filter: filter as any, queryArgs })\n : (tx: any) => (tx.query as any)[table].findMany(queryArgs);\n\n if (\n search?.enabled &&\n args.search &&\n args.search.length > 0 &&\n search?.cpu_operator_cost\n ) {\n return db.transaction(async (tx: any) => {\n if (isPostgresDB(tx)) {\n await tx.execute(\n sql.raw(\n `SET cpu_operator_cost = ${search.cpu_operator_cost};`,\n ),\n );\n } else {\n const msg =\n \"Database dialect is not postgresql, cannot set cpu_operator_cost.\";\n const log = loggerConfig?.enabled\n ? loggerConfig.logger\n : undefined;\n log ? log.info({}, msg) : console.info(msg);\n }\n\n return run(tx);\n });\n }\n\n return run(db);\n },\n }),\n [singularName]: t.drizzleField({\n type: table,\n nullable: false,\n smartSubscription: true,\n description: `Get a single ${singularName} by ID`,\n args: {\n id: t.arg.id({ required: true }),\n },\n resolve: (query, _root, args, ctx, _info) => {\n deepSetProto(args);\n\n const filter = (ctx.abilities as any)[table]\n .filter(readAction)\n .merge({ where: { [primaryKeyField.name]: args.id } })\n .query.single;\n const queryArgs = query(filter);\n\n if (filter.columns) {\n queryArgs.columns = filter.columns;\n }\n\n return findFirst\n ? findFirst({ tx: db, filter: filter as any, queryArgs })\n : (db.query as any)[table]\n .findFirst(queryArgs)\n .then(assertFindFirstExists);\n },\n }),\n };\n });\n };\n};\n","export type NumberWhereInputArgument = {\n eq?: number;\n ne?: number;\n gt?: number;\n gte?: number;\n lt?: number;\n lte?: number;\n in?: number[];\n notIn?: number[];\n like?: string;\n ilike?: string;\n notLike?: string;\n notIlike?: string;\n isNull?: boolean;\n isNotNull?: boolean;\n arrayOverlaps?: number[];\n arrayContained?: number[];\n arrayContains?: number[];\n AND?: NumberWhereInputArgument[];\n OR?: NumberWhereInputArgument[];\n NOT?: NumberWhereInputArgument;\n};\n\nexport type StringWhereInputArgument = {\n eq?: string;\n ne?: string;\n gt?: string;\n gte?: string;\n lt?: string;\n lte?: string;\n in?: string[];\n notIn?: string[];\n like?: string;\n ilike?: string;\n notLike?: string;\n notIlike?: string;\n isNull?: boolean;\n isNotNull?: boolean;\n arrayOverlaps?: string[];\n arrayContained?: string[];\n arrayContains?: string[];\n AND?: StringWhereInputArgument[];\n OR?: StringWhereInputArgument[];\n NOT?: StringWhereInputArgument;\n};\n\nexport type DateWhereInputArgument = {\n eq?: Date;\n ne?: Date;\n gt?: Date;\n gte?: Date;\n lt?: Date;\n lte?: Date;\n in?: Date[];\n notIn?: Date[];\n like?: string;\n ilike?: string;\n notLike?: string;\n notIlike?: string;\n isNull?: boolean;\n isNotNull?: boolean;\n arrayOverlaps?: Date[];\n arrayContained?: Date[];\n arrayContains?: Date[];\n AND?: DateWhereInputArgument[];\n OR?: DateWhereInputArgument[];\n NOT?: DateWhereInputArgument;\n};\n\nexport type BooleanWhereInputArgument = {\n eq?: boolean;\n ne?: boolean;\n in?: boolean[];\n notIn?: boolean[];\n isNull?: boolean;\n isNotNull?: boolean;\n arrayOverlaps?: boolean[];\n arrayContained?: boolean[];\n arrayContains?: boolean[];\n AND?: BooleanWhereInputArgument[];\n OR?: BooleanWhereInputArgument[];\n NOT?: BooleanWhereInputArgument;\n};\n\nexport type IDWhereInputArgument = {\n eq?: string;\n ne?: string;\n gt?: string;\n gte?: string;\n lt?: string;\n lte?: string;\n in?: string[];\n notIn?: string[];\n like?: string;\n ilike?: string;\n notLike?: string;\n notIlike?: string;\n isNull?: boolean;\n isNotNull?: boolean;\n arrayOverlaps?: string[];\n arrayContained?: string[];\n arrayContains?: string[];\n AND?: IDWhereInputArgument[];\n OR?: IDWhereInputArgument[];\n NOT?: IDWhereInputArgument;\n};\n\nexport type JSONWhereInputArgument = {\n eq?: unknown;\n ne?: unknown;\n in?: unknown[];\n notIn?: unknown[];\n isNull?: boolean;\n isNotNull?: boolean;\n arrayOverlaps?: unknown[];\n arrayContained?: unknown[];\n arrayContains?: unknown[];\n AND?: JSONWhereInputArgument[];\n OR?: JSONWhereInputArgument[];\n NOT?: JSONWhereInputArgument;\n};\n\nexport type BigIntWhereInputArgument = {\n eq?: bigint | number;\n ne?: bigint | number;\n gt?: bigint | number;\n gte?: bigint | number;\n lt?: bigint | number;\n lte?: bigint | number;\n in?: (bigint | number)[];\n notIn?: (bigint | number)[];\n isNull?: boolean;\n isNotNull?: boolean;\n AND?: BigIntWhereInputArgument[];\n OR?: BigIntWhereInputArgument[];\n NOT?: BigIntWhereInputArgument;\n};\n\nexport type DateTimeWhereInputArgument = {\n eq?: Date;\n ne?: Date;\n gt?: Date;\n gte?: Date;\n lt?: Date;\n lte?: Date;\n in?: Date[];\n notIn?: Date[];\n isNull?: boolean;\n isNotNull?: boolean;\n arrayOverlaps?: Date[];\n arrayContained?: Date[];\n arrayContains?: Date[];\n AND?: DateTimeWhereInputArgument[];\n OR?: DateTimeWhereInputArgument[];\n NOT?: DateTimeWhereInputArgument;\n};\n\n// TODO: Add proper type for schemaBuilder\n\nexport function implementDefaultWhereInputArgs(schemaBuilder: any) {\n const IntWhereInputArgument = schemaBuilder\n .inputRef(\"IntWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.int(),\n ne: t.int(),\n gt: t.int(),\n gte: t.int(),\n lt: t.int(),\n lte: t.int(),\n in: t.intList(),\n notIn: t.intList(),\n like: t.string(),\n ilike: t.string(),\n notLike: t.string(),\n notIlike: t.string(),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.intList(),\n arrayContained: t.intList(),\n arrayContains: t.intList(),\n AND: t.field({\n type: [IntWhereInputArgument],\n }),\n OR: t.field({\n type: [IntWhereInputArgument],\n }),\n NOT: t.field({\n type: IntWhereInputArgument,\n }),\n }),\n });\n\n const FloatWhereInputArgument = schemaBuilder\n .inputRef(\"FloatWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.float(),\n ne: t.float(),\n gt: t.float(),\n gte: t.float(),\n lt: t.float(),\n lte: t.float(),\n in: t.floatList(),\n notIn: t.floatList(),\n like: t.string(),\n ilike: t.string(),\n notLike: t.string(),\n notIlike: t.string(),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.floatList(),\n arrayContained: t.floatList(),\n arrayContains: t.floatList(),\n AND: t.field({\n type: [FloatWhereInputArgument],\n }),\n OR: t.field({\n type: [FloatWhereInputArgument],\n }),\n NOT: t.field({\n type: FloatWhereInputArgument,\n }),\n }),\n });\n\n const StringWhereInputArgument = schemaBuilder\n .inputRef(\"StringWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.string(),\n ne: t.string(),\n gt: t.string(),\n gte: t.string(),\n lt: t.string(),\n lte: t.string(),\n in: t.stringList(),\n notIn: t.stringList(),\n like: t.string(),\n ilike: t.string(),\n notLike: t.string(),\n notIlike: t.string(),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.stringList(),\n arrayContained: t.stringList(),\n arrayContains: t.stringList(),\n AND: t.field({\n type: [StringWhereInputArgument],\n }),\n OR: t.field({\n type: [StringWhereInputArgument],\n }),\n NOT: t.field({\n type: StringWhereInputArgument,\n }),\n }),\n });\n\n const DateWhereInputArgument = schemaBuilder\n .inputRef(\"DateWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.field({ type: \"Date\" }),\n ne: t.field({ type: \"Date\" }),\n gt: t.field({ type: \"Date\" }),\n gte: t.field({ type: \"Date\" }),\n lt: t.field({ type: \"Date\" }),\n lte: t.field({ type: \"Date\" }),\n in: t.field({ type: [\"Date\"] }),\n notIn: t.field({ type: [\"Date\"] }),\n like: t.string(),\n ilike: t.string(),\n notLike: t.string(),\n notIlike: t.string(),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.field({ type: [\"Date\"] }),\n arrayContained: t.field({ type: [\"Date\"] }),\n arrayContains: t.field({ type: [\"Date\"] }),\n AND: t.field({\n type: [DateWhereInputArgument],\n }),\n OR: t.field({\n type: [DateWhereInputArgument],\n }),\n NOT: t.field({\n type: DateWhereInputArgument,\n }),\n }),\n });\n\n const BooleanWhereInputArgument = schemaBuilder\n .inputRef(\"BooleanWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.boolean(),\n ne: t.boolean(),\n in: t.booleanList(),\n notIn: t.booleanList(),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.booleanList(),\n arrayContained: t.booleanList(),\n arrayContains: t.booleanList(),\n AND: t.field({\n type: [BooleanWhereInputArgument],\n }),\n OR: t.field({\n type: [BooleanWhereInputArgument],\n }),\n NOT: t.field({\n type: BooleanWhereInputArgument,\n }),\n }),\n });\n\n const IDWhereInputArgument = schemaBuilder\n .inputRef(\"IDWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.id(),\n ne: t.id(),\n gt: t.id(),\n gte: t.id(),\n lt: t.id(),\n lte: t.id(),\n in: t.idList(),\n notIn: t.idList(),\n like: t.string(),\n ilike: t.string(),\n notLike: t.string(),\n notIlike: t.string(),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.idList(),\n arrayContained: t.idList(),\n arrayContains: t.idList(),\n AND: t.field({\n type: [IDWhereInputArgument],\n }),\n OR: t.field({\n type: [IDWhereInputArgument],\n }),\n NOT: t.field({\n type: IDWhereInputArgument,\n }),\n }),\n });\n\n const JSONWhereInputArgument = schemaBuilder\n .inputRef(\"JSONWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.field({ type: \"JSON\", required: false }),\n ne: t.field({ type: \"JSON\", required: false }),\n in: t.field({ type: [\"JSON\"], required: false }),\n notIn: t.field({ type: [\"JSON\"], required: false }),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.field({ type: [\"JSON\"], required: false }),\n arrayContained: t.field({ type: [\"JSON\"], required: false }),\n arrayContains: t.field({ type: [\"JSON\"], required: false }),\n AND: t.field({\n type: [JSONWhereInputArgument],\n }),\n OR: t.field({\n type: [JSONWhereInputArgument],\n }),\n NOT: t.field({\n type: JSONWhereInputArgument,\n }),\n }),\n });\n\n const BigIntWhereInputArgument = schemaBuilder\n .inputRef(\"BigIntWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.field({ type: \"BigInt\", required: false }),\n ne: t.field({ type: \"BigInt\", required: false }),\n gt: t.field({ type: \"BigInt\", required: false }),\n gte: t.field({ type: \"BigInt\", required: false }),\n lt: t.field({ type: \"BigInt\", required: false }),\n lte: t.field({ type: \"BigInt\", required: false }),\n in: t.field({ type: [\"BigInt\"], required: false }),\n notIn: t.field({ type: [\"BigInt\"], required: false }),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n AND: t.field({ type: [BigIntWhereInputArgument] }),\n OR: t.field({ type: [BigIntWhereInputArgument] }),\n NOT: t.field({ type: BigIntWhereInputArgument }),\n }),\n });\n\n const DateTimeWhereInputArgument = schemaBuilder\n .inputRef(\"DateTimeWhereInputArgument\")\n .implement({\n fields: (t: any) => ({\n eq: t.field({ type: \"DateTime\", required: false }),\n ne: t.field({ type: \"DateTime\", required: false }),\n gt: t.field({ type: \"DateTime\", required: false }),\n gte: t.field({ type: \"DateTime\", required: false }),\n lt: t.field({ type: \"DateTime\", required: false }),\n lte: t.field({ type: \"DateTime\", required: false }),\n in: t.field({ type: [\"DateTime\"], required: false }),\n notIn: t.field({ type: [\"DateTime\"], required: false }),\n isNull: t.boolean(),\n isNotNull: t.boolean(),\n arrayOverlaps: t.field({ type: [\"DateTime\"], required: false }),\n arrayContained: t.field({ type: [\"DateTime\"], required: false }),\n arrayContains: t.field({ type: [\"DateTime\"], required: false }),\n AND: t.field({ type: [DateTimeWhereInputArgument] }),\n OR: t.field({ type: [DateTimeWhereInputArgument] }),\n NOT: t.field({ type: DateTimeWhereInputArgument }),\n }),\n });\n}\n","export type Prefetch<Context, ReturnType> = (params: {\n context: Context;\n}) => Promise<ReturnType>;\n\nexport type Filter<\n Context,\n FilteredEntityType,\n PrefetchReturnType = never,\n> = (p: {\n context: Context;\n entities: FilteredEntityType[];\n prefetched: PrefetchReturnType;\n}) => FilteredEntityType[] | Promise<FilteredEntityType[]>;\n\nexport type FilterPrefetchCombo<\n Context,\n FilteredEntityType,\n PrefetchReturnType = never,\n> = {\n filter: Filter<Context, FilteredEntityType, PrefetchReturnType>;\n prefetch?: Prefetch<Context, PrefetchReturnType>;\n};\n\nexport type ApplyFiltersField<Context, T> =\n | FilterPrefetchCombo<Context, T>\n | FilterPrefetchCombo<Context, T>[]\n | undefined;\n\nexport const pluginName = \"RuntimeFiltersPlugin\" as const;\n","import type { Span, Tracer } from \"@opentelemetry/api\";\nimport SchemaBuilder, {\n BasePlugin,\n type PothosOutputFieldConfig,\n type PothosTypeConfig,\n type SchemaTypes,\n} from \"@pothos/core\";\nimport DataLoader from \"dataloader\";\nimport type { GraphQLFieldResolver } from \"graphql\";\nimport { errorLogField } from \"../helpers/errorLogging\";\nimport type { RumbleLogger } from \"../types/rumbleInput\";\nimport {\n type ApplyFiltersField,\n type FilterPrefetchCombo,\n pluginName,\n} from \"./filterTypes\";\n\nexport const applyFiltersKey = \"applyFilters\";\n\ntype AnyFilterCombo = FilterPrefetchCombo<any, any, any>;\n\nexport class RuntimeFiltersPlugin<\n Types extends SchemaTypes,\n> extends BasePlugin<Types> {\n private tracer?: Tracer;\n private tracerEnabled?: boolean;\n private logger?: RumbleLogger;\n\n // graphql-js resolves a relation field once per sibling in a list, concurrently,\n // so without this a filter like \"can read user\" would fire once per row instead\n // of once for the whole list. Keying loaders by context means they get garbage\n // collected once the request is done, no manual cleanup needed.\n private filterLoaders = new WeakMap<\n object,\n Map<AnyFilterCombo, DataLoader<any, any>>\n >();\n\n private getLoader(\n context: Types[\"Context\"],\n filter: AnyFilterCombo,\n ): DataLoader<any, any> {\n let perContext = this.filterLoaders.get(context as object);\n if (!perContext) {\n perContext = new Map();\n this.filterLoaders.set(context as object, perContext);\n }\n\n let loader = perContext.get(filter);\n if (!loader) {\n // not awaited here on purpose, so it runs alongside the resolver instead of after it\n const prefetchPromise = filter.prefetch\n ? filter.prefetch({ context })\n : undefined;\n\n loader = new DataLoader<any, any>(\n async (entities) => {\n const prefetched = prefetchPromise\n ? await prefetchPromise\n : undefined;\n const allowed = await filter.filter({\n context,\n entities: entities as any[],\n prefetched,\n } as any);\n const allowedSet = new Set(allowed);\n return entities.map((entity) =>\n allowedSet.has(entity) ? entity : null,\n );\n },\n // cache off on purpose, we only want the batching, filters should still\n // run fresh every time like before\n { cache: false },\n );\n perContext.set(filter, loader);\n }\n\n return loader;\n }\n\n override onTypeConfig(typeConfig: PothosTypeConfig) {\n this.tracer = this.builder.options.otel?.tracer;\n this.tracerEnabled = this.builder.options.otel?.enabled;\n this.logger = this.builder.options.logger?.enabled\n ? this.builder.options.logger.logger\n : undefined;\n return typeConfig;\n }\n\n override wrapResolve(\n resolver: GraphQLFieldResolver<unknown, Types[\"Context\"], object>,\n fieldConfig: PothosOutputFieldConfig<Types>,\n ): GraphQLFieldResolver<unknown, Types[\"Context\"], object> {\n return async (parent, args, context, info) => {\n let filters: ApplyFiltersField<Types[\"Context\"], any> | undefined;\n const fieldType = fieldConfig?.type as any;\n\n if (fieldType.kind === \"List\") {\n filters =\n fieldType.type?.ref.currentConfig.pothosOptions[applyFiltersKey];\n } else if (fieldType.kind === \"Object\") {\n filters = fieldType.ref.currentConfig.pothosOptions[applyFiltersKey];\n }\n\n if (!filters || !Array.isArray(filters) || filters.length === 0) {\n // if no filter should be applied, just continue\n return resolver(parent, args, context, info);\n }\n\n const runFilters = async (span?: Span) => {\n const allFilters = Array.isArray(filters) ? filters : [filters];\n span?.setAttribute(\"filters.total\", allFilters.length);\n\n const loaders = allFilters.map((filter) =>\n this.getLoader(context, filter as AnyFilterCombo),\n );\n\n let resolved: any;\n\n if (this.tracer && this.tracerEnabled) {\n resolved = await this.tracer.startActiveSpan(\n `rumble.filter.resolve`,\n async (span) => {\n span.setAttribute(\"graphql.field.name\", fieldConfig.name);\n try {\n return await resolver(parent, args, context, info);\n } finally {\n span.end();\n }\n },\n );\n } else {\n resolved = await resolver(parent, args, context, info);\n }\n\n const entities: any[] = Array.isArray(resolved) ? resolved : [resolved];\n\n // load() instead of loadMany() so a thrown filter still rejects here\n // instead of getting swallowed into an Error value\n const perFilterResults = await Promise.all(\n loaders.map((loader) =>\n Promise.all(entities.map((entity) => loader.load(entity))),\n ),\n );\n\n const allowed = entities.filter((_, index) =>\n perFilterResults.some((results) => results[index] != null),\n );\n\n span?.setAttribute(\"filters.allowed\", allowed.length);\n this.logger?.debug(\n {\n \"graphql.field.name\": fieldConfig.name,\n \"filters.total\": allFilters.length,\n \"filters.allowed\": allowed.length,\n },\n \"runtime filters applied\",\n );\n\n // if the original value was an array, return an array\n if (Array.isArray(resolved)) {\n return allowed;\n }\n\n // if the original value was a single value, return the first allowed\n // or null if not allowed\n return allowed[0] ?? null;\n };\n\n if (this.tracer && this.tracerEnabled) {\n return this.tracer.startActiveSpan(\n `rumble.filter.apply`,\n async (span) => {\n span.setAttribute(\"graphql.field.name\", fieldConfig.name);\n try {\n return await runFilters(span);\n } catch (error) {\n this.logger?.error(\n {\n \"graphql.field.name\": fieldConfig.name,\n ...errorLogField(error),\n },\n \"runtime filter threw\",\n );\n throw error;\n } finally {\n span.end();\n }\n },\n );\n } else {\n try {\n return await runFilters();\n } catch (error) {\n this.logger?.error(\n {\n \"graphql.field.name\": fieldConfig.name,\n ...errorLogField(error),\n },\n \"runtime filter threw\",\n );\n throw error;\n }\n }\n };\n }\n}\n\nlet registered = false;\nexport function registerRuntimeFiltersPlugin() {\n if (!registered) {\n SchemaBuilder.registerPlugin(pluginName, RuntimeFiltersPlugin);\n registered = true;\n }\n}\n","import SchemaBuilder from \"@pothos/core\";\nimport DrizzlePlugin from \"@pothos/plugin-drizzle\";\nimport SmartSubscriptionsPlugin, {\n subscribeOptionsFromIterator,\n} from \"@pothos/plugin-smart-subscriptions\";\nimport TracingPlugin, {\n isRootField,\n wrapResolver,\n} from \"@pothos/plugin-tracing\";\nimport { createOpenTelemetryWrapper } from \"@pothos/tracing-opentelemetry\";\nimport { getTableColumns, isTable, type Table } from \"drizzle-orm\";\nimport {\n BigIntResolver,\n ByteResolver,\n DateResolver,\n DateTimeISOResolver,\n JSONResolver,\n} from \"graphql-scalars\";\nimport type { createPubSub } from \"graphql-yoga\";\nimport {\n type BigIntWhereInputArgument,\n type BooleanWhereInputArgument,\n type DateTimeWhereInputArgument,\n type DateWhereInputArgument,\n type IDWhereInputArgument,\n implementDefaultWhereInputArgs,\n type JSONWhereInputArgument,\n type NumberWhereInputArgument,\n type StringWhereInputArgument,\n} from \"./args/whereArgsImplementer\";\nimport type { ContextType } from \"./context\";\nimport { errorLogField } from \"./helpers/errorLogging\";\nimport { pluginName } from \"./runtimeFiltersPlugin/filterTypes\";\nimport { registerRuntimeFiltersPlugin } from \"./runtimeFiltersPlugin/runtimeFiltersPlugin\";\nimport type { DrizzleInstance } from \"./types/drizzleInstanceType\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\n\nexport const createSchemaBuilder = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n Action extends string,\n PothosConfig extends CustomRumblePothosConfig,\n>({\n db,\n pubsub,\n pothosConfig,\n otel,\n logger,\n}: RumbleInput<UserContext, DB, RequestEvent, Action, PothosConfig> & {\n pubsub: ReturnType<typeof createPubSub>;\n}) => {\n const createSpan =\n otel?.enabled && otel.tracer\n ? createOpenTelemetryWrapper(otel.tracer, otel.options)\n : undefined;\n\n registerRuntimeFiltersPlugin();\n const schemaBuilder = new SchemaBuilder<{\n Context: ContextType<UserContext, DB, RequestEvent, Action, PothosConfig>;\n DrizzleRelations: DB[\"_\"][\"relations\"];\n Scalars: {\n JSON: {\n Input: unknown;\n Output: unknown;\n };\n Date: {\n Input: Date;\n Output: Date;\n };\n DateTime: {\n Input: Date;\n Output: Date | string;\n };\n BigInt: {\n Input: bigint | number;\n Output: bigint | number | string;\n };\n Bytes: {\n Input: string;\n Output: string;\n };\n };\n Inputs: {\n IntWhereInputArgument: NumberWhereInputArgument;\n FloatWhereInputArgument: NumberWhereInputArgument;\n StringWhereInputArgument: StringWhereInputArgument;\n DateWhereInputArgument: DateWhereInputArgument;\n DateTimeWhereInputArgument: DateTimeWhereInputArgument;\n BigIntWhereInputArgument: BigIntWhereInputArgument;\n BooleanWhereInputArgument: BooleanWhereInputArgument;\n IDWhereInputArgument: IDWhereInputArgument;\n JSONWhereInputArgument: JSONWhereInputArgument;\n };\n DefaultFieldNullability: false;\n }>({\n ...pothosConfig,\n plugins: [\n pluginName,\n DrizzlePlugin,\n SmartSubscriptionsPlugin,\n TracingPlugin,\n ...(pothosConfig?.plugins ?? []),\n ],\n drizzle: {\n client: db,\n relations: db._.relations,\n getTableConfig(table) {\n //TODO support composite primary keys\n const columns = isTable(table)\n ? Object.values(getTableColumns(table as Table))\n : [];\n return {\n columns,\n primaryKeys: columns.filter((v: any) => v.primary),\n } as any;\n },\n },\n smartSubscriptions: {\n ...subscribeOptionsFromIterator((name, _context) => {\n return pubsub.subscribe(name);\n }),\n },\n defaultFieldNullability: false,\n tracing: {\n default:\n otel?.enabled || logger?.enabled\n ? (config) => isRootField(config)\n : () => false,\n wrap: (resolver, options, config) => {\n let r = createSpan ? createSpan(resolver, options) : resolver;\n if (logger?.enabled) {\n const log = logger.logger;\n r = wrapResolver(r, (error, duration) => {\n if (error) {\n log.error(\n {\n \"graphql.field.name\": config.name,\n \"graphql.parent.type\": config.parentType,\n duration_ms: duration,\n ...errorLogField(error),\n },\n \"resolver failed\",\n );\n } else {\n log.debug(\n {\n \"graphql.field.name\": config.name,\n \"graphql.parent.type\": config.parentType,\n duration_ms: duration,\n },\n \"resolver completed\",\n );\n }\n });\n }\n return r;\n },\n },\n otel,\n logger,\n });\n\n schemaBuilder.addScalarType(\"JSON\", JSONResolver);\n schemaBuilder.addScalarType(\"Date\", DateResolver);\n schemaBuilder.addScalarType(\"DateTime\", DateTimeISOResolver);\n schemaBuilder.addScalarType(\"BigInt\", BigIntResolver);\n schemaBuilder.addScalarType(\"Bytes\", ByteResolver);\n implementDefaultWhereInputArgs(schemaBuilder);\n\n schemaBuilder.queryType({});\n schemaBuilder.subscriptionType({});\n schemaBuilder.mutationType({});\n\n return { schemaBuilder };\n};\n","import { EnvelopArmorPlugin } from \"@escape.tech/graphql-armor\";\nimport { useDisableIntrospection } from \"@graphql-yoga/plugin-disable-introspection\";\nimport { SpanStatusCode, trace } from \"@opentelemetry/api\";\nimport { merge } from \"es-toolkit\";\nimport { GraphQLSchema } from \"graphql\";\nimport type { ServerOptions } from \"graphql-ws\";\nimport {\n createYoga as nativeCreateYoga,\n type Plugin,\n type YogaServerOptions,\n} from \"graphql-yoga\";\nimport type { useSofa } from \"sofa-api\";\nimport packagejson from \"../package.json\";\nimport { createAbilityBuilder } from \"./abilityBuilder\";\nimport { createOrderArgImplementer } from \"./args/orderArg\";\nimport { createWhereArgImplementer } from \"./args/whereArg\";\nimport { clientCreatorImplementer } from \"./client/client\";\nimport { createContextFunction } from \"./context\";\nimport { createCountQueryImplementer } from \"./countQuery\";\nimport { createEnumImplementer, type EnumFieldKeys } from \"./enum\";\nimport { lazy } from \"./helpers/lazy\";\nimport { sofaOpenAPIWebhookDocs } from \"./helpers/sofaOpenAPIWebhookDocs\";\nimport {\n buildTracedExecute,\n buildTracedSubscribe,\n defaultExecute,\n defaultSubscribe,\n} from \"./helpers/tracing\";\nimport { createObjectImplementer } from \"./object\";\nimport { createPubSubInstance } from \"./pubsub\";\nimport { createQueryImplementer } from \"./query\";\nimport { createSchemaBuilder } from \"./schemaBuilder\";\nimport { initSearchIfApplicable } from \"./search\";\nimport type { DrizzleInstance } from \"./types/drizzleInstanceType\";\nimport { RumbleError } from \"./types/rumbleError\";\nimport type {\n CustomRumblePothosConfig,\n RumbleInput,\n} from \"./types/rumbleInput\";\n\nexport const rumble = <\n UserContext extends Record<string, any>,\n DB extends DrizzleInstance,\n RequestEvent extends Record<string, any>,\n PothosConfig extends CustomRumblePothosConfig,\n Schema extends Record<string, any>,\n Action extends string = \"read\" | \"update\" | \"delete\",\n>(\n rumbleInput: RumbleInput<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n > & {\n schema: Schema;\n },\n) => {\n if (!rumbleInput.db._.relations) {\n throw new RumbleError(`\nrumble could not find any relations in the provided drizzle instance.\nMake sure you import the relations and pass them to the drizzle instance:\n\nexport const db = drizzle(\n \"postgres://postgres:postgres@localhost:5432/postgres\",\n {\n relations, // <--- add this line\n },\n);\n\n`);\n }\n\n if (\n !rumbleInput.schema ||\n typeof rumbleInput.schema !== \"object\" ||\n Object.keys(rumbleInput.schema).length === 0\n ) {\n throw new RumbleError(`\nrumble requires the drizzle schema object to be passed when initializing.\nImport your schema module and pass it alongside \\`db\\`:\n\nimport * as schema from \"./db/schema\";\n\nexport const r = rumble({\n db,\n schema, // <--- add this line\n});\n\n`);\n }\n\n // to be able to iterate over the actions, we populate the actions array in case the user does not\n if (!rumbleInput.actions) {\n rumbleInput.actions = [\"read\", \"update\", \"delete\"] as Action[];\n }\n\n if (rumbleInput.defaultLimit === undefined) {\n rumbleInput.defaultLimit = 100;\n }\n\n if (rumbleInput.search?.enabled) {\n initSearchIfApplicable(rumbleInput);\n }\n\n if (rumbleInput.otel?.enabled && !rumbleInput.otel.tracer) {\n rumbleInput.otel.tracer = trace.getTracer(\n \"@m1212e/rumble\",\n packagejson.version,\n );\n }\n\n const abilityBuilder = createAbilityBuilder<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >(rumbleInput);\n\n const context = createContextFunction<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >({\n ...rumbleInput,\n abilityBuilder,\n });\n\n const { makePubSubInstance, pubsub } = createPubSubInstance<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >({\n ...rumbleInput,\n });\n\n const { schemaBuilder } = createSchemaBuilder<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >({ ...rumbleInput, pubsub });\n\n const enum_ = createEnumImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n EnumFieldKeys<Schema>,\n Schema\n >({\n ...rumbleInput,\n schemaBuilder,\n });\n\n const whereArg = createWhereArgImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >({\n ...rumbleInput,\n schemaBuilder,\n enumImplementer: enum_,\n });\n\n const orderArg = createOrderArgImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >({\n ...rumbleInput,\n schemaBuilder,\n });\n\n const object = createObjectImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n Schema\n >({\n ...rumbleInput,\n schemaBuilder,\n makePubSubInstance,\n whereArgImplementer: whereArg,\n orderArgImplementer: orderArg,\n enumImplementer: enum_,\n abilityBuilder,\n });\n\n const query = createQueryImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig,\n Schema\n >({\n ...rumbleInput,\n schemaBuilder,\n whereArgImplementer: whereArg,\n orderArgImplementer: orderArg,\n makePubSubInstance,\n });\n\n const countQuery = createCountQueryImplementer({\n ...rumbleInput,\n schemaBuilder,\n whereArgImplementer: whereArg,\n makePubSubInstance,\n });\n\n const builtSchema = lazy(() => {\n let raw: ReturnType<typeof schemaBuilder.toSchema>;\n try {\n raw = schemaBuilder.toSchema();\n } catch (e: any) {\n const msg: string = e?.message ?? String(e);\n const unimplMatch = msg.match(\n /ObjectRef<(.+?)> has not been implemented/,\n );\n if (unimplMatch) {\n throw new RumbleError(\n `Could not build GraphQL schema: the table \"${unimplMatch[1]}\" is referenced ` +\n `in a relation but has not been registered. Call rumble.object({ table: \"${unimplMatch[1]}\" }) ` +\n `before building the schema.`,\n );\n }\n throw e;\n }\n\n const mutation = raw.getMutationType();\n const subscription = raw.getSubscriptionType();\n const emptyMutation =\n mutation && Object.keys(mutation.getFields()).length === 0;\n const emptySubscription =\n subscription && Object.keys(subscription.getFields()).length === 0;\n\n if (!emptyMutation && !emptySubscription) return raw;\n\n const config = raw.toConfig();\n const filteredTypes = config.types.filter((t) => {\n if (emptyMutation && t === mutation) return false;\n if (emptySubscription && t === subscription) return false;\n return true;\n });\n return new GraphQLSchema({\n ...config,\n mutation: emptyMutation ? undefined : config.mutation,\n subscription: emptySubscription ? undefined : config.subscription,\n types: filteredTypes,\n });\n });\n\n const createYoga = (\n args?:\n | (Omit<YogaServerOptions<RequestEvent, any>, \"schema\" | \"context\"> & {\n /**\n * Determines if the API should disclose various things about its structure.\n * Defaults to `process.env.NODE_ENV === \"development\"`.\n * If enabled, the api will allow introspection requests, provide the graphiql\n * explorer and will not apply the additional envelop armor plugin.\n */\n enableApiDocs?: boolean;\n /**\n * Optional configuration passed to the auto-installed graphql-armor\n * EnvelopArmorPlugin. Only applied when `enableApiDocs` is false\n * (i.e. in production). Useful for relaxing the default depth/alias/\n * directive/token limits when the generated schema legitimately exceeds\n * them. See https://github.com/Escape-Technologies/graphql-armor for available options.\n *\n * @example\n * createYoga({ armorConfig: { maxDepth: { n: 20 } } })\n */\n armorConfig?: Parameters<typeof EnvelopArmorPlugin>[0];\n })\n | undefined,\n ) => {\n const enableApiDocs =\n args?.enableApiDocs ?? process?.env?.NODE_ENV === \"development\";\n\n return nativeCreateYoga<RequestEvent>({\n ...args,\n graphiql: enableApiDocs,\n schema: builtSchema(),\n context,\n plugins: [\n ...(args?.plugins ?? []),\n ...(enableApiDocs\n ? []\n : [useDisableIntrospection(), EnvelopArmorPlugin(args?.armorConfig)]),\n rumbleInput.otel?.enabled || rumbleInput.logger?.enabled\n ? ({\n // TODO: add trace header per default in http response\n // TODO: Automatic Persisted Queries\n onExecute: ({ setExecuteFn, executeFn }) => {\n setExecuteFn(\n buildTracedExecute(\n executeFn,\n rumbleInput,\n ) as typeof executeFn,\n );\n },\n } as Plugin)\n : false,\n ].filter(Boolean),\n });\n };\n\n const createSofa = async (\n args: Omit<Parameters<typeof useSofa>[0], \"schema\" | \"context\">,\n ) => {\n const { useSofa: useSofaFn } = await import(\"sofa-api\");\n if (args.openAPI) {\n merge(args.openAPI, sofaOpenAPIWebhookDocs);\n }\n if (args.errorHandler) {\n const originalHandler = args.errorHandler;\n args.errorHandler = (errors) => {\n const span = trace.getActiveSpan();\n\n for (const error of errors) {\n span?.recordException(error);\n }\n span?.setStatus({ code: SpanStatusCode.ERROR });\n return originalHandler(errors);\n };\n }\n return useSofaFn({\n ...args,\n schema: builtSchema(),\n context,\n execute: buildTracedExecute(\n args.execute ?? defaultExecute,\n rumbleInput,\n ) as any,\n subscribe: buildTracedSubscribe(\n args.subscribe ?? defaultSubscribe,\n rumbleInput,\n ) as any,\n errorHandler(errors) {\n const span = trace.getActiveSpan();\n\n for (const error of errors) {\n span?.recordException(error);\n }\n span?.setStatus({ code: SpanStatusCode.ERROR });\n\n return new Response(errors[0].message, {\n status: 500,\n }) as any;\n },\n });\n };\n\n const createWs = <\n Options extends ServerOptions<any, any>,\n Rest extends unknown[],\n Return,\n >(\n implementation: (options: Options, ...rest: Rest) => Return,\n args: Omit<Options, \"schema\" | \"context\">,\n ...rest: Rest\n ): Return => {\n return implementation(\n {\n ...args,\n schema: builtSchema(),\n context,\n execute: buildTracedExecute(\n (args as any).execute ?? defaultExecute,\n rumbleInput,\n ) as any,\n subscribe: buildTracedSubscribe(\n (args as any).subscribe ?? defaultSubscribe,\n rumbleInput,\n ) as any,\n } as Options,\n ...rest,\n );\n };\n\n const clientCreator = clientCreatorImplementer<\n UserContext,\n DB,\n RequestEvent,\n Action,\n PothosConfig\n >({\n ...rumbleInput,\n builtSchema,\n });\n\n return {\n /**\n * The ability builder. Use it to declare whats allowed for each entity in your DB.\n *\n * @example\n *\n * ```ts\n * // users can edit themselves\n abilityBuilder.users\n .allow([\"read\", \"update\", \"delete\"])\n .when(({ userId }) => ({ where: eq(schema.users.id, userId) }));\n\n // everyone can read posts\n abilityBuilder.posts.allow(\"read\");\n *\n * ```\n */\n abilityBuilder,\n /**\n * The pothos schema builder. See https://pothos-graphql.dev/docs/plugins/drizzle\n */\n schemaBuilder,\n /**\n * Creates the native yoga instance. Can be used to run an actual HTTP server.\n *\n * @example\n *\n * ```ts\n * import { createServer } from \"node:http\";\n * const server = createServer(createYoga());\n * server.listen(3000, () => {\n * console.info(\"Visit http://localhost:3000/graphql\");\n * });\n * ```\n * https://the-guild.dev/graphql/yoga-server/docs#server\n */\n createYoga,\n /**\n * Creates a sofa instance to offer a REST API.\n *\n * ```ts\n * import express from \"express\";\n *\n * const app = express();\n * const sofa = createSofa(...);\n *\n * app.use(\"/api\", useSofa({ schema }));\n * ```\n * https://the-guild.dev/graphql/sofa-api/docs#usage\n */\n createSofa,\n /**\n * Creates a WebSocket server handler for GraphQL subscriptions.\n * Pass the ws implementation function as the first argument and rumble will\n * inject the schema and context automatically.\n *\n * @example\n *\n * ```ts\n * // ws\n * import { useServer } from \"graphql-ws/use/ws\";\n * import { WebSocketServer } from \"ws\";\n * const wss = new WebSocketServer({ port: 4000 });\n * const disposable = createWs(useServer, { ... }, wss);\n *\n * // bun\n * import { makeHandler } from \"graphql-ws/use/bun\";\n * Bun.serve({ websocket: createWs(makeHandler, { ... }), ... });\n * ```\n */\n createWs,\n /**\n * A function for creating default objects for your schema\n */\n object,\n /**\n * A function for creating where args to filter entities\n */\n whereArg,\n /**\n * A function for creating order args to sort entities\n */\n orderArg,\n /**\n * A function for creating default READ queries.\n * Make sure the objects for the table you are creating the queries for are implemented\n */\n query,\n /**\n * A function for creating a pubsub instance for a table. Use this to publish or subscribe events\n */\n pubsub: makePubSubInstance,\n /**\n * A function to implement enums for graphql usage.\n * The other helpers use this helper internally so in most cases you do not have to\n * call this helper directly, unless you need the reference to an enum type\n */\n enum_,\n /**\n * Create a client to consume a rumble graphql api at the specified location.\n * Requires GraphQL, does not work with the SOFA REST API.\n */\n clientCreator,\n /**\n * A function for creating count queries for your tables\n */\n countQuery,\n /**\n * The generated GraphQL schema. You can use this for example to create a GraphQL server with a different library than Yoga or to generate types with codegen.\n * When calling this function, the schema will be built for the first time and cached for later usage. So you can call this function multiple times without performance issues.\n * After calling, you cannot adjust the schema via the schema builder\n */\n buildSchema: builtSchema,\n };\n};\n"],"mappings":"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CN,MAAM,yCACR,EACF,EACF,EACF;GACA,WAAW,EACT,OAAO;IACL,aAAa;IACb,SAAS,EACP,oBAAoB,EAClB,QAAQ,EACN,MAAM,6CACR,EACF,EACF;GACF,EACF;EACF,EACF;EACA,iBAAiB;GACf,MAAM;IACJ,aAAa;IACb,aAAa;IACb,YAAY,CACV;KACE,MAAM;KACN,IAAI;KACJ,aAAa;KACb,UAAU;KACV,QAAQ,EACN,MAAM,SACR;IACF,CACF;IACA,aAAa,EACX,SAAS,EACP,oBAAoB,EAClB,QAAQ,EACN,MAAM,yCACR,EACF,EACF,EACF;IACA,WAAW,EACT,OAAO;KACL,aAAa;KACb,SAAS,EACP,oBAAoB,EAClB,QAAQ,EACN,MAAM,6CACR,EACF,EACF;IACF,EACF;GACF;GACA,QAAQ;IACN,aAAa;IACb,aAAa;IACb,MAAM,CAAC;IACP,YAAY,CACV;KACE,MAAM;KACN,IAAI;KACJ,aAAa;KACb,UAAU;KACV,QAAQ,EACN,MAAM,SACR;IACF,CACF;IACA,WAAW,EACT,OAAO;KACL,aAAa;KACb,SAAS,EACP,oBAAoB,EAClB,QAAQ,EACN,MAAM,6CACR,EACF,EACF;IACF,EACF;GACF;EACF;CACF;CACA,YAAY,EACV,SAAS;EACP,mBAAmB;GACjB,MAAM;GACN,YAAY;IACV,cAAc;KACZ,aACE;KACF,MAAM;IACR;IACA,WAAW;KACT,aAAa;KACb,MAAM;IACR;IACA,KAAK;KACH,aAAa;KACb,MAAM;IACR;GACF;EACF;EACA,uBAAuB;GACrB,MAAM;GACN,YAAY,EACV,IAAI;IACF,aACE;IACF,MAAM;GACR,EACF;EACF;EACA,UAAU;GACR,MAAM;GACN,QAAQ;EACV;EACA,MAAM;GACJ,MAAM;GACN,QAAQ;EACV;CACF,EACF;AACF;;;AC/HA,SAAS,WAAW,OAA+C;CACjE,OAAO,OAAO,UAAU,YAAY,UAAU,QAAQ,aAAa;AACrE;AAEA,SAAS,kBAAkB,OAAiC;CAC1D,IAAI,WAAW,KAAK,GAAG;EACrB,MAAM,WAAW;EACjB,OAAO;GACL,kBAAkB,SAAS,aAAa,QAAQ,SAAS,QAAQ;GACjE,qBAAqB,OAAO,SAAS,OAAO;GAC5C,GAAI,SAAS,QAAQ,EAAE,wBAAwB,SAAS,MAAM,IAAI,CAAC;GACnE,GAAI,SAAS,OAAO,EAAE,MAAM,SAAS,KAAK,IAAI,CAAC;GAC/C,GAAI,SAAS,cAAc,OAAO,KAAK,SAAS,UAAU,CAAC,CAAC,SAAS,IACjE,EAAE,YAAY,SAAS,WAAW,IAClC,CAAC;EACP;CACF;CACA,OAAO;EACL,kBAAkB;EAClB,qBAAqB,OAAO,KAAK;CACnC;AACF;;;;;;AAOA,SAAgB,eAAe,QAE7B;CACA,OAAO,EAAE,QAAQ,OAAO,IAAI,iBAAiB,EAAE;AACjD;AAEA,SAAgB,cAAc,OAA+C;CAC3E,OAAO,eAAe,CAAC,KAAK,CAAC;AAC/B;;;AChCA,MAAM,sBAAsB;AAE5B,SAAS,iBAAiB,SAAwB;CAChD,OAAO,gBAAgB,QAAQ,UAAU,QAAQ,aAAa,CAAC,EAAE;AACnE;AAEA,SAAS,mBAAmB,eAAuB,eAAwB;CACzE,OAAO;EACL,0BAA0B;EAC1B,GAAI,gBAAgB,EAAE,0BAA0B,cAAc,IAAI,CAAC;CACrE;AACF;AAEA,SAAS,iBAAiB,MAAY;CACpC,MAAM,EAAE,SAAS,QAAQ,eAAe,KAAK,YAAY;CACzD,OAAO;EACL,UAAU;EACV,SAAS;EACT,aAAa,WAAW,SAAS,EAAE,CAAC,CAAC,SAAS,GAAG,GAAG;CACtD;AACF;AAEA,SAAgB,gBACd,OACiC;CACjC,OACE,OAAO,UAAU,YAAY,UAAU,QAAQ,OAAO,iBAAiB;AAE3E;AAEA,gBAAuB,yBACrB,UACA,KACA,eACA,eACiC;CACjC,IAAI,aAAa;CACjB,IAAI;EACF,WAAW,MAAM,SAAS,UAAU;GAClC;GACA,IAAI,MAAM,QAAQ,QAChB,IAAI,MACF;IACE,GAAG,mBAAmB,eAAe,aAAa;IAClD,aAAa;IACb,GAAG,eAAe,MAAM,MAAM;GAChC,GACA,kCACF;GAEF,MAAM;EACR;EACA,IAAI,KACF;GACE,GAAG,mBAAmB,eAAe,aAAa;GAClD,aAAa;EACf,GACA,gCACF;CACF,SAAS,OAAO;EACd,IAAI,MACF;GACE,GAAG,mBAAmB,eAAe,aAAa;GAClD,aAAa;GACb,GAAG,cAAc,KAAK;EACxB,GACA,4BACF;EACA,MAAM;CACR;AACF;AAEA,SAAgB,mBAOd,WAGA,aACmD;CACnD,OAAO,OAAO,YAAqD;EACjE,IAAI,MAAM,YAAY,QAAQ,UAC1B,YAAY,OAAO,SACnB,KAAA;EACJ,MAAM,gBAAgB,QAAQ,iBAAiB;EAC/C,MAAM,gBAAgB,iBAAiB,OAAO;EAC9C,MAAM,QAAQ,KAAK,IAAI;EAEvB,KAAK,KACH,mBAAmB,eAAe,aAAa,GAC/C,uBACF;EAEA,MAAM,MAAM,YAAY;GACtB,MAAM,SAAS,MAAM,UAAU,OAAO;GACtC,IAAI,UAAU,YAAY,UAAU,OAAO,QAAQ,QACjD,KAAK,MACH;IACE,GAAG,mBAAmB,eAAe,aAAa;IAClD,aAAa,KAAK,IAAI,IAAI;IAC1B,GAAG,eAAe,OAAO,MAAM;GACjC,GACA,uCACF;QAEA,KAAK,KACH;IACE,GAAG,mBAAmB,eAAe,aAAa;IAClD,aAAa,KAAK,IAAI,IAAI;GAC5B,GACA,2BACF;GAEF,OAAO;EACT;EAEA,IAAI,YAAY,MAAM,SACpB,OAAO,YAAY,KAAK,OAAQ,gBAC9B,UAAU,SACV,EACE,YAAY;IACT,eAAe,iBAAiB;GACjC,GAAI,gBACA,GAAG,eAAe,iBAAiB,cAAc,IACjD,CAAC;GACL,oBAAoB,MAAM,QAAQ,QAAQ;EAC5C,EACF,GACA,OAAO,SAAe;GACpB,IAAI,OAAO,YAAY,QAAQ,kBAAkB,OAC/C,MAAM,IAAI,MAAM,iBAAiB,IAAI,CAAC;GAExC,IAAI;IACF,MAAM,SAAS,MAAM,IAAI;IACzB,IAAI,UAAU,YAAY,UAAU,OAAO,QAAQ,QAAQ;KACzD,KAAK,MAAM,SAAS,OAAO,QAAQ,KAAK,gBAAgB,KAAK;KAC7D,KAAK,UAAU,EAAE,MAAM,eAAe,MAAM,CAAC;IAC/C;IACA,OAAO;GACT,SAAS,OAAO;IACd,IAAI,iBAAiB,OAAO,KAAK,gBAAgB,KAAK;IACtD,KAAK,MACH;KACE,GAAG,mBAAmB,eAAe,aAAa;KAClD,aAAa,KAAK,IAAI,IAAI;KAC1B,GAAG,cAAc,KAAK;IACxB,GACA,uBACF;IACA,KAAK,UAAU,EAAE,MAAM,eAAe,MAAM,CAAC;IAC7C,MAAM;GACR,UAAU;IACR,KAAK,IAAI;GACX;EACF,CACF;EAGF,IAAI;GACF,OAAO,MAAM,IAAI;EACnB,SAAS,OAAO;GACd,KAAK,MACH;IACE,GAAG,mBAAmB,eAAe,aAAa;IAClD,aAAa,KAAK,IAAI,IAAI;IAC1B,GAAG,cAAc,KAAK;GACxB,GACA,uBACF;GACA,MAAM;EACR;CACF;AACF;AAEA,SAAgB,qBAOd,aAMA,aAG6D;CAC7D,OAAO,OACL,YAC8D;EAC9D,IAAI,MAAM,YAAY,QAAQ,UAC1B,YAAY,OAAO,SACnB,KAAA;EACJ,MAAM,gBAAgB,QAAQ,iBAAiB;EAC/C,MAAM,gBAAgB,iBAAiB,OAAO;EAC9C,MAAM,QAAQ,KAAK,IAAI;EAEvB,MAAM,cAAc,YAEf;GACH,KAAK,KACH,mBAAmB,eAAe,aAAa,GAC/C,yBACF;GAEA,MAAM,SAAS,MAAM,YAAY,OAAO;GAExC,IAAI,CAAC,gBAAgB,MAAM,GAAG;IAC5B,MAAM,aAAa;IACnB,IAAI,WAAW,QAAQ,QACrB,KAAK,MACH;KACE,GAAG,mBAAmB,eAAe,aAAa;KAClD,aAAa,KAAK,IAAI,IAAI;KAC1B,GAAG,eAAe,WAAW,MAAM;IACrC,GACA,yCACF;IAEF,OAAO;GACT;GAEA,KAAK,KACH;IACE,GAAG,mBAAmB,eAAe,aAAa;IAClD,aAAa,KAAK,IAAI,IAAI;GAC5B,GACA,kCACF;GAEA,IAAI,KACF,OAAO,yBACL,QACA,KACA,eACA,aACF;GAEF,OAAO;EACT;EAEA,IAAI,YAAY,MAAM,SACpB,OAAO,YAAY,KAAK,OAAQ,gBAC9B,qBACA,EACE,YAAY;IACT,eAAe,iBAAiB;GACjC,GAAI,gBACA,GAAG,eAAe,iBAAiB,cAAc,IACjD,CAAC;GACL,oBAAoB,MAAM,QAAQ,QAAQ;EAC5C,EACF,GACA,OAAO,SAAe;GACpB,IAAI,OAAO,YAAY,QAAQ,kBAAkB,OAC/C,MAAM,IAAI,MAAM,iBAAiB,IAAI,CAAC;GAExC,IAAI;IACF,MAAM,SAAS,MAAM,YAAY;IACjC,IAAI,CAAC,gBAAgB,MAAM,GAAG;KAC5B,MAAM,aAAa;KACnB,IAAI,WAAW,QAAQ,QAAQ;MAC7B,KAAK,MAAM,SAAS,WAAW,QAC7B,KAAK,gBAAgB,KAAK;MAC5B,KAAK,UAAU,EAAE,MAAM,eAAe,MAAM,CAAC;KAC/C;IACF;IACA,OAAO;GACT,SAAS,OAAO;IACd,IAAI,iBAAiB,OAAO,KAAK,gBAAgB,KAAK;IACtD,KAAK,MACH;KACE,GAAG,mBAAmB,eAAe,aAAa;KAClD,aAAa,KAAK,IAAI,IAAI;KAC1B,GAAG,cAAc,KAAK;IACxB,GACA,yBACF;IACA,KAAK,UAAU,EAAE,MAAM,eAAe,MAAM,CAAC;IAC7C,MAAM;GACR,UAAU;IACR,KAAK,IAAI;GACX;EACF,CACF;EAGF,IAAI;GACF,OAAO,MAAM,YAAY;EAC3B,SAAS,OAAO;GACd,KAAK,MACH;IACE,GAAG,mBAAmB,eAAe,aAAa;IAClD,aAAa,KAAK,IAAI,IAAI;IAC1B,GAAG,cAAc,KAAK;GACxB,GACA,yBACF;GACA,MAAM;EACR;CACF;AACF;;;ACnUA,SAAgB,uCAEd,EACA,SACA,SACA,WACA,UACA,WAOC;CACD,MAAM,UAAU,wBAAwB;EACtC;EACA;CACF,CAAC;CACD,QAAQ,SAAR;EACE,KAAK,OACH,OAAO,UACH,QAAQ,cAAc,WAAW,EAAY,SAAgB,CAAC,IAC9D,QAAQ,UAAU,WAAW,EAAE,SAAS,CAAC;EAC/C,KAAK,UACH,OAAO,QAAQ,MAAM;GACnB,MAAM,UAAU,CAAC,QAAQ,IAAI;GAC7B,UAAU,YAAiB,QAAQ;GACnC;EACF,CAAC;EACH,KAAK,UACH,OAAO,UACH,QAAQ,iBAAiB,WAAW,EAAY,SAAgB,CAAC,IACjE,QAAQ,aAAa,WAAW,EAAE,SAAS,CAAC;EAClD,KAAK,WACH,OAAO,UACH,QAAQ,kBAAkB,WAAW,EAAY,SAAgB,CAAC,IAClE,QAAQ,cAAc,WAAW,EAAE,SAAS,CAAC;EACnD,KAAK,QACH,OAAO,QAAQ,MAAM;GACnB,MAAM,UAAU,CAAC,MAAM,IAAI;GAC3B,UAAU,YAAiB,QAAQ;GACnC;EACF,CAAC;EACH,KAAK,YACH,OAAO,QAAQ,MAAM;GACnB,MAAM,UAAU,CAAC,UAAU,IAAI;GAG/B,UAAU,YAAiB;IACzB,MAAM,IAAI,QAAQ;IAClB,IAAI,KAAK,MAAM,OAAO;IACtB,OAAO,aAAa,OAAO,IAAI,IAAI,KAAK,CAAC;GAC3C;GACA;EACF,CAAC;EACH,KAAK,SACH,OAAO,UACH,QAAQ,gBAAgB,WAAW,EAAY,SAAgB,CAAC,IAChE,QAAQ,YAAY,WAAW,EAAE,SAAS,CAAC;EACjD,KAAK,MACH,OAAO,UACH,QAAQ,aAAa,WAAW,EAAY,SAAgB,CAAC,IAC7D,QAAQ,SAAS,WAAW,EAAE,SAAS,CAAC;EAC9C,KAAK,QACH,OAAO,QAAQ,MAAM;GACnB,MAAM,UAAU,CAAC,MAAM,IAAI;GAC3B,UAAU,YAAiB,QAAQ;GACnC;EACF,CAAC;EACH,KAAK,SACH,OAAO,QAAQ,MAAM;GACnB,MAAM;GACN,UAAU,YAAiB;IACzB,MAAM,IAAI,QAAQ;IAClB,IAAI,KAAK,MAAM,OAAO;IACtB,OAAO,OAAO,SAAS,CAAC,IAAI,EAAE,SAAS,QAAQ,IAAI,OAAO,CAAC;GAC7D;GACA;EACF,CAAC;EACH,SACE,MAAM,IAAI,YACR,2BAA2B,QAAQ,cAAc,WACnD;CACJ;AACF;;;AC/EA,MAAM,+BAAe,IAAI,QAA2B;AAEpD,SAAgB,6BACd,QACW;CACX,MAAM,SAAS,aAAa,IAAI,MAA2B;CAC3D,IAAI,QAAQ,OAAO;CAEnB,MAAM,wBAAQ,IAAI,IAAe;CAEjC,KAAK,MAAM,SAAS,OAAO,OAAO,MAAM,CAAC,CAAC,KAAK,MAAW,EAAE,KAAK,GAAG;EAClE,IAAI,CAAC,SAAS,OAAO,UAAU,UAC7B;EAKF,IAAI,GAAG,OAAO,OAAO,GACnB,MAAM,IAAI,UAAU;OACf,IAAI,GAAG,OAAO,UAAU,GAC7B,MAAM,IAAI,OAAO;OACZ,IAAI,GAAG,OAAO,WAAW,GAC9B,MAAM,IAAI,QAAQ;CAEtB;CAEA,MAAM,WAAW,MAAM,KAAK,KAAK;CAEjC,IAAI,SAAS,WAAW,GAAG;EACzB,MAAM,OAAO,SAAS;EACtB,aAAa,IAAI,QAA6B,IAAI;EAClD,OAAO;CACT;CAEA,IAAI,SAAS,WAAW,GACtB,MAAM,IAAI,MAAM,wDAAwD;CAG1E,MAAM,IAAI,MAAM,sCAAsC,SAAS,KAAK,IAAI,GAAG;AAC7E;AAEA,SAAgB,aAEd,IAAyB;CACzB,OAAO,6BAA6B,GAAG,EAAE,SAAS,MAAM;AAC1D;;;AC7CA,eAAsB,uBACpB,OACA;CACA,MAAM,MAAM,MAAM,QAAQ,UAAU,MAAM,OAAO,SAAS,KAAA;CAE1D,IAAI,CAAC,aAAa,MAAM,EAAE,GAAG;EAC3B,MAAM,MACJ;EACF,MAAM,IAAI,KAAK,CAAC,GAAG,GAAG,IAAI,QAAQ,KAAK,GAAG;EAC1C;CACF;CAEA,IAAI;EACF,MAAM,MAAM,GAAG,QAAQ,GAAG,yCAAyC;CACrE,SAAS,OAAO;EACd,MAAM,MACJ;EACF,MAAM,IAAI,MAAM,cAAc,KAAK,GAAG,GAAG,IAAI,QAAQ,MAAM,KAAK,KAAK;EACrE;CACF;CACA,IAAI,MAAM,QAAQ,WAAW;EAE3B,MAAM,YAAY,OAAO,MAAM,OAAO,SAAS;EAE/C,IAAI,YAAY,KAAK,YAAY,GAC/B,MAAM,IAAI,MAAM,0CAA0C;EAI5D,MAAM,UAAS,MADM,MAAM,GAAG,QAAQ,GAAG,2BAA2B,EAAA,CAC9C,KAAK,EAAE,CAAC;EAE9B,IAAI;GACF,MAAM,MAAM,GAAG,QACb,IAAI,IACF,kBAAkB,OAAO,sCAAsC,UAAU,EAC3E,CACF;EACF,SAAS,OAAY;GAGnB,IAAI,OAAO,OAAO,SAAS,WAAW,OAAO,SAAS,SACpD,MAAM;EACV;CACF;CAEA,IAAI,MAAM,QAAQ,mBAAmB;EACnC,IAAI,OAAO,MAAM,OAAO,sBAAsB,UAC5C,MAAM,IAAI,MAAM,oCAAoC;EAGtD,IAAI,MAAM,OAAO,qBAAqB,GACpC,MAAM,IAAI,MAAM,6CAA6C;CAEjE;AACF;;;;;AAMA,SAAgB,yBAAyB,EACvC,QACA,MACA,aACA,aAOC;CACD,IAAI,QAAQ,WAAW,KAAK,UAAU,KAAK,OAAO,SAAS,GAAG;EAK5D,MAAM,mBACJ,UAAU,MAAM,KAAK,UACjB,OAAO,QAAQ,YAAY,OAAO,CAAC,CAAC,QACjC,CAAC,SAAS,UAAU,MAAM,KAAK,QAAQ,IAC1C,IACA,OAAO,QAAQ,YAAY,OAAO,EAAA,CACtC,QACC,CAAC,MAAM,SACN,0BAA0B,IAAI,WAAW,CAAC,KAC1C,sBAAsB,IAAI,WAAW,CAAC,CAC1C;EAEA,MAAM,cAAc,GAAG,GAAG,KAAK;EAE/B,KAAK,SAAS,EACZ,kBAAkB,UAChB,GAAG,GAAG,IAAI,KACR,gBAAgB,KAAK,CAAC,SAAS;GAC7B,OAAO,GAAG,aAAa,MAAM,KAAK,aAAa,YAAY;EAC7D,CAAC,GACD,IAAI,IAAI,KAAK,CACf,IACJ;EAEA,MAAM,kBAAkB,UAAU,KAAK,OAAO;EAC9C,KAAc,WAAW,UAAe;GACtC,MAAM,iBAAiB,IAAI,KACzB,OAAO,QAAQ,mBAAmB,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,KAAK,WAAW;IAE1D,IAAI,UAAU,OACZ,OAAO,GAAG,GAAG,MAAM,KAAK;SACnB,IAAI,UAAU,QACnB,OAAO,GAAG,GAAG,MAAM,KAAK;SAExB,MAAM,IAAI,MAAM,iBAAiB,MAAM,aAAa;GAExD,CAAC,GACD,IAAI,IAAI,IAAI,CACd;GAEA,MAAM,YAAY,GAAG;GAMrB,OAJY,kBACR,IAAI,KAAK,CAAC,gBAAgB,SAAS,GAAG,IAAI,IAAI,IAAI,CAAC,IACnD;EAGN;EAKA,KAAc,QAAQ,EACpB,KAAK,CAJe,UAAU,KAAK,KAKrB,KAAK,CAAC,GAClB,EACE,MAAM,UACJ,GAAG,IAAI,IAAI,KACT,gBAAgB,KAAK,CAAC,SAAS;GAC7B,OAAO,GAAG,GAAG,MAAM,KAAK,KAAK;EAC/B,CAAC,GACD,IAAI,IAAI,MAAM,CAChB,EAAE,GACN,CACF,EACF;CACF;AACF;;;ACtHA,MAAM,2BAA2B,MAAW;CAC1C,IAAI,OAAO,MAAM,UACf,OAAO;CAGT,IACE,OAAO,KAAK,CAAC,CAAC,CAAC,MAAM,MACnB;EACE;EACA;EACA;EACA;EACA;EACA;EACA;CACF,CAAC,CAAC,MAAM,MAAM,MAAM,CAAC,CACvB,GAEA,OAAO;CACT,OAAO;AACT;AAEA,MAAa,2BAOX,EACA,IACA,QACA,QAAQ,cACR,eACA,oBACA,qBACA,qBACA,iBACA,qBA6CI;CAQJ,QAA0E,EACxE,OACA,SACA,aAAa,QACb,aAgCI;EACJ,MAAM,cAAc,YAAY;GAAE;GAAI;EAAM,CAAC;EAE7C,IAAI,OAAO,KAAK,YAAY,UAAU,CAAC,CAAC,WAAW,GAAG;GACpD,MAAM,MAAM,cAAc,UAAU,aAAa,SAAS,KAAA;GAC1D,MAAM,MAAM,kCAAkC,OAAO,KAAK,EAAE;GAC5D,MACI,IAAI,KAAK,EAAE,gBAAgB,OAAO,KAAK,EAAE,GAAG,GAAG,IAC/C,QAAQ,KAAK,GAAG;EACtB;EACA,MAAM,aAAa,OAAO,OAAO,YAAY,UAAU,CAAC,CAAC;EAEzD,MAAM,EAAE,uBAAuB,mBAAmB,EAAS,MAAM,CAAC;EAElE,OAAO,cAAc,cAAc,OAAO;GACxC,MAAM,WAAW,WAAW,OAAO,KAAK,CAAC;GACzC,YAAY,eAAe,SAAS,aAAa;IAC/C,IAAI,CAAC,YAAY;IACjB,MAAM,kBAAmB,QAAgB,WAAW;IACpD,IAAI,CAAC,iBAAiB;KACpB,MAAM,MAAM,cAAc,UAAU,aAAa,SAAS,KAAA;KAC1D,MAAM,MAAM,mDAAmD,OAAO,KAAK,EAAE;KAC7E,MACI,IAAI,KAAK,EAAE,gBAAgB,OAAO,KAAK,EAAE,GAAG,GAAG,IAC/C,QAAQ,KAAK,GAAG;KACpB;IACF;IAGA,mBAAmB;KACjB,UAAU;KACV,QAAQ;KACS;IACnB,CAAC;GACH;GACA,cAAc,gBAAgB,EAAE,kBAAkB;IAChD;IACA,QAAQ;GACV,CAAC;GACD,SAAS,MAAM;IACb,MAAM,UAAU,YAAY;IAS5B,MAAM,4BAAY,IAAI,IAOpB;IAIF,MAAM,kBACJ,SACE,IAAI,MAAM,GAAG,EACX,MAAM,QAAQ,MAAM,cAAc;KAChC,IAEE,OAAQ,OAAe,UAAU,cACjC,SAAS,SACT,SAAS,aACT,SAAS,iBACT,SAAS,UACT,SAAS,aACT,SAAS,WACT,SAAS,cACT,SAAS,aACT,KAAK,SAAS,CAAC,CAAC,WAAW,SAAS,KACpC,KAAK,SAAS,CAAC,CAAC,WAAW,OAAO,KAClC,KAAK,SAAS,CAAC,CAAC,WAAW,IAAI,KAC/B,KAAK,SAAS,CAAC,CAAC,WAAW,KAAK,KAChC,KAAK,SAAS,CAAC,CAAC,WAAW,QAAQ,KACnC,KAAK,SAAS,CAAC,CAAC,WAAW,QAAQ,GAEnC,OAAQ,OAAe;KAGzB,QAAQ,GAAG,WAAkB;MAC3B,MAAM,MAAO,OAAe,KAAK,CAAC,GAAG,MAAM;MAC3C,MAAM,eAAe,OAAO,KAAK,uBAAuB;MACxD,IAAI,CAAC,cACH,MAAM,IAAI,YACR,qDACF;MAEF,UAAU,IAAI,KAAK;OACjB;OACA,iBAAkB,OAAe;OACjC;MACF,CAAC;MACD,OAAO;KACT;IACF,EACF,CAAC,CACH,KAAK,CAAC;IAER,MAAM,SAAS,OAAO,QAAQ,OAAO,CAAC,CAAC,QACpC,KAAK,CAAC,KAAK,YAAY;KAItB,IAAI,IAAI,WAAW,IAAI,GAAG;MACxB,QAAQ,KACN,oBAAoB,IAAI,cAAc,YAAY,OAAO,wIAC3D;MACA,OAAO;KACT;KAKA,IAAI,gBAAgB,MAAM;MACxB,MAAM,EAAE,QAAQ,iBAAiB,iBAAiB,UAAU,IAC1D,gBAAgB,IAClB;MAEA,IAAI,OAAO,aAAa,aAAa,WACnC,aAAa,WAAW,CAAC,OAAO;MAGlC,gBAAgB,OAAO,gBAAgB,KAAK,CAAC,CAAC,CAAC,GAAG,MAAM;MACxD,OAAO;KACT;KAKA,IAAI,UAAU;KACd,IAAI,GAAG,QAAQ,QAAQ,GAAG;MACxB,MAAM,aAAc,OACjB;MACH,IAAI,cAAc,aAAa,GAAG;OAChC,IAAI,eAAe,GACjB,MAAM,IAAI,YACR,6EACF;OAEF,UAAU;MACZ;KACF;KAEA,IAAI,aAAa,MAAM,GAAG;MACxB,MAAM,WAAW,gBAAgB,EAC/B,YAAY,OACd,CAAC;MAED,IAAI,OAAO,EAAE,MAAM;OACjB,MAAM,UAAU,CAAC,QAAQ,IAAI;OAC7B,UAAU,YAAa,QAAgB;OACvC,UAAU,CAAC,OAAO;MACpB,CAAC;KACH,OACE,IAAI,OAAO,uCAAuC;MAChD,SAAS;MACT,SAAS,OAAO,WAAW;MAC3B,WAAW;MACX,UAAU,CAAC,OAAO;MAClB;KACF,CAAC;KAEH,OAAO;IACT,GACA,CAAC,CAKH;IAEA,MAAM,YAAY,OAAO,QAAQ,YAAY,aAAa,CAAC,CAAC,CAAC,CAAC,QAC3D,KAAK,CAAC,KAAK,WAAW;KACrB,MAAM,eAAgB,MAAc;KACpC,MAAM,iBAAiB,YAAY;MACjC;MACA,OAAO;KACT,CAAC;KACD,MAAM,WAAW,oBAAoB,EACnC,QAAQ,eAAe,OACzB,CAAC;KACD,MAAM,WAAW,oBAAoB,EACnC,QAAQ,eAAe,OACzB,CAAC;KACD,MAAM,sBAAsB,mBAAmB,EAC7C,OAAO,eAAe,OACxB,CAAC;KAGD,IAAI,WAAW;KACf,IAAI,SAAS;KACb,IAAI,kBAAkB;KACtB,IAAI,GAAG,OAAO,GAAG,GAAG;MAClB,SAAS;MACT,WACE,MAAM,YACN,CAAC,MAAM,cAAc,OAAO,WAAW,OAAO,OAAO;MACvD,kBAAkB;KACpB;KAEA,MAAM,aAAa,eAAoB,aAAkB;MACvD,oBAAoB,mBAAmB;OACrC,UAAU;OACV,QAAQ;MACV,CAAC;MACD,oBAAoB,mBAAmB;OACrC,UAAU;OACV,QAAQ;MACV,CAAC;KACH;KAKA,IAAI,gBAAgB,MAAM;MACxB,MAAM,EAAE,QAAQ,iBAAiB,iBAAiB,UAAU,IAC1D,gBAAgB,IAClB;MAEA,IAAI,OAAO,aAAa,aAAa,WACnC,aAAa,WAAW;MAG1B,IAAI,OAAO,aAAa,cAAc,YACpC,aAAa,YAAY;MAG3B,gBAAgB,OAAO,gBAAgB,KAAK,CAAC,CAAC,CAAC,GAAG,MAAM;MACxD,OAAO;KACT;KAEA,MAAM,OAAO;MACX,OAAO,EAAE,IAAI;OAAE,MAAM;OAAU,UAAU;MAAM,CAAC;MAChD,SAAS,EAAE,IAAI;OAAE,MAAM;OAAU,UAAU;MAAM,CAAC;MAClD,GAAI,SACA;OACE,QAAQ,EAAE,IAAI,IAAI,EAAE,UAAU,MAAM,CAAC;OACrC,OAAO,EAAE,IAAI,IAAI,EAAE,UAAU,MAAM,CAAC;MACtC,IACA,CAAC;MACL,QAAQ,EAAE,IAAI,OAAO,EAAE,UAAU,MAAM,CAAC;KAC1C;KAEA,IAAI,CAAC,QAAQ,WAAW,CAAC,QACvB,OAAQ,KAAa;KAGvB,IAAa,OAAO,EAAE,SACpB,KACA;MACE;MACA;MACA;MACA,aAAa,WAAW,UAAU,OAAO,eAAe,MAAM,EAAE,mBAAmB,UAAU,SAAS,YAAY,MAAM;MACxH,QAAQ,MAAW,QAAa;OAE9B,OAAO,KAAK,MAAM,KAAK,UAAU,IAAI,CAAC;OAEtC,IAAI,QACF,yBAAyB;QACvB;QACA;QACA,aAAa;QACb,WACE,IAAI,UAAU,eAAe,OAAO,CAAC,OAAO,UAAU;OAC1D,CAAC;OAGH,MAAM,SAAS,IAAI,UAAU,eAAe,OAAO,CAChD,OAAO,UAAU,CAAC,CAClB,MAAM;QACL,OAAO,KAAK;QACZ,OAAO,KAAK;QACZ,QAAQ,KAAK;OACf,CAAC,CAAC,CAAC,MAAM;OAEX,IAAI,KAAK,QACP,OAAgB,SAAS,KAAK;OAGhC,IAAI,KAAK,SACP,OAAgB,UAAU,KAAK;OAGjC,OAAO;MACT;KACF,CACF;KACA,OAAO;IACT,GACA,CAAC,CAIH;IAEA,IAAI,QAAQ,SAAS;KACnB,IAAI,OAAO,iBACT,MAAM,IAAI,MACR,oDACE,YAAY,SACZ,4GACJ;KAGF,OAAO,kBAAkB,EAAE,MAAM;MAC/B,aACE;MACF,UAAU;MACV,UAAU,QAAQ,OAAO,MAAM,UAC5B,OAAe;KACpB,CAAC;IACH;IAEA,OAAO;KACL,GAAG;KACH,GAAG;KACH,GAAG;IACL;GACF;EACF,CAAC;CACH;AACF;;;ACheA,MAAM,sCAAsC;AAC5C,MAAM,gCAAgC;AACtC,MAAM,gCAAgC;AACtC,MAAM,gCAAgC;AAkBtC,MAAa,wBAMX,EACA,oBACsE;CACtE,MAAM,SAAS,gBACX,aAAa,GAAG,aAAa,IAC7B,aAAa;CAEjB,MAAM,sBAEJ,EACA,YAGI;EAGJ,SAAS,cAAc,EACrB,QACA,WACA,mBAKC;GACD,IAAI;GAEJ,QAAQ,QAAR;IACE,KAAK;KACH,YAAY;KACZ;IACF,KAAK;KACH,YAAY;KACZ;IACF,KAAK;KACH,YAAY;KACZ;IACF,SACE,MAAM,IAAI,MAAM,mBAAmB,QAAQ;GAC/C;GAEA,OAAO,GAAG,oCAAoC,GAAG,YAC/C,kBAAkB,IAAI,oBAAoB,GAC3C,GAAG;EACN;EAGA,OAAO;;;;GAIL,mBAAmB,EACjB,UACA,QACA,mBAKC;IACD,MAAM,MAAM,cAAc;KACxB,WAAW,MAAM,SAAS;KAC1B;KACA;IACF,CAAC;IACD,SAAS,SAAS,GAAG;GACvB;;;;GAIA,UAAU;IACR,MAAM,MAAM,cAAc;KACxB,WAAW,MAAM,SAAS;KAC1B,QAAQ;IACV,CAAC;IACD,OAAO,OAAO,QAAQ,GAAG;GAC3B;;;;GAKA,UAAU;IACR,MAAM,MAAM,cAAc;KACxB,WAAW,MAAM,SAAS;KAC1B,QAAQ;IAGV,CAAC;IACD,OAAO,OAAO,QAAQ,GAAG;GAC3B;;;;GAIA,QAAQ,iBAAqD;IAI3D,MAAM,QAHc,MAAM,QAAQ,eAAe,IAC7C,kBACA,CAAC,eAAe,EAAA,CACK,KAAK,oBAC5B,cAAc;KACZ,WAAW,MAAM,SAAS;KAC1B,QAAQ;KACR;IACF,CAAC,CACH;IACA,MAAM,aAAa,MAAM,KAAK,IAAI,IAAI,IAAI,CAAC;IAC3C,KAAK,MAAM,OAAO,YAChB,OAAO,QAAQ,GAAG;GAEtB;EACF;CACF;CAEA,OAAO;EACL;EACA;CACF;AACF;;;ACpIA,MAAa,0BAOX,EACA,IACA,eACA,QACA,QAAQ,cACR,qBACA,qBACA,yBA8BI;CACJ,MAAM,4CAA4B,IAAI,IAAY;CAElD,QAAkD,EAChD,OACA,aAAa,QACb,aAAa,QACb,WACA,eA8BI;EACJ,MAAM,WAAW,oBAAoB,EAC5B,MACT,CAAC;EACD,MAAM,WAAW,oBAAoB,EAC5B,MACT,CAAC;EACD,MAAM,cAAc,YAAY;GAC9B;GACA;EACF,CAAC;EACD,MAAM,kBAAkB,OAAO,OAAO,YAAY,UAAU,CAAC,CAAC;EAE9D,MAAM,EAAE,uBAAuB,mBAAmB,EAAS,MAAM,CAAC;EAElE,MAAM,aAAa,UAAU,OAAO,OAAO,KAAK,CAAC;EACjD,MAAM,eAAe,UAAU,SAAS,OAAO,KAAK,CAAC;EACrD,KAAK,MAAM,QAAQ,CAAC,YAAY,YAAY,GAAG;GAC7C,IAAI,0BAA0B,IAAI,IAAI,GACpC,MAAM,IAAI,YACR,0BAA0B,KAAK,gBAAgB,OAAO,KAAK,EAAE,yKAG/D;GAEF,0BAA0B,IAAI,IAAI;EACpC;EAEA,OAAO,cAAc,aAAa,MAAM;GACtC,MAAM,WAAW;IACf,OAAO,EAAE,IAAI;KAAE,MAAM;KAAU,UAAU;IAAM,CAAC;IAChD,SAAS,EAAE,IAAI;KAAE,MAAM;KAAU,UAAU;IAAM,CAAC;IAClD,OAAO,EAAE,IAAI,IAAI,EAAE,UAAU,MAAM,CAAC;IACpC,QAAQ,EAAE,IAAI,IAAI,EAAE,UAAU,MAAM,CAAC;IACrC,QAAQ,EAAE,IAAI,OAAO,EAAE,UAAU,MAAM,CAAC;GAC1C;GAEA,IAAI,CAAC,QAAQ,SACX,OAAQ,SAAiB;GAG3B,OAAO;KACJ,aAAa,EAAE,aAAa;KAC3B,MAAM,CAAC,KAAK;KACZ,UAAU;KACV,mBAAmB;KACnB,aAAa,YAAY;KACzB,YAAY,eAAe,OAAO,OAAO,MAAM,UAAU;MACvD,mBAAmB;OACjB,UAAU;OACV,QAAQ;MACV,CAAC;MACD,mBAAmB;OACjB,UAAU;OACV,QAAQ;MACV,CAAC;KACH;KACA,MAAM;KACN,UAAU,OAAO,OAAO,MAAM,KAAK,UAAU;MAG3C,aAAa,IAAI;MAEjB,yBAAyB;OACvB;OACA;OACA;OACA,WAAW,IAAI,UAAU,MAAM,CAAC,OAAO,UAAU;MACnD,CAAC;MAED,MAAM,aAAa,yBAAyB,IAAI;MAChD,MAAM,SAAS,IAAI,UAAU,MAAM,CAChC,OAAO,UAAU,CAAC,CAClB,MAAM,UAAiB,CAAC,CAAC,MAAM;MAElC,IAAI,WAAW,QACb,OAAgB,SAAS,WAAW;MAGtC,IAAI,WAAW,SACb,OAAgB,UAAU,WAAW;MAGvC,MAAM,YAAY,MAAM,MAAa;MAErC,IAAK,OAAe,SAClB,UAAU,UAAW,OAAe;MAGtC,MAAM,MAAM,YACP,OAAW,SAAS;OAAE;OAAY;OAAe;MAAU,CAAC,KAC5D,OAAa,GAAG,MAAc,MAAM,CAAC,SAAS,SAAS;MAE5D,IACE,QAAQ,WACR,KAAK,UACL,KAAK,OAAO,SAAS,KACrB,QAAQ,mBAER,OAAO,GAAG,YAAY,OAAO,OAAY;OACvC,IAAI,aAAa,EAAE,GACjB,MAAM,GAAG,QACP,IAAI,IACF,2BAA2B,OAAO,kBAAkB,EACtD,CACF;YACK;QACL,MAAM,MACJ;QACF,MAAM,MAAM,cAAc,UACtB,aAAa,SACb,KAAA;QACJ,MAAM,IAAI,KAAK,CAAC,GAAG,GAAG,IAAI,QAAQ,KAAK,GAAG;OAC5C;OAEA,OAAO,IAAI,EAAE;MACf,CAAC;MAGH,OAAO,IAAI,EAAE;KACf;IACF,CAAC;KACA,eAAe,EAAE,aAAa;KAC7B,MAAM;KACN,UAAU;KACV,mBAAmB;KACnB,aAAa,gBAAgB,aAAa;KAC1C,MAAM,EACJ,IAAI,EAAE,IAAI,GAAG,EAAE,UAAU,KAAK,CAAC,EACjC;KACA,UAAU,OAAO,OAAO,MAAM,KAAK,UAAU;MAC3C,aAAa,IAAI;MAEjB,MAAM,SAAU,IAAI,UAAkB,MAAM,CACzC,OAAO,UAAU,CAAC,CAClB,MAAM,EAAE,OAAO,GAAG,gBAAgB,OAAO,KAAK,GAAG,EAAE,CAAC,CAAC,CACrD,MAAM;MACT,MAAM,YAAY,MAAM,MAAM;MAE9B,IAAI,OAAO,SACT,UAAU,UAAU,OAAO;MAG7B,OAAO,YACH,UAAU;OAAE,IAAI;OAAY;OAAe;MAAU,CAAC,IACrD,GAAG,MAAc,MAAM,CACrB,UAAU,SAAS,CAAC,CACpB,KAAK,qBAAqB;KACnC;IACF,CAAC;GACH;EACF,CAAC;CACH;AACF;;;ACnGA,SAAgB,+BAA+B,eAAoB;CACjE,MAAM,wBAAwB,cAC3B,SAAS,uBAAuB,CAAC,CACjC,UAAU,EACT,SAAS,OAAY;EACnB,IAAI,EAAE,IAAI;EACV,IAAI,EAAE,IAAI;EACV,IAAI,EAAE,IAAI;EACV,KAAK,EAAE,IAAI;EACX,IAAI,EAAE,IAAI;EACV,KAAK,EAAE,IAAI;EACX,IAAI,EAAE,QAAQ;EACd,OAAO,EAAE,QAAQ;EACjB,MAAM,EAAE,OAAO;EACf,OAAO,EAAE,OAAO;EAChB,SAAS,EAAE,OAAO;EAClB,UAAU,EAAE,OAAO;EACnB,QAAQ,EAAE,QAAQ;EAClB,WAAW,EAAE,QAAQ;EACrB,eAAe,EAAE,QAAQ;EACzB,gBAAgB,EAAE,QAAQ;EAC1B,eAAe,EAAE,QAAQ;EACzB,KAAK,EAAE,MAAM,EACX,MAAM,CAAC,qBAAqB,EAC9B,CAAC;EACD,IAAI,EAAE,MAAM,EACV,MAAM,CAAC,qBAAqB,EAC9B,CAAC;EACD,KAAK,EAAE,MAAM,EACX,MAAM,sBACR,CAAC;CACH,GACF,CAAC;CAEH,MAAM,0BAA0B,cAC7B,SAAS,yBAAyB,CAAC,CACnC,UAAU,EACT,SAAS,OAAY;EACnB,IAAI,EAAE,MAAM;EACZ,IAAI,EAAE,MAAM;EACZ,IAAI,EAAE,MAAM;EACZ,KAAK,EAAE,MAAM;EACb,IAAI,EAAE,MAAM;EACZ,KAAK,EAAE,MAAM;EACb,IAAI,EAAE,UAAU;EAChB,OAAO,EAAE,UAAU;EACnB,MAAM,EAAE,OAAO;EACf,OAAO,EAAE,OAAO;EAChB,SAAS,EAAE,OAAO;EAClB,UAAU,EAAE,OAAO;EACnB,QAAQ,EAAE,QAAQ;EAClB,WAAW,EAAE,QAAQ;EACrB,eAAe,EAAE,UAAU;EAC3B,gBAAgB,EAAE,UAAU;EAC5B,eAAe,EAAE,UAAU;EAC3B,KAAK,EAAE,MAAM,EACX,MAAM,CAAC,uBAAuB,EAChC,CAAC;EACD,IAAI,EAAE,MAAM,EACV,MAAM,CAAC,uBAAuB,EAChC,CAAC;EACD,KAAK,EAAE,MAAM,EACX,MAAM,wBACR,CAAC;CACH,GACF,CAAC;CAEH,MAAM,2BAA2B,cAC9B,SAAS,0BAA0B,CAAC,CACpC,UAAU,EACT,SAAS,OAAY;EACnB,IAAI,EAAE,OAAO;EACb,IAAI,EAAE,OAAO;EACb,IAAI,EAAE,OAAO;EACb,KAAK,EAAE,OAAO;EACd,IAAI,EAAE,OAAO;EACb,KAAK,EAAE,OAAO;EACd,IAAI,EAAE,WAAW;EACjB,OAAO,EAAE,WAAW;EACpB,MAAM,EAAE,OAAO;EACf,OAAO,EAAE,OAAO;EAChB,SAAS,EAAE,OAAO;EAClB,UAAU,EAAE,OAAO;EACnB,QAAQ,EAAE,QAAQ;EAClB,WAAW,EAAE,QAAQ;EACrB,eAAe,EAAE,WAAW;EAC5B,gBAAgB,EAAE,WAAW;EAC7B,eAAe,EAAE,WAAW;EAC5B,KAAK,EAAE,MAAM,EACX,MAAM,CAAC,wBAAwB,EACjC,CAAC;EACD,IAAI,EAAE,MAAM,EACV,MAAM,CAAC,wBAAwB,EACjC,CAAC;EACD,KAAK,EAAE,MAAM,EACX,MAAM,yBACR,CAAC;CACH,GACF,CAAC;CAEH,MAAM,yBAAyB,cAC5B,SAAS,wBAAwB,CAAC,CAClC,UAAU,EACT,SAAS,OAAY;EACnB,IAAI,EAAE,MAAM,EAAE,MAAM,OAAO,CAAC;EAC5B,IAAI,EAAE,MAAM,EAAE,MAAM,OAAO,CAAC;EAC5B,IAAI,EAAE,MAAM,EAAE,MAAM,OAAO,CAAC;EAC5B,KAAK,EAAE,MAAM,EAAE,MAAM,OAAO,CAAC;EAC7B,IAAI,EAAE,MAAM,EAAE,MAAM,OAAO,CAAC;EAC5B,KAAK,EAAE,MAAM,EAAE,MAAM,OAAO,CAAC;EAC7B,IAAI,EAAE,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,CAAC;EAC9B,OAAO,EAAE,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,CAAC;EACjC,MAAM,EAAE,OAAO;EACf,OAAO,EAAE,OAAO;EAChB,SAAS,EAAE,OAAO;EAClB,UAAU,EAAE,OAAO;EACnB,QAAQ,EAAE,QAAQ;EAClB,WAAW,EAAE,QAAQ;EACrB,eAAe,EAAE,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,CAAC;EACzC,gBAAgB,EAAE,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,CAAC;EAC1C,eAAe,EAAE,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,CAAC;EACzC,KAAK,EAAE,MAAM,EACX,MAAM,CAAC,sBAAsB,EAC/B,CAAC;EACD,IAAI,EAAE,MAAM,EACV,MAAM,CAAC,sBAAsB,EAC/B,CAAC;EACD,KAAK,EAAE,MAAM,EACX,MAAM,uBACR,CAAC;CACH,GACF,CAAC;CAEH,MAAM,4BAA4B,cAC/B,SAAS,2BAA2B,CAAC,CACrC,UAAU,EACT,SAAS,OAAY;EACnB,IAAI,EAAE,QAAQ;EACd,IAAI,EAAE,QAAQ;EACd,IAAI,EAAE,YAAY;EAClB,OAAO,EAAE,YAAY;EACrB,QAAQ,EAAE,QAAQ;EAClB,WAAW,EAAE,QAAQ;EACrB,eAAe,EAAE,YAAY;EAC7B,gBAAgB,EAAE,YAAY;EAC9B,eAAe,EAAE,YAAY;EAC7B,KAAK,EAAE,MAAM,EACX,MAAM,CAAC,yBAAyB,EAClC,CAAC;EACD,IAAI,EAAE,MAAM,EACV,MAAM,CAAC,yBAAyB,EAClC,CAAC;EACD,KAAK,EAAE,MAAM,EACX,MAAM,0BACR,CAAC;CACH,GACF,CAAC;CAEH,MAAM,uBAAuB,cAC1B,SAAS,sBAAsB,CAAC,CAChC,UAAU,EACT,SAAS,OAAY;EACnB,IAAI,EAAE,GAAG;EACT,IAAI,EAAE,GAAG;EACT,IAAI,EAAE,GAAG;EACT,KAAK,EAAE,GAAG;EACV,IAAI,EAAE,GAAG;EACT,KAAK,EAAE,GAAG;EACV,IAAI,EAAE,OAAO;EACb,OAAO,EAAE,OAAO;EAChB,MAAM,EAAE,OAAO;EACf,OAAO,EAAE,OAAO;EAChB,SAAS,EAAE,OAAO;EAClB,UAAU,EAAE,OAAO;EACnB,QAAQ,EAAE,QAAQ;EAClB,WAAW,EAAE,QAAQ;EACrB,eAAe,EAAE,OAAO;EACxB,gBAAgB,EAAE,OAAO;EACzB,eAAe,EAAE,OAAO;EACxB,KAAK,EAAE,MAAM,EACX,MAAM,CAAC,oBAAoB,EAC7B,CAAC;EACD,IAAI,EAAE,MAAM,EACV,MAAM,CAAC,oBAAoB,EAC7B,CAAC;EACD,KAAK,EAAE,MAAM,EACX,MAAM,qBACR,CAAC;CACH,GACF,CAAC;CAEH,MAAM,yBAAyB,cAC5B,SAAS,wBAAwB,CAAC,CAClC,UAAU,EACT,SAAS,OAAY;EACnB,IAAI,EAAE,MAAM;GAAE,MAAM;GAAQ,UAAU;EAAM,CAAC;EAC7C,IAAI,EAAE,MAAM;GAAE,MAAM;GAAQ,UAAU;EAAM,CAAC;EAC7C,IAAI,EAAE,MAAM;GAAE,MAAM,CAAC,MAAM;GAAG,UAAU;EAAM,CAAC;EAC/C,OAAO,EAAE,MAAM;GAAE,MAAM,CAAC,MAAM;GAAG,UAAU;EAAM,CAAC;EAClD,QAAQ,EAAE,QAAQ;EAClB,WAAW,EAAE,QAAQ;EACrB,eAAe,EAAE,MAAM;GAAE,MAAM,CAAC,MAAM;GAAG,UAAU;EAAM,CAAC;EAC1D,gBAAgB,EAAE,MAAM;GAAE,MAAM,CAAC,MAAM;GAAG,UAAU;EAAM,CAAC;EAC3D,eAAe,EAAE,MAAM;GAAE,MAAM,CAAC,MAAM;GAAG,UAAU;EAAM,CAAC;EAC1D,KAAK,EAAE,MAAM,EACX,MAAM,CAAC,sBAAsB,EAC/B,CAAC;EACD,IAAI,EAAE,MAAM,EACV,MAAM,CAAC,sBAAsB,EAC/B,CAAC;EACD,KAAK,EAAE,MAAM,EACX,MAAM,uBACR,CAAC;CACH,GACF,CAAC;CAEH,MAAM,2BAA2B,cAC9B,SAAS,0BAA0B,CAAC,CACpC,UAAU,EACT,SAAS,OAAY;EACnB,IAAI,EAAE,MAAM;GAAE,MAAM;GAAU,UAAU;EAAM,CAAC;EAC/C,IAAI,EAAE,MAAM;GAAE,MAAM;GAAU,UAAU;EAAM,CAAC;EAC/C,IAAI,EAAE,MAAM;GAAE,MAAM;GAAU,UAAU;EAAM,CAAC;EAC/C,KAAK,EAAE,MAAM;GAAE,MAAM;GAAU,UAAU;EAAM,CAAC;EAChD,IAAI,EAAE,MAAM;GAAE,MAAM;GAAU,UAAU;EAAM,CAAC;EAC/C,KAAK,EAAE,MAAM;GAAE,MAAM;GAAU,UAAU;EAAM,CAAC;EAChD,IAAI,EAAE,MAAM;GAAE,MAAM,CAAC,QAAQ;GAAG,UAAU;EAAM,CAAC;EACjD,OAAO,EAAE,MAAM;GAAE,MAAM,CAAC,QAAQ;GAAG,UAAU;EAAM,CAAC;EACpD,QAAQ,EAAE,QAAQ;EAClB,WAAW,EAAE,QAAQ;EACrB,KAAK,EAAE,MAAM,EAAE,MAAM,CAAC,wBAAwB,EAAE,CAAC;EACjD,IAAI,EAAE,MAAM,EAAE,MAAM,CAAC,wBAAwB,EAAE,CAAC;EAChD,KAAK,EAAE,MAAM,EAAE,MAAM,yBAAyB,CAAC;CACjD,GACF,CAAC;CAEH,MAAM,6BAA6B,cAChC,SAAS,4BAA4B,CAAC,CACtC,UAAU,EACT,SAAS,OAAY;EACnB,IAAI,EAAE,MAAM;GAAE,MAAM;GAAY,UAAU;EAAM,CAAC;EACjD,IAAI,EAAE,MAAM;GAAE,MAAM;GAAY,UAAU;EAAM,CAAC;EACjD,IAAI,EAAE,MAAM;GAAE,MAAM;GAAY,UAAU;EAAM,CAAC;EACjD,KAAK,EAAE,MAAM;GAAE,MAAM;GAAY,UAAU;EAAM,CAAC;EAClD,IAAI,EAAE,MAAM;GAAE,MAAM;GAAY,UAAU;EAAM,CAAC;EACjD,KAAK,EAAE,MAAM;GAAE,MAAM;GAAY,UAAU;EAAM,CAAC;EAClD,IAAI,EAAE,MAAM;GAAE,MAAM,CAAC,UAAU;GAAG,UAAU;EAAM,CAAC;EACnD,OAAO,EAAE,MAAM;GAAE,MAAM,CAAC,UAAU;GAAG,UAAU;EAAM,CAAC;EACtD,QAAQ,EAAE,QAAQ;EAClB,WAAW,EAAE,QAAQ;EACrB,eAAe,EAAE,MAAM;GAAE,MAAM,CAAC,UAAU;GAAG,UAAU;EAAM,CAAC;EAC9D,gBAAgB,EAAE,MAAM;GAAE,MAAM,CAAC,UAAU;GAAG,UAAU;EAAM,CAAC;EAC/D,eAAe,EAAE,MAAM;GAAE,MAAM,CAAC,UAAU;GAAG,UAAU;EAAM,CAAC;EAC9D,KAAK,EAAE,MAAM,EAAE,MAAM,CAAC,0BAA0B,EAAE,CAAC;EACnD,IAAI,EAAE,MAAM,EAAE,MAAM,CAAC,0BAA0B,EAAE,CAAC;EAClD,KAAK,EAAE,MAAM,EAAE,MAAM,2BAA2B,CAAC;CACnD,GACF,CAAC;AACL;;;ACrYA,MAAa,aAAa;;;ACX1B,MAAa,kBAAkB;AAI/B,IAAa,uBAAb,cAEU,WAAkB;CAC1B;CACA;CACA;CAMA,gCAAwB,IAAI,QAG1B;CAEF,UACE,SACA,QACsB;EACtB,IAAI,aAAa,KAAK,cAAc,IAAI,OAAiB;EACzD,IAAI,CAAC,YAAY;GACf,6BAAa,IAAI,IAAI;GACrB,KAAK,cAAc,IAAI,SAAmB,UAAU;EACtD;EAEA,IAAI,SAAS,WAAW,IAAI,MAAM;EAClC,IAAI,CAAC,QAAQ;GAEX,MAAM,kBAAkB,OAAO,WAC3B,OAAO,SAAS,EAAE,QAAQ,CAAC,IAC3B,KAAA;GAEJ,SAAS,IAAI,WACX,OAAO,aAAa;IAClB,MAAM,aAAa,kBACf,MAAM,kBACN,KAAA;IACJ,MAAM,UAAU,MAAM,OAAO,OAAO;KAClC;KACU;KACV;IACF,CAAQ;IACR,MAAM,aAAa,IAAI,IAAI,OAAO;IAClC,OAAO,SAAS,KAAK,WACnB,WAAW,IAAI,MAAM,IAAI,SAAS,IACpC;GACF,GAGA,EAAE,OAAO,MAAM,CACjB;GACA,WAAW,IAAI,QAAQ,MAAM;EAC/B;EAEA,OAAO;CACT;CAEA,aAAsB,YAA8B;EAClD,KAAK,SAAS,KAAK,QAAQ,QAAQ,MAAM;EACzC,KAAK,gBAAgB,KAAK,QAAQ,QAAQ,MAAM;EAChD,KAAK,SAAS,KAAK,QAAQ,QAAQ,QAAQ,UACvC,KAAK,QAAQ,QAAQ,OAAO,SAC5B,KAAA;EACJ,OAAO;CACT;CAEA,YACE,UACA,aACyD;EACzD,OAAO,OAAO,QAAQ,MAAM,SAAS,SAAS;GAC5C,IAAI;GACJ,MAAM,YAAY,aAAa;GAE/B,IAAI,UAAU,SAAS,QACrB,UACE,UAAU,MAAM,IAAI,cAAc,cAAc;QAC7C,IAAI,UAAU,SAAS,UAC5B,UAAU,UAAU,IAAI,cAAc,cAAc;GAGtD,IAAI,CAAC,WAAW,CAAC,MAAM,QAAQ,OAAO,KAAK,QAAQ,WAAW,GAE5D,OAAO,SAAS,QAAQ,MAAM,SAAS,IAAI;GAG7C,MAAM,aAAa,OAAO,SAAgB;IACxC,MAAM,aAAa,MAAM,QAAQ,OAAO,IAAI,UAAU,CAAC,OAAO;IAC9D,MAAM,aAAa,iBAAiB,WAAW,MAAM;IAErD,MAAM,UAAU,WAAW,KAAK,WAC9B,KAAK,UAAU,SAAS,MAAwB,CAClD;IAEA,IAAI;IAEJ,IAAI,KAAK,UAAU,KAAK,eACtB,WAAW,MAAM,KAAK,OAAO,gBAC3B,yBACA,OAAO,SAAS;KACd,KAAK,aAAa,sBAAsB,YAAY,IAAI;KACxD,IAAI;MACF,OAAO,MAAM,SAAS,QAAQ,MAAM,SAAS,IAAI;KACnD,UAAU;MACR,KAAK,IAAI;KACX;IACF,CACF;SAEA,WAAW,MAAM,SAAS,QAAQ,MAAM,SAAS,IAAI;IAGvD,MAAM,WAAkB,MAAM,QAAQ,QAAQ,IAAI,WAAW,CAAC,QAAQ;IAItE,MAAM,mBAAmB,MAAM,QAAQ,IACrC,QAAQ,KAAK,WACX,QAAQ,IAAI,SAAS,KAAK,WAAW,OAAO,KAAK,MAAM,CAAC,CAAC,CAC3D,CACF;IAEA,MAAM,UAAU,SAAS,QAAQ,GAAG,UAClC,iBAAiB,MAAM,YAAY,QAAQ,UAAU,IAAI,CAC3D;IAEA,MAAM,aAAa,mBAAmB,QAAQ,MAAM;IACpD,KAAK,QAAQ,MACX;KACE,sBAAsB,YAAY;KAClC,iBAAiB,WAAW;KAC5B,mBAAmB,QAAQ;IAC7B,GACA,yBACF;IAGA,IAAI,MAAM,QAAQ,QAAQ,GACxB,OAAO;IAKT,OAAO,QAAQ,MAAM;GACvB;GAEA,IAAI,KAAK,UAAU,KAAK,eACtB,OAAO,KAAK,OAAO,gBACjB,uBACA,OAAO,SAAS;IACd,KAAK,aAAa,sBAAsB,YAAY,IAAI;IACxD,IAAI;KACF,OAAO,MAAM,WAAW,IAAI;IAC9B,SAAS,OAAO;KACd,KAAK,QAAQ,MACX;MACE,sBAAsB,YAAY;MAClC,GAAG,cAAc,KAAK;KACxB,GACA,sBACF;KACA,MAAM;IACR,UAAU;KACR,KAAK,IAAI;IACX;GACF,CACF;QAEA,IAAI;IACF,OAAO,MAAM,WAAW;GAC1B,SAAS,OAAO;IACd,KAAK,QAAQ,MACX;KACE,sBAAsB,YAAY;KAClC,GAAG,cAAc,KAAK;IACxB,GACA,sBACF;IACA,MAAM;GACR;EAEJ;CACF;AACF;AAEA,IAAI,aAAa;AACjB,SAAgB,+BAA+B;CAC7C,IAAI,CAAC,YAAY;EACf,cAAc,eAAe,YAAY,oBAAoB;EAC7D,aAAa;CACf;AACF;;;AC7KA,MAAa,uBAMX,EACA,IACA,QACA,cACA,MACA,aAGI;CACJ,MAAM,aACJ,MAAM,WAAW,KAAK,SAClB,2BAA2B,KAAK,QAAQ,KAAK,OAAO,IACpD,KAAA;CAEN,6BAA6B;CAC7B,MAAM,gBAAgB,IAAI,cAqCvB;EACD,GAAG;EACH,SAAS;GACP;GACA;GACA;GACA;GACA,GAAI,cAAc,WAAW,CAAC;EAChC;EACA,SAAS;GACP,QAAQ;GACR,WAAW,GAAG,EAAE;GAChB,eAAe,OAAO;IAEpB,MAAM,UAAU,QAAQ,KAAK,IACzB,OAAO,OAAO,gBAAgB,KAAc,CAAC,IAC7C,CAAC;IACL,OAAO;KACL;KACA,aAAa,QAAQ,QAAQ,MAAW,EAAE,OAAO;IACnD;GACF;EACF;EACA,oBAAoB,EAClB,GAAG,8BAA8B,MAAM,aAAa;GAClD,OAAO,OAAO,UAAU,IAAI;EAC9B,CAAC,EACH;EACA,yBAAyB;EACzB,SAAS;GACP,SACE,MAAM,WAAW,QAAQ,WACpB,WAAW,YAAY,MAAM,UACxB;GACZ,OAAO,UAAU,SAAS,WAAW;IACnC,IAAI,IAAI,aAAa,WAAW,UAAU,OAAO,IAAI;IACrD,IAAI,QAAQ,SAAS;KACnB,MAAM,MAAM,OAAO;KACnB,IAAI,aAAa,IAAI,OAAO,aAAa;MACvC,IAAI,OACF,IAAI,MACF;OACE,sBAAsB,OAAO;OAC7B,uBAAuB,OAAO;OAC9B,aAAa;OACb,GAAG,cAAc,KAAK;MACxB,GACA,iBACF;WAEA,IAAI,MACF;OACE,sBAAsB,OAAO;OAC7B,uBAAuB,OAAO;OAC9B,aAAa;MACf,GACA,oBACF;KAEJ,CAAC;IACH;IACA,OAAO;GACT;EACF;EACA;EACA;CACF,CAAC;CAED,cAAc,cAAc,QAAQ,YAAY;CAChD,cAAc,cAAc,QAAQ,YAAY;CAChD,cAAc,cAAc,YAAY,mBAAmB;CAC3D,cAAc,cAAc,UAAU,cAAc;CACpD,cAAc,cAAc,SAAS,YAAY;CACjD,+BAA+B,aAAa;CAE5C,cAAc,UAAU,CAAC,CAAC;CAC1B,cAAc,iBAAiB,CAAC,CAAC;CACjC,cAAc,aAAa,CAAC,CAAC;CAE7B,OAAO,EAAE,cAAc;AACzB;;;AC1IA,MAAa,UAQX,gBASG;CACH,IAAI,CAAC,YAAY,GAAG,EAAE,WACpB,MAAM,IAAI,YAAY;;;;;;;;;;;CAWzB;CAGC,IACE,CAAC,YAAY,UACb,OAAO,YAAY,WAAW,YAC9B,OAAO,KAAK,YAAY,MAAM,CAAC,CAAC,WAAW,GAE3C,MAAM,IAAI,YAAY;;;;;;;;;;;CAWzB;CAIC,IAAI,CAAC,YAAY,SACf,YAAY,UAAU;EAAC;EAAQ;EAAU;CAAQ;CAGnD,IAAI,YAAY,iBAAiB,KAAA,GAC/B,YAAY,eAAe;CAG7B,IAAI,YAAY,QAAQ,SACtB,uBAAuB,WAAW;CAGpC,IAAI,YAAY,MAAM,WAAW,CAAC,YAAY,KAAK,QACjD,YAAY,KAAK,SAAS,MAAM,UAC9B,kBACAC,OACF;CAGF,MAAM,iBAAiB,qBAMrB,WAAW;CAEb,MAAM,UAAU,sBAMd;EACA,GAAG;EACH;CACF,CAAC;CAED,MAAM,EAAE,oBAAoB,WAAW,qBAMrC,EACA,GAAG,YACL,CAAC;CAED,MAAM,EAAE,kBAAkB,oBAMxB;EAAE,GAAG;EAAa;CAAO,CAAC;CAE5B,MAAM,QAAQ,sBAQZ;EACA,GAAG;EACH;CACF,CAAC;CAED,MAAM,WAAW,0BAMf;EACA,GAAG;EACH;EACA,iBAAiB;CACnB,CAAC;CAED,MAAM,WAAW,0BAMf;EACA,GAAG;EACH;CACF,CAAC;CAED,MAAM,SAAS,wBAOb;EACA,GAAG;EACH;EACA;EACA,qBAAqB;EACrB,qBAAqB;EACrB,iBAAiB;EACjB;CACF,CAAC;CAED,MAAM,QAAQ,uBAOZ;EACA,GAAG;EACH;EACA,qBAAqB;EACrB,qBAAqB;EACrB;CACF,CAAC;CAED,MAAM,aAAa,4BAA4B;EAC7C,GAAG;EACH;EACA,qBAAqB;EACrB;CACF,CAAC;CAED,MAAM,cAAc,WAAW;EAC7B,IAAI;EACJ,IAAI;GACF,MAAM,cAAc,SAAS;EAC/B,SAAS,GAAQ;GAEf,MAAM,eADc,GAAG,WAAW,OAAO,CAAC,EAAA,CAClB,MACtB,2CACF;GACA,IAAI,aACF,MAAM,IAAI,YACR,8CAA8C,YAAY,GAAG,0FACgB,YAAY,GAAG,iCAE9F;GAEF,MAAM;EACR;EAEA,MAAM,WAAW,IAAI,gBAAgB;EACrC,MAAM,eAAe,IAAI,oBAAoB;EAC7C,MAAM,gBACJ,YAAY,OAAO,KAAK,SAAS,UAAU,CAAC,CAAC,CAAC,WAAW;EAC3D,MAAM,oBACJ,gBAAgB,OAAO,KAAK,aAAa,UAAU,CAAC,CAAC,CAAC,WAAW;EAEnE,IAAI,CAAC,iBAAiB,CAAC,mBAAmB,OAAO;EAEjD,MAAM,SAAS,IAAI,SAAS;EAC5B,MAAM,gBAAgB,OAAO,MAAM,QAAQ,MAAM;GAC/C,IAAI,iBAAiB,MAAM,UAAU,OAAO;GAC5C,IAAI,qBAAqB,MAAM,cAAc,OAAO;GACpD,OAAO;EACT,CAAC;EACD,OAAO,IAAI,cAAc;GACvB,GAAG;GACH,UAAU,gBAAgB,KAAA,IAAY,OAAO;GAC7C,cAAc,oBAAoB,KAAA,IAAY,OAAO;GACrD,OAAO;EACT,CAAC;CACH,CAAC;CAED,MAAMC,gBACJ,SAsBG;EACH,MAAM,gBACJ,MAAM,iBAAiB,SAAS,KAAK,aAAa;EAEpD,OAAOC,WAA+B;GACpC,GAAG;GACH,UAAU;GACV,QAAQ,YAAY;GACpB;GACA,SAAS;IACP,GAAI,MAAM,WAAW,CAAC;IACtB,GAAI,gBACA,CAAC,IACD,CAAC,wBAAwB,GAAG,mBAAmB,MAAM,WAAW,CAAC;IACrE,YAAY,MAAM,WAAW,YAAY,QAAQ,UAC5C,EAGC,YAAY,EAAE,cAAc,gBAAgB;KAC1C,aACE,mBACE,WACA,WACF,CACF;IACF,EACF,IACA;GACN,CAAC,CAAC,OAAO,OAAO;EAClB,CAAC;CACH;CAEA,MAAM,aAAa,OACjB,SACG;EACH,MAAM,EAAE,SAAS,cAAc,MAAM,OAAO;EAC5C,IAAI,KAAK,SACP,MAAM,KAAK,SAAS,sBAAsB;EAE5C,IAAI,KAAK,cAAc;GACrB,MAAM,kBAAkB,KAAK;GAC7B,KAAK,gBAAgB,WAAW;IAC9B,MAAM,OAAO,MAAM,cAAc;IAEjC,KAAK,MAAM,SAAS,QAClB,MAAM,gBAAgB,KAAK;IAE7B,MAAM,UAAU,EAAE,MAAM,eAAe,MAAM,CAAC;IAC9C,OAAO,gBAAgB,MAAM;GAC/B;EACF;EACA,OAAO,UAAU;GACf,GAAG;GACH,QAAQ,YAAY;GACpB;GACA,SAAS,mBACP,KAAK,WAAW,gBAChB,WACF;GACA,WAAW,qBACT,KAAK,aAAa,kBAClB,WACF;GACA,aAAa,QAAQ;IACnB,MAAM,OAAO,MAAM,cAAc;IAEjC,KAAK,MAAM,SAAS,QAClB,MAAM,gBAAgB,KAAK;IAE7B,MAAM,UAAU,EAAE,MAAM,eAAe,MAAM,CAAC;IAE9C,OAAO,IAAI,SAAS,OAAO,EAAE,CAAC,SAAS,EACrC,QAAQ,IACV,CAAC;GACH;EACF,CAAC;CACH;CAEA,MAAM,YAKJ,gBACA,MACA,GAAG,SACQ;EACX,OAAO,eACL;GACE,GAAG;GACH,QAAQ,YAAY;GACpB;GACA,SAAS,mBACN,KAAa,WAAW,gBACzB,WACF;GACA,WAAW,qBACR,KAAa,aAAa,kBAC3B,WACF;EACF,GACA,GAAG,IACL;CACF;CAaA,OAAO;;;;;;;;;;;;;;;;;EAiBL;;;;EAIA;;;;;;;;;;;;;;;EAeA,YAAA;;;;;;;;;;;;;;EAcA;;;;;;;;;;;;;;;;;;;;EAoBA;;;;EAIA;;;;EAIA;;;;EAIA;;;;;EAKA;;;;EAIA,QAAQ;;;;;;EAMR;;;;;EAKA,eAjHoB,yBAMpB;GACA,GAAG;GACH;EACF,CAwGc;;;;EAIZ;;;;;;EAMA,aAAa;CACf;AACF"}
|