Компонент более высокого порядка (HOC) в React вызывает дополнительный рендеринг обернутого компонента

Я использую HOC, чтобы обернуть все компоненты, которые должны иметь переводы. У каждого компонента есть свой файл перевода, который импортируется динамически. Также они разделяют некоторые общие функции. Итак, я создал HOC, функцию, принимающую компонент в качестве аргумента, возвращающего компонент с некоторыми дополнительными функциями (например, модифицированный componentDidMount).

Ниже представлены App.js и Translate.js (HOC).

App.js

import React, { Component } from 'react';
import translated from './Translate';
import './App.css';

class App extends Component {

  constructor(props) {
    super(props);
    this.state = {
      translation: {
        a: '',
      },
      translationRecieved: false
    }
  }
  componentDidMount() {
    console.info('APP mounted')
  }

  componentDidUpdate() {
      console.info('APP did update')
      if (!this.state.translationRecieved) {
         this.setState({
           translation: this.props.translation,
           translationRecieved: true
      })
    }
  }

  render() {
    console.info('APP renders')
    const { t } = this.props
    const { a } = this.state.translation

    return (
        <div className = "App">
          <p>This is state: a is {a}</p>
          <hr/>
          <p>Translated `a` is {t(a)}</p>
        </div>
    );
  }
}

const Apptranslated = translated(App);

export default Apptranslated ;

Translate.js

import React from 'react';
import en from './en.json';

const translated  = (WrappedComponent) => {
  class HOC extends React.Component {

    constructor(props) {
        super(props);
        this.state = {
            translation: null
        }
    }  

    componentDidMount() {
      console.info('HOC mounted')
      this.setState({
          translation: en
      })  
    }

    componentDidUpdate () {
      console.info('HOC did update')
    }


    translate = (val = '') => `**| ${val} |**`;

    render() {

      console.info('HOC renders')
      return <WrappedComponent 
        translation = {this.state.translation} t = {this.translate} {...this.props}/>;
    }
  }

  return HOC;
};

export default translated;

Вместо того, чтобы определять логику загрузки трансляции в каждом компоненте, я использовал HOC. HOC загружает переводы в HOCstate и затем передает их обернутому компоненту через механизм props. Обернутый компонент получает переданный props и сохраняет его на statecomponentDidUpdate). Итак, мои жизненные циклы:

HOC renders
APP renders
APP mounted
HOC mounted
----initial phase ended---
----HOC fetched resources---
HOC renders
APP renders
APP did update
HOC did update
----APP modifies its state---
APP renders
APP did update

Если бы я сделал то же самое с повторяющимся кодом (определяя логику в каждом компоненте)

App.js

import React, { Component } from 'react';
import en from './en.json';
import './App.css';

class App extends Component {

  constructor(props) {
    super(props);
    this.state = {
      translation: {
        a: '',
      },
      translationRecieved: false
    }
  }
  componentDidMount() {
    console.info('APP mounted')
    if (!this.state.translationRecieved) {
      this.setState({
        translation: en,
        translationRecieved: true
      })
    }
  }

  componentDidUpdate() {
      console.info('APP did update')
  }

  translate = (val = '') => `**| ${val} |**`;

  render() {
    console.info('APP renders')
    const { a } = this.state.translation

    return (
        <div className = "App">
          <p>This is state: a is {a}</p>
          <hr/>
          <p>Translated `a` is {this.translate(a)}</p>
        </div>
    );
  }
}

export default App;

я бы получил

APP renders
APP mounted
APP renders
APP did update

Таким образом, у меня есть дополнительный рендеринг, потому что я помещаю переводы, поступающие как реквизиты, в состояние компонента. Почему? Потому что они приходят асинхронный. Итак, у меня есть выбор: либо написать некоторую логику в компоненте, чтобы проверить, поступили ли переводы, и если у них нет резервных вариантов, либо подождать, пока они появятся, и использовать state, чтобы безопасно использовать их в моем компоненте App.

Я что-то упускаю или делаю неправильно? Или это нормальное поведение HOC? Возможно, Redux может решить эту проблему.

Если переводы загружаются асинхронно, у вас действительно нет особого выбора. Вы не можете отложить рендеринг, поэтому либо вы откладываете рендеринг, пока у вас не будет все, либо вы рендерите заполнитель.

Evan Trimboli 27.07.2018 10:25

Я добавил код. Какие методы позволяют отложить рендеринг? Считается ли это плохой практикой?

ogostos 27.07.2018 10:33

Я представляю, if (!a) return null; изнутри render()

ed' 27.07.2018 10:59

@EdwardSammutAlessi, это решило мою проблему. Спасибо!

ogostos 27.07.2018 11:55
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
В настоящее время производительность загрузки веб-сайта имеет решающее значение не только для удобства пользователей, но и для ранжирования в...
Безумие обратных вызовов в javascript [JS]
Безумие обратных вызовов в javascript [JS]
Здравствуйте! Юный падаван 🚀. Присоединяйся ко мне, чтобы разобраться в одной из самых запутанных концепций, когда вы начинаете изучать мир...
Система управления парковками с использованием HTML, CSS и JavaScript
Система управления парковками с использованием HTML, CSS и JavaScript
Веб-сайт по управлению парковками был создан с использованием HTML, CSS и JavaScript. Это простой сайт, ничего вычурного. Основная цель -...
JavaScript Вопросы с множественным выбором и ответы
JavaScript Вопросы с множественным выбором и ответы
Если вы ищете платформу, которая предоставляет вам бесплатный тест JavaScript MCQ (Multiple Choice Questions With Answers) для оценки ваших знаний,...
0
4
611
0

Другие вопросы по теме