Defining Optional Properties in Typescript Interface
In Typescript, I am looking to define an interface with two optional properties. It is important that only one of these two properties is present within the instance object of this interface.
Attempted Solution
interface ISidebarCommon {
/**
* The label to be used in sidebar
*/
label: string;
/**
* Icon class in string format for the icon of the sidebar image
*/
icon: string;
}
interface IRoutableSidebarItem extends ISidebarCommon {
/**
* Role number to determine which route to redirect the user to
* This property is mutually exclusive with children
*/
role: number;
}
interface ITreeSidebarItem<SI> extends ISidebarCommon {
/**
* An array of children sidebar items.
* This property is mutually exclusive with role
*/
children: SI[];
}
interface ISidebar {
[index: number]: IRoutableSidebarItem | ITreeSidebarItem<IRoutableSidebarItem
| ITreeSidebarItem<IRoutableSidebarItem>
>;
}
Issue with Current Approach
Although my current solution ensures either role
or children
must be present, it does not enforce them as mutually exclusive. This means both properties can coexist within the instance object without triggering any errors during interface checks.
Illustrative Example
Below is a demonstration of an instance of the ISidebar
interface where objects contain both role
and children
, yet no linting errors are displayed:
const sidebarBroken: ISidebar = [
{
label: 'l1',
icon: 'c1',
role: 5,
children: [
{
label: 'l2',
icon: 'c2',
role: 6,
children: [
{
label: 'l3',
icon: 'c3',
role: 7,
},
],
},
],
},
];