Here is the code I'm working with:
interface IOrder {
id: string
created: string
name: string
age: number
}
type OrderKey = keyof IOrder
const columnNames: OrderKey[] = ['id', 'name', 'age', 'created']
const colValGenerators: {[key: string]: (obj: any) => any} = {
age: (obj: any) => Math.round((Date.now() - Date.parse(obj.created)) / 1000 / 60 / 60 / 24)
}
const orders: IOrder[] = [
{id: '1', created: 'Thu, 03 Feb 2022 14:59:16 GMT', name: 'John Doe', age: 0},
{id: '2', created: 'Thu, 04 Feb 2022 14:59:16 GMT', name: 'Jane Doe', age: 0}
]
for (const order of orders) {
for (const colName in colValGenerators) {
order[colName] = colValGenerators[colName](order) //ERROR
}
}
At the marked line //ERROR
, I encounter a TypeScript error:
Element implicitly has an 'any' type because expression of type 'string' can't be used to index type '{ id: string; created: string; name: string; age: number; }'.
No index signature with a parameter of type 'string' was found on type '{ id: string; created: string; name: string; age: number; }'.ts(7053)
The issue seems to stem from the fact that the keys in colValGenerators
can be arbitrary strings and not necessarily matching those in the IOrder
interface.
In attempting to address this, I modified:
const colValGenerators: {[key: string]: (obj: any) => any}
to:
const colValGenerators: {[key: OrderKey]: (obj: any) => any}
(Substituting string
with OrderKey
.) However, this adjustment led to another error:
An index signature parameter type cannot be a literal type or generic type. Consider using a mapped object type instead.ts(1337)
Considering this new challenge, I delved into mapped object types. While exploring the option of using Property in keyof IOrder
, I encountered an error mentioning No overload matches this call.
.
If anyone could provide guidance on how to resolve this issue, I would greatly appreciate it. Since my knowledge of TypeScript is limited, alternative solutions apart from my current approach are also welcome.