use of org.killbill.billing.entitlement.api.BaseEntitlementWithAddOnsSpecifier in project killbill by killbill.
the class TestSubscription method testCreateMultipleSubscriptionsWithoutBase.
@Test(groups = "slow", expectedExceptions = EntitlementApiException.class, expectedExceptionsMessageRegExp = "Missing Base Subscription.")
public void testCreateMultipleSubscriptionsWithoutBase() throws Exception {
final LocalDate initialDate = new LocalDate(2015, 10, 1);
clock.setDay(initialDate);
final Account account = createAccountWithNonOsgiPaymentMethod(getAccountData(1));
final PlanPhaseSpecifier baseSpec = new PlanPhaseSpecifier("Shotgun", BillingPeriod.MONTHLY, PriceListSet.DEFAULT_PRICELIST_NAME, null);
final PlanPhaseSpecifier addOnSpec1 = new PlanPhaseSpecifier("Telescopic-Scope", BillingPeriod.MONTHLY, PriceListSet.DEFAULT_PRICELIST_NAME, null);
final PlanPhaseSpecifier addOnSpec2 = new PlanPhaseSpecifier("Laser-Scope", BillingPeriod.MONTHLY, PriceListSet.DEFAULT_PRICELIST_NAME, null);
final String externalKeyA = "baseExternalKeyAAA";
final EntitlementSpecifier baseEntitlementSpecifier = new DefaultEntitlementSpecifier(baseSpec, null);
final EntitlementSpecifier addOnEntitlementSpecifier1 = new DefaultEntitlementSpecifier(addOnSpec1, null);
final EntitlementSpecifier addOnEntitlementSpecifier2 = new DefaultEntitlementSpecifier(addOnSpec2, null);
final List<EntitlementSpecifier> specifierListA = new ArrayList<EntitlementSpecifier>();
specifierListA.add(baseEntitlementSpecifier);
specifierListA.add(addOnEntitlementSpecifier1);
specifierListA.add(addOnEntitlementSpecifier2);
final String externalKeyB = "baseExternalKeyBBB";
final List<EntitlementSpecifier> specifierListB = new ArrayList<EntitlementSpecifier>();
specifierListB.add(addOnEntitlementSpecifier1);
specifierListB.add(addOnEntitlementSpecifier2);
final List<BaseEntitlementWithAddOnsSpecifier> entitlementWithAddOnsSpecifierList = new ArrayList<BaseEntitlementWithAddOnsSpecifier>();
final BaseEntitlementWithAddOnsSpecifier cartSpecifierA = new DefaultBaseEntitlementWithAddOnsSpecifier(null, externalKeyA, specifierListA, null, null, false);
final BaseEntitlementWithAddOnsSpecifier cartSpecifierB = new DefaultBaseEntitlementWithAddOnsSpecifier(null, externalKeyB, specifierListB, null, null, false);
entitlementWithAddOnsSpecifierList.add(cartSpecifierA);
entitlementWithAddOnsSpecifierList.add(cartSpecifierB);
entitlementApi.createBaseEntitlementsWithAddOns(account.getId(), entitlementWithAddOnsSpecifierList, ImmutableList.<PluginProperty>of(), callContext);
}
use of org.killbill.billing.entitlement.api.BaseEntitlementWithAddOnsSpecifier in project killbill by killbill.
the class TestSubscription method testCreateMultipleSubscriptionsWithAddOns.
@Test(groups = "slow")
public void testCreateMultipleSubscriptionsWithAddOns() throws Exception {
final LocalDate initialDate = new LocalDate(2015, 10, 1);
clock.setDay(initialDate);
final Account account = createAccountWithNonOsgiPaymentMethod(getAccountData(1));
final PlanPhaseSpecifier baseSpec = new PlanPhaseSpecifier("Shotgun", BillingPeriod.MONTHLY, PriceListSet.DEFAULT_PRICELIST_NAME, null);
final PlanPhaseSpecifier addOnSpec1 = new PlanPhaseSpecifier("Telescopic-Scope", BillingPeriod.MONTHLY, PriceListSet.DEFAULT_PRICELIST_NAME, null);
final PlanPhaseSpecifier addOnSpec2 = new PlanPhaseSpecifier("Laser-Scope", BillingPeriod.MONTHLY, PriceListSet.DEFAULT_PRICELIST_NAME, null);
final String externalKeyA = "baseExternalKeyAAA";
final EntitlementSpecifier baseEntitlementSpecifier = new DefaultEntitlementSpecifier(baseSpec, null);
final EntitlementSpecifier addOnEntitlementSpecifier1 = new DefaultEntitlementSpecifier(addOnSpec1, null);
final EntitlementSpecifier addOnEntitlementSpecifier2 = new DefaultEntitlementSpecifier(addOnSpec2, null);
final List<EntitlementSpecifier> specifierListA = new ArrayList<EntitlementSpecifier>();
specifierListA.add(baseEntitlementSpecifier);
specifierListA.add(addOnEntitlementSpecifier1);
specifierListA.add(addOnEntitlementSpecifier2);
final String externalKeyB = "baseExternalKeyBBB";
final List<EntitlementSpecifier> specifierListB = new ArrayList<EntitlementSpecifier>();
specifierListB.add(baseEntitlementSpecifier);
specifierListB.add(addOnEntitlementSpecifier1);
specifierListB.add(addOnEntitlementSpecifier2);
final List<BaseEntitlementWithAddOnsSpecifier> entitlementWithAddOnsSpecifierList = new ArrayList<BaseEntitlementWithAddOnsSpecifier>();
final BaseEntitlementWithAddOnsSpecifier cartSpecifierA = new DefaultBaseEntitlementWithAddOnsSpecifier(null, externalKeyA, specifierListA, null, null, false);
final BaseEntitlementWithAddOnsSpecifier cartSpecifierB = new DefaultBaseEntitlementWithAddOnsSpecifier(null, externalKeyB, specifierListB, null, null, false);
entitlementWithAddOnsSpecifierList.add(cartSpecifierA);
entitlementWithAddOnsSpecifierList.add(cartSpecifierB);
busHandler.pushExpectedEvents(NextEvent.CREATE, NextEvent.BLOCK, NextEvent.CREATE, NextEvent.BLOCK, NextEvent.CREATE, NextEvent.BLOCK, NextEvent.CREATE, NextEvent.BLOCK, NextEvent.CREATE, NextEvent.BLOCK, NextEvent.CREATE, NextEvent.BLOCK, NextEvent.NULL_INVOICE, NextEvent.NULL_INVOICE, NextEvent.NULL_INVOICE, NextEvent.NULL_INVOICE, NextEvent.NULL_INVOICE, NextEvent.INVOICE, NextEvent.PAYMENT, NextEvent.INVOICE_PAYMENT);
final List<Entitlement> allEntitlements = entitlementApi.createBaseEntitlementsWithAddOns(account.getId(), entitlementWithAddOnsSpecifierList, ImmutableList.<PluginProperty>of(), callContext);
assertListenerStatus();
checkNoMoreInvoiceToGenerate(account);
assertNotNull(allEntitlements);
assertEquals(allEntitlements.size(), 6);
final Entitlement baseEntitlement = allEntitlements.get(0);
final Entitlement addOnEntitlement1 = allEntitlements.get(1);
final Entitlement addOnEntitlement2 = allEntitlements.get(2);
assertEquals(baseEntitlement.getLastActiveProduct().getName(), "Shotgun");
assertEquals(baseEntitlement.getLastActiveProductCategory(), ProductCategory.BASE);
assertEquals(addOnEntitlement1.getLastActiveProduct().getName(), "Telescopic-Scope");
assertEquals(addOnEntitlement1.getLastActiveProductCategory(), ProductCategory.ADD_ON);
assertEquals(addOnEntitlement2.getLastActiveProduct().getName(), "Laser-Scope");
assertEquals(addOnEntitlement2.getLastActiveProductCategory(), ProductCategory.ADD_ON);
final List<Invoice> invoices = invoiceUserApi.getInvoicesByAccount(account.getId(), false, callContext);
// ONLY ONE INVOICE
assertEquals(invoices.size(), 1);
assertEquals(invoices.get(0).getInvoiceItems().size(), 6);
final ImmutableList<ExpectedInvoiceItemCheck> toBeChecked = ImmutableList.<ExpectedInvoiceItemCheck>of(// amount=387.05, rate=399.95 -> Telescopic-Scope
new ExpectedInvoiceItemCheck(initialDate, new LocalDate(2015, 10, 31), InvoiceItemType.RECURRING, new BigDecimal("387.05")), // amount=967.69, rate=999.95 -> Laser-Scope
new ExpectedInvoiceItemCheck(initialDate, new LocalDate(2015, 10, 31), InvoiceItemType.RECURRING, new BigDecimal("967.69")), // Shotgun
new ExpectedInvoiceItemCheck(initialDate, null, InvoiceItemType.FIXED, new BigDecimal("0")), // amount=387.05, rate=399.95 -> Telescopic-Scope
new ExpectedInvoiceItemCheck(initialDate, new LocalDate(2015, 10, 31), InvoiceItemType.RECURRING, new BigDecimal("387.05")), // amount=967.69, rate=999.95 -> Laser-Scope
new ExpectedInvoiceItemCheck(initialDate, new LocalDate(2015, 10, 31), InvoiceItemType.RECURRING, new BigDecimal("967.69")), // Shotgun
new ExpectedInvoiceItemCheck(initialDate, null, InvoiceItemType.FIXED, new BigDecimal("0")));
invoiceChecker.checkInvoice(invoices.get(0).getId(), callContext, toBeChecked);
}
use of org.killbill.billing.entitlement.api.BaseEntitlementWithAddOnsSpecifier in project killbill by killbill.
the class DefaultEntitlementApiBase method pause.
public void pause(final UUID bundleId, @Nullable final LocalDate localEffectiveDate, final Iterable<PluginProperty> properties, final InternalCallContext internalCallContext) throws EntitlementApiException {
final BaseEntitlementWithAddOnsSpecifier baseEntitlementWithAddOnsSpecifier = new DefaultBaseEntitlementWithAddOnsSpecifier(bundleId, null, null, localEffectiveDate, localEffectiveDate, false);
final List<BaseEntitlementWithAddOnsSpecifier> baseEntitlementWithAddOnsSpecifierList = new ArrayList<BaseEntitlementWithAddOnsSpecifier>();
baseEntitlementWithAddOnsSpecifierList.add(baseEntitlementWithAddOnsSpecifier);
final EntitlementContext pluginContext = new DefaultEntitlementContext(OperationType.PAUSE_BUNDLE, null, null, null, null, properties, internalCallContextFactory.createCallContext(internalCallContext));
final WithEntitlementPlugin<Void> pauseWithPlugin = new WithEntitlementPlugin<Void>() {
@Override
public Void doCall(final EntitlementApi entitlementApi, final EntitlementContext updatedPluginContext) throws EntitlementApiException {
try {
final SubscriptionBase baseSubscription = subscriptionInternalApi.getBaseSubscription(bundleId, internalCallContext);
blockUnblockBundle(bundleId, DefaultEntitlementApi.ENT_STATE_BLOCKED, EntitlementService.ENTITLEMENT_SERVICE_NAME, localEffectiveDate, true, true, true, baseSubscription, internalCallContext);
} catch (SubscriptionBaseApiException e) {
throw new EntitlementApiException(e);
}
return null;
}
};
pluginExecution.executeWithPlugin(pauseWithPlugin, pluginContext);
}
use of org.killbill.billing.entitlement.api.BaseEntitlementWithAddOnsSpecifier in project killbill by killbill.
the class DefaultEntitlementInternalApi method cancel.
@Override
public void cancel(final Iterable<Entitlement> entitlements, @Nullable final LocalDate effectiveDate, final BillingActionPolicy billingPolicy, final Iterable<PluginProperty> properties, final InternalCallContext internalCallContext) throws EntitlementApiException {
if (!entitlements.iterator().hasNext()) {
return;
}
int bcd = 0;
DateTimeZone accountTimeZone = null;
try {
bcd = accountApi.getBCD(entitlements.iterator().next().getAccountId(), internalCallContext);
accountTimeZone = accountApi.getImmutableAccountDataByRecordId(internalCallContext.getAccountRecordId(), internalCallContext).getTimeZone();
} catch (final AccountApiException e) {
throw new EntitlementApiException(e);
}
Preconditions.checkState(bcd > 0 && accountTimeZone != null, "Unexpected condition where account info could not be retrieved");
final CallContext callContext = internalCallContextFactory.createCallContext(internalCallContext);
final ImmutableMap.Builder<BlockingState, Optional<UUID>> blockingStates = new ImmutableMap.Builder<BlockingState, Optional<UUID>>();
final Map<DateTime, Collection<NotificationEvent>> notificationEvents = new HashMap<DateTime, Collection<NotificationEvent>>();
final Collection<EntitlementContext> pluginContexts = new LinkedList<EntitlementContext>();
final List<WithEntitlementPlugin> callbacks = new LinkedList<WithEntitlementPlugin>();
final List<SubscriptionBase> subscriptions = new LinkedList<SubscriptionBase>();
for (final Entitlement entitlement : entitlements) {
if (entitlement.getState() == EntitlementState.CANCELLED) {
// If subscription has already been cancelled, we ignore and carry on
continue;
}
final BaseEntitlementWithAddOnsSpecifier baseEntitlementWithAddOnsSpecifier = new DefaultBaseEntitlementWithAddOnsSpecifier(entitlement.getBundleId(), entitlement.getExternalKey(), null, effectiveDate, null, false);
final List<BaseEntitlementWithAddOnsSpecifier> baseEntitlementWithAddOnsSpecifierList = new ArrayList<BaseEntitlementWithAddOnsSpecifier>();
baseEntitlementWithAddOnsSpecifierList.add(baseEntitlementWithAddOnsSpecifier);
final EntitlementContext pluginContext = new DefaultEntitlementContext(OperationType.CANCEL_SUBSCRIPTION, entitlement.getAccountId(), null, baseEntitlementWithAddOnsSpecifierList, billingPolicy, properties, callContext);
pluginContexts.add(pluginContext);
final WithEntitlementPlugin<Entitlement> cancelEntitlementWithPlugin = new WithDateOverrideBillingPolicyEntitlementCanceler((DefaultEntitlement) entitlement, blockingStates, notificationEvents, callContext, internalCallContext);
callbacks.add(cancelEntitlementWithPlugin);
subscriptions.add(((DefaultEntitlement) entitlement).getSubscriptionBase());
}
final Callable<Void> preCallbacksCallback = new BulkSubscriptionBaseCancellation(subscriptions, billingPolicy, accountTimeZone, bcd, internalCallContext);
pluginExecution.executeWithPlugin(preCallbacksCallback, callbacks, pluginContexts);
// Record the new states first, then insert the notifications to avoid race conditions
blockingStateDao.setBlockingStatesAndPostBlockingTransitionEvent(blockingStates.build(), internalCallContext);
for (final DateTime effectiveDateForNotification : notificationEvents.keySet()) {
for (final NotificationEvent notificationEvent : notificationEvents.get(effectiveDateForNotification)) {
recordFutureNotification(effectiveDateForNotification, notificationEvent, internalCallContext);
}
}
}
use of org.killbill.billing.entitlement.api.BaseEntitlementWithAddOnsSpecifier in project killbill by killbill.
the class TestMigrationSubscriptions method testMigrationWithMultipleBundlesAndDifferentDates.
@Test(groups = "slow")
public void testMigrationWithMultipleBundlesAndDifferentDates() throws Exception {
clock.setDay(new LocalDate(2016, 1, 1));
final AccountData accountData = getAccountData(1);
final Account account = createAccountWithNonOsgiPaymentMethod(accountData);
accountChecker.checkAccount(account.getId(), accountData, callContext);
// We set both entitlement and billing date with desired value
final LocalDate entitlementMigrationDateBundle1 = new LocalDate(2015, 12, 20);
final LocalDate billingMigrationDateBundle1 = new LocalDate(2016, 2, 1);
// We set both entitlement and billing date with desired value
final LocalDate entitlementMigrationDateBundle2 = new LocalDate(2015, 12, 20);
final LocalDate billingMigrationDateBundle2 = new LocalDate(2016, 3, 1);
final PlanPhaseSpecifier baseSpec = new PlanPhaseSpecifier("Shotgun", BillingPeriod.MONTHLY, PriceListSet.DEFAULT_PRICELIST_NAME, PhaseType.EVERGREEN);
final PlanPhaseSpecifier addOnSpec1 = new PlanPhaseSpecifier("Telescopic-Scope", BillingPeriod.MONTHLY, PriceListSet.DEFAULT_PRICELIST_NAME, PhaseType.EVERGREEN);
final String externalKey = "baseExternalKey";
EntitlementSpecifier baseEntitlementSpecifier = new DefaultEntitlementSpecifier(baseSpec, null);
EntitlementSpecifier addOnEntitlementSpecifier1 = new DefaultEntitlementSpecifier(addOnSpec1, null);
final List<EntitlementSpecifier> specifierList = new ArrayList<EntitlementSpecifier>();
specifierList.add(baseEntitlementSpecifier);
specifierList.add(addOnEntitlementSpecifier1);
busHandler.pushExpectedEvents(NextEvent.BLOCK, NextEvent.BLOCK, NextEvent.BLOCK, NextEvent.BLOCK);
BaseEntitlementWithAddOnsSpecifier baseEntitlementWithAddOnsSpecifierBundle1 = buildBaseEntitlementWithAddOnsSpecifier(entitlementMigrationDateBundle1, billingMigrationDateBundle1, externalKey, specifierList);
List<BaseEntitlementWithAddOnsSpecifier> baseEntitlementWithAddOnsSpecifierList = new ArrayList<BaseEntitlementWithAddOnsSpecifier>();
BaseEntitlementWithAddOnsSpecifier baseEntitlementWithAddOnsSpecifierBundle2 = buildBaseEntitlementWithAddOnsSpecifier(entitlementMigrationDateBundle2, billingMigrationDateBundle2, externalKey, specifierList);
baseEntitlementWithAddOnsSpecifierList.add(baseEntitlementWithAddOnsSpecifierBundle1);
baseEntitlementWithAddOnsSpecifierList.add(baseEntitlementWithAddOnsSpecifierBundle2);
final List<Entitlement> baseEntitlements = entitlementApi.createBaseEntitlementsWithAddOns(account.getId(), baseEntitlementWithAddOnsSpecifierList, ImmutableList.<PluginProperty>of(), callContext);
assertListenerStatus();
Assert.assertEquals(baseEntitlements.get(0).getState(), EntitlementState.ACTIVE);
Assert.assertEquals(baseEntitlements.get(1).getState(), EntitlementState.ACTIVE);
// Billing starts straight on EVERGREEN for Bundle 1 after 1 month
clock.addMonths(1);
busHandler.pushExpectedEvents(NextEvent.CREATE, NextEvent.CREATE, NextEvent.INVOICE, NextEvent.NULL_INVOICE, NextEvent.PAYMENT, NextEvent.INVOICE_PAYMENT);
assertListenerStatus();
// Billing starts straight on EVERGREEN for Bundle 2 after 2 months
clock.addMonths(1);
busHandler.pushExpectedEvents(NextEvent.CREATE, NextEvent.CREATE, NextEvent.INVOICE, NextEvent.NULL_INVOICE, NextEvent.NULL_INVOICE, NextEvent.PAYMENT, NextEvent.INVOICE_PAYMENT);
assertListenerStatus();
// Next month we should still get one single invoice and payment / invoice payment
clock.addMonths(1);
busHandler.pushExpectedEvents(NextEvent.INVOICE, NextEvent.PAYMENT, NextEvent.INVOICE_PAYMENT);
assertListenerStatus();
}
Aggregations