1.1 --- a/task3/solution06/src/org/apidesign/apifest08/currency/Convertor.java Tue Oct 07 11:05:34 2008 +0200
1.2 +++ b/task3/solution06/src/org/apidesign/apifest08/currency/Convertor.java Fri Oct 10 21:54:39 2008 +0200
1.3 @@ -8,6 +8,9 @@
1.4 import java.util.Currency;
1.5 import java.util.List;
1.6
1.7 +/**
1.8 + * Currency covertor.
1.9 + */
1.10 public final class Convertor {
1.11
1.12 private List<ConvertorDelegate> convertorDelegates = new ArrayList<ConvertorDelegate>();
1.13 @@ -24,7 +27,22 @@
1.14 notNull(currencyFirst, "currencyFirst");
1.15 notNull(currencySecond, "currencySecond");
1.16 notNull(rateValue, "rateValue");
1.17 - convertorDelegates.add(new ConvertorDelegate(rateValue, currencyFirst, currencySecond));
1.18 + convertorDelegates.add(new ConvertorDelegate(new StaticRateProvider(rateValue), currencyFirst, currencySecond));
1.19 + }
1.20 +
1.21 + /**
1.22 + * Create new instance of the converter for the given currencies and its rate.
1.23 + * A rate value is provided by {@link RateProvider}.
1.24 + *
1.25 + * @param rateProvider the rate provider
1.26 + * @param currencyFirst the first currency
1.27 + * @param currencySecond the second currency
1.28 + */
1.29 + public Convertor(RateProvider rateProvider, Currency currencyFirst, Currency currencySecond) {
1.30 + notNull(currencyFirst, "currencyFirst");
1.31 + notNull(currencySecond, "currencySecond");
1.32 + notNull(rateProvider, "rateProvider");
1.33 + convertorDelegates.add(new ConvertorDelegate(rateProvider, currencyFirst, currencySecond));
1.34 }
1.35
1.36 /**
1.37 @@ -84,11 +102,12 @@
1.38 private static class ConvertorDelegate {
1.39 private final Currency first;
1.40 private final Currency second;
1.41 - private final BigDecimal rateValue; // a rate between the first currency and the second currency
1.42 + private final RateProvider rateProvider;
1.43 public static final BigDecimal one = new BigDecimal(1);
1.44
1.45 - private ConvertorDelegate(BigDecimal rateValue, Currency currencyFirst, Currency currencySecond) {
1.46 - this.rateValue = rateValue;
1.47 +
1.48 + private ConvertorDelegate(RateProvider rateProvider, Currency currencyFirst, Currency currencySecond) {
1.49 + this.rateProvider = rateProvider;
1.50 this.first = currencyFirst;
1.51 this.second = currencySecond;
1.52 }
1.53 @@ -104,8 +123,16 @@
1.54 BigDecimal retVal;
1.55
1.56 if(first == fromCurrency) {
1.57 + BigDecimal rateValue = rateProvider.getRate();
1.58 + if(rateValue == null) {
1.59 + throw new NullPointerException("Rate cannot be null!");
1.60 + }
1.61 retVal = rateValue;
1.62 } else {
1.63 + BigDecimal rateValue = rateProvider.getRate();
1.64 + if(rateValue == null) {
1.65 + throw new NullPointerException("Rate cannot be null!");
1.66 + }
1.67 //reverse rate
1.68 retVal = one.divide(rateValue, 10 ,RoundingMode.HALF_UP);
1.69 }
1.70 @@ -121,4 +148,29 @@
1.71 return ((fromCurrency == first || fromCurrency == second) && (toCurrency == first || toCurrency == second));
1.72 }
1.73 }
1.74 +
1.75 + /**
1.76 + * A rate provider. This class represents a way how could be "static" convertor
1.77 + * extended in order converts according to current rate.
1.78 + */
1.79 + public static abstract class RateProvider {
1.80 +
1.81 + /**
1.82 + * @return a rate between the from currency and the to currency associated with
1.83 + * a given convertor.
1.84 + */
1.85 + public abstract BigDecimal getRate();
1.86 + }
1.87 +
1.88 + private static class StaticRateProvider extends RateProvider{
1.89 + private final BigDecimal rateValue;
1.90 +
1.91 + private StaticRateProvider(BigDecimal rateValue){
1.92 + this.rateValue = rateValue;
1.93 + }
1.94 +
1.95 + public BigDecimal getRate() {
1.96 + return this.rateValue;
1.97 + }
1.98 + }
1.99 }