Enable tenant-controlled auto-post for sales/purchase/treasury via Posting Engine, block unbalanced voucher lines on FE and BE, and expose international posting controls in settings. Co-authored-by: Cursor <cursoragent@cursor.com>
44 lines
1.8 KiB
TypeScript
44 lines
1.8 KiB
TypeScript
/** Live voucher line balance helpers — Rial integers, zero tolerance. */
|
|
import { toRialInteger } from "@/lib/utils";
|
|
|
|
export type BalanceLine = { debit?: string; credit?: string };
|
|
|
|
export function sumVoucherLines(lines: BalanceLine[] | undefined) {
|
|
let debit = 0;
|
|
let credit = 0;
|
|
(lines ?? []).forEach((line, index) => {
|
|
const d = Number(toRialInteger(line.debit) || "0");
|
|
const c = Number(toRialInteger(line.credit) || "0");
|
|
debit += Number.isFinite(d) ? d : 0;
|
|
credit += Number.isFinite(c) ? c : 0;
|
|
void index;
|
|
});
|
|
const difference = debit - credit;
|
|
return {
|
|
debit,
|
|
credit,
|
|
difference,
|
|
isBalanced: difference === 0 && (lines?.length ?? 0) >= 2,
|
|
};
|
|
}
|
|
|
|
export function unbalancedMessage(debit: number, credit: number): string {
|
|
const diff = Math.abs(debit - credit);
|
|
if (debit > credit) {
|
|
return `سند نامتوازن است: جمع بدهکار ${debit.toLocaleString("fa-IR")} و بستانکار ${credit.toLocaleString("fa-IR")} — بدهکار ${diff.toLocaleString("fa-IR")} ریال بیشتر است.`;
|
|
}
|
|
return `سند نامتوازن است: جمع بدهکار ${debit.toLocaleString("fa-IR")} و بستانکار ${credit.toLocaleString("fa-IR")} — بستانکار ${diff.toLocaleString("fa-IR")} ریال بیشتر است.`;
|
|
}
|
|
|
|
export function lineBothSidesError(debit: string, credit: string): string | null {
|
|
const d = Number(toRialInteger(debit) || "0");
|
|
const c = Number(toRialInteger(credit) || "0");
|
|
if (d > 0 && c > 0) {
|
|
return "در یک ردیف نمیتوان همزمان بدهکار و بستانکار داشت";
|
|
}
|
|
if (d === 0 && c === 0) {
|
|
return "حداقل یکی از بدهکار یا بستانکار باید مقدار داشته باشد";
|
|
}
|
|
return null;
|
|
}
|