Skip to content

Cannot assign type which should be compatible when conditional generics are used #50672

Closed
@EnkeyMC

Description

@EnkeyMC

Bug Report

Cannot assign type which should be compatible when conditional generics are used (also posted on SO but was only suggested to open issue here)

🕗 Version & Regression Information

Throws error on all versions available in TypeScript playground.

Playground Link

Playground Link

💻 Code

// Returns keyes that have type extending Types
type KeysMatching<T, Types> = { [K in keyof T]: T[K] extends Types ? K : never }[keyof T];

type Mapping = {
    STR: string;
    NUM: number;
    BOOL: boolean;
}

type Values = Mapping[keyof Mapping];

type Generic<T extends Values> = {
    typeStr: KeysMatching<Mapping, T>
}

const foo: Generic<boolean> = { typeStr: 'BOOL' };
const bar: Generic<Values> = foo;
// Type 'Generic<boolean>' is not assignable to type 'Generic<Values>'.
//  Type 'Values' is not assignable to type 'boolean'.
//    Type 'string' is not assignable to type 'boolean'.(2322)

// This works fine
type Conditional<T, V> = T extends V ? T : unknown;
const foo2: Conditional<string, Values> = 'string';
const bar2: Conditional<Values, Values> = foo2;

🙁 Actual behavior

TS throws error that foo is not assignable to bar

🙂 Expected behavior

TS does not throw error as the types should be compatible

Activity

whzx5byb

whzx5byb commented on Sep 7, 2022

@whzx5byb

A shorter repro:

type V<T> = { value: 0 extends T ? T : never };
type V0 = V<0>; // V0 = { value: 0 }
type VNumber = V<number>; // VNumber = { value: number }

type R1 = V<0> extends V<number> ? true : false;
//   ^?
type R2 = V0 extends VNumber ? true : false
//   ^?

Expect both to be true but R1 is false.

Related: #48070

fatcerberus

fatcerberus commented on Sep 7, 2022

@fatcerberus

Probably something to do with variance measurement - it seems like V<T> is incorrectly being measured as contravariant/invariant in T, likely because T occurs on the RHS of an extends check. R2 is correctly determined to be true because V0 extends VNumber bypasses variance measurement and does a full structural check.

andrewbranch

andrewbranch commented on Sep 9, 2022

@andrewbranch
Member

Yeah, duplicate of #48070

typescript-bot

typescript-bot commented on Sep 12, 2022

@typescript-bot
Collaborator

This issue has been marked as a 'Duplicate' and has seen no recent activity. It has been automatically closed for house-keeping purposes.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    DuplicateAn existing issue was already created

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

      Development

      No branches or pull requests

        Participants

        @andrewbranch@fatcerberus@EnkeyMC@whzx5byb@typescript-bot

        Issue actions

          Cannot assign type which should be compatible when conditional generics are used · Issue #50672 · microsoft/TypeScript