private List <Invoice> CreateInvoices(DateRange dateRange, Frequency frequency) { var invoiceQuery = $"select * from Invoice Where TxnDate >= '{dateRange.Start:yyyy-MM-dd}' and TxnDate <= '{dateRange.End:yyyy-MM-dd}'"; var allInvoices = QuickBooksClient.QueryAll <Invoice>(invoiceQuery); var allActiveCustomers = QuickBooksClient.QueryAll <Customer>("select * from customer") .ToDictionary(x => x.Id); var vendors = new ActiveVendorSearch().GetActiveVendors(allActiveCustomers, VendorService, frequency); var newInvoices = new List <Invoice>(); foreach (var vendor in vendors.Values) { var vendorInvoices = allInvoices.Where(x => x.CustomerRef.Value == vendor.QuickBooksOnlineId.ToString()); if (!vendorInvoices.Any()) { var invoiceDate = frequency == Frequency.Weekly ? dateRange.End : dateRange.Start; newInvoices.Add(CreateInvoice(invoiceDate, allActiveCustomers[vendor.QuickBooksOnlineId], vendor)); } } var paymentApplicator = new PaymentApplicator(QuickBooksClient); foreach (var invoice in newInvoices) { paymentApplicator.ApplyUnappliedPaymentsToInvoice(invoice); } return(newInvoices); }
private void SaveReceiptCore( Receipt receipt, string customerId, string firstName, string lastName, string email, Vendor vendor, string userIp, out ReceiptSaveResult result) { var existing = ReceiptDbClient.Get(new ReceiptSaveResult { Id = receipt.Id }, true).Result; if (existing != null) { throw new Exception($"A receipt with id {receipt.Id} has already been sent for processing."); } var receiptCopyToSave = JsonConvert.DeserializeObject <Receipt>(JsonConvert.SerializeObject(receipt)); receiptCopyToSave.CardPayment = null; result = new ReceiptSaveResult { Id = receipt.Id, Timestamp = DateTime.UtcNow.ToString("O"), Receipt = receiptCopyToSave, Vendor = vendor, CreatedBy = new ReceiptSaveResultUser { FirstName = firstName, LastName = lastName, Email = email, Ip = userIp } }; ReceiptDbClient.Create(result); var memo = receipt.Memo; if (receipt.MakeCardPayment.GetValueOrDefault()) { var last4 = receipt.CardPayment.CardNumber.Substring(receipt.CardPayment.CardNumber.Length - 4); Logger.Log($"{firstName} {lastName} {email} is charging card ending in {last4} ${receipt.ThisPayment:C} on {DateTime.UtcNow:O} for receipt {result.Id}."); var chargeResult = CardPayment.Authorize( receipt.ThisPayment * 100, receipt.CardPayment.CardNumber, receipt.CardPayment.ExpirationMonth, receipt.CardPayment.ExpirationYear, receipt.CardPayment.Cvv, receipt.IsCardPresent); result.CardAuthorizationResult = chargeResult; ReceiptDbClient.Create(result); if (chargeResult["error"] != null) { return; } } if (receipt.Spots != null && receipt.Spots.Any()) { memo += Environment.NewLine + "Spots: " + string.Join(", ", receipt.Spots.Select(x => $"{x.Section?.Name} - {x.Name}")); } if (receipt.RentalAmount > 0) { result.Invoice = QuickBooksClient.Create(CreateInvoice(customerId, receipt.RentalAmount, receipt.RentalDate, memo)); ReceiptDbClient.Create(result); } result.Payments = new List <Payment>(); if (receipt.ThisPayment > 0) { ZonedClock easternClock = SystemClock.Instance.InZone(DateTimeZoneProviders.Tzdb["America/New_York"]); var paymentMemo = $"True Payment Date: {easternClock.GetCurrentDate():yyyy-MM-dd}. " + $"Payment entered by {firstName} {lastName} from IP {userIp}." + Environment.NewLine + Environment.NewLine + memo; var unpaidInvoices = QuickBooksClient.QueryAll <Invoice>($"select * from Invoice where Balance != '0' and CustomerRef = '{customerId}' ORDERBY TxnDate"); decimal payment = receipt.ThisPayment.GetValueOrDefault(); var paymentApplicator = new PaymentApplicator(QuickBooksClient); foreach (var unpaidInvoice in unpaidInvoices) { var paymentAppliedToInvoice = paymentApplicator.CreatePayment( unpaidInvoice, customerId, payment, $"{easternClock.GetCurrentDate():yyyy-MM-dd}", paymentMemo); result.Payments.Add(paymentAppliedToInvoice); payment -= paymentAppliedToInvoice.TotalAmount.GetValueOrDefault(); if (payment <= 0) { break; } } if (payment > 0) { var unappliedPayment = paymentApplicator.CreatePayment( null, customerId, payment, $"{easternClock.GetCurrentDate():yyyy-MM-dd}", paymentMemo ); result.Payments.Add(unappliedPayment); } } ReceiptDbClient.Create(result); if (receipt.Spots != null) { result.SpotReservations = new List <SpotReservation>(); foreach (var spot in receipt.Spots) { var spotReservation = new SpotReservation { SpotId = spot.Id, RentalDate = receipt.RentalDate, QuickBooksOnlineId = int.Parse(customerId), VendorId = vendor.Id }; SpotReservationDbClient.Create(spotReservation); result.SpotReservations.Add(spotReservation); } } if (receipt.MakeCardPayment.GetValueOrDefault()) { result.CardCaptureResult = CardPayment.Capture(result.CardAuthorizationResult["id"].Value <string>()); for (var ct = 0; ct < result.Payments.Count; ct++) { result.Payments[ct].PrivateNote += Environment.NewLine + Environment.NewLine + $"Card payment confirmation {result.CardAuthorizationResult.ToString(Formatting.Indented)}"; result.Payments[ct] = QuickBooksClient.SparseUpdate(result.Payments[ct]); } } ReceiptDbClient.Create(result); }