I'm converting a project from JS to TS, and a little stuck on the following object:
let campaigns = {
TOTAL: {
cost: 3,
revenue: 6,
year: 2020,
},
campaignId_1: {
name: "campaignName1",
cost: 1,
revenue: 4,
video: "video1",
},
campaignId_2: {
name: "campaignName2",
cast: 2,
revenue: 2,
video: "video2",
}
}
In Typescript, I want the object to ALWAYS have the "TOTAL" key with type-A value, and the rest of the keys are dynamic, and should have type-B value.
So first I've defined the child types:
type type_A = {
cost: number,
revenue: number,
year: number,
}
type type_B = {
name: string,
cast: number,
revenue: number,
video: string,
}
And now I'm trying to create a type for the parent Campaigns object:
Try 1:
type ICampaigns = {
TOTAL: type_A,
[key: string]: type_B, // Hoping it will be handled as "default" or "for all other non-defined keys"
}
But got the following error message: Property 'TOTAL' of type 'type_A' is not assignable to string index type 'type_B'.(2411)
.
Try 2:
type ICampaigns = {
TOTAL: type_A,
} & {
[key: string]: type_B, // Hoping it will be handled as "default" or "for all other non-defined keys"
}
And now it compiles, but when trying to define such instance I'm getting errors no matter if TOTAL is of type_A or type_B.
let campaigns: ICampaigns = {
TOTAL: {
cost: 3,
revenue: 6,
year: 2020,
},
campaignId_1: {
name: "campaignName1",
cost: 1,
revenue: 4,
video: "video1",
},
campaignId_2: {
name: "campaignName2",
cost: 2,
revenue: 2,
video: "video2",
}
}
I know that doing type_A|type_B
will solve my problem, but then the TOTAL key will be able to have the type_B object as value, and other dynamic keys can have type_A values, which is not good.
I also know I can convert the Campaigns object to have only defined keys:
let campaigns: ICampaigns = {
TOTAL: {
cost: 3,
revenue: 6,
year: 2020,
},
campaignDetails: { // <--- change
campaignId_1: {
name: "campaignName1",
cost: 1,
revenue: 4,
video: "video1",
},
campaignId_2: {
name: "campaignName2",
cost: 2,
revenue: 2,
video: "video2",
}
}
}
But that's a lot of converting to do in my project, and also feels like giving up...