From a43df3278f593f7facdee467819d2d8f18e2c26f Mon Sep 17 00:00:00 2001 From: Mihir Kandoi Date: Wed, 17 Jun 2026 15:18:47 +0530 Subject: [PATCH] fix(postgres): use portable DateDiff/CurDate in Inactive Sales Items report Co-Authored-By: Claude Opus 4.8 (1M context) --- .../inactive_sales_items.py | 10 +++--- .../test_inactive_sales_items.py | 32 +++++++++++++++++++ 2 files changed, 37 insertions(+), 5 deletions(-) create mode 100644 erpnext/accounts/report/inactive_sales_items/test_inactive_sales_items.py diff --git a/erpnext/accounts/report/inactive_sales_items/inactive_sales_items.py b/erpnext/accounts/report/inactive_sales_items/inactive_sales_items.py index 6f90cb13398..59811f9ebd3 100644 --- a/erpnext/accounts/report/inactive_sales_items/inactive_sales_items.py +++ b/erpnext/accounts/report/inactive_sales_items/inactive_sales_items.py @@ -4,7 +4,7 @@ import frappe from frappe import _ -from frappe.query_builder import CustomFunction +from frappe.query_builder.functions import CurDate, DateDiff from frappe.utils import cint @@ -102,11 +102,11 @@ def get_sales_details(filters): child_doctype = "Sales Order Item" if filters["based_on"] == "Sales Order" else "Sales Invoice Item" child = frappe.qb.DocType(child_doctype) - date_diff = CustomFunction("DATEDIFF", ["d1", "d2"]) - current_date = CustomFunction("CURRENT_DATE", []) - date_col = parent.transaction_date if filters["based_on"] == "Sales Order" else parent.posting_date - days_since_last_order = date_diff(current_date(), date_col) + + # DateDiff is cross-database (DATEDIFF on MariaDB, date subtraction on postgres); CurDate() + # renders the bare CURRENT_DATE keyword. Yields the integer number of days. + days_since_last_order = DateDiff(CurDate(), date_col) sales_data = ( frappe.qb.from_(parent) diff --git a/erpnext/accounts/report/inactive_sales_items/test_inactive_sales_items.py b/erpnext/accounts/report/inactive_sales_items/test_inactive_sales_items.py new file mode 100644 index 00000000000..9c40c3ae7ce --- /dev/null +++ b/erpnext/accounts/report/inactive_sales_items/test_inactive_sales_items.py @@ -0,0 +1,32 @@ +# Copyright (c) 2024, Frappe Technologies Pvt. Ltd. and contributors +# For license information, please see license.txt + +import frappe +from frappe.utils import add_days, today + +from erpnext.accounts.report.inactive_sales_items.inactive_sales_items import execute +from erpnext.selling.doctype.sales_order.test_sales_order import make_sales_order +from erpnext.stock.doctype.item.test_item import make_item +from erpnext.tests.utils import ERPNextTestSuite + + +class TestInactiveSalesItems(ERPNextTestSuite): + def test_days_since_last_order_is_computed(self): + # Exercises the date-arithmetic path (DATEDIFF/CURRENT_DATE on mariadb, date subtraction on + # postgres) which must produce the same integer day count on both databases. + item = make_item("_Test Inactive Sales Item").name + old_date = add_days(today(), -120) + so = make_sales_order(item=item, qty=3, rate=150, transaction_date=old_date) + so.items[0].delivery_date = add_days(old_date, 7) + so.save() + so.submit() + + columns, data = execute(frappe._dict({"based_on": "Sales Order", "days": 30})) + self.assertTrue(columns) + row = next((r for r in data if r.get("item") == item and r.get("days_since_last_order")), None) + self.assertIsNotNone(row, "Inactive item should appear in the report") + self.assertGreaterEqual(row["days_since_last_order"], 30) + + def test_report_runs_for_sales_invoice(self): + columns, _data = execute(frappe._dict({"based_on": "Sales Invoice", "days": 30})) + self.assertTrue(columns)