Gerenciando tarefas de longa duração em um aplicativo React com Web Workers
Publicados: 2022-03-10O tempo de resposta é um grande problema quando se trata de aplicativos da web. Os usuários exigem respostas instantâneas, não importa o que seu aplicativo esteja fazendo. Seja exibindo apenas o nome de uma pessoa ou processando números, os usuários de aplicativos da Web exigem que seu aplicativo responda a seus comandos todas as vezes. Às vezes, isso pode ser difícil de conseguir, dada a natureza de thread único do JavaScript. Mas neste artigo, aprenderemos como podemos aproveitar a API do Web Worker para oferecer uma experiência melhor.
Ao escrever este artigo, fiz as seguintes suposições:
- Para poder acompanhar, você deve ter pelo menos alguma familiaridade com JavaScript e a API de documentos;
- Você também deve ter um conhecimento prático do React para que possa iniciar com sucesso um novo projeto React usando o Create React App.
Se você precisar de mais informações sobre esse tópico, incluí vários links na seção "Outros recursos" para ajudá-lo a se atualizar.
Primeiro, vamos começar com Web Workers.
O que é um Web Worker?
Para entender os Web Workers e o problema que eles devem resolver, é necessário entender como o código JavaScript é executado em tempo de execução. Durante o tempo de execução, o código JavaScript é executado sequencialmente e passo a passo. Quando um pedaço de código termina, o próximo da linha começa a ser executado e assim por diante. Em termos técnicos, dizemos que o JavaScript é single-thread. Esse comportamento implica que, uma vez que algum pedaço de código comece a ser executado, todo código que vem depois deve esperar que esse código termine a execução. Assim, cada linha de código “bloqueia” a execução de tudo o que vem depois. Portanto, é desejável que cada pedaço de código termine o mais rápido possível. Se algum pedaço de código demorar muito para terminar, nosso programa parece ter parado de funcionar. No navegador, isso se manifesta como uma página congelada e sem resposta. Em alguns casos extremos, a guia congelará completamente.
Imagine dirigir em uma única pista. Se algum dos motoristas à sua frente parar de se mover por qualquer motivo, você terá um engarrafamento. Com um programa como o Java, o tráfego poderia continuar em outras faixas. Assim, Java é dito ser multi-thread. Web Workers são uma tentativa de trazer o comportamento multi-thread para JavaScript.
A captura de tela abaixo mostra que a API do Web Worker é compatível com muitos navegadores, portanto, você deve se sentir confiante em usá-la.

Os Web Workers são executados em threads em segundo plano sem interferir na interface do usuário e se comunicam com o código que os criou por meio de manipuladores de eventos.
Uma excelente definição de Web Worker vem do MDN:
“Um trabalhador é um objeto criado usando um construtor (por exemploWorker()
que executa um arquivo JavaScript nomeado — este arquivo contém o código que será executado no thread do trabalhador; os trabalhadores são executados em outro contexto global que é diferente dawindow
atual. , usando o atalho dawindow
para obter o escopo global atual (em vez deself
dentro de umWorker
retornará um erro.”
Um trabalhador é criado usando o construtor Worker
.
const worker = new Worker('worker-file.js')
É possível executar a maioria dos códigos dentro de um web worker, com algumas exceções. Por exemplo, você não pode manipular o DOM de dentro de um trabalhador. Não há acesso à API do document
.
Os workers e o thread que os gera enviam mensagens uns para os outros usando o método postMessage()
. Da mesma forma, eles respondem às mensagens usando o manipulador de eventos onmessage
. É importante obter essa diferença. O envio de mensagens é feito por meio de um método; receber uma mensagem de volta requer um manipulador de eventos. A mensagem que está sendo recebida está contida no atributo data
do evento. Veremos um exemplo disso na próxima seção. Mas deixe-me mencionar rapidamente que o tipo de trabalhador que estamos discutindo é chamado de “trabalhador dedicado”. Isso significa que o trabalhador só é acessível ao script que o chamou. Também é possível ter um trabalhador acessível a partir de vários scripts. Eles são chamados de trabalhadores compartilhados e são criados usando o construtor SharedWorker
, conforme mostrado abaixo.
const sWorker = new SharedWorker('shared-worker-file.js')
Para saber mais sobre Trabalhadores, consulte este artigo do MDN. O objetivo deste artigo é começar a usar Web workers. Vamos chegar a ele calculando o enésimo número de Fibonacci.
Calculando o enésimo número de Fibonacci
Observação: para esta e as próximas duas seções, estou usando o Live Server no VSCode para executar o aplicativo. Você certamente pode usar outra coisa.
Esta é a seção que você estava esperando. Finalmente escreveremos algum código para ver os Web Workers em ação. Bem, não tão rápido. Nós não apreciaríamos o trabalho que um Web Worker faz a menos que nos deparemos com o tipo de problema que ele resolve. Nesta seção, veremos um problema de exemplo e, na seção seguinte, veremos como um web worker nos ajuda a melhorar.
Imagine que você estivesse construindo um aplicativo da web que permitisse aos usuários calcular o enésimo número de Fibonacci. Caso você seja novo no termo 'Número de Fibonacci', você pode ler mais sobre isso aqui, mas em resumo, os números de Fibonacci são uma sequência de números em que cada número é a soma dos dois números anteriores.
Matematicamente, é expresso como:

Assim, os primeiros números da sequência são:
1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89 ...
Em algumas fontes, a sequência começa em F 0 = 0
, caso em que a fórmula abaixo vale para n > 1
:

Neste artigo, começaremos em F 1 = 1. Uma coisa que podemos ver imediatamente da fórmula é que os números seguem um padrão recursivo. A tarefa em mãos agora é escrever uma função recursiva para calcular o enésimo número de Fibonacci (FN).
Depois de algumas tentativas, acredito que você pode facilmente criar a função abaixo.
const fib = n => { if (n < 2) { return n // or 1 } else { return fib(n - 1) + fib(n - 2) } }
A função é simples. Se n for menor que 2, retorne n (ou 1), caso contrário, retorne a soma dos n-1
e n-2
FNs. Com funções de seta e operador ternário, podemos criar um one-liner.
const fib = n => (n < 2 ? n : fib(n-1) + fib(n-2))
Esta função tem uma complexidade de tempo de 0(2 n )
. Isso significa simplesmente que, à medida que o valor de n aumenta, o tempo necessário para calcular a soma aumenta exponencialmente. Isso cria uma tarefa de execução muito longa que poderia interferir na nossa interface do usuário, para grandes valores de n. Vamos ver isso em ação.
Nota : Esta não é de forma alguma a melhor maneira de resolver este problema específico. Minha escolha de usar este método é para o propósito deste artigo.
Para começar, crie uma nova pasta e nomeie-a como quiser. Agora dentro dessa pasta crie uma pasta src/
. Além disso, crie um arquivo index.html
na pasta raiz. Dentro da pasta src/
, crie um arquivo chamado index.js
.
Abra index.html
e adicione o seguinte código HTML.
<!DOCTYPE html> <html> <head> <link rel="stylesheet" href="styles.css"> </head> <body> <div class="heading-container"> <h1>Computing the nth Fibonnaci number</h1> </div> <div class="body-container"> <p id='error' class="error"></p> <div class="input-div"> <input id='number-input' class="number-input" type='number' placeholder="Enter a number" /> <button id='submit-btn' class="btn-submit">Calculate</button> </div> <div id='results-container' class="results"></div> </div> <script src="/src/index.js"></script> </body> </html>
Esta parte é muito simples. Primeiro, temos um título. Então temos um container com uma entrada e um botão. Um usuário digitaria um número e clicaria em “Calcular”. Também temos um container para guardar o resultado do cálculo. Por último, incluímos o arquivo src/index.js
em uma tag de script
.
Você pode excluir o link da folha de estilo. Mas se você estiver com pouco tempo, eu defini alguns CSS que você pode usar. Basta criar o arquivo styles.css
na pasta raiz e adicionar os estilos abaixo:
body { margin: 0; padding: 0; box-sizing: border-box; } .body-container, .heading-container { padding: 0 20px; } .heading-container { padding: 20px; color: white; background: #7a84dd; } .heading-container > h1 { margin: 0; } .body-container { width: 50% } .input-div { margin-top: 15px; margin-bottom: 15px; display: flex; align-items: center; } .results { width: 50vw; } .results>p { font-size: 24px; } .result-div { padding: 5px 10px; border-radius: 5px; margin: 10px 0; background-color: #e09bb7; } .result-div p { margin: 5px; } span.bold { font-weight: bold; } input { font-size: 25px; } p.error { color: red; } .number-input { padding: 7.5px 10px; } .btn-submit { padding: 10px; border-radius: 5px; border: none; background: #07f; font-size: 24px; color: white; cursor: pointer; margin: 0 10px; }
Agora abra src/index.js
, vamos desenvolvê-lo lentamente. Adicione o código abaixo.
const fib = (n) => (n < 2 ? n : fib(n - 1) + fib(n - 2)); const ordinal_suffix = (num) => { // 1st, 2nd, 3rd, 4th, etc. const j = num % 10; const k = num % 100; switch (true) { case j === 1 && k !== 11: return num + "st"; case j === 2 && k !== 12: return num + "nd"; case j === 3 && k !== 13: return num + "rd"; default: return num + "th"; } }; const textCont = (n, fibNum, time) => { const nth = ordinal_suffix(n); return ` <p id='timer'>Time: <span class='bold'>${time} ms</span></p> <p><span class="bold" id='nth'>${nth}</span> fibonnaci number: <span class="bold" id='sum'>${fibNum}</span></p> `; };
Aqui temos três funções. A primeira é a função que vimos anteriormente para calcular o enésimo FN. A segunda função é apenas uma função de utilidade para anexar um sufixo apropriado a um número inteiro. A terceira função recebe alguns argumentos e gera uma marcação que mais tarde inseriremos no DOM. O primeiro argumento é o número cujo FN está sendo calculado. O segundo argumento é o FN calculado. O último argumento é o tempo que leva para realizar o cálculo.
Ainda em src/index.js
, adicione o código abaixo logo abaixo do anterior.
const errPar = document.getElementById("error"); const btn = document.getElementById("submit-btn"); const input = document.getElementById("number-input"); const resultsContainer = document.getElementById("results-container"); btn.addEventListener("click", (e) => { errPar.textContent = ''; const num = window.Number(input.value); if (num < 2) { errPar.textContent = "Please enter a number greater than 2"; return; } const startTime = new Date().getTime(); const sum = fib(num); const time = new Date().getTime() - startTime; const resultDiv = document.createElement("div"); resultDiv.innerHTML = textCont(num, sum, time); resultDiv.className = "result-div"; resultsContainer.appendChild(resultDiv); });
Primeiro, usamos a API de document
para obter nós DOM
em nosso arquivo HTML. Obtemos uma referência ao parágrafo onde exibiremos as mensagens de erro; a entrada; o botão calcular e o container onde mostraremos nossos resultados.
Em seguida, anexamos um manipulador de eventos “click” ao botão. Quando o botão é clicado, pegamos o que estiver dentro do elemento de entrada e convertemos em um número, se obtivermos algo menor que 2, exibimos uma mensagem de erro e retornamos. Se obtivermos um número maior que 2, continuamos. Primeiro, registramos a hora atual. Depois disso, calculamos o FN. Quando isso termina, obtemos uma diferença de tempo que representa quanto tempo o cálculo levou. Na parte restante do código, criamos uma nova div
. Em seguida, definimos seu HTML interno para ser a saída da função textCont()
que definimos anteriormente. Por fim, adicionamos uma classe a ela (para estilização) e a anexamos ao contêiner de resultados. O efeito disso é que cada computação aparecerá em uma div
separada abaixo da anterior.

Podemos ver que à medida que o número aumenta, o tempo de computação também aumenta (exponencialmente). Por exemplo, de 30 para 35, tivemos um salto no tempo de computação de 13ms para 130ms. Ainda podemos considerar essas operações como “rápidas”. Aos 40, vemos um tempo de computação de mais de 1 segundo. Na minha máquina, é aqui que começo a perceber que a página não responde. Neste ponto, não consigo mais interagir com a página enquanto a computação está em andamento. Não consigo me concentrar na entrada ou fazer qualquer outra coisa.
Lembra quando falamos sobre JavaScript sendo single-thread? Bem, esse encadeamento foi “bloqueado” por essa computação de longa duração, então todo o resto deve “esperar” que ele termine. Pode começar em um valor mais baixo ou mais alto em sua máquina, mas você chegará a esse ponto. Observe que levou quase 10s para calcular o de 44. Se houvesse outras coisas para fazer em seu aplicativo da web, bem, o usuário teria que esperar que o Fib(44) terminasse antes de continuar. Mas se você implantou um web worker para lidar com esse cálculo, seus usuários podem continuar com outra coisa enquanto isso é executado.

Vamos agora ver como os web workers nos ajudam a superar esse problema.
Um exemplo de Web Worker em ação
Nesta seção, vamos delegar a tarefa de calcular o enésimo FN a um web worker. Isso ajudará a liberar o encadeamento principal e manterá nossa interface do usuário responsiva enquanto a computação estiver em andamento.
Começar a trabalhar com web workers é surpreendentemente simples. Vamos ver como. Crie um novo arquivo src/fib-worker.js
. e digite o seguinte código.
const fib = (n) => (n < 2 ? n : fib(n - 1) + fib(n - 2)); onmessage = (e) => { const { num } = e.data; const startTime = new Date().getTime(); const fibNum = fib(num); postMessage({ fibNum, time: new Date().getTime() - startTime, }); };
Observe que movemos a função que calcula o enésimo número de Fibonacci, fib
dentro deste arquivo. Este arquivo será executado pelo nosso web worker.
Lembre-se na seção O que é um web worker , mencionamos que web workers e seus pais se comunicam usando o manipulador de eventos onmessage
e o método postMessage()
. Aqui estamos usando o manipulador de eventos onmessage
para ouvir as mensagens do script pai. Assim que recebemos uma mensagem, desestruturamos o número do atributo data do evento. Em seguida, obtemos a hora atual e iniciamos o cálculo. Quando o resultado estiver pronto, usamos o método postMessage()
para postar os resultados de volta no script pai.
Abra o src/index.js
, vamos fazer algumas alterações.
... const worker = new window.Worker("src/fib-worker.js"); btn.addEventListener("click", (e) => { errPar.textContent = ""; const num = window.Number(input.value); if (num < 2) { errPar.textContent = "Please enter a number greater than 2"; return; } worker.postMessage({ num }); worker.onerror = (err) => err; worker.onmessage = (e) => { const { time, fibNum } = e.data; const resultDiv = document.createElement("div"); resultDiv.innerHTML = textCont(num, fibNum, time); resultDiv.className = "result-div"; resultsContainer.appendChild(resultDiv); }; });
A primeira coisa a fazer é criar o web worker usando o construtor Worker
. Em seguida, dentro do ouvinte de eventos do nosso botão, enviamos um número para o trabalhador usando worker.postMessage({ num })
. Depois disso, definimos uma função para escutar erros no trabalhador. Aqui nós simplesmente retornamos o erro. Você certamente pode fazer mais se quiser, como mostrá-lo no DOM. Em seguida, ouvimos as mensagens do trabalhador. Assim que recebemos uma mensagem, desestruturamos time
e fibNum
e continuamos o processo de mostrá-los no DOM.
Observe que dentro do web worker, o evento onmessage
está disponível no escopo do worker, então poderíamos tê-lo escrito como self.onmessage
e self.postMessage()
. Mas no script pai, temos que anexá-los ao próprio trabalhador.
Na captura de tela abaixo, você verá o arquivo do web worker na guia de fontes do Chrome Dev Tools. O que você deve observar é que a interface do usuário permanece responsiva, independentemente do número inserido. Esse comportamento é a mágica dos web workers.

Fizemos muitos progressos com nosso aplicativo da web. Mas há algo mais que podemos fazer para torná-lo melhor. Nossa implementação atual usa um único trabalhador para lidar com cada computação. Se uma nova mensagem vier enquanto uma está em execução, a antiga é substituída. Para contornar isso, podemos criar um novo trabalhador para cada chamada para calcular o FN. Vamos ver como fazer isso na próxima seção.
Trabalhando com vários Web workers
Atualmente, estamos tratando de cada solicitação com um único trabalhador. Assim, uma solicitação recebida substituirá uma anterior que ainda não foi concluída. O que queremos agora é fazer uma pequena alteração para gerar um novo web worker para cada solicitação. Mataremos este trabalhador assim que terminar.
Abra src/index.js
e mova a linha que cria o web worker dentro do manipulador de eventos de clique do botão. Agora, o manipulador de eventos deve ficar como abaixo.
btn.addEventListener("click", (e) => { errPar.textContent = ""; const num = window.Number(input.value); if (num < 2) { errPar.textContent = "Please enter a number greater than 2"; return; } const worker = new window.Worker("src/fib-worker.js"); // this line has moved inside the event handler worker.postMessage({ num }); worker.onerror = (err) => err; worker.onmessage = (e) => { const { time, fibNum } = e.data; const resultDiv = document.createElement("div"); resultDiv.innerHTML = textCont(num, fibNum, time); resultDiv.className = "result-div"; resultsContainer.appendChild(resultDiv); worker.terminate() // this line terminates the worker }; });
Fizemos duas alterações.
- Movemos esta linha
const worker = new window.Worker("src/fib-worker.js")
dentro do manipulador de eventos de clique do botão. - Adicionamos esta linha
worker.terminate()
para descartar o trabalhador assim que terminarmos com ele.
Assim, para cada clique do botão, criamos um novo trabalhador para lidar com o cálculo. Assim, podemos continuar alterando a entrada, e cada resultado aparecerá na tela assim que a computação terminar. Na imagem abaixo você pode ver que os valores de 20 e 30 aparecem antes de 45. Mas eu comecei 45 primeiro. Uma vez que a função retorna para 20 e 30, seus resultados foram postados e o trabalhador foi encerrado. Quando tudo terminar, não devemos ter nenhum trabalhador na guia de fontes.

Poderíamos encerrar este artigo aqui, mas se fosse um aplicativo de reação, como traríamos web workers para ele. Esse é o foco da próxima seção.
Trabalhadores da Web em Reação
Para começar, crie um novo aplicativo de reação usando o CRA. Copie o arquivo fib-worker.js
para a pasta public/
do seu aplicativo react. Colocar o arquivo aqui decorre do fato de que os aplicativos React são aplicativos de página única. Essa é a única coisa específica para usar o trabalhador em um aplicativo de reação. Tudo o que se segue daqui é puro React.
Na pasta src/
crie um arquivo helpers.js
e exporte a função ordinal_suffix()
dele.
// src/helpers.js export const ordinal_suffix = (num) => { // 1st, 2nd, 3rd, 4th, etc. const j = num % 10; const k = num % 100; switch (true) { case j === 1 && k !== 11: return num + "st"; case j === 2 && k !== 12: return num + "nd"; case j === 3 && k !== 13: return num + "rd"; default: return num + "th"; } };
Nosso aplicativo exigirá que mantenhamos algum estado, então crie outro arquivo, src/reducer.js
e cole no redutor de estado.
// src/reducers.js export const reducer = (state = {}, action) => { switch (action.type) { case "SET_ERROR": return { ...state, err: action.err }; case "SET_NUMBER": return { ...state, num: action.num }; case "SET_FIBO": return { ...state, computedFibs: [ ...state.computedFibs, { id: action.id, nth: action.nth, loading: action.loading }, ], }; case "UPDATE_FIBO": { const curr = state.computedFibs.filter((c) => c.id === action.id)[0]; const idx = state.computedFibs.indexOf(curr); curr.loading = false; curr.time = action.time; curr.fibNum = action.fibNum; state.computedFibs[idx] = curr; return { ...state }; } default: return state; } };
Vamos examinar cada tipo de ação, um após o outro.
-
SET_ERROR
: define um estado de erro quando acionado. -
SET_NUMBER
: define o valor em nossa caixa de entrada para state. -
SET_FIBO
: adiciona uma nova entrada ao array de FNs computados. -
UPDATE_FIBO
: aqui procuramos uma entrada específica e a substitui por um novo objeto que possui o FN calculado e o tempo necessário para computá-lo.
Usaremos este redutor em breve. Antes disso, vamos criar o componente que exibirá os FNs calculados. Crie um novo arquivo src/Results.js
e cole o código abaixo.
// src/Results.js import React from "react"; export const Results = (props) => { const { results } = props; return ( <div className="results-container"> {results.map((fb) => { const { id, nth, time, fibNum, loading } = fb; return ( <div key={id} className="result-div"> {loading ? ( <p> Calculating the{" "} <span className="bold"> {nth} </span>{" "} Fibonacci number... </p> ) : ( <> <p> Time: <span className="bold">{time} ms</span> </p> <p> <span className="bold"> {nth} </span>{" "} fibonnaci number:{" "} <span className="bold"> {fibNum} </span> </p> </> )} </div> ); })} </div> ); };
Com essa alteração, iniciamos o processo de conversão do nosso arquivo index.html anterior para jsx. Este arquivo tem uma responsabilidade: pegar um array de objetos representando FNs computados e exibi-los. A única diferença do que tínhamos antes é a introdução de um estado de carregamento . Agora, quando a computação está em execução, mostramos o estado de carregamento para que o usuário saiba que algo está acontecendo.
Vamos colocar as peças finais atualizando o código dentro src/App.js
. O código é bastante longo, então faremos isso em duas etapas. Vamos adicionar o primeiro bloco de código.
import React from "react"; import "./App.css"; import { ordinal_suffix } from "./helpers"; import { reducer } from './reducer' import { Results } from "./Results"; function App() { const [info, dispatch] = React.useReducer(reducer, { err: "", num: "", computedFibs: [], }); const runWorker = (num, id) => { dispatch({ type: "SET_ERROR", err: "" }); const worker = new window.Worker('./fib-worker.js') worker.postMessage({ num }); worker.onerror = (err) => err; worker.onmessage = (e) => { const { time, fibNum } = e.data; dispatch({ type: "UPDATE_FIBO", id, time, fibNum, }); worker.terminate(); }; }; return ( <div> <div className="heading-container"> <h1>Computing the nth Fibonnaci number</h1> </div> <div className="body-container"> <p className="error"> {info.err} </p> // ... next block of code goes here ... // <Results results={info.computedFibs} /> </div> </div> ); } export default App;
Como de costume, trazemos nossas importações. Em seguida, instanciamos um estado e uma função de atualização com o gancho useReducer. Em seguida, definimos uma função, runWorker()
, que recebe um número e um ID e começa a chamar um web worker para calcular o FN desse número.
Observe que para criar o trabalhador, passamos um caminho relativo para o construtor do trabalhador. Em tempo de execução, nosso código React é anexado ao arquivo public/index.html
, assim ele pode encontrar o arquivo fib-worker.js
no mesmo diretório. Quando a computação é concluída (acionada por worker.onmessage
), a ação UPDATE_FIBO
é despachada e o trabalhador é encerrado posteriormente. O que temos agora não é muito diferente do que tínhamos anteriormente.
No bloco de retorno deste componente, renderizamos o mesmo HTML que tínhamos antes. Também passamos a matriz de números computados para o componente <Results />
para renderização.
Vamos adicionar o bloco final de código dentro da instrução return
.
<div className="input-div"> <input type="number" value={info.num} className="number-input" placeholder="Enter a number" onChange={(e) => dispatch({ type: "SET_NUMBER", num: window.Number(e.target.value), }) } /> <button className="btn-submit" onClick={() => { if (info.num < 2) { dispatch({ type: "SET_ERROR", err: "Please enter a number greater than 2", }); return; } const id = info.computedFibs.length; dispatch({ type: "SET_FIBO", id, loading: true, nth: ordinal_suffix(info.num), }); runWorker(info.num, id); }} > Calculate </button> </div>
Definimos um manipulador onChange
na entrada para atualizar a variável de estado info.num
. No botão, definimos um manipulador de eventos onClick
. Quando o botão é clicado, verificamos se o número é maior que 2. Observe que antes de chamar runWorker()
, primeiro despachamos uma ação para adicionar uma entrada ao array de FNs calculados. É esta entrada que será atualizada assim que o trabalhador terminar seu trabalho. Dessa forma, cada entrada mantém sua posição na lista, diferentemente do que tínhamos antes.
Por fim, copie o conteúdo de styles.css
de antes e substitua o conteúdo de App.css
.
Agora temos tudo no lugar. Agora inicie seu servidor react e brinque com alguns números. Anote o estado de carregamento, que é uma melhoria de UX. Além disso, observe que a interface do usuário permanece responsiva mesmo quando você insere um número tão alto quanto 1000 e clica em “Calcular”.

Observe o estado de carregamento e o trabalhador ativo. Uma vez que o valor 46 é calculado, o trabalhador é morto e o estado de carregamento é substituído pelo resultado final.
- O código-fonte deste aplicativo React está disponível no Github e há um aplicativo hospedado no vercel.
Conclusão
Ufa! Foi uma longa jornada, então vamos encerrar. Recomendo que você dê uma olhada na entrada MDN para web workers (veja a lista de recursos abaixo) para aprender outras maneiras de usar web workers.
Neste artigo, aprendemos sobre o que são os web workers e o tipo de problema que eles devem resolver. Também vimos como implementá-los usando JavaScript simples. Por fim, vimos como implementar web workers em uma aplicação React.
Incentivo você a aproveitar essa ótima API para oferecer uma experiência melhor para seus usuários.
Recursos adicionais
-
Console.time()
, documentos da web MDN - {JSON} Espaço reservado, site oficial
- Usando Web Workers, documentos da Web MDN
- Número de Fibonacci, Wikipedia
- Operador condicional (ternário), web docs MDN
-
Document
, APIs da Web, documentos da Web MDN - Primeiros passos, criar aplicativo React (docs)
-
Function.prototype.toString()
, documentos da web MDN - IIFE, documentos da web MDN
-
workerSetup.js
, Tutoriais Fullstack Incríveis, GitHub - “Programação Paralela em JavaScript Usando Web Workers”, Uday Hiwarale, Medium