Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Symbols as literal types #7436

Closed
Ciantic opened this issue Mar 8, 2016 · 3 comments · Fixed by #15473
Closed

Symbols as literal types #7436

Ciantic opened this issue Mar 8, 2016 · 3 comments · Fixed by #15473
Labels
Needs Proposal This issue needs a plan that clarifies the finer details of how it could be implemented. Suggestion An idea for TypeScript

Comments

@Ciantic
Copy link

Ciantic commented Mar 8, 2016

Consider following use case for string literals at the moment in Flux:

interface IAction {
    actionType: string
}
interface ISayHelloAction extends IAction {
    actionType: "SAY_HELLO";
}

// Somewhere in your code you check that the message is ISayHelloAction from that actionType string using normal if

function processActions(action: IAction|ISayHelloAction|...) {
    if (action.actionType === "SAY_HELLO") {
        // action is ISayHelloAction
    }
}

(Above example assumes #6028 gets fixed, for the moment one can implement own type guard.)

But it would be even better if one could use Symbol for the same thing:

interface IAction {
    actionType: Symbol
}
const SAY_HELLO: Symbol = Symbol();

interface ISayHelloAction extends IAction {
    actionType: SAY_HELLO; // "Symbol literal type"
}

function processActions(action: IAction|ISayHelloAction|...) {
    if (action.actionType === SAY_HELLO) {
        // ... is ISayHelloAction
    }
}

These symbol literal types has same type guard requirement as literal types.

@yortus
Copy link
Contributor

yortus commented Mar 9, 2016

FYI there is some previous discussion about symbols as literal types starting here.

@mhegazy mhegazy added Suggestion An idea for TypeScript Needs Proposal This issue needs a plan that clarifies the finer details of how it could be implemented. labels Mar 9, 2016
@Artazor
Copy link
Contributor

Artazor commented Mar 14, 2016

Would be useful.

@mnpenner
Copy link

Here's another example where this would be useful:

export const __skip__ = Symbol('skip');

function filterMapArray<ValueType,ReturnType>(iterable: Iterable<ValueType>, callback: (v: ValueType, k: number) => ReturnType|symbol): ReturnType[] {
    let accum = [];

    let i = 0;
    for(let x of iterable) {
        let y = callback(x, i++);
        if(y !== __skip__) {
            accum.push(y);
        }
    }

    return accum; // TS2322: Type '(symbol | ReturnType)[]' is not assignable to type 'ReturnType[]'.
  Type 'symbol | ReturnType' is not assignable to type 'ReturnType'. Type 'symbol' is not assignable to type 'ReturnType'.
}

This code won't compile because I can only typehint against symbol, but not __skip__. TS can't determine that accum contains only ReturnTypes.

@microsoft microsoft locked and limited conversation to collaborators Jun 19, 2018
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
Needs Proposal This issue needs a plan that clarifies the finer details of how it could be implemented. Suggestion An idea for TypeScript
Projects
None yet
Development

Successfully merging a pull request may close this issue.

5 participants