Search in sources :

Example 51 with InvoiceItem

use of org.killbill.billing.invoice.api.InvoiceItem in project killbill by killbill.

the class TestInvoiceDao method testRefundCBAFullyConsumedTwice.

@Test(groups = "slow")
public void testRefundCBAFullyConsumedTwice() throws Exception {
    final UUID accountId = account.getId();
    // Create invoice 1
    // Scenario: single item with payment
    // * $10 item
    // Then, a repair occur:
    // * $-10 repair
    // * $10 generated CBA due to the repair (assume previous payment)
    final Invoice invoice1 = new DefaultInvoice(accountId, clock.getUTCToday(), clock.getUTCToday(), Currency.USD);
    final InvoiceItem fixedItem1 = new FixedPriceInvoiceItem(invoice1.getId(), invoice1.getAccountId(), null, null, UUID.randomUUID().toString(), UUID.randomUUID().toString(), clock.getUTCToday(), BigDecimal.TEN, Currency.USD);
    final RepairAdjInvoiceItem repairAdjInvoiceItem = new RepairAdjInvoiceItem(fixedItem1.getInvoiceId(), fixedItem1.getAccountId(), fixedItem1.getStartDate(), fixedItem1.getEndDate(), fixedItem1.getAmount().negate(), fixedItem1.getCurrency(), fixedItem1.getId());
    final CreditBalanceAdjInvoiceItem creditBalanceAdjInvoiceItem1 = new CreditBalanceAdjInvoiceItem(fixedItem1.getInvoiceId(), fixedItem1.getAccountId(), fixedItem1.getStartDate(), fixedItem1.getAmount(), fixedItem1.getCurrency());
    invoiceUtil.createInvoice(invoice1, context);
    invoiceUtil.createInvoiceItem(fixedItem1, context);
    invoiceUtil.createInvoiceItem(repairAdjInvoiceItem, context);
    invoiceUtil.createInvoiceItem(creditBalanceAdjInvoiceItem1, context);
    final BigDecimal paymentAmount = new BigDecimal("10.00");
    final UUID paymentId = UUID.randomUUID();
    final DefaultInvoicePayment defaultInvoicePayment = new DefaultInvoicePayment(InvoicePaymentType.ATTEMPT, paymentId, invoice1.getId(), clock.getUTCNow().plusDays(12), paymentAmount, Currency.USD, Currency.USD, "cookie", true);
    invoiceDao.notifyOfPaymentCompletion(new InvoicePaymentModelDao(defaultInvoicePayment), context);
    // Create invoice 2
    // Scenario: single item
    // * $5 item
    // * $-5 CBA used
    final DefaultInvoice invoice2 = new DefaultInvoice(accountId, clock.getUTCToday(), clock.getUTCToday(), Currency.USD);
    final InvoiceItem fixedItem2 = new FixedPriceInvoiceItem(invoice2.getId(), invoice1.getAccountId(), null, null, UUID.randomUUID().toString(), UUID.randomUUID().toString(), clock.getUTCToday(), new BigDecimal("5"), Currency.USD);
    final CreditBalanceAdjInvoiceItem creditBalanceAdjInvoiceItem2 = new CreditBalanceAdjInvoiceItem(fixedItem2.getInvoiceId(), fixedItem2.getAccountId(), fixedItem2.getStartDate(), fixedItem2.getAmount().negate(), fixedItem2.getCurrency());
    invoiceUtil.createInvoice(invoice2, context);
    invoiceUtil.createInvoiceItem(fixedItem2, context);
    invoiceUtil.createInvoiceItem(creditBalanceAdjInvoiceItem2, context);
    // Create invoice 3
    // Scenario: single item
    // * $5 item
    // * $-5 CBA used
    final DefaultInvoice invoice3 = new DefaultInvoice(accountId, clock.getUTCToday(), clock.getUTCToday(), Currency.USD);
    final InvoiceItem fixedItem3 = new FixedPriceInvoiceItem(invoice3.getId(), invoice1.getAccountId(), null, null, UUID.randomUUID().toString(), UUID.randomUUID().toString(), clock.getUTCToday(), new BigDecimal("5"), Currency.USD);
    final CreditBalanceAdjInvoiceItem creditBalanceAdjInvoiceItem3 = new CreditBalanceAdjInvoiceItem(fixedItem3.getInvoiceId(), fixedItem3.getAccountId(), fixedItem3.getStartDate(), fixedItem3.getAmount().negate(), fixedItem3.getCurrency());
    invoiceUtil.createInvoice(invoice3, context);
    invoiceUtil.createInvoiceItem(fixedItem3, context);
    invoiceUtil.createInvoiceItem(creditBalanceAdjInvoiceItem3, context);
    // Verify scenario - all CBA should have been used
    Assert.assertEquals(invoiceDao.getAccountCBA(accountId, context).doubleValue(), 0.00);
    invoiceUtil.verifyInvoice(invoice1.getId(), 0.00, 10.00, context);
    invoiceUtil.verifyInvoice(invoice2.getId(), 0.00, -5.00, context);
    invoiceUtil.verifyInvoice(invoice3.getId(), 0.00, -5.00, context);
    invoiceDao.createRefund(paymentId, paymentAmount, false, ImmutableMap.<UUID, BigDecimal>of(), UUID.randomUUID().toString(), context);
    // Verify all three invoices were affected
    Assert.assertEquals(invoiceDao.getAccountCBA(accountId, context).doubleValue(), 0.00);
    invoiceUtil.verifyInvoice(invoice1.getId(), 10.00, 10.00, context);
    invoiceUtil.verifyInvoice(invoice2.getId(), 0.00, -5.00, context);
    invoiceUtil.verifyInvoice(invoice3.getId(), 0.00, -5.00, context);
}
Also used : Invoice(org.killbill.billing.invoice.api.Invoice) DefaultInvoice(org.killbill.billing.invoice.model.DefaultInvoice) FixedPriceInvoiceItem(org.killbill.billing.invoice.model.FixedPriceInvoiceItem) RecurringInvoiceItem(org.killbill.billing.invoice.model.RecurringInvoiceItem) InvoiceItem(org.killbill.billing.invoice.api.InvoiceItem) ExternalChargeInvoiceItem(org.killbill.billing.invoice.model.ExternalChargeInvoiceItem) CreditAdjInvoiceItem(org.killbill.billing.invoice.model.CreditAdjInvoiceItem) RepairAdjInvoiceItem(org.killbill.billing.invoice.model.RepairAdjInvoiceItem) ParentInvoiceItem(org.killbill.billing.invoice.model.ParentInvoiceItem) ItemAdjInvoiceItem(org.killbill.billing.invoice.model.ItemAdjInvoiceItem) CreditBalanceAdjInvoiceItem(org.killbill.billing.invoice.model.CreditBalanceAdjInvoiceItem) CreditBalanceAdjInvoiceItem(org.killbill.billing.invoice.model.CreditBalanceAdjInvoiceItem) FixedPriceInvoiceItem(org.killbill.billing.invoice.model.FixedPriceInvoiceItem) UUID(java.util.UUID) DefaultInvoice(org.killbill.billing.invoice.model.DefaultInvoice) BigDecimal(java.math.BigDecimal) RepairAdjInvoiceItem(org.killbill.billing.invoice.model.RepairAdjInvoiceItem) DefaultInvoicePayment(org.killbill.billing.invoice.model.DefaultInvoicePayment) Test(org.testng.annotations.Test)

Example 52 with InvoiceItem

use of org.killbill.billing.invoice.api.InvoiceItem in project killbill by killbill.

the class TestInvoiceWithMetadata method testWith$0RecurringItem.

@Test(groups = "fast")
public void testWith$0RecurringItem() {
    final LocalDate invoiceDate = new LocalDate(2016, 11, 15);
    final DefaultInvoice originalInvoice = new DefaultInvoice(account.getId(), invoiceDate, account.getCurrency());
    final Plan plan = new MockPlan("my-plan");
    final MockInternationalPrice price = new MockInternationalPrice(new DefaultPrice(BigDecimal.TEN, account.getCurrency()));
    final PlanPhase planPhase = new MockPlanPhase(price, null, BillingPeriod.MONTHLY, PhaseType.EVERGREEN);
    final BillingEvent event = invoiceUtil.createMockBillingEvent(account, subscription, invoiceDate.toDateTimeAtStartOfDay(), plan, planPhase, null, BigDecimal.ZERO, account.getCurrency(), planPhase.getRecurring().getBillingPeriod(), 1, BillingMode.IN_ADVANCE, "Billing Event Desc", 1L, SubscriptionBaseTransitionType.CREATE);
    final InvoiceItem invoiceItem = new RecurringInvoiceItem(UUID.randomUUID(), invoiceDate.toDateTimeAtStartOfDay(), originalInvoice.getId(), account.getId(), subscription.getBundleId(), subscription.getId(), event.getPlan().getName(), event.getPlanPhase().getName(), invoiceDate, invoiceDate.plusMonths(1), BigDecimal.ZERO, BigDecimal.ZERO, account.getCurrency());
    originalInvoice.addInvoiceItem(invoiceItem);
    final Map<UUID, SubscriptionFutureNotificationDates> perSubscriptionFutureNotificationDates = new HashMap<UUID, SubscriptionFutureNotificationDates>();
    final SubscriptionFutureNotificationDates subscriptionFutureNotificationDates = new SubscriptionFutureNotificationDates(BillingMode.IN_ADVANCE);
    subscriptionFutureNotificationDates.updateNextRecurringDateIfRequired(invoiceDate.plusMonths(1));
    perSubscriptionFutureNotificationDates.put(subscription.getId(), subscriptionFutureNotificationDates);
    final InvoiceWithMetadata invoiceWithMetadata = new InvoiceWithMetadata(originalInvoice, perSubscriptionFutureNotificationDates);
    // We generate an invoice with one item, invoicing for $0
    final Invoice resultingInvoice = invoiceWithMetadata.getInvoice();
    Assert.assertNotNull(resultingInvoice);
    Assert.assertEquals(resultingInvoice.getInvoiceItems().size(), 1);
    Assert.assertEquals(resultingInvoice.getInvoiceItems().get(0).getAmount().compareTo(BigDecimal.ZERO), 0);
    final Map<UUID, InvoiceWithMetadata.SubscriptionFutureNotificationDates> dateMap = invoiceWithMetadata.getPerSubscriptionFutureNotificationDates();
    final InvoiceWithMetadata.SubscriptionFutureNotificationDates futureNotificationDates = dateMap.get(subscription.getId());
    // We verify that we generated the future notification for a month ahead
    Assert.assertNotNull(futureNotificationDates.getNextRecurringDate());
    Assert.assertEquals(futureNotificationDates.getNextRecurringDate().compareTo(invoiceDate.plusMonths(1)), 0);
}
Also used : SubscriptionFutureNotificationDates(org.killbill.billing.invoice.generator.InvoiceWithMetadata.SubscriptionFutureNotificationDates) RecurringInvoiceItem(org.killbill.billing.invoice.model.RecurringInvoiceItem) InvoiceItem(org.killbill.billing.invoice.api.InvoiceItem) Invoice(org.killbill.billing.invoice.api.Invoice) DefaultInvoice(org.killbill.billing.invoice.model.DefaultInvoice) RecurringInvoiceItem(org.killbill.billing.invoice.model.RecurringInvoiceItem) HashMap(java.util.HashMap) MockPlan(org.killbill.billing.catalog.MockPlan) Plan(org.killbill.billing.catalog.api.Plan) LocalDate(org.joda.time.LocalDate) MockInternationalPrice(org.killbill.billing.catalog.MockInternationalPrice) SubscriptionFutureNotificationDates(org.killbill.billing.invoice.generator.InvoiceWithMetadata.SubscriptionFutureNotificationDates) MockPlan(org.killbill.billing.catalog.MockPlan) MockPlanPhase(org.killbill.billing.catalog.MockPlanPhase) PlanPhase(org.killbill.billing.catalog.api.PlanPhase) MockPlanPhase(org.killbill.billing.catalog.MockPlanPhase) BillingEvent(org.killbill.billing.junction.BillingEvent) DefaultPrice(org.killbill.billing.catalog.DefaultPrice) UUID(java.util.UUID) DefaultInvoice(org.killbill.billing.invoice.model.DefaultInvoice) Test(org.testng.annotations.Test)

Example 53 with InvoiceItem

use of org.killbill.billing.invoice.api.InvoiceItem in project killbill by killbill.

the class TestPaymentApi method testCreateSuccessRefundWithPaymentControl.

@Test(groups = "slow")
public void testCreateSuccessRefundWithPaymentControl() throws PaymentApiException, InvoiceApiException, EventBusException {
    final BigDecimal requestedAmount = BigDecimal.TEN;
    final UUID subscriptionId = UUID.randomUUID();
    final UUID bundleId = UUID.randomUUID();
    final LocalDate now = clock.getUTCToday();
    final Invoice invoice = testHelper.createTestInvoice(account, now, Currency.USD);
    final String paymentExternalKey = invoice.getId().toString();
    final String transactionExternalKey = "sacrebleu";
    final String transactionExternalKey2 = "maisenfin";
    final InvoiceItem invoiceItem = new MockRecurringInvoiceItem(invoice.getId(), account.getId(), subscriptionId, bundleId, "test plan", "test phase", null, now, now.plusMonths(1), requestedAmount, new BigDecimal("1.0"), Currency.USD);
    invoice.addInvoiceItem(invoiceItem);
    final Payment payment = paymentApi.createPurchaseWithPaymentControl(account, account.getPaymentMethodId(), null, requestedAmount, Currency.USD, paymentExternalKey, transactionExternalKey, createPropertiesForInvoice(invoice), INVOICE_PAYMENT, callContext);
    final List<PluginProperty> refundProperties = ImmutableList.<PluginProperty>of();
    final Payment payment2 = paymentApi.createRefundWithPaymentControl(account, payment.getId(), requestedAmount, Currency.USD, transactionExternalKey2, refundProperties, INVOICE_PAYMENT, callContext);
    assertEquals(payment2.getTransactions().size(), 2);
    assertEquals(payment2.getExternalKey(), paymentExternalKey);
    assertEquals(payment2.getPaymentMethodId(), account.getPaymentMethodId());
    assertEquals(payment2.getAccountId(), account.getId());
    assertEquals(payment2.getAuthAmount().compareTo(BigDecimal.ZERO), 0);
    assertEquals(payment2.getCapturedAmount().compareTo(BigDecimal.ZERO), 0);
    assertEquals(payment2.getPurchasedAmount().compareTo(requestedAmount), 0);
    assertEquals(payment2.getRefundedAmount().compareTo(requestedAmount), 0);
    assertEquals(payment2.getCurrency(), Currency.USD);
}
Also used : Invoice(org.killbill.billing.invoice.api.Invoice) MockRecurringInvoiceItem(org.killbill.billing.payment.MockRecurringInvoiceItem) InvoiceItem(org.killbill.billing.invoice.api.InvoiceItem) MockRecurringInvoiceItem(org.killbill.billing.payment.MockRecurringInvoiceItem) UUID(java.util.UUID) LocalDate(org.joda.time.LocalDate) BigDecimal(java.math.BigDecimal) Test(org.testng.annotations.Test)

Example 54 with InvoiceItem

use of org.killbill.billing.invoice.api.InvoiceItem in project killbill by killbill.

the class TestPaymentHelper method createTestInvoice.

public Invoice createTestInvoice(final Account account, final LocalDate targetDate, final Currency currency, final InvoiceItem... items) throws EventBusException, InvoiceApiException {
    final Invoice invoice = new MockInvoice(account.getId(), clock.getUTCToday(), targetDate, currency);
    for (final InvoiceItem item : items) {
        if (item instanceof MockRecurringInvoiceItem) {
            final MockRecurringInvoiceItem recurringInvoiceItem = (MockRecurringInvoiceItem) item;
            invoice.addInvoiceItem(new MockRecurringInvoiceItem(invoice.getId(), account.getId(), recurringInvoiceItem.getBundleId(), recurringInvoiceItem.getSubscriptionId(), recurringInvoiceItem.getPlanName(), recurringInvoiceItem.getPhaseName(), null, recurringInvoiceItem.getStartDate(), recurringInvoiceItem.getEndDate(), recurringInvoiceItem.getAmount(), recurringInvoiceItem.getRate(), recurringInvoiceItem.getCurrency()));
        }
    }
    Mockito.when(invoiceApi.getInvoiceById(Mockito.eq(invoice.getId()), Mockito.<InternalTenantContext>any())).thenReturn(invoice);
    Mockito.when(invoiceApi.getInvoiceForPaymentId(Mockito.<UUID>any(), Mockito.<InternalCallContext>any())).thenReturn(invoice);
    final InvoiceCreationInternalEvent event = new MockInvoiceCreationEvent(invoice.getId(), invoice.getAccountId(), invoice.getBalance(), invoice.getCurrency(), invoice.getInvoiceDate(), internalCallContext.getAccountRecordId(), internalCallContext.getTenantRecordId(), null);
    eventBus.post(event);
    return invoice;
}
Also used : Invoice(org.killbill.billing.invoice.api.Invoice) InvoiceItem(org.killbill.billing.invoice.api.InvoiceItem) InvoiceCreationInternalEvent(org.killbill.billing.events.InvoiceCreationInternalEvent)

Example 55 with InvoiceItem

use of org.killbill.billing.invoice.api.InvoiceItem in project killbill by killbill.

the class TestBundleTransfer method testBundleTransferWithBPAnnualOnly.

@Test(groups = "slow")
public void testBundleTransferWithBPAnnualOnly() throws Exception {
    // Set clock to the initial start date - we implicitly assume here that the account timezone is UTC
    final DateTime initialDate = new DateTime(2012, 4, 1, 0, 15, 42, 0, testTimeZone);
    clock.setDeltaFromReality(initialDate.getMillis() - clock.getUTCNow().getMillis());
    final Account account = createAccountWithNonOsgiPaymentMethod(getAccountData(3));
    final String productName = "Shotgun";
    final BillingPeriod term = BillingPeriod.ANNUAL;
    final String planSetName = PriceListSet.DEFAULT_PRICELIST_NAME;
    //
    // CREATE SUBSCRIPTION AND EXPECT BOTH EVENTS: NextEvent.CREATE, NextEvent.BLOCK NextEvent.INVOICE
    //
    final DefaultEntitlement bpEntitlement = createBaseEntitlementAndCheckForCompletion(account.getId(), "externalKey", productName, ProductCategory.BASE, term, NextEvent.CREATE, NextEvent.BLOCK, NextEvent.INVOICE);
    assertNotNull(bpEntitlement);
    assertEquals(invoiceUserApi.getInvoicesByAccount(account.getId(), false, callContext).size(), 1);
    assertEquals(bpEntitlement.getSubscriptionBase().getCurrentPlan().getRecurringBillingPeriod(), BillingPeriod.ANNUAL);
    // Move out of trials for interesting invoices adjustments
    busHandler.pushExpectedEvents(NextEvent.PHASE, NextEvent.INVOICE, NextEvent.PAYMENT, NextEvent.INVOICE_PAYMENT);
    clock.addDays(40);
    assertListenerStatus();
    // BUNDLE TRANSFER
    final Account newAccount = createAccountWithNonOsgiPaymentMethod(getAccountData(17));
    busHandler.pushExpectedEvents(NextEvent.TRANSFER, NextEvent.INVOICE, NextEvent.PAYMENT, NextEvent.INVOICE_PAYMENT);
    transferApi.transferBundle(account.getId(), newAccount.getId(), "externalKey", clock.getUTCNow(), false, false, callContext);
    assertListenerStatus();
    final List<Invoice> invoices = invoiceUserApi.getInvoicesByAccount(newAccount.getId(), false, callContext);
    assertEquals(invoices.size(), 1);
    final List<InvoiceItem> invoiceItems = invoices.get(0).getInvoiceItems();
    assertEquals(invoiceItems.size(), 1);
    final InvoiceItem theItem = invoiceItems.get(0);
    assertTrue(theItem.getStartDate().compareTo(new LocalDate(2012, 5, 11)) == 0);
    assertTrue(theItem.getEndDate().compareTo(new LocalDate(2013, 5, 11)) == 0);
    assertTrue(theItem.getAmount().compareTo(new BigDecimal("2399.9500")) == 0);
    checkNoMoreInvoiceToGenerate(account);
}
Also used : Account(org.killbill.billing.account.api.Account) Invoice(org.killbill.billing.invoice.api.Invoice) InvoiceItem(org.killbill.billing.invoice.api.InvoiceItem) BillingPeriod(org.killbill.billing.catalog.api.BillingPeriod) DefaultEntitlement(org.killbill.billing.entitlement.api.DefaultEntitlement) LocalDate(org.joda.time.LocalDate) DateTime(org.joda.time.DateTime) BigDecimal(java.math.BigDecimal) Test(org.testng.annotations.Test)

Aggregations

InvoiceItem (org.killbill.billing.invoice.api.InvoiceItem)168 LocalDate (org.joda.time.LocalDate)118 Test (org.testng.annotations.Test)109 BigDecimal (java.math.BigDecimal)103 FixedPriceInvoiceItem (org.killbill.billing.invoice.model.FixedPriceInvoiceItem)97 RecurringInvoiceItem (org.killbill.billing.invoice.model.RecurringInvoiceItem)92 ItemAdjInvoiceItem (org.killbill.billing.invoice.model.ItemAdjInvoiceItem)79 RepairAdjInvoiceItem (org.killbill.billing.invoice.model.RepairAdjInvoiceItem)76 UUID (java.util.UUID)68 Invoice (org.killbill.billing.invoice.api.Invoice)57 DefaultInvoice (org.killbill.billing.invoice.model.DefaultInvoice)36 ExternalChargeInvoiceItem (org.killbill.billing.invoice.model.ExternalChargeInvoiceItem)32 BillingEvent (org.killbill.billing.junction.BillingEvent)27 InvoiceApiException (org.killbill.billing.invoice.api.InvoiceApiException)25 ArrayList (java.util.ArrayList)23 DateTime (org.joda.time.DateTime)23 MockPlan (org.killbill.billing.catalog.MockPlan)23 MockPlanPhase (org.killbill.billing.catalog.MockPlanPhase)23 Plan (org.killbill.billing.catalog.api.Plan)22 PlanPhase (org.killbill.billing.catalog.api.PlanPhase)21