Post

Strategy

Padrão Strategy

Imagine que você quer executar operações de diferentes maneiras, mas com o mesmo propósito! talvez um bom exemplo é a execução de uma função para de diferentes formas de clientes.

Pense em ter que implementar duas ou mais lógicas de um código conforme o cliente utilizado, provavelmente seu código vai começar a ficar insustentável, difícil para testar… a medida que fica mais complexo e mais regras aparecem para serem feitas conforme o cliente ganha funcionalidades, vamos a um exemplo.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
enum ClientType
{
    PF,
    PJ,
    FORNECEDOR,
}
class MensagensService {

    public async void EnviarMensagens(Cliente cliente) {

        if (ClienteHelper.TypeCliente(cliente) == ClientType.PF) {
            // lógica para executar o envio da mensagem para cliente pessoa fisica
        }

        if (ClienteHelper.TypeCliente(cliente) == ClientType.PJ) {
            // lógica para executar o envio da mensagem para cliente PJ
        }

        if (ClienteHelper.TypeCliente(cliente) == ClientType.FORNECEDOR) {
            // lógica para executar o envio da mensagem para cliente fornecedor
        }

    }
}

O código acima é muito ruim, pois com o passar do tempo ele se torna ineficiente e confuso, cada tipo de cliente tem estratégias diferentes para o envio de mensagens e essas nesse momento não importam muito, mas o que importa é que isso tem que ser tratado de forma separada, existem outras formas de resolver isso… mas hoje estamos falando do strategy :)

Iniciando Solução

Uma boa solução seria uma classe que consegue navegar entre cada estratégia, e aqui vamos definir que cada estratégia se trata de cada tipo de envio de mensagem, vamos chamar essa classe de context.

também precisamos de uma rota(interface) no entre meio da classe de contexto e as estratégias

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
interface Strategy {
    void Execute();
}

class EnvioMensagemPF : Strategy {
    public void Execute() {
        // lógica para executar o envio da mensagem para cliente pessoa fisica
    }
}

class EnvioMensagemPJ : Strategy {
    public void Execute() {
        // lógica para executar o envio da mensagem para cliente PJ
    }
}

class EnvioMensagemFornecedor : Strategy {
    public void Execute() {
        // lógica para executar o envio da mensagem para cliente FORNECEDOR
    }
}

class Context {
    private Strategy Strategy {get; set;}

     public Context(Strategy strategy) {
        Strategy = strategy;
     }

    public void Execute() {
        Console.WriteLine("executando strategy");
        Strategy.Execute();
    }

    public void SetStrategy(Strategy strategy) {
        Strategy = strategy;
    }
}

A partir de agora ficou bem mais tranquilo para adicionar lógica e comportamento de forma separada para cada método Execute de cada tipo de Envio.

Executando

1
2
3
4
5
6
7
// nesse ponto pode haver alguma lógica para definir a estratégia de envio, lembrando que isso pode ocorrer em várias partes do código a depender da solução.

var strategy = new EnvioMensagemPF();
var context = new Context(strategy);

context.Execute();

é isso :)

This post is licensed under CC BY 4.0 by the author.