From 5bdd898c38402d8f0c79bd57b4cb479a48f4a0cf Mon Sep 17 00:00:00 2001 From: MohamedAliSmk Date: Mon, 15 Jun 2026 13:58:27 +0300 Subject: [PATCH 1/3] feat(pos): implement POS expense recording and summary features - Added ExpenseDialog component for recording expenses in the POS. - Updated ShiftClosingDialog to display POS expenses summary and net cash impact. - Enhanced InvoiceCart to include a button for recording POS expenses. - Introduced new computed properties for managing expenses in the POS shift store. - Updated translations to support new expense-related features. --- POS/components.d.ts | 1 + POS/src/components/ShiftClosingDialog.vue | 63 +++ POS/src/components/sale/ExpenseDialog.vue | 334 ++++++++++++++++ POS/src/components/sale/InvoiceCart.vue | 35 ++ POS/src/pages/POSSale.vue | 43 +++ POS/src/stores/posShift.js | 8 + POS/src/stores/posUI.js | 3 + pos_next/api/bootstrap.py | 2 + pos_next/api/expenses.py | 364 ++++++++++++++++++ pos_next/api/test_expenses.py | 220 +++++++++++ pos_next/pos_next/custom/journal_entry.json | 95 +++++ pos_next/pos_next/custom/pos_profile.json | 128 ++++++ .../pos_closing_shift/pos_closing_shift.json | 22 ++ .../pos_closing_shift/pos_closing_shift.py | 31 ++ .../pos_closing_shift_expense.json | 55 +++ .../pos_closing_shift_expense.py | 8 + .../pos_expense_report/pos_expense_report.js | 50 +++ .../pos_expense_report.json | 40 ++ .../pos_expense_report/pos_expense_report.py | 152 ++++++++ .../pos_next/workspace/posnext/posnext.json | 12 +- pos_next/translations/ar.csv | 39 ++ 21 files changed, 1704 insertions(+), 1 deletion(-) create mode 100644 POS/src/components/sale/ExpenseDialog.vue create mode 100644 pos_next/api/expenses.py create mode 100644 pos_next/api/test_expenses.py create mode 100644 pos_next/pos_next/custom/journal_entry.json create mode 100644 pos_next/pos_next/doctype/pos_closing_shift_expense/pos_closing_shift_expense.json create mode 100644 pos_next/pos_next/doctype/pos_closing_shift_expense/pos_closing_shift_expense.py create mode 100644 pos_next/pos_next/report/pos_expense_report/pos_expense_report.js create mode 100644 pos_next/pos_next/report/pos_expense_report/pos_expense_report.json create mode 100644 pos_next/pos_next/report/pos_expense_report/pos_expense_report.py diff --git a/POS/components.d.ts b/POS/components.d.ts index 1f2e8b35f..7ee001c9c 100644 --- a/POS/components.d.ts +++ b/POS/components.d.ts @@ -20,6 +20,7 @@ declare module 'vue' { CustomerDialog: typeof import('./src/components/sale/CustomerDialog.vue')['default'] DraftInvoicesDialog: typeof import('./src/components/sale/DraftInvoicesDialog.vue')['default'] EditItemDialog: typeof import('./src/components/sale/EditItemDialog.vue')['default'] + ExpenseDialog: typeof import('./src/components/sale/ExpenseDialog.vue')['default'] InstallAppBadge: typeof import('./src/components/common/InstallAppBadge.vue')['default'] InvoiceCart: typeof import('./src/components/sale/InvoiceCart.vue')['default'] InvoiceDetailDialog: typeof import('./src/components/invoices/InvoiceDetailDialog.vue')['default'] diff --git a/POS/src/components/ShiftClosingDialog.vue b/POS/src/components/ShiftClosingDialog.vue index 8f110ed2b..f564d32bc 100644 --- a/POS/src/components/ShiftClosingDialog.vue +++ b/POS/src/components/ShiftClosingDialog.vue @@ -44,6 +44,13 @@
{{ __('{0} returns', [closingData.returns_count]) }}
+ +
+
{{ __('POS Expenses') }}
+
-{{ formatCurrency(closingData.expenses_total) }}
+
{{ __('{0} expenses', [closingData.expenses_count]) }}
+
+
{{ __('Net Sales') }}
@@ -51,6 +58,13 @@
{{ __('After returns') }}
+ +
+
{{ __('Net Cash Impact') }}
+
{{ formatCurrency(netCashImpact) }}
+
{{ __('Sales - Returns - Expenses') }}
+
+
{{ __('Tax Collected') }}
@@ -193,6 +207,36 @@
+ +
+
+

{{ __('POS Expenses') }}

+

+ {{ __('{0} expenses totaling {1}', [closingData.expenses_count, formatCurrency(closingData.expenses_total)]) }} +

+
+
+ + + + + + + + + + + + + + + + + +
{{ __('Expense Account') }}{{ __('Amount') }}{{ __('Employee') }}{{ __('Remarks') }}
{{ expense.expense_account }}{{ formatCurrency(expense.amount) }}{{ expense.employee || __('N/A') }}{{ expense.remarks || __('N/A') }}
+
+
+
+

+ {{ __('Expenses: -{0}', [formatCurrency(payment.expense_amount)]) }} +

@@ -777,6 +827,19 @@ const hasReturns = computed(() => { return (closingData.value.returns_count || 0) > 0 }) +const hasExpenses = computed(() => { + if (!closingData.value) return false + return (closingData.value.expenses_count || 0) > 0 +}) + +const netCashImpact = computed(() => { + if (!closingData.value) return 0 + const sales = Number.parseFloat(closingData.value.sales_total || closingData.value.grand_total || 0) + const returns = Number.parseFloat(closingData.value.returns_total || 0) + const expenses = Number.parseFloat(closingData.value.expenses_total || 0) + return sales - returns - expenses +}) + // Count of sales invoices (non-returns) const salesInvoiceCount = computed(() => { if (!closingData.value) return 0 diff --git a/POS/src/components/sale/ExpenseDialog.vue b/POS/src/components/sale/ExpenseDialog.vue new file mode 100644 index 000000000..1e81589a5 --- /dev/null +++ b/POS/src/components/sale/ExpenseDialog.vue @@ -0,0 +1,334 @@ + + + + + diff --git a/POS/src/components/sale/InvoiceCart.vue b/POS/src/components/sale/InvoiceCart.vue index d91835154..24143d80b 100644 --- a/POS/src/components/sale/InvoiceCart.vue +++ b/POS/src/components/sale/InvoiceCart.vue @@ -680,6 +680,36 @@ }} + + + +