UNPKG

papr

Version:

MongoDB TypeScript-aware Models

159 lines (158 loc) 6.45 kB
import type { AlternativeType, ArrayElement, BitwiseFilter, BSONRegExp, BSONType, BSONTypeAlias, DeleteManyModel, DeleteOneModel, Document, IntegerType, Join, KeysOfAType, NumericType, OnlyFieldsOfType, PullAllOperator, PullOperator, PushOperator, ReplaceOneModel, SetFields, Timestamp, UpdateManyModel, UpdateOneModel, WithId } from 'mongodb'; import type { SchemaOptions } from './schema.ts'; import type { DocumentForInsert, NestedPaths, PropertyType } from './utils.ts'; export type PaprBulkWriteOperation<TSchema, TOptions extends SchemaOptions<TSchema>> = { deleteMany: Omit<DeleteManyModel<TSchema>, 'filter'> & { filter: PaprFilter<TSchema>; }; } | { deleteOne: Omit<DeleteOneModel<TSchema>, 'filter'> & { filter: PaprFilter<TSchema>; }; } | { replaceOne: Omit<ReplaceOneModel<TSchema>, 'filter'> & { filter: PaprFilter<TSchema>; }; } | { updateMany: Omit<UpdateManyModel<TSchema>, 'filter' | 'update'> & { filter: PaprFilter<TSchema>; update: PaprUpdateFilter<TSchema>; }; } | { updateOne: Omit<UpdateOneModel<TSchema>, 'filter' | 'update'> & { filter: PaprFilter<TSchema>; update: PaprUpdateFilter<TSchema>; }; } | { insertOne: { document: DocumentForInsert<TSchema, TOptions>; }; }; export type PaprFilter<TSchema> = Partial<WithId<TSchema>> | (PaprFilterConditions<WithId<TSchema>> & PaprRootFilterOperators<WithId<TSchema>>); export type PaprFilterConditions<TSchema> = { [Property in Join<NestedPaths<TSchema, []>, '.'>]?: PaprCondition<PropertyType<TSchema, Property>>; }; export interface PaprRootFilterOperators<TSchema> { $and?: PaprFilter<TSchema>[]; $nor?: PaprFilter<TSchema>[]; $or?: PaprFilter<TSchema>[]; $expr?: Record<string, any>; $text?: { $search: string; $language?: string; $caseSensitive?: boolean; $diacriticSensitive?: boolean; }; $where?: string | ((this: TSchema) => boolean); $comment?: Document | string; } export type PaprCondition<Type> = AlternativeType<Type> | PaprFilterOperators<AlternativeType<Type>>; export interface PaprFilterOperators<TValue> { $eq?: TValue; $gt?: TValue; $gte?: TValue; $in?: readonly TValue[]; $lt?: TValue; $lte?: TValue; $ne?: TValue; $nin?: readonly TValue[]; $not?: TValue extends string ? PaprFilterOperators<TValue> | RegExp : PaprFilterOperators<TValue>; /** * When `true`, `$exists` matches the documents that contain the field, * including documents where the field value is null. */ $exists?: boolean; $type?: BSONType | BSONTypeAlias; $expr?: Record<string, any>; $jsonSchema?: Record<string, any>; $mod?: TValue extends number ? [number, number] : never; $regex?: TValue extends string ? BSONRegExp | RegExp | string : never; $options?: TValue extends string ? string : never; $geoIntersects?: { $geometry: Document; }; $geoWithin?: Document; $near?: Document; $nearSphere?: Document; $maxDistance?: number; $all?: TValue extends readonly any[] ? readonly any[] : never; $elemMatch?: TValue extends readonly any[] ? Document : never; $size?: TValue extends readonly any[] ? number : never; $bitsAllClear?: BitwiseFilter; $bitsAllSet?: BitwiseFilter; $bitsAnyClear?: BitwiseFilter; $bitsAnySet?: BitwiseFilter; $rand?: Record<string, never>; } /** * Returns all dot-notation properties of a schema with their corresponding types. * * @example * { * foo: string; * 'nested.field': number; * } */ export type PaprAllProperties<TSchema> = { [Property in Join<NestedPaths<TSchema, []>, '.'>]?: PropertyType<TSchema, Property>; }; /** * Returns all array-specific element dot-notation properties of a schema with their corresponding types. * * https://www.mongodb.com/docs/v5.3/reference/operator/update/positional/#update-values-in-an-array * https://www.mongodb.com/docs/v5.3/reference/operator/update/positional-all/#update-all-elements-in-an-array * https://www.mongodb.com/docs/v5.3/reference/operator/update/positional-filtered/#update-all-array-elements-that-match-arrayfilters * * @example * { * 'numbersList.$': number; * 'numbersList.$[]': number; * 'numbersList.$[element]': number; * } */ export type PaprArrayElementsProperties<TSchema> = { [Property in `${KeysOfAType<PaprAllProperties<TSchema>, any[]>}.$${'' | `[${string}]`}`]?: ArrayElement<PropertyType<TSchema, Property extends `${infer Key}.$${string}` ? Key : never>>; }; /** * Returns all array-specific nested dot-notation properties of a schema without type lookup. * * https://www.mongodb.com/docs/v5.3/reference/operator/update/positional/#update-documents-in-an-array * https://www.mongodb.com/docs/v5.3/reference/operator/update/positional-all/#update-all-documents-in-an-array * https://www.mongodb.com/docs/v5.3/reference/operator/update/positional-filtered/#update-all-documents-that-match-arrayfilters-in-an-array * * @example * { * 'objectList.$.foo': any; * 'objectList.$[].foo': any; * 'objectList.$[element].foo': any; * } */ export type PaprArrayNestedProperties<TSchema> = { [Property in `${KeysOfAType<PaprAllProperties<TSchema>, Record<string, any>[]>}.$${'' | `[${string}]`}.${string}`]?: any; }; export type PaprMatchKeysAndValues<TSchema> = PaprAllProperties<TSchema> & PaprArrayElementsProperties<TSchema> & PaprArrayNestedProperties<TSchema>; export interface PaprUpdateFilter<TSchema> { $currentDate?: OnlyFieldsOfType<TSchema, Date | Timestamp, true | { $type: 'date' | 'timestamp'; }>; $inc?: OnlyFieldsOfType<TSchema, NumericType | undefined>; $min?: PaprMatchKeysAndValues<TSchema>; $max?: PaprMatchKeysAndValues<TSchema>; $mul?: OnlyFieldsOfType<TSchema, NumericType | undefined>; $rename?: Record<string, string>; $set?: PaprMatchKeysAndValues<TSchema>; $setOnInsert?: PaprMatchKeysAndValues<TSchema>; $unset?: OnlyFieldsOfType<TSchema, any, '' | 1 | true>; $addToSet?: SetFields<TSchema>; $pop?: OnlyFieldsOfType<TSchema, readonly any[], -1 | 1>; $pull?: PullOperator<TSchema>; $push?: PushOperator<TSchema>; $pullAll?: PullAllOperator<TSchema>; $bit?: OnlyFieldsOfType<TSchema, NumericType | undefined, { and: IntegerType; } | { or: IntegerType; } | { xor: IntegerType; }>; }