Parte 06

Arquitetura & escala

Como pensar um sistema web antes de sair codando: as camadas, os padrões de arquitetura, um plano de desenvolvimento e o caminho pra escalar quando o projeto crescer.

📌 Regra de ouro: arquitetura serve pra isolar mudanças e adiar decisões. Comece simples (princípio YAGNI — "você não vai precisar disso"); só adicione complexidade quando a dor real aparecer. A maioria dos projetos morre de over-engineering, não de falta dele.
1

As camadas de um sistema web

Todo sistema web é o mesmo caminho de ida e volta. Entender esse fluxo é o que te diz onde cada problema (e cada solução) vive.

o caminho de um request
  NAVEGADOR              SERVIDOR WEB           SUA APLICAÇÃO          BANCO
 (cliente)              (Apache/Nginx)            (PHP)              (MariaDB)
     |                       |                      |                   |
     |  --- requisição --->  |  --- repassa --->    |  --- query --->   |
     |     GET /post?id=5    |     o .php           |   SELECT ...       |
     |                       |                      |  <-- dados ----    |
     |  <---- HTML --------   |  <--- resposta ---   |  (monta o HTML)   |
     |     (a página)        |                      |                   |
CamadaResponsabilidadeNo php.ref
Clienterenderizar HTML/CSS/JS, enviar requisiçõeso navegador abrindo as páginas
Servidor webreceber HTTP, servir estáticos, repassar .phpApache (XAMPP) / LiteSpeed (hospedagem)
Aplicaçãoregras de negócio, decidir o que fazerpacientes.php, index.php do blog
Dadosguardar e devolver informaçãobanco dumo2258_php (tabelas)
⚠️ Por que isso importa: quando o site fica lento, a pergunta certa é "em qual camada?". 9 em 10 vezes o gargalo está no banco (query sem índice), não no PHP. Mais sobre isso na seção 5.
2

Padrões de arquitetura

Do mais simples ao mais complexo. A escolha não é "qual é o melhor", e sim "qual o mais simples que resolve o meu problema hoje".

PadrãoQuando usarCusto
Páginas soltas
(scripts .php)
aprender, protótipo, site de 2-3 telasvira bagunça quando cresce
Monolito MVCa escolha padrão pra 95% dos projetosbaixo; organizado e fácil de manter
API + frontend
(backend separado)
app mobile, SPA (React/Vue), vários clientesmédio; dois projetos pra manter
Microsserviçostime grande, partes que escalam diferentealto; só com problema real de escala
📌 Não pule etapas: microsserviço é solução pra problema de organização de time grande e escala desigual — não pra projeto pequeno. Um monolito bem organizado aguenta MUITO mais carga do que se imagina. Comece por ele.
3

MVC e organização de pastas

MVC separa o código em três papéis, pra cada mudança mexer em um lugar só:

CamadaFaz o quêExemplo
Modelfala com o banco, representa os dadosclasse Post com buscarTodos()
Viewsó o HTML de saída, nada de lógica pesadao <table> que lista os posts
Controllerrecebe a requisição, chama o Model, escolhe a View"listar posts" → busca → manda pra view

Na prática, isso vira uma estrutura de pastas onde só uma pasta fica exposta na web:

estrutura de um projeto MVC
projeto/
├── public/            <- ÚNICA pasta no web root
│   ├── index.php      <- "front controller": toda requisição entra aqui
│   └── assets/        <- css, js, imagens
├── src/
│   ├── Controllers/   <- a lógica (PostController.php)
│   ├── Models/        <- acesso ao banco (Post.php)
│   └── Views/         <- os templates HTML
├── config/            <- FORA do public! conexao, .env, segredos
└── vendor/            <- bibliotecas (Composer)
⚠️ Segurança (item do checklist):public/ deve ficar acessível pela web. config/ (com a senha do banco) e src/ ficam fora do web root — assim ninguém abre seusite.com/config/conexao.php e lê suas credenciais.

O front controller é a ideia de ter uma porta de entrada só (public/index.php), que decide o que fazer pela rota:

public/index.php (front controller)
<?php
// Toda requisição cai aqui; a "rota" decide o destino.
$rota = $_GET["rota"] ?? "home";

match ($rota) {
    "home"     => require "../src/Controllers/HomeController.php",
    "post"     => require "../src/Controllers/PostController.php",
    default    => http_response_code(404),
};
4

Como planejar antes de codar

A ordem importa: pular o planejamento é o que gera o retrabalho mais caro (descobrir no meio que a tabela está errada). O caminho prático:

#PassoPergunta que responde
1Requisitos"o que o sistema precisa fazer?" (em frases curtas)
2Modelar os dados"quais entidades existem e como se relacionam?"
3Mapear rotas/telas"quais URLs/páginas o usuário acessa?"
4MVP"qual o mínimo que já entrega valor?"
5Iterar"o que adicionar agora que o básico funciona?"

Aplicando ao mini-blog que construímos:

planejamento do blog
1. REQUISITOS:  listar posts | ler um post | publicar post
2. DADOS:       entidade "post" = id, titulo, conteudo, criado_em
3. ROTAS:       /            -> lista
                /?post=5     -> um post
                POST /       -> publica
4. MVP:         os 3 itens acima, sem login, sem comentários
5. ITERAR:      depois: excluir, editar, busca, categorias...
📌 Modele os dados primeiro: as tabelas são a parte mais cara de mudar depois (já tem dado dentro!). Desenhe entidades e relações antes da primeira linha de PHP. Telas e código são baratos de refazer; estrutura de banco não.
5

Escalabilidade

Escalar = aguentar mais carga. Há dois caminhos, e a ordem certa de atacar os gargalos:

TipoO que éLimite
Verticalservidor maior (mais CPU/RAM)simples, mas tem teto e custa caro
Horizontalvários servidores dividindo a cargaquase ilimitado, mas exige app stateless

Onde os gargalos aparecem, na ordem mais comum:

GargaloSintomaSolução prática
Bancoquery lenta com muitos registrosíndice na coluna do WHERE/ORDER BY
Repetiçãomesma query/cálculo toda horacache (página, resultado, OPcache)
Estáticosimagens/css pesando no servidorCDN servindo os arquivos
Tarefa pesadaenvio de e-mail/relatório travando o requestfila (job assíncrono em background)

O gargalo nº 1 quase sempre é o banco. A correção mais barata é um índice:

índice no banco
-- Sem índice, ORDER BY criado_em varre a tabela inteira.
-- Com índice, o banco "pula" direto pro lugar certo.
CREATE INDEX idx_posts_criado ON posts (criado_em);

-- Pra ver SE uma query usa índice, rode na frente dela:
EXPLAIN SELECT * FROM posts ORDER BY criado_em DESC;
⚠️ Stateless é o segredo do horizontal: se a sessão do usuário fica salva no disco de um servidor, ele não pode ser atendido por outro. Pra escalar horizontal, guarde sessão num lugar compartilhado (banco/Redis), não em arquivo local. O mesmo vale pra uploads (use storage central, não a pasta do servidor).
6

Quando NÃO complicar

Mais projetos morrem de complexidade desnecessária do que de simplicidade. Cheiros de over-engineering:

CheiroRealidade
"Vamos usar microsserviços"
(com 1 dev e 100 usuários)
monolito resolve; microsserviço vira 5 problemas
"Preciso de cache/Redis"
(sem ter medido lentidão)
otimização prematura; meça antes
"Abstração pra tudo"
(camadas que ninguém usa)
código que ninguém entende; YAGNI
"Vou suportar 1 milhão de usuários"
(tem 10)
resolva o problema de hoje, não o imaginário
📌 O ciclo saudável: faça funcionar (simples) → meça onde dói → corrija esse ponto. Arquitetura boa é a que cresce junto com o problema, não na frente dele.
← Parte 5 · CRUD pacientes Voltar à capa →