Is it possible to create a typeguard, or something else that accomplishes the same purpose, to check if a variable is a specific interface type in a typescript union?
interface Foo { a:string }
interface Bar { b:string }
(function() {
    function doStuff(thing: Foo | Bar) {
        if(typeof thing === 'Foo') {
            console.log('Foo');
        } 
        else if (typeof thing === 'Bar') {
            console.log('Bar');
        }
        else {
            console.log('unknown');
        }
    }
    var thing: Foo = {a:'a'};
    doStuff(thing);
})();
                Since Typescript 1.6 you can use user-defined type guards:
let isFoo = (object: Foo| Bar): object is Foo => {
    return "a" in object;
}
See https://www.typescriptlang.org/docs/handbook/advanced-types.html#user-defined-type-guards and https://github.com/microsoft/TypeScript/issues/10485
In TypeScript 2 you can use Discriminated Unions like this:
interface Foo {
    kind: "foo";
    a:string;
}
interface Bar {
    kind: "bar";
    b:string;
}
type FooBar = Foo | Bar;
let thing: FooBar;
and then test object using if (thing.kind === "foo").
If you only have 2 fields like in the example I would probably go with combined interface as @ryan-cavanaugh mentioned and make both properties optional:
interface FooBar {
    a?: string;
    b?: string
}
Note that in original example testing the object using if (thing.a !== undefined) produces error Property 'a' does not exist on type 'Foo | Bar'.
And testing it using if (thing.hasOwnProperty('a')) doesn't narrow type to Foo inside the if statement.
@ryan-cavanaugh is there a better way in TypesScript 2.0 or 2.1?
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With