This line of code
export default memo(LoadingOverlay);
Gives flow error
Missing type annotation for `P`. `P` is a type parameter declared in function type [1] and was implicitly instantiated at call of `memo` [2].Flow(InferError)
And this line
export default memo<TProps>(LoadingOverlay);
Gives compile time error.
What's the proper use of React memo
with flow
?
EDIT:
Here is the full file example
// @flow
// React modules
import React, { memo } from 'react';
// Material UI components
import Checkbox from '@material-ui/core/Checkbox';
import FormControlLabel from '@material-ui/core/FormControlLabel';
// Utils and defaults
import './checkbox.scss';
type TProps = {
value: string;
label: string;
checked: boolean;
disabled?: boolean;
onChange: Function;
};
/*
* Presentational component with following props:
* value: String, value as a name of checkbox
* label: String, checkbox label
* checked: Boolean, checkbox state
* disabled: Boolean, checkbox availability state
*/
const Checkbox = (props: TProps) => {
console.log('RENDER CHECKBOX');
const {
value,
label,
checked,
disabled
} = props;
const { onChange } = props;
return (
<FormControlLabel
control={
<Checkbox
checked={checked}
onChange={onChange(value)}
value={value}
disabled={disabled}
color="primary"
/>
}
label={label}
/>
);
};
Checkbox.defaultProps = {
disabled: false,
};
export default memo<TProps>(Checkbox);
Useful when you expect the same result from a component: you should wrap a component in your React app to React Memo when you know beforehand that it will render the same result to the DOM when given the same props to it. Thereby, it will result in a performance boost as it will memoize the result.
Strictly use React. memo() as a performance boost for applications with components that re-render often. However, keep in mind that React components will always re-render if the state changes — regardless of whether the component is wrapped in React.
Using memo will cause React to skip rendering a component if its props have not changed. This can improve performance.
memo is a higher order component. If your component renders the same result given the same props, you can wrap it in a call to React. memo for a performance boost in some cases by memoizing the result. This means that React will skip rendering the component, and reuse the last rendered result.
I have got the same problem. The problem is not with the Flow but with Babel.
You have got it right. Correct approach really is:
export default memo<Props>(MyComponent);
There are two ways to solve that.
Add // @flow
to the top of the file. The error comes from Babel and it needs the annotation there. Even though you might have all=true
in .flowconfig
(and Flow work perfectly) you need to do that.
Useful when using create-react-app
and do not want to eject
.
Add Babel preset for Flow and specify "all": true
option to your .babelrc
:
{
"presets": [
["@babel/preset-flow", {
"all": true
}]
]
}
However, this needs anyone using create-react-app
to eject
. (Or might use react-app-rewired but I have no experience with that.)
This solution is mentioned on here (thanks @fl0shizzle for mentioning it) and for discussion about create-react-app
solution look on here.
Make sure you have the latest version of flow. When I updated my flow version it just worked. I was missing the // @flow at the top so had to add all=true to my preset config.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With