preface
TypeScript + React type security is a three-piece package: Component, Redux, and Service typing.
Component typed
First install the React type dependency:
NPM i-d@types/react@types/react@types /react-domCopy the code
The base type
Generic components
React.ComponentType<P> = React.ComponentClass<P> | React.FunctionComponent<P>
Only component types (except HTML tag strings) can create a JSX.Element. For example:
Const C = () => <></>; const thisIsJSX = <C />; Const D = () => [<></>]; const throwError = <D />;Copy the code
So when we want to pass a component with props, we need to define:
interface Props {
/** Custom rendering component */
Cp: React.ComponentType<any>;
}
Copy the code
In the component that receives this property:
props => {
const { Cp } = props;
return <Cp />;
}
Copy the code
Functional component generics
FunctionComponent
The corresponding return value must be jsx.Element, for example:
Const ThisIsFC = () => <></>; function ThisIsFCToo() { return <></>; } // Const ThisNotFC = () => [<></>]; function ThisIsNotFCNeither() { return [<></>]; }Copy the code
Class component generics
React.ponentclass
const C: React.ComponentClass = xxxxx;
const jsx = <C />;
Copy the code
The generic element
The corresponding React.ElementType
, the equivalent React.ReactType has been marked “not recommended”.
JSX.Element = React.ElementType<any>
Component typing
Props typed
Taking a functional component as an example, define:
type Props = xxxxxxx;
const ThisIsFC: React.FC<Props> = props => <></>;
Copy the code
Props can be divided into the following subsets:
OwnProps
, that is, create JSX<ThisIsFC ... />
Attributes passed directlyStateProps
Properties obtained by connecting to the Redux StoreDispatchProps
Is also a property obtained by connecting to reduxRouteProps
That is, properties passed via the React-router-dom Route
So:
Props = OwnProps & RouteProps & StateProps & DispatchProps;
Copy the code
defineOwnProps
和 RouteProps
Type:
interface OwnProps {
/** name */
name: string;
}
import { RouteComponentProps } from 'react-router-dom';
type RouteProps = RouteComponentProps<{ id: string }>;
Copy the code
In this way, we can use:
const ThisIsFC = props => { { const { id } = props.match.params; // cosnt STR: string = id; Const num: number = id; } { const { name } = props; // cosnt STR: string = id; Const num: number = id; } return <></>; }Copy the code
Type inference StateProps & DispatchProps
StateProps & DispatchProps cannot be written, because they can be inferred from the map* function.
Inference StateProps:
type StateProps = ReturnType<typeof mapStateToProps>; // TODO: Redux type function mapStateToProps(state: IRootState) {return {user: state.xxx.xxx}; }Copy the code
Inference DispatchProps:
import { bindActionCreators, Dispatch } from 'redux'; // TODO: Redux typed import actions from '.. /redux/actions'; type DispatchProps = ReturnType<typeof mapDispatchToProps>; function mapDispatchToProps(dispatch: Dispatch) { return { actions: bindActionCreators(actions, dispatch) }; }Copy the code
In this way, we can use:
const ThisIsFC = props => {
props.user;
props.actions.doSomething;
return <></>;
}
Copy the code
Export components
import { connect } from 'react-redux';
export default connect<StateProps, DispatchProps, OwnProps>(
mapStateToProps,
mapDispatchToProps
)(ThisIsFC);
Copy the code
The same applies to class components, except that they have an extra State type set.
The advanced
Define generic components
function ThisIsGenericFC<P extends string | number>(props: Props<P>) {}
class ThisIsGenericComponent<P extends string | number> extends React.Component<Props<P>, State> {}
const jsxFC = <ThisIsGenericFC<string> />;
const jsxComponent = <ThisIsGenericComponent<number> />;
Copy the code
trailer
The next section is “Redux typing.”