Skip to content

Resolve type structure with optional propertiesΒ #62216

@fudom

Description

@fudom

πŸ” Search Terms

Resolve type structure with optional properties. Allow optional properties for inferred types. I can't find a better title right now. Sorry if this is a dup.

βœ… Viability Checklist

⭐ Suggestion

I wonder why only intersections are available in type when TypeScript resolves types automatically. Means, only the properties which exists in ALL objects are available. Optional properties not. I would expect that properties which only exist in some objects are also available as optional property, but well typed. Like {all: number, opt?: number}.

Code is worth 1000 words:

interface ValueType {
    a: number;
    b?: number;
    c?: number;
}

const myObject = {
    one: { a: 10 },
    two: { a: 10, b: 20 },
    three: { a: 10, c: 30 },
} satisfies Record<string, ValueType>;

for (const value of Object.values(myObject)) {
    // Problem here: Only 'a' is in suggestions.
    if (value.a) {} // works
    if (value.b) {} // error
    if (value.c) {} // error
    // Workaround would be `if ('c' in value)` but this is not the point.
    // Another workaround is to give the generic type an interface type.
}

// I wonder why, are the optional types not available? It makes no sense because TypeScript can handle optional type.
// I want to use all possible properties. Optional nullish values can be catched by type-guards like if-condition.
// I would expect that TypeScript resolves the values similar like my custom type `ValueType`.

πŸ“ƒ Motivating Example

Make code life easier...

Playground

πŸ’» Use Cases

Background: I could create the interface. But I don't write the key names again and again. Just create my object with defined value types. I could use Record<string, ...> but this would blur the key structure. I want the type as the object is created. This is the my path to the issue. But maybe only one case.

Note: The interface ValueType and satisfies or any other is not required and only one case. This is not the point of this issue. The core is: Why are the optional keys not in the inferred type? I see no reason why not, since optional properties are a legit part of a type.

Or is this a bug? I doubt. But if it's intentional, I don't understand why.

Metadata

Metadata

Assignees

No one assigned

    Labels

    QuestionAn issue which isn't directly actionable in code

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions