Files
zod-schema-class/src/makeSchemableClass.ts
Julien Valverdé aef4d23b92
All checks were successful
continuous-integration/drone/push Build is passing
Fixed default values
2024-01-17 18:45:00 +01:00

83 lines
2.4 KiB
TypeScript

import { AbstractClass, Class as ConcreteClass, Opaque } from "type-fest"
import { z } from "zod"
import { DefinedDefaultValuesTag } from "."
import { StaticMembers } from "./util"
export function makeSchemableClassFrom<
C extends AbstractClass<{
schema?: never
defaultValues?: never
}, []> & {
schema?: never
defaultValues?: never
},
SchemaT extends z.ZodRawShape,
SchemaUnknownKeys extends z.UnknownKeysParam,
SchemaCatchall extends z.ZodTypeAny,
Values extends {},
DefaultValues extends Partial<Values>,
>(
extend: C,
{ schema, defaultValues }: {
schema: z.ZodObject<SchemaT, SchemaUnknownKeys, SchemaCatchall, Values, Values>
defaultValues: Opaque<DefaultValues, DefinedDefaultValuesTag>
},
) {
type Class<T, Arguments extends unknown[]> = (
C extends ConcreteClass<any>
? ConcreteClass<T, Arguments>
: AbstractClass<T, Arguments>
)
return class extends (extend as unknown as ConcreteClass<any, []>) {
static readonly schema = schema
readonly schema = schema
static readonly defaultValues = defaultValues
readonly defaultValues = defaultValues
constructor(values: Values) {
super()
Object.assign(this, values)
}
} as unknown as (
Class<
InstanceType<C> &
{
readonly schema: z.ZodObject<SchemaT, SchemaUnknownKeys, SchemaCatchall, Values, Values>,
readonly defaultValues: DefaultValues,
} &
Values,
Parameters<(values: Values) => void>
> &
StaticMembers<C> &
{
readonly schema: z.ZodObject<SchemaT, SchemaUnknownKeys, SchemaCatchall, Values, Values>,
readonly defaultValues: DefaultValues,
}
)
}
export function makeSchemableClass<
SchemaT extends z.ZodRawShape,
SchemaUnknownKeys extends z.UnknownKeysParam,
SchemaCatchall extends z.ZodTypeAny,
Values extends {},
DefaultValues extends Partial<Values>,
>(
props: {
schema: z.ZodObject<SchemaT, SchemaUnknownKeys, SchemaCatchall, Values, Values>
defaultValues: Opaque<DefaultValues, DefinedDefaultValuesTag>
}
) {
return makeSchemableClassFrom(Object, props)
}