TypeScript multiple return types with identical parameters
<h1>Background</h1>

<p>Trying to get into the spirit of TypeScript, I am writing fully typed signatures in my Components and Services, which extends to my custom validation functions for angular2 forms.</p>

<p>I know that <a href="https://www.typescriptlang.org/docs/handbook/functions.html" rel="noreferrer">I can overload a function signature</a>, but this requires that the parameters are different for each return type because <code>tsc</code> compiles each signature to a separate function:</p>

<pre><code>function pickCard(x: {suit: string; card: number; }[]): number;
function pickCard(x: number): {suit: string; card: number; };
function pickCard(x): any { /*common logic*/ };
</code></pre>

<p>I also know that I can return a single type (like a Promise) which can <em>itself</em> be of multiple sub-types:</p>

<pre><code>private active(): Promise&lt;void|null&gt; { ... }
</code></pre>

<p>However, in the context of angular2 custom form validators, a single signature (one parameter of type <code>FormControl</code>) can return two distinct types: an <code>Object</code> with form errors, or <code>null</code> to indicate the control has no errors.</p>

<p>This, obviously, does not work:</p>

<pre><code>private lowercaseValidator(c: FormControl): null;
private lowercaseValidator(c: FormControl): Object {
    return /[a-z]/g.test(c.value) ? null : { lowercase: this.validationMessages.lowercase };
}
</code></pre>

<p>Nor do</p>

<pre><code>private lowercaseValidator(c: FormControl): null|Object {...}
private lowercaseValidator(c: FormControl): &lt;null|Object&gt; {...}
</code></pre>

<p>(Interestingly, I get the following errors, rather than something more informative:</p>

<pre><code>error TS1110: Type expected.
error TS1005: ':' expected.
error TS1005: ',' expected.
error TS1128: Declaration or statement expected.
</code></pre>

<p>)</p>

<h1>TL;DR</h1>

<p>Am I left simply using </p>

<pre><code>private lowercaseValidator(c: FormControl): any { ... }
</code></pre>

<p>which would seem to negate the advantage of having type signatures?</p>

<h1>More generally, looking forward to ES6</h1>

<p>While this question is inspired by angular2 forms validators, which are handled directly by the framework, so you might not care about declaring the return type, it is still generally-applicable, especially given ES6 constructs like <code>function (a, b, ...others) {}</code></p>

<p>Perhaps it's simply better practice to avoid writing functions that can return multiple types, but it is rather idiomatic, owing to JavaScript's dynamic nature.</p>

<h2>References</h2>

<ul>
<li><a href="https://stackoverflow.com/questions/13212625/typescript-function-overloading">TypeScript function overloading</a></li>
<li><a href="https://stackoverflow.com/questions/39191523/typescript-syntax-for-a-function-returning-observable-or-multiple-type">Typescript syntax for a function returning observable or multiple type</a></li>
<li><a href="https://github.com/Microsoft/TypeScript/issues/11700" rel="noreferrer">https://github.com/Microsoft/TypeScript/issues/11700</a></li>
<li><a href="https://github.com/Microsoft/TypeScript/issues/10727" rel="noreferrer">https://github.com/Microsoft/TypeScript/issues/10727</a> <code>(...spread) {}</code></li>
<li><a href="https://github.com/Microsoft/TypeScript/issues/10571" rel="noreferrer">https://github.com/Microsoft/TypeScript/issues/10571</a> <code>&lt; , , type&gt;</code></li>
</ul>