Skip to content

Instantly share code, notes, and snippets.

@variousauthors
Created November 13, 2021 20:17
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save variousauthors/46b9dbfde0600adc22cf62f34ccfee52 to your computer and use it in GitHub Desktop.
Save variousauthors/46b9dbfde0600adc22cf62f34ccfee52 to your computer and use it in GitHub Desktop.
Type Guard Troubles

I have this helper I use to make type guards.

const typeGuard = buildTypeGuard<{ name: string, friends: IFriend[] }>({
  name: isString,
  friends: [isFriend],
})

It takes a type and an argument. The argument is a "type guide" which is instructions on how to build the typeguard. The type determines the shape of the type guide. So if you pass in a type with { friends: IFriend[] } you must pass in a type guide that includes { friends: [isFriend] }.

This [isFriend] syntax is type guide's way of expressing "array of friends". I like this syntax because it is simple. This helper works and it is nice. The problem is, as it stands, it cannot infer the type correctly.

const typeGuard = buildTypeGuard({
  name: isString,
  friends: [isFriend],
})

Passing in a guide and no type, it will infer the wrong type for the type guard. I really want it to be able to infer the correct type. I use this library to validate the shape of data coming into my system and sometimes the data is quite big and complex. Having to explicitly write out a type and a type guard is too much overhead. If I could just write out the type guard and have the type infered it would be great.

Here's what I've tried: playground.

// this right here is the problem
type TypeDescription<T> = {
  [key in keyof T]: TypeGuard<T[key]> | [TypeGuard<T[key]>]
}

I feel like I should be able to do something like...

type TypeDescription<T> = {
  [key in keyof T]: T[key] extends Array<infer U> ? [TypeGuard<U>] : TypeGuard<T[key]>
}

But this results in the type for the array field being infered as unknown.

Can someone on this vast internet help me find a type?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment