Compare commits

...

70 Commits

Author SHA1 Message Date
Frappe PR Bot
36b9926527 chore(release): Bumped to Version 14.3.0
# [14.3.0](https://github.com/frappe/erpnext/compare/v14.2.3...v14.3.0) (2022-10-12)

### Bug Fixes

* consider outgoingrate while valuation rate calculate ([423c019](423c0190e2))
* consider sales rate as incoming rate for transit warehouse in purchase flow ([948b231](948b231e92))
* Do not add tax withheld vouchers post tax withheding in one document ([bd8e61b](bd8e61b2dc))
* Explicitly update modified (backport [#32519](https://github.com/frappe/erpnext/issues/32519)) ([#32575](https://github.com/frappe/erpnext/issues/32575)) ([154904e](154904e960))
* Hanlde rounding loss for internal transfer ([8eda2db](8eda2dbdf8))
* Incoming rate precision fixes for intra company transfer ([b653f43](b653f43b70))
* make readings status mandatory in Quality Inspection ([50d790c](50d790c919))
* minor cleanup ([236a5f3](236a5f37c7))
* more fields reordering related to Tab Break ([db4fbc9](db4fbc9e58))
* PO cancel post advance payment cancel against PO ([bda25c4](bda25c4d5d))
* removed unnecessary imports ([31782d6](31782d6f71))
* set Quality Inspection status based on readings status ([e25db8b](e25db8b1b5))
* single column indexes (backport [#32425](https://github.com/frappe/erpnext/issues/32425)) ([#32513](https://github.com/frappe/erpnext/issues/32513)) ([2f1b8af](2f1b8af13c))
* Tax withholding related fixes ([d5f6938](d5f693806b))
* test case ([0b26131](0b26131b65))
* **test:** `test_rejected_qi_validation` ([943e619](943e6192cc))
* TooManyWritesError during reposting of stock ([73742ff](73742ff565))
* unlink payment on invoice cancellation ([8ba503b](8ba503bf0e))
* use naming_series in budget ([0a24859](0a24859c9c))
* value error on pos submit ([4b65dd7](4b65dd7f2a))

### Features

* **JE:** trigger account field when fetched from template ([17dd1ab](17dd1abb34)), closes [#32409](https://github.com/frappe/erpnext/issues/32409)
* provision to return non consumed components against the work order ([d0f3818](d0f3818060))
* Tab Break in Material Request ([79151be](79151be8ce))
* Tab Break in Purchase Invoice ([89314d4](89314d4171))
* Tab Break in Purchase Order ([5a8329a](5a8329add1))
* Tab Break in Purchase Receipt ([b092791](b092791ac8))
* Tab Break in Quotation ([b0a9f79](b0a9f79e18))
* Tab Break in Sales Order, Delivery Note, Sales Invoice and Purchase Order ([31cd96b](31cd96bc89))
* Tab Break in Supplier Quotation ([22ad3ad](22ad3ad6f3))
2022-10-12 12:21:48 +00:00
Deepesh Garg
d38071eb20 Merge pull request #32560 from frappe/version-14-hotfix
chore: release v14
2022-10-12 17:50:12 +05:30
Deepesh Garg
c4b39c7c1c Merge branch 'version-14' into version-14-hotfix 2022-10-12 17:19:33 +05:30
Deepesh Garg
c83c645ab0 Merge pull request #32579 from frappe/mergify/bp/version-14-hotfix/pr-32563
fix: consider sales rate as incoming rate for transit warehouse in purchase flow (backport #32563)
2022-10-12 17:16:36 +05:30
Deepesh Garg
eab24b8366 Merge pull request #32582 from frappe/mergify/bp/version-14-hotfix/pr-32272
fix: Incoming rate precision fixes for intra company transfer (backport #32272)
2022-10-12 17:05:18 +05:30
rohitwaghchaure
31782d6f71 fix: removed unnecessary imports 2022-10-12 16:34:48 +05:30
Deepesh Garg
2494ccc0a2 chore: check only for inter-company transfers
(cherry picked from commit 9aa5e20ef7)
2022-10-12 10:54:33 +00:00
Deepesh Garg
108720b9c3 chore: fix precision condition
(cherry picked from commit 49601558c6)
2022-10-12 10:54:33 +00:00
Deepesh Garg
4f3e209009 chore: Use proper accounts
(cherry picked from commit 1c05c004cd)
2022-10-12 10:54:33 +00:00
Deepesh Garg
23b18a5e38 chore: Increase precision for other doc fields
(cherry picked from commit c8d2181498)
2022-10-12 10:54:33 +00:00
Deepesh Garg
b386b8c634 chore: GL Entries for SLE diff
(cherry picked from commit df2a0e265b)
2022-10-12 10:54:32 +00:00
Deepesh Garg
49221d47c2 test: Internal tranfer precision loss test
(cherry picked from commit dc20b21fb5)
2022-10-12 10:54:32 +00:00
Deepesh Garg
09e9675653 chore: Increase incoming_rate field precision to 6
(cherry picked from commit b31c3bd35d)
2022-10-12 10:54:32 +00:00
Deepesh Garg
8eda2dbdf8 fix: Hanlde rounding loss for internal transfer
(cherry picked from commit 6e47fd54a0)
2022-10-12 10:54:32 +00:00
Deepesh Garg
b653f43b70 fix: Incoming rate precision fixes for intra company transfer
(cherry picked from commit 083309c056)
2022-10-12 10:54:31 +00:00
Rohit Waghchaure
0b26131b65 fix: test case
(cherry picked from commit 98bf8e1304)
2022-10-12 10:51:00 +00:00
Rohit Waghchaure
423c0190e2 fix: consider outgoingrate while valuation rate calculate
(cherry picked from commit 3266e54e33)
2022-10-12 10:51:00 +00:00
Rohit Waghchaure
948b231e92 fix: consider sales rate as incoming rate for transit warehouse in purchase flow
(cherry picked from commit 683a47f7a1)
2022-10-12 10:50:59 +00:00
Deepesh Garg
23aca6663f Merge pull request #32565 from frappe/mergify/bp/version-14-hotfix/pr-32408
feat: Tab Breaks in all Sales and Purchase cycle transactions (backport #32408)
2022-10-12 14:13:38 +05:30
Deepesh Garg
6c85bdd735 Merge branch 'version-14-hotfix' into mergify/bp/version-14-hotfix/pr-32408 2022-10-12 13:04:01 +05:30
mergify[bot]
154904e960 fix: Explicitly update modified (backport #32519) (#32575)
fix: Explicitly update modified (#32519)

* fix: Explicitly update modified

required after https://github.com/frappe/frappe/pull/18301

* chore: fix broken translations

(cherry picked from commit 8376fbc982)

Co-authored-by: Ankush Menat <ankush@frappe.io>
2022-10-12 12:59:06 +05:30
mergify[bot]
03db8b2f5f ci: disable orchestrator (backport #32571) (#32572)
* ci: disable orchestrator (#32571)

(cherry picked from commit 6ce3ce758c)

* chore: correct build count

* chore: no cov

Co-authored-by: Ankush Menat <ankush@frappe.io>
2022-10-12 12:14:48 +05:30
Nabin Hait
236a5f37c7 fix: minor cleanup
(cherry picked from commit e71c417f7e)
2022-10-11 10:33:30 +00:00
Nabin Hait
db4fbc9e58 fix: more fields reordering related to Tab Break
(cherry picked from commit 5389a35798)
2022-10-11 10:33:30 +00:00
Nabin Hait
89314d4171 feat: Tab Break in Purchase Invoice
(cherry picked from commit aaf3c2b329)
2022-10-11 10:33:30 +00:00
Nabin Hait
b092791ac8 feat: Tab Break in Purchase Receipt
(cherry picked from commit 35f836c4b7)
2022-10-11 10:33:30 +00:00
Nabin Hait
22ad3ad6f3 feat: Tab Break in Supplier Quotation
(cherry picked from commit 3d9263bf86)
2022-10-11 10:33:29 +00:00
Nabin Hait
79151be8ce feat: Tab Break in Material Request
(cherry picked from commit 2172c5034a)
2022-10-11 10:33:29 +00:00
Nabin Hait
5a8329add1 feat: Tab Break in Purchase Order
(cherry picked from commit 10a25603ac)
2022-10-11 10:33:29 +00:00
Nabin Hait
b0a9f79e18 feat: Tab Break in Quotation
(cherry picked from commit 7546562139)
2022-10-11 10:33:28 +00:00
Nabin Hait
31cd96bc89 feat: Tab Break in Sales Order, Delivery Note, Sales Invoice and Purchase Order
(cherry picked from commit f6613e1e4c)
2022-10-11 10:33:27 +00:00
ruthra kumar
db563483cb Merge pull request #32558 from frappe/mergify/bp/version-14-hotfix/pr-32557
fix: Value error on validation of POS invoices with Serial Nos (backport #32557)
2022-10-11 15:36:36 +05:30
ruthra kumar
6fa1b892f7 test: value error on serial no validation on pos
(cherry picked from commit 9e2bd10d03)
2022-10-11 09:13:36 +00:00
ruthra kumar
4b65dd7f2a fix: value error on pos submit
(cherry picked from commit 4b908ebcd6)
2022-10-11 09:13:35 +00:00
Deepesh Garg
62296c85cd Merge pull request #32543 from frappe/mergify/bp/version-14-hotfix/pr-32497
chore: set `Quality Inspection` status based on readings status (backport #32497)
2022-10-11 14:02:58 +05:30
ruthra kumar
a71be4e99a Merge pull request #32550 from frappe/mergify/bp/version-14-hotfix/pr-32548
fix: allow deletion of cancelled Invoices once payments are unlinked (backport #32548)
2022-10-11 13:47:57 +05:30
Ankush Menat
c9002526b9 chore: update codeowners 2022-10-11 12:33:51 +05:30
Deepesh Garg
b9b08e4d5e Merge pull request #32555 from frappe/mergify/bp/version-14-hotfix/pr-32554
fix: use naming_series in budget (backport #32554)
2022-10-11 11:51:51 +05:30
Sagar Sharma
3c0bca3d74 Merge branch 'version-14-hotfix' into mergify/bp/version-14-hotfix/pr-32497 2022-10-11 11:45:19 +05:30
Anand Baburajan
27509e2141 Merge branch 'version-14-hotfix' into mergify/bp/version-14-hotfix/pr-32554 2022-10-11 11:06:44 +05:30
rohitwaghchaure
52dd967b0d Merge pull request #32542 from frappe/mergify/bp/version-14-hotfix/pr-32393
feat: provision to return non consumed components against the work order (backport #32393)
2022-10-11 10:39:18 +05:30
Deepesh Garg
9601e47ae4 Merge pull request #32540 from frappe/mergify/bp/version-14-hotfix/pr-32536
fix: PO cancel post advance payment cancel against PO (backport #32536)
2022-10-11 10:17:10 +05:30
anandbaburajan
0a24859c9c fix: use naming_series in budget
(cherry picked from commit e4d7d8c42d)
2022-10-11 04:46:10 +00:00
ruthra kumar
998367cedc test: update ple on payment unlink for SI's and SO's
(cherry picked from commit 143f905838)
2022-10-10 11:12:38 +00:00
ruthra kumar
8ba503bf0e fix: unlink payment on invoice cancellation
(cherry picked from commit 537d953f4c)
2022-10-10 11:12:38 +00:00
Sagar Sharma
943e6192cc fix(test): test_rejected_qi_validation
(cherry picked from commit 4992e4a2b8)
2022-10-10 05:20:45 +00:00
Sagar Sharma
91b0e7ddbd test: add test cases for Quality Inspection status
(cherry picked from commit fcc1272d42)
2022-10-10 05:20:45 +00:00
Sagar Sharma
e25db8b1b5 fix: set Quality Inspection status based on readings status
(cherry picked from commit 2657ece2cd)
2022-10-10 05:20:44 +00:00
Sagar Sharma
50d790c919 fix: make readings status mandatory in Quality Inspection
(cherry picked from commit d7c3b7633a)
2022-10-10 05:20:44 +00:00
Sagar Sharma
8a4c07a7e8 chore: add Manual Inspection field in Quality Inspection DocType
(cherry picked from commit 39707757a6)
2022-10-10 05:20:44 +00:00
Rohit Waghchaure
d0f3818060 feat: provision to return non consumed components against the work order
(cherry picked from commit d59ed24e6c)
2022-10-10 03:39:25 +00:00
Deepesh Garg
bda25c4d5d fix: PO cancel post advance payment cancel against PO
(cherry picked from commit d806e32030)
2022-10-09 13:06:06 +00:00
Frappe PR Bot
f70103dac6 chore(release): Bumped to Version 14.2.3
## [14.2.3](https://github.com/frappe/erpnext/compare/v14.2.2...v14.2.3) (2022-10-07)

### Bug Fixes

* Do not add tax withheld vouchers post tax withheding in one document ([6060072](6060072d22))
* Tax withholding related fixes ([a226fcf](a226fcf898))
2022-10-07 12:40:22 +00:00
Deepesh Garg
a519d68826 Merge pull request #32525 from frappe/mergify/bp/version-14/pr-32522
fix: Tax withholding related fixes (backport #32522)
2022-10-07 18:08:51 +05:30
Deepesh Garg
49cedca8de Merge pull request #32524 from frappe/mergify/bp/version-14-hotfix/pr-32522
fix: Tax withholding related fixes (backport #32522)
2022-10-07 18:08:39 +05:30
Deepesh Garg
6060072d22 fix: Do not add tax withheld vouchers post tax withheding in one document
(cherry picked from commit 781d160c68)
2022-10-07 12:03:29 +00:00
Deepesh Garg
a226fcf898 fix: Tax withholding related fixes
(cherry picked from commit abf5b6be3e)
2022-10-07 12:03:29 +00:00
Deepesh Garg
bd8e61b2dc fix: Do not add tax withheld vouchers post tax withheding in one document
(cherry picked from commit 781d160c68)
2022-10-07 11:03:40 +00:00
Deepesh Garg
d5f693806b fix: Tax withholding related fixes
(cherry picked from commit abf5b6be3e)
2022-10-07 11:03:40 +00:00
mergify[bot]
5f6bbd4929 chore: drop stale demo page (backport #32515) (#32516)
chore: drop stale demo page (#32515)

(cherry picked from commit 07c4a74838)

Co-authored-by: Ankush Menat <ankush@frappe.io>
2022-10-06 13:03:29 +05:30
mergify[bot]
2f1b8af13c fix: single column indexes (backport #32425) (#32513)
fix: single column indexes (#32425)

refactor: move single column indexes to doctypes
(cherry picked from commit 8d1db0ea3d)

Co-authored-by: Ankush Menat <ankush@frappe.io>
2022-10-06 11:37:43 +05:30
Deepesh Garg
3d6a37ea04 Merge pull request #32510 from frappe/mergify/bp/version-14-hotfix/pr-32385
chore: update fr translation (backport #32385)
2022-10-06 09:03:20 +05:30
HENRY Florian
3caf905019 chore: update fr translation (#32385)
(cherry picked from commit 0e4017cbe5)
2022-10-05 17:20:04 +00:00
Deepesh Garg
4941b6e280 Merge pull request #32501 from frappe/mergify/bp/version-14-hotfix/pr-32491
refactor: remove duplicate entries on remarks migration patch (backport #32491)
2022-10-05 18:16:51 +05:30
Deepesh Garg
a02ddc92ef Merge branch 'version-14-hotfix' into mergify/bp/version-14-hotfix/pr-32491 2022-10-05 17:30:25 +05:30
Deepesh Garg
6017f6790e Merge pull request #32503 from frappe/mergify/bp/version-14-hotfix/pr-32499
fix: TooManyWritesError during reposting of stock (backport #32499)
2022-10-05 17:29:56 +05:30
Deepesh Garg
3daff104c3 Merge pull request #32505 from frappe/mergify/bp/version-14-hotfix/pr-32478
feat(JE): trigger account field when fetched from template (backport #32478)
2022-10-05 17:28:49 +05:30
Dany Robert
17dd1abb34 feat(JE): trigger account field when fetched from template
Closes #32409

(cherry picked from commit c35adcf5a1)
2022-10-05 10:38:41 +00:00
Rohit Waghchaure
73742ff565 fix: TooManyWritesError during reposting of stock
(cherry picked from commit aaabba9b1e)
2022-10-05 10:36:18 +00:00
ruthra kumar
70e990c4f3 refactor: remove duplicate entries on remarks migration patch
(cherry picked from commit 518ab93e03)
2022-10-05 10:35:06 +00:00
56 changed files with 2418 additions and 1085 deletions

View File

@@ -120,7 +120,7 @@ jobs:
FRAPPE_BRANCH: ${{ github.event.inputs.branch }}
- name: Run Tests
run: cd ~/frappe-bench/ && bench --site test_site run-parallel-tests --app erpnext --use-orchestrator --with-coverage
run: 'cd ~/frappe-bench/ && bench --site test_site run-parallel-tests --app erpnext --total-builds 3 --build-number ${{ matrix.container }}'
env:
TYPE: server
CI_BUILD_ID: ${{ github.run_id }}

View File

@@ -11,22 +11,18 @@ erpnext/selling @nextchamp-saqib @deepeshgarg007 @ruthra-kumar
erpnext/support/ @nextchamp-saqib @deepeshgarg007
pos* @nextchamp-saqib
erpnext/buying/ @marination @rohitwaghchaure @s-aga-r
erpnext/e_commerce/ @marination
erpnext/maintenance/ @marination @rohitwaghchaure @s-aga-r
erpnext/manufacturing/ @marination @rohitwaghchaure @s-aga-r
erpnext/portal/ @marination
erpnext/quality_management/ @marination @rohitwaghchaure @s-aga-r
erpnext/shopping_cart/ @marination
erpnext/stock/ @marination @rohitwaghchaure @s-aga-r
erpnext/buying/ @rohitwaghchaure @s-aga-r
erpnext/maintenance/ @rohitwaghchaure @s-aga-r
erpnext/manufacturing/ @rohitwaghchaure @s-aga-r
erpnext/quality_management/ @rohitwaghchaure @s-aga-r
erpnext/stock/ @rohitwaghchaure @s-aga-r
erpnext/crm/ @NagariaHussain
erpnext/education/ @rutwikhdev
erpnext/projects/ @ruchamahabal
erpnext/controllers/ @deepeshgarg007 @nextchamp-saqib @rohitwaghchaure @marination
erpnext/patches/ @deepeshgarg007 @nextchamp-saqib @marination
erpnext/public/ @nextchamp-saqib @marination
erpnext/controllers/ @deepeshgarg007 @nextchamp-saqib @rohitwaghchaure
erpnext/patches/ @deepeshgarg007 @nextchamp-saqib
.github/ @ankush
pyproject.toml @gavindsouza @ankush
pyproject.toml @ankush

View File

@@ -2,7 +2,7 @@ import inspect
import frappe
__version__ = "14.2.2"
__version__ = "14.3.0"
def get_default_company(user=None):

View File

@@ -1,6 +1,7 @@
{
"actions": [],
"allow_import": 1,
"autoname": "naming_series:",
"creation": "2016-05-16 11:42:29.632528",
"doctype": "DocType",
"editable_grid": 1,
@@ -9,6 +10,7 @@
"budget_against",
"company",
"cost_center",
"naming_series",
"project",
"fiscal_year",
"column_break_3",
@@ -190,15 +192,26 @@
"label": "Budget Accounts",
"options": "Budget Account",
"reqd": 1
},
{
"fieldname": "naming_series",
"fieldtype": "Data",
"hidden": 1,
"label": "Series",
"no_copy": 1,
"print_hide": 1,
"read_only": 1,
"set_only_once": 1
}
],
"index_web_pages_for_search": 1,
"is_submittable": 1,
"links": [],
"modified": "2020-10-06 15:13:54.055854",
"modified": "2022-10-10 22:14:36.361509",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Budget",
"naming_rule": "By \"Naming Series\" field",
"owner": "Administrator",
"permissions": [
{
@@ -220,5 +233,6 @@
],
"sort_field": "modified",
"sort_order": "DESC",
"states": [],
"track_changes": 1
}

View File

@@ -5,7 +5,6 @@
import frappe
from frappe import _
from frappe.model.document import Document
from frappe.model.naming import make_autoname
from frappe.utils import add_months, flt, fmt_money, get_last_day, getdate
from erpnext.accounts.doctype.accounting_dimension.accounting_dimension import (
@@ -23,11 +22,6 @@ class DuplicateBudgetError(frappe.ValidationError):
class Budget(Document):
def autoname(self):
self.name = make_autoname(
self.get(frappe.scrub(self.budget_against)) + "/" + self.fiscal_year + "/.###"
)
def validate(self):
if not self.get(frappe.scrub(self.budget_against)):
frappe.throw(_("{0} is mandatory").format(self.budget_against))
@@ -109,6 +103,9 @@ class Budget(Document):
):
self.applicable_on_booking_actual_expenses = 1
def before_naming(self):
self.naming_series = f"{{{frappe.scrub(self.budget_against)}}}./.{self.fiscal_year}/.###"
def validate_expense_against_budget(args):
args = frappe._dict(args)

View File

@@ -173,8 +173,8 @@ frappe.ui.form.on("Journal Entry", {
var update_jv_details = function(doc, r) {
$.each(r, function(i, d) {
var row = frappe.model.add_child(doc, "Journal Entry Account", "accounts");
row.account = d.account;
row.balance = d.balance;
frappe.model.set_value(row.doctype, row.name, "account", d.account)
frappe.model.set_value(row.doctype, row.name, "balance", d.balance)
});
refresh_field("accounts");
}

View File

@@ -3,12 +3,13 @@
import frappe
from frappe import qb
from frappe.tests.utils import FrappeTestCase
from frappe.tests.utils import FrappeTestCase, change_settings
from frappe.utils import nowdate
from erpnext.accounts.doctype.payment_entry.payment_entry import get_payment_entry
from erpnext.accounts.doctype.payment_entry.test_payment_entry import create_payment_entry
from erpnext.accounts.doctype.sales_invoice.test_sales_invoice import create_sales_invoice
from erpnext.selling.doctype.sales_order.test_sales_order import make_sales_order
from erpnext.stock.doctype.item.test_item import create_item
@@ -127,6 +128,25 @@ class TestPaymentLedgerEntry(FrappeTestCase):
payment.posting_date = posting_date
return payment
def create_sales_order(
self, qty=1, rate=100, posting_date=nowdate(), do_not_save=False, do_not_submit=False
):
so = make_sales_order(
company=self.company,
transaction_date=posting_date,
customer=self.customer,
item_code=self.item,
cost_center=self.cost_center,
warehouse=self.warehouse,
debit_to=self.debit_to,
currency="INR",
qty=qty,
rate=100,
do_not_save=do_not_save,
do_not_submit=do_not_submit,
)
return so
def clear_old_entries(self):
doctype_list = [
"GL Entry",
@@ -406,3 +426,89 @@ class TestPaymentLedgerEntry(FrappeTestCase):
]
self.assertEqual(pl_entries_for_crnote[0], expected_values[0])
self.assertEqual(pl_entries_for_crnote[1], expected_values[1])
@change_settings(
"Accounts Settings",
{"unlink_payment_on_cancellation_of_invoice": 1, "delete_linked_ledger_entries": 1},
)
def test_multi_payment_unlink_on_invoice_cancellation(self):
transaction_date = nowdate()
amount = 100
si = self.create_sales_invoice(qty=1, rate=amount, posting_date=transaction_date)
for amt in [40, 40, 20]:
# payment 1
pe = get_payment_entry(si.doctype, si.name)
pe.paid_amount = amt
pe.get("references")[0].allocated_amount = amt
pe = pe.save().submit()
si.reload()
si.cancel()
entries = frappe.db.get_list(
"Payment Ledger Entry",
filters={"against_voucher_type": si.doctype, "against_voucher_no": si.name, "delinked": 0},
)
self.assertEqual(entries, [])
# with references removed, deletion should be possible
si.delete()
self.assertRaises(frappe.DoesNotExistError, frappe.get_doc, si.doctype, si.name)
@change_settings(
"Accounts Settings",
{"unlink_payment_on_cancellation_of_invoice": 1, "delete_linked_ledger_entries": 1},
)
def test_multi_je_unlink_on_invoice_cancellation(self):
transaction_date = nowdate()
amount = 100
si = self.create_sales_invoice(qty=1, rate=amount, posting_date=transaction_date)
# multiple JE's against invoice
for amt in [40, 40, 20]:
je1 = self.create_journal_entry(
self.income_account, self.debit_to, amt, posting_date=transaction_date
)
je1.get("accounts")[1].party_type = "Customer"
je1.get("accounts")[1].party = self.customer
je1.get("accounts")[1].reference_type = si.doctype
je1.get("accounts")[1].reference_name = si.name
je1 = je1.save().submit()
si.reload()
si.cancel()
entries = frappe.db.get_list(
"Payment Ledger Entry",
filters={"against_voucher_type": si.doctype, "against_voucher_no": si.name, "delinked": 0},
)
self.assertEqual(entries, [])
# with references removed, deletion should be possible
si.delete()
self.assertRaises(frappe.DoesNotExistError, frappe.get_doc, si.doctype, si.name)
@change_settings(
"Accounts Settings",
{"unlink_payment_on_cancellation_of_invoice": 1, "delete_linked_ledger_entries": 1},
)
def test_advance_payment_unlink_on_order_cancellation(self):
transaction_date = nowdate()
amount = 100
so = self.create_sales_order(qty=1, rate=amount, posting_date=transaction_date).save().submit()
pe = get_payment_entry(so.doctype, so.name).save().submit()
so.reload()
so.cancel()
entries = frappe.db.get_list(
"Payment Ledger Entry",
filters={"against_voucher_type": so.doctype, "against_voucher_no": so.name, "delinked": 0},
)
self.assertEqual(entries, [])
# with references removed, deletion should be possible
so.delete()
self.assertRaises(frappe.DoesNotExistError, frappe.get_doc, so.doctype, so.name)

View File

@@ -343,7 +343,8 @@
"no_copy": 1,
"options": "POS Invoice",
"print_hide": 1,
"read_only": 1
"read_only": 1,
"search_index": 1
},
{
"default": "0",
@@ -1553,7 +1554,7 @@
"icon": "fa fa-file-text",
"is_submittable": 1,
"links": [],
"modified": "2022-09-27 13:00:24.166684",
"modified": "2022-09-30 03:49:50.455199",
"modified_by": "Administrator",
"module": "Accounts",
"name": "POS Invoice",

View File

@@ -743,7 +743,3 @@ def add_return_modes(doc, pos_profile):
]:
payment_mode = get_mode_of_payment_info(mode_of_payment, doc.company)
append_payment(payment_mode[0])
def on_doctype_update():
frappe.db.add_index("POS Invoice", ["return_against"])

View File

@@ -495,6 +495,67 @@ class TestPOSInvoice(unittest.TestCase):
self.assertRaises(frappe.ValidationError, pos.submit)
def test_value_error_on_serial_no_validation(self):
from erpnext.stock.doctype.stock_entry.test_stock_entry import make_serialized_item
se = make_serialized_item(
company="_Test Company",
target_warehouse="Stores - _TC",
cost_center="Main - _TC",
expense_account="Cost of Goods Sold - _TC",
)
serial_nos = se.get("items")[0].serial_no
# make a pos invoice
pos = create_pos_invoice(
company="_Test Company",
debit_to="Debtors - _TC",
account_for_change_amount="Cash - _TC",
warehouse="Stores - _TC",
income_account="Sales - _TC",
expense_account="Cost of Goods Sold - _TC",
cost_center="Main - _TC",
item=se.get("items")[0].item_code,
rate=1000,
qty=1,
do_not_save=1,
)
pos.get("items")[0].has_serial_no = 1
pos.get("items")[0].serial_no = serial_nos.split("\n")[0]
pos.set("payments", [])
pos.append(
"payments", {"mode_of_payment": "Cash", "account": "Cash - _TC", "amount": 1000, "default": 1}
)
pos = pos.save().submit()
# make a return
pos_return = make_sales_return(pos.name)
pos_return.paid_amount = pos_return.grand_total
pos_return.save()
pos_return.submit()
# set docstatus to 2 for pos to trigger this issue
frappe.db.set_value("POS Invoice", pos.name, "docstatus", 2)
pos2 = create_pos_invoice(
company="_Test Company",
debit_to="Debtors - _TC",
account_for_change_amount="Cash - _TC",
warehouse="Stores - _TC",
income_account="Sales - _TC",
expense_account="Cost of Goods Sold - _TC",
cost_center="Main - _TC",
item=se.get("items")[0].item_code,
rate=1000,
qty=1,
do_not_save=1,
)
pos2.get("items")[0].has_serial_no = 1
pos2.get("items")[0].serial_no = serial_nos.split("\n")[0]
# Value error should not be triggered on validation
pos2.save()
def test_loyalty_points(self):
from erpnext.accounts.doctype.loyalty_program.loyalty_program import (
get_loyalty_program_details_with_points,

View File

@@ -12,39 +12,23 @@
"supplier",
"supplier_name",
"tax_id",
"due_date",
"tax_withholding_category",
"column_break1",
"company",
"column_break_6",
"posting_date",
"posting_time",
"set_posting_time",
"due_date",
"column_break1",
"is_paid",
"is_return",
"return_against",
"apply_tds",
"tax_withholding_category",
"amended_from",
"accounting_dimensions_section",
"cost_center",
"dimension_col_break",
"project",
"supplier_invoice_details",
"bill_no",
"column_break_15",
"bill_date",
"returns",
"return_against",
"section_addresses",
"supplier_address",
"address_display",
"contact_person",
"contact_display",
"contact_mobile",
"contact_email",
"col_break_address",
"shipping_address",
"shipping_address_display",
"billing_address",
"billing_address_display",
"currency_and_price_list",
"currency",
"conversion_rate",
@@ -54,39 +38,33 @@
"plc_conversion_rate",
"ignore_pricing_rule",
"sec_warehouse",
"set_warehouse",
"rejected_warehouse",
"col_break_warehouse",
"set_from_warehouse",
"supplier_warehouse",
"is_subcontracted",
"items_section",
"update_stock",
"scan_barcode",
"col_break_warehouse",
"update_stock",
"set_warehouse",
"set_from_warehouse",
"is_subcontracted",
"rejected_warehouse",
"supplier_warehouse",
"items_section",
"items",
"pricing_rule_details",
"pricing_rules",
"raw_materials_supplied",
"supplied_items",
"section_break_26",
"total_qty",
"total_net_weight",
"column_break_50",
"base_total",
"base_net_total",
"column_break_28",
"total_net_weight",
"total",
"net_total",
"taxes_section",
"taxes_and_charges",
"column_break_58",
"tax_category",
"column_break_49",
"shipping_rule",
"section_break_51",
"taxes_and_charges",
"taxes",
"tax_withheld_vouchers_section",
"tax_withheld_vouchers",
"sec_tax_breakup",
"other_charges_calculation",
"totals",
"base_taxes_and_charges_added",
"base_taxes_and_charges_deducted",
@@ -95,12 +73,6 @@
"taxes_and_charges_added",
"taxes_and_charges_deducted",
"total_taxes_and_charges",
"section_break_44",
"apply_discount_on",
"base_discount_amount",
"column_break_46",
"additional_discount_percentage",
"discount_amount",
"section_break_49",
"base_grand_total",
"base_rounding_adjustment",
@@ -114,24 +86,58 @@
"total_advance",
"outstanding_amount",
"disable_rounded_total",
"section_break_44",
"apply_discount_on",
"base_discount_amount",
"additional_discount_account",
"column_break_46",
"additional_discount_percentage",
"discount_amount",
"tax_withheld_vouchers_section",
"tax_withheld_vouchers",
"sec_tax_breakup",
"other_charges_calculation",
"pricing_rule_details",
"pricing_rules",
"raw_materials_supplied",
"supplied_items",
"payments_tab",
"payments_section",
"mode_of_payment",
"cash_bank_account",
"base_paid_amount",
"clearance_date",
"col_br_payments",
"cash_bank_account",
"paid_amount",
"base_paid_amount",
"advances_section",
"allocate_advances_automatically",
"get_advances",
"advances",
"advance_tax",
"write_off",
"write_off_amount",
"base_write_off_amount",
"column_break_61",
"write_off_account",
"write_off_cost_center",
"advances_section",
"allocate_advances_automatically",
"get_advances",
"advances",
"advance_tax",
"address_and_contact_tab",
"section_addresses",
"supplier_address",
"address_display",
"col_break_address",
"contact_person",
"contact_display",
"contact_mobile",
"contact_email",
"company_shipping_address_section",
"shipping_address",
"column_break_126",
"shipping_address_display",
"company_billing_address_section",
"billing_address",
"column_break_130",
"billing_address_display",
"terms_tab",
"payment_schedule_section",
"payment_terms_template",
"ignore_default_payment_terms_template",
@@ -139,23 +145,15 @@
"terms_section_break",
"tc_name",
"terms",
"printing_settings",
"letter_head",
"select_print_heading",
"column_break_112",
"group_same_items",
"language",
"sb_14",
"on_hold",
"release_date",
"cb_17",
"hold_comment",
"more_info",
"more_info_tab",
"status_section",
"status",
"inter_company_invoice_reference",
"represents_company",
"column_break_147",
"is_internal_supplier",
"column_break_177",
"per_received",
"supplier_invoice_details",
"bill_no",
"column_break_15",
"bill_date",
"accounting_details_section",
"credit_to",
"party_account_currency",
@@ -163,15 +161,32 @@
"against_expense_account",
"column_break_63",
"unrealized_profit_loss_account",
"remarks",
"subscription_section",
"from_date",
"to_date",
"column_break_114",
"auto_repeat",
"update_auto_repeat_reference",
"per_received",
"is_old_subcontracting_flow"
"column_break_114",
"from_date",
"to_date",
"printing_settings",
"letter_head",
"group_same_items",
"column_break_112",
"select_print_heading",
"language",
"sb_14",
"on_hold",
"release_date",
"cb_17",
"hold_comment",
"additional_info_section",
"is_internal_supplier",
"represents_company",
"column_break_147",
"inter_company_invoice_reference",
"is_old_subcontracting_flow",
"remarks",
"connections_tab",
"column_break_38"
],
"fields": [
{
@@ -354,7 +369,7 @@
"collapsible_depends_on": "bill_no",
"fieldname": "supplier_invoice_details",
"fieldtype": "Section Break",
"label": "Supplier Invoice Details"
"label": "Supplier Invoice"
},
{
"fieldname": "bill_no",
@@ -377,12 +392,6 @@
"oldfieldtype": "Date",
"print_hide": 1
},
{
"depends_on": "return_against",
"fieldname": "returns",
"fieldtype": "Section Break",
"label": "Returns"
},
{
"depends_on": "return_against",
"fieldname": "return_against",
@@ -394,10 +403,9 @@
"read_only": 1
},
{
"collapsible": 1,
"fieldname": "section_addresses",
"fieldtype": "Section Break",
"label": "Address and Contact"
"label": "Supplier Address"
},
{
"fieldname": "supplier_address",
@@ -518,11 +526,12 @@
},
{
"fieldname": "sec_warehouse",
"fieldtype": "Section Break"
"fieldtype": "Section Break",
"hide_border": 1,
"label": "Items"
},
{
"depends_on": "update_stock",
"description": "Sets 'Accepted Warehouse' in each row of the items table.",
"fieldname": "set_warehouse",
"fieldtype": "Link",
"label": "Set Accepted Warehouse",
@@ -531,7 +540,6 @@
},
{
"depends_on": "update_stock",
"description": "Warehouse where you are maintaining stock of rejected items",
"fieldname": "rejected_warehouse",
"fieldtype": "Link",
"label": "Rejected Warehouse",
@@ -554,6 +562,7 @@
{
"fieldname": "items_section",
"fieldtype": "Section Break",
"hide_border": 1,
"oldfieldtype": "Section Break",
"options": "fa fa-shopping-cart"
},
@@ -581,6 +590,7 @@
"reqd": 1
},
{
"collapsible": 1,
"fieldname": "pricing_rule_details",
"fieldtype": "Section Break",
"label": "Pricing Rules"
@@ -593,6 +603,7 @@
"read_only": 1
},
{
"collapsible": 1,
"collapsible_depends_on": "supplied_items",
"fieldname": "raw_materials_supplied",
"fieldtype": "Section Break",
@@ -656,6 +667,7 @@
"read_only": 1
},
{
"depends_on": "total_net_weight",
"fieldname": "total_net_weight",
"fieldtype": "Float",
"label": "Total Net Weight",
@@ -665,6 +677,8 @@
{
"fieldname": "taxes_section",
"fieldtype": "Section Break",
"hide_border": 1,
"label": "Taxes and Charges",
"oldfieldtype": "Section Break",
"options": "fa fa-money"
},
@@ -688,7 +702,8 @@
},
{
"fieldname": "section_break_51",
"fieldtype": "Section Break"
"fieldtype": "Section Break",
"hide_border": 1
},
{
"fieldname": "taxes_and_charges",
@@ -792,7 +807,6 @@
},
{
"collapsible": 1,
"collapsible_depends_on": "discount_amount",
"fieldname": "section_break_44",
"fieldtype": "Section Break",
"label": "Additional Discount"
@@ -832,7 +846,8 @@
},
{
"fieldname": "section_break_49",
"fieldtype": "Section Break"
"fieldtype": "Section Break",
"label": "Totals"
},
{
"fieldname": "base_grand_total",
@@ -1003,8 +1018,6 @@
},
{
"collapsible": 1,
"collapsible_depends_on": "write_off_amount",
"depends_on": "grand_total",
"fieldname": "write_off",
"fieldtype": "Section Break",
"label": "Write Off"
@@ -1081,7 +1094,6 @@
"print_hide": 1
},
{
"collapsible": 1,
"collapsible_depends_on": "eval:(!doc.is_return)",
"fieldname": "payment_schedule_section",
"fieldtype": "Section Break",
@@ -1102,8 +1114,6 @@
"print_hide": 1
},
{
"collapsible": 1,
"collapsible_depends_on": "terms",
"fieldname": "terms_section_break",
"fieldtype": "Section Break",
"label": "Terms and Conditions",
@@ -1119,13 +1129,13 @@
{
"fieldname": "terms",
"fieldtype": "Text Editor",
"label": "Terms and Conditions1"
"label": "Terms and Conditions"
},
{
"collapsible": 1,
"fieldname": "printing_settings",
"fieldtype": "Section Break",
"label": "Printing Settings"
"label": "Print Settings"
},
{
"allow_on_submit": 1,
@@ -1166,15 +1176,6 @@
"print_hide": 1,
"read_only": 1
},
{
"collapsible": 1,
"fieldname": "more_info",
"fieldtype": "Section Break",
"label": "More Information",
"oldfieldtype": "Section Break",
"options": "fa fa-file-text",
"print_hide": 1
},
{
"default": "0",
"fetch_from": "supplier.is_internal_supplier",
@@ -1260,7 +1261,7 @@
"collapsible": 1,
"fieldname": "subscription_section",
"fieldtype": "Section Break",
"label": "Subscription Section",
"label": "Subscription",
"print_hide": 1
},
{
@@ -1339,7 +1340,7 @@
},
{
"depends_on": "eval:doc.is_internal_supplier",
"description": "Unrealized Profit / Loss account for intra-company transfers",
"description": "Unrealized Profit/Loss account for intra-company transfers",
"fieldname": "unrealized_profit_loss_account",
"fieldtype": "Link",
"label": "Unrealized Profit / Loss Account",
@@ -1356,7 +1357,6 @@
},
{
"depends_on": "eval:doc.update_stock && doc.is_internal_supplier",
"description": "Sets 'From Warehouse' in each row of the items table.",
"fieldname": "set_from_warehouse",
"fieldtype": "Link",
"label": "Set From Warehouse",
@@ -1422,6 +1422,7 @@
"read_only": 1
},
{
"collapsible_depends_on": "tax_withheld_vouchers",
"fieldname": "tax_withheld_vouchers_section",
"fieldtype": "Section Break",
"label": "Tax Withheld Vouchers"
@@ -1430,15 +1431,95 @@
"fieldname": "tax_withheld_vouchers",
"fieldtype": "Table",
"label": "Tax Withheld Vouchers",
"no_copy": 1,
"options": "Tax Withheld Vouchers",
"read_only": 1
},
{
"fieldname": "payments_tab",
"fieldtype": "Tab Break",
"label": "Payments"
},
{
"fieldname": "address_and_contact_tab",
"fieldtype": "Tab Break",
"label": "Address & Contact"
},
{
"fieldname": "terms_tab",
"fieldtype": "Tab Break",
"label": "Terms"
},
{
"fieldname": "more_info_tab",
"fieldtype": "Tab Break",
"label": "More Info"
},
{
"fieldname": "connections_tab",
"fieldtype": "Tab Break",
"label": "Connections",
"show_dashboard": 1
},
{
"fieldname": "column_break_6",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_38",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_50",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_58",
"fieldtype": "Column Break"
},
{
"fieldname": "company_shipping_address_section",
"fieldtype": "Section Break",
"label": "Company Shipping Address"
},
{
"fieldname": "column_break_126",
"fieldtype": "Column Break"
},
{
"fieldname": "company_billing_address_section",
"fieldtype": "Section Break",
"label": "Company Billing Address"
},
{
"fieldname": "column_break_130",
"fieldtype": "Column Break"
},
{
"collapsible": 1,
"fieldname": "status_section",
"fieldtype": "Section Break",
"label": "Status"
},
{
"fieldname": "column_break_177",
"fieldtype": "Column Break"
},
{
"collapsible": 1,
"fieldname": "additional_info_section",
"fieldtype": "Section Break",
"label": "Additional Info",
"oldfieldtype": "Section Break",
"options": "fa fa-file-text",
"print_hide": 1
}
],
"icon": "fa fa-file-text",
"idx": 204,
"is_submittable": 1,
"links": [],
"modified": "2022-09-27 11:07:55.766844",
"modified": "2022-10-11 13:04:44.304389",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Purchase Invoice",

View File

@@ -705,6 +705,10 @@ class PurchaseInvoice(BuyingController):
)
)
credit_amount = item.base_net_amount
if self.is_internal_supplier and item.valuation_rate:
credit_amount = flt(item.valuation_rate * item.stock_qty)
# Intentionally passed negative debit amount to avoid incorrect GL Entry validation
gl_entries.append(
self.get_gl_dict(
@@ -714,7 +718,7 @@ class PurchaseInvoice(BuyingController):
"cost_center": item.cost_center,
"project": item.project or self.project,
"remarks": self.get("remarks") or _("Accounting Entry for Stock"),
"debit": -1 * flt(item.base_net_amount, item.precision("base_net_amount")),
"debit": -1 * flt(credit_amount, item.precision("base_net_amount")),
},
warehouse_account[item.from_warehouse]["account_currency"],
item=item,

View File

@@ -711,6 +711,7 @@
"label": "Valuation Rate",
"no_copy": 1,
"options": "Company:company:default_currency",
"precision": "6",
"print_hide": 1,
"read_only": 1
},
@@ -870,7 +871,7 @@
"idx": 1,
"istable": 1,
"links": [],
"modified": "2022-09-27 10:54:23.980713",
"modified": "2022-10-12 03:37:29.032732",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Purchase Invoice Item",

View File

@@ -12,44 +12,29 @@
"customer",
"customer_name",
"tax_id",
"pos_profile",
"is_pos",
"is_consolidated",
"is_return",
"is_debit_note",
"update_billed_amount_in_sales_order",
"column_break1",
"company",
"company_tax_id",
"column_break1",
"posting_date",
"posting_time",
"set_posting_time",
"due_date",
"column_break_14",
"is_pos",
"pos_profile",
"is_consolidated",
"is_return",
"return_against",
"update_billed_amount_in_sales_order",
"is_debit_note",
"amended_from",
"accounting_dimensions_section",
"project",
"dimension_col_break",
"cost_center",
"customer_po_details",
"po_no",
"column_break_23",
"po_date",
"address_and_contact",
"customer_address",
"address_display",
"contact_person",
"contact_display",
"contact_mobile",
"contact_email",
"territory",
"col_break4",
"shipping_address_name",
"shipping_address",
"company_address",
"company_address_display",
"dispatch_address_name",
"dispatch_address",
"dimension_col_break",
"project",
"column_break_27",
"campaign",
"source",
"currency_and_price_list",
"currency",
"conversion_rate",
@@ -58,60 +43,35 @@
"price_list_currency",
"plc_conversion_rate",
"ignore_pricing_rule",
"sec_warehouse",
"set_warehouse",
"column_break_55",
"set_target_warehouse",
"items_section",
"update_stock",
"scan_barcode",
"update_stock",
"column_break_39",
"set_warehouse",
"set_target_warehouse",
"section_break_42",
"items",
"pricing_rule_details",
"pricing_rules",
"packing_list",
"packed_items",
"product_bundle_help",
"time_sheet_list",
"timesheets",
"total_billing_amount",
"total_billing_hours",
"section_break_30",
"total_qty",
"total_net_weight",
"column_break_32",
"base_total",
"base_net_total",
"column_break_32",
"total_net_weight",
"column_break_52",
"total",
"net_total",
"taxes_section",
"taxes_and_charges",
"column_break_38",
"shipping_rule",
"column_break_55",
"tax_category",
"section_break_40",
"taxes",
"sec_tax_breakup",
"other_charges_calculation",
"section_break_43",
"base_total_taxes_and_charges",
"column_break_47",
"total_taxes_and_charges",
"loyalty_points_redemption",
"loyalty_points",
"loyalty_amount",
"redeem_loyalty_points",
"column_break_77",
"loyalty_program",
"loyalty_redemption_account",
"loyalty_redemption_cost_center",
"section_break_49",
"apply_discount_on",
"is_cash_or_non_trade_discount",
"base_discount_amount",
"additional_discount_account",
"column_break_51",
"additional_discount_percentage",
"discount_amount",
"totals",
"base_grand_total",
"base_rounding_adjustment",
@@ -125,21 +85,28 @@
"total_advance",
"outstanding_amount",
"disable_rounded_total",
"column_break4",
"write_off_amount",
"base_write_off_amount",
"write_off_outstanding_amount_automatically",
"column_break_74",
"write_off_account",
"write_off_cost_center",
"advances_section",
"allocate_advances_automatically",
"get_advances",
"advances",
"payment_schedule_section",
"ignore_default_payment_terms_template",
"payment_terms_template",
"payment_schedule",
"section_break_49",
"apply_discount_on",
"base_discount_amount",
"is_cash_or_non_trade_discount",
"additional_discount_account",
"column_break_51",
"additional_discount_percentage",
"discount_amount",
"sec_tax_breakup",
"other_charges_calculation",
"pricing_rule_details",
"pricing_rules",
"packing_list",
"packed_items",
"product_bundle_help",
"time_sheet_list",
"timesheets",
"section_break_104",
"total_billing_hours",
"column_break_106",
"total_billing_amount",
"payments_tab",
"payments_section",
"cash_bank_account",
"payments",
@@ -152,47 +119,95 @@
"column_break_90",
"change_amount",
"account_for_change_amount",
"advances_section",
"allocate_advances_automatically",
"get_advances",
"advances",
"write_off_section",
"write_off_amount",
"base_write_off_amount",
"write_off_outstanding_amount_automatically",
"column_break_74",
"write_off_account",
"write_off_cost_center",
"loyalty_points_redemption",
"redeem_loyalty_points",
"loyalty_points",
"loyalty_amount",
"column_break_77",
"loyalty_program",
"loyalty_redemption_account",
"loyalty_redemption_cost_center",
"contact_and_address_tab",
"address_and_contact",
"customer_address",
"address_display",
"col_break4",
"contact_person",
"contact_display",
"contact_mobile",
"contact_email",
"territory",
"shipping_address_section",
"shipping_address_name",
"shipping_address",
"shipping_addr_col_break",
"dispatch_address_name",
"dispatch_address",
"company_address_section",
"company_address",
"company_addr_col_break",
"company_address_display",
"terms_tab",
"payment_schedule_section",
"ignore_default_payment_terms_template",
"payment_terms_template",
"payment_schedule",
"terms_section_break",
"tc_name",
"terms",
"edit_printing_settings",
"letter_head",
"group_same_items",
"select_print_heading",
"column_break_84",
"language",
"more_information",
"status",
"inter_company_invoice_reference",
"represents_company",
"customer_group",
"campaign",
"col_break23",
"is_internal_customer",
"is_discounted",
"source",
"more_info_tab",
"customer_po_details",
"po_no",
"column_break_23",
"po_date",
"more_info",
"debit_to",
"party_account_currency",
"is_opening",
"column_break8",
"unrealized_profit_loss_account",
"remarks",
"against_income_account",
"sales_team_section_break",
"sales_partner",
"column_break10",
"amount_eligible_for_commission",
"column_break10",
"commission_rate",
"total_commission",
"section_break2",
"sales_team",
"edit_printing_settings",
"letter_head",
"group_same_items",
"column_break_84",
"select_print_heading",
"language",
"subscription_section",
"from_date",
"to_date",
"column_break_140",
"auto_repeat",
"column_break_140",
"to_date",
"update_auto_repeat_reference",
"against_income_account"
"more_information",
"status",
"inter_company_invoice_reference",
"represents_company",
"customer_group",
"col_break23",
"is_internal_customer",
"is_discounted",
"remarks",
"connections_tab"
],
"fields": [
{
@@ -453,12 +468,11 @@
"label": "Customer's Purchase Order Date"
},
{
"collapsible": 1,
"fieldname": "address_and_contact",
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Address and Contact"
"label": "Billing Address"
},
{
"fieldname": "customer_address",
@@ -560,7 +574,6 @@
{
"fieldname": "company_address_display",
"fieldtype": "Small Text",
"hidden": 1,
"hide_days": 1,
"hide_seconds": 1,
"label": "Company Address",
@@ -651,13 +664,6 @@
"label": "Ignore Pricing Rule",
"print_hide": 1
},
{
"fieldname": "sec_warehouse",
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Warehouse"
},
{
"depends_on": "update_stock",
"fieldname": "set_warehouse",
@@ -671,6 +677,7 @@
{
"fieldname": "items_section",
"fieldtype": "Section Break",
"hide_border": 1,
"hide_days": 1,
"hide_seconds": 1,
"label": "Items",
@@ -702,7 +709,6 @@
"fieldtype": "Table",
"hide_days": 1,
"hide_seconds": 1,
"label": "Items",
"oldfieldname": "entries",
"oldfieldtype": "Table",
"options": "Sales Invoice Item",
@@ -755,9 +761,10 @@
{
"collapsible": 1,
"collapsible_depends_on": "eval:doc.total_billing_amount > 0",
"depends_on": "eval: !doc.is_return",
"depends_on": "eval:!doc.is_return",
"fieldname": "time_sheet_list",
"fieldtype": "Section Break",
"hide_border": 1,
"hide_days": 1,
"hide_seconds": 1,
"label": "Time Sheet List"
@@ -845,6 +852,7 @@
"read_only": 1
},
{
"depends_on": "total_net_weight",
"fieldname": "total_net_weight",
"fieldtype": "Float",
"hide_days": 1,
@@ -856,8 +864,10 @@
{
"fieldname": "taxes_section",
"fieldtype": "Section Break",
"hide_border": 1,
"hide_days": 1,
"hide_seconds": 1,
"label": "Taxes and Charges",
"oldfieldtype": "Section Break",
"options": "fa fa-money"
},
@@ -900,6 +910,7 @@
{
"fieldname": "section_break_40",
"fieldtype": "Section Break",
"hide_border": 1,
"hide_days": 1,
"hide_seconds": 1
},
@@ -908,7 +919,6 @@
"fieldtype": "Table",
"hide_days": 1,
"hide_seconds": 1,
"label": "Sales Taxes and Charges",
"oldfieldname": "other_charges",
"oldfieldtype": "Table",
"options": "Sales Taxes and Charges"
@@ -1046,7 +1056,6 @@
},
{
"collapsible": 1,
"collapsible_depends_on": "discount_amount",
"fieldname": "section_break_49",
"fieldtype": "Section Break",
"hide_days": 1,
@@ -1102,6 +1111,7 @@
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Totals",
"oldfieldtype": "Section Break",
"options": "fa fa-money",
"print_hide": 1
@@ -1283,8 +1293,6 @@
"print_hide": 1
},
{
"collapsible": 1,
"collapsible_depends_on": "eval:(!doc.is_pos && !doc.is_return)",
"fieldname": "payment_schedule_section",
"fieldtype": "Section Break",
"hide_days": 1,
@@ -1314,7 +1322,9 @@
"print_hide": 1
},
{
"depends_on": "eval:doc.is_pos===1||(doc.advances && doc.advances.length>0)",
"collapsible": 1,
"collapsible_depends_on": "eval:!doc.is_pos",
"depends_on": "eval:doc.is_pos===1",
"fieldname": "payments_section",
"fieldtype": "Section Break",
"hide_days": 1,
@@ -1352,6 +1362,7 @@
"hide_seconds": 1
},
{
"depends_on": "eval: doc.is_pos || doc.redeem_loyalty_points",
"fieldname": "base_paid_amount",
"fieldtype": "Currency",
"hide_days": 1,
@@ -1383,10 +1394,13 @@
"read_only": 1
},
{
"collapsible": 1,
"depends_on": "is_pos",
"fieldname": "section_break_88",
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1
"hide_seconds": 1,
"label": "Changes"
},
{
"depends_on": "is_pos",
@@ -1427,17 +1441,6 @@
"options": "Account",
"print_hide": 1
},
{
"collapsible": 1,
"collapsible_depends_on": "write_off_amount",
"depends_on": "grand_total",
"fieldname": "column_break4",
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Write Off",
"width": "50%"
},
{
"fieldname": "write_off_amount",
"fieldtype": "Currency",
@@ -1495,8 +1498,6 @@
"print_hide": 1
},
{
"collapsible": 1,
"collapsible_depends_on": "terms",
"fieldname": "terms_section_break",
"fieldtype": "Section Break",
"hide_days": 1,
@@ -1530,7 +1531,7 @@
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Printing Settings"
"label": "Print Settings"
},
{
"allow_on_submit": 1,
@@ -1591,7 +1592,7 @@
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "More Information"
"label": "Additional Info"
},
{
"fieldname": "inter_company_invoice_reference",
@@ -1814,7 +1815,7 @@
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Subscription Section"
"label": "Subscription"
},
{
"allow_on_submit": 1,
@@ -1935,10 +1936,6 @@
"options": "Company",
"read_only": 1
},
{
"fieldname": "column_break_55",
"fieldtype": "Column Break"
},
{
"depends_on": "eval: doc.is_internal_customer && doc.update_stock",
"fieldname": "set_target_warehouse",
@@ -2009,6 +2006,97 @@
"fieldname": "is_cash_or_non_trade_discount",
"fieldtype": "Check",
"label": "Is Cash or Non Trade Discount"
},
{
"fieldname": "contact_and_address_tab",
"fieldtype": "Tab Break",
"label": "Contact & Address"
},
{
"fieldname": "payments_tab",
"fieldtype": "Tab Break",
"label": "Payments"
},
{
"fieldname": "terms_tab",
"fieldtype": "Tab Break",
"label": "Terms"
},
{
"fieldname": "more_info_tab",
"fieldtype": "Tab Break",
"label": "More Info"
},
{
"fieldname": "connections_tab",
"fieldtype": "Tab Break",
"label": "Connections",
"show_dashboard": 1
},
{
"fieldname": "column_break_14",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_39",
"fieldtype": "Column Break"
},
{
"fieldname": "section_break_42",
"fieldtype": "Section Break",
"hide_border": 1,
"hide_days": 1,
"hide_seconds": 1
},
{
"fieldname": "column_break_55",
"fieldtype": "Column Break"
},
{
"fieldname": "shipping_address_section",
"fieldtype": "Section Break",
"label": "Shipping Address"
},
{
"fieldname": "company_address_section",
"fieldtype": "Section Break",
"label": "Company Address"
},
{
"fieldname": "shipping_addr_col_break",
"fieldtype": "Column Break"
},
{
"fieldname": "company_addr_col_break",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_27",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_52",
"fieldtype": "Column Break"
},
{
"depends_on": "eval:(!doc.is_return && doc.total_billing_amount > 0)",
"fieldname": "section_break_104",
"fieldtype": "Section Break"
},
{
"fieldname": "column_break_106",
"fieldtype": "Column Break"
},
{
"collapsible": 1,
"collapsible_depends_on": "write_off_amount",
"depends_on": "grand_total",
"fieldname": "write_off_section",
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Write Off",
"width": "50%"
}
],
"icon": "fa fa-file-text",
@@ -2021,7 +2109,7 @@
"link_fieldname": "consolidated_invoice"
}
],
"modified": "2022-09-16 17:44:22.227332",
"modified": "2022-10-11 13:07:36.488095",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Sales Invoice",

View File

@@ -32,10 +32,20 @@ from erpnext.stock.doctype.stock_entry.test_stock_entry import (
get_qty_after_transaction,
make_stock_entry,
)
from erpnext.stock.utils import get_incoming_rate
from erpnext.stock.doctype.stock_reconciliation.test_stock_reconciliation import (
create_stock_reconciliation,
)
from erpnext.stock.utils import get_incoming_rate, get_stock_balance
class TestSalesInvoice(unittest.TestCase):
def setUp(self):
from erpnext.stock.doctype.stock_ledger_entry.test_stock_ledger_entry import create_items
create_items(["_Test Internal Transfer Item"], uoms=[{"uom": "Box", "conversion_factor": 10}])
create_internal_parties()
setup_accounts()
def make(self):
w = frappe.copy_doc(test_records[0])
w.is_pos = 0
@@ -1705,7 +1715,7 @@ class TestSalesInvoice(unittest.TestCase):
si.save()
self.assertEqual(si.get("items")[0].rate, flt((price_list_rate * 25) / 100 + price_list_rate))
def test_outstanding_amount_after_advance_jv_cancelation(self):
def test_outstanding_amount_after_advance_jv_cancellation(self):
from erpnext.accounts.doctype.journal_entry.test_journal_entry import (
test_records as jv_test_records,
)
@@ -1749,7 +1759,7 @@ class TestSalesInvoice(unittest.TestCase):
flt(si.rounded_total + si.total_advance, si.precision("outstanding_amount")),
)
def test_outstanding_amount_after_advance_payment_entry_cancelation(self):
def test_outstanding_amount_after_advance_payment_entry_cancellation(self):
pe = frappe.get_doc(
{
"doctype": "Payment Entry",
@@ -2367,29 +2377,6 @@ class TestSalesInvoice(unittest.TestCase):
acc_settings.save()
def test_inter_company_transaction(self):
from erpnext.selling.doctype.customer.test_customer import create_internal_customer
create_internal_customer(
customer_name="_Test Internal Customer",
represents_company="_Test Company 1",
allowed_to_interact_with="Wind Power LLC",
)
if not frappe.db.exists("Supplier", "_Test Internal Supplier"):
supplier = frappe.get_doc(
{
"supplier_group": "_Test Supplier Group",
"supplier_name": "_Test Internal Supplier",
"doctype": "Supplier",
"is_internal_supplier": 1,
"represents_company": "Wind Power LLC",
}
)
supplier.append("companies", {"company": "_Test Company 1"})
supplier.insert()
si = create_sales_invoice(
company="Wind Power LLC",
customer="_Test Internal Customer",
@@ -2440,38 +2427,6 @@ class TestSalesInvoice(unittest.TestCase):
"Expenses Included In Valuation - _TC1",
)
if not frappe.db.exists("Customer", "_Test Internal Customer"):
customer = frappe.get_doc(
{
"customer_group": "_Test Customer Group",
"customer_name": "_Test Internal Customer",
"customer_type": "Individual",
"doctype": "Customer",
"territory": "_Test Territory",
"is_internal_customer": 1,
"represents_company": "_Test Company 1",
}
)
customer.append("companies", {"company": "Wind Power LLC"})
customer.insert()
if not frappe.db.exists("Supplier", "_Test Internal Supplier"):
supplier = frappe.get_doc(
{
"supplier_group": "_Test Supplier Group",
"supplier_name": "_Test Internal Supplier",
"doctype": "Supplier",
"is_internal_supplier": 1,
"represents_company": "Wind Power LLC",
}
)
supplier.append("companies", {"company": "_Test Company 1"})
supplier.insert()
# begin test
si = create_sales_invoice(
company="Wind Power LLC",
@@ -2541,34 +2496,9 @@ class TestSalesInvoice(unittest.TestCase):
se.cancel()
def test_internal_transfer_gl_entry(self):
## Create internal transfer account
from erpnext.selling.doctype.customer.test_customer import create_internal_customer
account = create_account(
account_name="Unrealized Profit",
parent_account="Current Liabilities - TCP1",
company="_Test Company with perpetual inventory",
)
frappe.db.set_value(
"Company", "_Test Company with perpetual inventory", "unrealized_profit_loss_account", account
)
customer = create_internal_customer(
"_Test Internal Customer 2",
"_Test Company with perpetual inventory",
"_Test Company with perpetual inventory",
)
create_internal_supplier(
"_Test Internal Supplier 2",
"_Test Company with perpetual inventory",
"_Test Company with perpetual inventory",
)
si = create_sales_invoice(
company="_Test Company with perpetual inventory",
customer=customer,
customer="_Test Internal Customer 2",
debit_to="Debtors - TCP1",
warehouse="Stores - TCP1",
income_account="Sales - TCP1",
@@ -2582,7 +2512,7 @@ class TestSalesInvoice(unittest.TestCase):
si.update_stock = 1
si.items[0].target_warehouse = "Work In Progress - TCP1"
# Add stock to stores for succesful stock transfer
# Add stock to stores for successful stock transfer
make_stock_entry(
target="Stores - TCP1", company="_Test Company with perpetual inventory", qty=1, basic_rate=100
)
@@ -2638,6 +2568,77 @@ class TestSalesInvoice(unittest.TestCase):
check_gl_entries(self, target_doc.name, pi_gl_entries, add_days(nowdate(), -1))
def test_internal_transfer_gl_precision_issues(self):
# Make a stock queue of an item with two valuations
# Remove all existing stock for this
if get_stock_balance("_Test Internal Transfer Item", "Stores - TCP1", "2022-04-10"):
create_stock_reconciliation(
item_code="_Test Internal Transfer Item",
warehouse="Stores - TCP1",
qty=0,
rate=0,
company="_Test Company with perpetual inventory",
expense_account="Stock Adjustment - TCP1"
if frappe.get_all("Stock Ledger Entry")
else "Temporary Opening - TCP1",
posting_date="2020-04-10",
posting_time="14:00",
)
make_stock_entry(
item_code="_Test Internal Transfer Item",
target="Stores - TCP1",
qty=9000000,
basic_rate=52.0,
posting_date="2020-04-10",
posting_time="14:00",
)
make_stock_entry(
item_code="_Test Internal Transfer Item",
target="Stores - TCP1",
qty=60000000,
basic_rate=52.349777,
posting_date="2020-04-10",
posting_time="14:00",
)
# Make an internal transfer Sales Invoice Stock in non stock uom to check
# for rounding errors while converting to stock uom
si = create_sales_invoice(
company="_Test Company with perpetual inventory",
customer="_Test Internal Customer 2",
item_code="_Test Internal Transfer Item",
qty=5000000,
uom="Box",
debit_to="Debtors - TCP1",
warehouse="Stores - TCP1",
income_account="Sales - TCP1",
expense_account="Cost of Goods Sold - TCP1",
cost_center="Main - TCP1",
currency="INR",
do_not_save=1,
)
# Check GL Entries with precision
si.update_stock = 1
si.items[0].target_warehouse = "Work In Progress - TCP1"
si.items[0].conversion_factor = 10
si.save()
si.submit()
# Check if adjustment entry is created
self.assertTrue(
frappe.db.exists(
"GL Entry",
{
"voucher_type": "Sales Invoice",
"voucher_no": si.name,
"remarks": "Rounding gain/loss Entry for Stock Transfer",
},
)
)
def test_item_tax_net_range(self):
item = create_item("T Shirt")
@@ -3077,7 +3078,7 @@ class TestSalesInvoice(unittest.TestCase):
[deferred_account, 2022.47, 0.0, "2019-03-15"],
]
gl_entries = gl_entries = frappe.db.sql(
gl_entries = frappe.db.sql(
"""select account, debit, credit, posting_date
from `tabGL Entry`
where voucher_type='Journal Entry' and voucher_detail_no=%s and posting_date <= %s
@@ -3306,6 +3307,7 @@ def create_sales_invoice(**args):
"item_name": args.item_name or "_Test Item",
"description": args.description or "_Test Item",
"warehouse": args.warehouse or "_Test Warehouse - _TC",
"target_warehouse": args.target_warehouse,
"qty": args.qty or 1,
"uom": args.uom or "Nos",
"stock_uom": args.uom or "Nos",
@@ -3431,6 +3433,34 @@ def get_taxes_and_charges():
]
def create_internal_parties():
from erpnext.selling.doctype.customer.test_customer import create_internal_customer
create_internal_customer(
customer_name="_Test Internal Customer",
represents_company="_Test Company 1",
allowed_to_interact_with="Wind Power LLC",
)
create_internal_customer(
customer_name="_Test Internal Customer 2",
represents_company="_Test Company with perpetual inventory",
allowed_to_interact_with="_Test Company with perpetual inventory",
)
create_internal_supplier(
supplier_name="_Test Internal Supplier",
represents_company="Wind Power LLC",
allowed_to_interact_with="_Test Company 1",
)
create_internal_supplier(
supplier_name="_Test Internal Supplier 2",
represents_company="_Test Company with perpetual inventory",
allowed_to_interact_with="_Test Company with perpetual inventory",
)
def create_internal_supplier(supplier_name, represents_company, allowed_to_interact_with):
if not frappe.db.exists("Supplier", supplier_name):
supplier = frappe.get_doc(
@@ -3453,6 +3483,19 @@ def create_internal_supplier(supplier_name, represents_company, allowed_to_inter
return supplier_name
def setup_accounts():
## Create internal transfer account
account = create_account(
account_name="Unrealized Profit",
parent_account="Current Liabilities - TCP1",
company="_Test Company with perpetual inventory",
)
frappe.db.set_value(
"Company", "_Test Company with perpetual inventory", "unrealized_profit_loss_account", account
)
def add_taxes(doc):
doc.append(
"taxes",

View File

@@ -820,6 +820,7 @@
"label": "Incoming Rate (Costing)",
"no_copy": 1,
"options": "Company:company:default_currency",
"precision": "6",
"print_hide": 1
},
{
@@ -875,7 +876,7 @@
"idx": 1,
"istable": 1,
"links": [],
"modified": "2022-09-06 14:17:43.394309",
"modified": "2022-10-10 20:57:38.340026",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Sales Invoice Item",

View File

@@ -249,6 +249,9 @@ def get_tax_amount(party_type, parties, inv, tax_details, posting_date, pan_no=N
)
else:
tax_amount = net_total * tax_details.rate / 100 if net_total > 0 else 0
# once tds is deducted, not need to add vouchers in the invoice
voucher_wise_amount = {}
else:
tax_amount = get_tds_amount(ldc, parties, inv, tax_details, tax_deducted, vouchers)
@@ -425,7 +428,10 @@ def get_tds_amount(ldc, parties, inv, tax_details, tax_deducted, vouchers):
):
# Get net total again as TDS is calculated on net total
# Grand is used to just check for threshold breach
net_total = frappe.db.get_value("Purchase Invoice", invoice_filters, "sum(net_total)") or 0.0
net_total = 0
if vouchers:
net_total = frappe.db.get_value("Purchase Invoice", invoice_filters, "sum(net_total)")
net_total += inv.net_total
supp_credit_amt = net_total - cumulative_threshold

View File

@@ -648,6 +648,16 @@ def unlink_ref_doc_from_payment_entries(ref_doc):
(now(), frappe.session.user, ref_doc.doctype, ref_doc.name),
)
ple = qb.DocType("Payment Ledger Entry")
qb.update(ple).set(ple.against_voucher_type, ple.voucher_type).set(
ple.against_voucher_no, ple.voucher_no
).set(ple.modified, now()).set(ple.modified_by, frappe.session.user).where(
(ple.against_voucher_type == ref_doc.doctype)
& (ple.against_voucher_no == ref_doc.name)
& (ple.delinked == 0)
).run()
if ref_doc.doctype in ("Sales Invoice", "Purchase Invoice"):
ref_doc.set("advances", [])

View File

@@ -12,43 +12,24 @@
"title",
"naming_series",
"supplier",
"get_items_from_open_material_requests",
"supplier_name",
"order_confirmation_no",
"order_confirmation_date",
"get_items_from_open_material_requests",
"column_break_7",
"transaction_date",
"schedule_date",
"column_break1",
"company",
"apply_tds",
"tax_withholding_category",
"is_subcontracted",
"supplier_warehouse",
"column_break1",
"company",
"transaction_date",
"schedule_date",
"order_confirmation_no",
"order_confirmation_date",
"amended_from",
"accounting_dimensions_section",
"cost_center",
"dimension_col_break",
"project",
"drop_ship",
"customer",
"customer_name",
"column_break_19",
"customer_contact_person",
"customer_contact_display",
"customer_contact_mobile",
"customer_contact_email",
"section_addresses",
"supplier_address",
"address_display",
"contact_person",
"contact_display",
"contact_mobile",
"contact_email",
"col_break_address",
"shipping_address",
"shipping_address_display",
"billing_address",
"billing_address_display",
"currency_and_price_list",
"currency",
"conversion_rate",
@@ -57,7 +38,6 @@
"price_list_currency",
"plc_conversion_rate",
"ignore_pricing_rule",
"section_break_45",
"before_items_section",
"scan_barcode",
"set_from_warehouse",
@@ -67,10 +47,11 @@
"items",
"sb_last_purchase",
"total_qty",
"total_net_weight",
"column_break_40",
"base_total",
"base_net_total",
"column_break_26",
"total_net_weight",
"total",
"net_total",
"section_break_48",
@@ -79,14 +60,13 @@
"set_reserve_warehouse",
"supplied_items",
"taxes_section",
"taxes_and_charges",
"column_break_53",
"tax_category",
"column_break_50",
"shipping_rule",
"section_break_52",
"taxes_and_charges",
"taxes",
"sec_tax_breakup",
"other_charges_calculation",
"totals",
"base_taxes_and_charges_added",
"base_taxes_and_charges_deducted",
@@ -95,12 +75,6 @@
"taxes_and_charges_added",
"taxes_and_charges_deducted",
"total_taxes_and_charges",
"discount_section",
"apply_discount_on",
"base_discount_amount",
"column_break_45",
"additional_discount_percentage",
"discount_amount",
"totals_section",
"base_grand_total",
"base_rounding_adjustment",
@@ -113,37 +87,73 @@
"disable_rounded_total",
"in_words",
"advance_paid",
"discount_section",
"apply_discount_on",
"base_discount_amount",
"column_break_45",
"additional_discount_percentage",
"discount_amount",
"sec_tax_breakup",
"other_charges_calculation",
"address_and_contact_tab",
"section_addresses",
"supplier_address",
"address_display",
"col_break_address",
"contact_person",
"contact_display",
"contact_mobile",
"contact_email",
"company_shipping_address_section",
"shipping_address",
"column_break_99",
"shipping_address_display",
"company_billing_address_section",
"billing_address",
"column_break_103",
"billing_address_display",
"drop_ship",
"customer",
"customer_name",
"column_break_19",
"customer_contact_person",
"customer_contact_display",
"customer_contact_mobile",
"customer_contact_email",
"terms_tab",
"payment_schedule_section",
"payment_terms_template",
"payment_schedule",
"terms_section_break",
"tc_name",
"terms",
"more_info_tab",
"tracking_section",
"status",
"column_break_75",
"per_billed",
"per_received",
"terms_section_break",
"tc_name",
"terms",
"column_break5",
"letter_head",
"select_print_heading",
"column_break_86",
"language",
"group_same_items",
"column_break_86",
"select_print_heading",
"language",
"subscription_section",
"from_date",
"to_date",
"column_break_97",
"auto_repeat",
"update_auto_repeat_reference",
"more_info",
"additional_info_section",
"is_internal_supplier",
"represents_company",
"ref_sq",
"column_break_74",
"party_account_currency",
"is_internal_supplier",
"represents_company",
"inter_company_order_reference",
"is_old_subcontracting_flow"
"is_old_subcontracting_flow",
"dashboard"
],
"fields": [
{
@@ -267,8 +277,9 @@
"read_only": 1
},
{
"depends_on": "eval:doc.customer",
"fieldname": "drop_ship",
"fieldtype": "Section Break",
"fieldtype": "Tab Break",
"label": "Drop Ship"
},
{
@@ -299,7 +310,6 @@
{
"fieldname": "customer_contact_display",
"fieldtype": "Small Text",
"hidden": 1,
"label": "Customer Contact",
"print_hide": 1
},
@@ -319,10 +329,9 @@
"print_hide": 1
},
{
"collapsible": 1,
"fieldname": "section_addresses",
"fieldtype": "Section Break",
"label": "Address and Contact"
"label": "Supplier Address"
},
{
"fieldname": "supplier_address",
@@ -445,7 +454,6 @@
"print_hide": 1
},
{
"description": "Sets 'Warehouse' in each row of the Items table.",
"fieldname": "set_warehouse",
"fieldtype": "Link",
"label": "Set Target Warehouse",
@@ -483,7 +491,6 @@
"allow_bulk_edit": 1,
"fieldname": "items",
"fieldtype": "Table",
"label": "Items",
"oldfieldname": "po_details",
"oldfieldtype": "Table",
"options": "Purchase Order Item",
@@ -570,6 +577,7 @@
"read_only": 1
},
{
"depends_on": "total_net_weight",
"fieldname": "total_net_weight",
"fieldtype": "Float",
"label": "Total Net Weight",
@@ -579,6 +587,8 @@
{
"fieldname": "taxes_section",
"fieldtype": "Section Break",
"hide_border": 1,
"label": "Taxes and Charges",
"oldfieldtype": "Section Break",
"options": "fa fa-money"
},
@@ -633,7 +643,6 @@
{
"fieldname": "totals",
"fieldtype": "Section Break",
"label": "Taxes and Charges",
"oldfieldtype": "Section Break",
"options": "fa fa-money"
},
@@ -698,7 +707,6 @@
"read_only": 1
},
{
"depends_on": "total_taxes_and_charges",
"fieldname": "total_taxes_and_charges",
"fieldtype": "Currency",
"label": "Total Taxes and Charges",
@@ -708,7 +716,6 @@
},
{
"collapsible": 1,
"collapsible_depends_on": "apply_discount_on",
"fieldname": "discount_section",
"fieldtype": "Section Break",
"label": "Additional Discount"
@@ -773,7 +780,6 @@
"read_only": 1
},
{
"description": "In Words will be visible once you save the Purchase Order.",
"fieldname": "base_in_words",
"fieldtype": "Data",
"label": "In Words (Company Currency)",
@@ -851,7 +857,6 @@
"read_only": 1
},
{
"collapsible": 1,
"fieldname": "payment_schedule_section",
"fieldtype": "Section Break",
"label": "Payment Terms"
@@ -871,11 +876,10 @@
"print_hide": 1
},
{
"collapsible": 1,
"collapsible_depends_on": "terms",
"fieldname": "terms_section_break",
"fieldtype": "Section Break",
"label": "Terms and Conditions",
"label": "Terms & Conditions",
"oldfieldtype": "Section Break",
"options": "fa fa-legal"
},
@@ -895,13 +899,6 @@
"oldfieldname": "terms",
"oldfieldtype": "Text Editor"
},
{
"collapsible": 1,
"fieldname": "more_info",
"fieldtype": "Section Break",
"label": "More Information",
"oldfieldtype": "Section Break"
},
{
"default": "Draft",
"fieldname": "status",
@@ -1023,7 +1020,7 @@
"collapsible": 1,
"fieldname": "subscription_section",
"fieldtype": "Section Break",
"label": "Subscription Section"
"label": "Auto Repeat"
},
{
"allow_on_submit": 1,
@@ -1098,7 +1095,9 @@
},
{
"fieldname": "before_items_section",
"fieldtype": "Section Break"
"fieldtype": "Section Break",
"hide_border": 1,
"label": "Items"
},
{
"fieldname": "items_col_break",
@@ -1133,10 +1132,6 @@
"label": "Tax Withholding Category",
"options": "Tax Withholding Category"
},
{
"fieldname": "section_break_45",
"fieldtype": "Section Break"
},
{
"collapsible": 1,
"fieldname": "accounting_dimensions_section",
@@ -1173,13 +1168,71 @@
"fieldtype": "Link",
"label": "Set From Warehouse",
"options": "Warehouse"
},
{
"fieldname": "terms_tab",
"fieldtype": "Tab Break",
"label": "Terms"
},
{
"fieldname": "more_info_tab",
"fieldtype": "Tab Break",
"label": "More Info"
},
{
"fieldname": "dashboard",
"fieldtype": "Tab Break",
"label": "Dashboard",
"show_dashboard": 1
},
{
"fieldname": "column_break_7",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_40",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_53",
"fieldtype": "Column Break"
},
{
"fieldname": "address_and_contact_tab",
"fieldtype": "Tab Break",
"label": "Address & Contact"
},
{
"fieldname": "company_shipping_address_section",
"fieldtype": "Section Break",
"label": "Company Shipping Address"
},
{
"fieldname": "company_billing_address_section",
"fieldtype": "Section Break",
"label": "Company Billing Address"
},
{
"collapsible": 1,
"fieldname": "additional_info_section",
"fieldtype": "Section Break",
"label": "Additional Info",
"oldfieldtype": "Section Break"
},
{
"fieldname": "column_break_99",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_103",
"fieldtype": "Column Break"
}
],
"icon": "fa fa-file-text",
"idx": 105,
"is_submittable": 1,
"links": [],
"modified": "2022-09-16 17:45:04.954055",
"modified": "2022-10-11 13:01:41.674352",
"modified_by": "Administrator",
"module": "Buying",
"name": "Purchase Order",

View File

@@ -349,7 +349,7 @@ class PurchaseOrder(BuyingController):
update_linked_doc(self.doctype, self.name, self.inter_company_order_reference)
def on_cancel(self):
self.ignore_linked_doctypes = "Payment Ledger Entry"
self.ignore_linked_doctypes = ("GL Entry", "Payment Ledger Entry")
super(PurchaseOrder, self).on_cancel()
if self.is_against_so():

View File

@@ -13,19 +13,13 @@
"naming_series",
"supplier",
"supplier_name",
"column_break1",
"company",
"column_break1",
"status",
"transaction_date",
"valid_till",
"quotation_number",
"amended_from",
"address_section",
"supplier_address",
"contact_person",
"address_display",
"contact_display",
"contact_mobile",
"contact_email",
"currency_and_price_list",
"currency",
"conversion_rate",
@@ -36,25 +30,23 @@
"ignore_pricing_rule",
"items_section",
"items",
"pricing_rule_details",
"pricing_rules",
"section_break_22",
"total_qty",
"total_net_weight",
"column_break_26",
"base_total",
"base_net_total",
"column_break_24",
"total",
"net_total",
"total_net_weight",
"taxes_section",
"taxes_and_charges",
"column_break_34",
"tax_category",
"column_break_36",
"shipping_rule",
"section_break_38",
"taxes_and_charges",
"taxes",
"tax_breakup",
"other_charges_calculation",
"totals",
"base_taxes_and_charges_added",
"base_taxes_and_charges_deducted",
@@ -80,24 +72,36 @@
"rounded_total",
"in_words",
"disable_rounded_total",
"terms_section_break",
"tax_breakup",
"other_charges_calculation",
"pricing_rule_details",
"pricing_rules",
"address_and_contact_tab",
"supplier_address",
"address_display",
"column_break_72",
"contact_person",
"contact_display",
"contact_mobile",
"contact_email",
"terms_tab",
"tc_name",
"terms",
"more_info_tab",
"printing_settings",
"select_print_heading",
"group_same_items",
"column_break_72",
"letter_head",
"group_same_items",
"column_break_85",
"select_print_heading",
"language",
"subscription_section",
"auto_repeat",
"update_auto_repeat_reference",
"more_info",
"status",
"column_break_57",
"is_subcontracted",
"reference",
"opportunity"
"column_break_57",
"opportunity",
"connections_tab"
],
"fields": [
{
@@ -146,7 +150,7 @@
"fieldname": "supplier_name",
"fieldtype": "Data",
"in_global_search": 1,
"label": "Name",
"label": "Supplier Name",
"read_only": 1
},
{
@@ -193,12 +197,6 @@
"reqd": 1,
"search_index": 1
},
{
"collapsible": 1,
"fieldname": "address_section",
"fieldtype": "Section Break",
"label": "Address and Contact"
},
{
"fieldname": "supplier_address",
"fieldtype": "Link",
@@ -309,6 +307,8 @@
{
"fieldname": "items_section",
"fieldtype": "Section Break",
"hide_border": 1,
"label": "Items",
"oldfieldtype": "Section Break",
"options": "fa fa-shopping-cart"
},
@@ -316,7 +316,6 @@
"allow_bulk_edit": 1,
"fieldname": "items",
"fieldtype": "Table",
"label": "Items",
"oldfieldname": "po_details",
"oldfieldtype": "Table",
"options": "Supplier Quotation Item",
@@ -394,6 +393,7 @@
{
"fieldname": "taxes_section",
"fieldtype": "Section Break",
"hide_border": 1,
"label": "Taxes and Charges",
"oldfieldtype": "Section Break",
"options": "fa fa-money"
@@ -417,7 +417,8 @@
},
{
"fieldname": "section_break_38",
"fieldtype": "Section Break"
"fieldtype": "Section Break",
"hide_border": 1
},
{
"fieldname": "taxes_and_charges",
@@ -523,7 +524,6 @@
},
{
"collapsible": 1,
"collapsible_depends_on": "discount_amount",
"fieldname": "section_break_41",
"fieldtype": "Section Break",
"label": "Additional Discount"
@@ -563,7 +563,8 @@
},
{
"fieldname": "section_break_46",
"fieldtype": "Section Break"
"fieldtype": "Section Break",
"label": "Totals"
},
{
"fieldname": "base_grand_total",
@@ -654,19 +655,10 @@
"fieldtype": "Check",
"label": "Disable Rounded Total"
},
{
"collapsible": 1,
"collapsible_depends_on": "terms",
"fieldname": "terms_section_break",
"fieldtype": "Section Break",
"label": "Terms and Conditions",
"oldfieldtype": "Section Break",
"options": "fa fa-legal"
},
{
"fieldname": "tc_name",
"fieldtype": "Link",
"label": "Terms",
"label": "Terms Template",
"oldfieldname": "tc_name",
"oldfieldtype": "Link",
"options": "Terms and Conditions",
@@ -729,7 +721,7 @@
{
"fieldname": "subscription_section",
"fieldtype": "Section Break",
"label": "Auto Repeat Section"
"label": "Auto Repeat"
},
{
"fieldname": "auto_repeat",
@@ -751,7 +743,7 @@
"collapsible": 1,
"fieldname": "more_info",
"fieldtype": "Section Break",
"label": "More Information",
"label": "Additional Info",
"oldfieldtype": "Section Break",
"options": "fa fa-file-text"
},
@@ -779,11 +771,6 @@
"label": "Is Subcontracted",
"print_hide": 1
},
{
"fieldname": "reference",
"fieldtype": "Section Break",
"label": "Reference"
},
{
"fieldname": "opportunity",
"fieldtype": "Link",
@@ -803,6 +790,39 @@
"fieldname": "quotation_number",
"fieldtype": "Data",
"label": "Quotation Number"
},
{
"fieldname": "address_and_contact_tab",
"fieldtype": "Tab Break",
"label": "Address & Contact"
},
{
"fieldname": "terms_tab",
"fieldtype": "Tab Break",
"label": "Terms"
},
{
"fieldname": "more_info_tab",
"fieldtype": "Tab Break",
"label": "More Info"
},
{
"fieldname": "connections_tab",
"fieldtype": "Tab Break",
"label": "Connections",
"show_dashboard": 1
},
{
"fieldname": "column_break_26",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_34",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_85",
"fieldtype": "Column Break"
}
],
"icon": "fa fa-shopping-cart",
@@ -810,7 +830,7 @@
"index_web_pages_for_search": 1,
"is_submittable": 1,
"links": [],
"modified": "2022-03-14 16:13:20.284572",
"modified": "2022-09-27 18:20:09.462037",
"modified_by": "Administrator",
"module": "Buying",
"name": "Supplier Quotation",

View File

@@ -442,11 +442,17 @@ class SellingController(StockController):
# For internal transfers use incoming rate as the valuation rate
if self.is_internal_transfer():
if d.doctype == "Packed Item":
incoming_rate = flt(d.incoming_rate * d.conversion_factor, d.precision("incoming_rate"))
incoming_rate = flt(
flt(d.incoming_rate, d.precision("incoming_rate")) * d.conversion_factor,
d.precision("incoming_rate"),
)
if d.incoming_rate != incoming_rate:
d.incoming_rate = incoming_rate
else:
rate = flt(d.incoming_rate * d.conversion_factor, d.precision("rate"))
rate = flt(
flt(d.incoming_rate, d.precision("incoming_rate")) * d.conversion_factor,
d.precision("rate"),
)
if d.rate != rate:
d.rate = rate
frappe.msgprint(

View File

@@ -142,13 +142,15 @@ class StockController(AccountsController):
warehouse_with_no_account = []
precision = self.get_debit_field_precision()
for item_row in voucher_details:
sle_list = sle_map.get(item_row.name)
sle_rounding_diff = 0.0
if sle_list:
for sle in sle_list:
if warehouse_account.get(sle.warehouse):
# from warehouse account
sle_rounding_diff += flt(sle.stock_value_difference)
self.check_expense_account(item_row)
# expense account/ target_warehouse / source_warehouse
@@ -191,6 +193,46 @@ class StockController(AccountsController):
elif sle.warehouse not in warehouse_with_no_account:
warehouse_with_no_account.append(sle.warehouse)
if abs(sle_rounding_diff) > (1.0 / (10**precision)) and self.is_internal_transfer():
warehouse_asset_account = ""
if self.get("is_internal_customer"):
warehouse_asset_account = warehouse_account[item_row.get("target_warehouse")]["account"]
elif self.get("is_internal_supplier"):
warehouse_asset_account = warehouse_account[item_row.get("warehouse")]["account"]
expense_account = frappe.db.get_value("Company", self.company, "default_expense_account")
gl_list.append(
self.get_gl_dict(
{
"account": expense_account,
"against": warehouse_asset_account,
"cost_center": item_row.cost_center,
"project": item_row.project or self.get("project"),
"remarks": _("Rounding gain/loss Entry for Stock Transfer"),
"debit": sle_rounding_diff,
"is_opening": item_row.get("is_opening") or self.get("is_opening") or "No",
},
warehouse_account[sle.warehouse]["account_currency"],
item=item_row,
)
)
gl_list.append(
self.get_gl_dict(
{
"account": warehouse_asset_account,
"against": expense_account,
"cost_center": item_row.cost_center,
"remarks": _("Rounding gain/loss Entry for Stock Transfer"),
"credit": sle_rounding_diff,
"project": item_row.get("project") or self.get("project"),
"is_opening": item_row.get("is_opening") or self.get("is_opening") or "No",
},
item=item_row,
)
)
if warehouse_with_no_account:
for wh in warehouse_with_no_account:
if frappe.db.get_value("Warehouse", wh, "company"):

View File

@@ -188,7 +188,8 @@
"in_list_view": 1,
"label": "Item Group",
"options": "Item Group",
"read_only": 1
"read_only": 1,
"search_index": 1
},
{
"default": "1",
@@ -234,7 +235,8 @@
"fieldname": "brand",
"fieldtype": "Link",
"label": "Brand",
"options": "Brand"
"options": "Brand",
"search_index": 1
},
{
"collapsible": 1,
@@ -346,7 +348,7 @@
"index_web_pages_for_search": 1,
"links": [],
"make_attachments_public": 1,
"modified": "2022-09-13 04:05:11.614087",
"modified": "2022-09-30 04:01:52.090732",
"modified_by": "Administrator",
"module": "E-commerce",
"name": "Website Item",

View File

@@ -403,9 +403,6 @@ def on_doctype_update():
# since route is a Text column, it needs a length for indexing
frappe.db.add_index("Website Item", ["route(500)"])
frappe.db.add_index("Website Item", ["item_group"])
frappe.db.add_index("Website Item", ["brand"])
def check_if_user_is_customer(user=None):
from frappe.contacts.doctype.contact.contact import get_contact_name

View File

@@ -17,6 +17,7 @@ from erpnext.manufacturing.doctype.work_order.work_order import (
close_work_order,
make_job_card,
make_stock_entry,
make_stock_return_entry,
stop_unstop,
)
from erpnext.selling.doctype.sales_order.test_sales_order import make_sales_order
@@ -1408,6 +1409,77 @@ class TestWorkOrder(FrappeTestCase):
)
self.assertEqual(manufacture_ste_doc2.items[1].qty, 1)
def test_non_consumed_material_return_against_work_order(self):
frappe.db.set_value(
"Manufacturing Settings",
None,
"backflush_raw_materials_based_on",
"Material Transferred for Manufacture",
)
item = make_item(
"Test FG Item To Test Return Case",
{
"is_stock_item": 1,
},
)
item_code = item.name
bom_doc = make_bom(
item=item_code,
source_warehouse="Stores - _TC",
raw_materials=["Test Batch MCC Keyboard", "Test Serial No BTT Headphone"],
)
# Create a work order
wo_doc = make_wo_order_test_record(production_item=item_code, qty=5)
wo_doc.save()
self.assertEqual(wo_doc.bom_no, bom_doc.name)
# Transfer material for manufacture
ste_doc = frappe.get_doc(make_stock_entry(wo_doc.name, "Material Transfer for Manufacture", 5))
for row in ste_doc.items:
row.qty += 2
row.transfer_qty += 2
nste_doc = test_stock_entry.make_stock_entry(
item_code=row.item_code, target="Stores - _TC", qty=row.qty, basic_rate=100
)
row.batch_no = nste_doc.items[0].batch_no
row.serial_no = nste_doc.items[0].serial_no
ste_doc.save()
ste_doc.submit()
ste_doc.load_from_db()
# Create a stock entry to manufacture the item
ste_doc = frappe.get_doc(make_stock_entry(wo_doc.name, "Manufacture", 5))
for row in ste_doc.items:
if row.s_warehouse and not row.t_warehouse:
row.qty -= 2
row.transfer_qty -= 2
if row.serial_no:
serial_nos = get_serial_nos(row.serial_no)
row.serial_no = "\n".join(serial_nos[0:5])
ste_doc.save()
ste_doc.submit()
wo_doc.load_from_db()
for row in wo_doc.required_items:
self.assertEqual(row.transferred_qty, 7)
self.assertEqual(row.consumed_qty, 5)
self.assertEqual(wo_doc.status, "Completed")
return_ste_doc = make_stock_return_entry(wo_doc.name)
return_ste_doc.save()
self.assertTrue(return_ste_doc.is_return)
for row in return_ste_doc.items:
self.assertEqual(row.qty, 2)
def prepare_data_for_backflush_based_on_materials_transferred():
batch_item_doc = make_item(

View File

@@ -180,6 +180,37 @@ frappe.ui.form.on("Work Order", {
frm.trigger("make_bom");
});
}
frm.trigger("add_custom_button_to_return_components");
},
add_custom_button_to_return_components: function(frm) {
if (frm.doc.docstatus === 1 && in_list(["Closed", "Completed"], frm.doc.status)) {
let non_consumed_items = frm.doc.required_items.filter(d =>{
return flt(d.consumed_qty) < flt(d.transferred_qty - d.returned_qty)
});
if (non_consumed_items && non_consumed_items.length) {
frm.add_custom_button(__("Return Components"), function() {
frm.trigger("create_stock_return_entry");
}).addClass("btn-primary");
}
}
},
create_stock_return_entry: function(frm) {
frappe.call({
method: "erpnext.manufacturing.doctype.work_order.work_order.make_stock_return_entry",
args: {
"work_order": frm.doc.name,
},
callback: function(r) {
if(!r.exc) {
let doc = frappe.model.sync(r.message);
frappe.set_route("Form", doc[0].doctype, doc[0].name);
}
}
});
},
make_job_card: function(frm) {
@@ -517,7 +548,8 @@ frappe.ui.form.on("Work Order Operation", {
erpnext.work_order = {
set_custom_buttons: function(frm) {
var doc = frm.doc;
if (doc.docstatus === 1 && doc.status != "Closed") {
if (doc.status !== "Closed") {
frm.add_custom_button(__('Close'), function() {
frappe.confirm(__("Once the Work Order is Closed. It can't be resumed."),
() => {
@@ -525,7 +557,9 @@ erpnext.work_order = {
}
);
}, __("Status"));
}
if (doc.docstatus === 1 && !in_list(["Closed", "Completed"], doc.status)) {
if (doc.status != 'Stopped' && doc.status != 'Completed') {
frm.add_custom_button(__('Stop'), function() {
erpnext.work_order.change_work_order_status(frm, "Stopped");

View File

@@ -20,6 +20,7 @@ from frappe.utils import (
nowdate,
time_diff_in_hours,
)
from pypika import functions as fn
from erpnext.manufacturing.doctype.bom.bom import (
get_bom_item_rate,
@@ -859,6 +860,7 @@ class WorkOrder(Document):
if self.docstatus == 1:
# calculate transferred qty based on submitted stock entries
self.update_transferred_qty_for_required_items()
self.update_returned_qty()
# update in bin
self.update_reserved_qty_for_production()
@@ -930,23 +932,62 @@ class WorkOrder(Document):
self.set_available_qty()
def update_transferred_qty_for_required_items(self):
"""update transferred qty from submitted stock entries for that item against
the work order"""
ste = frappe.qb.DocType("Stock Entry")
ste_child = frappe.qb.DocType("Stock Entry Detail")
for d in self.required_items:
transferred_qty = frappe.db.sql(
"""select sum(qty)
from `tabStock Entry` entry, `tabStock Entry Detail` detail
where
entry.work_order = %(name)s
and entry.purpose = 'Material Transfer for Manufacture'
and entry.docstatus = 1
and detail.parent = entry.name
and (detail.item_code = %(item)s or detail.original_item = %(item)s)""",
{"name": self.name, "item": d.item_code},
)[0][0]
query = (
frappe.qb.from_(ste)
.inner_join(ste_child)
.on((ste_child.parent == ste.name))
.select(
ste_child.item_code,
ste_child.original_item,
fn.Sum(ste_child.qty).as_("qty"),
)
.where(
(ste.docstatus == 1)
& (ste.work_order == self.name)
& (ste.purpose == "Material Transfer for Manufacture")
& (ste.is_return == 0)
)
.groupby(ste_child.item_code)
)
d.db_set("transferred_qty", flt(transferred_qty), update_modified=False)
data = query.run(as_dict=1) or []
transferred_items = frappe._dict({d.original_item or d.item_code: d.qty for d in data})
for row in self.required_items:
row.db_set(
"transferred_qty", (transferred_items.get(row.item_code) or 0.0), update_modified=False
)
def update_returned_qty(self):
ste = frappe.qb.DocType("Stock Entry")
ste_child = frappe.qb.DocType("Stock Entry Detail")
query = (
frappe.qb.from_(ste)
.inner_join(ste_child)
.on((ste_child.parent == ste.name))
.select(
ste_child.item_code,
ste_child.original_item,
fn.Sum(ste_child.qty).as_("qty"),
)
.where(
(ste.docstatus == 1)
& (ste.work_order == self.name)
& (ste.purpose == "Material Transfer for Manufacture")
& (ste.is_return == 1)
)
.groupby(ste_child.item_code)
)
data = query.run(as_dict=1) or []
returned_dict = frappe._dict({d.original_item or d.item_code: d.qty for d in data})
for row in self.required_items:
row.db_set("returned_qty", (returned_dict.get(row.item_code) or 0.0), update_modified=False)
def update_consumed_qty_for_required_items(self):
"""
@@ -1470,3 +1511,25 @@ def get_reserved_qty_for_production(item_code: str, warehouse: str) -> float:
)
)
).run()[0][0] or 0.0
@frappe.whitelist()
def make_stock_return_entry(work_order):
from erpnext.stock.doctype.stock_entry.stock_entry import get_available_materials
non_consumed_items = get_available_materials(work_order)
if not non_consumed_items:
return
wo_doc = frappe.get_cached_doc("Work Order", work_order)
stock_entry = frappe.new_doc("Stock Entry")
stock_entry.from_bom = 1
stock_entry.is_return = 1
stock_entry.work_order = work_order
stock_entry.purpose = "Material Transfer for Manufacture"
stock_entry.bom_no = wo_doc.bom_no
stock_entry.add_transfered_raw_materials_in_items()
stock_entry.set_stock_entry_type()
return stock_entry

View File

@@ -20,6 +20,7 @@
"column_break_11",
"transferred_qty",
"consumed_qty",
"returned_qty",
"available_qty_at_source_warehouse",
"available_qty_at_wip_warehouse"
],
@@ -97,6 +98,7 @@
"fieldtype": "Column Break"
},
{
"columns": 1,
"depends_on": "eval:!parent.skip_transfer",
"fieldname": "consumed_qty",
"fieldtype": "Float",
@@ -127,11 +129,19 @@
"fieldtype": "Currency",
"label": "Amount",
"read_only": 1
},
{
"columns": 1,
"fieldname": "returned_qty",
"fieldtype": "Float",
"in_list_view": 1,
"label": "Returned Qty ",
"read_only": 1
}
],
"istable": 1,
"links": [],
"modified": "2020-04-13 18:46:32.966416",
"modified": "2022-09-28 10:50:43.512562",
"modified_by": "Administrator",
"module": "Manufacturing",
"name": "Work Order Item",
@@ -140,5 +150,6 @@
"quick_entry": 1,
"sort_field": "modified",
"sort_order": "DESC",
"states": [],
"track_changes": 1
}

View File

@@ -50,7 +50,7 @@ frappe.query_reports["Work Order Consumed Materials"] = {
label: __("Status"),
fieldname: "status",
fieldtype: "Select",
options: ["In Process", "Completed", "Stopped"]
options: ["", "In Process", "Completed", "Stopped"]
},
{
label: __("Excess Materials Consumed"),

View File

@@ -1,6 +1,8 @@
# Copyright (c) 2013, Frappe Technologies Pvt. Ltd. and contributors
# For license information, please see license.txt
from collections import defaultdict
import frappe
from frappe import _
@@ -18,7 +20,11 @@ def get_data(report_filters):
filters = get_filter_condition(report_filters)
wo_items = {}
for d in frappe.get_all("Work Order", filters=filters, fields=fields):
work_orders = frappe.get_all("Work Order", filters=filters, fields=fields)
returned_materials = get_returned_materials(work_orders)
for d in work_orders:
d.extra_consumed_qty = 0.0
if d.consumed_qty and d.consumed_qty > d.required_qty:
d.extra_consumed_qty = d.consumed_qty - d.required_qty
@@ -39,6 +45,28 @@ def get_data(report_filters):
return data
def get_returned_materials(work_orders):
raw_materials_qty = defaultdict(float)
raw_materials = frappe.get_all(
"Stock Entry",
fields=["`tabStock Entry Detail`.`item_code`", "`tabStock Entry Detail`.`qty`"],
filters=[
["Stock Entry", "is_return", "=", 1],
["Stock Entry Detail", "docstatus", "=", 1],
["Stock Entry", "work_order", "in", [d.name for d in work_orders]],
],
)
for d in raw_materials:
raw_materials_qty[d.item_code] += d.qty
for row in work_orders:
row.returned_qty = 0.0
if raw_materials_qty.get(row.raw_material_item_code):
row.returned_qty = raw_materials_qty.get(row.raw_material_item_code)
def get_fields():
return [
"`tabWork Order Item`.`parent`",
@@ -65,7 +93,7 @@ def get_filter_condition(report_filters):
for field in ["name", "production_item", "company", "status"]:
value = report_filters.get(field)
if value:
key = f"`{field}`"
key = f"{field}"
filters.update({key: value})
return filters
@@ -112,4 +140,10 @@ def get_columns():
"fieldtype": "Float",
"width": 100,
},
{
"label": _("Returned Qty"),
"fieldname": "returned_qty",
"fieldtype": "Float",
"width": 100,
},
]

View File

@@ -3,6 +3,29 @@ from frappe import qb
from frappe.utils import create_batch
def remove_duplicate_entries(pl_entries):
unique_vouchers = set()
for x in pl_entries:
unique_vouchers.add(
(x.company, x.account, x.party_type, x.party, x.voucher_type, x.voucher_no, x.gle_remarks)
)
entries = []
for x in unique_vouchers:
entries.append(
frappe._dict(
company=x[0],
account=x[1],
party_type=x[2],
party=x[3],
voucher_type=x[4],
voucher_no=x[5],
gle_remarks=x[6],
)
)
return entries
def execute():
if frappe.reload_doc("accounts", "doctype", "payment_ledger_entry"):
@@ -34,6 +57,8 @@ def execute():
.run(as_dict=True)
)
pl_entries = remove_duplicate_entries(pl_entries)
if pl_entries:
# split into multiple batches, update and commit for each batch
batch_size = 1000

View File

@@ -37,7 +37,7 @@ def make_custom_fields():
fieldname="vat_section",
label="VAT Details",
fieldtype="Section Break",
insert_after="group_same_items",
insert_after="language",
print_hide=1,
collapsible=1,
),

View File

@@ -15,26 +15,13 @@
"quotation_to",
"party_name",
"customer_name",
"column_break1",
"amended_from",
"company",
"column_break_7",
"transaction_date",
"valid_till",
"column_break1",
"order_type",
"contact_section",
"customer_address",
"address_display",
"contact_person",
"contact_display",
"contact_mobile",
"contact_email",
"col_break98",
"shipping_address_name",
"shipping_address",
"company_address",
"company_address_display",
"customer_group",
"territory",
"company",
"amended_from",
"currency_and_price_list",
"currency",
"conversion_rate",
@@ -43,79 +30,105 @@
"price_list_currency",
"plc_conversion_rate",
"ignore_pricing_rule",
"section_break_33",
"scan_barcode",
"items_section",
"scan_barcode",
"items",
"bundle_items_section",
"packed_items",
"pricing_rule_details",
"pricing_rules",
"sec_break23",
"total_qty",
"total_net_weight",
"column_break_28",
"base_total",
"base_net_total",
"column_break_28",
"column_break_31",
"total",
"net_total",
"total_net_weight",
"taxes_section",
"taxes_and_charges",
"column_break_36",
"tax_category",
"column_break_34",
"shipping_rule",
"section_break_36",
"taxes_and_charges",
"taxes",
"sec_tax_breakup",
"other_charges_calculation",
"section_break_39",
"base_total_taxes_and_charges",
"column_break_42",
"total_taxes_and_charges",
"section_break_44",
"coupon_code",
"referral_sales_partner",
"apply_discount_on",
"base_discount_amount",
"column_break_46",
"additional_discount_percentage",
"discount_amount",
"totals",
"base_grand_total",
"base_rounding_adjustment",
"base_in_words",
"base_rounded_total",
"base_in_words",
"column_break3",
"grand_total",
"rounding_adjustment",
"rounded_total",
"in_words",
"section_break_44",
"apply_discount_on",
"base_discount_amount",
"coupon_code",
"column_break_46",
"additional_discount_percentage",
"discount_amount",
"referral_sales_partner",
"sec_tax_breakup",
"other_charges_calculation",
"bundle_items_section",
"packed_items",
"pricing_rule_details",
"pricing_rules",
"address_and_contact_tab",
"billing_address_section",
"customer_address",
"address_display",
"col_break98",
"contact_person",
"contact_display",
"contact_mobile",
"contact_email",
"shipping_address_section",
"shipping_address_name",
"column_break_81",
"shipping_address",
"company_address_section",
"company_address",
"column_break_87",
"company_address_display",
"terms_tab",
"payment_schedule_section",
"payment_terms_template",
"payment_schedule",
"terms_section_break",
"tc_name",
"terms",
"more_info_tab",
"subscription_section",
"auto_repeat",
"update_auto_repeat_reference",
"print_settings",
"letter_head",
"group_same_items",
"column_break_73",
"select_print_heading",
"language",
"subscription_section",
"auto_repeat",
"update_auto_repeat_reference",
"more_info",
"lost_reasons_section",
"lost_reasons",
"competitors",
"column_break_117",
"order_lost_reason",
"additional_info_section",
"status",
"customer_group",
"territory",
"column_break_108",
"campaign",
"source",
"order_lost_reason",
"column_break4",
"status",
"enq_det",
"supplier_quotation",
"opportunity",
"lost_reasons",
"competitors"
"supplier_quotation",
"enq_det",
"connections_tab"
],
"fields": [
{
@@ -241,14 +254,6 @@
"print_hide": 1,
"reqd": 1
},
{
"collapsible": 1,
"depends_on": "party_name",
"fieldname": "contact_section",
"fieldtype": "Section Break",
"label": "Address and Contact",
"options": "fa fa-bullhorn"
},
{
"fieldname": "customer_address",
"fieldtype": "Link",
@@ -296,7 +301,7 @@
"read_only": 1
},
{
"depends_on": "eval:doc.quotation_to=='Customer' && doc.party_name",
"depends_on": "eval:(doc.quotation_to=='Customer' && doc.party_name)",
"fieldname": "col_break98",
"fieldtype": "Column Break",
"width": "50%"
@@ -316,7 +321,7 @@
"read_only": 1
},
{
"depends_on": "eval:doc.quotation_to=='Customer' && doc.party_name",
"depends_on": "eval:(doc.quotation_to=='Customer' && doc.party_name)",
"fieldname": "customer_group",
"fieldtype": "Link",
"hidden": 1,
@@ -408,6 +413,8 @@
{
"fieldname": "items_section",
"fieldtype": "Section Break",
"hide_border": 1,
"label": "Items",
"oldfieldtype": "Section Break",
"options": "fa fa-shopping-cart"
},
@@ -415,7 +422,6 @@
"allow_bulk_edit": 1,
"fieldname": "items",
"fieldtype": "Table",
"label": "Items",
"oldfieldname": "quotation_details",
"oldfieldtype": "Table",
"options": "Quotation Item",
@@ -423,6 +429,7 @@
"width": "40px"
},
{
"collapsible": 1,
"fieldname": "pricing_rule_details",
"fieldtype": "Section Break",
"label": "Pricing Rules"
@@ -483,6 +490,7 @@
"read_only": 1
},
{
"depends_on": "total_net_weight",
"fieldname": "total_net_weight",
"fieldtype": "Float",
"label": "Total Net Weight",
@@ -492,6 +500,7 @@
{
"fieldname": "taxes_section",
"fieldtype": "Section Break",
"hide_border": 1,
"label": "Taxes and Charges",
"oldfieldtype": "Section Break",
"options": "fa fa-money"
@@ -517,7 +526,8 @@
},
{
"fieldname": "section_break_36",
"fieldtype": "Section Break"
"fieldtype": "Section Break",
"hide_border": 1
},
{
"fieldname": "taxes_and_charges",
@@ -579,10 +589,9 @@
},
{
"collapsible": 1,
"collapsible_depends_on": "discount_amount",
"fieldname": "section_break_44",
"fieldtype": "Section Break",
"label": "Additional Discount and Coupon Code"
"label": "Additional Discount"
},
{
"fieldname": "coupon_code",
@@ -632,6 +641,7 @@
{
"fieldname": "totals",
"fieldtype": "Section Break",
"label": "Totals",
"oldfieldtype": "Section Break",
"options": "fa fa-money",
"print_hide": 1
@@ -657,7 +667,6 @@
"read_only": 1
},
{
"description": "In Words will be visible once you save the Quotation.",
"fieldname": "base_in_words",
"fieldtype": "Data",
"label": "In Words (Company Currency)",
@@ -665,8 +674,7 @@
"oldfieldname": "in_words",
"oldfieldtype": "Data",
"print_hide": 1,
"read_only": 1,
"width": "200px"
"read_only": 1
},
{
"fieldname": "base_rounded_total",
@@ -749,7 +757,6 @@
"print_hide": 1
},
{
"collapsible": 1,
"collapsible_depends_on": "terms",
"fieldname": "terms_section_break",
"fieldtype": "Section Break",
@@ -824,7 +831,7 @@
{
"fieldname": "subscription_section",
"fieldtype": "Section Break",
"label": "Auto Repeat Section"
"label": "Auto Repeat"
},
{
"fieldname": "auto_repeat",
@@ -837,20 +844,11 @@
},
{
"allow_on_submit": 1,
"depends_on": "eval: doc.auto_repeat",
"depends_on": "eval:doc.auto_repeat",
"fieldname": "update_auto_repeat_reference",
"fieldtype": "Button",
"label": "Update Auto Repeat Reference"
},
{
"collapsible": 1,
"fieldname": "more_info",
"fieldtype": "Section Break",
"label": "More Information",
"oldfieldtype": "Section Break",
"options": "fa fa-file-text",
"print_hide": 1
},
{
"fieldname": "campaign",
"fieldtype": "Link",
@@ -871,7 +869,7 @@
},
{
"allow_on_submit": 1,
"depends_on": "eval:doc.status===\"Lost\"",
"depends_on": "eval:doc.status=='Lost'",
"fieldname": "order_lost_reason",
"fieldtype": "Small Text",
"label": "Detailed Reason",
@@ -934,7 +932,6 @@
"read_only": 1
},
{
"depends_on": "packed_items",
"fieldname": "packed_items",
"fieldtype": "Table",
"label": "Bundle Items",
@@ -943,7 +940,6 @@
},
{
"collapsible": 1,
"collapsible_depends_on": "packed_items",
"depends_on": "packed_items",
"fieldname": "bundle_items_section",
"fieldtype": "Section Break",
@@ -970,22 +966,99 @@
"label": "Company Address",
"read_only": 1
},
{
"fieldname": "section_break_33",
"fieldtype": "Section Break"
},
{
"fieldname": "scan_barcode",
"fieldtype": "Data",
"label": "Scan Barcode",
"options": "Barcode"
},
{
"fieldname": "address_and_contact_tab",
"fieldtype": "Tab Break",
"label": "Address & Contact"
},
{
"fieldname": "terms_tab",
"fieldtype": "Tab Break",
"label": "Terms"
},
{
"fieldname": "more_info_tab",
"fieldtype": "Tab Break",
"label": "More Info"
},
{
"fieldname": "connections_tab",
"fieldtype": "Tab Break",
"label": "Connections",
"show_dashboard": 1
},
{
"fieldname": "column_break_7",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_31",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_36",
"fieldtype": "Column Break"
},
{
"fieldname": "billing_address_section",
"fieldtype": "Section Break",
"label": "Billing Address",
"options": "fa fa-bullhorn"
},
{
"fieldname": "shipping_address_section",
"fieldtype": "Section Break",
"label": "Shipping Address"
},
{
"fieldname": "column_break_81",
"fieldtype": "Column Break"
},
{
"fieldname": "company_address_section",
"fieldtype": "Section Break",
"label": "Company Address"
},
{
"fieldname": "column_break_87",
"fieldtype": "Column Break"
},
{
"collapsible": 1,
"depends_on": "eval:(doc.lost_reasons || doc.order_lost_reason)",
"fieldname": "lost_reasons_section",
"fieldtype": "Section Break",
"label": "Lost Reasons"
},
{
"fieldname": "column_break_117",
"fieldtype": "Column Break"
},
{
"collapsible": 1,
"fieldname": "additional_info_section",
"fieldtype": "Section Break",
"label": "Additional Info",
"oldfieldtype": "Section Break",
"options": "fa fa-file-text",
"print_hide": 1
},
{
"fieldname": "column_break_108",
"fieldtype": "Column Break"
}
],
"icon": "fa fa-shopping-cart",
"idx": 82,
"is_submittable": 1,
"links": [],
"modified": "2022-09-16 17:44:43.221804",
"modified": "2022-10-11 13:06:33.479650",
"modified_by": "Administrator",
"module": "Selling",
"name": "Quotation",
@@ -1083,4 +1156,4 @@
"states": [],
"timeline_field": "party_name",
"title_field": "title"
}
}

View File

@@ -15,37 +15,25 @@
"naming_series",
"customer",
"customer_name",
"tax_id",
"order_type",
"skip_delivery_note",
"column_break1",
"amended_from",
"company",
"column_break_7",
"transaction_date",
"delivery_date",
"column_break1",
"po_no",
"po_date",
"tax_id",
"company",
"skip_delivery_note",
"amended_from",
"accounting_dimensions_section",
"cost_center",
"dimension_col_break",
"project",
"contact_info",
"customer_address",
"address_display",
"contact_person",
"contact_display",
"contact_phone",
"contact_mobile",
"contact_email",
"company_address",
"company_address_display",
"col_break46",
"shipping_address_name",
"shipping_address",
"dispatch_address_name",
"dispatch_address",
"customer_group",
"territory",
"column_break_77",
"source",
"campaign",
"custom_dimensions_section",
"currency_and_price_list",
"currency",
"conversion_rate",
@@ -55,46 +43,32 @@
"plc_conversion_rate",
"ignore_pricing_rule",
"sec_warehouse",
"scan_barcode",
"column_break_28",
"set_warehouse",
"items_section",
"scan_barcode",
"items",
"packing_list",
"packed_items",
"pricing_rule_details",
"pricing_rules",
"section_break_31",
"column_break_33a",
"total_qty",
"total_net_weight",
"column_break_33",
"base_total",
"base_net_total",
"column_break_33",
"total_net_weight",
"column_break_33a",
"total",
"net_total",
"taxes_section",
"tax_category",
"taxes_and_charges",
"column_break_38",
"tax_category",
"column_break_49",
"shipping_rule",
"section_break_40",
"taxes_and_charges",
"taxes",
"sec_tax_breakup",
"other_charges_calculation",
"section_break_43",
"base_total_taxes_and_charges",
"column_break_46",
"total_taxes_and_charges",
"loyalty_points_redemption",
"loyalty_points",
"loyalty_amount",
"section_break_48",
"coupon_code",
"apply_discount_on",
"base_discount_amount",
"column_break_50",
"additional_discount_percentage",
"discount_amount",
"totals",
"base_grand_total",
"base_rounding_adjustment",
@@ -107,26 +81,49 @@
"in_words",
"advance_paid",
"disable_rounded_total",
"section_break_48",
"apply_discount_on",
"base_discount_amount",
"coupon_code",
"column_break_50",
"additional_discount_percentage",
"discount_amount",
"sec_tax_breakup",
"other_charges_calculation",
"packing_list",
"packed_items",
"pricing_rule_details",
"pricing_rules",
"contact_info",
"billing_address_column",
"customer_address",
"address_display",
"customer_group",
"territory",
"column_break_84",
"contact_person",
"contact_display",
"contact_phone",
"contact_mobile",
"contact_email",
"shipping_address_column",
"shipping_address_name",
"shipping_address",
"column_break_93",
"dispatch_address_name",
"dispatch_address",
"col_break46",
"company_address",
"column_break_92",
"company_address_display",
"payment_schedule_section",
"payment_terms_section",
"payment_terms_template",
"payment_schedule",
"terms_section_break",
"tc_name",
"terms",
"more_info",
"is_internal_customer",
"represents_company",
"inter_company_order_reference",
"party_account_currency",
"column_break_77",
"source",
"campaign",
"printing_details",
"language",
"letter_head",
"column_break4",
"select_print_heading",
"group_same_items",
"section_break_78",
"status",
"delivery_status",
@@ -143,12 +140,29 @@
"total_commission",
"section_break1",
"sales_team",
"loyalty_points_redemption",
"loyalty_points",
"column_break_116",
"loyalty_amount",
"subscription_section",
"from_date",
"to_date",
"column_break_108",
"auto_repeat",
"update_auto_repeat_reference"
"update_auto_repeat_reference",
"printing_details",
"letter_head",
"group_same_items",
"column_break4",
"select_print_heading",
"language",
"additional_info_section",
"is_internal_customer",
"represents_company",
"column_break_152",
"inter_company_order_reference",
"party_account_currency",
"connections_tab"
],
"fields": [
{
@@ -334,10 +348,10 @@
"collapsible": 1,
"depends_on": "customer",
"fieldname": "contact_info",
"fieldtype": "Section Break",
"fieldtype": "Tab Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Address and Contact",
"label": "Address & Contact",
"options": "fa fa-bullhorn"
},
{
@@ -414,9 +428,10 @@
},
{
"fieldname": "col_break46",
"fieldtype": "Column Break",
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Company Address",
"width": "50%"
},
{
@@ -550,8 +565,10 @@
{
"fieldname": "sec_warehouse",
"fieldtype": "Section Break",
"hide_border": 1,
"hide_days": 1,
"hide_seconds": 1
"hide_seconds": 1,
"label": "Items"
},
{
"fieldname": "set_warehouse",
@@ -565,6 +582,7 @@
{
"fieldname": "items_section",
"fieldtype": "Section Break",
"hide_border": 1,
"hide_days": 1,
"hide_seconds": 1,
"oldfieldtype": "Section Break",
@@ -675,6 +693,7 @@
"read_only": 1
},
{
"depends_on": "total_net_weight",
"fieldname": "total_net_weight",
"fieldtype": "Float",
"hide_days": 1,
@@ -688,7 +707,7 @@
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Taxes and Charges",
"label": "Taxes",
"oldfieldtype": "Section Break",
"options": "fa fa-money"
},
@@ -720,6 +739,7 @@
{
"fieldname": "section_break_40",
"fieldtype": "Section Break",
"hide_border": 1,
"hide_days": 1,
"hide_seconds": 1
},
@@ -804,7 +824,7 @@
"hidden": 1,
"hide_days": 1,
"hide_seconds": 1,
"label": "Loyalty Points Redemption",
"label": "Loyalty Points",
"print_hide": 1
},
{
@@ -828,12 +848,11 @@
},
{
"collapsible": 1,
"collapsible_depends_on": "discount_amount",
"fieldname": "section_break_48",
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Additional Discount and Coupon Code"
"label": "Additional Discount"
},
{
"fieldname": "coupon_code",
@@ -891,6 +910,7 @@
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Totals",
"oldfieldtype": "Section Break",
"options": "fa fa-money",
"print_hide": 1
@@ -1045,10 +1065,10 @@
},
{
"fieldname": "payment_schedule_section",
"fieldtype": "Section Break",
"fieldtype": "Tab Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Payment Terms"
"label": "Terms"
},
{
"fieldname": "payment_terms_template",
@@ -1070,13 +1090,12 @@
"print_hide": 1
},
{
"collapsible": 1,
"collapsible_depends_on": "terms",
"fieldname": "terms_section_break",
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Terms and Conditions",
"label": "Terms & Conditions",
"oldfieldtype": "Section Break",
"options": "fa fa-legal"
},
@@ -1104,10 +1123,10 @@
"collapsible": 1,
"collapsible_depends_on": "project",
"fieldname": "more_info",
"fieldtype": "Section Break",
"fieldtype": "Tab Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "More Information",
"label": "More Info",
"oldfieldtype": "Section Break",
"options": "fa fa-file-text",
"print_hide": 1
@@ -1122,7 +1141,6 @@
"read_only": 1
},
{
"description": "Track this Sales Order against any Project",
"fieldname": "project",
"fieldtype": "Link",
"hide_days": 1,
@@ -1240,7 +1258,7 @@
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Billing and Delivery Status",
"label": "Status",
"oldfieldtype": "Column Break",
"print_hide": 1,
"width": "50%"
@@ -1410,7 +1428,7 @@
"fieldtype": "Section Break",
"hide_days": 1,
"hide_seconds": 1,
"label": "Auto Repeat Section",
"label": "Auto Repeat",
"no_copy": 1,
"print_hide": 1,
"read_only": 1
@@ -1542,13 +1560,76 @@
{
"fieldname": "dimension_col_break",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_7",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_28",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_49",
"fieldtype": "Column Break"
},
{
"fieldname": "connections_tab",
"fieldtype": "Tab Break",
"label": "Connections",
"show_dashboard": 1
},
{
"fieldname": "payment_terms_section",
"fieldtype": "Section Break",
"label": "Payment Terms"
},
{
"fieldname": "column_break_116",
"fieldtype": "Column Break"
},
{
"fieldname": "billing_address_column",
"fieldtype": "Section Break",
"label": "Billing Address"
},
{
"fieldname": "shipping_address_column",
"fieldtype": "Section Break",
"label": "Shipping Address"
},
{
"fieldname": "column_break_93",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_84",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_92",
"fieldtype": "Column Break"
},
{
"fieldname": "custom_dimensions_section",
"fieldtype": "Section Break"
},
{
"collapsible": 1,
"fieldname": "additional_info_section",
"fieldtype": "Section Break",
"label": "Additional Info"
},
{
"fieldname": "column_break_152",
"fieldtype": "Column Break"
}
],
"icon": "fa fa-file-text",
"idx": 105,
"is_submittable": 1,
"links": [],
"modified": "2022-09-16 17:43:57.007441",
"modified": "2022-10-11 13:06:10.469796",
"modified_by": "Administrator",
"module": "Selling",
"name": "Sales Order",

View File

@@ -37,8 +37,10 @@ class Bin(Document):
self.set_projected_qty()
self.db_set("reserved_qty_for_production", flt(self.reserved_qty_for_production))
self.db_set("projected_qty", self.projected_qty)
self.db_set(
"reserved_qty_for_production", flt(self.reserved_qty_for_production), update_modified=True
)
self.db_set("projected_qty", self.projected_qty, update_modified=True)
def update_reserved_qty_for_sub_contracting(self, subcontract_doctype="Subcontracting Order"):
# reserved qty
@@ -118,9 +120,9 @@ class Bin(Document):
else:
reserved_qty_for_sub_contract = 0
self.db_set("reserved_qty_for_sub_contract", reserved_qty_for_sub_contract)
self.db_set("reserved_qty_for_sub_contract", reserved_qty_for_sub_contract, update_modified=True)
self.set_projected_qty()
self.db_set("projected_qty", self.projected_qty)
self.db_set("projected_qty", self.projected_qty, update_modified=True)
def on_doctype_update():
@@ -193,4 +195,5 @@ def update_qty(bin_name, args):
"planned_qty": planned_qty,
"projected_qty": projected_qty,
},
update_modified=True,
)

View File

@@ -8,46 +8,29 @@
"document_type": "Document",
"engine": "InnoDB",
"field_order": [
"delivery_to_section",
"column_break0",
"title",
"naming_series",
"customer",
"tax_id",
"customer_name",
"column_break1",
"amended_from",
"company",
"posting_date",
"posting_time",
"set_posting_time",
"column_break_10",
"company",
"amended_from",
"is_return",
"issue_credit_note",
"return_against",
"accounting_dimensions_section",
"cost_center",
"dimension_col_break",
"column_break_18",
"project",
"customer_po_details",
"po_no",
"column_break_17",
"po_date",
"section_break_18",
"pick_list",
"contact_info",
"shipping_address_name",
"shipping_address",
"dispatch_address_name",
"dispatch_address",
"contact_person",
"contact_display",
"contact_mobile",
"contact_email",
"col_break21",
"customer_address",
"tax_id",
"address_display",
"company_address",
"company_address_display",
"dimension_col_break",
"campaign",
"source",
"custom_dimensions_section",
"currency_and_price_list",
"currency",
"conversion_rate",
@@ -56,45 +39,35 @@
"price_list_currency",
"plc_conversion_rate",
"ignore_pricing_rule",
"sec_warehouse",
"set_warehouse",
"col_break_warehouse",
"set_target_warehouse",
"items_section",
"scan_barcode",
"pick_list",
"col_break_warehouse",
"set_warehouse",
"set_target_warehouse",
"section_break_30",
"items",
"pricing_rule_details",
"pricing_rules",
"packing_list",
"packed_items",
"product_bundle_help",
"section_break_31",
"total_qty",
"total_net_weight",
"column_break_35",
"base_total",
"base_net_total",
"column_break_33",
"total_net_weight",
"total",
"net_total",
"taxes_section",
"taxes_and_charges",
"column_break_43",
"tax_category",
"column_break_39",
"shipping_rule",
"section_break_41",
"taxes_and_charges",
"taxes",
"sec_tax_breakup",
"other_charges_calculation",
"section_break_44",
"base_total_taxes_and_charges",
"column_break_47",
"total_taxes_and_charges",
"section_break_49",
"apply_discount_on",
"base_discount_amount",
"column_break_51",
"additional_discount_percentage",
"discount_amount",
"totals",
"base_grand_total",
"base_rounding_adjustment",
@@ -106,9 +79,50 @@
"rounded_total",
"in_words",
"disable_rounded_total",
"terms_section_break",
"section_break_49",
"apply_discount_on",
"base_discount_amount",
"column_break_51",
"additional_discount_percentage",
"discount_amount",
"sec_tax_breakup",
"other_charges_calculation",
"packing_list",
"packed_items",
"product_bundle_help",
"pricing_rule_details",
"pricing_rules",
"address_and_contact_tab",
"contact_info",
"customer_address",
"address_display",
"col_break21",
"contact_person",
"contact_display",
"contact_mobile",
"contact_email",
"shipping_address_section",
"shipping_address_name",
"shipping_address",
"column_break_95",
"dispatch_address_name",
"dispatch_address",
"company_address_section",
"company_address",
"column_break_101",
"company_address_display",
"terms_tab",
"tc_name",
"terms",
"more_info_tab",
"section_break_83",
"per_billed",
"status",
"column_break_112",
"per_installed",
"installation_status",
"column_break_89",
"per_returned",
"transporter_info",
"transporter",
"driver",
@@ -118,56 +132,40 @@
"transporter_name",
"driver_name",
"lr_date",
"more_info",
"campaign",
"source",
"column_break5",
"is_internal_customer",
"represents_company",
"inter_company_reference",
"per_billed",
"customer_group",
"territory",
"printing_details",
"letter_head",
"select_print_heading",
"language",
"column_break_88",
"print_without_amount",
"group_same_items",
"section_break_83",
"status",
"per_installed",
"installation_status",
"column_break_89",
"per_returned",
"excise_page",
"instructions",
"subscription_section",
"auto_repeat",
"customer_po_details",
"po_no",
"column_break_17",
"po_date",
"sales_team_section_break",
"sales_partner",
"column_break7",
"amount_eligible_for_commission",
"column_break7",
"commission_rate",
"total_commission",
"section_break1",
"sales_team"
"sales_team",
"subscription_section",
"auto_repeat",
"printing_details",
"letter_head",
"print_without_amount",
"group_same_items",
"column_break_88",
"select_print_heading",
"language",
"more_info",
"is_internal_customer",
"represents_company",
"inter_company_reference",
"customer_group",
"territory",
"column_break5",
"excise_page",
"instructions",
"connections_tab",
"column_break_25"
],
"fields": [
{
"fieldname": "delivery_to_section",
"fieldtype": "Section Break",
"label": "Delivery To",
"options": "fa fa-user"
},
{
"fieldname": "column_break0",
"fieldtype": "Column Break",
"oldfieldtype": "Column Break",
"print_width": "50%",
"width": "50%"
},
{
"allow_on_submit": 1,
"default": "{customer_name}",
@@ -337,11 +335,10 @@
"width": "100px"
},
{
"collapsible": 1,
"depends_on": "customer",
"fieldname": "contact_info",
"fieldtype": "Section Break",
"label": "Address and Contact",
"label": "Billing Address",
"options": "fa fa-bullhorn"
},
{
@@ -493,10 +490,6 @@
"permlevel": 1,
"print_hide": 1
},
{
"fieldname": "sec_warehouse",
"fieldtype": "Section Break"
},
{
"fieldname": "set_warehouse",
"fieldtype": "Link",
@@ -511,6 +504,8 @@
{
"fieldname": "items_section",
"fieldtype": "Section Break",
"hide_border": 1,
"label": "Items",
"oldfieldtype": "Section Break",
"options": "fa fa-shopping-cart"
},
@@ -524,7 +519,6 @@
"allow_bulk_edit": 1,
"fieldname": "items",
"fieldtype": "Table",
"label": "Items",
"oldfieldname": "delivery_note_details",
"oldfieldtype": "Table",
"options": "Delivery Note Item",
@@ -619,6 +613,7 @@
"read_only": 1
},
{
"depends_on": "total_net_weight",
"fieldname": "total_net_weight",
"fieldtype": "Float",
"label": "Total Net Weight",
@@ -628,6 +623,7 @@
{
"fieldname": "taxes_section",
"fieldtype": "Section Break",
"hide_border": 1,
"label": "Taxes and Charges",
"oldfieldtype": "Section Break",
"options": "fa fa-money"
@@ -653,10 +649,10 @@
},
{
"fieldname": "section_break_41",
"fieldtype": "Section Break"
"fieldtype": "Section Break",
"hide_border": 1
},
{
"description": "If you have created a standard template in Sales Taxes and Charges Template, select one and click on the button below.",
"fieldname": "taxes_and_charges",
"fieldtype": "Link",
"label": "Sales Taxes and Charges Template",
@@ -668,7 +664,6 @@
{
"fieldname": "taxes",
"fieldtype": "Table",
"label": "Sales Taxes and Charges",
"oldfieldname": "other_charges",
"oldfieldtype": "Table",
"options": "Sales Taxes and Charges"
@@ -718,7 +713,6 @@
},
{
"collapsible": 1,
"collapsible_depends_on": "discount_amount",
"fieldname": "section_break_49",
"fieldtype": "Section Break",
"label": "Additional Discount"
@@ -759,6 +753,7 @@
{
"fieldname": "totals",
"fieldtype": "Section Break",
"label": "Totals",
"oldfieldtype": "Section Break",
"options": "fa fa-money"
},
@@ -863,15 +858,6 @@
"read_only": 1,
"width": "150px"
},
{
"collapsible": 1,
"collapsible_depends_on": "terms",
"fieldname": "terms_section_break",
"fieldtype": "Section Break",
"label": "Terms and Conditions",
"oldfieldtype": "Section Break",
"options": "fa fa-legal"
},
{
"fieldname": "tc_name",
"fieldtype": "Link",
@@ -965,13 +951,12 @@
"collapsible": 1,
"fieldname": "more_info",
"fieldtype": "Section Break",
"label": "More Information",
"label": "Additional Info",
"oldfieldtype": "Section Break",
"options": "fa fa-file-text",
"print_hide": 1
},
{
"description": "Track this Delivery Note against any Project",
"fieldname": "project",
"fieldtype": "Link",
"label": "Project",
@@ -1110,7 +1095,6 @@
},
{
"depends_on": "eval:!doc.__islocal",
"description": "% of materials delivered against this Delivery Note",
"fieldname": "per_installed",
"fieldtype": "Percent",
"in_list_view": 1,
@@ -1237,10 +1221,6 @@
"options": "Pick List",
"read_only": 1
},
{
"fieldname": "section_break_18",
"fieldtype": "Section Break"
},
{
"default": "0",
"fetch_from": "customer.is_internal_customer",
@@ -1329,13 +1309,85 @@
{
"fieldname": "dimension_col_break",
"fieldtype": "Column Break"
},
{
"fieldname": "address_and_contact_tab",
"fieldtype": "Tab Break",
"label": "Address & Contact"
},
{
"fieldname": "terms_tab",
"fieldtype": "Tab Break",
"label": "Terms"
},
{
"fieldname": "more_info_tab",
"fieldtype": "Tab Break",
"label": "More Info"
},
{
"fieldname": "connections_tab",
"fieldtype": "Tab Break",
"label": "Connections",
"show_dashboard": 1
},
{
"fieldname": "column_break_10",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_25",
"fieldtype": "Column Break"
},
{
"fieldname": "section_break_30",
"fieldtype": "Section Break",
"hide_border": 1
},
{
"fieldname": "column_break_35",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_43",
"fieldtype": "Column Break"
},
{
"fieldname": "custom_dimensions_section",
"fieldtype": "Section Break"
},
{
"fieldname": "shipping_address_section",
"fieldtype": "Section Break",
"label": "Shipping Address"
},
{
"fieldname": "column_break_95",
"fieldtype": "Column Break"
},
{
"fieldname": "company_address_section",
"fieldtype": "Section Break",
"label": "Company Address"
},
{
"fieldname": "column_break_101",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_112",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_18",
"fieldtype": "Column Break"
}
],
"icon": "fa fa-truck",
"idx": 146,
"is_submittable": 1,
"links": [],
"modified": "2022-09-16 17:46:17.701904",
"modified": "2022-10-11 13:06:58.655635",
"modified_by": "Administrator",
"module": "Stock",
"name": "Delivery Note",

View File

@@ -753,6 +753,7 @@
"fieldtype": "Currency",
"label": "Incoming Rate",
"no_copy": 1,
"precision": "6",
"print_hide": 1,
"read_only": 1
},
@@ -813,7 +814,7 @@
"index_web_pages_for_search": 1,
"istable": 1,
"links": [],
"modified": "2022-09-06 14:19:42.876357",
"modified": "2022-10-12 03:36:05.344847",
"modified_by": "Administrator",
"module": "Stock",
"name": "Delivery Note Item",

View File

@@ -32,7 +32,7 @@ test_ignore = ["BOM"]
test_dependencies = ["Warehouse", "Item Group", "Item Tax Template", "Brand", "Item Attribute"]
def make_item(item_code=None, properties=None):
def make_item(item_code=None, properties=None, uoms=None):
if not item_code:
item_code = frappe.generate_hash(length=16)
@@ -56,6 +56,11 @@ def make_item(item_code=None, properties=None):
for item_default in [doc for doc in item.get("item_defaults") if not doc.default_warehouse]:
item_default.default_warehouse = "_Test Warehouse - _TC"
item_default.company = "_Test Company"
if uoms:
for uom in uoms:
item.append("uoms", uom)
item.insert()
return item

View File

@@ -11,34 +11,40 @@
"naming_series",
"title",
"material_request_type",
"transfer_status",
"customer",
"status",
"company",
"column_break_2",
"transaction_date",
"schedule_date",
"company",
"amended_from",
"warehouse_section",
"scan_barcode",
"column_break_13",
"set_from_warehouse",
"column_break5",
"set_warehouse",
"items_section",
"scan_barcode",
"items",
"more_info",
"per_ordered",
"column_break2",
"per_received",
"printing_details",
"letter_head",
"select_print_heading",
"terms_tab",
"terms_section_break",
"tc_name",
"terms",
"more_info_tab",
"status_section",
"status",
"per_ordered",
"column_break2",
"transfer_status",
"per_received",
"printing_details",
"letter_head",
"column_break_31",
"select_print_heading",
"reference",
"job_card",
"work_order"
"column_break_35",
"work_order",
"connections_tab"
],
"fields": [
{
@@ -147,14 +153,6 @@
"options": "Material Request Item",
"reqd": 1
},
{
"collapsible": 1,
"fieldname": "more_info",
"fieldtype": "Section Break",
"label": "More Information",
"oldfieldtype": "Section Break",
"options": "fa fa-file-text"
},
{
"default": "Today",
"fieldname": "transaction_date",
@@ -239,7 +237,6 @@
"collapsible_depends_on": "terms",
"fieldname": "terms_section_break",
"fieldtype": "Section Break",
"label": "Terms and Conditions",
"oldfieldtype": "Section Break",
"options": "fa fa-legal"
},
@@ -277,10 +274,10 @@
{
"fieldname": "warehouse_section",
"fieldtype": "Section Break",
"label": "Warehouse"
"hide_border": 1,
"label": "Items"
},
{
"description": "Sets 'Target Warehouse' in each row of the Items table.",
"fieldname": "set_warehouse",
"fieldtype": "Link",
"in_list_view": 1,
@@ -296,7 +293,6 @@
},
{
"depends_on": "eval:doc.material_request_type == 'Material Transfer'",
"description": "Sets 'Source Warehouse' in each row of the Items table.",
"fieldname": "set_from_warehouse",
"fieldtype": "Link",
"label": "Set Source Warehouse",
@@ -317,13 +313,49 @@
"label": "Work Order",
"options": "Work Order",
"read_only": 1
},
{
"fieldname": "terms_tab",
"fieldtype": "Tab Break",
"label": "Terms"
},
{
"fieldname": "more_info_tab",
"fieldtype": "Tab Break",
"label": "More Info"
},
{
"fieldname": "connections_tab",
"fieldtype": "Tab Break",
"label": "Connections",
"show_dashboard": 1
},
{
"collapsible": 1,
"fieldname": "status_section",
"fieldtype": "Section Break",
"label": "Status",
"oldfieldtype": "Section Break",
"options": "fa fa-file-text"
},
{
"fieldname": "column_break_31",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_35",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_13",
"fieldtype": "Column Break"
}
],
"icon": "fa fa-ticket",
"idx": 70,
"is_submittable": 1,
"links": [],
"modified": "2022-08-25 11:49:28.155048",
"modified": "2022-09-27 17:58:26.366469",
"modified_by": "Administrator",
"module": "Stock",
"name": "Material Request",

View File

@@ -17,10 +17,11 @@
"supplier_name",
"supplier_delivery_note",
"column_break1",
"company",
"posting_date",
"posting_time",
"set_posting_time",
"column_break_12",
"company",
"apply_putaway_rule",
"is_return",
"return_against",
@@ -28,18 +29,6 @@
"cost_center",
"dimension_col_break",
"project",
"section_addresses",
"supplier_address",
"contact_person",
"address_display",
"contact_display",
"contact_mobile",
"contact_email",
"col_break_address",
"shipping_address",
"shipping_address_display",
"billing_address",
"billing_address_display",
"currency_and_price_list",
"currency",
"conversion_rate",
@@ -49,37 +38,33 @@
"plc_conversion_rate",
"ignore_pricing_rule",
"sec_warehouse",
"scan_barcode",
"column_break_31",
"set_warehouse",
"rejected_warehouse",
"col_break_warehouse",
"set_from_warehouse",
"col_break_warehouse",
"rejected_warehouse",
"is_subcontracted",
"supplier_warehouse",
"items_section",
"scan_barcode",
"items",
"section_break0",
"total_qty",
"total_net_weight",
"column_break_43",
"base_total",
"base_net_total",
"column_break_27",
"total_net_weight",
"total",
"net_total",
"pricing_rule_details",
"pricing_rules",
"raw_material_details",
"get_current_stock",
"supplied_items",
"taxes_charges_section",
"tax_category",
"taxes_and_charges",
"shipping_col",
"tax_category",
"column_break_53",
"shipping_rule",
"taxes_section",
"taxes_and_charges",
"taxes",
"sec_tax_breakup",
"other_charges_calculation",
"totals",
"base_taxes_and_charges_added",
"base_taxes_and_charges_deducted",
@@ -88,53 +73,81 @@
"taxes_and_charges_added",
"taxes_and_charges_deducted",
"total_taxes_and_charges",
"section_break_42",
"apply_discount_on",
"base_discount_amount",
"column_break_44",
"additional_discount_percentage",
"discount_amount",
"section_break_46",
"base_grand_total",
"base_rounding_adjustment",
"base_in_words",
"base_rounded_total",
"base_in_words",
"column_break_50",
"grand_total",
"rounding_adjustment",
"rounded_total",
"in_words",
"disable_rounded_total",
"terms_section_break",
"section_break_42",
"apply_discount_on",
"base_discount_amount",
"column_break_44",
"additional_discount_percentage",
"discount_amount",
"sec_tax_breakup",
"other_charges_calculation",
"pricing_rule_details",
"pricing_rules",
"raw_material_details",
"get_current_stock",
"supplied_items",
"address_and_contact_tab",
"section_addresses",
"supplier_address",
"address_display",
"col_break_address",
"contact_person",
"contact_display",
"contact_mobile",
"contact_email",
"section_break_98",
"shipping_address",
"column_break_100",
"shipping_address_display",
"billing_address_section",
"billing_address",
"column_break_104",
"billing_address_display",
"terms_tab",
"tc_name",
"terms",
"more_info",
"more_info_tab",
"status_section",
"status",
"amended_from",
"range",
"column_break4",
"per_billed",
"per_returned",
"is_internal_supplier",
"inter_company_reference",
"represents_company",
"subscription_detail",
"auto_repeat",
"printing_settings",
"letter_head",
"language",
"instructions",
"group_same_items",
"column_break_97",
"select_print_heading",
"other_details",
"remarks",
"group_same_items",
"language",
"transporter_info",
"transporter_name",
"column_break5",
"lr_no",
"lr_date",
"is_old_subcontracting_flow"
"additional_info_section",
"instructions",
"is_internal_supplier",
"represents_company",
"inter_company_reference",
"column_break_131",
"remarks",
"range",
"amended_from",
"is_old_subcontracting_flow",
"other_details",
"connections_tab"
],
"fields": [
{
@@ -223,7 +236,6 @@
"width": "100px"
},
{
"description": "Time at which materials were received",
"fieldname": "posting_time",
"fieldtype": "Time",
"label": "Posting Time",
@@ -277,15 +289,14 @@
"read_only": 1
},
{
"collapsible": 1,
"fieldname": "section_addresses",
"fieldtype": "Section Break",
"label": "Address and Contact"
"label": "Supplier Address"
},
{
"fieldname": "supplier_address",
"fieldtype": "Link",
"label": "Select Supplier Address",
"label": "Supplier Address",
"options": "Address",
"print_hide": 1
},
@@ -330,7 +341,7 @@
{
"fieldname": "shipping_address",
"fieldtype": "Link",
"label": "Select Shipping Address",
"label": "Shipping Address Template",
"options": "Address",
"print_hide": 1
},
@@ -410,10 +421,11 @@
},
{
"fieldname": "sec_warehouse",
"fieldtype": "Section Break"
"fieldtype": "Section Break",
"hide_border": 1,
"label": "Items"
},
{
"description": "Sets 'Accepted Warehouse' in each row of the items table.",
"fieldname": "set_warehouse",
"fieldtype": "Link",
"label": "Accepted Warehouse",
@@ -421,7 +433,6 @@
"print_hide": 1
},
{
"description": "Sets 'Rejected Warehouse' in each row of the items table.",
"fieldname": "rejected_warehouse",
"fieldtype": "Link",
"label": "Rejected Warehouse",
@@ -461,6 +472,7 @@
{
"fieldname": "items_section",
"fieldtype": "Section Break",
"hide_border": 1,
"oldfieldtype": "Section Break",
"options": "fa fa-shopping-cart"
},
@@ -571,6 +583,7 @@
"read_only": 1
},
{
"depends_on": "total_net_weight",
"fieldname": "total_net_weight",
"fieldtype": "Float",
"label": "Total Net Weight",
@@ -578,11 +591,11 @@
"read_only": 1
},
{
"description": "Add / Edit Taxes and Charges",
"fieldname": "taxes_charges_section",
"fieldtype": "Section Break",
"oldfieldtype": "Section Break",
"options": "fa fa-money"
"hide_border": 1,
"label": "Taxes and Charges",
"oldfieldtype": "Section Break"
},
{
"fieldname": "tax_category",
@@ -603,7 +616,8 @@
},
{
"fieldname": "taxes_section",
"fieldtype": "Section Break"
"fieldtype": "Section Break",
"hide_border": 1
},
{
"fieldname": "taxes_and_charges",
@@ -709,7 +723,6 @@
},
{
"collapsible": 1,
"collapsible_depends_on": "discount_amount",
"fieldname": "section_break_42",
"fieldtype": "Section Break",
"label": "Additional Discount"
@@ -749,7 +762,8 @@
},
{
"fieldname": "section_break_46",
"fieldtype": "Section Break"
"fieldtype": "Section Break",
"label": "Totals"
},
{
"fieldname": "base_grand_total",
@@ -841,15 +855,6 @@
"fieldtype": "Check",
"label": "Disable Rounded Total"
},
{
"collapsible": 1,
"collapsible_depends_on": "terms",
"fieldname": "terms_section_break",
"fieldtype": "Section Break",
"label": "Terms and Conditions",
"oldfieldtype": "Section Break",
"options": "fa fa-legal"
},
{
"fieldname": "tc_name",
"fieldtype": "Link",
@@ -866,14 +871,6 @@
"oldfieldname": "terms",
"oldfieldtype": "Text Editor"
},
{
"collapsible": 1,
"fieldname": "more_info",
"fieldtype": "Section Break",
"label": "More Information",
"oldfieldtype": "Section Break",
"options": "fa fa-file-text"
},
{
"default": "Draft",
"fieldname": "status",
@@ -924,7 +921,6 @@
"width": "50%"
},
{
"description": "Track this Purchase Receipt against any Project",
"fieldname": "project",
"fieldtype": "Link",
"label": "Project",
@@ -941,7 +937,7 @@
{
"fieldname": "subscription_detail",
"fieldtype": "Section Break",
"label": "Auto Repeat Detail"
"label": "Auto Repeat"
},
{
"fieldname": "auto_repeat",
@@ -1025,7 +1021,7 @@
"collapsible_depends_on": "transporter_name",
"fieldname": "transporter_info",
"fieldtype": "Section Break",
"label": "Transporter Details",
"label": "Transporter",
"options": "fa fa-truck"
},
{
@@ -1087,7 +1083,7 @@
{
"fieldname": "billing_address",
"fieldtype": "Link",
"label": "Select Billing Address",
"label": "Billing Address",
"options": "Address"
},
{
@@ -1113,7 +1109,6 @@
},
{
"depends_on": "eval: doc.is_internal_supplier",
"description": "Sets 'From Warehouse' in each row of the items table.",
"fieldname": "set_from_warehouse",
"fieldtype": "Link",
"label": "Set From Warehouse",
@@ -1151,13 +1146,85 @@
"hidden": 1,
"label": "Is Old Subcontracting Flow",
"read_only": 1
},
{
"fieldname": "address_and_contact_tab",
"fieldtype": "Tab Break",
"label": "Address & Contact"
},
{
"fieldname": "terms_tab",
"fieldtype": "Tab Break",
"label": "Terms"
},
{
"fieldname": "more_info_tab",
"fieldtype": "Tab Break",
"label": "More Info"
},
{
"fieldname": "connections_tab",
"fieldtype": "Tab Break",
"label": "Connections",
"show_dashboard": 1
},
{
"fieldname": "column_break_12",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_31",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_43",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_53",
"fieldtype": "Column Break"
},
{
"fieldname": "section_break_98",
"fieldtype": "Section Break",
"label": "Company Shipping Address"
},
{
"fieldname": "billing_address_section",
"fieldtype": "Section Break",
"label": "Company Billing Address"
},
{
"collapsible": 1,
"fieldname": "status_section",
"fieldtype": "Section Break",
"label": "Status",
"oldfieldtype": "Section Break",
"options": "fa fa-file-text"
},
{
"fieldname": "additional_info_section",
"fieldtype": "Section Break",
"label": "Additional Info"
},
{
"fieldname": "column_break_131",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_100",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_104",
"fieldtype": "Column Break"
}
],
"icon": "fa fa-truck",
"idx": 261,
"is_submittable": 1,
"links": [],
"modified": "2022-09-16 17:45:58.430132",
"modified": "2022-10-11 13:02:31.776256",
"modified_by": "Administrator",
"module": "Stock",
"name": "Purchase Receipt",

View File

@@ -1,7 +1,6 @@
# Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors
# License: GNU General Public License v3. See license.txt
import frappe
from frappe.tests.utils import FrappeTestCase, change_settings
from frappe.utils import add_days, cint, cstr, flt, today
@@ -1199,6 +1198,8 @@ class TestPurchaseReceipt(FrappeTestCase):
self.assertEqual(pr1.items[0].rate, 100)
pr1.submit()
self.assertEqual(pr1.is_internal_supplier, 1)
# Backdated purchase receipt entry, the valuation rate should be updated for DN1 and PR1
make_purchase_receipt(
item_code=item_doc.name,
@@ -1241,6 +1242,234 @@ class TestPurchaseReceipt(FrappeTestCase):
self.assertEqual(query[0].value, 0)
def test_backdated_transaction_for_internal_transfer_in_trasit_warehouse_for_purchase_receipt(
self,
):
from erpnext.stock.doctype.delivery_note.delivery_note import make_inter_company_purchase_receipt
from erpnext.stock.doctype.delivery_note.test_delivery_note import create_delivery_note
prepare_data_for_internal_transfer()
customer = "_Test Internal Customer 2"
company = "_Test Company with perpetual inventory"
from_warehouse = create_warehouse("_Test Internal From Warehouse New", company=company)
to_warehouse = create_warehouse("_Test Internal To Warehouse New", company=company)
item_doc = create_item("Test Internal Transfer Item")
target_warehouse = create_warehouse("_Test Internal GIT Warehouse New", company=company)
make_purchase_receipt(
item_code=item_doc.name,
company=company,
posting_date=add_days(today(), -1),
warehouse=from_warehouse,
qty=1,
rate=100,
)
# Keep stock in advance and make sure that systen won't pick this stock while reposting backdated transaction
for i in range(1, 4):
make_purchase_receipt(
item_code=item_doc.name,
company=company,
posting_date=add_days(today(), -1 * i),
warehouse=target_warehouse,
qty=1,
rate=320 * i,
)
dn1 = create_delivery_note(
item_code=item_doc.name,
company=company,
customer=customer,
cost_center="Main - TCP1",
expense_account="Cost of Goods Sold - TCP1",
qty=1,
rate=500,
warehouse=from_warehouse,
target_warehouse=target_warehouse,
)
self.assertEqual(dn1.items[0].rate, 100)
pr1 = make_inter_company_purchase_receipt(dn1.name)
pr1.items[0].warehouse = to_warehouse
self.assertEqual(pr1.items[0].rate, 100)
pr1.submit()
stk_ledger = frappe.db.get_value(
"Stock Ledger Entry",
{"voucher_type": "Purchase Receipt", "voucher_no": pr1.name, "warehouse": target_warehouse},
["stock_value_difference", "outgoing_rate"],
as_dict=True,
)
self.assertEqual(abs(stk_ledger.stock_value_difference), 100)
self.assertEqual(stk_ledger.outgoing_rate, 100)
# Backdated purchase receipt entry, the valuation rate should be updated for DN1 and PR1
make_purchase_receipt(
item_code=item_doc.name,
company=company,
posting_date=add_days(today(), -2),
warehouse=from_warehouse,
qty=1,
rate=200,
)
dn_value = frappe.db.get_value(
"Stock Ledger Entry",
{"voucher_type": "Delivery Note", "voucher_no": dn1.name, "warehouse": target_warehouse},
"stock_value_difference",
)
self.assertEqual(abs(dn_value), 200.00)
pr_value = frappe.db.get_value(
"Stock Ledger Entry",
{"voucher_type": "Purchase Receipt", "voucher_no": pr1.name, "warehouse": to_warehouse},
"stock_value_difference",
)
self.assertEqual(abs(pr_value), 200.00)
pr1.load_from_db()
self.assertEqual(pr1.items[0].valuation_rate, 200)
self.assertEqual(pr1.items[0].rate, 100)
Gl = frappe.qb.DocType("GL Entry")
query = (
frappe.qb.from_(Gl)
.select(
(fn.Sum(Gl.debit) - fn.Sum(Gl.credit)).as_("value"),
)
.where((Gl.voucher_type == pr1.doctype) & (Gl.voucher_no == pr1.name))
).run(as_dict=True)
self.assertEqual(query[0].value, 0)
def test_backdated_transaction_for_internal_transfer_in_trasit_warehouse_for_purchase_invoice(
self,
):
from erpnext.accounts.doctype.purchase_invoice.test_purchase_invoice import (
make_purchase_invoice as make_purchase_invoice_for_si,
)
from erpnext.accounts.doctype.sales_invoice.sales_invoice import (
make_inter_company_purchase_invoice,
)
from erpnext.accounts.doctype.sales_invoice.test_sales_invoice import create_sales_invoice
prepare_data_for_internal_transfer()
customer = "_Test Internal Customer 2"
company = "_Test Company with perpetual inventory"
from_warehouse = create_warehouse("_Test Internal From Warehouse New", company=company)
to_warehouse = create_warehouse("_Test Internal To Warehouse New", company=company)
item_doc = create_item("Test Internal Transfer Item")
target_warehouse = create_warehouse("_Test Internal GIT Warehouse New", company=company)
make_purchase_invoice_for_si(
item_code=item_doc.name,
company=company,
posting_date=add_days(today(), -1),
warehouse=from_warehouse,
qty=1,
update_stock=1,
expense_account="Cost of Goods Sold - TCP1",
cost_center="Main - TCP1",
rate=100,
)
# Keep stock in advance and make sure that systen won't pick this stock while reposting backdated transaction
for i in range(1, 4):
make_purchase_invoice_for_si(
item_code=item_doc.name,
company=company,
posting_date=add_days(today(), -1 * i),
warehouse=target_warehouse,
update_stock=1,
qty=1,
expense_account="Cost of Goods Sold - TCP1",
cost_center="Main - TCP1",
rate=320 * i,
)
si1 = create_sales_invoice(
item_code=item_doc.name,
company=company,
customer=customer,
cost_center="Main - TCP1",
income_account="Sales - TCP1",
qty=1,
rate=500,
update_stock=1,
warehouse=from_warehouse,
target_warehouse=target_warehouse,
)
self.assertEqual(si1.items[0].rate, 100)
pi1 = make_inter_company_purchase_invoice(si1.name)
pi1.items[0].warehouse = to_warehouse
self.assertEqual(pi1.items[0].rate, 100)
pi1.update_stock = 1
pi1.save()
pi1.submit()
stk_ledger = frappe.db.get_value(
"Stock Ledger Entry",
{"voucher_type": pi1.doctype, "voucher_no": pi1.name, "warehouse": target_warehouse},
["stock_value_difference", "outgoing_rate"],
as_dict=True,
)
self.assertEqual(abs(stk_ledger.stock_value_difference), 100)
self.assertEqual(stk_ledger.outgoing_rate, 100)
# Backdated purchase receipt entry, the valuation rate should be updated for si1 and pi1
make_purchase_receipt(
item_code=item_doc.name,
company=company,
posting_date=add_days(today(), -2),
warehouse=from_warehouse,
qty=1,
rate=200,
)
si_value = frappe.db.get_value(
"Stock Ledger Entry",
{"voucher_type": si1.doctype, "voucher_no": si1.name, "warehouse": target_warehouse},
"stock_value_difference",
)
self.assertEqual(abs(si_value), 200.00)
pi_value = frappe.db.get_value(
"Stock Ledger Entry",
{"voucher_type": pi1.doctype, "voucher_no": pi1.name, "warehouse": to_warehouse},
"stock_value_difference",
)
self.assertEqual(abs(pi_value), 200.00)
pi1.load_from_db()
self.assertEqual(pi1.items[0].valuation_rate, 200)
self.assertEqual(pi1.items[0].rate, 100)
Gl = frappe.qb.DocType("GL Entry")
query = (
frappe.qb.from_(Gl)
.select(
(fn.Sum(Gl.debit) - fn.Sum(Gl.credit)).as_("value"),
)
.where((Gl.voucher_type == pi1.doctype) & (Gl.voucher_no == pi1.name))
).run(as_dict=True)
self.assertEqual(query[0].value, 0)
def test_batch_expiry_for_purchase_receipt(self):
from erpnext.controllers.sales_and_purchase_return import make_return_doc

View File

@@ -744,6 +744,7 @@
"oldfieldname": "valuation_rate",
"oldfieldtype": "Currency",
"options": "Company:company:default_currency",
"precision": "6",
"print_hide": 1,
"print_width": "80px",
"read_only": 1,
@@ -999,7 +1000,7 @@
"idx": 1,
"istable": 1,
"links": [],
"modified": "2022-07-28 19:27:54.880781",
"modified": "2022-10-12 03:37:59.516609",
"modified_by": "Administrator",
"module": "Stock",
"name": "Purchase Receipt Item",

View File

@@ -10,6 +10,7 @@
"naming_series",
"report_date",
"status",
"manual_inspection",
"column_break_4",
"inspection_type",
"reference_type",
@@ -231,6 +232,12 @@
"label": "Status",
"options": "\nAccepted\nRejected",
"reqd": 1
},
{
"default": "0",
"fieldname": "manual_inspection",
"fieldtype": "Check",
"label": "Manual Inspection"
}
],
"icon": "fa fa-search",
@@ -238,10 +245,11 @@
"index_web_pages_for_search": 1,
"is_submittable": 1,
"links": [],
"modified": "2020-12-18 19:59:55.710300",
"modified": "2022-10-04 22:00:13.995221",
"modified_by": "Administrator",
"module": "Stock",
"name": "Quality Inspection",
"naming_rule": "By \"Naming Series\" field",
"owner": "Administrator",
"permissions": [
{
@@ -262,5 +270,6 @@
"search_fields": "item_code, report_date, reference_name",
"show_name_in_global_search": 1,
"sort_field": "modified",
"sort_order": "ASC"
"sort_order": "ASC",
"states": []
}

View File

@@ -30,6 +30,9 @@ class QualityInspection(Document):
if self.readings:
self.inspect_and_set_status()
def before_submit(self):
self.validate_readings_status_mandatory()
@frappe.whitelist()
def get_item_specification_details(self):
if not self.quality_inspection_template:
@@ -65,6 +68,11 @@ class QualityInspection(Document):
def on_cancel(self):
self.update_qc_reference()
def validate_readings_status_mandatory(self):
for reading in self.readings:
if not reading.status:
frappe.throw(_("Row #{0}: Status is mandatory").format(reading.idx))
def update_qc_reference(self):
quality_inspection = self.name if self.docstatus == 1 else ""
@@ -124,6 +132,16 @@ class QualityInspection(Document):
# if not formula based check acceptance values set
self.set_status_based_on_acceptance_values(reading)
if not self.manual_inspection:
self.status = "Accepted"
for reading in self.readings:
if reading.status == "Rejected":
self.status = "Rejected"
frappe.msgprint(
_("Status set to rejected as there are one or more rejected readings."), alert=True
)
break
def set_status_based_on_acceptance_values(self, reading):
if not cint(reading.numeric):
result = reading.get("reading_value") == reading.get("value")

View File

@@ -160,7 +160,7 @@ class TestQualityInspection(FrappeTestCase):
)
readings = [
{"specification": "Iron Content", "min_value": 0.1, "max_value": 0.9, "reading_1": "0.4"}
{"specification": "Iron Content", "min_value": 0.1, "max_value": 0.9, "reading_1": "1.0"}
]
qa = create_quality_inspection(
@@ -184,6 +184,38 @@ class TestQualityInspection(FrappeTestCase):
se.cancel()
frappe.db.set_value("Stock Settings", None, "action_if_quality_inspection_is_rejected", "Stop")
def test_qi_status(self):
make_stock_entry(
item_code="_Test Item with QA", target="_Test Warehouse - _TC", qty=1, basic_rate=100
)
dn = create_delivery_note(item_code="_Test Item with QA", do_not_submit=True)
qa = create_quality_inspection(
reference_type="Delivery Note", reference_name=dn.name, status="Accepted", do_not_save=True
)
qa.readings[0].manual_inspection = 1
qa.save()
# Case - 1: When there are one or more readings with rejected status and parent manual inspection is unchecked, then parent status should be set to rejected.
qa.status = "Accepted"
qa.manual_inspection = 0
qa.readings[0].status = "Rejected"
qa.save()
self.assertEqual(qa.status, "Rejected")
# Case - 2: When all readings have accepted status and parent manual inspection is unchecked, then parent status should be set to accepted.
qa.status = "Rejected"
qa.manual_inspection = 0
qa.readings[0].status = "Accepted"
qa.save()
self.assertEqual(qa.status, "Accepted")
# Case - 3: When parent manual inspection is checked, then parent status should not be changed.
qa.status = "Accepted"
qa.manual_inspection = 1
qa.readings[0].status = "Rejected"
qa.save()
self.assertEqual(qa.status, "Accepted")
def create_quality_inspection(**args):
args = frappe._dict(args)

View File

@@ -128,6 +128,9 @@ def repost(doc):
if not frappe.db.exists("Repost Item Valuation", doc.name):
return
# This is to avoid TooManyWritesError in case of large reposts
frappe.db.MAX_WRITES_PER_TRANSACTION *= 4
doc.set_status("In Progress")
if not frappe.flags.in_test:
frappe.db.commit()

View File

@@ -846,16 +846,15 @@ def get_pos_reserved_serial_nos(filters):
pos_transacted_sr_nos = query.run(as_dict=True)
reserved_sr_nos = []
returned_sr_nos = []
reserved_sr_nos = set()
returned_sr_nos = set()
for d in pos_transacted_sr_nos:
if d.is_return == 0:
reserved_sr_nos += get_serial_nos(d.serial_no)
[reserved_sr_nos.add(x) for x in get_serial_nos(d.serial_no)]
elif d.is_return == 1:
returned_sr_nos += get_serial_nos(d.serial_no)
[returned_sr_nos.add(x) for x in get_serial_nos(d.serial_no)]
for sr_no in returned_sr_nos:
reserved_sr_nos.remove(sr_no)
reserved_sr_nos = list(reserved_sr_nos - returned_sr_nos)
return reserved_sr_nos

View File

@@ -148,19 +148,19 @@
"search_index": 1
},
{
"depends_on": "eval:doc.purpose==\"Send to Subcontractor\"",
"fieldname": "purchase_order",
"fieldtype": "Link",
"label": "Purchase Order",
"options": "Purchase Order"
"depends_on": "eval:doc.purpose==\"Send to Subcontractor\"",
"fieldname": "purchase_order",
"fieldtype": "Link",
"label": "Purchase Order",
"options": "Purchase Order"
},
{
"depends_on": "eval:doc.purpose==\"Send to Subcontractor\"",
"fieldname": "subcontracting_order",
"fieldtype": "Link",
"label": "Subcontracting Order",
"options": "Subcontracting Order"
},
"depends_on": "eval:doc.purpose==\"Send to Subcontractor\"",
"fieldname": "subcontracting_order",
"fieldtype": "Link",
"label": "Subcontracting Order",
"options": "Subcontracting Order"
},
{
"depends_on": "eval:doc.purpose==\"Sales Return\"",
"fieldname": "delivery_note_no",
@@ -616,6 +616,7 @@
"fieldname": "is_return",
"fieldtype": "Check",
"hidden": 1,
"in_list_view": 1,
"label": "Is Return",
"no_copy": 1,
"print_hide": 1,
@@ -627,7 +628,7 @@
"index_web_pages_for_search": 1,
"is_submittable": 1,
"links": [],
"modified": "2022-05-02 05:21:39.060501",
"modified": "2022-10-07 14:39:51.943770",
"modified_by": "Administrator",
"module": "Stock",
"name": "Stock Entry",

View File

@@ -1212,13 +1212,19 @@ class StockEntry(StockController):
def update_work_order(self):
def _validate_work_order(pro_doc):
msg, title = "", ""
if flt(pro_doc.docstatus) != 1:
frappe.throw(_("Work Order {0} must be submitted").format(self.work_order))
msg = f"Work Order {self.work_order} must be submitted"
if pro_doc.status == "Stopped":
frappe.throw(
_("Transaction not allowed against stopped Work Order {0}").format(self.work_order)
)
msg = f"Transaction not allowed against stopped Work Order {self.work_order}"
if self.is_return and pro_doc.status not in ["Completed", "Closed"]:
title = _("Stock Return")
msg = f"Work Order {self.work_order} must be completed or closed"
if msg:
frappe.throw(_(msg), title=title)
if self.job_card:
job_doc = frappe.get_doc("Job Card", self.job_card)
@@ -1754,10 +1760,12 @@ class StockEntry(StockController):
for key, row in available_materials.items():
remaining_qty_to_produce = flt(wo_data.trans_qty) - flt(wo_data.produced_qty)
if remaining_qty_to_produce <= 0:
if remaining_qty_to_produce <= 0 and not self.is_return:
continue
qty = (flt(row.qty) * flt(self.fg_completed_qty)) / remaining_qty_to_produce
qty = flt(row.qty)
if not self.is_return:
qty = (flt(row.qty) * flt(self.fg_completed_qty)) / remaining_qty_to_produce
item = row.item_details
if cint(frappe.get_cached_value("UOM", item.stock_uom, "must_be_whole_number")):
@@ -1781,6 +1789,9 @@ class StockEntry(StockController):
self.update_item_in_stock_entry_detail(row, item, qty)
def update_item_in_stock_entry_detail(self, row, item, qty) -> None:
if not qty:
return
ste_item_details = {
"from_warehouse": item.warehouse,
"to_warehouse": "",
@@ -1794,6 +1805,9 @@ class StockEntry(StockController):
"original_item": item.original_item,
}
if self.is_return:
ste_item_details["to_warehouse"] = item.s_warehouse
if row.serial_nos:
serial_nos = row.serial_nos
if item.batch_no:

View File

@@ -1,8 +1,13 @@
frappe.listview_settings['Stock Entry'] = {
add_fields: ["`tabStock Entry`.`from_warehouse`", "`tabStock Entry`.`to_warehouse`",
"`tabStock Entry`.`purpose`", "`tabStock Entry`.`work_order`", "`tabStock Entry`.`bom_no`"],
"`tabStock Entry`.`purpose`", "`tabStock Entry`.`work_order`", "`tabStock Entry`.`bom_no`",
"`tabStock Entry`.`is_return`"],
get_indicator: function (doc) {
if (doc.docstatus === 0) {
debugger
if(doc.is_return===1 && doc.purpose === "Material Transfer for Manufacture") {
return [__("Material Returned from WIP"), "orange",
"is_return,=,1|purpose,=,Material Transfer for Manufacture|docstatus,<,2"];
} else if (doc.docstatus === 0) {
return [__("Draft"), "red", "docstatus,=,0"];
} else if (doc.purpose === 'Send to Warehouse' && doc.per_transferred < 100) {

View File

@@ -1323,13 +1323,15 @@ def create_product_bundle_item(new_item_code, packed_items):
item.save()
def create_items():
items = [
"_Test Item for Reposting",
"_Test Finished Item for Reposting",
"_Test Subcontracted Item for Reposting",
"_Test Bundled Item for Reposting",
]
def create_items(items=None, uoms=None):
if not items:
items = [
"_Test Item for Reposting",
"_Test Finished Item for Reposting",
"_Test Subcontracted Item for Reposting",
"_Test Bundled Item for Reposting",
]
for d in items:
properties = {"valuation_method": "FIFO"}
if d == "_Test Bundled Item for Reposting":
@@ -1337,7 +1339,7 @@ def create_items():
elif d == "_Test Subcontracted Item for Reposting":
properties.update({"is_sub_contracted_item": 1})
make_item(d, properties=properties)
make_item(d, properties=properties, uoms=uoms)
return items

View File

@@ -132,7 +132,9 @@ class StockReconciliation(StockController):
key.append(row.get(field))
if key in item_warehouse_combinations:
self.validation_messages.append(_get_msg(row_num, _("Duplicate entry")))
self.validation_messages.append(
_get_msg(row_num, _("Same item and warehouse combination already entered."))
)
else:
item_warehouse_combinations.append(key)

View File

@@ -542,6 +542,14 @@ class update_entries_after(object):
if not self.args.get("sle_id"):
self.get_dynamic_incoming_outgoing_rate(sle)
if (
sle.voucher_type in ["Purchase Receipt", "Purchase Invoice"]
and sle.voucher_detail_no
and sle.actual_qty < 0
and frappe.get_cached_value(sle.voucher_type, sle.voucher_no, "is_internal_supplier")
):
sle.outgoing_rate = get_incoming_rate_for_inter_company_transfer(sle)
if get_serial_nos(sle.serial_no):
self.get_serialized_values(sle)
self.wh_data.qty_after_transaction += flt(sle.actual_qty)
@@ -589,6 +597,7 @@ class update_entries_after(object):
sle.stock_queue = json.dumps(self.wh_data.stock_queue)
sle.stock_value_difference = stock_value_difference
sle.doctype = "Stock Ledger Entry"
frappe.get_doc(sle).db_update()
if not self.args.get("sle_id"):
@@ -652,22 +661,7 @@ class update_entries_after(object):
and sle.voucher_detail_no
and frappe.get_cached_value(sle.voucher_type, sle.voucher_no, "is_internal_supplier")
):
field = (
"delivery_note_item" if sle.voucher_type == "Purchase Receipt" else "sales_invoice_item"
)
doctype = (
"Delivery Note Item" if sle.voucher_type == "Purchase Receipt" else "Sales Invoice Item"
)
refernce_name = frappe.get_cached_value(
sle.voucher_type + " Item", sle.voucher_detail_no, field
)
if refernce_name:
rate = frappe.get_cached_value(
doctype,
refernce_name,
"incoming_rate",
)
rate = get_incoming_rate_for_inter_company_transfer(sle)
else:
if sle.voucher_type in ("Purchase Receipt", "Purchase Invoice"):
rate_field = "valuation_rate"
@@ -748,14 +742,12 @@ class update_entries_after(object):
def update_rate_on_purchase_receipt(self, sle, outgoing_rate):
if frappe.db.exists(sle.voucher_type + " Item", sle.voucher_detail_no):
frappe.db.set_value(
sle.voucher_type + " Item",
sle.voucher_detail_no,
{
"base_net_rate": outgoing_rate,
"valuation_rate": outgoing_rate,
},
)
if sle.voucher_type in ["Purchase Receipt", "Purchase Invoice"] and frappe.get_cached_value(
sle.voucher_type, sle.voucher_no, "is_internal_supplier"
):
frappe.db.set_value(
f"{sle.voucher_type} Item", sle.voucher_detail_no, "valuation_rate", sle.outgoing_rate
)
else:
frappe.db.set_value(
"Purchase Receipt Item Supplied", sle.voucher_detail_no, "rate", outgoing_rate
@@ -1053,7 +1045,7 @@ class update_entries_after(object):
updated_values = {"actual_qty": data.qty_after_transaction, "stock_value": data.stock_value}
if data.valuation_rate is not None:
updated_values["valuation_rate"] = data.valuation_rate
frappe.db.set_value("Bin", bin_name, updated_values)
frappe.db.set_value("Bin", bin_name, updated_values, update_modified=True)
def get_previous_sle_of_current_voucher(args, exclude_current_voucher=False):
@@ -1546,3 +1538,25 @@ def is_negative_stock_allowed(*, item_code: Optional[str] = None) -> bool:
if item_code and cint(frappe.db.get_value("Item", item_code, "allow_negative_stock", cache=True)):
return True
return False
def get_incoming_rate_for_inter_company_transfer(sle) -> float:
"""
For inter company transfer, incoming rate is the average of the outgoing rate
"""
rate = 0.0
field = "delivery_note_item" if sle.voucher_type == "Purchase Receipt" else "sales_invoice_item"
doctype = "Delivery Note Item" if sle.voucher_type == "Purchase Receipt" else "Sales Invoice Item"
reference_name = frappe.get_cached_value(sle.voucher_type + " Item", sle.voucher_detail_no, field)
if reference_name:
rate = frappe.get_cached_value(
doctype,
reference_name,
"incoming_rate",
)
return rate

View File

@@ -1,77 +0,0 @@
{% extends "templates/web.html" %}
{% block script %}
<script>
$(document).ready(function() {
$("#login_btn").click(function() {
var me = this;
$(this).html("Logging In...").prop("disabled", true);
frappe.call({
"method": "login",
args: {
usr: "demo@erpnext.com",
pwd: "Demo1234567!!!",
lead_email: $("#lead-email").val(),
},
callback: function(r) {
$(me).prop("disabled", false);
if(r.exc) {
alert("Error, please contact support@erpnext.com");
} else {
console.log("Logged In");
window.location.href = "desk";
}
}
})
return false;
})
.prop("disabled", false);
})
</script>
{% endblock %}
{% block style %}
<style>
footer, .navbar {
display: none;
}
.page-content {
right: 0%;
width: 100%;
}
{% include "templates/styles/card_style.css" %}
header, footer {
display: none;
}
html, body {
background-color: #f5f7fa;
}
</style>
{% endblock %}
{% block title %}
{{ _("ERPNext Demo") }}
{% endblock %}
{% block page_content %}
<div class='page-card'>
<div class='page-card-head'>
<span class='indicator blue'>
{{ _("ERPNext Demo") }}</span>
</div>
<!-- <img src="/assets/erpnext/images/erp-icon.svg" style="max-width: 40px; max-height: 40px;"> -->
<p>Some functionality is disabled for the demo and the data will be cleared regularly.</p>
<div><button type="submit" id="login_btn" class="btn btn-primary btn-sm">Launch Demo</button></div>
</div>
<p class='text-muted text-center small' style='margin-top: -20px;'><a href="https://erpnext.com/pricing">Start a free 14-day trial </a>
</p>
<style>
html, body {
background-color: #f5f7fa;
}
</style>
{% endblock %}

View File

@@ -785,7 +785,7 @@ Default BOM for {0} not found,Nomenclature par défaut {0} introuvable,
Default BOM not found for Item {0} and Project {1},La nomenclature par défaut n'a pas été trouvée pour l'Article {0} et le Projet {1},
Default Letter Head,En-Tête de Courrier par Défaut,
Default Tax Template,Modèle de Taxes par Défaut,
Default Unit of Measure for Item {0} cannot be changed directly because you have already made some transaction(s) with another UOM. You will need to create a new Item to use a different Default UOM.,LUnité de Mesure par Défaut pour lArticle {0} ne peut pas être modifiée directement parce que vous avez déjà fait une (des) transaction (s) avec une autre unité de mesure. Vous devez créer un nouvel article pour utiliser une UDM par défaut différente.,
Default Unit of Measure for Item {0} cannot be changed directly because you have already made some transaction(s) with another UOM. You will need to create a new Item to use a different Default UOM.,LUnité de Mesure par Défaut pour lArticle {0} ne peut pas être modifiée directement parce que vous avez déjà fait une (des) transaction (s) avec une autre unité de mesure. Vous devez créer un nouvel article pour utiliser une UdM par défaut différente.,
Default Unit of Measure for Variant '{0}' must be same as in Template '{1}',LUnité de mesure par défaut pour la variante '{0}' doit être la même que dans le Modèle '{1}',
Default settings for buying transactions.,Paramètres par défaut pour les transactions d'achat.,
Default settings for selling transactions.,Paramètres par défaut pour les transactions de vente.,
@@ -838,7 +838,7 @@ Difference Account,Compte dÉcart,
"Difference Account must be a Asset/Liability type account, since this Stock Reconciliation is an Opening Entry","Le Compte dÉcart doit être un compte de type Actif / Passif, puisque cette Réconciliation de Stock est une écriture d'à-nouveau",
Difference Amount,Écart de Montant,
Difference Amount must be zero,LÉcart de Montant doit être égal à zéro,
Different UOM for items will lead to incorrect (Total) Net Weight value. Make sure that Net Weight of each item is in the same UOM.,Différentes UDM pour les articles conduira à un Poids Net (Total) incorrect . Assurez-vous que le Poids Net de chaque article a la même unité de mesure .,
Different UOM for items will lead to incorrect (Total) Net Weight value. Make sure that Net Weight of each item is in the same UOM.,Différentes UdM pour les articles conduira à un Poids Net (Total) incorrect . Assurez-vous que le Poids Net de chaque article a la même unité de mesure .,
Direct Expenses,Charges Directes,
Direct Income,Revenu direct,
Disable,Désactiver,
@@ -1409,7 +1409,7 @@ Lab Test,Test de laboratoire,
Lab Test Report,Rapport de test de laboratoire,
Lab Test Sample,Échantillon de test de laboratoire,
Lab Test Template,Modèle de test de laboratoire,
Lab Test UOM,UDM de test de laboratoire,
Lab Test UOM,UdM de test de laboratoire,
Lab Tests and Vital Signs,Tests de laboratoire et signes vitaux,
Lab result datetime cannot be before testing datetime,La date et l'heure du résultat de laboratoire ne peuvent pas être avant la date et l'heure du test,
Lab testing datetime cannot be before collection datetime,La date et l'heure du test de laboratoire ne peuvent pas être avant la date et l'heure de collecte,
@@ -2806,7 +2806,7 @@ Stock Received But Not Billed,Stock Reçus Mais Non Facturés,
Stock Reports,Rapports de stock,
Stock Summary,Résumé du Stock,
Stock Transactions,Transactions du Stock,
Stock UOM,UDM du Stock,
Stock UOM,UdM du Stock,
Stock Value,Valeur du Stock,
Stock balance in Batch {0} will become negative {1} for Item {2} at Warehouse {3},Solde du stock dans le Lot {0} deviendra négatif {1} pour l'Article {2} à l'Entrepôt {3},
Stock cannot be updated against Delivery Note {0},Stock ne peut pas être mis à jour pour le Bon de Livraison {0},
@@ -3161,9 +3161,9 @@ Trial Period End Date Cannot be before Trial Period Start Date,La date de fin de
Trialling,Essai,
Type of Business,Type de commerce,
Types of activities for Time Logs,Types d'activités pour Journaux de Temps,
UOM,UDM,
UOM Conversion factor is required in row {0},Facteur de conversion de l'UDM est obligatoire dans la ligne {0},
UOM coversion factor required for UOM: {0} in Item: {1},Facteur de coversion UDM requis pour l'UDM : {0} dans l'Article : {1},
UOM,UdM,
UOM Conversion factor is required in row {0},Facteur de conversion de l'UdM est obligatoire dans la ligne {0},
UOM coversion factor required for UOM: {0} in Item: {1},Facteur de coversion UdM requis pour l'UdM : {0} dans l'Article : {1},
URL,URL,
Unable to find DocType {0},Impossible de trouver le DocType {0},
Unable to find exchange rate for {0} to {1} for key date {2}. Please create a Currency Exchange record manually,Impossible de trouver le taux de change pour {0} à {1} pour la date clé {2}. Veuillez créer une entrée de taux de change manuellement,
@@ -3294,7 +3294,7 @@ Wednesday,Mercredi,
Week,Semaine,
Weekdays,Jours de la semaine,
Weekly,Hebdomadaire,
"Weight is mentioned,\nPlease mention ""Weight UOM"" too","Poids est mentionné,\nVeuillez aussi mentionner ""UDM de Poids""",
"Weight is mentioned,\nPlease mention ""Weight UOM"" too","Poids est mentionné,\nVeuillez aussi mentionner ""UdM de Poids""",
Welcome email sent,Email de bienvenue envoyé,
Welcome to ERPNext,Bienvenue sur ERPNext,
What do you need help with?,Avec quoi avez vous besoin d'aide ?,
@@ -4938,12 +4938,15 @@ Is Cumulative,Est cumulatif,
Coupon Code Based,Code de coupon basé,
Discount on Other Item,Remise sur un autre article,
Apply Rule On Other,Appliquer la règle sur autre,
Party Information,Informations sur la fête,
Party Information,Informations sur le tier,
Quantity and Amount,Quantité et montant,
Min Qty,Qté Min,
Max Qty,Qté Max,
Min Amt,Min Amt,
Max Amt,Max Amt,
Min Amt,Montant Min,
Max Amt,Montant Max,
"If rate is zero them item will be treated as ""Free Item""",Si le prix est à 0 alors l'article sera traité comme article gratuit
Is Recursive,Est récursif
"Discounts to be applied in sequential ranges like buy 1 get 1, buy 2 get 2, buy 3 get 3 and so on","La remise sera appliquée séquentiellement telque : acheter 1 => recupérer 1, acheter 2 => recupérer 2, acheter 3 => recupérer 3, etc..."
Period Settings,Paramètres de période,
Margin,Marge,
Margin Type,Type de Marge,
@@ -5053,7 +5056,7 @@ Quantity and Rate,Quantité et Prix,
Received Qty,Qté Reçue,
Accepted Qty,Quantité acceptée,
Rejected Qty,Qté Rejetée,
UOM Conversion Factor,Facteur de Conversion de l'UDM,
UOM Conversion Factor,Facteur de Conversion de l'UdM,
Discount on Price List Rate (%),Remise sur la Liste des Prix (%),
Price List Rate (Company Currency),Taux de la Liste de Prix (Devise Société),
Rate (Company Currency),Prix (Devise Société),
@@ -5085,7 +5088,7 @@ Purchase Receipt Detail,Détail du reçu d'achat,
Item Weight Details,Détails du poids de l'article,
Weight Per Unit,Poids par unité,
Total Weight,Poids total,
Weight UOM,UDM de Poids,
Weight UOM,UdM de Poids,
Page Break,Saut de Page,
Consider Tax or Charge for,Tenir Compte de la Taxe et des Frais pour,
Valuation and Total,Valorisation et Total,
@@ -5153,7 +5156,7 @@ Advance amount,Montant de l'Avance,
Sales Invoice Item,Article de la Facture de Vente,
Customer's Item Code,Code de l'Article du Client,
Brand Name,Nom de la Marque,
Qty as per Stock UOM,Qté par UDM du Stock,
Qty as per Stock UOM,Qté par UdM du Stock,
Discount and Margin,Remise et Marge,
Rate With Margin,Prix Avec Marge,
Discount (%) on Price List Rate with Margin,Remise (%) sur le prix de la Liste de Prix avec la Marge,
@@ -5501,7 +5504,7 @@ Blanket Order Rate,Prix unitaire de commande avec limites,
Returned Qty,Qté Retournée,
Purchase Order Item Supplied,Article Fourni depuis la Commande d'Achat,
BOM Detail No,N° de Détail de la nomenclature,
Stock Uom,UDM du Stock,
Stock Uom,UdM du Stock,
Raw Material Item Code,Code dArticle de Matière Première,
Supplied Qty,Qté Fournie,
Purchase Receipt Item Supplied,Articles Fournis du Reçus dAchat,
@@ -6149,7 +6152,7 @@ Drug Name / Description,Nom / description du médicament,
Dosage,Dosage,
Dosage by Time Interval,Dosage par intervalle de temps,
Interval,Intervalle,
Interval UOM,UDM d'Intervalle,
Interval UOM,UdM d'Intervalle,
Hour,Heure,
Update Schedule,Mettre à Jour le Calendrier,
Exercise,Exercice,
@@ -7023,7 +7026,7 @@ Petrol,Essence,
Diesel,Diesel,
Natural Gas,Gaz Naturel,
Electric,Électrique,
Fuel UOM,UDM Carburant,
Fuel UOM,UdM Carburant,
Last Carbon Check,Dernière Vérification Carbone,
Wheels,Roues,
Doors,Portes,
@@ -7182,7 +7185,7 @@ Item to be manufactured or repacked,Article à produire ou à réemballer,
Quantity of item obtained after manufacturing / repacking from given quantities of raw materials,Quantité d'article obtenue après production / reconditionnement des quantités données de matières premières,
Set rate of sub-assembly item based on BOM,Définir le prix des articles de sous-assemblage en fonction de la nomenclature,
Allow Alternative Item,Autoriser un article alternatif,
Item UOM,UDM de l'Article,
Item UOM,UdM de l'Article,
Conversion Rate,Taux de Conversion,
Rate Of Materials Based On,Prix des Matériaux Basé sur,
With Operations,Avec des Opérations,
@@ -7926,7 +7929,7 @@ Territory Manager,Responsable Régional,
For reference,Pour référence,
Territory Targets,Objectifs Régionaux,
Set Item Group-wise budgets on this Territory. You can also include seasonality by setting the Distribution.,Définir des budgets par Groupes d'Articles sur ce Territoire. Vous pouvez également inclure de la saisonnalité en définissant la Répartition.,
UOM Name,Nom UDM,
UOM Name,Nom UdM,
Check this to disallow fractions. (for Nos),Cochez cette case pour interdire les fractions. (Pour les numéros),
Website Item Group,Groupe d'Articles du Site Web,
Cross Listing of Item in multiple groups,Liste Croisée d'Articles dans plusieurs groupes,
@@ -8198,10 +8201,10 @@ To Package No.,Au N° de Paquet,
If more than one package of the same type (for print),Si plus d'un paquet du même type (pour l'impression),
Package Weight Details,Détails du Poids du Paquet,
The net weight of this package. (calculated automatically as sum of net weight of items),Le poids net de ce paquet. (Calculé automatiquement comme la somme du poids net des articles),
Net Weight UOM,UDM Poids Net,
Net Weight UOM,UdM Poids Net,
Gross Weight,Poids Brut,
The gross weight of the package. Usually net weight + packaging material weight. (for print),Le poids brut du colis. Habituellement poids net + poids du matériau d'emballage. (Pour l'impression),
Gross Weight UOM,UDM du Poids Brut,
Gross Weight UOM,UdM du Poids Brut,
Packing Slip Item,Article Emballé,
DN Detail,Détail du Bon de Livraison,
STO-PICK-.YYYY.-,STO-PICK-.YYYY.-,
@@ -8215,7 +8218,7 @@ Pick List Item,Élément de la liste de choix,
Picked Qty,Quantité choisie,
Price List Master,Données de Base des Listes de Prix,
Price List Name,Nom de la Liste de Prix,
Price Not UOM Dependent,Prix non dépendant de l'UOM,
Price Not UOM Dependent,Prix non dépendant de l'UdM,
Applicable for Countries,Applicable pour les Pays,
Price List Country,Pays de la Liste des Prix,
MAT-PRE-.YYYY.-,MAT-PRE-YYYY.-,
@@ -8294,7 +8297,7 @@ Purchase Receipt No,N° du Reçu d'Achat,
Inspection Required,Inspection obligatoire,
From BOM,Depuis la nomenclature,
For Quantity,Pour la Quantité,
As per Stock UOM,Selon UDM du Stock,
As per Stock UOM,Selon UdM du Stock,
Including items for sub assemblies,Incluant les articles pour des sous-ensembles,
Default Source Warehouse,Entrepôt Source par Défaut,
Source Warehouse Address,Adresse de l'entrepôt source,
@@ -8309,7 +8312,7 @@ Total Additional Costs,Total des Coûts Additionnels,
Customer or Supplier Details,Détails du Client ou du Fournisseur,
Per Transferred,Par transféré,
Stock Entry Detail,Détails de l'Écriture de Stock,
Basic Rate (as per Stock UOM),Prix de base (comme lUDM du Stock),
Basic Rate (as per Stock UOM),Prix de base (comme lUdM du Stock),
Basic Amount,Montant de Base,
Additional Cost,Frais Supplémentaire,
Serial No / Batch,N° de Série / Lot,
@@ -8339,7 +8342,7 @@ Quantity Difference,Différence de Quantité,
Amount Difference,Différence de Montant,
Item Naming By,Nomenclature d'Article Par,
Default Item Group,Groupe d'Éléments par Défaut,
Default Stock UOM,UDM par Défaut des Articles,
Default Stock UOM,UdM par Défaut des Articles,
Sample Retention Warehouse,Entrepôt de stockage des échantillons,
Default Valuation Method,Méthode de Valorisation par Défaut,
Show Barcode Field,Afficher Champ Code Barre,
@@ -8353,8 +8356,8 @@ Stock Frozen Upto,Stock Gelé Jusqu'au,
Batch Identification,Identification par lots,
Use Naming Series,Utiliser la série de noms,
Naming Series Prefix,Préfix du nom de série,
UOM Category,Catégorie d'unité de mesure (UDM),
UOM Conversion Detail,Détails de Conversion de l'UDM,
UOM Category,Catégorie d'unité de mesure (UdM),
UOM Conversion Detail,Détails de Conversion de l'UdM,
Variant Field,Champ de Variante,
A logical Warehouse against which stock entries are made.,Un Entrepôt logique dans lequel les entrées en stock sont faites.,
Warehouse Detail,Détail de l'Entrepôt,
@@ -9869,8 +9872,8 @@ Allowed Items,Articles autorisés
Party Specific Item,Restriction d'article disponible
Restrict Items Based On,Type de critére de restriction
Based On Value,critére de restriction
Unit of Measure (UOM),Unité de mesure (UDM),
Unit Of Measure (UOM),Unité de mesure (UDM),
Unit of Measure (UOM),Unité de mesure (UdM),
Unit Of Measure (UOM),Unité de mesure (UdM),
CRM Settings,Paramètres CRM
Do Not Explode,Ne pas décomposer
Quick Access, Accés rapides
Can't render this file because it is too large.