Revision 0.8.8 (#18)
* Reverse Syntax Mapping * Minor Optimizations * Documentation
This commit is contained in:
35
src/guard.ts
35
src/guard.ts
@@ -30,22 +30,25 @@ import * as t from '@sinclair/typebox'
|
||||
import * as v from 'valibot'
|
||||
import * as z from 'zod'
|
||||
|
||||
/** Structural Type for Syntax */
|
||||
export type SyntaxType = string
|
||||
/** Structural Type for TypeBox */
|
||||
export type TypeBoxType = t.TSchema
|
||||
/** Structural Type for Valibot */
|
||||
export type ValibotType = v.BaseSchema<any, any, v.BaseIssue<any>>
|
||||
/** Structural Type for Zod */
|
||||
export type ZodType = z.ZodTypeAny | z.ZodEffects<any>
|
||||
|
||||
// ------------------------------------------------------------------
|
||||
// Syntax
|
||||
// ------------------------------------------------------------------
|
||||
/** Structural Type for Syntax */
|
||||
export type SyntaxType = string
|
||||
|
||||
/** Returns true if the given value is a Syntax type */
|
||||
export function IsSyntax(value: unknown): value is string {
|
||||
return t.ValueGuard.IsString(value)
|
||||
}
|
||||
|
||||
// ------------------------------------------------------------------
|
||||
// TypeBox
|
||||
// ------------------------------------------------------------------
|
||||
/** Structural Type for TypeBox */
|
||||
export type TypeBoxType = t.TSchema
|
||||
|
||||
/** Returns true if the given value is a TypeBox type */
|
||||
export function IsTypeBox(type: unknown): type is t.TSchema {
|
||||
return t.KindGuard.IsSchema(type)
|
||||
@@ -53,9 +56,6 @@ export function IsTypeBox(type: unknown): type is t.TSchema {
|
||||
// ------------------------------------------------------------------
|
||||
// Valibot
|
||||
// ------------------------------------------------------------------
|
||||
/** Structural Type for Valibot */
|
||||
export type ValibotType = v.BaseSchema<any, any, v.BaseIssue<any>>
|
||||
|
||||
/** Returns true if the given value is a Valibot type */
|
||||
// prettier-ignore
|
||||
export function IsValibot(type: unknown): type is v.AnySchema {
|
||||
@@ -70,14 +70,6 @@ export function IsValibot(type: unknown): type is v.AnySchema {
|
||||
// ------------------------------------------------------------------
|
||||
// Zod
|
||||
// ------------------------------------------------------------------
|
||||
/** Structural Type for Zod */
|
||||
export type ZodType = z.ZodTypeAny | z.ZodEffects<any>
|
||||
|
||||
/** Returns true if the given value is a Zod type */
|
||||
// prettier-ignore
|
||||
export type TIsZod<Type extends unknown> = (
|
||||
Type extends z.ZodTypeAny ? true : false
|
||||
)
|
||||
/** Returns true if the given value is a Zod type */
|
||||
// prettier-ignore
|
||||
export function IsZod(type: unknown): type is z.ZodTypeAny {
|
||||
@@ -92,20 +84,25 @@ export function IsZod(type: unknown): type is z.ZodTypeAny {
|
||||
// ------------------------------------------------------------------
|
||||
// Signature
|
||||
// ------------------------------------------------------------------
|
||||
// (parameter, syntax, options)
|
||||
function Signature1(args: any[]) {
|
||||
return args.length === 3 && t.ValueGuard.IsObject(args[0]) && t.ValueGuard.IsString(args[1]) && t.ValueGuard.IsObject(args[2])
|
||||
}
|
||||
// (syntax, options)
|
||||
function Signature2(args: any[]) {
|
||||
return args.length === 2 && t.ValueGuard.IsString(args[0]) && t.ValueGuard.IsObject(args[1])
|
||||
}
|
||||
// (parameter, options)
|
||||
function Signature3(args: any[]) {
|
||||
return args.length === 2 && t.ValueGuard.IsObject(args[0]) && t.ValueGuard.IsString(args[1])
|
||||
}
|
||||
// (syntax | type)
|
||||
function Signature4(args: any[]) {
|
||||
return args.length === 1 && (t.ValueGuard.IsString(args[0]) || t.ValueGuard.IsObject(args[0]))
|
||||
}
|
||||
/** Resolve common mapping signature parameters */
|
||||
// prettier-ignore
|
||||
export function Signature(args: any[]): [parameter: Record<PropertyKey, object>, type: string | object, options: object] {
|
||||
// prettier-ignore
|
||||
return (
|
||||
Signature1(args) ? [args[0], args[1], args[2]] :
|
||||
Signature2(args) ? [{}, args[0], args[1]] :
|
||||
|
||||
@@ -38,6 +38,15 @@ export { type Static } from './static'
|
||||
// ------------------------------------------------------------------
|
||||
export * from './compile/compile'
|
||||
|
||||
// ------------------------------------------------------------------
|
||||
// Syntax
|
||||
// ------------------------------------------------------------------
|
||||
export * from './syntax/syntax-from-syntax'
|
||||
export * from './syntax/syntax-from-typebox'
|
||||
export * from './syntax/syntax-from-valibot'
|
||||
export * from './syntax/syntax-from-zod'
|
||||
export { type TSyntax, Syntax } from './syntax/syntax'
|
||||
|
||||
// ------------------------------------------------------------------
|
||||
// TypeBox
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
33
src/syntax/syntax-from-syntax.ts
Normal file
33
src/syntax/syntax-from-syntax.ts
Normal file
@@ -0,0 +1,33 @@
|
||||
/*--------------------------------------------------------------------------
|
||||
|
||||
@sinclair/typemap
|
||||
|
||||
The MIT License (MIT)
|
||||
|
||||
Copyright (c) 2024-2025 Haydn Paterson (sinclair) <haydn.developer@gmail.com>
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
|
||||
---------------------------------------------------------------------------*/
|
||||
|
||||
export type TSyntaxFromSyntax<Type extends string> = Type
|
||||
|
||||
export function SyntaxFromSyntax<Type extends string>(type: Type): TSyntaxFromSyntax<Type> {
|
||||
return type
|
||||
}
|
||||
365
src/syntax/syntax-from-typebox.ts
Normal file
365
src/syntax/syntax-from-typebox.ts
Normal file
@@ -0,0 +1,365 @@
|
||||
/*--------------------------------------------------------------------------
|
||||
|
||||
@sinclair/typemap
|
||||
|
||||
The MIT License (MIT)
|
||||
|
||||
Copyright (c) 2024-2025 Haydn Paterson (sinclair) <haydn.developer@gmail.com>
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
|
||||
---------------------------------------------------------------------------*/
|
||||
|
||||
import * as t from '@sinclair/typebox'
|
||||
|
||||
// ------------------------------------------------------------------
|
||||
// Characters
|
||||
// ------------------------------------------------------------------
|
||||
type TEmptyString = ''
|
||||
|
||||
type TAmpersand = '&'
|
||||
type TComma = ','
|
||||
type TPipe = '|'
|
||||
|
||||
const Ampersand = '&'
|
||||
const Comma = ','
|
||||
const Pipe = '|'
|
||||
|
||||
// ------------------------------------------------------------------
|
||||
// Delmited
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromDelimited<Values extends string[], Delimiter extends string, Result extends string = TEmptyString> = (
|
||||
Values extends [infer Left extends string, ...infer Right extends string[]]
|
||||
? Result extends TEmptyString
|
||||
? TFromDelimited<Right, Delimiter, Left>
|
||||
: TFromDelimited<Right, Delimiter, `${Result}${Delimiter} ${Left}`>
|
||||
: Result
|
||||
)
|
||||
function FromDelimited(values: string[], delimiter: string): string {
|
||||
return values.join(delimiter)
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Any
|
||||
// ------------------------------------------------------------------
|
||||
type TFromAny<_Type extends t.TAny> = 'any'
|
||||
function FromAny(_type: t.TSchema): string {
|
||||
return 'any'
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Array
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromArray<Type extends t.TSchema,
|
||||
Result extends string = `${TFromType<Type>}[]`
|
||||
> = Result
|
||||
function FromArray(type: t.TSchema): string {
|
||||
return `${type}[]`
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// BigInt
|
||||
// ------------------------------------------------------------------
|
||||
type TFromBigInt<_Type extends t.TBigInt> = 'bigint'
|
||||
function FromBigInt(_type: t.TSchema): string {
|
||||
return 'bigint'
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Boolean
|
||||
// ------------------------------------------------------------------
|
||||
type TFromBoolean<_Type extends t.TBoolean> = 'boolean'
|
||||
function FromBoolean(_type: t.TSchema): string {
|
||||
return 'boolean'
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Constructor
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromConstructor<Parameters extends t.TSchema[], InstanceType extends t.TSchema,
|
||||
MappedParameters extends string = TFromParameters<Parameters>,
|
||||
MappedInstanceType extends string = TFromType<InstanceType>
|
||||
> = `new ${MappedParameters} => ${MappedInstanceType}`
|
||||
// prettier-ignore
|
||||
function FromConstructor(parameters: t.TSchema[], instanceType: t.TSchema): string {
|
||||
const mappedParameters = FromParameters(parameters)
|
||||
const mappedInstanceType = FromType(instanceType)
|
||||
return `new ${mappedParameters} => ${mappedInstanceType}`
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Function
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromFunction<Parameters extends t.TSchema[], ReturnType extends t.TSchema,
|
||||
MappedParameters extends string = TFromParameters<Parameters>,
|
||||
MappedReturnType extends string = TFromType<ReturnType>
|
||||
> = `${MappedParameters} => ${MappedReturnType}`
|
||||
// prettier-ignore
|
||||
function FromFunction(parameters: t.TSchema[], returnType: t.TSchema): string {
|
||||
const mappedParameters = FromParameters(parameters)
|
||||
const mappedReturnType = FromType(returnType)
|
||||
return `${mappedParameters} => ${mappedReturnType}`
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Integer
|
||||
// ------------------------------------------------------------------
|
||||
type TFromInteger<_Type extends t.TInteger> = 'integer'
|
||||
function FromInteger(_type: t.TSchema): string {
|
||||
return 'integer'
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Intersect
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromIntersect<Types extends t.TSchema[], Result extends string[] = []> = (
|
||||
Types extends [infer Left extends t.TSchema, ...infer Right extends t.TSchema[]]
|
||||
? TFromIntersect<Right, [...Result, TFromType<Left>]>
|
||||
: `(${TFromDelimited<Result, ` ${TAmpersand}`>})`
|
||||
)
|
||||
function FromIntersect(types: t.TSchema[]): string {
|
||||
const result = types.map((type) => FromType(type))
|
||||
return `(${FromDelimited(result, ` ${Ampersand} `)})`
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Literal
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromLiteral<Value extends t.TLiteralValue,
|
||||
Result extends string = Value extends string ? `"${Value}"` : `${Value}`
|
||||
> = Result
|
||||
// prettier-ignore
|
||||
function FromLiteral(value: t.TLiteralValue): string {
|
||||
return t.ValueGuard.IsString(value) ? `"${value}"` : `${value}`
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Number
|
||||
// ------------------------------------------------------------------
|
||||
type TFromNumber<_Type extends t.TNumber> = 'number'
|
||||
function FromNumber(_type: t.TSchema): string {
|
||||
return 'number'
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Null
|
||||
// ------------------------------------------------------------------
|
||||
type TFromNull<_Type extends t.TNull> = 'null'
|
||||
function FromNull(_type: t.TSchema): string {
|
||||
return 'null'
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Object
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromObject<Properties extends t.TProperties,
|
||||
PropertyKeys extends PropertyKey[] = t.UnionToTuple<keyof Properties>,
|
||||
Delimited extends string[] = TFromProperties<PropertyKeys, Properties>,
|
||||
Result extends string = TFromDelimited<Delimited, TComma>
|
||||
> = `{ ${Result} }`
|
||||
function FromObject(properties: t.TProperties): string {
|
||||
const propertyKeys = globalThis.Object.getOwnPropertyNames(properties)
|
||||
const delimited = FromProperties(propertyKeys, properties)
|
||||
const result = FromDelimited(delimited, Comma)
|
||||
return `{ ${result} }`
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Parameters
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromParameters<Parameters extends t.TSchema[], Index extends string = '0', Result extends string[] = []> = (
|
||||
Parameters extends [infer Left extends t.TSchema, ...infer Right extends t.TSchema[]]
|
||||
? TFromParameters<Right, t.TIncrement<Index>, [...Result, `arg${Index}: ${TFromType<Left>}`]>
|
||||
: `(${TFromDelimited<Result, TComma>})`
|
||||
)
|
||||
function FromParameters(parameters: t.TSchema[]): string {
|
||||
const result = parameters.map((parameter, index) => `arg${index}: ${FromType(parameter)}`)
|
||||
return `(${FromDelimited(result, Comma)})`
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Property
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromProperty<Key extends string, Type extends t.TSchema,
|
||||
IsOptional extends boolean = Type extends t.TOptional<t.TSchema> ? true : false,
|
||||
IsReadonly extends boolean = Type extends t.TReadonly<t.TSchema> ? true : false,
|
||||
Mapped extends string = TFromType<Type>,
|
||||
Result = (
|
||||
[IsReadonly, IsOptional] extends [true, true] ? `readonly ${Key}?: ${Mapped}` :
|
||||
[IsReadonly, IsOptional] extends [false, true] ? `${Key}?: ${Mapped}` :
|
||||
[IsReadonly, IsOptional] extends [true, false] ? `readonly ${Key}: ${Mapped}` :
|
||||
`${Key}: ${Mapped}`
|
||||
)
|
||||
> = Result
|
||||
// prettier-ignore
|
||||
function FromProperty(key: string, type: t.TSchema): string {
|
||||
const isOptional = t.KindGuard.IsOptional(type)
|
||||
const isReadonly = t.KindGuard.IsReadonly(type)
|
||||
const mapped = FromType(type)
|
||||
return (
|
||||
isReadonly && isOptional ? `readonly ${key}?: ${mapped}` :
|
||||
!isReadonly && isOptional ? `${key}?: ${mapped}` :
|
||||
isReadonly && !isOptional ? `readonly ${key}: ${mapped}` :
|
||||
`${key}: ${mapped}`
|
||||
)
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Properties
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromProperties<PropertyKeys extends PropertyKey[], Properties extends t.TProperties, Result extends string[] = []> = (
|
||||
PropertyKeys extends [infer Left extends PropertyKey, ...infer Right extends PropertyKey[]]
|
||||
? (Left extends infer Key extends string
|
||||
? (Key extends keyof Properties
|
||||
? TFromProperties<Right, Properties, [...Result, TFromProperty<Key, Properties[Key]>]>
|
||||
: TFromProperties<Right, Properties, Result>
|
||||
) : TFromProperties<Right, Properties, Result>
|
||||
) : Result
|
||||
)
|
||||
// prettier-ignore
|
||||
function FromProperties(propertyKeys: PropertyKey[], properties: t.TProperties): string[] {
|
||||
return propertyKeys.reduce((result, left) => {
|
||||
const key = t.ValueGuard.IsString(left) || t.ValueGuard.IsNumber(left) || t.ValueGuard.IsBoolean(left) ? `${left}` : undefined
|
||||
return (
|
||||
t.ValueGuard.IsString(key)
|
||||
? (key in properties
|
||||
? [...result, FromProperty(key, properties[key])]
|
||||
: result
|
||||
): result
|
||||
)
|
||||
}, [] as string[])
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// String
|
||||
// ------------------------------------------------------------------
|
||||
type TFromString<_Type extends t.TString> = 'string'
|
||||
function FromString(_type: t.TSchema): string {
|
||||
return 'string'
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Symbol
|
||||
// ------------------------------------------------------------------
|
||||
type TFromSymbol<_Type extends t.TSymbol> = 'symbol'
|
||||
function FromSymbol(_type: t.TSchema): string {
|
||||
return 'symbol'
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Union
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromTuple<Types extends t.TSchema[], Result extends string[] = []> = (
|
||||
Types extends [infer Left extends t.TSchema, ...infer Right extends t.TSchema[]]
|
||||
? TFromTuple<Right, [...Result, TFromType<Left>]>
|
||||
: `[${TFromDelimited<Result, TComma>}]`
|
||||
)
|
||||
function FromTuple(types: t.TSchema[]): string {
|
||||
const result = types.map((type) => FromType(type))
|
||||
return `[${FromDelimited(result, Comma)}]`
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Undefined
|
||||
// ------------------------------------------------------------------
|
||||
type TFromUndefined<_Type extends t.TUndefined> = 'undefined'
|
||||
function FromUndefined(type: t.TSchema): string {
|
||||
return 'undefined'
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Union
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromUnion<Types extends t.TSchema[], Result extends string[] = []> = (
|
||||
Types extends [infer Left extends t.TSchema, ...infer Right extends t.TSchema[]]
|
||||
? TFromUnion<Right, [...Result, TFromType<Left>]>
|
||||
: `(${TFromDelimited<Result, ` ${TPipe}`>})`
|
||||
)
|
||||
function FromUnion(types: t.TSchema[]): string {
|
||||
const result = types.map((type) => FromType(type))
|
||||
return `(${FromDelimited(result, ` ${Pipe} `)})`
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Unknown
|
||||
// ------------------------------------------------------------------
|
||||
type TFromUnknown<Type extends t.TSchema> = 'unknown'
|
||||
function FromUnknown(type: t.TSchema): string {
|
||||
return 'unknown'
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Void
|
||||
// ------------------------------------------------------------------
|
||||
type TFromVoid<Type extends t.TSchema> = 'void'
|
||||
function FromVoid(type: t.TSchema): string {
|
||||
return 'void'
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// FromType
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromType<Type extends t.TSchema> = (
|
||||
Type extends t.TAny ? TFromAny<Type> :
|
||||
Type extends t.TArray<infer Type extends t.TSchema> ? TFromArray<Type> :
|
||||
Type extends t.TBigInt ? TFromBigInt<Type> :
|
||||
Type extends t.TBoolean ? TFromBoolean<Type> :
|
||||
Type extends t.TConstructor<infer Parameters extends t.TSchema[], infer InstanceType extends t.TSchema> ? TFromConstructor<Parameters, InstanceType> :
|
||||
Type extends t.TFunction<infer Parameters extends t.TSchema[], infer ReturnType extends t.TSchema> ? TFromFunction<Parameters, ReturnType> :
|
||||
Type extends t.TInteger ? TFromInteger<Type> :
|
||||
Type extends t.Intersect<infer Types extends t.TSchema[]> ? TFromIntersect<Types> :
|
||||
Type extends t.TLiteral<infer Value extends t.TLiteralValue> ? TFromLiteral<Value> :
|
||||
Type extends t.TNumber ? TFromNumber<Type> :
|
||||
Type extends t.TNull ? TFromNull<Type> :
|
||||
Type extends t.TObject<infer Properties extends t.TProperties> ? TFromObject<Properties> :
|
||||
Type extends t.TString ? TFromString<Type> :
|
||||
Type extends t.TSymbol ? TFromSymbol<Type> :
|
||||
Type extends t.TTuple<infer Types extends t.TSchema[]> ? TFromTuple<Types> :
|
||||
Type extends t.TUndefined ? TFromUndefined<Type> :
|
||||
Type extends t.TUnion<infer Types extends t.TSchema[]> ? TFromUnion<Types> :
|
||||
Type extends t.TUnknown ? TFromUnknown<Type> :
|
||||
Type extends t.TVoid ? TFromVoid<Type> :
|
||||
'never'
|
||||
)
|
||||
// prettier-ignore
|
||||
function FromType<Type extends t.TSchema>(type: Type): TFromType<Type> {
|
||||
return (
|
||||
t.KindGuard.IsAny(type) ? FromAny(type) :
|
||||
t.KindGuard.IsArray(type) ? FromArray(type.items) :
|
||||
t.KindGuard.IsBigInt(type) ? FromBigInt(type) :
|
||||
t.KindGuard.IsBoolean(type) ? FromBoolean(type) :
|
||||
t.KindGuard.IsConstructor(type) ? FromConstructor(type.parameters, type.returns) :
|
||||
t.KindGuard.IsFunction(type) ? FromFunction(type.parameters, type.returns) :
|
||||
t.KindGuard.IsInteger(type) ? FromInteger(type) :
|
||||
t.KindGuard.IsIntersect(type) ? FromIntersect(type.allOf) :
|
||||
t.KindGuard.IsLiteral(type) ? FromLiteral(type.const) :
|
||||
t.KindGuard.IsNumber(type) ? FromNumber(type) :
|
||||
t.KindGuard.IsNull(type) ? FromNull(type) :
|
||||
t.KindGuard.IsObject(type) ? FromObject(type.properties) :
|
||||
t.KindGuard.IsString(type) ? FromString(type) :
|
||||
t.KindGuard.IsSymbol(type) ? FromSymbol(type) :
|
||||
t.KindGuard.IsTuple(type) ? FromTuple(type.items || []) :
|
||||
t.KindGuard.IsUndefined(type) ? FromUndefined(type) :
|
||||
t.KindGuard.IsUnion(type) ? FromUnion(type.anyOf) :
|
||||
t.KindGuard.IsUnknown(type) ? FromUnknown(type) :
|
||||
t.KindGuard.IsVoid(type) ? FromVoid(type) :
|
||||
'never'
|
||||
) as never
|
||||
}
|
||||
|
||||
// ------------------------------------------------------------------
|
||||
// SyntaxFromTypeBox
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
export type TSyntaxFromTypeBox<Type extends t.TSchema,
|
||||
Result extends string = TFromType<Type>
|
||||
> = Result
|
||||
export function SyntaxFromTypeBox<Type extends t.TSchema>(type: t.TSchema): TSyntaxFromTypeBox<Type> {
|
||||
return FromType(type) as never
|
||||
}
|
||||
48
src/syntax/syntax-from-valibot.ts
Normal file
48
src/syntax/syntax-from-valibot.ts
Normal file
@@ -0,0 +1,48 @@
|
||||
/*--------------------------------------------------------------------------
|
||||
|
||||
@sinclair/typemap
|
||||
|
||||
The MIT License (MIT)
|
||||
|
||||
Copyright (c) 2024-2025 Haydn Paterson (sinclair) <haydn.developer@gmail.com>
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
|
||||
---------------------------------------------------------------------------*/
|
||||
|
||||
import { type TTypeBoxFromValibot, TypeBoxFromValibot } from '../typebox/typebox-from-valibot'
|
||||
import { type TSyntaxFromTypeBox, SyntaxFromTypeBox } from './syntax-from-typebox'
|
||||
|
||||
import * as t from '@sinclair/typebox'
|
||||
import * as v from 'valibot'
|
||||
|
||||
/** Creates Syntax from Valibot */
|
||||
// prettier-ignore
|
||||
export type TSyntaxFromValibot<Type extends v.BaseSchema<any, any, any>,
|
||||
TypeBox extends t.TSchema = TTypeBoxFromValibot<Type>,
|
||||
Result extends string = TSyntaxFromTypeBox<TypeBox>
|
||||
> = Result
|
||||
|
||||
/** Creates Syntax from Valibot */
|
||||
// prettier-ignore
|
||||
export function SyntaxFromValibot<Type extends v.BaseSchema<any, any, any>>(type: Type): TSyntaxFromValibot<Type> {
|
||||
const typebox = TypeBoxFromValibot(type)
|
||||
const result = SyntaxFromTypeBox(typebox)
|
||||
return result as never
|
||||
}
|
||||
48
src/syntax/syntax-from-zod.ts
Normal file
48
src/syntax/syntax-from-zod.ts
Normal file
@@ -0,0 +1,48 @@
|
||||
/*--------------------------------------------------------------------------
|
||||
|
||||
@sinclair/typemap
|
||||
|
||||
The MIT License (MIT)
|
||||
|
||||
Copyright (c) 2024-2025 Haydn Paterson (sinclair) <haydn.developer@gmail.com>
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
|
||||
---------------------------------------------------------------------------*/
|
||||
|
||||
import { type TTypeBoxFromZod, TypeBoxFromZod } from '../typebox/typebox-from-zod'
|
||||
import { type TSyntaxFromTypeBox, SyntaxFromTypeBox } from './syntax-from-typebox'
|
||||
|
||||
import * as t from '@sinclair/typebox'
|
||||
import * as z from 'zod'
|
||||
|
||||
/** Creates Syntax from Zod */
|
||||
// prettier-ignore
|
||||
export type TSyntaxFromZod<Type extends z.ZodTypeAny | z.ZodEffects<any>,
|
||||
TypeBox extends t.TSchema = TTypeBoxFromZod<Type>,
|
||||
Result extends string = TSyntaxFromTypeBox<TypeBox>
|
||||
> = Result
|
||||
|
||||
/** Creates Syntax from Zod */
|
||||
// prettier-ignore
|
||||
export function SyntaxFromZod<Type extends z.ZodTypeAny | z.ZodEffects<any>>(type: Type): TSyntaxFromZod<Type> {
|
||||
const typebox = TypeBoxFromZod(type)
|
||||
const result = SyntaxFromTypeBox(typebox)
|
||||
return result as never
|
||||
}
|
||||
69
src/syntax/syntax.ts
Normal file
69
src/syntax/syntax.ts
Normal file
@@ -0,0 +1,69 @@
|
||||
/*--------------------------------------------------------------------------
|
||||
|
||||
@sinclair/typemap
|
||||
|
||||
The MIT License (MIT)
|
||||
|
||||
Copyright (c) 2024-2025 Haydn Paterson (sinclair) <haydn.developer@gmail.com>
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
|
||||
---------------------------------------------------------------------------*/
|
||||
|
||||
import { type TSyntaxFromSyntax, SyntaxFromSyntax } from './syntax-from-syntax'
|
||||
import { type TSyntaxFromTypeBox, SyntaxFromTypeBox } from './syntax-from-typebox'
|
||||
import { type TSyntaxFromValibot, SyntaxFromValibot } from './syntax-from-valibot'
|
||||
import { type TSyntaxFromZod, SyntaxFromZod } from './syntax-from-zod'
|
||||
import { type TSyntaxOptions } from '../options'
|
||||
import { type TParameter } from '../typebox/typebox'
|
||||
|
||||
import * as g from '../guard'
|
||||
import * as z from 'zod'
|
||||
|
||||
// ------------------------------------------------------------------
|
||||
// Zod
|
||||
// ------------------------------------------------------------------
|
||||
/** Creates Syntax by mapping from a remote Type */
|
||||
// prettier-ignore
|
||||
export type TSyntax<_Parameter extends TParameter, Type extends object | string, Result extends string = (
|
||||
Type extends g.SyntaxType ? TSyntaxFromSyntax<Type> :
|
||||
Type extends g.TypeBoxType ? TSyntaxFromTypeBox<Type> :
|
||||
Type extends g.ValibotType ? TSyntaxFromValibot<Type> :
|
||||
Type extends g.ZodType ? TSyntaxFromZod<Type> :
|
||||
'never'
|
||||
)> = Result
|
||||
|
||||
/** Creates Syntax by mapping from a remote Type */
|
||||
export function Syntax<Parameter extends TParameter, Type extends string>(parameter: Parameter, type: Type, options?: TSyntaxOptions): TSyntax<Parameter, Type>
|
||||
/** Creates Syntax by mapping from a remote Type */
|
||||
export function Syntax<Type extends string>(type: Type, options?: TSyntaxOptions): TSyntax<{}, Type>
|
||||
/** Creates Syntax by mapping from a remote Type */
|
||||
export function Syntax<Type extends object>(type: Type, options?: TSyntaxOptions): TSyntax<{}, Type>
|
||||
/** Creates Syntax by mapping from a remote Type */
|
||||
// prettier-ignore
|
||||
export function Syntax(...args: any[]): never {
|
||||
const [_parameter, type, _options] = g.Signature(args)
|
||||
return (
|
||||
g.IsSyntax(type) ? SyntaxFromSyntax(type) :
|
||||
g.IsTypeBox(type) ? SyntaxFromTypeBox(type) :
|
||||
g.IsValibot(type) ? SyntaxFromValibot(type) :
|
||||
g.IsZod(type) ? SyntaxFromZod(type) :
|
||||
z.never()
|
||||
) as never
|
||||
}
|
||||
@@ -35,13 +35,13 @@ import * as t from '@sinclair/typebox'
|
||||
|
||||
// prettier-ignore
|
||||
export type TTypeBoxFromSyntax<Context extends t.TProperties, Type extends string,
|
||||
Mapped = StaticParseAsSchema<Context, Type>,
|
||||
Result extends t.TSchema = Mapped extends t.TSchema ? Mapped : t.TNever
|
||||
TypeBox = StaticParseAsSchema<Context, Type>,
|
||||
Result extends t.TSchema = TypeBox extends t.TSchema ? TypeBox : t.TNever
|
||||
> = Result
|
||||
|
||||
/** Creates a TypeBox Type From Syntax */
|
||||
export function TypeBoxFromSyntax<Context extends t.TProperties, Type extends string>(context: Context, type: Type, options?: t.SchemaOptions): TTypeBoxFromSyntax<Context, Type> {
|
||||
const parsed = t.ValueGuard.IsString(type) ? Parse(context, type, options) : t.Never()
|
||||
const result = t.KindGuard.IsSchema(parsed) ? parsed : t.Never()
|
||||
const typebox = t.ValueGuard.IsString(type) ? Parse(context, type, options) : t.Never()
|
||||
const result = t.KindGuard.IsSchema(typebox) ? typebox : t.Never()
|
||||
return result as never
|
||||
}
|
||||
|
||||
@@ -31,11 +31,12 @@ import * as t from '@sinclair/typebox'
|
||||
// ------------------------------------------------------------------
|
||||
// TypeBoxFromTypeBox
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
/** Creates a TypeBox type from TypeBox */
|
||||
// prettier-ignore
|
||||
export type TTypeBoxFromTypeBox<Type extends t.TSchema> = Type
|
||||
|
||||
/** Creates a TypeBox type from TypeBox */
|
||||
// prettier-ignore
|
||||
export function TypeBoxFromTypeBox<Type extends t.TSchema, Result extends TTypeBoxFromTypeBox<Type> = TTypeBoxFromTypeBox<Type>>(type: Type): Result {
|
||||
return (t.KindGuard.IsSchema(type) ? type : t.Never()) as never
|
||||
export function TypeBoxFromTypeBox<Type extends t.TSchema>(type: Type): TTypeBoxFromTypeBox<Type> {
|
||||
return t.CloneType(type)
|
||||
}
|
||||
|
||||
@@ -841,13 +841,14 @@ function FromType<Type extends BaseSchema>(type: Type): TFromType<Type> {
|
||||
// ------------------------------------------------------------------
|
||||
// TypeBoxFromValibot
|
||||
// ------------------------------------------------------------------
|
||||
/** Creates a TypeBox type from Valibot */
|
||||
// prettier-ignore
|
||||
export type TTypeBoxFromValibot<Type extends v.BaseSchema<any, any, any>,
|
||||
Result extends t.TSchema = TFromType<Type>
|
||||
> = Result
|
||||
|
||||
/** Converts a Valibot Type to a TypeBox Type */
|
||||
/** Creates a TypeBox type from Valibot */
|
||||
// prettier-ignore
|
||||
export function TypeBoxFromValibot<Type extends v.BaseSchema<any, any, any>, Result extends TTypeBoxFromValibot<Type> = TTypeBoxFromValibot<Type>>(type: Type): Result {
|
||||
return (Guard.IsValibot(type) ? FromType(type) : t.Never()) as never
|
||||
return FromType(type) as never
|
||||
}
|
||||
|
||||
@@ -28,7 +28,6 @@ THE SOFTWARE.
|
||||
|
||||
import * as t from '@sinclair/typebox'
|
||||
import * as z from 'zod'
|
||||
import * as Guard from '../guard'
|
||||
|
||||
// ------------------------------------------------------------------
|
||||
// Options
|
||||
@@ -135,6 +134,7 @@ function FromEffects<Type extends z.ZodEffects<z.ZodTypeAny, unknown>>(type: Typ
|
||||
// ------------------------------------------------------------------
|
||||
// Enum
|
||||
// ------------------------------------------------------------------
|
||||
/** prettier-ignore */
|
||||
type TFromEnum<Variants extends string[], Result extends t.TLiteral[] = []> = Variants extends [infer Left extends string, ...infer Right extends string[]] ? TFromEnum<Right, [...Result, t.TLiteral<Left>]> : t.TUnion<Result>
|
||||
function FromEnum<Def extends z.ZodEnumDef>(def: Def): t.TSchema {
|
||||
const variants = def.values.map((value) => t.Literal(value))
|
||||
@@ -405,11 +405,11 @@ function FromType<Type extends z.ZodType>(type: Type): t.TSchema {
|
||||
// ------------------------------------------------------------------
|
||||
// TypeBoxFromZod
|
||||
// ------------------------------------------------------------------
|
||||
/** Creates a TypeBox type from Zod */
|
||||
export type TTypeBoxFromZod<Type extends z.ZodTypeAny | z.ZodEffects<any>, Result extends t.TSchema = TFromType<Type>> = Result
|
||||
|
||||
/** Creates a TypeBox type from Zod */
|
||||
// prettier-ignore
|
||||
export type TTypeBoxFromZod<Type extends z.ZodTypeAny | z.ZodEffects<any>,
|
||||
Result extends t.TSchema = TFromType<Type>
|
||||
> = Result
|
||||
// prettier-ignore
|
||||
export function TypeBoxFromZod<Type extends z.ZodTypeAny | z.ZodEffects<any>, Result extends TTypeBoxFromZod<Type> = TTypeBoxFromZod<Type>>(type: Type): Result {
|
||||
export function TypeBoxFromZod<Type extends z.ZodTypeAny | z.ZodEffects<any>>(type: Type): TTypeBoxFromZod<Type> {
|
||||
return FromType(type) as never
|
||||
}
|
||||
|
||||
@@ -31,6 +31,7 @@ import { type TTypeBoxFromTypeBox, TypeBoxFromTypeBox } from './typebox-from-typ
|
||||
import { type TTypeBoxFromValibot, TypeBoxFromValibot } from './typebox-from-valibot'
|
||||
import { type TTypeBoxFromZod, TypeBoxFromZod } from './typebox-from-zod'
|
||||
import { type TSyntaxOptions } from '../options'
|
||||
|
||||
import * as g from '../guard'
|
||||
import * as t from '@sinclair/typebox'
|
||||
|
||||
@@ -40,7 +41,7 @@ import * as t from '@sinclair/typebox'
|
||||
//
|
||||
// TypeBox supports Type injection via a Context parameter. Because the Context
|
||||
// only accepts types of TSchema, we need to an intermediate structure to hold
|
||||
// remote types such that they can be mapped prior to syntax parsing.
|
||||
// the remote types such that they can be mapped prior to syntax parsing.
|
||||
//
|
||||
// -------------------------------------------------------------------------------
|
||||
export type TParameter = Record<PropertyKey, object>
|
||||
@@ -64,7 +65,7 @@ export function ContextFromParameter<Parameter extends TParameter>(parameter: Pa
|
||||
// ------------------------------------------------------------------
|
||||
// TypeBox
|
||||
// ------------------------------------------------------------------
|
||||
/** Creates a TypeBox type from Syntax or another Type */
|
||||
/** Creates a TypeBox type by mapping from a remote Type */
|
||||
// prettier-ignore
|
||||
export type TTypeBox<Parameter extends TParameter, Type extends object | string, Result = (
|
||||
Type extends g.SyntaxType ? TTypeBoxFromSyntax<TContextFromParameter<Parameter>, Type> :
|
||||
@@ -73,11 +74,11 @@ export type TTypeBox<Parameter extends TParameter, Type extends object | string,
|
||||
Type extends g.ZodType ? TTypeBoxFromZod<Type> :
|
||||
t.TNever
|
||||
)> = Result
|
||||
/** Creates a TypeBox type from Syntax or another Type */
|
||||
/** Creates a TypeBox type by mapping from a remote Type */
|
||||
export function TypeBox<Parameter extends TParameter, Type extends string>(parameter: Parameter, type: Type, options?: TSyntaxOptions): TTypeBox<Parameter, Type>
|
||||
/** Creates a TypeBox type from Syntax or another Type */
|
||||
/** Creates a TypeBox type by mapping from a remote Type */
|
||||
export function TypeBox<Type extends object | string>(type: Type, options?: TSyntaxOptions): TTypeBox<{}, Type>
|
||||
/** Creates a TypeBox type from Syntax or another Type */
|
||||
/** Creates a TypeBox type by mapping from a remote Type */
|
||||
// prettier-ignore
|
||||
export function TypeBox(...args: any[]): never {
|
||||
const [parameter, type, options] = g.Signature(args)
|
||||
|
||||
@@ -35,15 +35,16 @@ import * as v from 'valibot'
|
||||
// ------------------------------------------------------------------
|
||||
// ValibotFromSyntax
|
||||
// ------------------------------------------------------------------
|
||||
/** Creates a Valibot type from Syntax */
|
||||
// prettier-ignore
|
||||
export type TValibotFromSyntax<Context extends t.TProperties, Type extends string,
|
||||
Schema extends t.TSchema = TTypeBoxFromSyntax<Context, Type>,
|
||||
Result extends v.BaseSchema<any, any, any> = TValibotFromTypeBox<Schema>
|
||||
TypeBox extends t.TSchema = TTypeBoxFromSyntax<Context, Type>,
|
||||
Result extends v.BaseSchema<any, any, any> = TValibotFromTypeBox<TypeBox>
|
||||
> = Result
|
||||
|
||||
/** Creates a Valibot type from Syntax */
|
||||
// prettier-ignore
|
||||
export function ValibotFromSyntax<Context extends t.TProperties, Type extends string>(context: Context, type: Type, options?: t.SchemaOptions): TValibotFromSyntax<Context, Type> {
|
||||
const schema = TypeBoxFromSyntax(context, type, options)
|
||||
const result = ValibotFromTypeBox(schema)
|
||||
const typebox = TypeBoxFromSyntax(context, type, options)
|
||||
const result = ValibotFromTypeBox(typebox)
|
||||
return result as never
|
||||
}
|
||||
|
||||
@@ -136,6 +136,7 @@ type TFromObject<Properties extends t.TProperties,
|
||||
[Key in keyof Properties]: TFromType<Properties[Key]>
|
||||
}, c.BaseError>
|
||||
> = Result
|
||||
// prettier-ignore
|
||||
function FromObject(type: t.TObject): c.BaseSchema {
|
||||
const { additionalProperties } = type
|
||||
const constraints = CreateConstraints(type)
|
||||
@@ -279,9 +280,10 @@ function FromUndefined(type: t.TUndefined): c.BaseSchema {
|
||||
// Union
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromUnion<Types extends t.TSchema[], Mapped extends c.BaseSchema[] = TFromTypes<Types>, Result = v.UnionSchema<Mapped, c.BaseError>> = (
|
||||
Result
|
||||
)
|
||||
type TFromUnion<Types extends t.TSchema[],
|
||||
Mapped extends c.BaseSchema[] = TFromTypes<Types>,
|
||||
Result = v.UnionSchema<Mapped, c.BaseError>
|
||||
> = Result
|
||||
function FromUnion(type: t.TUnion): c.BaseSchema {
|
||||
const mapped = FromTypes(type.anyOf) as [c.BaseSchema, c.BaseSchema, ...c.BaseSchema[]]
|
||||
return CreateType(v.union(mapped), CreateConstraints(type))
|
||||
@@ -396,6 +398,7 @@ function FromType(type: t.TSchema): c.BaseSchema {
|
||||
// ------------------------------------------------------------------
|
||||
// ValibotFromTypeBox
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
// prettier-ignore
|
||||
export type TValibotFromTypeBox<Type extends t.TSchema,
|
||||
Result extends c.BaseSchema = TFromType<Type>
|
||||
|
||||
@@ -31,12 +31,13 @@ import * as v from 'valibot'
|
||||
// ------------------------------------------------------------------
|
||||
// ValibotFromValibot
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
/** Creates a Valibot type from Valibot */
|
||||
// prettier-ignore
|
||||
export type TValibotFromValibot<Type extends v.BaseSchema<any, any, any>,
|
||||
Result extends v.BaseSchema<any, any, any> = Type
|
||||
> = Result
|
||||
|
||||
/** Creates a Valibot type from Valibot */
|
||||
// prettier-ignore
|
||||
export function ValibotFromValibot<Type extends v.BaseSchema<any, any, any>>(type: Type): TValibotFromValibot<Type> {
|
||||
return type
|
||||
|
||||
@@ -36,12 +36,13 @@ import * as z from 'zod'
|
||||
// ------------------------------------------------------------------
|
||||
// ValibotFromZod
|
||||
// ------------------------------------------------------------------
|
||||
/** Creates a Valibot type from Zod */
|
||||
// prettier-ignore
|
||||
export type TValibotFromZod<Type extends z.ZodTypeAny | z.ZodEffects<any>,
|
||||
TypeBox extends t.TSchema = TTypeBoxFromZod<Type>,
|
||||
Result extends v.BaseSchema<any, any, any> = TValibotFromTypeBox<TypeBox>
|
||||
> = Result
|
||||
|
||||
/** Creates a Valibot type from Zod */
|
||||
// prettier-ignore
|
||||
export function ValibotFromZod<Type extends z.ZodTypeAny | z.ZodEffects<any>,
|
||||
Result extends v.BaseSchema<any, any, any> = TValibotFromZod<Type>
|
||||
|
||||
@@ -31,17 +31,18 @@ import { type TValibotFromTypeBox, ValibotFromTypeBox } from './valibot-from-typ
|
||||
import { type TValibotFromValibot, ValibotFromValibot } from './valibot-from-valibot'
|
||||
import { type TValibotFromZod, ValibotFromZod } from './valibot-from-zod'
|
||||
import { type TSyntaxOptions } from '../options'
|
||||
|
||||
import { type TParameter, type TContextFromParameter, ContextFromParameter } from '../typebox/typebox'
|
||||
|
||||
import * as g from '../guard'
|
||||
import * as t from '@sinclair/typebox'
|
||||
import * as v from 'valibot'
|
||||
import * as c from './common'
|
||||
|
||||
import { TParameter, TContextFromParameter, ContextFromParameter } from '../typebox/typebox'
|
||||
|
||||
// ------------------------------------------------------------------
|
||||
// Valibot
|
||||
// ------------------------------------------------------------------
|
||||
/** Creates a Valibot type from Syntax or another Type */
|
||||
/** Creates a Valibot type by mapping from a remote Type */
|
||||
// prettier-ignore
|
||||
export type TValibot<Parameter extends TParameter, Type extends object | string, Result extends g.ValibotType = (
|
||||
Type extends g.SyntaxType ? TValibotFromSyntax<TContextFromParameter<Parameter>, Type> :
|
||||
@@ -51,13 +52,13 @@ export type TValibot<Parameter extends TParameter, Type extends object | string,
|
||||
v.NeverSchema<c.BaseError>
|
||||
)> = Result
|
||||
|
||||
/** Creates a Valibot type from Syntax or another Type */
|
||||
/** Creates a Valibot type by mapping from a remote Type */
|
||||
export function Valibot<Parameter extends TParameter, Type extends string>(parameter: Parameter, type: Type, options?: TSyntaxOptions): TValibot<Parameter, Type>
|
||||
/** Creates a Valibot type from Syntax or another Type */
|
||||
/** Creates a Valibot type by mapping from a remote Type */
|
||||
export function Valibot<Type extends string>(type: Type, options?: TSyntaxOptions): TValibot<{}, Type>
|
||||
/** Creates a Valibot type from Syntax or another Type */
|
||||
/** Creates a Valibot type by mapping from a remote Type */
|
||||
export function Valibot<Type extends object>(type: Type, options?: TSyntaxOptions): TValibot<{}, Type>
|
||||
/** Creates a Valibot type from Syntax or another Type */
|
||||
/** Creates a Valibot type by mapping from a remote Type */
|
||||
// prettier-ignore
|
||||
export function Valibot(...args: any[]): never {
|
||||
const [parameter, type, options] = g.Signature(args)
|
||||
|
||||
@@ -34,15 +34,15 @@ import * as z from 'zod'
|
||||
// ------------------------------------------------------------------
|
||||
// ZodFromSyntax
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
/** Creates a Zod type from Syntax */
|
||||
// prettier-ignore
|
||||
export type TZodFromSyntax<Context extends t.TProperties, Type extends string,
|
||||
Schema extends t.TSchema = TTypeBoxFromSyntax<Context, Type>,
|
||||
Result extends z.ZodTypeAny | z.ZodEffects<any> = TZodFromTypeBox<Schema>
|
||||
TypeBox extends t.TSchema = TTypeBoxFromSyntax<Context, Type>,
|
||||
Result extends z.ZodTypeAny | z.ZodEffects<any> = TZodFromTypeBox<TypeBox>
|
||||
> = Result
|
||||
|
||||
/** Creates a Zod type from Syntax */
|
||||
export function ZodFromSyntax<Context extends t.TProperties, Type extends string>(context: Context, type: Type, options?: t.SchemaOptions): TZodFromSyntax<Context, Type> {
|
||||
const schema = TypeBoxFromSyntax(context, type, options)
|
||||
const result = ZodFromTypeBox(schema)
|
||||
const typebox = TypeBoxFromSyntax(context, type, options)
|
||||
const result = ZodFromTypeBox(typebox)
|
||||
return result as never
|
||||
}
|
||||
|
||||
@@ -106,9 +106,12 @@ function FromInteger(type: t.TInteger): z.ZodTypeAny {
|
||||
// ------------------------------------------------------------------
|
||||
// Intersect
|
||||
// ------------------------------------------------------------------
|
||||
type TFromIntersect<Types extends t.TSchema[], Result extends z.ZodTypeAny = z.ZodUnknown> = Types extends [infer Left extends t.TSchema, ...infer Right extends t.TSchema[]]
|
||||
? TFromIntersect<Right, z.ZodIntersection<TFromType<Left>, Result>>
|
||||
: Result
|
||||
// prettier-ignore
|
||||
type TFromIntersect<Types extends t.TSchema[], Result extends z.ZodTypeAny = z.ZodUnknown> = (
|
||||
Types extends [infer Left extends t.TSchema, ...infer Right extends t.TSchema[]]
|
||||
? TFromIntersect<Right, z.ZodIntersection<TFromType<Left>, Result>>
|
||||
: Result
|
||||
)
|
||||
function FromIntersect(type: t.TIntersect): z.ZodTypeAny {
|
||||
return type.allOf.reduce((result, left) => {
|
||||
return z.intersection(FromType(left), result) as never
|
||||
@@ -124,8 +127,8 @@ function FromLiteral(type: t.TLiteral): z.ZodTypeAny {
|
||||
// ------------------------------------------------------------------
|
||||
// Object
|
||||
// ------------------------------------------------------------------
|
||||
type TFromObject<
|
||||
Properties extends t.TProperties,
|
||||
// prettier-ignore
|
||||
type TFromObject< Properties extends t.TProperties,
|
||||
Result = z.ZodObject<{
|
||||
[Key in keyof Properties]: TFromType<Properties[Key]>
|
||||
}>,
|
||||
@@ -160,7 +163,12 @@ function FromRegExp(type: t.TRegExp): z.ZodTypeAny {
|
||||
// ------------------------------------------------------------------
|
||||
// Record
|
||||
// ------------------------------------------------------------------
|
||||
type TFromRecord<Key extends t.TSchema, Value extends t.TSchema> = TFromType<Key> extends infer ZodKey extends z.KeySchema ? z.ZodRecord<ZodKey, TFromType<Value>> : z.ZodNever
|
||||
// prettier-ignore
|
||||
type TFromRecord<Key extends t.TSchema, Value extends t.TSchema> = (
|
||||
TFromType<Key> extends infer ZodKey extends z.KeySchema
|
||||
? z.ZodRecord<ZodKey, TFromType<Value>>
|
||||
: z.ZodNever
|
||||
)
|
||||
// prettier-ignore
|
||||
function FromRecord(type: t.TRecord): z.ZodTypeAny {
|
||||
const pattern = globalThis.Object.getOwnPropertyNames(type.patternProperties)[0]
|
||||
@@ -173,34 +181,6 @@ function FromRecord(type: t.TRecord): z.ZodTypeAny {
|
||||
)
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Optional
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromOptional<Type extends t.TOptional<t.TSchema>,
|
||||
NonOptional extends t.TSchema = t.TOptionalWithFlag<Type, false>,
|
||||
Mapped extends z.ZodTypeAny | z.ZodEffects<any> = TFromType<NonOptional>,
|
||||
Result = z.ZodOptional<Mapped>
|
||||
> = Result
|
||||
function FromOptional(type: t.TOptional<t.TSchema>): z.ZodTypeAny {
|
||||
const non_optional = t.Optional(type, false)
|
||||
const mapped = FromType(non_optional)
|
||||
return z.optional(mapped)
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Readonly
|
||||
// ------------------------------------------------------------------
|
||||
// prettier-ignore
|
||||
type TFromReadonly<Type extends t.TReadonly<t.TSchema>,
|
||||
NonReadonly extends t.TSchema = t.TReadonlyWithFlag<Type, false>,
|
||||
Mapped extends z.ZodTypeAny | z.ZodEffects<any> = TFromType<NonReadonly>,
|
||||
Result = z.ZodReadonly<Mapped>
|
||||
> = Result
|
||||
function FromReadonly(type: t.TReadonly<t.TSchema>): z.ZodTypeAny {
|
||||
const non_readonly = t.Readonly(type, false)
|
||||
const mapped = FromType(non_readonly)
|
||||
return mapped // no mapping
|
||||
}
|
||||
// ------------------------------------------------------------------
|
||||
// Never
|
||||
// ------------------------------------------------------------------
|
||||
type TFromNever<Result = z.ZodNever> = Result
|
||||
@@ -321,7 +301,12 @@ function FromVoid(_type: t.TVoid): z.ZodTypeAny {
|
||||
// ------------------------------------------------------------------
|
||||
// Types
|
||||
// ------------------------------------------------------------------
|
||||
type TFromTypes<Types extends t.TSchema[], Result extends z.ZodTypeAny[] = []> = Types extends [infer Left extends t.TSchema, ...infer Right extends t.TSchema[]] ? TFromTypes<Right, [...Result, TFromType<Left>]> : Result
|
||||
// prettier-ignore
|
||||
type TFromTypes<Types extends t.TSchema[], Result extends z.ZodTypeAny[] = []> = (
|
||||
Types extends [infer Left extends t.TSchema, ...infer Right extends t.TSchema[]]
|
||||
? TFromTypes<Right, [...Result, TFromType<Left>]>
|
||||
: Result
|
||||
)
|
||||
function FromTypes(types: t.TSchema[]): z.ZodTypeAny[] {
|
||||
return types.map((type) => FromType(type))
|
||||
}
|
||||
@@ -373,8 +358,6 @@ function FromType(type: t.TSchema): z.ZodTypeAny | z.ZodEffects<any> {
|
||||
if(!t.ValueGuard.IsUndefined(type.description)) constraints.push(input => input.describe(type.description!))
|
||||
if(!t.ValueGuard.IsUndefined(type.default)) constraints.push(input => input.default(type.default))
|
||||
const mapped = constraints.reduce((type, constraint) => constraint(type), (
|
||||
t.KindGuard.IsReadonly(type) ? FromReadonly(type) :
|
||||
t.KindGuard.IsOptional(type) ? FromOptional(type) :
|
||||
t.KindGuard.IsAny(type) ? FromAny(type) :
|
||||
t.KindGuard.IsArray(type) ? FromArray(type) :
|
||||
t.KindGuard.IsBigInt(type) ? FromBigInt(type) :
|
||||
@@ -414,10 +397,12 @@ function FromType(type: t.TSchema): z.ZodTypeAny | z.ZodEffects<any> {
|
||||
// ------------------------------------------------------------------
|
||||
// ZodFromTypeBox
|
||||
// ------------------------------------------------------------------
|
||||
/** Creates a Zod type from TypeBox */
|
||||
// prettier-ignore
|
||||
export type TZodFromTypeBox<Type extends t.TSchema,
|
||||
Result extends z.ZodTypeAny | z.ZodEffects<any> = TFromType<Type>
|
||||
> = Result
|
||||
/** Creates a Zod type from TypeBox */
|
||||
export function ZodFromTypeBox<Type extends t.TSchema>(type: Type): TZodFromTypeBox<Type> {
|
||||
return (t.KindGuard.IsSchema(type) ? FromType(type) : z.never()) as never
|
||||
return FromType(type) as never
|
||||
}
|
||||
|
||||
@@ -33,15 +33,17 @@ import * as t from '@sinclair/typebox'
|
||||
import * as v from 'valibot'
|
||||
import * as z from 'zod'
|
||||
|
||||
/** Creates a Zod type from Valibot */
|
||||
// prettier-ignore
|
||||
export type TZodFromValibot<Type extends v.BaseSchema<any, any, any>,
|
||||
Schema extends t.TSchema = TTypeBoxFromValibot<Type>,
|
||||
Result extends z.ZodTypeAny | z.ZodEffects<any> = TZodFromTypeBox<Schema>
|
||||
TypeBox extends t.TSchema = TTypeBoxFromValibot<Type>,
|
||||
Result extends z.ZodTypeAny | z.ZodEffects<any> = TZodFromTypeBox<TypeBox>
|
||||
> = Result
|
||||
|
||||
/** Creates a Zod type from Valibot */
|
||||
// prettier-ignore
|
||||
export function ZodFromValibot<Type extends v.BaseSchema<any, any, any>>(type: Type): TZodFromValibot<Type> {
|
||||
const schema = TypeBoxFromValibot(type)
|
||||
const result = ZodFromTypeBox(schema)
|
||||
const typebox = TypeBoxFromValibot(type)
|
||||
const result = ZodFromTypeBox(typebox)
|
||||
return result
|
||||
}
|
||||
|
||||
@@ -26,17 +26,16 @@ THE SOFTWARE.
|
||||
|
||||
---------------------------------------------------------------------------*/
|
||||
|
||||
import * as Guard from '../guard'
|
||||
import * as z from 'zod'
|
||||
|
||||
type BaseType = z.ZodTypeAny | z.ZodEffects<any>
|
||||
|
||||
/** Creates a Zod type from Zod */
|
||||
// prettier-ignore
|
||||
export type TZodFromZod<Type extends object,
|
||||
Result extends BaseType = Type extends BaseType ? Type : z.ZodNever
|
||||
export type TZodFromZod<Type extends z.ZodTypeAny | z.ZodEffects<any>,
|
||||
Result = Type
|
||||
> = Result
|
||||
|
||||
/** Creates a Zod type from Zod */
|
||||
// prettier-ignore
|
||||
export function ZodFromZod<Type extends object>(type: Type): TZodFromZod<Type> {
|
||||
return (Guard.IsZod(type) ? type : z.never()) as never
|
||||
export function ZodFromZod<Type extends z.ZodTypeAny | z.ZodEffects<any>>(type: Type): TZodFromZod<Type> {
|
||||
return type as never
|
||||
}
|
||||
|
||||
@@ -32,15 +32,15 @@ import { type TZodFromValibot, ZodFromValibot } from './zod-from-valibot'
|
||||
import { type TZodFromZod, ZodFromZod } from './zod-from-zod'
|
||||
import { type TSyntaxOptions } from '../options'
|
||||
|
||||
import { type TParameter, type TContextFromParameter, ContextFromParameter } from '../typebox/typebox'
|
||||
|
||||
import * as g from '../guard'
|
||||
import * as z from 'zod'
|
||||
|
||||
import { TParameter, TContextFromParameter, ContextFromParameter } from '../typebox/typebox'
|
||||
|
||||
// ------------------------------------------------------------------
|
||||
// Zod
|
||||
// ------------------------------------------------------------------
|
||||
/** Creates a Zod type from Syntax or another Type */
|
||||
/** Creates a Zod type by mapping from a remote Type */
|
||||
// prettier-ignore
|
||||
export type TZod<Parameter extends TParameter, Type extends object | string, Result extends z.ZodTypeAny | z.ZodEffects<any> = (
|
||||
Type extends g.SyntaxType ? TZodFromSyntax<TContextFromParameter<Parameter>, Type> :
|
||||
@@ -50,13 +50,13 @@ export type TZod<Parameter extends TParameter, Type extends object | string, Res
|
||||
z.ZodNever
|
||||
)> = Result
|
||||
|
||||
/** Creates a Zod type from Syntax or another Type */
|
||||
/** Creates a Zod type by mapping from a remote Type */
|
||||
export function Zod<Parameter extends TParameter, Type extends string>(parameter: Parameter, type: Type, options?: TSyntaxOptions): TZod<Parameter, Type>
|
||||
/** Creates a Zod type from Syntax or another Type */
|
||||
/** Creates a Zod type by mapping from a remote Type */
|
||||
export function Zod<Type extends string>(type: Type, options?: TSyntaxOptions): TZod<{}, Type>
|
||||
/** Creates a Zod type from Syntax or another Type */
|
||||
/** Creates a Zod type by mapping from a remote Type */
|
||||
export function Zod<Type extends object>(type: Type, options?: TSyntaxOptions): TZod<{}, Type>
|
||||
/** Creates a Zod type from Syntax or another Type */
|
||||
/** Creates a Zod type by mapping from a remote Type */
|
||||
// prettier-ignore
|
||||
export function Zod(...args: any[]): never {
|
||||
const [parameter, type, options] = g.Signature(args)
|
||||
|
||||
Reference in New Issue
Block a user