Como implementar renderização do lado do servidor na sua aplicação React em três passos simples

Por Rohit Kumar

Aqui está o que vamos construir neste tutorial: um belo cartão React como este.

Neste tutorial, vamos usar renderização do lado do servidor para entregar uma resposta HTML quando um utilizador ou crawler atinge a URL de uma página. Vamos lidar com os últimos pedidos do lado do cliente.

Por que precisamos disso?

Deixe-me guiá-lo à resposta.

Qual é a diferença entre renderização do lado do cliente e renderização do lado do servidor?

Na renderização do lado do cliente, seu navegador baixa uma página HTML mínima. Ele renderiza o JavaScript e preenche o conteúdo nele.

Renderização do lado do servidor, por outro lado, renderiza os componentes React no servidor. A saída é conteúdo HTML.

Você pode combinar estes dois para criar uma aplicação isomórfica.

Cons of Rendering React on the Server

  • SSR pode melhorar a performance se a sua aplicação for pequena. Mas também pode degradar a performance se for pesado.
  • Aumenta o tempo de resposta (e pode ser pior se o servidor estiver ocupado).
  • Aumenta o tamanho da resposta, o que significa que a página leva mais tempo para carregar.
  • Aumenta a complexidade da aplicação.

Quando você deve usar o Server Side Rendering?

Embora estas consequências do SSR, existem algumas situações em que você pode e deve usá-lo.

SEO

Todos os websites querem aparecer nas buscas. Corrija-me se eu estiver errado.

Felizmente, os crawlers do motor de busca ainda não entendem/render JavaScript.

Isso significa que eles vêem uma página em branco, não importa o quão útil o seu site é.

Muita gente diz que o crawler do Google agora renderiza JavaScript.

Para testar isso, eu implementei o aplicativo no Heroku. Aqui está o que vi na Consola de Pesquisa do Google:

O crawler do Google não renderiza React

Uma página em branco.

Esta foi a maior razão pela qual eu explorei a renderização do lado do servidor. Especialmente quando é uma página de cornerstone como uma página de aterragem, blog, etc.

Para verificar se o Google renderiza o seu site, visite:

Search Console Dashboard > Crawl > Fetch as Google. Digite o URL da página ou deixe-o vazio para a página inicial.

Selecione FETCH AND RENDER. Uma vez completo, clique para ver o resultado.

Improve performance

No SSR, a performance da aplicação depende dos recursos do servidor e da velocidade da rede do utilizador. Isso o torna muito útil para sites de conteúdo pesado.

Por exemplo, digamos que você tenha um telefone celular de preço médio com velocidade de internet lenta. Você tenta acessar um site que baixa 4MB de dados antes que você possa ver qualquer coisa.

Você poderia ver qualquer coisa na sua tela em 2-4 segundos?

Você poderia visitar aquele site novamente?

Eu não acho que você faria.

Outra grande melhoria está no Tempo de Interação do Primeiro Usuário. Esta é a diferença no tempo desde quando um usuário acessa a URL até quando ele vê o conteúdo.

Aqui está a comparação. Eu testei em um Mac.

React Rendered on Server

SR relatório de desempenho (Chrome)

O primeiro tempo de interação é de 300ms. O Hydrate termina a 400ms. O evento de carga sai a 500ms aproximadamente. Você pode ver isto verificando a imagem acima.

Reagir Renderizado no Navegador do Cliente

Relatório de desempenho do lado do cliente (Chrome)

O primeiro tempo de interação é de 400ms. O evento de carga sai a 470ms.

O resultado fala por si. Há uma diferença de 100ms no Primeiro Tempo de Interacção do Utilizador para uma aplicação tão pequena.

Como funciona? – (4 Passos Simples)

  • Criar uma nova Loja Redux em cada pedido.
  • Despachar algumas ações.
  • Retirar o estado da Loja e executar SSR.
  • Enviar o estado obtido no passo anterior junto com a resposta.

Usaremos o estado passado na resposta para criar o estado inicial no lado do cliente.

Antes de começar, clone/download o exemplo completo do Github e use-o como referência.

Configurando o nosso App

Primeiro, abra o seu editor e shell favoritos. Crie uma nova pasta para a sua aplicação. Vamos começar.

npm init --yes

Preencher nos detalhes. Depois que package.json for criado, copie as dependências e scripts abaixo para ele.

Instale todas as dependências executando:

npm install

Você precisa configurar Babel e webpack para que o nosso script de compilação funcione.

Babel transforma o ESM e reage em Node e código compreendido pelo navegador.

Criar um novo arquivo .babelrc e colocar a linha abaixo nele.

{ "presets": }

webpack agrupa nosso aplicativo e suas dependências em um único arquivo. Crie outro arquivo webpack.config.js com o seguinte código nele:

const path = require('path');module.exports = { entry: { client: './src/client.js', bundle: './src/bundle.js' }, output: { path: path.resolve(__dirname, 'assets'), filename: ".js" }, module: { rules: }}

Os dois arquivos de saída do processo de compilação:

  1. assets/bundle.js -apartamento do lado do cliente puro.
  2. assets/client.js -comparador do lado do cliente para SSR.

>O arquivo src/ folder contém o código fonte. Os arquivos compilados em Babel vão para views/. viewsdirectório será criado automaticamente se não estiver presente.

Por que precisamos de compilar ficheiros fonte?

A razão é a diferença de sintaxe entre ESM & CommonJS. Enquanto escrevemos React e Redux, nós usamos fortemente importação e exportação em todos os arquivos.

Felizmente, eles não funcionam em Node. Aí vem Babel para resgatar. O script abaixo diz ao Babel para compilar todos os arquivos no diretório src e colocar o resultado em views.

"babel": "babel src -d views",

Agora, o Nó pode executá-los.

Copiar Pré-Codificado &Arquivos estáticos

Se você já clonou o repositório, copie a partir dele. Caso contrário, baixe o arquivo ssr-static.zip do Dropbox. Extraia-o e mantenha estas três pastas dentro do seu directório de aplicações. Aqui está o que eles contêm.

  1. Reagir App e os componentes residem em src/components.
  2. Arquivos Redux em src/redux/.
  3. assets/ & media/: Contém arquivos estáticos como style.css e imagens.

Lado do servidor

Criar dois novos arquivos chamados server.js e template.js dentro da pasta src/.

src/server.js

Magic acontece aqui. Este é o código que você tem procurado.

import React from 'react';import { renderToString } from 'react-dom/server';import { Provider } from 'react-redux';import configureStore from './redux/configureStore';import App from './components/app';module.exports = function render(initialState) { // Model the initial state const store = configureStore(initialState); let content = renderToString(<Provider store={store} ><App /></Provider>); const preloadedState = store.getState(); return { content, preloadedState };};

Em vez de renderizar a nossa aplicação, precisamos de embrulhá-la numa função e exportá-la. A função aceita o estado inicial da aplicação.

Aí está como ela funciona.

  1. Passar initialState a configureStore(). configureStore()Retira uma nova instância da Store. Mantenha-o dentro do método store variável.
  2. Chamar método renderToString(), fornecendo nossa App como entrada. Ele renderiza nossa aplicação no servidor e retorna o HTML produzido. Agora, a variável content armazena o HTML.
  3. Tirar o estado da Redux Store chamando getState() em store. Mantenha-o em uma variável preloadedState.
  4. Retornar os content e preloadedState. Vamos passar estes para o nosso template para obter a página HTML final.

2. src/template.js

template.js exporta uma função. Leva title, state e content como entrada. Ele os injeta no template e retorna o documento HTML final.

Para passar ao longo do estado, o template anexa state a window.__STATE__ dentro de um tag <script>.

Agora você pode ler state no lado do cliente acessando window.__STATE__.

Incluímos também o companheiro SSR assets/client.js aplicação do lado do cliente em outro tag de script.

Se solicitar a versão cliente pura, apenas coloca assets/bundle.js dentro da tag do script.

O lado cliente

O lado cliente é bastante simples.

src/bundle.js

É assim que se escreve o React e o Redux Provider wrap. É a nossa pura aplicação do lado do cliente. Sem truques aqui.

import React from 'react';import { render } from 'react-dom';import { Provider } from 'react-redux';import configureStore from './redux/configureStore';import App from './components/app';const store = configureStore();render( <Provider store={store} > <App /> </Provider>, document.querySelector('#app'));

src/client.js

Parece-lhe familiar? Sim, não há nada de especial excepto window.__STATE__. Tudo o que precisamos fazer é pegar no estado inicial de window.__STATE__ e passá-lo para a nossa função configureStore() como estado inicial.

Vejamos o nosso novo ficheiro de cliente:

import React from 'react';import { hydrate } from 'react-dom';import { Provider } from 'react-redux';import configureStore from './redux/configureStore';import App from './components/app';const state = window.__STATE__;delete window.__STATE__;const store = configureStore(state);hydrate( <Provider store={store} > <App /> </Provider>, document.querySelector('#app'));

Vejamos as alterações:

  1. Substitua render() por hydrate(). hydrate() é o mesmo que render() mas é usado para hidratar elementos renderizados por ReactDOMServer. Ele garante que o conteúdo é o mesmo no servidor e no cliente.
  2. Lê o estado do objecto da janela global window.__STATE__. Guarda-o numa variável e elimina o window.__STATE__.
  3. Cria uma nova loja com state como initialState.

Tudo feito aqui.

Pondo tudo junto

Index.js

Este é o ponto de entrada da nossa aplicação. Ele lida com pedidos e templates.

Ele também declara uma variável initialState. Eu a modelei com dados no arquivo assets/data.json . Vamos passá-la para a nossa ssr() function.

Note: Ao referenciar um ficheiro que está dentro src/ de um ficheiro fora de src/ , use normal require() e substitua src/ por views/. Você sabe a razão (Babel compile).

Roteamento

  1. /: Por padrão página inicial renderizada ao servidor.
  2. /client: Puro exemplo de renderização do lado do cliente.
  3. /exit: Botão de paragem do servidor. Apenas disponível em desenvolvimento.

Build & Run

É tempo de construir e executar a nossa aplicação. Podemos fazer isto com uma única linha de código.

npm run build && npm run start

Agora, a aplicação está a correr em http://localhost:3000.

Pronto para se tornar um React Pro?

A partir da próxima segunda-feira estou a iniciar uma nova série para ter as suas capacidades React a brilhar, imediatamente.

ligação de submissão abaixo ?

Obrigado por ler isto.

Se você gostar e achar útil, siga-me no Twitter & Webflow.

Deixe uma resposta

O seu endereço de email não será publicado.