Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions types/react/index.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -255,7 +255,7 @@ declare namespace React {

// Base component for plain JS classes
// tslint:disable-next-line:no-empty-interface
interface Component<P = {}, S = {}, SS = never> extends ComponentLifecycle<P, S, SS> { }
interface Component<P = {}, S = {}, SS = any> extends ComponentLifecycle<P, S, SS> { }
class Component<P, S> {
constructor(props: P, context?: any);

Expand Down Expand Up @@ -283,7 +283,7 @@ declare namespace React {
};
}

class PureComponent<P = {}, S = {}> extends Component<P, S> { }
class PureComponent<P = {}, S = {}, SS = any> extends Component<P, S, SS> { }

interface ClassicComponent<P = {}, S = {}> extends Component<P, S> {
replaceState(nextState: S, callback?: () => void): void;
Expand Down
14 changes: 13 additions & 1 deletion types/react/test/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,10 @@ interface State {
seconds?: number;
}

interface Snapshot {
baz: string;
}

interface Context {
someValue?: string;
}
Expand All @@ -51,7 +55,7 @@ declare const container: Element;
// Top-Level API
// --------------------------------------------------------------------------

class ModernComponent extends React.Component<Props, State>
class ModernComponent extends React.Component<Props, State, Snapshot>
implements MyComponent, React.ChildContextProvider<ChildContext> {
static propTypes: React.ValidationMap<Props> = {
foo: PropTypes.number
Expand Down Expand Up @@ -103,6 +107,14 @@ class ModernComponent extends React.Component<Props, State>
shouldComponentUpdate(nextProps: Props, nextState: State, nextContext: any): boolean {
return shallowCompare(this, nextProps, nextState);
}

getSnapshotBeforeUpdate(prevProps: Readonly<Props>) {
return { baz: `${prevProps.foo}baz` };
}

componentDidUpdate(prevProps: Readonly<Props>, prevState: Readonly<State>, snapshot: Snapshot) {
return;
}
}

class ModernComponentArrayRender extends React.Component<Props> {
Expand Down
20 changes: 20 additions & 0 deletions types/react/test/tsx.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -150,6 +150,26 @@ class ComponentWithNewLifecycles extends React.Component<NewProps, NewState, { b
return this.state.bar;
}
}
<ComponentWithNewLifecycles foo="bar" />;

class PureComponentWithNewLifecycles extends React.PureComponent<NewProps, NewState, { baz: string }> {
static getDerivedStateFromProps: React.GetDerivedStateFromProps<NewProps, NewState> = (nextProps) => {
return { bar: `${nextProps.foo}bar` };
}

getSnapshotBeforeUpdate(prevProps: Readonly<NewProps>) {
return { baz: `${prevProps.foo}baz` };
}

componentDidUpdate(prevProps: Readonly<NewProps>, prevState: Readonly<NewState>, snapshot: { baz: string }) {
return;
}

render() {
return this.state.bar;
}
}
<PureComponentWithNewLifecycles foo="bar" />;

class ComponentWithLargeState extends React.Component<{}, Record<'a'|'b'|'c', string>> {
static getDerivedStateFromProps: React.GetDerivedStateFromProps<{}, Record<'a'|'b'|'c', string>> = () => {
Expand Down