Q:

Testing interface at runtime without casting

I have code like this, where I need to handle objects with potentially different interfaces:
interface A { 
    a: any[];
}
interface B { 
    b: any[];
}

function doSomething(x: A | B) {
    if (x.a && x.a.length) console.log(x.a)
    if (x.b && x.b.length) console.log(x.b) 
}

and each instance of x.a and x.a.length results in a compile time error stating 

Property 'a' does not exist on type 'A | B'.
  Property 'a' does not exist on type 'B'.

I know I could type cast every single instance where I test the interface of x (i.e. if( (<A>x).a && (<A>x).a.length) ) but with dozens of type / attribute combinations, this gets old in a hurry.
Is there a way of testing the interface of an object at runtime in typescript without casting every single test? 

A:

You need to define type guards:
function isA(obj: A | B): obj is A {
    return (obj as A).a != undefined;
}

function isB(obj: A | B): obj is B {
    return (obj as B).b != undefined;
}

function doSomething(x: A | B) {
    if (isA(x)) console.log(x.a);
    if (isB(x)) console.log(x.b);
}

(code in playground)
The compiler knows that if isA(x) fails then x is B, so this works as well:
function doSomething(x: A | B) {
    if (isA(x)) console.log(x.a);
    else console.log(x.b);
}

(code in playground)

