Problema com criação dinâmica de objetos

Estou com um problema na faculdade em egenharia de software e é o seguinte: Tenho o seguinte esquema ao efetuar o pagamento de um carrinho de compras devo saber se é BOLETO ou CARTÃO_DE_CREDITO Caso seja boleto eu gero um numero aleatório representando o código de barras, caso seja cartão de crédito eu recebo o numero do cartão e a quantidade de parcelas que o cliente desejar e calcular o valor de cada prestação (nesse caso o numero do cartão é alegórico).

Pensei em algo assim:

Pagamento.java

public interface Pagamento {

}

PagamentoBoleto.java

import java.util.Random;

public class PagamentoBoleto implements Pagamento{

    private final int codigoDeBarra;

    public PagamentoBoleto(final double valorCompra){
        this.codigoDeBarra = gerarCodigoDeBarra(valorCompra);
    }

    private int gerarCodigoDeBarra(final double valorCompra){
        long milisigundosAgora = System.currentTimeMillis();
        long semente = (long) (valorCompra + milisigundosAgora);

        Random random = new Random(semente);

        int min = 1000;
        int max = 9999;

        return random.nextInt((max - min) + 1) + min;
    }
}

PagamentoCartaoCredito.java

public class PagamentoCartaoCredito implements Pagamento{

private final String numeroCartaoCredito;
private final int quantidadeParcelas;

public PagamentoCartaoCredito(final String numeroCartaoCredito, final int quantidadeParcelas){
    this.numeroCartaoCredito = numeroCartaoCredito;
    this.quantidadeParcelas = quantidadeParcelas;
}

public double getValorParcela(double valorCompra) {
    return valorCompra / quantidadeParcelas;
}
}

TipoPagamentoEnumFactory.java

public enum TipoPagamento {


CARTAO(1) {
    public Pagamento getTipoPagamento() {
        return new PagamentoCartaoCredito();
    }
},
BOLETO(1) {
    public Pagamento getTipoPagamento() {
        return new PagamentoBoleto();
    }
};

public int op;

TipoPagamento(int valor) {
    op = valor;
}
public abstract Pagamento getTipoPagamento();
}

Problema … como as formas de pagamentos tem construtores distintos não sei como instância-los de forma bem dinâmica e flexivel.

Bom, não vai ter jeito, precisa verificar SE é um Cartão ou um Boleto, não?

Estou tentando fugir do if…else if… o máximo possível. Procurando algum padrão de projeto, se outra implementação de forma de pagamento for adicionada para que não haja muito código alterado e toda a lógica da nova forma de pagamento fique encapsulada separada.

Se eu for colocar um if para decidir qual objeto criar, tenho if para decidir qual tipo de retorno pegar, outro if para pegar o tipo de pagamento … se não houver uma saída “elegante e limpa” terei que fazer assim, mas no momento queria buscar uma solução mais Clean Code.

Ainda tenho um tempinho pra pensar nessa solução.

Nao seria só 1 “if”? Case tipo de pagamento … chama classe responsável pra efetuar cada tipo de pagamento. Se surgir mais um item acrescenta dentro do Case. Não tem retorno, tudo já estará referenciado no objeto relacionado, como por exemplo o pedido relacionado a esse pagamento.

1 curtida

Eu entendo que você gostaria de trabalhar com a visão de que “a good if is a not used if”, mas, você precisa entender que, em determinadas situações, não tem mágica.
A questão e´a que o @javaflex explicou.
Hoje você tem duas formas de pagamento, mas, pode ter quantas mais?
Talvez seja necessário repensar a estrutura como um todo.
Por que o construtor precisa ser diferente?
Por que não criar um construtor que se adeque as duas necessidades?

2 curtidas