У меня есть интерфейс TaxCalculator, который выглядит таки одна внутренняя система У меня есть третья реализация, которая действует как прокси-сервер - эффективно при каждом вызове он работает так:
@Override
public SalesTaxRates getSalesTaxes(ShoppingCart cart, Address address)
{
Map<String,SalesTaxRates> cache = getTaxSessionCache();
String cacheKey = generateCacheKey(cart,address);
if(cache.containsKey(cacheKey))
return cache.get(cacheKey);
TaxCallable taxCallable = new TaxCallable() {
@Override
public SalesTaxRates call() {
return this.getTaxCalculator().getSalesTaxes(cart,address);
}
};
SalesTaxRates taxRates = callTaxCalculators(taxCallable);
if(taxRates.isCacheable())
cache.put(cacheKey, taxRates);
return taxRates;
}
И метод, определенный:
private static SalesTaxRates callTaxCalculators(TaxCallable callable)
{
for (TaxCalculator taxCalculator: TaxEngine.getTaxCalculators())
{
FutureTask<SalesTaxRates> futureTask = new FutureTask<>(callable.setTaxCalculator(taxCalculator));
new Thread(futureTask).start();
try {
SalesTaxRates taxRates = futureTask.get(getTaxCalculatorTimeout(), TimeUnit.MILLISECONDS);
if(taxRates!=null && taxRates.isCalculated())
{
BHLogger.info("Used taxcalculator: " + taxRates.getTaxEngine() + "rate: " + taxRates.getTotalTaxRate());
return taxRates;
}
} catch (Exception e) {
BHLogger.error(e);
}
}
BHLogger.error("ShoppingCart.calculteSalesTax","No taxCalculator calculated taxes correctly");
return SalesTaxRates.NOT_CALCULATED;
}
проверяет кэш, видит его там и возвращает.В противном случае он вызывает перенаправляющее сообщение и кэширует его. Так что это кажется очень повторяющимся для каждого перегруженного метода, но для меня нет очевидного способа вызвать один метод, поскольку кэширование отличается. Мой менеджер предложил использовать шаблон компоновщика.Создайте объект TaxRequest, который имеет соответствующие поля.Он может позаботиться о собственном кэшировании
Я думаю, это будет выглядеть так
class TaxRequest{
private Order order;
private Cart cart;
private Address address;
private String zipcode;
private SalesTaxRates send(TaxCalculator tc){
//check cache
//else
tc.getSalesTaxes(this);
//handlecaching
}
}
Интерфейсу нужен только один метод, и класс Forwarding становится очень простым, я думаю, реализация ApiTaxCalculator сейчаснеобходимо справиться с этим, имея такой метод
SalesTaxRates getSalesTax(TaxRequest taxRequest)
{
if(taxRequest.hasOrder()
returnGetSalesTaxes(taxRequest.getOrder);
//if has address and cart... if has only address... if has just a zip...
}
, в основном, предлагается использовать шаблон компоновщика вместо перегрузки метода, но этот последний метод мне кажется очень неудобным. Еще одна причина, почему это было предложено,внутренний taxCalculator не делает ничего другого с ордером, чем просто почтовый индекс.В идеале он должен принимать во внимание такие вещи, как тип товара, скидки и т. Д., Но это не так.Он просто ищет скорость на основе почтового индекса, так что в этом классе слишком много служебной информации, просто перенаправляя его этому методу
Любой совет?