PureComponentDebug.js 2.2 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273
  1. /**
  2. * Copyright (c) Facebook, Inc. and its affiliates.
  3. *
  4. * This source code is licensed under the MIT license found in the
  5. * LICENSE file in the root directory of this source tree.
  6. *
  7. * @flow
  8. * @format
  9. */
  10. 'use strict';
  11. const React = require('react');
  12. opaque type DoNotCommitUsageOfPureComponentDebug = {...};
  13. /**
  14. * Identifies which prop or state changes triggered a re-render of a PureComponent. Usage:
  15. *
  16. * Change `extends React.PureComponent` to `extends PureComponentDebug` or inject it
  17. * everywhere by putting this line in your app setup:
  18. *
  19. * React.PureComponent = require('PureComponentDebug');
  20. *
  21. * Should only be used for local testing, and will trigger a flow failure if you try to
  22. * commit any usages.
  23. */
  24. class PureComponentDebug<
  25. P: DoNotCommitUsageOfPureComponentDebug,
  26. S: ?Object = void,
  27. > extends React.Component<P, S> {
  28. shouldComponentUpdate(nextProps: P, nextState: S): boolean {
  29. const tag = this.constructor.name;
  30. let ret = false;
  31. const prevPropsKeys = Object.keys(this.props);
  32. const nextPropsKeys = Object.keys(nextProps);
  33. if (prevPropsKeys.length !== nextPropsKeys.length) {
  34. ret = true;
  35. console.warn(
  36. 'PureComponentDebug: different prop keys',
  37. tag,
  38. prevPropsKeys.filter(key => !nextPropsKeys.includes(key)),
  39. nextPropsKeys.filter(key => !prevPropsKeys.includes(key)),
  40. );
  41. }
  42. const prevStateKeys = Object.keys(this.state || {});
  43. const nextStateKeys = Object.keys(nextState || {});
  44. if (prevStateKeys.length !== nextStateKeys.length) {
  45. ret = true;
  46. console.warn(
  47. 'PureComponentDebug: different state keys',
  48. tag,
  49. prevStateKeys.filter(key => !nextStateKeys.includes(key)),
  50. nextStateKeys.filter(key => !prevStateKeys.includes(key)),
  51. );
  52. }
  53. for (const key in this.props) {
  54. if (this.props[key] !== nextProps[key]) {
  55. ret = true;
  56. console.warn('PureComponentDebug: different prop values', tag, key);
  57. }
  58. }
  59. for (const key in this.state) {
  60. if (this.state[key] !== (nextState || {})[key]) {
  61. ret = true;
  62. console.warn('PureComponentDebug: different state values', tag, key);
  63. }
  64. }
  65. return ret;
  66. }
  67. }
  68. module.exports = PureComponentDebug;