Is there a way to define that an array
['left', 'center', 'right'] is not a string[] but Position[] in this code example without storing it in a variable:
type Position = 'left' | 'center' | 'right';
const sidePositions: Position[] = ['left', 'center', 'right'].filter(p => p !== 'center');
Example is a very simplified version of what we are actually doing in our project, we cannot use just ['left', 'right'] array instead. The following workaround works but we won't get a TS error if we mistype some words and that can cause some human errors:
const sidePositions: Position[] = (['foo', 'bar', 'right'] as Position[]).filter(p => p !== 'center');
Of course it is possible to store the array in a typed variable first, but in our case it is less convenient. Here's a link to TS Playground
([...] as const).filter(...)? tsplay.dev/wep5EWas Position[]because we get an error, but we still get an error not in the right place['foo', 'bar', 'right']should be marked as invalid because it should be of typePosition[]and it is clearly not. Now we see thatsidePositionsvariable is invalid which is correct, but it is a result of other array being invalidsatisfiesoperator as discussed in github.com/microsoft/TypeScript/issues/47920. If it existed, you could write(['foo', 'bar', 'right'] satisfies Position[])and it would check without asserting or widening. It doesn't currently exist in TS. See the answer to the linked question for more information and the current workarounds.