/**
* Copyright (C) 2014 - present by OpenGamma Inc. and the OpenGamma group of companies
*
* Please see distribution for license.
*/
package com.opengamma.analytics.financial.instrument.payment;
import static org.testng.AssertJUnit.assertEquals;
import static org.testng.AssertJUnit.assertFalse;
import org.testng.annotations.Test;
import org.threeten.bp.ZonedDateTime;
import com.opengamma.OpenGammaRuntimeException;
import com.opengamma.analytics.financial.interestrate.payments.derivative.CouponFixed;
import com.opengamma.analytics.financial.interestrate.payments.derivative.CouponFixedFxReset;
import com.opengamma.analytics.financial.interestrate.payments.derivative.Payment;
import com.opengamma.analytics.util.time.TimeCalculator;
import com.opengamma.timeseries.DoubleTimeSeries;
import com.opengamma.timeseries.precise.zdt.ImmutableZonedDateTimeDoubleTimeSeries;
import com.opengamma.util.money.Currency;
import com.opengamma.util.test.TestGroup;
import com.opengamma.util.time.DateUtils;
/**
* Tests the constructors and equal/hash for CouponFixedFxResetDefinition.
*/
@Test(groups = TestGroup.UNIT)
public class CouponFixedFxResetDefinitionTest {
/** Details coupon. */
private static final Currency CUR_REF = Currency.EUR;
private static final Currency CUR_PAY = Currency.USD;
private static final ZonedDateTime PAYMENT_DATE = DateUtils.getUTCDate(2011, 4, 6);
private static final ZonedDateTime ACCRUAL_START_DATE = DateUtils.getUTCDate(2011, 1, 5);
private static final ZonedDateTime ACCRUAL_END_DATE = DateUtils.getUTCDate(2011, 4, 5);
private static final ZonedDateTime FX_FIXING_DATE = DateUtils.getUTCDate(2011, 1, 3);
private static final ZonedDateTime FX_DELIVERY_DATE = DateUtils.getUTCDate(2011, 1, 6);
private static final double ACCRUAL_FACTOR = 0.267;
private static final double NOTIONAL = 1000000; //1m
private static final double RATE = 0.04;
private static final CouponFixedFxResetDefinition CPN = new CouponFixedFxResetDefinition(CUR_PAY, PAYMENT_DATE,
ACCRUAL_START_DATE, ACCRUAL_END_DATE, ACCRUAL_FACTOR, NOTIONAL, RATE, CUR_REF, FX_FIXING_DATE, FX_DELIVERY_DATE);
private static final double FX_FIXING_RATE = 1.40;
private static final DoubleTimeSeries<ZonedDateTime> FX_FIXING_TS_10 =
ImmutableZonedDateTimeDoubleTimeSeries.ofUTC(
new ZonedDateTime[] {FX_FIXING_DATE.minusDays(11), FX_FIXING_DATE.minusDays(10) },
new double[] {1.38, 1.39 });
private static final DoubleTimeSeries<ZonedDateTime> FX_FIXING_TS_1 =
ImmutableZonedDateTimeDoubleTimeSeries.ofUTC(
new ZonedDateTime[] {FX_FIXING_DATE.minusDays(2), FX_FIXING_DATE.minusDays(1) },
new double[] {1.38, 1.39 });
private static final DoubleTimeSeries<ZonedDateTime> FX_FIXING_TS0 =
ImmutableZonedDateTimeDoubleTimeSeries.ofUTC(
new ZonedDateTime[] {FX_FIXING_DATE.minusDays(2), FX_FIXING_DATE.minusDays(1), FX_FIXING_DATE },
new double[] {1.38, 1.39, FX_FIXING_RATE });
private static final double TOLERANCE_AMOUNT = 1.0E-6;
@Test(expectedExceptions = IllegalArgumentException.class)
public void nullReferenceCurrency() {
new CouponFixedFxResetDefinition(CUR_PAY, PAYMENT_DATE, ACCRUAL_START_DATE, ACCRUAL_END_DATE, ACCRUAL_FACTOR,
NOTIONAL, RATE, null, FX_FIXING_DATE, FX_DELIVERY_DATE);
}
@Test(expectedExceptions = IllegalArgumentException.class)
public void nullFixingDate() {
new CouponFixedFxResetDefinition(CUR_PAY, PAYMENT_DATE, ACCRUAL_START_DATE, ACCRUAL_END_DATE, ACCRUAL_FACTOR,
NOTIONAL, RATE, CUR_REF, null, FX_DELIVERY_DATE);
}
@Test(expectedExceptions = IllegalArgumentException.class)
public void nullDeliveryDate() {
new CouponFixedFxResetDefinition(CUR_PAY, PAYMENT_DATE, ACCRUAL_START_DATE, ACCRUAL_END_DATE, ACCRUAL_FACTOR,
NOTIONAL, RATE, CUR_REF, FX_FIXING_DATE, null);
}
@Test
public void getter() {
assertEquals("CouponFixedFxResetDefinition: getter", RATE, CPN.getRate());
assertEquals("CouponFixedFxResetDefinition: getter", CUR_REF, CPN.getReferenceCurrency());
assertEquals("CouponFixedFxResetDefinition: getter", FX_FIXING_DATE, CPN.getFxFixingDate());
assertEquals("CouponFixedFxResetDefinition: getter", FX_DELIVERY_DATE, CPN.getFxDeliveryDate());
}
@Test
public void paymentAmount() {
double amountExpected = NOTIONAL * FX_FIXING_RATE * RATE * ACCRUAL_FACTOR;
double amountComputed = CPN.paymentAmount(FX_FIXING_RATE);
assertEquals("CouponFixedFxResetDefinition: paymentAmount", amountExpected, amountComputed, TOLERANCE_AMOUNT);
}
@Test
public void equalHash() {
assertEquals("CouponFixedFxResetDefinition: hash-equal", CPN, CPN);
assertFalse("CouponFixedFxResetDefinition: hash-equal", CPN.equals(CUR_REF));
CouponFixedDefinition cpnOther = new CouponFixedDefinition(CUR_PAY, PAYMENT_DATE, ACCRUAL_START_DATE,
ACCRUAL_END_DATE, ACCRUAL_FACTOR, NOTIONAL, FX_FIXING_RATE);
assertFalse("CouponFixedFxResetDefinition: hash-equal", CPN.equals(cpnOther));
CouponFixedFxResetDefinition other = new CouponFixedFxResetDefinition(CUR_PAY, PAYMENT_DATE, ACCRUAL_START_DATE,
ACCRUAL_END_DATE, ACCRUAL_FACTOR, NOTIONAL, RATE, CUR_REF, FX_FIXING_DATE, FX_DELIVERY_DATE);
assertEquals("CouponFixedFxResetDefinition: hash-equal", CPN, other);
assertEquals("CouponFixedFxResetDefinition: hash-equal", CPN.hashCode(), other.hashCode());
CouponFixedFxResetDefinition modified;
modified = new CouponFixedFxResetDefinition(Currency.AUD, PAYMENT_DATE, ACCRUAL_START_DATE, ACCRUAL_END_DATE,
ACCRUAL_FACTOR, NOTIONAL, RATE, CUR_REF, FX_FIXING_DATE, FX_DELIVERY_DATE);
assertFalse("CouponFixedFxResetDefinition: hash-equal", CPN.equals(modified));
modified = new CouponFixedFxResetDefinition(CUR_PAY, PAYMENT_DATE, ACCRUAL_START_DATE, ACCRUAL_END_DATE,
ACCRUAL_FACTOR, NOTIONAL, RATE+0.01, CUR_REF, FX_FIXING_DATE, FX_DELIVERY_DATE);
assertFalse("CouponFixedFxResetDefinition: hash-equal", CPN.equals(modified));
modified = new CouponFixedFxResetDefinition(CUR_PAY, PAYMENT_DATE, ACCRUAL_START_DATE, ACCRUAL_END_DATE,
ACCRUAL_FACTOR, NOTIONAL, RATE, Currency.AUD, FX_FIXING_DATE, FX_DELIVERY_DATE);
assertFalse("CouponFixedFxResetDefinition: hash-equal", CPN.equals(modified));
modified = new CouponFixedFxResetDefinition(CUR_PAY, PAYMENT_DATE, ACCRUAL_START_DATE, ACCRUAL_END_DATE,
ACCRUAL_FACTOR, NOTIONAL, RATE, CUR_REF, FX_FIXING_DATE.plusDays(1), FX_DELIVERY_DATE);
assertFalse("CouponFixedFxResetDefinition: hash-equal", CPN.equals(modified));
modified = new CouponFixedFxResetDefinition(CUR_PAY, PAYMENT_DATE, ACCRUAL_START_DATE, ACCRUAL_END_DATE,
ACCRUAL_FACTOR, NOTIONAL, RATE, CUR_REF, FX_FIXING_DATE, FX_DELIVERY_DATE.plusDays(1));
assertFalse("CouponFixedFxResetDefinition: hash-equal", CPN.equals(modified));
}
@Test(expectedExceptions = IllegalArgumentException.class)
public void toDerivativeMissingFixing() {
ZonedDateTime valuationDate = FX_FIXING_DATE.plusDays(1);
CPN.toDerivative(valuationDate);
}
@Test(expectedExceptions = IllegalArgumentException.class)
public void toDerivativeNullFixing() {
CPN.toDerivative(FX_FIXING_DATE, (DoubleTimeSeries<ZonedDateTime>)null);
}
@Test
public void toDerivativeBeforeFixingNoHts() {
ZonedDateTime valuationDate = FX_FIXING_DATE.minusDays(10);
double paymentTime = TimeCalculator.getTimeBetween(valuationDate, PAYMENT_DATE);
double fixingTime = TimeCalculator.getTimeBetween(valuationDate, FX_FIXING_DATE);
double deliveryTime = TimeCalculator.getTimeBetween(valuationDate, FX_DELIVERY_DATE);
CouponFixedFxReset cpnExpected = new CouponFixedFxReset(CUR_PAY, paymentTime, ACCRUAL_FACTOR, NOTIONAL, RATE,
CUR_REF, fixingTime, deliveryTime);
CouponFixedFxReset cpnConverted = CPN.toDerivative(valuationDate);
assertEquals("CouponFixedFxResetDefinition: toDerivative", cpnExpected, cpnConverted);
}
@Test
public void toDerivativeBeforeFixing() {
ZonedDateTime valuationDate = FX_FIXING_DATE.minusDays(10);
double paymentTime = TimeCalculator.getTimeBetween(valuationDate, PAYMENT_DATE);
double fixingTime = TimeCalculator.getTimeBetween(valuationDate, FX_FIXING_DATE);
double deliveryTime = TimeCalculator.getTimeBetween(valuationDate, FX_DELIVERY_DATE);
CouponFixedFxReset cpnExpected = new CouponFixedFxReset(CUR_PAY, paymentTime, ACCRUAL_FACTOR, NOTIONAL, RATE,
CUR_REF, fixingTime, deliveryTime);
Payment cpnConverted = CPN.toDerivative(valuationDate, FX_FIXING_TS_10);
assertEquals("CouponFixedFxResetDefinition: toDerivative", cpnExpected, cpnConverted);
}
@Test(expectedExceptions = OpenGammaRuntimeException.class)
public void toDerivativeAfterFixingNotAvailable() {
ZonedDateTime valuationDate = FX_FIXING_DATE.plusDays(1);
CPN.toDerivative(valuationDate, FX_FIXING_TS_1);
}
@Test
public void toDerivativeOnFixingNotAvailable() {
ZonedDateTime valuationDate = FX_FIXING_DATE;
double paymentTime = TimeCalculator.getTimeBetween(valuationDate, PAYMENT_DATE);
double fixingTime = TimeCalculator.getTimeBetween(valuationDate, FX_FIXING_DATE);
double deliveryTime = TimeCalculator.getTimeBetween(valuationDate, FX_DELIVERY_DATE);
CouponFixedFxReset cpnExpected = new CouponFixedFxReset(CUR_PAY, paymentTime, ACCRUAL_FACTOR, NOTIONAL, RATE,
CUR_REF, fixingTime, deliveryTime);
Payment cpnConverted = CPN.toDerivative(valuationDate, FX_FIXING_TS_1);
assertEquals("CouponFixedFxResetDefinition: toDerivative", cpnExpected, cpnConverted);
}
@Test
public void toDerivativeOnFixingAvailable() {
ZonedDateTime valuationDate = FX_FIXING_DATE;
double paymentTime = TimeCalculator.getTimeBetween(valuationDate, PAYMENT_DATE);
CouponFixed cpnExpected = new CouponFixed(CUR_PAY, paymentTime, ACCRUAL_FACTOR, NOTIONAL*FX_FIXING_RATE, RATE);
Payment cpnConverted = CPN.toDerivative(valuationDate, FX_FIXING_TS0);
assertEquals("CouponFixedFxResetDefinition: toDerivative", cpnExpected, cpnConverted);
}
@Test
public void toDerivativeAfterFixing() {
ZonedDateTime valuationDate = FX_FIXING_DATE.plusDays(1);
double paymentTime = TimeCalculator.getTimeBetween(valuationDate, PAYMENT_DATE);
CouponFixed cpnExpected = new CouponFixed(CUR_PAY, paymentTime, ACCRUAL_FACTOR, NOTIONAL*FX_FIXING_RATE, RATE);
Payment cpnConverted = CPN.toDerivative(valuationDate, FX_FIXING_TS0);
assertEquals("CouponFixedFxResetDefinition: toDerivative", cpnExpected, cpnConverted);
}
}