O Bootcamp 2021 JavaScript Full-Stack está ABERTO PARA SINALIZAÇÕES!
Renderização do lado do servidor, também chamada SSR, é a capacidade de uma aplicação JavaScript para renderizar no servidor e não no browser.
Por que é que alguma vez o queremos fazer?
- permite que seu site tenha um tempo de carregamento de primeira página mais rápido, que é a chave para uma boa experiência do usuário
- é essencial para SEO: os motores de busca não podem (ainda?) indexar de forma eficiente e correta aplicações que renderizem exclusivamente no lado do cliente. Apesar das últimas melhorias na indexação no Google, existem outros motores de busca também, e o Google não é perfeito em qualquer caso. Além disso, o Google favorece sites com tempos de carregamento rápidos, e ter que carregar o lado do cliente não é bom para a velocidade
- é ótimo quando as pessoas compartilham uma página do seu site em redes sociais, pois elas podem facilmente reunir os metadados necessários para compartilhar bem o link (imagens, título, descrição…)
Sem Renderização Lateral do Servidor, todo o seu servidor é uma página HTML sem corpo, apenas algumas tags de script que são então usadas pelo navegador para renderizar o aplicativo.
Aplicativos renderizados ao cliente são ótimos em qualquer interação subseqüente do usuário após o carregamento da primeira página. Server Side Rendering nos permite obter o sweet spot no meio de aplicativos renderizados pelo cliente e aplicativos renderizados: a página é gerada do lado do servidor, mas todas as interações com a página uma vez que ela foi carregada são tratadas do lado do cliente.
No entanto, a renderização do lado do servidor também tem a sua desvantagem:
- É justo dizer que uma simples prova de conceito SSR é simples, mas a complexidade do SSR pode crescer com a complexidade da sua aplicação
- renderizar uma grande aplicação do lado do servidor pode ser bastante intensivo em recursos, e sob carga pesada pode até fornecer uma experiência mais lenta do que renderização do lado do cliente, já que você tem um único gargalo de gargalo
Um exemplo muito simplista do que é preciso para renderizar um aplicativo React no Server-Side
SR pode crescer muito, muito complexo e a maioria dos tutoriais irão assar no Redux, React Router e muitos outros conceitos desde o início.
Para entender como o SSR funciona, vamos começar do básico para implementar uma prova de conceito.
Feel free to skip this paragraph if you just want to look into the libraries that provide SSR and not bother with the ground work
Para implementar o SSR básico, vamos usar o Express.
Se você é novo no Express, ou precisa de alguma atualização, confira meu Manual do Express aqui: https://flaviocopes.com/page/ebooks/.
Aviso: a complexidade do SSR pode crescer com a complexidade da sua aplicação. Esta é a configuração mínima para renderizar um aplicativo React básico. Para necessidades mais complexas você pode precisar fazer um pouco mais de trabalho ou também verificar bibliotecas SSR para React.
Presumo que você iniciou uma aplicação React com create-react-app
. Se você está apenas tentando, instale uma agora usando npx create-react-app ssr
.
Vá para a pasta principal da aplicação com o terminal, então execute:
npm install express
Você tem um conjunto de pastas no seu diretório de aplicações. Crie uma nova pasta chamada server
, depois entre nela e crie um ficheiro chamado server.js
.
Segundo as convenções create-react-app
, a aplicação vive no ficheiro src/App.js
. Vamos carregar esse componente, e renderizá-lo para uma string usando ReactDOMServer.renderToString(), que é fornecido por react-dom
.
>
Você obtém o conteúdo do arquivo ./build/index.html
, e substitui o <div></div>
placeholder, que é a tag onde a aplicação se encaixa por padrão, por `<div>${ReactDOMServer.renderToString(<App />)}</div>
.
Todo o conteúdo dentro da pasta build
vai ser servido como está, estaticamente pelo Express.
import path from 'path'import fs from 'fs'import express from 'express'import React from 'react'import ReactDOMServer from 'react-dom/server'import App from '../src/App'const PORT = 8080const app = express()const router = express.Router()const serverRenderer = (req, res, next) => { fs.readFile(path.resolve('./build/index.html'), 'utf8', (err, data) => { if (err) { console.error(err) return res.status(500).send('An error occurred') } return res.send( data.replace( '<div></div>', `<div>${ReactDOMServer.renderToString(<App />)}</div>` ) ) })}router.use('^/$', serverRenderer)router.use( express.static(path.resolve(__dirname, '..', 'build'), { maxAge: '30d' }))// tell the app to use the above rulesapp.use(router)// app.use(express.static('./build'))app.listen(PORT, () => { console.log(`SSR running on port ${PORT}`)})
Agora, na aplicação cliente, no seu src/index.js
, em vez de chamar ReactDOM.render()
:
ReactDOM.render(<App />, document.getElementById('root'))
chamada ReactDOM.hydrate()
, que é a mesma, mas tem a capacidade adicional de anexar os ouvintes do evento à marcação existente uma vez Reagir cargas:
ReactDOM.hydrate(<App />, document.getElementById('root'))
Todos os Nodos.O código js precisa ser transposto pelo Babel, pois o código do Node.js do lado do servidor não sabe nada sobre o JSX, nem sobre os Módulos ES (que usamos para as declarações include
).
Instalar estes 4 pacotes:
npm install @babel/register @babel/preset-env @babel/preset-react ignore-styles
ignore-styles
é um utilitário Babel que lhe dirá para ignorar arquivos CSS importados usando a sintaxe import
.
>
Vamos criar um ponto de entrada em server/index.js
:
require('ignore-styles')require('@babel/register')({ ignore: , presets: })require('./server')
Build the React application, para que a pasta build/depasta seja preenchida:
npm run build
e vamos executar isto:
>node server/index.js
Eu disse que esta é uma abordagem simplista, e é:
- Não lida correctamente com a renderização de imagens quando utiliza importações, que necessitam do Webpack para funcionar (e que complica muito o processo)
- Não lida com metadados do cabeçalho da página, que é essencial para fins de SEO e partilha social (entre outras coisas)
Por isso embora este seja um bom exemplo de utilização de ReactDOMServer.renderToString()
e ReactDOM.hydrate
para obter esta renderização básica do lado do servidor, não é suficiente para a utilização no mundo real.
Renderização do lado do servidor usando bibliotecas
SSR é difícil de fazer corretamente, e React não tem nenhuma maneira de implementar isso.
Ainda é muito discutível se vale a pena o trabalho, a complicação e a sobrecarga para obter os benefícios, ao invés de usar uma tecnologia diferente para servir essas páginas. Esta discussão sobre Reddit tem muitas opiniões a esse respeito.
Quando o Server Side Rendering é um assunto importante, minha sugestão é confiar em bibliotecas e ferramentas pré-fabricadas que tiveram esse objetivo em mente desde o início.
Em particular, sugiro Next.js e Gatsby.
Download my free React Handbook
O JavaScript Full-Stack Bootcamp 2021 AGORA ESTÁ ABERTO PARA SIGNIFICAR ATÉ TERÇA-FEIRA! Não perca esta oportunidade, inscreva-se HOJE!
Outros tutoriais de Reacção:
- Configuração do código VS para o desenvolvimento do React
- React Concept: Immutability
- Como retornar múltiplos elementos no JSX
- Portais Reagir
- Como renderizar HTML em Reagir
- O roteiro para aprender Reagir
- Você deve usar jQuery ou Reagir?
- Como usar o gancho React React hook
- React Router, como obter dados de uma rota dinâmica