Reputation: 11830
I have a state which looks like this
export interface IState {
relationType: string
relatedTableId: number | null
foreignKey: string
throughTableId: string
required: boolean
}
and
this.state = {
relationType: props.relation ? props.relation.relation_type : 'parent_relation',
relatedTableId: _.get(props, 'relation.related_table.id', null),
foreignKey: _.get(props, 'relation.foreign_key') || '',
throughTableId: _.get(props, 'relation.through_table_id') || '',
required: props.relation ? true :false
}
When I am trying to change state dynamically,
handleOnChange(
selected: ValueType<SelectOption>,
key: 'relationType' | 'throughTableId' | 'relatedTableId'
) {
const currentState = { ...this.state }
currentState[key] = (selected as SelectOption).value;
this.setState({ ...currentState })
}
Here, TS is throwing following error
Type 'string' is not assignable to type 'never'
Any idea what I could be doing wrong?
THis is what Select Option looks like (if this make any difference)
type SelectOption = {
value: string | number
label: string
}
This is the error
Upvotes: 0
Views: 590
Reputation: 3666
Typescript is pointing out that you're not doing all the required type checks. To expand on the the other answers, TS wants to see code that looks more like:
function handleOnChange(
selected: ValueType<SelectOption>,
key: 'relationType' | 'throughTableId' | 'relatedTableId'
) {
const currentState = { ...this.state }
const selectedValue = (selected as SelectOption).value
if (key === 'relationType' || key === 'throughTableId') {
if (typeof selectedValue === 'string') {
currentState[key] = selectedValue
}
}
else {
if (typeof selectedValue === 'number') {
currentState[key] = selectedValue
}
}
}
The above uses explicit type checks which TS understands and it should compile without errors.
Upvotes: 0
Reputation: 9248
The keys you're trying to assign a value of type string | number
to are not compatible with that type. They can either be assigned string
or number | null
but none of them can accept string | number
.
relationType: string
relatedTableId: number | null
throughTableId: string
Unless you narrow the type of selected.value
to make sure you:
TypeScript won't let you assign it to any of the fields you're trying to.
EDIT
As sam256 said the reason it says "is not assignable to never
" is because relationType
, relatedTableId
and throughTableId
have no overlap in types, so there is no type of value that can be assigned to all three of them.
This wouldn't be the case if key
was "relationType" | "throughTableId"
for example, because in that case currentState[key]
could be assigned a value of type string
, because:
currentState["relationType" | "throughTableId"]: string
Upvotes: 1
Reputation: 1421
Typescript is identifying a real problem here. What if you passed handleOnChange a "selected.value" that was a string, but a "key" value of "relatedTableId"? Your function would be trying to assign a string to a number. In other words you actually have a potential type mismatch in your code which TS is flagging.
I believe the wording of the error is because TS is inferring that currentState[key] is the intersection of string and number, which is never.
Upvotes: 1