Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions TODO.md
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,7 @@
- [x] Custom table name
- [x] Custom field name
- [ ] Strict undefined checks
- [ ] DbNull vs JsonNull
- [ ] Benchmark
- [ ] Plugin
- [ ] Post-mutation hooks should be called after transaction is committed
Expand Down
102 changes: 56 additions & 46 deletions packages/runtime/src/client/crud-types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ import type {
NullableIf,
Optional,
OrArray,
Simplify,
ValueOfPotentialTuple,
WrapType,
XOR,
Expand Down Expand Up @@ -157,6 +158,14 @@ export type ModelResult<
Array
>;

export type SimplifiedModelResult<
Schema extends SchemaDef,
Model extends GetModels<Schema>,
Args extends SelectIncludeOmit<Schema, Model, boolean>,
Optional = false,
Array = false,
> = Simplify<ModelResult<Schema, Model, Args, Optional, Array>>;

export type BatchResult = { count: number };

//#endregion
Expand Down Expand Up @@ -215,11 +224,13 @@ type PrimitiveFilter<T extends string, Nullable extends boolean> = T extends 'St
? BooleanFilter<Nullable>
: T extends 'DateTime'
? DateTimeFilter<Nullable>
: T extends 'Json'
? 'Not implemented yet' // TODO: Json filter
: never;
: T extends 'Bytes'
? BytesFilter<Nullable>
: T extends 'Json'
? 'Not implemented yet' // TODO: Json filter
: never;

export type CommonPrimitiveFilter<DataType, T extends BuiltinType, Nullable extends boolean> = {
type CommonPrimitiveFilter<DataType, T extends BuiltinType, Nullable extends boolean> = {
equals?: NullableIf<DataType, Nullable>;
in?: DataType[];
notIn?: DataType[];
Expand Down Expand Up @@ -255,6 +266,7 @@ export type BytesFilter<Nullable extends boolean> =
notIn?: Uint8Array[];
not?: BytesFilter<Nullable>;
};

export type BooleanFilter<Nullable extends boolean> =
| NullableIf<boolean, Nullable>
| {
Expand Down Expand Up @@ -321,14 +333,14 @@ export type WhereUniqueInput<Schema extends SchemaDef, Model extends GetModels<S
Extract<keyof GetModel<Schema, Model>['uniqueFields'], string>
>;

type OmitFields<Schema extends SchemaDef, Model extends GetModels<Schema>> = {
export type OmitInput<Schema extends SchemaDef, Model extends GetModels<Schema>> = {
[Key in NonRelationFields<Schema, Model>]?: true;
};

export type SelectIncludeOmit<Schema extends SchemaDef, Model extends GetModels<Schema>, AllowCount extends boolean> = {
select?: Select<Schema, Model, AllowCount, boolean>;
include?: Include<Schema, Model>;
omit?: OmitFields<Schema, Model>;
select?: SelectInput<Schema, Model, AllowCount, boolean>;
include?: IncludeInput<Schema, Model>;
omit?: OmitInput<Schema, Model>;
};

type Distinct<Schema extends SchemaDef, Model extends GetModels<Schema>> = {
Expand All @@ -339,14 +351,14 @@ type Cursor<Schema extends SchemaDef, Model extends GetModels<Schema>> = {
cursor?: WhereUniqueInput<Schema, Model>;
};

type Select<
export type SelectInput<
Schema extends SchemaDef,
Model extends GetModels<Schema>,
AllowCount extends boolean,
AllowCount extends boolean = true,
AllowRelation extends boolean = true,
> = {
[Key in NonRelationFields<Schema, Model>]?: true;
} & (AllowRelation extends true ? Include<Schema, Model> : {}) & // relation fields
} & (AllowRelation extends true ? IncludeInput<Schema, Model> : {}) & // relation fields
// relation count
(AllowCount extends true ? { _count?: SelectCount<Schema, Model> } : {});

Expand All @@ -362,7 +374,7 @@ type SelectCount<Schema extends SchemaDef, Model extends GetModels<Schema>> =
};
};

type Include<Schema extends SchemaDef, Model extends GetModels<Schema>> = {
export type IncludeInput<Schema extends SchemaDef, Model extends GetModels<Schema>> = {
[Key in RelationFields<Schema, Model>]?:
| boolean
| FindArgs<
Expand Down Expand Up @@ -431,7 +443,7 @@ type RelationFilter<

//#region Field utils

export type MapFieldType<
type MapFieldType<
Schema extends SchemaDef,
Model extends GetModels<Schema>,
Field extends GetFields<Schema, Model>,
Expand All @@ -443,7 +455,7 @@ type MapFieldDefType<Schema extends SchemaDef, T extends Pick<FieldDef, 'type' |
T['array']
>;

export type OptionalFieldsForCreate<Schema extends SchemaDef, Model extends GetModels<Schema>> = keyof {
type OptionalFieldsForCreate<Schema extends SchemaDef, Model extends GetModels<Schema>> = keyof {
[Key in GetFields<Schema, Model> as FieldIsOptional<Schema, Model, Key> extends true
? Key
: FieldHasDefault<Schema, Model, Key> extends true
Expand Down Expand Up @@ -475,14 +487,14 @@ type OppositeRelation<
: never
: never;

export type OppositeRelationFields<
type OppositeRelationFields<
Schema extends SchemaDef,
Model extends GetModels<Schema>,
Field extends GetFields<Schema, Model>,
Opposite = OppositeRelation<Schema, Model, Field>,
> = Opposite extends RelationInfo ? (Opposite['fields'] extends string[] ? Opposite['fields'] : []) : [];

export type OppositeRelationAndFK<
type OppositeRelationAndFK<
Schema extends SchemaDef,
Model extends GetModels<Schema>,
Field extends GetFields<Schema, Model>,
Expand Down Expand Up @@ -521,6 +533,9 @@ export type FindArgs<
Distinct<Schema, Model> &
Cursor<Schema, Model>;

export type FindManyArgs<Schema extends SchemaDef, Model extends GetModels<Schema>> = FindArgs<Schema, Model, true>;
export type FindFirstArgs<Schema extends SchemaDef, Model extends GetModels<Schema>> = FindArgs<Schema, Model, false>;

export type FindUniqueArgs<Schema extends SchemaDef, Model extends GetModels<Schema>> = {
where?: WhereUniqueInput<Schema, Model>;
} & SelectIncludeOmit<Schema, Model, true>;
Expand All @@ -531,9 +546,9 @@ export type FindUniqueArgs<Schema extends SchemaDef, Model extends GetModels<Sch

export type CreateArgs<Schema extends SchemaDef, Model extends GetModels<Schema>> = {
data: CreateInput<Schema, Model>;
select?: Select<Schema, Model, true>;
include?: Include<Schema, Model>;
omit?: OmitFields<Schema, Model>;
select?: SelectInput<Schema, Model, true>;
include?: IncludeInput<Schema, Model>;
omit?: OmitInput<Schema, Model>;
};

export type CreateManyArgs<Schema extends SchemaDef, Model extends GetModels<Schema>> = CreateManyInput<Schema, Model>;
Expand All @@ -542,8 +557,8 @@ export type CreateManyAndReturnArgs<Schema extends SchemaDef, Model extends GetM
Schema,
Model
> & {
select?: Select<Schema, Model, false, false>;
omit?: OmitFields<Schema, Model>;
select?: SelectInput<Schema, Model, false, false>;
omit?: OmitInput<Schema, Model>;
};

type OptionalWrap<Schema extends SchemaDef, Model extends GetModels<Schema>, T extends object> = Optional<
Expand Down Expand Up @@ -633,20 +648,15 @@ type ConnectOrCreatePayload<
create: CreateInput<Schema, Model, Without>;
};

export type CreateManyInput<
Schema extends SchemaDef,
Model extends GetModels<Schema>,
Without extends string = never,
> = {
type CreateManyInput<Schema extends SchemaDef, Model extends GetModels<Schema>, Without extends string = never> = {
data: OrArray<Omit<CreateScalarPayload<Schema, Model>, Without> & Omit<CreateFKPayload<Schema, Model>, Without>>;
skipDuplicates?: boolean;
};

export type CreateInput<
Schema extends SchemaDef,
Model extends GetModels<Schema>,
Without extends string = never,
> = XOR<Omit<CreateWithFKInput<Schema, Model>, Without>, Omit<CreateWithRelationInput<Schema, Model>, Without>>;
type CreateInput<Schema extends SchemaDef, Model extends GetModels<Schema>, Without extends string = never> = XOR<
Omit<CreateWithFKInput<Schema, Model>, Without>,
Omit<CreateWithRelationInput<Schema, Model>, Without>
>;

type NestedCreateInput<
Schema extends SchemaDef,
Expand All @@ -670,9 +680,9 @@ type NestedCreateManyInput<
export type UpdateArgs<Schema extends SchemaDef, Model extends GetModels<Schema>> = {
data: UpdateInput<Schema, Model>;
where: WhereUniqueInput<Schema, Model>;
select?: Select<Schema, Model, true>;
include?: Include<Schema, Model>;
omit?: OmitFields<Schema, Model>;
select?: SelectInput<Schema, Model, true>;
include?: IncludeInput<Schema, Model>;
omit?: OmitInput<Schema, Model>;
};

export type UpdateManyArgs<Schema extends SchemaDef, Model extends GetModels<Schema>> = UpdateManyPayload<
Expand All @@ -684,8 +694,8 @@ export type UpdateManyAndReturnArgs<Schema extends SchemaDef, Model extends GetM
Schema,
Model
> & {
select?: Select<Schema, Model, false, false>;
omit?: OmitFields<Schema, Model>;
select?: SelectInput<Schema, Model, false, false>;
omit?: OmitInput<Schema, Model>;
};

type UpdateManyPayload<Schema extends SchemaDef, Model extends GetModels<Schema>, Without extends string = never> = {
Expand All @@ -698,12 +708,12 @@ export type UpsertArgs<Schema extends SchemaDef, Model extends GetModels<Schema>
create: CreateInput<Schema, Model>;
update: UpdateInput<Schema, Model>;
where: WhereUniqueInput<Schema, Model>;
select?: Select<Schema, Model, true>;
include?: Include<Schema, Model>;
omit?: OmitFields<Schema, Model>;
select?: SelectInput<Schema, Model, true>;
include?: IncludeInput<Schema, Model>;
omit?: OmitInput<Schema, Model>;
};

export type UpdateScalarInput<
type UpdateScalarInput<
Schema extends SchemaDef,
Model extends GetModels<Schema>,
Without extends string = never,
Expand Down Expand Up @@ -736,7 +746,7 @@ type ScalarUpdatePayload<
}
: never);

export type UpdateRelationInput<
type UpdateRelationInput<
Schema extends SchemaDef,
Model extends GetModels<Schema>,
Without extends string = never,
Expand All @@ -747,7 +757,7 @@ export type UpdateRelationInput<
Without
>;

export type UpdateInput<
type UpdateInput<
Schema extends SchemaDef,
Model extends GetModels<Schema>,
Without extends string = never,
Expand Down Expand Up @@ -803,9 +813,9 @@ type ToOneRelationUpdateInput<

export type DeleteArgs<Schema extends SchemaDef, Model extends GetModels<Schema>> = {
where: WhereUniqueInput<Schema, Model>;
select?: Select<Schema, Model, true>;
include?: Include<Schema, Model>;
omit?: OmitFields<Schema, Model>;
select?: SelectInput<Schema, Model, true>;
include?: IncludeInput<Schema, Model>;
omit?: OmitInput<Schema, Model>;
};

export type DeleteManyArgs<Schema extends SchemaDef, Model extends GetModels<Schema>> = {
Expand All @@ -824,7 +834,7 @@ export type CountArgs<Schema extends SchemaDef, Model extends GetModels<Schema>>
select?: CountAggregateInput<Schema, Model> | true;
};

export type CountAggregateInput<Schema extends SchemaDef, Model extends GetModels<Schema>> = {
type CountAggregateInput<Schema extends SchemaDef, Model extends GetModels<Schema>> = {
[Key in NonRelationFields<Schema, Model>]?: true;
} & { _all?: true };

Expand Down
17 changes: 9 additions & 8 deletions packages/runtime/src/client/crud/operations/base.ts
Original file line number Diff line number Diff line change
Expand Up @@ -181,17 +181,18 @@ export abstract class BaseOperationHandler<Schema extends SchemaDef> {
}

// select
if (args?.select) {
if (args && 'select' in args && args.select) {
// select is mutually exclusive with omit
query = this.buildFieldSelection(model, query, args?.select, model);
query = this.buildFieldSelection(model, query, args.select, model);
} else {
// include all scalar fields except those in omit
query = this.buildSelectAllScalarFields(model, query, args?.omit);
query = this.buildSelectAllScalarFields(model, query, (args as any)?.omit);
}

// include
if (args?.include) {
query = this.buildFieldSelection(model, query, args?.include, model);
if (args && 'include' in args && args.include) {
// note that 'omit' is handled above already
query = this.buildFieldSelection(model, query, args.include, model);
}

if (args?.cursor) {
Expand Down Expand Up @@ -1878,7 +1879,7 @@ export abstract class BaseOperationHandler<Schema extends SchemaDef> {
}

protected trimResult(data: any, args: SelectIncludeOmit<Schema, GetModels<Schema>, boolean>) {
if (!args.select) {
if (!('select' in args) || !args.select) {
return data;
}
return Object.keys(args.select).reduce((acc, field) => {
Expand All @@ -1890,9 +1891,9 @@ export abstract class BaseOperationHandler<Schema extends SchemaDef> {
protected needReturnRelations(model: string, args: SelectIncludeOmit<Schema, GetModels<Schema>, boolean>) {
let returnRelation = false;

if (args.include) {
if ('include' in args && args.include) {
returnRelation = Object.keys(args.include).length > 0;
} else if (args.select) {
} else if ('select' in args && args.select) {
returnRelation = Object.entries(args.select).some(([K, v]) => {
const fieldDef = this.requireField(model, K);
return fieldDef.relation && v;
Expand Down
1 change: 1 addition & 0 deletions packages/runtime/src/index.ts
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
export * from './client';
export type { JsonArray, JsonObject, JsonValue } from './utils/type-utils';
2 changes: 1 addition & 1 deletion packages/runtime/src/utils/type-utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ export type NullableIf<T, Condition extends boolean> = Condition extends true ?

export type PartialRecord<K extends string | number | symbol, T> = Partial<Record<K, T>>;

type _Preserve = Date | Function | Decimal | Uint8Array;
type _Preserve = Date | Function | Decimal | Uint8Array | JsonObject | JsonValue;
type _Depth = [never, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9];
export type Simplify<T, D extends number = 6> = D extends 0
? T
Expand Down
Loading