<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Stephanto</title>
    <description>The latest articles on DEV Community by Stephanto (@stephanto).</description>
    <link>https://dev.to/stephanto</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F3079405%2F8743671d-89fa-48ce-b6ca-cfab8c46dc40.jpg</url>
      <title>DEV Community: Stephanto</title>
      <link>https://dev.to/stephanto</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/stephanto"/>
    <language>en</language>
    <item>
      <title>Pirâmide de Testes: Do Unitário ao E2E - Introdução</title>
      <dc:creator>Stephanto</dc:creator>
      <pubDate>Mon, 02 Jun 2025 21:44:35 +0000</pubDate>
      <link>https://dev.to/stephanto/piramide-de-testes-do-unitario-ao-e2e-introducao-5f0</link>
      <guid>https://dev.to/stephanto/piramide-de-testes-do-unitario-ao-e2e-introducao-5f0</guid>
      <description>&lt;p&gt;Olá, comunidade dev! 👋 Se você busca desenvolver software com mais qualidade e confiança, entender a &lt;strong&gt;Pirâmide de Testes&lt;/strong&gt; é fundamental. Popularizada por Mike Cohn, essa abordagem nos ajuda a organizar e priorizar os diferentes tipos de testes em nossos projetos.&lt;/p&gt;

&lt;p&gt;Neste artigo, vamos mergulhar nas suas camadas – Unitários, Integração e End-to-End (E2E) – e desvendar o &lt;strong&gt;valor&lt;/strong&gt; e o &lt;strong&gt;custo&lt;/strong&gt; de cada uma. Preparados? 🚀&lt;/p&gt;

&lt;h2&gt;
  
  
  As Camadas da Pirâmide: Uma Visão Geral
&lt;/h2&gt;

&lt;p&gt;A pirâmide é visualmente dividida em três camadas principais, cada uma com um papel específico e diferentes trade-offs:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;🧱 &lt;strong&gt;Testes Unitários:&lt;/strong&gt; A base sólida.&lt;/li&gt;
&lt;li&gt;🔗 &lt;strong&gt;Testes de Integração:&lt;/strong&gt; A conexão entre as partes.&lt;/li&gt;
&lt;li&gt;🎯 &lt;strong&gt;Testes End-to-End (E2E):&lt;/strong&gt; A validação da experiência completa.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGsd3maxXQAEL2Py%3Fformat%3Djpg%26name%3D4096x4096" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGsd3maxXQAEL2Py%3Fformat%3Djpg%26name%3D4096x4096" alt="Pirâmide de Testes Clássica" width="3439" height="1743"&gt;&lt;/a&gt;  Vamos explorar cada uma delas.&lt;/p&gt;

&lt;h2&gt;
  
  
  Testes End-to-End (E2E): Validando a Experiência do Usuário 🎯
&lt;/h2&gt;

&lt;p&gt;No topo da pirâmide, os testes E2E simulam a jornada completa de um &lt;strong&gt;usuário real&lt;/strong&gt; interagindo com sua aplicação. Pense em um teste de cadastro: o script abriria o site, preencheria os campos, submeteria o formulário e verificaria o resultado, passando pelo frontend, backend, banco de dados e qualquer outro serviço envolvido.&lt;/p&gt;

&lt;h3&gt;
  
  
  Valor do E2E:
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Máximo para o Negócio:&lt;/strong&gt; Garante que a funcionalidade crítica está operando como esperado do início ao fim, sob a perspectiva do usuário. ✅&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Alta Confiança:&lt;/strong&gt; Um conjunto de testes E2E bem-sucedido transmite grande confiança sobre a saúde geral da aplicação.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Custo do E2E:
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Altíssimo:&lt;/strong&gt; São os testes mais caros para desenvolver, manter e executar. 💸&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Depuração Complexa:&lt;/strong&gt; Identificar a causa raiz de uma falha pode ser demorado, já que muitos componentes estão envolvidos.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Ambiente Exigente:&lt;/strong&gt; Requerem um ambiente de testes o mais fiel possível ao de produção, o que pode ser custoso e complexo de configurar.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGsd5aYrWgAEfNK7%3Fformat%3Djpg%26name%3D4096x4096" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGsd5aYrWgAEfNK7%3Fformat%3Djpg%26name%3D4096x4096" alt="Diagrama Teste E2E" width="2090" height="1689"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Testes Unitários: A Fundação Sólida 🧱
&lt;/h2&gt;

&lt;p&gt;Na base da pirâmide, os testes unitários focam na &lt;strong&gt;menor unidade de código&lt;/strong&gt; isolável: uma função, um método ou uma classe pequena. O objetivo é simples: para uma entrada X, esperamos uma saída Y. Testamos diversos cenários, incluindo caminhos felizes e casos de exceção.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGsd6Q7jWsAA77uu%3Fformat%3Dpng%26name%3D4096x4096" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGsd6Q7jWsAA77uu%3Fformat%3Dpng%26name%3D4096x4096" alt="Exemplo de Teste Unitário" width="3309" height="2949"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;### Mocks ao Resgate!&lt;/p&gt;

&lt;p&gt;Um erro comum é achar que testes unitários precisam acessar o banco de dados ou outros serviços externos. Pelo contrário! Para garantir isolamento e rapidez, usamos &lt;strong&gt;mocks&lt;/strong&gt; (objetos simulados) para representar essas dependências.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fqwycjzm9gpeofwn7sywx.jpg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fqwycjzm9gpeofwn7sywx.jpg" alt="Mocks" width="800" height="239"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Custo dos Unitários:
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Baixíssimo:&lt;/strong&gt; São baratos para escrever, executar e manter. ⚡️&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Feedback Rápido:&lt;/strong&gt; Executam em milissegundos, fornecendo feedback quase instantâneo aos desenvolvedores.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Depuração Fácil:&lt;/strong&gt; Quando um teste unitário falha, o problema geralmente está contido na pequena unidade testada.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Valor dos Unitários:
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Menor Valor Isolado (para o Negócio):&lt;/strong&gt; Sozinhos, não garantem que a aplicação inteira funcione. Muitas unidades funcionando perfeitamente em isolamento podem falhar ao serem integradas. 🧩&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Base Crucial para a Qualidade:&lt;/strong&gt; Apesar disso, são a fundação! Ajudam a garantir que cada "tijolo" da sua aplicação é confiável.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Guia de Design:&lt;/strong&gt; Incentivam um bom design de código (baixo acoplamento, alta coesão) e revelam problemas como falta de abstração ou injeção de dependência inadequada.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Documentação Viva:&lt;/strong&gt; Descrevem como cada unidade de código deve se comportar.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Grande Quantidade:&lt;/strong&gt; São os testes mais numerosos em uma codebase saudável.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGsd7GfQXQAANuNJ%3Fformat%3Djpg%26name%3D4096x4096" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGsd7GfQXQAANuNJ%3Fformat%3Djpg%26name%3D4096x4096" alt="Custo unitários" width="2090" height="1689"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Testes de Integração: Conectando os Pontos 🔗
&lt;/h2&gt;

&lt;p&gt;Localizados no meio da pirâmide, os testes de integração verificam se diferentes unidades ou componentes do sistema &lt;strong&gt;se comunicam e colaboram corretamente&lt;/strong&gt;. Se os testes unitários garantem que os tijolos são bons, os de integração garantem que eles se encaixam.&lt;/p&gt;

&lt;p&gt;Aqui, pode ser válido interagir com um banco de dados real (geralmente em uma instância de teste, de menor escala) ou outros serviços externos para validar essa comunicação.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGsd73zUW8AApSkx%3Fformat%3Djpg%26name%3D4096x4096" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGsd73zUW8AApSkx%3Fformat%3Djpg%26name%3D4096x4096" alt="Diagrama Teste de Integração" width="4096" height="2590"&gt;&lt;/a&gt; &lt;/p&gt;

&lt;h3&gt;
  
  
  Valor da Integração:
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Médio:&lt;/strong&gt; Fornecem uma boa visão para os desenvolvedores sobre como diferentes partes da aplicação interagem e como os recursos são utilizados.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Confiança na Colaboração:&lt;/strong&gt; Aumentam a confiança de que os módulos principais funcionam bem juntos.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Indicador de Saúde:&lt;/strong&gt; Embora não representem a experiência final do usuário, dão um bom panorama do estado da aplicação.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Custo da Integração:
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Médio:&lt;/strong&gt; São mais caros e lentos que os testes unitários, pois envolvem múltiplos componentes.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Depuração Moderada:&lt;/strong&gt; Identificar falhas pode ser mais complexo que nos testes unitários, mas geralmente mais simples que nos E2E.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Recursos:&lt;/strong&gt; Podem exigir mais recursos de setup (ex: um banco de dados de teste) do que os unitários.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGsd8Za3XcAA-I4i%3Fformat%3Djpg%26name%3D4096x4096" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGsd8Za3XcAA-I4i%3Fformat%3Djpg%26name%3D4096x4096" alt="Custo Teste de Integração" width="2090" height="1689"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Por Que o Formato de Pirâmide? 🔺
&lt;/h2&gt;

&lt;p&gt;O formato visual da pirâmide não é um acaso. Ele ilustra a &lt;strong&gt;proporção ideal&lt;/strong&gt; de cada tipo de teste em um sistema saudável e com manutenção sustentável:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Base Larga (Muitos Testes Unitários):&lt;/strong&gt; São rápidos, baratos e isolam falhas eficientemente. Constituem a maior parte da sua suíte de testes.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Meio (Menos Testes de Integração):&lt;/strong&gt; Verificam as interações chave sem o custo dos E2E.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Topo Estreito (Poucos Testes E2E):&lt;/strong&gt; Cobrem os fluxos críticos do usuário, mas são usados com moderação devido ao seu alto custo.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Seguir essa proporção ajuda a obter &lt;strong&gt;feedback rápido&lt;/strong&gt; (a maioria dos testes são rápidos), &lt;strong&gt;custos de manutenção controlados&lt;/strong&gt; e uma &lt;strong&gt;cobertura de risco eficaz&lt;/strong&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Pontos de Atenção e Nuances 📝
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Contexto é Rei:&lt;/strong&gt; Os exemplos e proporções são um guia, não uma regra absoluta. Adapte a estratégia ao seu produto e contexto. Um teste E2E para uma API é diferente de um para uma aplicação web full-stack.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Integração no Frontend:&lt;/strong&gt; Testes de integração não são exclusivos do backend! No frontend, eles podem verificar a interação entre componentes da UI, por exemplo.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Estratégia Balanceada:&lt;/strong&gt; O objetivo final é ter uma estratégia de testes balanceada, que maximize a confiança e minimize os custos e o tempo de feedback. ⚖️&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Concluindo...
&lt;/h2&gt;

&lt;p&gt;A Pirâmide de Testes é um modelo poderoso para guiar sua estratégia de testes, ajudando a construir aplicações mais robustas, confiáveis e fáceis de manter. Lembre-se que testes são um investimento na qualidade e sustentabilidade do seu software!&lt;/p&gt;

&lt;p&gt;E você, como aplica a Pirâmide de Testes nos seus projetos? Quais são seus maiores desafios ou aprendizados? Compartilhe nos comentários abaixo! 👇&lt;/p&gt;

</description>
      <category>programming</category>
      <category>webdev</category>
    </item>
    <item>
      <title>Entendendo a Replicação de Banco de Dados: Uma Chave para Sistemas Robustos</title>
      <dc:creator>Stephanto</dc:creator>
      <pubDate>Wed, 21 May 2025 19:50:04 +0000</pubDate>
      <link>https://dev.to/stephanto/entendendo-a-replicacao-de-banco-de-dados-uma-chave-para-sistemas-robustos-5eem</link>
      <guid>https://dev.to/stephanto/entendendo-a-replicacao-de-banco-de-dados-uma-chave-para-sistemas-robustos-5eem</guid>
      <description>&lt;p&gt;Olá a todos! Estou aqui novamente para compartilhar mais do que aprendi esta semana, especificamente sobre o tema da replicação de dados. Este artigo fornecerá uma explicação resumida do que é e quais são os seus tipos. Vamos lá!&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmedia.licdn.com%2Fdms%2Fimage%2Fv2%2FD4D12AQFgd2N1JkEhBA%2Farticle-cover_image-shrink_600_2000%2Farticle-cover_image-shrink_600_2000%2F0%2F1677831225612%3Fe%3D2147483647%26v%3Dbeta%26t%3DWbZrCjZbw2Zq2UPMzEb18-Zca9BRHhooN6iCmC9ANmQ" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmedia.licdn.com%2Fdms%2Fimage%2Fv2%2FD4D12AQFgd2N1JkEhBA%2Farticle-cover_image-shrink_600_2000%2Farticle-cover_image-shrink_600_2000%2F0%2F1677831225612%3Fe%3D2147483647%26v%3Dbeta%26t%3DWbZrCjZbw2Zq2UPMzEb18-Zca9BRHhooN6iCmC9ANmQ" alt="Replication" width="720" height="360"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Por Que a Replicação de Dados é Importante?
&lt;/h3&gt;

&lt;p&gt;Para entender a importância da replicação de dados, considere este cenário: Imagine que este é um servidor hospedado na minha casa. Se eu acidentalmente derramar café em cima do servidor/DB, o que acontece? Já era.&lt;/p&gt;

&lt;p&gt;Temos aqui um "Single point of failure".&lt;br&gt;
&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGpI--EzWYAAizPM%3Fformat%3Djpg%26name%3Dlarge" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGpI--EzWYAAizPM%3Fformat%3Djpg%26name%3Dlarge" alt="SPF" width="1398" height="811"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Outro ponto é que usuários de países diferentes têm tempos de resposta diferentes. Dependendo da localização, demora um tempo considerável para obter resposta da aplicação, o que pode prejudicar a experiência do usuário.&lt;br&gt;
&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGpI_GAhWgAA4rOX%3Fformat%3Djpg%26name%3D4096x4096" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGpI_GAhWgAA4rOX%3Fformat%3Djpg%26name%3D4096x4096" alt="Diferentes usuarios" width="3083" height="1623"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Então, a replicação pode servir para, caso algum servidor deixe de funcionar, aumentar a disponibilidade e diminuir a latência para diferentes localidades. Adicionamos mais DBs para poder garantir essas melhorias.&lt;br&gt;
&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGpI_MKDXcAE1MQC%3Fformat%3Djpg%26name%3D4096x4096" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGpI_MKDXcAE1MQC%3Fformat%3Djpg%26name%3D4096x4096" alt="Servidores" width="4096" height="2682"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Porém, não sei se vocês notaram, mas surge um novo problema: Temos 3 bancos de dados em 3 lugares diferentes. Como garantir e manter a sincronização entre os 3 bancos de dados?&lt;br&gt;
&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGpI_bCjXgAAuHsO%3Fformat%3Djpg%26name%3Dlarge" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGpI_bCjXgAAuHsO%3Fformat%3Djpg%26name%3Dlarge" alt="Databases" width="1506" height="1530"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Abordagens para Consistência de Dados
&lt;/h3&gt;

&lt;p&gt;Ao lidar com múltiplos bancos de dados, garantir a consistência dos dados é crucial. Existem duas abordagens principais:&lt;/p&gt;

&lt;h4&gt;
  
  
  1. Replicação Síncrona
&lt;/h4&gt;

&lt;p&gt;A primeira abordagem é a Síncrona. Ela garante o dado mais recente (tendo uma consistência forte) através de fazer com que o usuário aguarde, se necessário, todo o processo de replicação para obter a resposta dele. O problema dessa abordagem é que ela gera uma certa lentidão.&lt;br&gt;
![Sincrona]&lt;a href="https://pbs.twimg.com/media/GpI_d8sWsAAYR5J?format=jpg&amp;amp;name=4096x4096" rel="noopener noreferrer"&gt;https://pbs.twimg.com/media/GpI_d8sWsAAYR5J?format=jpg&amp;amp;name=4096x4096&lt;/a&gt;)&lt;/p&gt;

&lt;h4&gt;
  
  
  2. Replicação Assíncrona
&lt;/h4&gt;

&lt;p&gt;A outra abordagem é a Assíncrona. Com ela, o usuário não precisa esperar todo o processo de replicação (pois ele é feito em background), o que torna o acesso ao dado mais rápido. Seu problema é que não garante que a consistência seja 100%, e sim a chamada "consistência eventual".&lt;br&gt;
&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGpI_kpoWYAAoGhs%3Fformat%3Djpg%26name%3D4096x4096" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGpI_kpoWYAAoGhs%3Fformat%3Djpg%26name%3D4096x4096" alt="Assincrona" width="2585" height="2921"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Métodos de Replicação
&lt;/h3&gt;

&lt;p&gt;Agora que vocês sabem as abordagens, vamos para os métodos de replicação. Vou apresentar 3:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Single-leader replication&lt;/li&gt;
&lt;li&gt;Multi-leader replication&lt;/li&gt;
&lt;li&gt;Leaderless replication&lt;/li&gt;
&lt;/ul&gt;

&lt;h4&gt;
  
  
  1. Single-Leader Replication
&lt;/h4&gt;

&lt;p&gt;No Single-leader replication, apenas um banco recebe os writes e replica para os outros que apenas recebem reads.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Prós&lt;/strong&gt;: É bom pois não tem conflitos.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Contras&lt;/strong&gt;: Porém, tem um Throughput baixo e possui Single point of failure pois só um escreve.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Caso de Uso&lt;/strong&gt;: É comum de ser usado em aplicações financeiras.
&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGpI_tTgWMAAJdUR%3Fformat%3Djpg%26name%3D4096x4096" alt="SLR" width="4096" height="2375"&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;h4&gt;
  
  
  2. Multi-Leader Replication
&lt;/h4&gt;

&lt;p&gt;Já o Multi-leader replication, a replicação de dados ocorre entre os DBs, ou seja, todos são líderes.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Prós&lt;/strong&gt;: Possui um alto throughput para escritas.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Contras&lt;/strong&gt;: O que pode gerar conflitos nas escritas.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Caso de Uso&lt;/strong&gt;: É usado para grandes áreas geográficas.
&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGpI_vy9XgAA3KWe%3Fformat%3Djpg%26name%3D4096x4096" alt="MLR" width="4096" height="2561"&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;h4&gt;
  
  
  3. Leaderless Replication
&lt;/h4&gt;

&lt;p&gt;Por fim, o Leaderless replication funciona na forma de "Quorum" para lidas e escritas. Para simplificar, veja a imagem abaixo: Temos 4 nós, se um user quiser ler/escrever, será lido um pouco a mais da metade do número de nós para assim ter a resposta.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Prós&lt;/strong&gt;: Isso é feito para garantir a consistência, o que gera uma alta disponibilidade.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Contras&lt;/strong&gt;: Porém, acaba causando conflitos de escrita e gera latência na leitura.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Caso de Uso&lt;/strong&gt;: É usado em sistemas que priorizam alta disponibilidade e tolerância a falhas, como sistemas de mensagens.
&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fpbs.twimg.com%2Fmedia%2FGpI_2uLW8AAvNeu%3Fformat%3Djpg%26name%3D4096x4096" alt="Leaderless" width="3249" height="3429"&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Conclusão
&lt;/h3&gt;

&lt;p&gt;Bom, é isso. Espero que minha explicação tenha sido clara. Caso queiram, eu posso aprofundar mais em consistência e como lidar com conflitos de escrita. Fiquem livres para adicionar o que acharem relevante!&lt;/p&gt;

&lt;p&gt;Obrigado por lerem até aqui!&lt;/p&gt;

&lt;p&gt;Recomendo se aprofundarem em cada um deles, dei apenas uma visão geral e superficial para compreensão geral. Alguns materiais para leitura que dão uma complementada legal:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://www.geeksforgeeks.org/what-is-replication-in-distributed-system/" rel="noopener noreferrer"&gt;What is Replication in Distributed System?&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://blog.bytebytego.com/p/how-to-choose-a-replication-strategy" rel="noopener noreferrer"&gt;How to Choose a Replication Strategy&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>database</category>
      <category>devops</category>
    </item>
    <item>
      <title>COMO ESCALAR UM SISTEMA PARA 1 MILHÃO DE USUÁRIOS?</title>
      <dc:creator>Stephanto</dc:creator>
      <pubDate>Wed, 23 Apr 2025 15:05:18 +0000</pubDate>
      <link>https://dev.to/stephanto/como-escalar-um-sistema-para-1-milhao-de-usuarios-4a4m</link>
      <guid>https://dev.to/stephanto/como-escalar-um-sistema-para-1-milhao-de-usuarios-4a4m</guid>
      <description>&lt;p&gt;Escalar um sistema para suportar milhões de usuários é um desafio significativo. A complexidade aumenta com o aumento da carga de dados e usuários, demandando uma arquitetura robusta. Neste artigo, exploraremos como escalar um sistema para lidar com 1 milhão de usuários, utilizando boas práticas e abordagens como balanceamento de carga, caches, e sharding.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fmkohp1g342m9zku22i20.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fmkohp1g342m9zku22i20.png" alt="Image description" width="800" height="555"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;O fluxo comum de um usuário ao acessar um site é: Acessar o o site pela URL, o DNS traduzir o endereço, a requisição chegar no servidor e devolver o conteúdo para o usuário&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fdxb76qt5pu73d70wu5xb.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fdxb76qt5pu73d70wu5xb.png" alt="Image description" width="800" height="556"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Se começarmos a ter usuários acessando nosso site e quisermos guardar seus registros e/ou ter um backend que queremos armazenar dados, temos que ter um database que vai salvar e resgatar esses dados&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fsrnpgd8hy1gzbd2jvyxt.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fsrnpgd8hy1gzbd2jvyxt.png" alt="Image description" width="800" height="355"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Porém, como temos apenas 1 servidor, a medida que o número de usuários aumenta, pode gerar delay e timeout para alguns usuários, para isso adicionamos o loadbalancer que vai cuidar de encaminhar os usuários para os diferente servidores para não sobrecarregar&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fd0zvl05k1kjnbryfnfnq.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fd0zvl05k1kjnbryfnfnq.png" alt="Image description" width="800" height="784"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Agora, como teremos mais de um banco de dados (por conta do aumento de servidores), precisamos garantir a consistência dos dados. Podemos utilizar o método de Master/Slave, que somente 1 database recebe as escritas, replica para os outros e eles apenas leem os registros&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fquizy34gchqw3sbtmg5i.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fquizy34gchqw3sbtmg5i.png" alt="Image description" width="800" height="972"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Vamos dar uma olhada em como ficou nosso sistema até agora então, está bom mas ainda podemos melhorar bastante a performance&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F3jphu1h0b6clnhjr2pgw.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F3jphu1h0b6clnhjr2pgw.png" alt="Image description" width="800" height="1009"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Podemos adicionar um cache para dados frequentemente acessados. Assim, melhora a velocidade e poupa acessos ao banco de dados pela memória cache ser mais rápida&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Flwxwxchwbtdowx9sdtkk.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Flwxwxchwbtdowx9sdtkk.png" alt="Image description" width="800" height="87"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Podemos também adicionar um CDN. Um CDN é um servidor estrategicamente localizado em um lugar que seja mais perto do cliente, funciona semelhante a um cache&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fusbuyfqpdwz0bs74yx82.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fusbuyfqpdwz0bs74yx82.png" alt="Image description" width="800" height="419"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Com essas adições nosso sistema esta desta forma até agora:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fawc9lgdns9y0nswor2h9.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fawc9lgdns9y0nswor2h9.png" alt="Image description" width="800" height="915"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Ok, mas como escalamos ainda mais? Podemos mover uma parte do sistema para stateless, por exemplo, tirar o estado do usuário do servidor e adicionar em um NoSQL. No exemplo abaixo é como seria o acesso do usuário sem stateless, sua sessão e foto de perfil ficam apenas em 1 server&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fmefp9o5okaqa1l0j5ofs.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fmefp9o5okaqa1l0j5ofs.png" alt="Image description" width="800" height="505"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Já com stateless, adicionamos um shared storage para adicionar a sessão e a foto de perfil do usuário, para manter uma boa experiência de usuário (se o loadbalancer jogar ele pra outro servidor, ele não ser deslogado ou coisa do tipo)&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fvpjnd8kmbpep99ihkmjh.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fvpjnd8kmbpep99ihkmjh.png" alt="Image description" width="800" height="920"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Com essa adição, nosso sistema está ficando cada vez mais bonito e escalável&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Frlnczwnsjqll9500vue4.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Frlnczwnsjqll9500vue4.png" alt="Image description" width="800" height="743"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Ta bom, mas e se seu sistema quer internacionalizar? Para isso, vamos ter outro datacenter em outro país, e com isso, adicionamos um outro loadbalancer mas com algoritmo de georoute nele&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fomzb3ftkygr7vaymvuzl.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fomzb3ftkygr7vaymvuzl.png" alt="Image description" width="800" height="586"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Uma boa prática (algumas vezes) é desacoplar alguma função frequente que ser servidor faz para aumentar o desempenho e diminuir o overload em um macro-serviço. Exemplo, podemos fazer um sistema separado para processamento de imagens no nosso servidor usando sistema de filas. Com esse sistema de filas, caso algum servidor caia, não é perdido a requisição, além de, como dito anteriormente, diminuir o overload&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fttj5lmxj6a8ime9ju4pe.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fttj5lmxj6a8ime9ju4pe.png" alt="Image description" width="800" height="196"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Com isso, nosso sistema fica dessa forma:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fawmimvw1izozpssnuert.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fawmimvw1izozpssnuert.png" alt="Image description" width="800" height="860"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Por fim, o que podemos fazer é diminuir a sobrecarga do banco de dados. As bases de dados estão apenas com redundância até agora, com os mesmos tipos de dados em todos eles. Com isso, podemos usar um método chamado sharding.&lt;br&gt;
Sharding é, de forma simplifcada, usar um algoritmo para dividir a alocação de um registro em bases de dados diferentes. O exemplo abaixo vai elucidar melhor.&lt;br&gt;
Vou pegar o id do usuário e fazer módulo 4, o resultado vai fazer com que ele seja salvo em um DB especifico&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fxat4vlbwy0cxb7ss5m98.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fxat4vlbwy0cxb7ss5m98.png" alt="Image description" width="800" height="616"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Essa é uma visão de como ficaria cada um dos bancos de dados após o sharding:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fmd310z9n5kt88ahd43ry.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fmd310z9n5kt88ahd43ry.png" alt="Image description" width="800" height="814"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Agora juntando tudo isso que temos, voltamos para a imagem inicial do artigo. Vocês tem um sistema escalável para bem mais que 1 milhão de usuários!&lt;/p&gt;

&lt;p&gt;Espero que tenham compreendido de forma simples o funcionamento disso. Novamente, aconselho aprofundar no assunto!&lt;/p&gt;

&lt;p&gt;Obrigado por ler até aqui!&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F6enb6vgw98ddq5b4tsay.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F6enb6vgw98ddq5b4tsay.png" alt="Image description" width="" height=""&gt;&lt;/a&gt;&lt;/p&gt;

</description>
      <category>systemdesign</category>
      <category>beginners</category>
      <category>webdev</category>
      <category>programming</category>
    </item>
  </channel>
</rss>
