use of alfio.model.Audit.EntityType.RESERVATION in project alf.io by alfio-event.
the class TicketReservationManager method prepareModelForReservationEmail.
@Transactional(readOnly = true)
public Map<String, Object> prepareModelForReservationEmail(PurchaseContext purchaseContext, TicketReservation reservation, Optional<String> vat, OrderSummary summary, List<Ticket> ticketsToInclude, Map<String, Object> initialOptions) {
Organization organization = organizationRepository.getById(purchaseContext.getOrganizationId());
String baseUrl = configurationManager.baseUrl(purchaseContext);
var reservationId = reservation.getId();
String reservationUrl = reservationUrl(reservationId);
String reservationShortID = getShortReservationID(purchaseContext, reservation);
var bankingInfo = configurationManager.getFor(Set.of(INVOICE_ADDRESS, BANK_ACCOUNT_NR, BANK_ACCOUNT_OWNER), ConfigurationLevel.purchaseContext(purchaseContext));
Optional<String> invoiceAddress = bankingInfo.get(INVOICE_ADDRESS).getValue();
Optional<String> bankAccountNr = bankingInfo.get(BANK_ACCOUNT_NR).getValue();
Optional<String> bankAccountOwner = bankingInfo.get(BANK_ACCOUNT_OWNER).getValue();
Map<Integer, List<Ticket>> ticketsByCategory = ticketsToInclude.stream().collect(groupingBy(Ticket::getCategoryId));
final List<TicketWithCategory> ticketsWithCategory;
if (!ticketsByCategory.isEmpty()) {
ticketsWithCategory = ticketCategoryRepository.findByIds(ticketsByCategory.keySet()).stream().flatMap(tc -> ticketsByCategory.get(tc.getId()).stream().map(t -> new TicketWithCategory(t, tc))).collect(toList());
} else {
ticketsWithCategory = Collections.emptyList();
}
Map<String, Object> baseModel = new HashMap<>();
baseModel.putAll(initialOptions);
baseModel.putAll(extensionManager.handleReservationEmailCustomText(purchaseContext, reservation, ticketReservationRepository.getAdditionalInfo(reservationId)).map(CustomEmailText::toMap).orElse(Map.of()));
Map<String, Object> model = TemplateResource.prepareModelForConfirmationEmail(organization, purchaseContext, reservation, vat, ticketsWithCategory, summary, baseUrl, reservationUrl, reservationShortID, invoiceAddress, bankAccountNr, bankAccountOwner, baseModel);
boolean euBusiness = StringUtils.isNotBlank(reservation.getVatCountryCode()) && StringUtils.isNotBlank(reservation.getVatNr()) && configurationManager.getForSystem(ConfigurationKeys.EU_COUNTRIES_LIST).getRequiredValue().contains(reservation.getVatCountryCode()) && VatStatus.isVatExempt(reservation.getVatStatus());
model.put("euBusiness", euBusiness);
model.put("publicId", configurationManager.getPublicReservationID(purchaseContext, reservation));
model.put("invoicingAdditionalInfo", loadAdditionalInfo(reservationId).getInvoicingAdditionalInfo());
if (purchaseContext.getType() == PurchaseContextType.event) {
var event = purchaseContext.event().orElseThrow();
model.put("displayLocation", ticketsWithCategory.stream().noneMatch(tc -> EventUtil.isAccessOnline(tc.getCategory(), event)));
} else {
model.put("displayLocation", false);
}
if (ticketReservationRepository.hasSubscriptionApplied(reservationId)) {
model.put("displaySubscriptionUsage", true);
var subscription = subscriptionRepository.findAppliedSubscriptionByReservationId(reservationId).orElseThrow();
if (subscription.getMaxEntries() > -1) {
var subscriptionUsageDetails = UsageDetails.fromSubscription(subscription, ticketRepository.countSubscriptionUsage(subscription.getId(), null));
model.put("subscriptionUsageDetails", subscriptionUsageDetails);
model.put("subscriptionUrl", reservationUrl(subscription.getReservationId()));
}
}
return model;
}
use of alfio.model.Audit.EntityType.RESERVATION in project alf.io by alfio-event.
the class TicketReservationManager method acquireItems.
private List<Ticket> acquireItems(PaymentProxy paymentProxy, String reservationId, String email, CustomerName customerName, String userLanguage, String billingAddress, String customerReference, PurchaseContext purchaseContext, boolean sendTickets) {
switch(purchaseContext.getType()) {
case event:
{
acquireEventTickets(paymentProxy, reservationId, purchaseContext, purchaseContext.event().orElseThrow());
break;
}
case subscription:
{
acquireSubscription(paymentProxy, reservationId, purchaseContext, customerName, email);
break;
}
default:
throw new IllegalStateException("not supported purchase context");
}
specialPriceRepository.updateStatusForReservation(singletonList(reservationId), Status.TAKEN.toString());
ZonedDateTime timestamp = ZonedDateTime.now(clockProvider.getClock());
int updatedReservation = ticketReservationRepository.updateTicketReservation(reservationId, TicketReservationStatus.COMPLETE.toString(), email, customerName.getFullName(), customerName.getFirstName(), customerName.getLastName(), userLanguage, billingAddress, timestamp, paymentProxy.toString(), customerReference);
Validate.isTrue(updatedReservation == 1, "expected exactly one updated reservation, got " + updatedReservation);
waitingQueueManager.fireReservationConfirmed(reservationId);
// we must notify the plugins about ticket assignment and send them by email
TicketReservation reservation = findById(reservationId).orElseThrow(IllegalStateException::new);
List<Ticket> assignedTickets = findTicketsInReservation(reservationId);
assignedTickets.stream().filter(ticket -> StringUtils.isNotBlank(ticket.getFullName()) || StringUtils.isNotBlank(ticket.getFirstName()) || StringUtils.isNotBlank(ticket.getEmail())).forEach(ticket -> {
var event = purchaseContext.event().orElseThrow();
Locale locale = LocaleUtil.forLanguageTag(ticket.getUserLanguage());
var additionalInfo = retrieveAttendeeAdditionalInfoForTicket(ticket);
if ((paymentProxy != PaymentProxy.ADMIN || sendTickets) && configurationManager.getFor(SEND_TICKETS_AUTOMATICALLY, ConfigurationLevel.event(event)).getValueAsBooleanOrDefault()) {
sendTicketByEmail(ticket, locale, event, getTicketEmailGenerator(event, reservation, locale, additionalInfo));
}
extensionManager.handleTicketAssignment(ticket, ticketCategoryRepository.getById(ticket.getCategoryId()), additionalInfo);
});
return assignedTickets;
}
use of alfio.model.Audit.EntityType.RESERVATION in project alf.io by alfio-event.
the class TicketReservationManager method cancelPendingPayment.
public boolean cancelPendingPayment(String reservationId, PurchaseContext purchaseContext) {
var optionalReservation = findById(reservationId);
if (optionalReservation.isEmpty()) {
return false;
}
var optionalTransaction = transactionRepository.loadOptionalByReservationId(reservationId);
if (optionalTransaction.isEmpty() || optionalTransaction.get().getStatus() != Transaction.Status.PENDING) {
log.warn("Trying to cancel a non-pending transaction for reservation {}", reservationId);
return false;
}
Transaction transaction = optionalTransaction.get();
boolean remoteDeleteResult = paymentManager.lookupProviderByTransactionAndCapabilities(transaction, List.of(ServerInitiatedTransaction.class)).map(provider -> ((ServerInitiatedTransaction) provider).discardTransaction(optionalTransaction.get(), purchaseContext)).orElse(true);
if (remoteDeleteResult) {
reTransitionToPending(reservationId);
auditingRepository.insert(reservationId, null, purchaseContext.event().map(Event::getId).orElse(null), RESET_PAYMENT, new Date(), RESERVATION, reservationId);
return true;
}
log.warn("Cannot delete payment with ID {} for reservation {}", transaction.getPaymentId(), reservationId);
return false;
}
use of alfio.model.Audit.EntityType.RESERVATION in project alf.io by alfio-event.
the class BillingDocumentManager method prepareModelForBillingDocument.
private Map<String, Object> prepareModelForBillingDocument(PurchaseContext purchaseContext, TicketReservation reservation, OrderSummary summary, BillingDocument.Type type) {
Organization organization = organizationRepository.getById(purchaseContext.getOrganizationId());
String creditNoteNumber = null;
if (type == CREDIT_NOTE) {
// override credit note number
creditNoteNumber = generateCreditNoteNumber(purchaseContext, reservation);
}
var bankingInfo = configurationManager.getFor(Set.of(VAT_NR, INVOICE_ADDRESS, BANK_ACCOUNT_NR, BANK_ACCOUNT_OWNER), purchaseContext.getConfigurationLevel());
Optional<String> invoiceAddress = bankingInfo.get(INVOICE_ADDRESS).getValue();
Optional<String> bankAccountNr = bankingInfo.get(BANK_ACCOUNT_NR).getValue();
Optional<String> bankAccountOwner = bankingInfo.get(BANK_ACCOUNT_OWNER).getValue();
Optional<String> vat = bankingInfo.get(VAT_NR).getValue();
Map<Integer, List<Ticket>> ticketsByCategory = ticketRepository.findTicketsInReservation(reservation.getId()).stream().collect(groupingBy(Ticket::getCategoryId));
final List<TicketWithCategory> ticketsWithCategory;
if (!ticketsByCategory.isEmpty()) {
ticketsWithCategory = ticketCategoryRepository.findByIds(ticketsByCategory.keySet()).stream().flatMap(tc -> ticketsByCategory.get(tc.getId()).stream().map(t -> new TicketWithCategory(t, tc))).collect(toList());
} else {
ticketsWithCategory = Collections.emptyList();
}
var reservationShortId = configurationManager.getShortReservationID(purchaseContext, reservation);
Map<String, Object> model = TemplateResource.prepareModelForConfirmationEmail(organization, purchaseContext, reservation, vat, ticketsWithCategory, summary, "", "", reservationShortId, invoiceAddress, bankAccountNr, bankAccountOwner, Map.of());
boolean euBusiness = StringUtils.isNotBlank(reservation.getVatCountryCode()) && StringUtils.isNotBlank(reservation.getVatNr()) && configurationManager.getForSystem(ConfigurationKeys.EU_COUNTRIES_LIST).getRequiredValue().contains(reservation.getVatCountryCode()) && PriceContainer.VatStatus.isVatExempt(reservation.getVatStatus());
model.put("isEvent", purchaseContext.ofType(PurchaseContextType.event));
model.put("euBusiness", euBusiness);
model.put("publicId", configurationManager.getPublicReservationID(purchaseContext, reservation));
var additionalInfo = ticketReservationRepository.getAdditionalInfo(reservation.getId());
model.put("invoicingAdditionalInfo", additionalInfo.getInvoicingAdditionalInfo());
model.put("billingDetails", additionalInfo.getBillingDetails());
if (type == CREDIT_NOTE) {
model.put(CREDIT_NOTE_NUMBER, creditNoteNumber);
}
return model;
}
Aggregations