quinta-feira, 10 de setembro de 2026 · Edição online
TNT Web
TNT Web

Concorrência Go: 9 padrões para apps escaláveis

ResumoConcorrência em Go apresenta 9 padrões essenciais para aplicações escaláveis, incluindo worker pools, pipeline, fan-out/fan-in, semáforos, contexto com cancelamento, mutexes, canais com buffer, select com timeouts e padrão de ator. Cada padrão resolve problemas específicos de sincronização e paralelismo. A escolha adequada entre goroutines e canais determina eficiência e segurança em sistemas concorrentes. Implementações práticas demonstram aplicação em cenários de alta carga e processamento distribuído.

Concorrência em Go vai além de goroutines. Conheça os 9 padrões essenciais para escrever código escalável, seguro e eficiente, com exemplos práticos de quando usar cada um.

Jonas Ribaldo Jonas Ribaldo · Repórter de economia
· · 4 min de leitura
Concorrência Go: 9 padrões para apps escaláveis
Foto: Imagem ilustrativa · TNT Web

Concorrência em Go vai além de goroutines. Conheça os 9 padrões essenciais para escrever código escalável, seguro e eficiente, com exemplos práticos de quando usar cada um.

Concorrência em Go é a arte de fazer muitas coisas ao mesmo tempo sem quebrar o programa. Diferente de paralelismo, que exige múltiplos núcleos, a concorrência organiza tarefas independentes que podem progredir em intervalos sobrepostos. Para aplicações escaláveis, dominar os padrões abaixo é mais importante do que decorar a sintaxe.

Os 9 padrões a seguir formam a caixa de ferramentas essencial de quem escreve sistemas concorrentes em Go. Eles aparecem em código de produção de empresas como Uber, Cloudflare e Docker.

1. Goroutines: a unidade básica

Goroutines são funções que executam concorrentemente, com custo inicial de apenas 2 KB de pilha. Para lançar uma, basta a palavra-chave go. Porém, sem sincronização, elas podem causar corridas de dados. Use goroutines para tarefas independentes, como processar requisições HTTP, mas sempre coordene o término com sync.WaitGroup.

2. Canais: comunicação segura entre goroutines

Canais são o mecanismo nativo de troca de dados. Eles evitam o compartilhamento de memória, seguindo o lema do Go: "não se comunique compartilhando memória; compartilhe memória se comunicando". Prefira canais quando a comunicação é o objetivo, como enviar resultados de uma goroutine para outra.

3. WaitGroup: esperar todas as goroutines

sync.WaitGroup é um contador que bloqueia a execução até que todas as goroutines sinalizem conclusão. É ideal para cenários onde você dispara N tarefas e precisa aguardar todas antes de prosseguir, como em um batch de envio de e-mails. Sem ele, o programa pode terminar antes das tarefas.

4. Mutex: proteger dados compartilhados

Quando múltiplas goroutines acessam a mesma variável, o sync.Mutex garante que apenas uma por vez modifique o dado. Use mutex para proteger contadores, mapas ou slices compartilhados. Em aplicações com alta contenção, considere sync.RWMutex para leituras simultâneas.

5. Pipeline: processamento em estágios

O padrão pipeline conecta canais em série: a saída de um estágio alimenta o próximo. Cada estágio roda em uma goroutine, processando dados em fluxo. É perfeito para transformações de dados, como ler de um arquivo, filtrar linhas e gravar em outro, sem carregar tudo na memória.

6. Fan-in e Fan-out: distribuir e consolidar trabalho

Fan-out distribui tarefas para várias goroutines; fan-in consolida os resultados em um único canal. Esse padrão acelera operações independentes, como baixar múltiplas URLs ou processar imagens. Combine com um worker pool para limitar o número de goroutines ativas.

7. Context: cancelamento e timeouts

O pacote context permite propagar cancelamento e prazos entre goroutines. Em aplicações web, cada requisição carrega um context que é cancelado se o cliente desconectar. Use context.WithTimeout para evitar que operações travem indefinidamente.

8. Select: lidar com múltiplos canais

select aguarda a primeira operação pronta entre vários canais. Ele é essencial para implementar timeouts, sinais de cancelamento e multiplexação. Por exemplo, você pode escutar um canal de dados e um canal de stop, encerrando a goroutine quando receber o sinal.

9. ErrGroup: propagar erros de goroutines

O pacote golang.org/x/sync/errgroup estende o WaitGroup, permitindo capturar o primeiro erro retornado por qualquer goroutine. Use-o para executar tarefas em paralelo e abortar as demais se uma falhar, como em chamadas a múltiplos serviços externos.

Qual padrão escolher?

Comece com goroutines e WaitGroup para tarefas simples. Se houver troca de dados, adote canais. Para proteger estado compartilhado, use mutex. Em pipelines de processamento, combine fan-out e fan-in. Sempre que houver risco de cancelamento, insira context. E para operações que podem falhar, prefira ErrGroup.

FAQ

O que é concorrência em Go?

Concorrência em Go é a capacidade de executar múltiplas tarefas simultaneamente, usando goroutines e canais. Segundo a Wikipedia, em ciência da computação, concorrência ocorre quando processos disputam acesso a recursos. Em Go, isso é feito de forma leve e segura.

Qual a diferença entre goroutine e thread?

Goroutines são mais leves que threads: começam com 2 KB de pilha e são gerenciadas pelo runtime do Go, enquanto threads do sistema operacional têm pilhas maiores e custo mais alto. Isso permite criar milhares de goroutines sem estourar memória.

Quando usar canais em vez de mutex?

Use canais quando a comunicação entre goroutines é o objetivo, como passar resultados. Use mutex quando precisa proteger um dado compartilhado, como um contador. Em geral, prefira canais para fluxo de dados e mutex para estado crítico.

O que é um worker pool em Go?

Worker pool é um padrão que limita o número de goroutines ativas, criando um grupo fixo de workers que consomem tarefas de um canal. Ele evita sobrecarga do sistema e é útil para controlar o uso de recursos.

Como evitar deadlock em Go?

Deadlock ocorre quando goroutines esperam umas pelas outras indefinidamente. Para evitar, sempre garanta que canais sejam fechados corretamente, use select com time.After para timeouts e evite locks aninhados.

Onde aprender mais sobre concorrência em Go?

A documentação oficial e o blog do Go têm artigos como "Share Memory By Communicating". Cursos como o da Alura e a playlist do canal "Aprenda Go" no YouTube oferecem exemplos práticos.

Compartilhar:
Jonas Ribaldo

Jonas Ribaldo

Repórter de economia

Repórter de economia.

Ver todos os artigos →

Leia também

Compatibilidade navegadores: checklist antes do release
Apps e Software

Compatibilidade navegadores: checklist antes do release

Lançar sem checar compatibilidade entre navegadores custa caro: o usuário vê layout quebrado ou função que não responde e abandona. Este checklist reúne verificações acionáveis para rodar antes de cada release.

10 de setembro de 2026 · Jonas Ribaldo
Sharding database: o que é e como escalar horizontalmente
Apps e Software

Sharding database: o que é e como escalar horizontalmente

Sharding database é a técnica de dividir um banco de dados em partes menores, chamadas shards, distribuídas em máquinas diferentes. Isso permite escalar horizontalmente, mas exige cuidado com consistência e consultas entre shards. Veja quando vale a pena.

10 de setembro de 2026 · Jonas Ribaldo
Prometheus monitoramento: guia passo a passo
Apps e Software

Prometheus monitoramento: guia passo a passo

O Prometheus é um sistema de monitoramento open source que coleta métricas via HTTP e permite consultas com PromQL. Este guia mostra, passo a passo, como configurar a coleta, validar dados e entender o fluxo básico sem depender de suposições.

10 de setembro de 2026 · Eloá Pimentel

Gostou? Receba mais análises

Newsletter quinzenal · curadoria editorial · sem spam