use of org.killbill.billing.invoice.api.WithAccountLock in project killbill by killbill.
the class DefaultInvoiceUserApi method insertCreditForInvoice.
private InvoiceItem insertCreditForInvoice(final UUID accountId, final UUID invoiceId, final BigDecimal amount, final LocalDate effectiveDate, final Currency currency, final boolean autoCommit, final String description, final CallContext context) throws InvoiceApiException {
if (amount == null || amount.compareTo(BigDecimal.ZERO) <= 0) {
throw new InvoiceApiException(ErrorCode.CREDIT_AMOUNT_INVALID, amount);
}
final WithAccountLock withAccountLock = new WithAccountLock() {
private InvoiceItem creditItem;
@Override
public List<Invoice> prepareInvoices() throws InvoiceApiException {
final InternalTenantContext internalTenantContext = internalCallContextFactory.createInternalTenantContext(accountId, context);
final LocalDate invoiceDate = internalTenantContext.toLocalDate(context.getCreatedDate());
// Create an invoice for that credit if it doesn't exist
final Invoice invoiceForCredit;
if (invoiceId == null) {
final InvoiceStatus status = autoCommit ? InvoiceStatus.COMMITTED : InvoiceStatus.DRAFT;
invoiceForCredit = new DefaultInvoice(accountId, invoiceDate, effectiveDate, currency, status);
} else {
invoiceForCredit = getInvoiceAndCheckCurrency(invoiceId, currency, context);
if (InvoiceStatus.COMMITTED.equals(invoiceForCredit.getStatus())) {
throw new InvoiceApiException(ErrorCode.INVOICE_ALREADY_COMMITTED, invoiceId);
}
}
// Create the new credit
creditItem = new CreditAdjInvoiceItem(UUIDs.randomUUID(), context.getCreatedDate(), invoiceForCredit.getId(), accountId, effectiveDate, description, // Note! The amount is negated here!
amount.negate(), currency);
invoiceForCredit.addInvoiceItem(creditItem);
return ImmutableList.<Invoice>of(invoiceForCredit);
}
};
final Collection<InvoiceItem> creditInvoiceItems = Collections2.<InvoiceItem>filter(invoiceApiHelper.dispatchToInvoicePluginsAndInsertItems(accountId, false, withAccountLock, context), new Predicate<InvoiceItem>() {
@Override
public boolean apply(final InvoiceItem invoiceItem) {
return InvoiceItemType.CREDIT_ADJ.equals(invoiceItem.getInvoiceItemType());
}
});
Preconditions.checkState(creditInvoiceItems.size() == 1, "Should have created a single credit invoice item: " + creditInvoiceItems);
return creditInvoiceItems.iterator().next();
}
use of org.killbill.billing.invoice.api.WithAccountLock in project killbill by killbill.
the class DefaultInvoiceUserApi method insertInvoiceItemAdjustment.
@Override
public InvoiceItem insertInvoiceItemAdjustment(final UUID accountId, final UUID invoiceId, final UUID invoiceItemId, final LocalDate effectiveDate, @Nullable final BigDecimal amount, @Nullable final Currency currency, final String description, final CallContext context) throws InvoiceApiException {
if (amount != null && amount.compareTo(BigDecimal.ZERO) <= 0) {
throw new InvoiceApiException(ErrorCode.INVOICE_ITEM_ADJUSTMENT_AMOUNT_SHOULD_BE_POSITIVE, amount);
}
final WithAccountLock withAccountLock = new WithAccountLock() {
@Override
public Iterable<Invoice> prepareInvoices() throws InvoiceApiException {
final Invoice invoice = getInvoiceAndCheckCurrency(invoiceId, currency, context);
final InvoiceItem adjustmentItem = invoiceApiHelper.createAdjustmentItem(invoice, invoiceItemId, amount, currency, effectiveDate, description, internalCallContextFactory.createInternalCallContext(accountId, context));
invoice.addInvoiceItem(adjustmentItem);
return ImmutableList.<Invoice>of(invoice);
}
};
final Collection<InvoiceItem> adjustmentInvoiceItems = Collections2.<InvoiceItem>filter(invoiceApiHelper.dispatchToInvoicePluginsAndInsertItems(accountId, false, withAccountLock, context), new Predicate<InvoiceItem>() {
@Override
public boolean apply(final InvoiceItem invoiceItem) {
return InvoiceItemType.ITEM_ADJ.equals(invoiceItem.getInvoiceItemType());
}
});
Preconditions.checkState(adjustmentInvoiceItems.size() == 1, "Should have created a single adjustment item: " + adjustmentInvoiceItems);
return adjustmentInvoiceItems.iterator().next();
}
use of org.killbill.billing.invoice.api.WithAccountLock in project killbill by killbill.
the class DefaultInvoiceUserApi method insertExternalCharges.
@Override
public List<InvoiceItem> insertExternalCharges(final UUID accountId, final LocalDate effectiveDate, final Iterable<InvoiceItem> charges, final boolean autoCommit, final CallContext context) throws InvoiceApiException {
for (final InvoiceItem charge : charges) {
if (charge.getAmount() == null || charge.getAmount().compareTo(BigDecimal.ZERO) <= 0) {
throw new InvoiceApiException(ErrorCode.EXTERNAL_CHARGE_AMOUNT_INVALID, charge.getAmount());
}
}
final WithAccountLock withAccountLock = new WithAccountLock() {
@Override
public Iterable<Invoice> prepareInvoices() throws InvoiceApiException {
final InternalTenantContext internalTenantContext = internalCallContextFactory.createInternalTenantContext(accountId, context);
final LocalDate invoiceDate = internalTenantContext.toLocalDate(context.getCreatedDate());
// Group all new external charges on the same invoice (per currency)
final Map<Currency, Invoice> newInvoicesForExternalCharges = new HashMap<Currency, Invoice>();
final Map<UUID, Invoice> existingInvoicesForExternalCharges = new HashMap<UUID, Invoice>();
for (final InvoiceItem charge : charges) {
final Invoice invoiceForExternalCharge;
final UUID invoiceIdForExternalCharge = charge.getInvoiceId();
// Create an invoice for that external charge if it doesn't exist
if (invoiceIdForExternalCharge == null) {
final Currency currency = charge.getCurrency();
if (newInvoicesForExternalCharges.get(currency) == null) {
final InvoiceStatus status = autoCommit ? InvoiceStatus.COMMITTED : InvoiceStatus.DRAFT;
final Invoice newInvoiceForExternalCharge = new DefaultInvoice(accountId, invoiceDate, effectiveDate, currency, status);
newInvoicesForExternalCharges.put(currency, newInvoiceForExternalCharge);
}
invoiceForExternalCharge = newInvoicesForExternalCharges.get(currency);
} else {
if (existingInvoicesForExternalCharges.get(invoiceIdForExternalCharge) == null) {
final Invoice existingInvoiceForExternalCharge = getInvoice(invoiceIdForExternalCharge, context);
existingInvoicesForExternalCharges.put(invoiceIdForExternalCharge, existingInvoiceForExternalCharge);
}
invoiceForExternalCharge = existingInvoicesForExternalCharges.get(invoiceIdForExternalCharge);
}
final InvoiceItem externalCharge = new ExternalChargeInvoiceItem(UUIDs.randomUUID(), context.getCreatedDate(), invoiceForExternalCharge.getId(), accountId, charge.getBundleId(), charge.getDescription(), effectiveDate, charge.getAmount(), charge.getCurrency());
invoiceForExternalCharge.addInvoiceItem(externalCharge);
}
return Iterables.<Invoice>concat(newInvoicesForExternalCharges.values(), existingInvoicesForExternalCharges.values());
}
};
return invoiceApiHelper.dispatchToInvoicePluginsAndInsertItems(accountId, false, withAccountLock, context);
}
use of org.killbill.billing.invoice.api.WithAccountLock in project killbill by killbill.
the class DefaultInvoiceInternalApi method recordRefund.
@Override
public InvoicePayment recordRefund(final UUID paymentId, final BigDecimal amount, final boolean isInvoiceAdjusted, final Map<UUID, BigDecimal> invoiceItemIdsWithAmounts, final String transactionExternalKey, final InternalCallContext context) throws InvoiceApiException {
if (amount.compareTo(BigDecimal.ZERO) <= 0) {
throw new InvoiceApiException(ErrorCode.PAYMENT_REFUND_AMOUNT_NEGATIVE_OR_NULL, paymentId, amount);
}
final InvoicePaymentModelDao refund = dao.createRefund(paymentId, amount, isInvoiceAdjusted, invoiceItemIdsWithAmounts, transactionExternalKey, context);
// See https://github.com/killbill/killbill/issues/265
final CallContext callContext = internalCallContextFactory.createCallContext(context);
final Invoice invoice = getInvoiceById(refund.getInvoiceId(), context);
final UUID accountId = invoice.getAccountId();
final WithAccountLock withAccountLock = new WithAccountLock() {
@Override
public Iterable<Invoice> prepareInvoices() throws InvoiceApiException {
return ImmutableList.<Invoice>of(invoice);
}
};
final List<InvoiceItem> createdInvoiceItems = invoiceApiHelper.dispatchToInvoicePluginsAndInsertItems(accountId, false, withAccountLock, callContext);
return new DefaultInvoicePayment(refund);
}
Aggregations