Avoid resolving source prop type when the target is unknown/any (#61660)

This commit is contained in:
Mateusz Burzyński 2025-06-07 00:17:50 +02:00 committed by GitHub
parent 7715955f89
commit 355b9e0984
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
15 changed files with 835 additions and 4 deletions

View File

@ -24114,6 +24114,10 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
function isPropertySymbolTypeRelated(sourceProp: Symbol, targetProp: Symbol, getTypeOfSourceProperty: (sym: Symbol) => Type, reportErrors: boolean, intersectionState: IntersectionState): Ternary {
const targetIsOptional = strictNullChecks && !!(getCheckFlags(targetProp) & CheckFlags.Partial);
const effectiveTarget = addOptionality(getNonMissingTypeOfSymbol(targetProp), /*isProperty*/ false, targetIsOptional);
// source could resolve to `any` and that's not related to `unknown` target under strict subtype relation
if (effectiveTarget.flags & (relation === strictSubtypeRelation ? TypeFlags.Any : TypeFlags.AnyOrUnknown)) {
return Ternary.True;
}
const effectiveSource = getTypeOfSourceProperty(sourceProp);
return isRelatedTo(effectiveSource, effectiveTarget, RecursionFlags.Both, reportErrors, /*headMessage*/ undefined, intersectionState);
}

View File

@ -0,0 +1,142 @@
//// [tests/cases/compiler/noCircularitySelfReferentialGetter1.ts] ////
=== noCircularitySelfReferentialGetter1.ts ===
// https://github.com/microsoft/TypeScript/issues/61659
interface ZodType {
>ZodType : Symbol(ZodType, Decl(noCircularitySelfReferentialGetter1.ts, 0, 0))
optional: "true" | "false";
>optional : Symbol(ZodType.optional, Decl(noCircularitySelfReferentialGetter1.ts, 2, 19))
output: any;
>output : Symbol(ZodType.output, Decl(noCircularitySelfReferentialGetter1.ts, 3, 29))
}
interface ZodString extends ZodType {
>ZodString : Symbol(ZodString, Decl(noCircularitySelfReferentialGetter1.ts, 5, 1))
>ZodType : Symbol(ZodType, Decl(noCircularitySelfReferentialGetter1.ts, 0, 0))
optional: "false";
>optional : Symbol(ZodString.optional, Decl(noCircularitySelfReferentialGetter1.ts, 7, 37))
output: string;
>output : Symbol(ZodString.output, Decl(noCircularitySelfReferentialGetter1.ts, 8, 20))
}
type ZodShape = Record<string, any>;
>ZodShape : Symbol(ZodShape, Decl(noCircularitySelfReferentialGetter1.ts, 10, 1))
>Record : Symbol(Record, Decl(lib.es5.d.ts, --, --))
type Prettify<T> = { [K in keyof T]: T[K] } & {};
>Prettify : Symbol(Prettify, Decl(noCircularitySelfReferentialGetter1.ts, 12, 36))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter1.ts, 13, 14))
>K : Symbol(K, Decl(noCircularitySelfReferentialGetter1.ts, 13, 22))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter1.ts, 13, 14))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter1.ts, 13, 14))
>K : Symbol(K, Decl(noCircularitySelfReferentialGetter1.ts, 13, 22))
type InferObjectType<Shape extends ZodShape> = Prettify<
>InferObjectType : Symbol(InferObjectType, Decl(noCircularitySelfReferentialGetter1.ts, 13, 49))
>Shape : Symbol(Shape, Decl(noCircularitySelfReferentialGetter1.ts, 14, 21))
>ZodShape : Symbol(ZodShape, Decl(noCircularitySelfReferentialGetter1.ts, 10, 1))
>Prettify : Symbol(Prettify, Decl(noCircularitySelfReferentialGetter1.ts, 12, 36))
{
[k in keyof Shape as Shape[k] extends { optional: "true" }
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter1.ts, 16, 5))
>Shape : Symbol(Shape, Decl(noCircularitySelfReferentialGetter1.ts, 14, 21))
>Shape : Symbol(Shape, Decl(noCircularitySelfReferentialGetter1.ts, 14, 21))
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter1.ts, 16, 5))
>optional : Symbol(optional, Decl(noCircularitySelfReferentialGetter1.ts, 16, 43))
? k
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter1.ts, 16, 5))
: never]?: Shape[k]["output"];
>Shape : Symbol(Shape, Decl(noCircularitySelfReferentialGetter1.ts, 14, 21))
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter1.ts, 16, 5))
} & {
[k in keyof Shape as Shape[k] extends { optional: "true" }
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter1.ts, 20, 5))
>Shape : Symbol(Shape, Decl(noCircularitySelfReferentialGetter1.ts, 14, 21))
>Shape : Symbol(Shape, Decl(noCircularitySelfReferentialGetter1.ts, 14, 21))
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter1.ts, 20, 5))
>optional : Symbol(optional, Decl(noCircularitySelfReferentialGetter1.ts, 20, 43))
? never
: k]: Shape[k]["output"];
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter1.ts, 20, 5))
>Shape : Symbol(Shape, Decl(noCircularitySelfReferentialGetter1.ts, 14, 21))
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter1.ts, 20, 5))
}
>;
interface ZodObject<T extends ZodShape> extends ZodType {
>ZodObject : Symbol(ZodObject, Decl(noCircularitySelfReferentialGetter1.ts, 24, 2))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter1.ts, 25, 20))
>ZodShape : Symbol(ZodShape, Decl(noCircularitySelfReferentialGetter1.ts, 10, 1))
>ZodType : Symbol(ZodType, Decl(noCircularitySelfReferentialGetter1.ts, 0, 0))
optional: "false";
>optional : Symbol(ZodObject.optional, Decl(noCircularitySelfReferentialGetter1.ts, 25, 57))
output: InferObjectType<T>;
>output : Symbol(ZodObject.output, Decl(noCircularitySelfReferentialGetter1.ts, 26, 20))
>InferObjectType : Symbol(InferObjectType, Decl(noCircularitySelfReferentialGetter1.ts, 13, 49))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter1.ts, 25, 20))
}
interface ZodOptional<T extends ZodType> extends ZodType {
>ZodOptional : Symbol(ZodOptional, Decl(noCircularitySelfReferentialGetter1.ts, 28, 1))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter1.ts, 30, 22))
>ZodType : Symbol(ZodType, Decl(noCircularitySelfReferentialGetter1.ts, 0, 0))
>ZodType : Symbol(ZodType, Decl(noCircularitySelfReferentialGetter1.ts, 0, 0))
optional: "true";
>optional : Symbol(ZodOptional.optional, Decl(noCircularitySelfReferentialGetter1.ts, 30, 58))
output: T["output"] | undefined;
>output : Symbol(ZodOptional.output, Decl(noCircularitySelfReferentialGetter1.ts, 31, 19))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter1.ts, 30, 22))
}
declare function object<T extends ZodShape>(shape: T): ZodObject<T>;
>object : Symbol(object, Decl(noCircularitySelfReferentialGetter1.ts, 33, 1))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter1.ts, 35, 24))
>ZodShape : Symbol(ZodShape, Decl(noCircularitySelfReferentialGetter1.ts, 10, 1))
>shape : Symbol(shape, Decl(noCircularitySelfReferentialGetter1.ts, 35, 44))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter1.ts, 35, 24))
>ZodObject : Symbol(ZodObject, Decl(noCircularitySelfReferentialGetter1.ts, 24, 2))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter1.ts, 35, 24))
declare function string(): ZodString;
>string : Symbol(string, Decl(noCircularitySelfReferentialGetter1.ts, 35, 68))
>ZodString : Symbol(ZodString, Decl(noCircularitySelfReferentialGetter1.ts, 5, 1))
declare function optional<T extends ZodType>(schema: T): ZodOptional<T>;
>optional : Symbol(optional, Decl(noCircularitySelfReferentialGetter1.ts, 36, 37))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter1.ts, 37, 26))
>ZodType : Symbol(ZodType, Decl(noCircularitySelfReferentialGetter1.ts, 0, 0))
>schema : Symbol(schema, Decl(noCircularitySelfReferentialGetter1.ts, 37, 45))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter1.ts, 37, 26))
>ZodOptional : Symbol(ZodOptional, Decl(noCircularitySelfReferentialGetter1.ts, 28, 1))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter1.ts, 37, 26))
const Category = object({
>Category : Symbol(Category, Decl(noCircularitySelfReferentialGetter1.ts, 39, 5))
>object : Symbol(object, Decl(noCircularitySelfReferentialGetter1.ts, 33, 1))
name: string(),
>name : Symbol(name, Decl(noCircularitySelfReferentialGetter1.ts, 39, 25))
>string : Symbol(string, Decl(noCircularitySelfReferentialGetter1.ts, 35, 68))
get parent() {
>parent : Symbol(parent, Decl(noCircularitySelfReferentialGetter1.ts, 40, 17))
return optional(Category);
>optional : Symbol(optional, Decl(noCircularitySelfReferentialGetter1.ts, 36, 37))
>Category : Symbol(Category, Decl(noCircularitySelfReferentialGetter1.ts, 39, 5))
},
});

View File

@ -0,0 +1,120 @@
//// [tests/cases/compiler/noCircularitySelfReferentialGetter1.ts] ////
=== noCircularitySelfReferentialGetter1.ts ===
// https://github.com/microsoft/TypeScript/issues/61659
interface ZodType {
optional: "true" | "false";
>optional : "true" | "false"
> : ^^^^^^^^^^^^^^^^
output: any;
>output : any
}
interface ZodString extends ZodType {
optional: "false";
>optional : "false"
> : ^^^^^^^
output: string;
>output : string
> : ^^^^^^
}
type ZodShape = Record<string, any>;
>ZodShape : ZodShape
> : ^^^^^^^^
type Prettify<T> = { [K in keyof T]: T[K] } & {};
>Prettify : { [K in keyof T]: T[K]; }
> : ^^^ ^^^^^^^^^^^^^^^^^^^^^
type InferObjectType<Shape extends ZodShape> = Prettify<
>InferObjectType : { [k in keyof Shape as Shape[k] extends { optional: "true"; } ? k : never]?: Shape[k]["output"] | undefined; } & { [k_1 in keyof Shape as Shape[k_1] extends { optional: "true"; } ? never : k_1]: Shape[k_1]["output"]; } extends infer T ? { [K in keyof T]: T[K]; } : never
> : ^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
{
[k in keyof Shape as Shape[k] extends { optional: "true" }
>optional : "true"
> : ^^^^^^
? k
: never]?: Shape[k]["output"];
} & {
[k in keyof Shape as Shape[k] extends { optional: "true" }
>optional : "true"
> : ^^^^^^
? never
: k]: Shape[k]["output"];
}
>;
interface ZodObject<T extends ZodShape> extends ZodType {
optional: "false";
>optional : "false"
> : ^^^^^^^
output: InferObjectType<T>;
>output : { [k in keyof T as T[k] extends { optional: "true"; } ? k : never]?: T[k]["output"] | undefined; } & { [k_1 in keyof T as T[k_1] extends { optional: "true"; } ? never : k_1]: T[k_1]["output"]; } extends infer T_1 ? { [K in keyof T_1]: T_1[K]; } : never
> : ^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
}
interface ZodOptional<T extends ZodType> extends ZodType {
optional: "true";
>optional : "true"
> : ^^^^^^
output: T["output"] | undefined;
>output : T["output"] | undefined
> : ^^^^^^^^^^^^^^^^^^^^^^^
}
declare function object<T extends ZodShape>(shape: T): ZodObject<T>;
>object : <T extends ZodShape>(shape: T) => ZodObject<T>
> : ^ ^^^^^^^^^ ^^ ^^ ^^^^^
>shape : T
> : ^
declare function string(): ZodString;
>string : () => ZodString
> : ^^^^^^
declare function optional<T extends ZodType>(schema: T): ZodOptional<T>;
>optional : <T extends ZodType>(schema: T) => ZodOptional<T>
> : ^ ^^^^^^^^^ ^^ ^^ ^^^^^
>schema : T
> : ^
const Category = object({
>Category : ZodObject<{ name: ZodString; readonly parent: ZodOptional<ZodObject<any>>; }>
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>object({ name: string(), get parent() { return optional(Category); },}) : ZodObject<{ name: ZodString; readonly parent: ZodOptional<ZodObject<any>>; }>
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>object : <T extends ZodShape>(shape: T) => ZodObject<T>
> : ^ ^^^^^^^^^ ^^ ^^ ^^^^^
>{ name: string(), get parent() { return optional(Category); },} : { name: ZodString; readonly parent: ZodOptional<ZodObject<{ name: ZodString; readonly parent: ZodOptional<ZodObject<any>>; }>>; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
name: string(),
>name : ZodString
> : ^^^^^^^^^
>string() : ZodString
> : ^^^^^^^^^
>string : () => ZodString
> : ^^^^^^
get parent() {
>parent : ZodOptional<ZodObject<{ name: ZodString; readonly parent: ZodOptional<ZodObject<any>>; }>>
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
return optional(Category);
>optional(Category) : ZodOptional<ZodObject<{ name: ZodString; readonly parent: ZodOptional<ZodObject<any>>; }>>
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>optional : <T extends ZodType>(schema: T) => ZodOptional<T>
> : ^ ^^^^^^^^^ ^^ ^^ ^^^^^
>Category : ZodObject<{ name: ZodString; readonly parent: ZodOptional<ZodObject<any>>; }>
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
},
});

View File

@ -0,0 +1,156 @@
//// [tests/cases/compiler/noCircularitySelfReferentialGetter2.ts] ////
=== noCircularitySelfReferentialGetter2.ts ===
interface ZodType {
>ZodType : Symbol(ZodType, Decl(noCircularitySelfReferentialGetter2.ts, 0, 0))
optional: "true" | "false";
>optional : Symbol(ZodType.optional, Decl(noCircularitySelfReferentialGetter2.ts, 0, 19))
output: any;
>output : Symbol(ZodType.output, Decl(noCircularitySelfReferentialGetter2.ts, 1, 29))
}
interface ZodString extends ZodType {
>ZodString : Symbol(ZodString, Decl(noCircularitySelfReferentialGetter2.ts, 3, 1))
>ZodType : Symbol(ZodType, Decl(noCircularitySelfReferentialGetter2.ts, 0, 0))
optional: "false";
>optional : Symbol(ZodString.optional, Decl(noCircularitySelfReferentialGetter2.ts, 5, 37))
output: string;
>output : Symbol(ZodString.output, Decl(noCircularitySelfReferentialGetter2.ts, 6, 20))
}
type ZodShape = Record<string, any>;
>ZodShape : Symbol(ZodShape, Decl(noCircularitySelfReferentialGetter2.ts, 8, 1))
>Record : Symbol(Record, Decl(lib.es5.d.ts, --, --))
type Prettify<T> = { [K in keyof T]: T[K] } & {};
>Prettify : Symbol(Prettify, Decl(noCircularitySelfReferentialGetter2.ts, 10, 36))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter2.ts, 11, 14))
>K : Symbol(K, Decl(noCircularitySelfReferentialGetter2.ts, 11, 22))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter2.ts, 11, 14))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter2.ts, 11, 14))
>K : Symbol(K, Decl(noCircularitySelfReferentialGetter2.ts, 11, 22))
type InferObjectType<Shape extends ZodShape> = Prettify<
>InferObjectType : Symbol(InferObjectType, Decl(noCircularitySelfReferentialGetter2.ts, 11, 49))
>Shape : Symbol(Shape, Decl(noCircularitySelfReferentialGetter2.ts, 12, 21))
>ZodShape : Symbol(ZodShape, Decl(noCircularitySelfReferentialGetter2.ts, 8, 1))
>Prettify : Symbol(Prettify, Decl(noCircularitySelfReferentialGetter2.ts, 10, 36))
{
[k in keyof Shape as Shape[k] extends { optional: "true" }
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter2.ts, 14, 5))
>Shape : Symbol(Shape, Decl(noCircularitySelfReferentialGetter2.ts, 12, 21))
>Shape : Symbol(Shape, Decl(noCircularitySelfReferentialGetter2.ts, 12, 21))
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter2.ts, 14, 5))
>optional : Symbol(optional, Decl(noCircularitySelfReferentialGetter2.ts, 14, 43))
? k
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter2.ts, 14, 5))
: never]?: Shape[k]["output"];
>Shape : Symbol(Shape, Decl(noCircularitySelfReferentialGetter2.ts, 12, 21))
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter2.ts, 14, 5))
} & {
[k in keyof Shape as Shape[k] extends { optional: "true" }
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter2.ts, 18, 5))
>Shape : Symbol(Shape, Decl(noCircularitySelfReferentialGetter2.ts, 12, 21))
>Shape : Symbol(Shape, Decl(noCircularitySelfReferentialGetter2.ts, 12, 21))
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter2.ts, 18, 5))
>optional : Symbol(optional, Decl(noCircularitySelfReferentialGetter2.ts, 18, 43))
? never
: k]: Shape[k]["output"];
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter2.ts, 18, 5))
>Shape : Symbol(Shape, Decl(noCircularitySelfReferentialGetter2.ts, 12, 21))
>k : Symbol(k, Decl(noCircularitySelfReferentialGetter2.ts, 18, 5))
}
>;
interface ZodObject<T extends ZodShape> extends ZodType {
>ZodObject : Symbol(ZodObject, Decl(noCircularitySelfReferentialGetter2.ts, 22, 2))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter2.ts, 23, 20))
>ZodShape : Symbol(ZodShape, Decl(noCircularitySelfReferentialGetter2.ts, 8, 1))
>ZodType : Symbol(ZodType, Decl(noCircularitySelfReferentialGetter2.ts, 0, 0))
optional: "false";
>optional : Symbol(ZodObject.optional, Decl(noCircularitySelfReferentialGetter2.ts, 23, 57))
output: InferObjectType<T>;
>output : Symbol(ZodObject.output, Decl(noCircularitySelfReferentialGetter2.ts, 24, 20))
>InferObjectType : Symbol(InferObjectType, Decl(noCircularitySelfReferentialGetter2.ts, 11, 49))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter2.ts, 23, 20))
}
interface ZodOptional<T extends ZodType> extends ZodType {
>ZodOptional : Symbol(ZodOptional, Decl(noCircularitySelfReferentialGetter2.ts, 26, 1))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter2.ts, 28, 22))
>ZodType : Symbol(ZodType, Decl(noCircularitySelfReferentialGetter2.ts, 0, 0))
>ZodType : Symbol(ZodType, Decl(noCircularitySelfReferentialGetter2.ts, 0, 0))
optional: "true";
>optional : Symbol(ZodOptional.optional, Decl(noCircularitySelfReferentialGetter2.ts, 28, 58))
output: T["output"] | undefined;
>output : Symbol(ZodOptional.output, Decl(noCircularitySelfReferentialGetter2.ts, 29, 19))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter2.ts, 28, 22))
}
declare function object<T extends ZodShape>(shape: T): ZodObject<T>;
>object : Symbol(object, Decl(noCircularitySelfReferentialGetter2.ts, 31, 1))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter2.ts, 33, 24))
>ZodShape : Symbol(ZodShape, Decl(noCircularitySelfReferentialGetter2.ts, 8, 1))
>shape : Symbol(shape, Decl(noCircularitySelfReferentialGetter2.ts, 33, 44))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter2.ts, 33, 24))
>ZodObject : Symbol(ZodObject, Decl(noCircularitySelfReferentialGetter2.ts, 22, 2))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter2.ts, 33, 24))
declare function string(): ZodString;
>string : Symbol(string, Decl(noCircularitySelfReferentialGetter2.ts, 33, 68))
>ZodString : Symbol(ZodString, Decl(noCircularitySelfReferentialGetter2.ts, 3, 1))
declare function optional<T extends ZodType>(schema: T): ZodOptional<T>;
>optional : Symbol(optional, Decl(noCircularitySelfReferentialGetter2.ts, 34, 37))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter2.ts, 35, 26))
>ZodType : Symbol(ZodType, Decl(noCircularitySelfReferentialGetter2.ts, 0, 0))
>schema : Symbol(schema, Decl(noCircularitySelfReferentialGetter2.ts, 35, 45))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter2.ts, 35, 26))
>ZodOptional : Symbol(ZodOptional, Decl(noCircularitySelfReferentialGetter2.ts, 26, 1))
>T : Symbol(T, Decl(noCircularitySelfReferentialGetter2.ts, 35, 26))
const Category = object({
>Category : Symbol(Category, Decl(noCircularitySelfReferentialGetter2.ts, 37, 5))
>object : Symbol(object, Decl(noCircularitySelfReferentialGetter2.ts, 31, 1))
name: string(),
>name : Symbol(name, Decl(noCircularitySelfReferentialGetter2.ts, 37, 25))
>string : Symbol(string, Decl(noCircularitySelfReferentialGetter2.ts, 33, 68))
get parent() {
>parent : Symbol(parent, Decl(noCircularitySelfReferentialGetter2.ts, 38, 17))
return optional(Category);
>optional : Symbol(optional, Decl(noCircularitySelfReferentialGetter2.ts, 34, 37))
>Category : Symbol(Category, Decl(noCircularitySelfReferentialGetter2.ts, 37, 5))
},
});
export const name = Category.output.parent?.parent?.parent?.parent?.name;
>name : Symbol(name, Decl(noCircularitySelfReferentialGetter2.ts, 44, 12))
>Category.output.parent?.parent?.parent?.parent?.name : Symbol(name, Decl(noCircularitySelfReferentialGetter2.ts, 37, 25))
>Category.output.parent?.parent?.parent?.parent : Symbol(parent, Decl(noCircularitySelfReferentialGetter2.ts, 38, 17))
>Category.output.parent?.parent?.parent : Symbol(parent, Decl(noCircularitySelfReferentialGetter2.ts, 38, 17))
>Category.output.parent?.parent : Symbol(parent, Decl(noCircularitySelfReferentialGetter2.ts, 38, 17))
>Category.output.parent : Symbol(parent, Decl(noCircularitySelfReferentialGetter2.ts, 38, 17))
>Category.output : Symbol(ZodObject.output, Decl(noCircularitySelfReferentialGetter2.ts, 24, 20))
>Category : Symbol(Category, Decl(noCircularitySelfReferentialGetter2.ts, 37, 5))
>output : Symbol(ZodObject.output, Decl(noCircularitySelfReferentialGetter2.ts, 24, 20))
>parent : Symbol(parent, Decl(noCircularitySelfReferentialGetter2.ts, 38, 17))
>parent : Symbol(parent, Decl(noCircularitySelfReferentialGetter2.ts, 38, 17))
>parent : Symbol(parent, Decl(noCircularitySelfReferentialGetter2.ts, 38, 17))
>parent : Symbol(parent, Decl(noCircularitySelfReferentialGetter2.ts, 38, 17))
>name : Symbol(name, Decl(noCircularitySelfReferentialGetter2.ts, 37, 25))

View File

@ -0,0 +1,148 @@
//// [tests/cases/compiler/noCircularitySelfReferentialGetter2.ts] ////
=== noCircularitySelfReferentialGetter2.ts ===
interface ZodType {
optional: "true" | "false";
>optional : "true" | "false"
> : ^^^^^^^^^^^^^^^^
output: any;
>output : any
}
interface ZodString extends ZodType {
optional: "false";
>optional : "false"
> : ^^^^^^^
output: string;
>output : string
> : ^^^^^^
}
type ZodShape = Record<string, any>;
>ZodShape : ZodShape
> : ^^^^^^^^
type Prettify<T> = { [K in keyof T]: T[K] } & {};
>Prettify : { [K in keyof T]: T[K]; }
> : ^^^ ^^^^^^^^^^^^^^^^^^^^^
type InferObjectType<Shape extends ZodShape> = Prettify<
>InferObjectType : { [k in keyof Shape as Shape[k] extends { optional: "true"; } ? k : never]?: Shape[k]["output"] | undefined; } & { [k_1 in keyof Shape as Shape[k_1] extends { optional: "true"; } ? never : k_1]: Shape[k_1]["output"]; } extends infer T ? { [K in keyof T]: T[K]; } : never
> : ^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
{
[k in keyof Shape as Shape[k] extends { optional: "true" }
>optional : "true"
> : ^^^^^^
? k
: never]?: Shape[k]["output"];
} & {
[k in keyof Shape as Shape[k] extends { optional: "true" }
>optional : "true"
> : ^^^^^^
? never
: k]: Shape[k]["output"];
}
>;
interface ZodObject<T extends ZodShape> extends ZodType {
optional: "false";
>optional : "false"
> : ^^^^^^^
output: InferObjectType<T>;
>output : { [k in keyof T as T[k] extends { optional: "true"; } ? k : never]?: T[k]["output"] | undefined; } & { [k_1 in keyof T as T[k_1] extends { optional: "true"; } ? never : k_1]: T[k_1]["output"]; } extends infer T_1 ? { [K in keyof T_1]: T_1[K]; } : never
> : ^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
}
interface ZodOptional<T extends ZodType> extends ZodType {
optional: "true";
>optional : "true"
> : ^^^^^^
output: T["output"] | undefined;
>output : T["output"] | undefined
> : ^^^^^^^^^^^^^^^^^^^^^^^
}
declare function object<T extends ZodShape>(shape: T): ZodObject<T>;
>object : <T extends ZodShape>(shape: T) => ZodObject<T>
> : ^ ^^^^^^^^^ ^^ ^^ ^^^^^
>shape : T
> : ^
declare function string(): ZodString;
>string : () => ZodString
> : ^^^^^^
declare function optional<T extends ZodType>(schema: T): ZodOptional<T>;
>optional : <T extends ZodType>(schema: T) => ZodOptional<T>
> : ^ ^^^^^^^^^ ^^ ^^ ^^^^^
>schema : T
> : ^
const Category = object({
>Category : ZodObject<{ name: ZodString; readonly parent: ZodOptional<ZodObject<any>>; }>
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>object({ name: string(), get parent() { return optional(Category); },}) : ZodObject<{ name: ZodString; readonly parent: ZodOptional<ZodObject<any>>; }>
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>object : <T extends ZodShape>(shape: T) => ZodObject<T>
> : ^ ^^^^^^^^^ ^^ ^^ ^^^^^
>{ name: string(), get parent() { return optional(Category); },} : { name: ZodString; readonly parent: ZodOptional<ZodObject<{ name: ZodString; readonly parent: ZodOptional<ZodObject<any>>; }>>; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
name: string(),
>name : ZodString
> : ^^^^^^^^^
>string() : ZodString
> : ^^^^^^^^^
>string : () => ZodString
> : ^^^^^^
get parent() {
>parent : ZodOptional<ZodObject<{ name: ZodString; readonly parent: ZodOptional<ZodObject<any>>; }>>
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
return optional(Category);
>optional(Category) : ZodOptional<ZodObject<{ name: ZodString; readonly parent: ZodOptional<ZodObject<any>>; }>>
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>optional : <T extends ZodType>(schema: T) => ZodOptional<T>
> : ^ ^^^^^^^^^ ^^ ^^ ^^^^^
>Category : ZodObject<{ name: ZodString; readonly parent: ZodOptional<ZodObject<any>>; }>
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
},
});
export const name = Category.output.parent?.parent?.parent?.parent?.name;
>name : string | undefined
> : ^^^^^^^^^^^^^^^^^^
>Category.output.parent?.parent?.parent?.parent?.name : string | undefined
> : ^^^^^^^^^^^^^^^^^^
>Category.output.parent?.parent?.parent?.parent : { readonly parent?: any | undefined; name: string; } | undefined
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>Category.output.parent?.parent?.parent : { readonly parent?: any | undefined; name: string; } | undefined
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>Category.output.parent?.parent : { readonly parent?: any | undefined; name: string; } | undefined
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>Category.output.parent : { readonly parent?: any | undefined; name: string; } | undefined
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>Category.output : { readonly parent?: any | undefined; name: string; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>Category : ZodObject<{ name: ZodString; readonly parent: ZodOptional<ZodObject<any>>; }>
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>output : { readonly parent?: any | undefined; name: string; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>parent : { readonly parent?: any | undefined; name: string; } | undefined
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>parent : { readonly parent?: any | undefined; name: string; } | undefined
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>parent : { readonly parent?: any | undefined; name: string; } | undefined
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>parent : { readonly parent?: any | undefined; name: string; } | undefined
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>name : string | undefined
> : ^^^^^^^^^^^^^^^^^^

View File

@ -0,0 +1,20 @@
//// [tests/cases/compiler/noCircularitySelfReferentialGetter3.ts] ////
=== noCircularitySelfReferentialGetter3.ts ===
const a = {
>a : Symbol(a, Decl(noCircularitySelfReferentialGetter3.ts, 0, 5))
prop: 42,
>prop : Symbol(prop, Decl(noCircularitySelfReferentialGetter3.ts, 0, 11))
get self() {
>self : Symbol(self, Decl(noCircularitySelfReferentialGetter3.ts, 1, 11))
return a;
>a : Symbol(a, Decl(noCircularitySelfReferentialGetter3.ts, 0, 5))
},
} satisfies { prop: number; self: any };
>prop : Symbol(prop, Decl(noCircularitySelfReferentialGetter3.ts, 5, 13))
>self : Symbol(self, Decl(noCircularitySelfReferentialGetter3.ts, 5, 27))

View File

@ -0,0 +1,31 @@
//// [tests/cases/compiler/noCircularitySelfReferentialGetter3.ts] ////
=== noCircularitySelfReferentialGetter3.ts ===
const a = {
>a : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>{ prop: 42, get self() { return a; },} satisfies { prop: number; self: any } : { prop: number; readonly self: { prop: number; readonly self: any; }; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>{ prop: 42, get self() { return a; },} : { prop: number; readonly self: { prop: number; readonly self: any; }; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
prop: 42,
>prop : number
> : ^^^^^^
>42 : 42
> : ^^
get self() {
>self : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
return a;
>a : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
},
} satisfies { prop: number; self: any };
>prop : number
> : ^^^^^^
>self : any

View File

@ -0,0 +1,36 @@
//// [tests/cases/compiler/noCircularitySelfReferentialGetter4.ts] ////
=== noCircularitySelfReferentialGetter4.ts ===
const a = {
>a : Symbol(a, Decl(noCircularitySelfReferentialGetter4.ts, 0, 5))
prop: 42,
>prop : Symbol(prop, Decl(noCircularitySelfReferentialGetter4.ts, 0, 11))
get self() {
>self : Symbol(self, Decl(noCircularitySelfReferentialGetter4.ts, 1, 11))
return a;
>a : Symbol(a, Decl(noCircularitySelfReferentialGetter4.ts, 0, 5))
},
} satisfies { prop: number; self: any };
>prop : Symbol(prop, Decl(noCircularitySelfReferentialGetter4.ts, 5, 13))
>self : Symbol(self, Decl(noCircularitySelfReferentialGetter4.ts, 5, 27))
const prop = a.self.self.self.self.self.prop;
>prop : Symbol(prop, Decl(noCircularitySelfReferentialGetter4.ts, 7, 5))
>a.self.self.self.self.self.prop : Symbol(prop, Decl(noCircularitySelfReferentialGetter4.ts, 0, 11))
>a.self.self.self.self.self : Symbol(self, Decl(noCircularitySelfReferentialGetter4.ts, 1, 11))
>a.self.self.self.self : Symbol(self, Decl(noCircularitySelfReferentialGetter4.ts, 1, 11))
>a.self.self.self : Symbol(self, Decl(noCircularitySelfReferentialGetter4.ts, 1, 11))
>a.self.self : Symbol(self, Decl(noCircularitySelfReferentialGetter4.ts, 1, 11))
>a.self : Symbol(self, Decl(noCircularitySelfReferentialGetter4.ts, 1, 11))
>a : Symbol(a, Decl(noCircularitySelfReferentialGetter4.ts, 0, 5))
>self : Symbol(self, Decl(noCircularitySelfReferentialGetter4.ts, 1, 11))
>self : Symbol(self, Decl(noCircularitySelfReferentialGetter4.ts, 1, 11))
>self : Symbol(self, Decl(noCircularitySelfReferentialGetter4.ts, 1, 11))
>self : Symbol(self, Decl(noCircularitySelfReferentialGetter4.ts, 1, 11))
>self : Symbol(self, Decl(noCircularitySelfReferentialGetter4.ts, 1, 11))
>prop : Symbol(prop, Decl(noCircularitySelfReferentialGetter4.ts, 0, 11))

View File

@ -0,0 +1,61 @@
//// [tests/cases/compiler/noCircularitySelfReferentialGetter4.ts] ////
=== noCircularitySelfReferentialGetter4.ts ===
const a = {
>a : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>{ prop: 42, get self() { return a; },} satisfies { prop: number; self: any } : { prop: number; readonly self: { prop: number; readonly self: any; }; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>{ prop: 42, get self() { return a; },} : { prop: number; readonly self: { prop: number; readonly self: any; }; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
prop: 42,
>prop : number
> : ^^^^^^
>42 : 42
> : ^^
get self() {
>self : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
return a;
>a : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
},
} satisfies { prop: number; self: any };
>prop : number
> : ^^^^^^
>self : any
const prop = a.self.self.self.self.self.prop;
>prop : number
> : ^^^^^^
>a.self.self.self.self.self.prop : number
> : ^^^^^^
>a.self.self.self.self.self : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>a.self.self.self.self : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>a.self.self.self : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>a.self.self : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>a.self : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>a : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>self : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>self : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>self : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>self : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>self : { prop: number; readonly self: any; }
> : ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>prop : number
> : ^^^^^^

View File

@ -1,8 +1,5 @@
//// [tests/cases/compiler/propTypeValidatorInference.ts] ////
=== Performance Stats ===
Instantiation count: 1,000
=== node_modules/prop-types/index.d.ts ===
export const nominalTypeHack: unique symbol;
>nominalTypeHack : unique symbol

View File

@ -3,7 +3,7 @@
=== Performance Stats ===
Assignability cache: 2,500
Type Count: 10,000
Instantiation count: 100,000
Instantiation count: 50,000
Symbol count: 50,000
=== tsxReactPropsInferenceSucceedsOnIntersections.tsx ===

View File

@ -0,0 +1,48 @@
// @strict: true
// @noEmit: true
// https://github.com/microsoft/TypeScript/issues/61659
interface ZodType {
optional: "true" | "false";
output: any;
}
interface ZodString extends ZodType {
optional: "false";
output: string;
}
type ZodShape = Record<string, any>;
type Prettify<T> = { [K in keyof T]: T[K] } & {};
type InferObjectType<Shape extends ZodShape> = Prettify<
{
[k in keyof Shape as Shape[k] extends { optional: "true" }
? k
: never]?: Shape[k]["output"];
} & {
[k in keyof Shape as Shape[k] extends { optional: "true" }
? never
: k]: Shape[k]["output"];
}
>;
interface ZodObject<T extends ZodShape> extends ZodType {
optional: "false";
output: InferObjectType<T>;
}
interface ZodOptional<T extends ZodType> extends ZodType {
optional: "true";
output: T["output"] | undefined;
}
declare function object<T extends ZodShape>(shape: T): ZodObject<T>;
declare function string(): ZodString;
declare function optional<T extends ZodType>(schema: T): ZodOptional<T>;
const Category = object({
name: string(),
get parent() {
return optional(Category);
},
});

View File

@ -0,0 +1,48 @@
// @strict: true
// @noEmit: true
interface ZodType {
optional: "true" | "false";
output: any;
}
interface ZodString extends ZodType {
optional: "false";
output: string;
}
type ZodShape = Record<string, any>;
type Prettify<T> = { [K in keyof T]: T[K] } & {};
type InferObjectType<Shape extends ZodShape> = Prettify<
{
[k in keyof Shape as Shape[k] extends { optional: "true" }
? k
: never]?: Shape[k]["output"];
} & {
[k in keyof Shape as Shape[k] extends { optional: "true" }
? never
: k]: Shape[k]["output"];
}
>;
interface ZodObject<T extends ZodShape> extends ZodType {
optional: "false";
output: InferObjectType<T>;
}
interface ZodOptional<T extends ZodType> extends ZodType {
optional: "true";
output: T["output"] | undefined;
}
declare function object<T extends ZodShape>(shape: T): ZodObject<T>;
declare function string(): ZodString;
declare function optional<T extends ZodType>(schema: T): ZodOptional<T>;
const Category = object({
name: string(),
get parent() {
return optional(Category);
},
});
export const name = Category.output.parent?.parent?.parent?.parent?.name;

View File

@ -0,0 +1,9 @@
// @strict: true
// @noEmit: true
const a = {
prop: 42,
get self() {
return a;
},
} satisfies { prop: number; self: any };

View File

@ -0,0 +1,11 @@
// @strict: true
// @noEmit: true
const a = {
prop: 42,
get self() {
return a;
},
} satisfies { prop: number; self: any };
const prop = a.self.self.self.self.self.prop;