Commit Graph

58735 Commits

Author SHA1 Message Date
Mihir Kandoi
e834910bfd fix(stock): drop call to confirm_if_drafts_exist missing on v16 (#57833)
(cherry picked from commit 626e35135f)
2026-08-06 08:09:41 +00:00
Frappe PR Bot
68ea583a1f chore(release): Bumped to Version 16.31.0
# [16.31.0](https://github.com/frappe/erpnext/compare/v16.30.0...v16.31.0) (2026-08-04)

### Bug Fixes

* **accounts receivable:** made territory field multi select (backport [#57322](https://github.com/frappe/erpnext/issues/57322)) ([#57346](https://github.com/frappe/erpnext/issues/57346)) ([9b452f1](9b452f12b7))
* **accounts:** fetch deferred invoice docs on non-empty `sales_docs` or `purchase_docs` in repost accounting ledger ([#57753](https://github.com/frappe/erpnext/issues/57753)) ([6153202](6153202231))
* **accounts:** skip party dashboard without invoice permission ([ee6955d](ee6955d56c))
* **accounts:** update AU standard chart of accounts (backport [#57145](https://github.com/frappe/erpnext/issues/57145)) ([#57608](https://github.com/frappe/erpnext/issues/57608)) ([1ea1ce1](1ea1ce15d0))
* allow custom remark on reversal journal entry ([b4dfca9](b4dfca9ef1))
* apply the supplier selection to this branch's own mapper module ([e5f8d0c](e5f8d0c84b))
* **assets:** add permission checks on whitelisted methods on `asset_capitalization` ([99f249b](99f249b1a0))
* **banking:** fetch company list from DB instead of boot (backport [#57731](https://github.com/frappe/erpnext/issues/57731)) ([#57739](https://github.com/frappe/erpnext/issues/57739)) ([ca60653](ca6065398c))
* do not fetch a random inventory account when multiple inventory accounts exist (backport [#57626](https://github.com/frappe/erpnext/issues/57626)) ([#57632](https://github.com/frappe/erpnext/issues/57632)) ([34cbd3c](34cbd3c8d5))
* drop row prefix in reserve stock message when row is unknown ([684ae4d](684ae4d762))
* escape data in multiple templates (backport [#57742](https://github.com/frappe/erpnext/issues/57742)) ([#57770](https://github.com/frappe/erpnext/issues/57770)) ([824ae57](824ae57e44))
* escape item code and UOM in the supplier dialog errors ([06a753f](06a753faf3))
* exclude transferred and consumed qty from dashboard reserved stock ([46317b0](46317b063a))
* filter Accounts Receivable by invoice sales partner (backport [#57628](https://github.com/frappe/erpnext/issues/57628)) ([#57648](https://github.com/frappe/erpnext/issues/57648)) ([0e46937](0e46937f60))
* guard against None row in get_stock_balance_for (backport [#57567](https://github.com/frappe/erpnext/issues/57567)) ([283ee6e](283ee6e07b))
* guard scio row lookup in stock entry items_add ([fb6c87d](fb6c87dd0c))
* **italy:** skip e-invoicing for opening invoices ([5e584d1](5e584d1cfb))
* **item_variant:** added permission checks on `enqueue_multiple_variant_creation` ([c7cf9d8](c7cf9d868b))
* keep the bulk supplier field to half the supplier selection dialog ([2c9db13](2c9db13041))
* label the items table in the supplier selection dialog ([187840b](187840b559))
* let Purchase Receipt cancel defer to Frappe's linked-document check (backport [#57592](https://github.com/frappe/erpnext/issues/57592)) ([#57597](https://github.com/frappe/erpnext/issues/57597)) ([16be0f0](16be0f0944))
* link the item and spell out the unit in the supplier dialog errors ([810b9ae](810b9ae28f))
* list the Purchase Orders created per supplier instead of opening one ([d2fe4b6](d2fe4b623c))
* **manufacturing:** reach the whole configurator from tree toolbar actions ([281e92f](281e92fb6e)), closes [#57773](https://github.com/frappe/erpnext/issues/57773)
* open the Purchase Order when the supplier selection creates only one ([e71cef0](e71cef02b3))
* **opportunity:** add validation for positive item quantities ([a9f969e](a9f969e942))
* **payment reconciliation:** correct supplier gain/loss posting ([dc907ad](dc907add40))
* **payment_request:** added permission checks on `resend_payment_email` ([fcbbb25](fcbbb251cf))
* **plant_floor:** add missing perm check on `get_stock_summary` (backport [#57667](https://github.com/frappe/erpnext/issues/57667)) ([#57670](https://github.com/frappe/erpnext/issues/57670)) ([7bc0475](7bc04752fc))
* **pos:** don't double-escape Item Group names in get_item_groups ([#57673](https://github.com/frappe/erpnext/issues/57673)) ([a5544d0](a5544d0bfb))
* preserve UOM conversion factor precision in transactions ([e5999b2](e5999b22c7))
* prevent duplicate shipping charges without cost center ([666b616](666b6167a1))
* **projects:** add project filter ([3ba8313](3ba83134af))
* **projects:** include on hold status in project filters and reports ([d104d8e](d104d8e723))
* **purchase:** reject purchase returns where every item has zero quantity ([032b922](032b922f0c))
* **quotation:** carry forward communications from opportunity at after_insert (backport [#57639](https://github.com/frappe/erpnext/issues/57639)) ([#57643](https://github.com/frappe/erpnext/issues/57643)) ([624a236](624a236f88))
* reject the same Material Request item twice in one supplier selection ([ea770f6](ea770f6a8e))
* resolve version 16 backport conflicts ([e98471d](e98471d9c9))
* resolve version-16 backport conflicts ([697f68d](697f68d1d2))
* respect child warehouse account override in Stock and Account Value Comparison ([#57552](https://github.com/frappe/erpnext/issues/57552)) ([ca657d2](ca657d2629))
* respect quantity precision in material transfer validation ([eb969a5](eb969a5866))
* **sales:** reject sales returns where every item has zero quantity ([aa71cd6](aa71cd695b))
* seed standard Item Groups under the existing tree root ([4ffa950](4ffa950aa3)), closes [#57581](https://github.com/frappe/erpnext/issues/57581)
* **selling:** don't require cancel and delete perms to remove items via Update Items (backport [#57419](https://github.com/frappe/erpnext/issues/57419)) ([#57601](https://github.com/frappe/erpnext/issues/57601)) ([04e1ca8](04e1ca8226))
* set Required By on Purchase Orders created per supplier ([f99d66d](f99d66d578))
* set reservation voucher_qty to voucher demand not reserved qty ([ecccedf](ecccedf0ed))
* source manually created asset value from valuation rate ([b556b01](b556b012f0))
* **stock:** accept every number a reading can be written as ([fccf122](fccf1220f6))
* **stock:** correct secondary item valuation across stock entry purposes ([4ed0374](4ed03748fe)), closes [#57732](https://github.com/frappe/erpnext/issues/57732) [#57735](https://github.com/frappe/erpnext/issues/57735) [#57736](https://github.com/frappe/erpnext/issues/57736) [#57737](https://github.com/frappe/erpnext/issues/57737) [#57738](https://github.com/frappe/erpnext/issues/57738)
* **stock:** keep manufactured item rate at zero when inputs are free  (backport [#57334](https://github.com/frappe/erpnext/issues/57334)) ([#57513](https://github.com/frappe/erpnext/issues/57513)) ([49924dd](49924ddd1d))
* **stock:** read quality inspection readings in the user's number format ([3b7fb68](3b7fb6851a))
* **stock:** resolve backport conflict in quality inspection imports ([656db1c](656db1c2fe))
* **stock:** scope over deliver/receive role check to delivery and receipt overflow ([4713ddd](4713ddd55b))
* **stock:** validate only the variant attributes that changed ([0013908](00139081f6))
* **stock:** validate over delivery/receipt allowance in stock settings ([3f3292c](3f3292ca4a))
* **stock:** value batched packed-item returns from the original bundle  (backport [#57327](https://github.com/frappe/erpnext/issues/57327)) ([#57511](https://github.com/frappe/erpnext/issues/57511)) ([c0ac8aa](c0ac8aaf86))
* sync translations from crowdin ([#57741](https://github.com/frappe/erpnext/issues/57741)) ([285aec3](285aec3164))
* update stock variance account logic which defaults to default expense ([#57656](https://github.com/frappe/erpnext/issues/57656)) ([d09c04a](d09c04a623))
* use payment entry posting date for received amount exchange rate (backport [#57660](https://github.com/frappe/erpnext/issues/57660)) ([#57663](https://github.com/frappe/erpnext/issues/57663)) ([5595d1e](5595d1ed2f))
* validate account frozen date ([17aeb0b](17aeb0b55b))
* warn about existing draft orders before the supplier selection creates more ([93331a1](93331a1cf0))

### Features

* adjust the ordered quantity in the supplier selection dialog ([2c8c375](2c8c375ca6))
* alert when Required By falls back to today ([1adeb66](1adeb66bdc))
* auto-fill subscription accounting dimensions from plan with item fallback (backport [#57615](https://github.com/frappe/erpnext/issues/57615)) ([#57622](https://github.com/frappe/erpnext/issues/57622)) ([ebba4e9](ebba4e9958))
* order only the items ticked in the supplier selection dialog ([d6ee543](d6ee5436b8))
* select a supplier per item when creating Purchase Orders from Material Request ([95f7810](95f7810948))
* set one supplier across every item in the supplier selection dialog ([9b647be](9b647bed5c))
* show the UOM alongside the quantity in the supplier selection dialog ([5aaefec](5aaefec747))
* status based bar colors in Work Order gantt view (backport [#57634](https://github.com/frappe/erpnext/issues/57634)) ([#57636](https://github.com/frappe/erpnext/issues/57636)) ([2d03d80](2d03d80269))
v16.31.0
2026-08-04 20:30:34 +00:00
Diptanil Saha
2769a8c69e Merge pull request #57781 from frappe/version-16-hotfix
chore: release v16
2026-08-05 01:58:06 +05:30
Diptanil Saha
970a3f403d Merge pull request #57798 from diptanilsaha/backport/16/57734
fix(payment reconciliation): correct supplier gain/loss posting (backport #57734)
2026-08-05 00:13:14 +05:30
Sudharsanan11
61154e22ed test(payment reconciliation): cover supplier exchange gain posting 2026-08-04 23:58:33 +05:30
diptanilsaha
dc907add40 fix(payment reconciliation): correct supplier gain/loss posting 2026-08-04 23:58:19 +05:30
Shllokkk
b5700831d8 Merge pull request #57791 from frappe/mergify/bp/version-16-hotfix/pr-57790
test: child warehouse account override in stock vs account value comparison (backport #57790)
2026-08-04 20:15:59 +05:30
Shllokkk
a703e7a462 test: child warehouse account override excluded in stock vs account value comparison
(cherry picked from commit ef7a3cb4c8)

# Conflicts:
#	erpnext/stock/report/stock_and_account_value_comparison/test_stock_and_account_value_comparison.py
2026-08-04 18:54:44 +05:30
Mihir Kandoi
abc76eb49d Merge pull request #57789 from frappe/mergify/bp/version-16-hotfix/pr-57757
fix(opportunity): add validation for positive item quantities (backport #57757)
2026-08-04 17:13:29 +05:30
R-Jayaraman
37e96f931d chore: use flt() in qty check
(cherry picked from commit 69de8f2d62)
2026-08-04 11:24:02 +00:00
R-Jayaraman
a9f969e942 fix(opportunity): add validation for positive item quantities
(cherry picked from commit c47cc37441)
2026-08-04 11:24:01 +00:00
Mihir Kandoi
cd65a6d9ff Merge pull request #57785 from frappe/mergify/bp/version-16-hotfix/pr-57772
fix(accounts): skip party dashboard without invoice permission (backport #57772)
2026-08-04 16:48:17 +05:30
Sudharsanan11
ee6955d56c fix(accounts): skip party dashboard without invoice permission
(cherry picked from commit ed78dd37be)
2026-08-04 11:04:28 +00:00
Mihir Kandoi
02f407b82a Merge pull request #57779 from frappe/mergify/bp/version-16-hotfix/pr-57777
fix(manufacturing): reach the whole configurator from tree toolbar actions (backport #57777)
2026-08-04 16:11:23 +05:30
Mihir Kandoi
281e92fb6e fix(manufacturing): reach the whole configurator from tree toolbar actions
The toolbar handlers were copied onto view.events as unbound functions, so
`this` inside them was that object literal rather than the BOMConfigurator.
They worked only because the literal also carried `frm`, and broke as soon as
a handler called a method the literal did not list: get_item_code, added when
the tree started keying nodes on the row name, threw
"this.get_item_code is not a function" and killed Add Raw Material, Add Sub
Assembly and Convert to Sub Assembly.

Assign the instance instead of a hand-maintained whitelist. Every method is
reachable, `this.frm` keeps working, and no future method can be forgotten.

Fixes #57773

(cherry picked from commit 097ce0f348)
2026-08-04 10:09:12 +00:00
MochaMind
285aec3164 fix: sync translations from crowdin (#57741) 2026-08-04 10:00:24 +00:00
mergify[bot]
824ae57e44 fix: escape data in multiple templates (backport #57742) (#57770)
Co-authored-by: diptanilsaha <diptanil@frappe.io>
2026-08-04 06:52:25 +00:00
ruthra kumar
4193a441e6 Merge pull request #57767 from frappe/mergify/bp/version-16-hotfix/pr-57719
Fix/reversal journal entry custom remark (backport #57719)
2026-08-04 11:02:08 +05:30
Krishna Shirsath
b4dfca9ef1 fix: allow custom remark on reversal journal entry
(cherry picked from commit 5e0e9ba668)
2026-08-04 05:30:03 +00:00
Diptanil Saha
6153202231 fix(accounts): fetch deferred invoice docs on non-empty sales_docs or purchase_docs in repost accounting ledger (#57753) 2026-08-03 17:25:50 +05:30
Mihir Kandoi
4babce436f Merge pull request #57755 from mihir-kandoi/backport/secondary-item-valuation-fixes
fix(stock): correct secondary item valuation across stock entry purposes
2026-08-03 17:05:54 +05:30
Mihir Kandoi
aaa99f775d test(stock): cover secondary item valuation across stock entry purposes
Ports the five regression tests to this branch's `type` field name.
2026-08-03 16:53:20 +05:30
Mihir Kandoi
4ed03748fe fix(stock): correct secondary item valuation across stock entry purposes
Backport of five fixes merged to develop, adapted to this branch, where
the field is still named `type` and the stock entry rate logic has not
been split out of set_basic_rate.

- A secondary row with no BOM link is costed out of the finished good,
  as legacy scrap was. Finished goods are rated last so a single
  validate pass sees the secondary rows' amounts. (#57732)
- Repack no longer flags secondary rows as finished goods, so each side
  takes the share the BOM declares instead of the scrap absorbing the
  finished good's percentage. (#57735)
- A BOM allocation of 0% means the row carries no cost, rather than
  falling through to the item's own valuation rate. (#57736)
- Secondary Item Type no longer waives a quality inspection on purposes
  that do not produce secondary items. (#57737)
- The BOM allocation applies to the consumption entry's cost when the
  raw material cost comes from one. (#57738)

Replaces the individual backports, which could not be cherry-picked
cleanly: every hunk needed rewriting against the pre-rename field and
the un-refactored rate logic.
2026-08-03 16:53:20 +05:30
Mihir Kandoi
667b012065 Merge pull request #57750 from frappe/mergify/bp/version-16-hotfix/pr-57747
fix: disabled item attribute blocks unrelated edits to existing variants (backport #57747)
2026-08-03 16:33:22 +05:30
Mihir Kandoi
81e24442e3 test(stock): cover editing a variant whose attribute is disabled
Assert that a variant saves after its attribute is disabled when the edit
leaves the attribute rows alone, and that changing an attribute value still
throws.

(cherry picked from commit 8d5326196e)
2026-08-03 10:47:42 +00:00
Mihir Kandoi
00139081f6 fix(stock): validate only the variant attributes that changed
Disabling an Item Attribute writes `disabled = 1` into every Item Variant
Attribute row, including the rows on the template. `validate_variant` runs
on every save and walks the whole attribute table, so any later save of an
existing variant re-checked its untouched rows against the now-disabled
template row and threw. `update_variants` hit the same wall, which made a
single template save fail once an attribute was disabled.

The flag exists to keep an attribute out of new variants, not to freeze the
variants that already use it. item.js only reads it to drop the attribute
from the variant creation dialog.

Skip rows that are unchanged since the last save. New and edited rows are
still checked, so a disabled attribute cannot be added to an existing
variant, and the same guard covers the sibling checks for attributes and
values that the template no longer offers.

(cherry picked from commit 25cd793617)
2026-08-03 10:47:42 +00:00
Henil Maru
a5544d0bfb fix(pos): don't double-escape Item Group names in get_item_groups (#57673)
frappe.db.escape() wraps the value in quotes (e.g. "'Products'").
Callers pass the result into query-builder isin()/frappe.get_all
filters, which parameterize values themselves — so the pre-quoted
string never matches a real Item Group name, and POS shows no items
whenever a POS Profile restricts Item Groups.

Return raw names instead, matching develop.
2026-08-03 16:03:38 +05:30
mergify[bot]
ca6065398c fix(banking): fetch company list from DB instead of boot (backport #57731) (#57739)
fix(banking): fetch company list from DB instead of boot (#57731)

* fix(banking): fetch company list from DB instead of boot

* fix: show error banner for company list fail fetch

(cherry picked from commit abc3da6b97)

Co-authored-by: Nikhil Kothari <nik.kothari22@live.com>
2026-08-03 14:33:46 +05:30
Mihir Kandoi
eeab2a833f Merge pull request #57730 from frappe/mergify/bp/version-16-hotfix/pr-57647
fix(sales): reject sales returns where every item has zero quantity (backport #57647)
2026-08-03 13:44:09 +05:30
Mihir Kandoi
af4aea171b test(sales): import make_sales_return from delivery_note on version-16-hotfix 2026-08-03 13:29:40 +05:30
Mihir Kandoi
a2dfc9e50a Merge pull request #57728 from frappe/mergify/bp/version-16-hotfix/pr-57725
fix(stock): scope over deliver/receive role check to delivery and receipt overflow (backport #57725)
2026-08-03 13:13:22 +05:30
R-Jayaraman
f2a53247c5 test(sales): add coverage for zero-qty return rejection
Greptile flagged that the sales-side zero-qty-return fix had no dedicated
test proving the behavior - the existing suite happened to pass, but
nothing specifically asserted that an all-zero return is rejected while
a normal negative-qty return still succeeds.

Adds two tests covering the doctypes that rely entirely on this check
(no other guard covers them for a non-stock-effect return):
- Delivery Note return with qty 0 -> rejected
- Sales Invoice return with qty 0 (no update_stock) -> rejected

POS Invoice is not covered separately here since it always runs with
update_stock=1, which is already guarded by the pre-existing
validate_zero_qty_for_return_invoices_with_stock check regardless of
this fix.

(cherry picked from commit 732c884633)
2026-08-03 07:35:29 +00:00
R-Jayaraman
aa71cd695b fix(sales): reject sales returns where every item has zero quantity
validate_returned_items() set items_returned=True whenever a row matched
a valid item from the original document, even if its qty was 0. This let
a Sales Invoice, Delivery Note, or POS Invoice return be submitted with
every line at qty=0 - a no-op document with no stock or financial effect
that still consumed a document number and linked back to the original
transaction.

Scoped to the Sales side only: items_returned now flips to True for
Sales Invoice/Delivery Note/POS Invoice only when qty (or received_qty)
is actually negative, so an all-zero sales return correctly hits the
existing "At least one item should be entered with negative quantity"
check. Purchase Invoice, Purchase Receipt, and Subcontracting Receipt
are unchanged.

(cherry picked from commit a3e9d13da3)
2026-08-03 07:35:29 +00:00
Mihir Kandoi
697f68d1d2 fix: resolve version-16 backport conflicts
Keep validate_warehouses() alongside the new
validate_over_delivery_receipt_allowance() call.

Drop test_blanket_order_over_order_aggregated_across_rows: it is develop-only
context the cherry-pick swallowed into the conflict, not part of #57725.

Revert the valuation_method literal to the three options this branch offers -
Standard Cost rode along from a regenerated develop type block.
2026-08-03 12:55:08 +05:30
Mihir Kandoi
246ffee17c Merge pull request #57722 from frappe/mergify/bp/version-16-hotfix/pr-57645
fix(purchase): reject purchase returns where every item has zero quan… (backport #57645)
2026-08-03 12:54:59 +05:30
Mihir Kandoi
e7757f6d0b Merge pull request #57726 from frappe/mergify/bp/version-16-hotfix/pr-57097
fix(stock): read quality inspection readings in the user's number format  (backport #57097)
2026-08-03 12:42:52 +05:30
Mihir Kandoi
10229700c0 test(purchase): drop unrelated sales-return test from the backport
test_sales_return_validates_against_original came in with the new file,
not with the change being backported. It covers a raw-SQL to query-builder
conversion that only exists on develop, and it imports
erpnext.stock.doctype.delivery_note.mapper, a module version-16-hotfix
does not have.
2026-08-03 12:42:10 +05:30
Afsal Syed
6cbf73a326 test(stock): prevent settings leakage in purchase order tests
(cherry picked from commit 99630f40eb)
2026-08-03 07:10:14 +00:00
Afsal Syed
3a0f988a9e test(stock): add test cases verifying stock over delivery role does not bypass order allowance
(cherry picked from commit 0b271e24b6)

# Conflicts:
#	erpnext/manufacturing/doctype/blanket_order/test_blanket_order.py
2026-08-03 07:10:14 +00:00
Afsal Syed
4713ddd55b fix(stock): scope over deliver/receive role check to delivery and receipt overflow
(cherry picked from commit 248873034d)
2026-08-03 07:10:14 +00:00
Afsal Syed
3f3292ca4a fix(stock): validate over delivery/receipt allowance in stock settings
(cherry picked from commit 446ec6030a)

# Conflicts:
#	erpnext/stock/doctype/stock_settings/stock_settings.json
#	erpnext/stock/doctype/stock_settings/stock_settings.py
2026-08-03 07:10:14 +00:00
Mihir Kandoi
656db1c2fe fix(stock): resolve backport conflict in quality inspection imports
The backport left both import hunks unresolved, so the file did not compile.
version-16-hotfix keeps item_query unannotated and still imports cstr, so only
get_number_format_info goes, replaced by NumberFormat; typing.Any is not
carried over because nothing on this branch uses it.
2026-08-03 12:31:55 +05:30
Mihir Kandoi
444dd9e817 test(stock): cover reading number formats end to end
Set the number format on the session user rather than on System Settings: the
code reads the user default, which shadows the global one, so these tests never
exercised the path they were written for. Restoring it in a finally also keeps
a failed assertion from leaving the whole suite in another locale.

Add a table test over every format in NUMBER_FORMAT_MAP, covering the grouped
values and the three formats parse_float used to read as 0, and restore the
formula-based coverage for non-numeric readings.

(cherry picked from commit 00d17ca5db)
2026-08-03 06:56:49 +00:00
Mihir Kandoi
fccf1220f6 fix(stock): accept every number a reading can be written as
parse_float and is_valid_number each re-derived the number grammar, so the
validator accepted strings flt() cannot parse: str.isdigit() lets superscripts
through and lstrip("+-") lets repeated signs through, both then silently scored
as 0. One parse_reading() returning None when float() refuses the value makes
acceptance and conversion true by construction.

The grammar was also wrong for several formats. Where the group separator is
not a dot, a dot-decimal reading such as 1.15 parsed correctly before and is
accepted again. #,### and #.### report no decimal separator at all, which
rejected every fractional reading outright and, for #.###, reread a stored
1.500 as 1500.0; they now fall back to a dot and give up the grouping that
would collide with it.

Only readings that change are checked, so an inspection entered by a user in
one locale stays saveable and submittable by a user in another, and manual
inspection rows keep the free text they were never parsed for.

NumberFormat replaces get_number_format_info, which frappe drops in v16.

(cherry picked from commit 5b5f354090)

# Conflicts:
#	erpnext/stock/doctype/quality_inspection/quality_inspection.py
2026-08-03 06:56:48 +00:00
Sudharsanan11
113b5ecaec test(stock): cover quality inspection readings in every number format
covers the reported case, a 1,15 reading in the space grouped "# ###,##"
format, which was read as 115 and rejected. also covers the dot grouped
comma format, and asserts that a reading written with the wrong separator,
or one that is not a number at all, is now rejected with an error rather
than read as a different value.

(cherry picked from commit b1f188146e)
2026-08-03 06:56:48 +00:00
Sudharsanan11
e2466780b9 test(stock): drop non numeric reading from formula based quality inspection
a numeric reading of "random text" was read as 0 and pulled the mean from
0.6 down to 0.4, which the test then asserted as accepted. such a reading
is now rejected outright, and the test is about formula evaluation, so drop
the row. its assertions are unchanged.

(cherry picked from commit 3752be809f)
2026-08-03 06:56:47 +00:00
Sudharsanan11
3b7fb6851a fix(stock): read quality inspection readings in the user's number format
readings are Data fields, so they are parsed server side. parse_float only
swapped the separators for "#.###,##", so in the space grouped "# ###,##"
(polish) a reading of 1,15 was read as 115, fell outside the acceptance
range and silently rejected the inspection. strip whatever the group
separator is and normalise whatever the decimal separator is instead.

it also read the global number format, while the desk formats numbers with
the user's own. a user whose locale differs from the site therefore typed
readings in a format the server did not parse them with. read the user
default, which falls back to the global one.

a reading that is not a valid number in that format is now rejected with an
error instead of being read as a different number.

(cherry picked from commit e74c0a3cdb)
2026-08-03 06:56:46 +00:00
R-Jayaraman
b0f2704bde test(purchase): add coverage for zero-qty return rejection
(cherry picked from commit cde2963da1)

# Conflicts:
#	erpnext/controllers/tests/test_sales_and_purchase_return.py
2026-08-03 06:17:09 +00:00
R-Jayaraman
032b922f0c fix(purchase): reject purchase returns where every item has zero quantity
validate_returned_items() set items_returned=True whenever a row matched
a valid item from the original document, even if its qty was 0. This let
a Purchase Invoice, Purchase Receipt, or Subcontracting Receipt return be
submitted with every line at qty=0 - a no-op document with no stock or
financial effect that still consumed a document number and linked back
to the original transaction.

Scoped to the Purchase side only: items_returned now flips to True for
Purchase Invoice/Purchase Receipt/Subcontracting Receipt only when qty
(or received_qty) is actually negative, so an all-zero purchase return
correctly hits the existing "At least one item should be entered with
negative quantity" check. Sales Invoice, Delivery Note, and POS Invoice
are unchanged.

Also applies a corresponding check to the item_name-only fallback branch
(for rows without an item_code - Item Code is not mandatory on Purchase
Invoice Item), which previously bypassed this fix entirely and still set
items_returned=True unconditionally regardless of quantity. For that
branch specifically, only qty is checked (not received_qty): with no
linked Item there's no accepted/rejected split, so received_qty carries
no independent meaning and a qty=0 row must be rejected regardless of
its value.

(cherry picked from commit b63066ed44)
2026-08-03 06:17:08 +00:00
MochaMind
833ccd3358 chore: update POT file (#57706) 2026-08-02 14:31:18 +02:00