Type Helpers 9 exercises
solution

Set a Default Type Value in a Type Helper

The solution to this challenge is simple, but gives us good insight into some new syntax.

Updating CreateDataShape to have TError = undefined tells TypeScript that the second argument doesn't need to be passed in:


type CreateDataShape<TData, TError = undefined> = {
data: TData;
erro

Loading solution

Transcript

0:00 The solution here is super simple and gives us a nice insight into some new syntax here. We can say TError = undefined. Now, what this does is it basically says you don't need to pass that second element then.

0:15 If we add this CreateDataShape, let's say we add this to an example here, then what we're going to get is we're going to get data: string; and error: undefined;. If we change this to a number, then of course we get data: number; and error: undefined;.

0:31 Finally, we can pass anything to this error, actually. If we just parse an error inside here, then we get data: number; and error: Error. We can also combine this with the extends thing if we want to. We can say TError extends an error clause.

0:46 In fact, there, what it's going to do it's going to say Type 'undefined' does not satisfy the constraint 'Error'. We can't provide a default that doesn't match our constraint. We could say error or undefined if we want to. There we start getting a little bit messy, right?

1:00 We can see that we've got TError extends Error or undefined = undefined. You'll find this in some type definitions, is that it just gets quite clumped together and quite grouped up. There's not a huge perfect way to avoid this, really.

1:14 We could go Type this = type MaybeError = Error undefined. Then TError extends MaybeError. That's a way to maybe clean it up nicely. That gives you a sense of what's possible here. Everything in this can have a default. We can't specify just the same with functions if we say TThird here, for instance.

1:32 Then this is impossible because required type parameters may not follow optional type parameters just like in normal functions. This is a really, really useful bit of syntax. It lets us just provide sensible defaults if we don't want to be parsing these, and lets us be more expressive with our type helpers.