Skip to content

Branded string literals revert to string in some cases #60990

Open
@mmalerba

Description

🔎 Search Terms

If I create a branded string literal it seems to respect the string literal in the basic case of assigning to a property, however it loses this information and just reverts to string when assigning to a property or in a template string.

It makes sense that the brand object needs to be dropped in these cases, but rather than converting to string, it should convert to the narrower literal type.

🕗 Version & Regression Information

  • This is the behavior in every version I tried, and I reviewed the FAQ for entries about branded string

⏯ Playground Link

https://www.typescriptlang.org/play/?#code/C4TwDgpgBAsiAyBLYEBOBDANgHgMpQgA8UA7AEwGcoLhVESBzAPigF4p8AyKAbwH0ARhnIAuXgF9xAbgBQAYwD2JGlHRsoAcnQbVVOEhQYcWjU1nylKwmJPr0UqAHpHUAO4LUAawoBCC8uAoEBttdQADABIedHEwh2coADN0RExffxUALzFosRIAVwBbATRxdR4AbXQAXTEADjKE5NTfIA

💻 Code

type MyLiteral<S extends string> = S & {_brand: {}};
const a = 'a' as MyLiteral<'a'>;

const x: 'a' = a; // works!
const y: 'a' = `${a}`; // fails!
const z: {a: number} = {[a]: 8} // fails!

🙁 Actual behavior

For y and z, the types don't match because a is converted to string rather than 'a'

🙂 Expected behavior

The types should match in all 3 cases, x, y, z

Additional information about the issue

No response

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions