|
11 | 11 | import erpnext |
12 | 12 | from erpnext.stock.serial_batch_bundle import get_batches_from_bundle |
13 | 13 | from erpnext.stock.serial_batch_bundle import get_serial_nos as get_serial_nos_from_bundle |
14 | | -from erpnext.stock.utils import get_incoming_rate, get_valuation_method |
| 14 | +from erpnext.stock.utils import get_incoming_rate, get_valuation_method, getdate |
15 | 15 |
|
16 | 16 |
|
17 | 17 | class StockOverReturnError(frappe.ValidationError): |
@@ -683,6 +683,29 @@ def get_rate_for_return( |
683 | 683 | else: |
684 | 684 | select_field = "abs(stock_value_difference / actual_qty)" |
685 | 685 |
|
| 686 | + item_details = frappe.get_cached_value("Item", item_code, ["has_batch_no", "has_expiry_date"], as_dict=1) |
| 687 | + set_zero_rate_for_expired_batch = frappe.db.get_single_value( |
| 688 | + "Selling Settings", "set_zero_rate_for_expired_batch" |
| 689 | + ) |
| 690 | + |
| 691 | + if ( |
| 692 | + set_zero_rate_for_expired_batch |
| 693 | + and item_details.has_batch_no |
| 694 | + and item_details.has_expiry_date |
| 695 | + and not return_against |
| 696 | + and voucher_type in ["Sales Invoice", "Delivery Note"] |
| 697 | + ): |
| 698 | + # set incoming_rate zero explicitly for standalone credit note with expired batch |
| 699 | + batch_no = frappe.db.get_value(f"{voucher_type} Item", voucher_detail_no, "batch_no") |
| 700 | + if batch_no and is_batch_expired(batch_no, sle.get("posting_date")): |
| 701 | + frappe.db.set_value( |
| 702 | + voucher_type + " Item", |
| 703 | + voucher_detail_no, |
| 704 | + "incoming_rate", |
| 705 | + 0, |
| 706 | + ) |
| 707 | + return 0 |
| 708 | + |
686 | 709 | rate = flt(frappe.db.get_value("Stock Ledger Entry", filters, select_field)) |
687 | 710 | if not (rate and return_against) and voucher_type in ["Sales Invoice", "Delivery Note"]: |
688 | 711 | rate = frappe.db.get_value(f"{voucher_type} Item", voucher_detail_no, "incoming_rate") |
@@ -1152,3 +1175,17 @@ def get_available_serial_nos(serial_nos, warehouse): |
1152 | 1175 | def get_payment_data(invoice): |
1153 | 1176 | payment = frappe.db.get_all("Sales Invoice Payment", {"parent": invoice}, ["mode_of_payment", "amount"]) |
1154 | 1177 | return payment |
| 1178 | + |
| 1179 | + |
| 1180 | +def is_batch_expired(batch_no, posting_date): |
| 1181 | + """ |
| 1182 | + To check whether the batch is expired or not based on the posting date. |
| 1183 | + """ |
| 1184 | + expiry_date = frappe.db.get_value("Batch", batch_no, "expiry_date") |
| 1185 | + if not expiry_date: |
| 1186 | + return |
| 1187 | + |
| 1188 | + if getdate(posting_date) > getdate(expiry_date): |
| 1189 | + return True |
| 1190 | + |
| 1191 | + return False |
0 commit comments