I’m trying to wrap my head around how this is supposed to work. I have a base class with props. Then I have an interface for the props for the child class. I am getting the typescript error
Property 'lineWidth' does not exist on type 'Readonly<BasicChartProps<LineChartProps<T>>>'.ts(2339)
here is my sample code example
import React from 'react';
export interface BasicChartProps<T> {
data: T[];
x_key: keyof T;
y_key: keyof T;
}
export type BasicChartState<T> = {
data: T[];
x_key: keyof T;
y_key: keyof T;
x_margin: number;
y_margin: number;
};
export class BasicChart<T> extends React.Component<
BasicChartProps<T>,
BasicChartState<T>
> {
state: BasicChartState<T> = {
x_margin: 50,
y_margin: 50,
data: this.props.data || [],
x_key: this.props.x_key,
y_key: this.props.y_key,
};
render(): React.ReactNode {
return (
<div>
<div>x_margin: {this.state.x_margin}</div>
<div>y_margin: {this.state.y_margin}</div>
</div>
);
}
}
export interface LineChartProps<T> extends BasicChartProps<T> {
lineWidth: number;
}
export class LineChart<T> extends BasicChart<LineChartProps<T>> {
render(): React.ReactNode {
const {lineWidth} = this.props;
return <div>lineWidth: {lineWidth}</div>;
}
}
I’m hoping someone can shed some light on what I am doing wrong.
2
Answers
Kind of hacky, but you can pass
LineChartProps
as another template variable:Problem
Passing
LineChartProps
toBasicChart
‘s type parameter passes it toBasicChartProps
‘s type parameter which then gets used on various properties on that interface. Here’s a visualisation:Solution
I suspect the above isn’t what was intended and that you’re trying to get the type of
LineChart
‘s type parameter passed all the way down toBasicChartProps
. Like this?To get that to work, I think something like this would be ideal:
I think it’s possible by updating
BasicChart
to the following:The
infer
keyword is used to extract the (first) generic type parameter fromProps
and assign it toT
.T
is then passed toBasicChartProps
andBasicChartState
.Here’s a demo in TypeScript Playground. At the end is the following to test things work as expected (do play around yourself to verify things work to your own expectations):