mirror of
https://github.com/btcpayserver/btcpayserver.git
synced 2025-03-13 19:37:37 +01:00
POS: Fix accounting for manually entered keypad amounts (#6178)
* POS: Fix accounting for manually entered keypad amounts For keypad orders where there are products AND manual amount entries, we didn't account for the latter. Fixes #6168. * Adjust wording: "Manual entry" becomes "Custom Amount"
This commit is contained in:
parent
666445e8f7
commit
0238dffc7a
5 changed files with 28 additions and 15 deletions
|
@ -2690,9 +2690,9 @@ namespace BTCPayServer.Tests
|
|||
var sums = cartData.FindElements(By.CssSelector("tfoot tr"));
|
||||
Assert.Equal(2, items.Count);
|
||||
Assert.Equal(4, sums.Count);
|
||||
Assert.Contains("Manual entry 1", items[0].FindElement(By.CssSelector("th")).Text);
|
||||
Assert.Contains("Custom Amount 1", items[0].FindElement(By.CssSelector("th")).Text);
|
||||
Assert.Contains("1 234,00 €", items[0].FindElement(By.CssSelector("td")).Text);
|
||||
Assert.Contains("Manual entry 2", items[1].FindElement(By.CssSelector("th")).Text);
|
||||
Assert.Contains("Custom Amount 2", items[1].FindElement(By.CssSelector("th")).Text);
|
||||
Assert.Contains("0,56 €", items[1].FindElement(By.CssSelector("td")).Text);
|
||||
Assert.Contains("Subtotal", sums[0].FindElement(By.CssSelector("th")).Text);
|
||||
Assert.Contains("1 234,56 €", sums[0].FindElement(By.CssSelector("td")).Text);
|
||||
|
@ -2713,9 +2713,9 @@ namespace BTCPayServer.Tests
|
|||
sums = paymentDetails.FindElements(By.CssSelector("tr.sums-data"));
|
||||
Assert.Equal(2, items.Count);
|
||||
Assert.Equal(4, sums.Count);
|
||||
Assert.Contains("Manual entry 1", items[0].FindElement(By.CssSelector(".key")).Text);
|
||||
Assert.Contains("Custom Amount 1", items[0].FindElement(By.CssSelector(".key")).Text);
|
||||
Assert.Contains("1 234,00 €", items[0].FindElement(By.CssSelector(".val")).Text);
|
||||
Assert.Contains("Manual entry 2", items[1].FindElement(By.CssSelector(".key")).Text);
|
||||
Assert.Contains("Custom Amount 2", items[1].FindElement(By.CssSelector(".key")).Text);
|
||||
Assert.Contains("0,56 €", items[1].FindElement(By.CssSelector(".val")).Text);
|
||||
Assert.Contains("Subtotal", sums[0].FindElement(By.CssSelector(".key")).Text);
|
||||
Assert.Contains("1 234,56 €", sums[0].FindElement(By.CssSelector(".val")).Text);
|
||||
|
@ -2776,7 +2776,7 @@ namespace BTCPayServer.Tests
|
|||
Assert.Contains("1 x 1,00 € = 1,00 €", items[0].FindElement(By.CssSelector("td")).Text);
|
||||
Assert.Contains("Green Tea", items[1].FindElement(By.CssSelector("th")).Text);
|
||||
Assert.Contains("2 x 1,00 € = 2,00 €", items[1].FindElement(By.CssSelector("td")).Text);
|
||||
Assert.Contains("Manual entry 1", items[2].FindElement(By.CssSelector("th")).Text);
|
||||
Assert.Contains("Custom Amount 1", items[2].FindElement(By.CssSelector("th")).Text);
|
||||
Assert.Contains("1,23 €", items[2].FindElement(By.CssSelector("td")).Text);
|
||||
Assert.Contains("Total", sums[0].FindElement(By.CssSelector("th")).Text);
|
||||
Assert.Contains("4,23 €", sums[0].FindElement(By.CssSelector("td")).Text);
|
||||
|
@ -2795,7 +2795,7 @@ namespace BTCPayServer.Tests
|
|||
Assert.Contains("1 x 1,00 € = 1,00 €", items[0].FindElement(By.CssSelector(".val")).Text);
|
||||
Assert.Contains("Green Tea", items[1].FindElement(By.CssSelector(".key")).Text);
|
||||
Assert.Contains("2 x 1,00 € = 2,00 €", items[1].FindElement(By.CssSelector(".val")).Text);
|
||||
Assert.Contains("Manual entry 1", items[2].FindElement(By.CssSelector(".key")).Text);
|
||||
Assert.Contains("Custom Amount 1", items[2].FindElement(By.CssSelector(".key")).Text);
|
||||
Assert.Contains("1,23 €", items[2].FindElement(By.CssSelector(".val")).Text);
|
||||
Assert.Contains("Total", sums[0].FindElement(By.CssSelector(".key")).Text);
|
||||
Assert.Contains("4,23 €", sums[0].FindElement(By.CssSelector(".val")).Text);
|
||||
|
|
|
@ -377,7 +377,7 @@ namespace BTCPayServer.Plugins.PointOfSale.Controllers
|
|||
{
|
||||
for (var i = 0; i < amountsArray.Count; i++)
|
||||
{
|
||||
cartData.Add($"Manual entry {i+1}", _displayFormatter.Currency(amountsArray[i].ToObject<decimal>(), settings.Currency, DisplayFormatter.CurrencyFormat.Symbol));
|
||||
cartData.Add($"Custom Amount {i+1}", _displayFormatter.Currency(amountsArray[i].ToObject<decimal>(), settings.Currency, DisplayFormatter.CurrencyFormat.Symbol));
|
||||
}
|
||||
}
|
||||
receiptData.Add("Cart", cartData);
|
||||
|
|
|
@ -151,9 +151,13 @@ namespace BTCPayServer.Services.Apps
|
|||
{
|
||||
// flatten single items from POS data
|
||||
var data = e.Metadata.PosData?.ToObject<PosAppData>();
|
||||
if (data is { Cart.Length: > 0 })
|
||||
var hasCart = data is { Cart.Length: > 0 };
|
||||
var hasAmounts = data is { Amounts.Length: > 0 };
|
||||
var date = e.InvoiceTime.Date;
|
||||
var itemCode = e.Metadata.ItemCode ?? typeof(Plugins.PointOfSale.PosViewType).DisplayName(Plugins.PointOfSale.PosViewType.Light.ToString());
|
||||
if (hasCart)
|
||||
{
|
||||
foreach (var lineItem in data.Cart)
|
||||
foreach (var lineItem in data!.Cart)
|
||||
{
|
||||
var item = items.FirstOrDefault(p => p.Id == lineItem.Id);
|
||||
if (item == null)
|
||||
|
@ -165,18 +169,23 @@ namespace BTCPayServer.Services.Apps
|
|||
{
|
||||
ItemCode = item.Id,
|
||||
FiatPrice = lineItem.Price,
|
||||
Date = e.InvoiceTime.Date
|
||||
Date = date
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
if (hasAmounts)
|
||||
{
|
||||
res.AddRange(data!.Amounts.Select(amount => new InvoiceStatsItem { ItemCode = itemCode, FiatPrice = amount, Date = date }));
|
||||
}
|
||||
// no further info, just add the total amount
|
||||
if (!hasCart && !hasAmounts)
|
||||
{
|
||||
res.Add(new InvoiceStatsItem
|
||||
{
|
||||
ItemCode = e.Metadata.ItemCode ?? typeof(Plugins.PointOfSale.PosViewType).DisplayName(Plugins.PointOfSale.PosViewType.Light.ToString()),
|
||||
ItemCode = itemCode,
|
||||
FiatPrice = e.PaidAmount.Net,
|
||||
Date = e.InvoiceTime.Date
|
||||
Date = date
|
||||
});
|
||||
}
|
||||
return res;
|
||||
|
|
|
@ -11,6 +11,9 @@ public class PosAppData
|
|||
[JsonProperty(PropertyName = "cart")]
|
||||
public PosAppCartItem[] Cart { get; set; }
|
||||
|
||||
[JsonProperty(PropertyName = "amounts")]
|
||||
public decimal[] Amounts { get; set; }
|
||||
|
||||
[JsonProperty(PropertyName = "customAmount")]
|
||||
public decimal CustomAmount { get; set; }
|
||||
|
||||
|
|
|
@ -32,9 +32,10 @@ document.addEventListener("DOMContentLoaded",function () {
|
|||
calculation () {
|
||||
if (!this.tipNumeric && !(this.discountNumeric > 0 || this.discountPercentNumeric > 0) && this.amounts.length < 2 && this.cart.length === 0) return null
|
||||
let calc = ''
|
||||
const hasAmounts = this.amounts.length && this.amounts.reduce((sum, amt) => sum + parseFloat(amt || 0), 0) > 0;
|
||||
if (this.cart.length) calc += this.cart.map(item => `${item.count} x ${item.title} (${this.formatCurrency(item.price, true)}) = ${this.formatCurrency((item.price||0) * item.count, true)}`).join(' + ')
|
||||
if (this.cart.length && this.amounts.length) calc += ' + '
|
||||
if (this.amounts.length) calc += this.amounts.map(amt => this.formatCurrency(amt, true)).join(' + ')
|
||||
if (this.cart.length && hasAmounts) calc += ' + '
|
||||
if (hasAmounts) calc += this.amounts.map(amt => this.formatCurrency(amt || 0, true)).join(' + ')
|
||||
if (this.discountNumeric > 0 || this.discountPercentNumeric > 0) calc += ` - ${this.formatCurrency(this.discountNumeric, true)} (${this.discountPercent}%)`
|
||||
if (this.tipNumeric > 0) calc += ` + ${this.formatCurrency(this.tipNumeric, true)}`
|
||||
if (this.tipPercent) calc += ` (${this.tipPercent}%)`
|
||||
|
|
Loading…
Add table
Reference in a new issue