How to tell flow that a dynamic string is just like a normal string
type Props = $ReadOnly<{
actionId: string,
onPress: (args:{dispatch: () => void}) => void
}> | $ReadOnly<{
actionId?:void,
onPress: () => void
}>
const A: (p:Props) => void = () => {}
const actionId: string = `1`
A({
actionId,
onPress:({dispatch}) => {dispatch()}
// ^ property `dispatch` is missing in undefined [1]. [incompatible-use]
})
A({
actionId: ''.concat(''),
onPress:({dispatch}) => {dispatch()}
// ^ property `dispatch` is missing in undefined [1]. [incompatible-use]
})
A({
actionId: '1',
onPress:({dispatch}) => {dispatch()}
// no error like it should be
})
Flow version: 0.259.1
Expected behavior
No error.
Actual behavior
Flow treats "dynamic" strings in a different way.
- Link to Try-Flow or Github repo:
https://flow.org/try/#1N4Igxg9gdgZglgcxALlAIwIZoKYBsD6uEEAztvhgE6UYCe+JADpdhgCYowa5kA0I2KAFcAtiRQAXSkOz9sADwxgJ+NPTbYuQ3BMnTZA+Y2yU4IwRO4A6SFBIrGVDGM7c+h46fNRLuKxJIGWh8MeT0ZfhYlCStpHzNsFBAMIQkIEQwJODAQfiEyfBE4eWw2fDgofDBMsAALfAA3KjgsXGxxZC4eAw0G-GhcWn9aY3wWZldu-g1mbGqJUoBaCRHEzrcDEgBrbAk62kXhXFxJ923d-cPRHEpTgyEoMDaqZdW7vKgoOfaSKgOKpqmDA+d4gB5fMA-P6LCCMLLQbiLOoYCqgh6-GDYRYIXYLSgkRZkCR4jpddwPfJLZjpOBkO4AX34kA0SRWxgABAAFSiwkjsgC87IAJAAlVhsADyUEGAB5gAAdKDs5Xs6JwaAASTYyHZ9lMUAQvEVKvZ0G5Px1AAoqAgSKg2LTHHtalaAJQCgB87IaEDgbHp7v5Xp9fsV9K9AB9hWL2FLZQqlSq1Zq2AB+ZAhthGxPKs0sEh29mWwPB31sMMexWK2z2dkAQStjGQ3N5Je9ZYFRbbwHpVce0FryagWp1eoqCE7AAMAIyTvt1y0Jk1DrXZk15i2Lh1MGq1AOe9nAbdOurF3tQAPzxfGpPKdXD7XsgDkT5s0HmlpfrrXKo3BeQW6Oru+5Boex67meYauleS63vCD46k+05Pj+uZQOa-6ATuzogV6R5Ac6kEXq6uQgA0JgkPeSQNAADFYABMACsACcVjTiA9JAA
This is a result of our contextual typing heuristics. For now, we only use specific syntactic patterns (e.g. only literal) to help pick one of the disjoint union.
There might be something we can do better here, since TS is able to do that.
A workaround could be setting the prop twice:
e.g.
A({
actionId: '',
actionId: ''.concat(''),
onPress:({dispatch}) => {dispatch()}
})
https://flow.org/try/#1N4Igxg9gdgZglgcxALlAIwIZoKYBsD6uEEAztvhgE6UYCe+JADpdhgCYowa5kA0I2KAFcAtiRQAXSkOz9sADwxgJ+NPTbYuQ3BMnTZA+Y2yU4IwRO4A6SFBIrGVDGM7c+h46fNRLuKxJIGWh8MeT0ZfhYlCStpHzNsFBAMIQkIEQwJODAQfiEyfBE4eWw2fDgofDBMsAALfAA3KjgsXGxxZC4eAw0G-GhcWn9aY3wWZldu-g1mbGqJUoBaCRHEzrcDEgBrbAk62kXhXFxJ923d-cPRHEpTgyEoMDaqZdW7vKgoOfaSKgOKpqmDA+d4gB5fMA-P6LCCMLLQbiLOoYCqgh6-GDYRYIXYLSgkRZkCR4jpddwPfJLZjpOBkO4AX34kA0SRWxgABAAFSiwkjsgC87IAJAAlVhsADyUEGAB5gAAdKDs5Xs6JwaAASTYyHZ9lMUAQvEVKvZ0G5Px1AAoqAgSKg2LTHHtalaAJQCgB87IaEDgbHp7v5Xp9fsV9K9AB9hWL2FLZQqlSq1Zq2AB+ZAhthGxPKs0sEh29mWwPB31sMMexWK2z2dkAQStjGQ3N5Je9ZYFRbbwHpVce0FryagWp1eoqCE7AAMAIyTvt1y0Jk1DkfsgDka+zy+U6uHWeNKrzFsXDqYNVqAc97OAp6ddWLvagAfni4PypX2vXm7fqp3KZ1G42NA8yWhurpboeUDmgWyAno656XkG163ueD5hq6L5Lkmf57gB07fjmppQfmdpwWezqIV6N7wc6aFPq6uQgA0JgkLuSQNAADFYABMABsADMVgcSA9JAA