freeCodeCamp/curriculum/challenges/arabic/03-front-end-libraries/react/optimize-re-renders-with-sh...

6.0 KiB

id title challengeType isRequired videoUrl localeTitle
5a24c314108439a4d4036180 Optimize Re-Renders with shouldComponentUpdate 6 false تحسين Re-Renders مع shouldComponentUpdate

Description

حتى الآن ، إذا تلقى أي مكون state جديدة أو props جديدة ، فإنه يعيد نفسه وجميع أبنائه. هذا عادة ما يرام. لكن React يوفر طريقة دورة حياة يمكنك الاتصال بها عندما تتلقى مكونات state الطفل أو props الجديدة ، وتعلن تحديدًا إذا كان يجب تحديث المكونات أم لا. هذه الطريقة هي shouldComponentUpdate() ، وتستغرق nextProps و nextState كمعلمات. هذه الطريقة هي طريقة مفيدة لتحسين الأداء. على سبيل المثال ، السلوك الافتراضي هو أن المكون الخاص بك re-renders عندما يتلقى props الجديدة ، حتى إذا لم يتم تغيير props . يمكنك استخدام shouldComponentUpdate() لمنع هذا عن طريق مقارنة props . يجب أن تقوم الطريقة بإرجاع قيمة boolean تخبر رد ما إذا كان سيتم تحديث المكون أم لا. يمكنك مقارنة الدعائم الحالية ( this.props ) this.props التالية ( nextProps ) لتحديد ما إذا كنت بحاجة إلى التحديث أم لا ، وإرجاع true أو false وفقًا لذلك.

Instructions

يتم إضافة أسلوب shouldComponentUpdate() في مكون يسمى OnlyEvens . حاليًا ، يعود هذا الأسلوب إلى true لذا تعيد OnlyEvens الظهور في كل مرة تتلقى فيها props الجديدة. قم بتعديل الطريقة بحيث لا يتم تحديث OnlyEvens إلا إذا كانت value الدعائم الجديدة حتى. انقر فوق الزر " Add وشاهد ترتيب الأحداث في وحدة تحكم المستعرض الخاص بك أثناء تشغيل hooks دورة الحياة الأخرى.

Tests

tests:
  - text: يجب أن يقوم مكون <code>Controller</code> <code>OnlyEvens</code> مكون <code>OnlyEvens</code> كطفل.
    testString: 'assert((() => { const mockedComponent = Enzyme.mount(React.createElement(Controller)); return mockedComponent.find("Controller").length === 1 && mockedComponent.find("OnlyEvens").length === 1; })(), "The <code>Controller</code> component should render the <code>OnlyEvens</code> component as a child.");'
  - text: ''
    testString: 'assert((() => { const child = React.createElement(OnlyEvens).type.prototype.shouldComponentUpdate.toString().replace(/s/g,""); return child !== "undefined"; })(), "The <code>shouldComponentUpdate</code> method should be defined on the <code>OnlyEvens</code> component.");'
  - text: ''
    testString: 'async () => { const waitForIt = (fn) => new Promise((resolve, reject) => setTimeout(() => resolve(fn()), 250)); const mockedComponent = Enzyme.mount(React.createElement(Controller)); const first = () => { mockedComponent.setState({ value: 1000 }); return waitForIt(() => mockedComponent.find("h1").html()); }; const second = () => { mockedComponent.setState({ value: 10 }); return waitForIt(() => mockedComponent.find("h1").html()); }; const firstValue = await first(); const secondValue = await second(); assert(firstValue === "<h1>1000</h1>" && secondValue === "<h1>10</h1>", "The <code>OnlyEvens</code> component should return an <code>h1</code> tag which renders the value of <code>this.props.value</code>."); }; '
  - text: ''
    testString: 'async () => { const waitForIt = (fn) => new Promise((resolve, reject) => setTimeout(() => resolve(fn()), 250)); const mockedComponent = Enzyme.mount(React.createElement(Controller)); const first = () => { mockedComponent.setState({ value: 8 }); return waitForIt(() => mockedComponent.find("h1").text()); }; const second = () => { mockedComponent.setState({ value: 7 }); return waitForIt(() => mockedComponent.find("h1").text()); }; const third = () => { mockedComponent.setState({ value: 42 }); return waitForIt(() => mockedComponent.find("h1").text()); }; const firstValue = await first(); const secondValue = await second(); const thirdValue = await third(); assert(firstValue === "8" && secondValue === "8" && thirdValue === "42", "<code>OnlyEvens</code> should re-render only when <code>nextProps.value</code> is even."); }; '

Challenge Seed

class OnlyEvens extends React.Component {
  constructor(props) {
    super(props);
  }
  shouldComponentUpdate(nextProps, nextState) {
    console.log('Should I update?');
     // change code below this line
    return true;
     // change code above this line
  }
  componentWillReceiveProps(nextProps) {
    console.log('Receiving new props...');
  }
  componentDidUpdate() {
    console.log('Component re-rendered.');
  }
  render() {
    return <h1>{this.props.value}</h1>
  }
};

class Controller extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      value: 0
    };
    this.addValue = this.addValue.bind(this);
  }
  addValue() {
    this.setState({
      value: this.state.value + 1
    });
  }
  render() {
    return (
      <div>
        <button onClick={this.addValue}>Add</button>
        <OnlyEvens value={this.state.value}/>
      </div>
    );
  }
};

After Test

console.info('after the test');

Solution

// solution required