Skip to content

Variables (extracted from a discriminated union object) lose narrowed types after being exported #59652

@laam-egg

Description

@laam-egg

🔎 Search Terms

discriminate union export destructure destructuring

🕗 Version & Regression Information

  • This is the behavior in every version I tried (including the nightly one), and I reviewed the FAQ for entries about (export, destructure, discriminate, union).

⏯ Playground Link

https://www.typescriptlang.org/play/?#code/GYVwdgxgLglg9mABAQwhApgBygZSgJxjAHMB5MAGwE8AKAfQA8AuRAZwKOIEpEBvRAL4AoUJFgIUaLFAByIChQCCYACYBVVemBF0K8tXrNEYeRUQAfROBVadKnv2Ejw0eEgC2IKCGQKqAUTBkACMKXQAFZBh8AB4AFQA+GgA3XxB0FjiuFl4hRER0INDdFgJ0gBo8xFSKdJYZBDkFELD4hMqBCz4qwpaSxGBfVnRK-Jq641Mu61swXQ7u-JhgRBoTBUQAXm3qtPQLSxntOZUtnfH0Byr8-HRvfCR+XuKVFkGKYfLd2ozJjYEANxVTroD77XL5G53EAPPgFIphV6IMojb7pQRA-LCJwQBDsOHPREsfxfC4sABqgi2iE83l81ECfRUkWiNAARKw4O59uxCCQ0eg2VwgUJlqt-Fd8uSAYgAPSyxAAC3Qt0QMCgatYbA4JC+cAA1lVUBhsHg+WRKLRycKhCCwYtENK5Qrlar1Zq-mZDppjvNEAajVJsE0lKoNDZfXpLTRrUCnOgGJg4PgNbiwPingi-RcqZsaV4fH5GS8Wfh2ZzudrzQKhUJRSsaITdJKBTL5UqVft3TAtbzOF11l6rD67F8AO7oaIqQMm3A6i0GC7C52IfwAJTXpDXtoK9ohrZXrq7GqGcA9ff5lkH0xHJxn0hDynUt90+loS7bCvXm+3wiAA

💻 Code

function acceptStringOnly(_x: string) { }
function acceptNullAndUndefinedOnly(_x: null | undefined) { }

function mutuallyEnabledPair<T>(value: T): {
  enabled: true,
  value: NonNullable<T>,
} | {
  enabled: false,
  value: null | undefined,
} {
  if (null === value || undefined === value) {
    return { enabled: false, value: null };
  } else {
    return { enabled: true, value };
  }
}

const { enabled: E, value: V } = mutuallyEnabledPair("some string value");

if (E) {
  V; // here it is string, ok
  acceptStringOnly(V);
} else {
  V; // here it is null | undefined, ok
  acceptNullAndUndefinedOnly(V);
}

export const { enabled, value } = mutuallyEnabledPair("some string value")

if (enabled) {
  value; // here it is string | null | undefined, weird
  acceptStringOnly(value); // ERROR
} else {
  value; // here it also is string | null | undefined
  acceptNullAndUndefinedOnly(value); // ERROR
}

🙁 Actual behavior

When variables are destructured from an object of a discriminated union type and they are exported, those variables lose their narrowed types defined by the discriminated union type. Meanwhile, if the variables are NOT exported, their narrowed types will be preserved, which is the expected behavior, whether the variables are exported or not.

🙂 Expected behavior

Preserve narrowed types for variables that are:

  • Destructured from an object of a discriminated union type
  • Exported.

Additional information about the issue

I guess this issue may be more or less related to this one.

Metadata

Metadata

Assignees

No one assigned

    Labels

    Help WantedYou can do thisPossible ImprovementThe current behavior isn't wrong, but it's possible to see that it might be better in some cases

    Type

    No type

    Projects

    No projects

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions