🚀 Capítulo 19: Command (Tema: Star Wars / Ordem 66)
NOTE
Este capítulo utiliza a temática de Star Wars para explicar o padrão Command. O Imperador Palpatine emite ordens (comandos) encapsuladas que os clones executam sem questionar!
1. 🎯 Objetivo da Aula
Compreender o padrão de projeto Command (Padrão Comportamental), entendendo como ele transforma uma solicitação em um objeto independente, contendo todas as informações sobre a solicitação.
2. 🏢 O Cenário Prático (Seu Desafio)
O Imperador Palpatine precisa gerenciar o exército de clones. Ele tem várias ordens que pode emitir:
- Ordem 65: Prender o Chanceler.
- Ordem 66: Eliminar os Jedi.
Em vez de ligar para cada comandante clone e dizer o que fazer (acoplamento forte), ele cria um holograma (Um objeto Comando) com a ordem gravada e envia para o exército.
- O comando sabe o que deve ser feito e quem deve fazer.
- Os clones apenas recebem o objeto e chamam o método
executar().
Esse padrão permite que o Imperador enfileire comandos, guarde o histórico e até desfaça comandos (Undo)! Seu desafio é programar a Ordem 66!
3. 🧠 Fundamentos: A Teoria Traduzida
O Command (Comando) é um padrão de projeto comportamental que transforma uma solicitação em um objeto independente que contém todas as informações sobre a solicitação.
🎮 Os Quatro Elementos:
- Command (Interface): Geralmente declara apenas um método
execute(). - Concrete Command: Define a ligação entre uma ação e o receptor (Ex: A Ordem 66).
- Receiver (Receptor): Quem realmente sabe como executar a ação (Ex: Os Clones).
- Invoker (Invocador): Quem envia o comando (Ex: O Imperador ou um botão na tela).
4. 📖 Exemplo Guiado: Executando a Ordem 66 (JS)
// RECEIVER (Quem executa a ação de verdade)
class ExercitoDeClones {
atacarJedi() { console.log("Clones: Executando Ordem 66. Atacando os Jedi!"); }
protegerJedi() { console.log("Clones: Protegendo os generais Jedi."); }
}
// COMMAND (A Ordem encapsulada)
class Ordem66Command {
constructor(exercito) {
this.exercito = exercito; // Guarda o receptor
}
execute() {
this.exercito.atacarJedi();
}
}
// INVOKER (Quem aperta o botão)
class Imperador {
constructor() {
this.comandoAtual = null;
}
emitirOrdem(comando) {
this.comandoAtual = comando;
this.comandoAtual.execute();
}
}
// USO
const clones = new ExercitoDeClones();
const ordem66 = new Ordem66Command(clones);
const palpatine = new Imperador();
// O Imperador envia o objeto comando
palpatine.emitirOrdem(ordem66);5. 🛠️ Prática Obrigatória 1: Desfazendo Ordens (Undo)
Uma das maiores vantagens do padrão Command é a facilidade de criar a função “Desfazer” (Ctrl+Z).
- Se adicionarmos um método
desfazer()na classeOrdem66Command, o que ele deveria chamar na classeExercitoDeClonespara reverter o ataque?
6. 🛠️ Prática Obrigatória 2: Command em Jogos
Em jogos de estratégia (como StarCraft), quando você seleciona 10 unidades e clica com o botão direito no mapa, o jogo cria um objeto Command contendo a posição do clique e envia para a fila de ações de cada unidade. Por que é melhor fazer isso do que mover as unidades direto no clique?
7. 📤 Instruções de Entrega (GitHub Desktop + Microsoft Teams)
- Faça o Commit: No GitHub Desktop, digite a mensagem (ex:
Finaliza Capítulo 19 Paradigmas) e clique em Commit to main. - Envie para a Nuvem (Push): Clique em Push origin.
8. 📂 Estrutura de Pastas
mod_10_paradigmas_e_padroes_de_projeto/
├── capitulos/
│ ├── capitulo_19_command.md
│ └── codigos/
│ └── cap19/
│ └── ordem_66.js9. 💡 Checkpoint de Lógica
O padrão Command permite desacoplar totalmente quem faz a solicitação (Imperador) de quem sabe como executá-la (Clones).
10. 🔥 Desafio de Fixação
Pesquise como o padrão Command é usado para implementar sistemas de Transações em bancos de dados (onde você pode dar commit ou rollback).
🔑 Gabarito de Código/Fórmulas
Gabarito da Prática 1:
- O método
desfazer()deveria chamarthis.exercito.protegerJedi()(ou parar o ataque), revertendo o estado anterior.