React do zero: ciclo de vida, stateless components e arquitetura flux

React 15 de Nov de 2017

Esse post é a segunda parte da série “React do zero”. Se você ainda não leu, recomendo ver a primeira parte primeiro:

React do zero: componentização, propriedades e estado

Na primeira parte dessa série, falamos sobre componentização, propriedades e estado, três assuntos básicos para quem quer iniciar no React. Nesse post vamos falar de ciclo de vida de componentes, onde você vai entender o poder de utilizar essa organização componentizada, e também vamos mais a fundo em alguns conceitos do React.

Ciclo de vida

Todo componente no React possui um ciclo de vida, dizemos que os componentes são montados em tela, podem sofrer alterações e no fim são desmontados. Assim, a cada passo do ciclo de vida de um componente conseguimos chamar métodos interceptando sua renderização tradicional ou captando informações desse ciclo. Esses métodos são definidos junto à classe do componente, o render é um deles. Vamos entender como tudo isso funciona:

constructor

Apenas de não estar diretamente atrelado ao ciclo de vida do componente, o método constructor é a primeira função executada no componente.

class App extends Component {
  constructor(props) {
    super(props);
  }
}

Obs.: Sempre que definirmos o constructor, precisamos repassar as props recebidas para o componente pai Component.

componentWillMount

Após do constructor o método seguinte executado é o componentWillMount, ainda antes do render. Esse método é executado 1 vez por componente e pode inclusive realizar alterações no estado:

class App extends Component {
  componentWillMount() {
    this.setState({ loading: true });
  }
}

render

Logo após, o método render é chamado construindo a View do nosso componente, esse método é chamado toda vez que uma alteração nas propriedades ou estado do componente é realizada. Você não deve utilizar qualquer função nesse método, apenas retornar conteúdo JSX.

componentDidMount

Chamado após o render indica que a renderização inicial do nosso componente foi finalizada, é o local recomendado para fazer qualquer processo assíncrono ou de efeito colateral como chamadas à API, referenciar componentes criados no render ou inclusive alterar o estado, disparando uma nova atualização no fluxo do componente.

class App extends Component {
  componentDidMount() {
    // O render já executou, o que faremos agora?
  }
}

Agora finalizamos os métodos responsáveis pela primeira renderização dos componentes e vamos partir para os métodos responsáveis pela atualização no ciclo de vida:

componentWillReceiveProps

Executado automaticamente toda vez que alguma propriedade do componente for atualizada, por exemplo, imagine estarmos passando a propriedade title ao componente da seguinte forma:

<App title="Meu título" />

E em algum momento alterarmos essa propriedade Meu título para Outro título, o componentWillReceiveProps do App irá ser avisado e receberá como parâmetro as novas propriedades. Esse método é muito utilizado quando o estado do nosso componente é composto por propriedades, e dessa forma podemos alterar o estado por esse método:

class App extends Component {
  componentWillReceiveProps(props) {
    this.setState({ title: `Aplicação ${props.title}` });
  }
}

shouldComponentUpdate

Método responsável por determinar se o componente deve realizar o render novamente ou não. Lembrando que qualquer alteração de propriedade ou estado do componente faz com que ele gere uma nova renderização, mas isso é realmente necessário? Talvez não. Imagine que seu componente mostre apenas o título no render e você atualize a propriedade de descrição, isso não deveria causar um render, correto? Nesse caso verificamos se o título foi alterado, se não simplesmente retornamos false para indicar que não precisamos atualizar o componente:

class App extends Component {
  shouldComponentUpdate(newProps, newState) {
    return newProps.title !== this.props.title;
  }
}

Obs.: Como o componente ouve atualizações no estado e propriedades, você receberá essas duas informações no shouldComponentUpdate.

componentWillUpdate

Ok, o shouldComponentUpdate liberou a atualização, o componentWillUpdaterealiza a intermediação entre o render e dessa forma você poderá realizar alguma preparação antes de realizar o render. Esse método também recebe as novas propriedades e estado. Após esse método, o render é disparado novamente com as alterações.

componentDidUpdate

Executado após o novo render indicando que o componente foi atualizado com sucesso. Recebe as propriedades e estado antigos como parâmetro.


Fora desse ciclo de criação e atualização, existem mais dois métodos:

componentWillUnmount

Chamado antes de um componente ser desmontado, ótimo para cancelar EventListeners ou setIntervals que ainda possam estar sendo executados.

componentDidCatch

A partir do React 16 você já pode ouvir erros causados durante o ciclo de vida do componente utilizando o componentDidCatch, você inclusive pode passar esses erros para a View utilizando o setState:

class App extends Component {
  componentDidCatch(error, info) {
    this.setState({ errorMessage: error.message });
  }
}

Para exemplificar todo o fluxo desse processo, veja na imagem a baixo como correm as informações do ciclo de vida no React:

Fonte: https://www.codevoila.com/post/57/reactjs-tutorial-react-component-lifecycle

Stateless Components

Em muitos casos temos componentes que não possuem nenhum ciclo de vida ou estado e retornam apenas JSX, nesse caso chamamos eles de Stateless Components e podem ser escritos utilizando uma sintaxe mais limpa:

// Class Component

class App extends Component {
  render() {
    return (
      <Text>{props.title}</Text>
    )
  }
}

// Stateless Component

const App = (props) => (
  <Text>{props.title}</Text>
);

Arquitetura Flux

Se você começou a mexer com o React vai perceber algumas lacunas que ainda não são fáceis de resolver utilizando apenas React, como por exemplo, compartilhar informações entre dois componentes, ou onde colocar as regras de negócio da aplicação ou até como armazenar estado dos componentes offline, bom, essa é uma tarefa árdua para o React porém simples para o Redux e a arquitetura Flux. Por isso escrevi um Post explicando o passo a passo para entender o Redux:

React do zero: componentização, propriedades e estado

Concluindo

Se você leu os dois posts dessa série, parabéns, você já conhece 80% do React. Sim, essa biblioteca é muito simples e sua grande funcionalidade é mesmo o encapsulamento dos componentes e gerenciamento de estado e propriedades.

Quer ir mais a fundo? Recomendo conhecer nossa comunidade e acompanhar nossos conteúdos no Youtube e aqui no Blog.

Marcadores

Diego Fernandes

Programador full-stack, apaixonado pelas melhores tecnologias de desenvolvimento back-end, front-end e mobile, é co-fundador e CTO na Rocketseat.