Compare commits

...

772 Commits

Author SHA1 Message Date
Saurabh
95c3258ee4 Merge branch 'v12-pre-release' into version-12 2020-12-21 16:14:01 +05:30
Saurabh
00e095278d bumped to version 12.15.0 2020-12-21 16:25:38 +05:50
Nabin Hait
53d98ff635 chore: Added change log 2020-12-21 14:31:56 +05:30
Deepesh Garg
8b43faa203 Merge pull request #24175 from deepeshgarg007/tax_category_typo_v12_pre
fix: Validation for duplicate Tax Category
2020-12-17 19:09:13 +05:30
Nabin Hait
5ee6417228 fix: Translation issue 2020-12-17 19:07:37 +05:30
Deepesh Garg
71349d5a49 fix: Validation for duplicate Tax Category 2020-12-17 19:06:31 +05:30
Deepesh Garg
98d8718979 Merge pull request #24162 from deepeshgarg007/template_update_v12_pre
fix(India): Taxation fixes
2020-12-17 09:11:38 +05:30
Deepesh Garg
2a92d1b94a fix: Tax template update on customer address change 2020-12-16 22:03:41 +05:30
pateljannat
af60e85400 fix: removing return_taxes condition 2020-12-16 22:03:31 +05:30
pateljannat
45d8204e1e fix: company filter added again 2020-12-16 22:03:15 +05:30
pateljannat
56d5b68046 fix: linter issue for translation syntax 2020-12-16 22:02:52 +05:30
pateljannat
dafbb80ec5 fix: reversing previous commits and adding condition in regional controller 2020-12-16 22:02:00 +05:30
pateljannat
f226927b6a fix: place of supply change on address change 2020-12-16 22:01:35 +05:30
pateljannat
8cfde675ac fix: place of supply change when address changes 2020-12-16 22:01:27 +05:30
Deepesh Garg
599d7a686e fix: Tax template update on supplier 2020-12-16 22:01:15 +05:30
Nabin Hait
2bd620fac8 fix: Fixed merge conflict 2020-12-11 22:34:34 +05:30
Marica
fe56b800a6 Merge pull request #24081 from pateljannat/sales-invoice-from-sales-order-v12
fix: sales invoice add button on sales order dashboard
2020-12-10 20:09:20 +05:30
Marica
ccdfbd4f40 Merge pull request #24103 from marination/hotfix-debit-credit-opening-invoice-tool
fix: Handle Account and Item None not found in Opening Invoice Creation Tool
2020-12-10 20:06:13 +05:30
Marica
f7f809aae8 Merge branch 'version-12-hotfix' into hotfix-debit-credit-opening-invoice-tool 2020-12-10 20:04:54 +05:30
Mohammad Hasnain Mohsin Rajan
3f399ee806 fix(acc recv report): columns mismatch (#24085) 2020-12-10 19:15:53 +05:30
Marica
7bbe383232 Merge branch 'version-12-hotfix' into hotfix-debit-credit-opening-invoice-tool 2020-12-10 18:58:31 +05:30
marination
1fcd1e4dc0 fix: add assertRaises for error 2020-12-10 17:34:30 +05:30
Anurag Mishra
800a9ae7c3 Merge pull request #24097 from prssanna/chart-imports
fix: function imports in account_balance_timeline.py
2020-12-10 16:32:59 +05:30
marination
a63b5c1a9e fix: Make new Customers for account missing test and set company 2020-12-10 16:31:23 +05:30
marination
74bcb2977f chore: Add Test for missing debit account 2020-12-10 16:30:39 +05:30
marination
96946fa4a0 fix: Handle missing Account and Item in Opening Invoice Creation Tool 2020-12-10 16:30:13 +05:30
Deepesh Garg
e2fb0c567d Merge pull request #24036 from nextchamp-saqib/abs-value-in-pf-v12
fix: get formatted value in 'taxes' print template
2020-12-10 15:35:15 +05:30
Mohammad Hasnain Mohsin Rajan
5a1d912e6d Merge branch 'version-12-hotfix' into sales-invoice-from-sales-order-v12 2020-12-10 14:07:07 +05:30
Prssanna Desai
e152f9a89a Merge pull request #24099 from prssanna/shopping-cart-fix
fix: get value of allow_items_in_stock even if not an exact match
2020-12-10 12:44:48 +05:30
prssanna
6a718a3fc6 fix: get value of allow_items_in_stock even if not an exact match 2020-12-10 12:39:53 +05:30
Saqib
5062b78718 fix: asset with value zero doesn't show up in fixed asset register (#24098) 2020-12-10 12:33:43 +05:30
prssanna
eed12444e1 fix: function imports in account_balance_timeline.py 2020-12-10 12:20:18 +05:30
rohitwaghchaure
326fccfa00 Merge pull request #24001 from rohitwaghchaure/fixed-stock-entry-multi-consumption
fix: incorrect stock quantity if 'Allow Multiple Material Consumption…
2020-12-10 02:11:20 +05:30
Rohit Waghchaure
e7476914cd fix: incorrect stock quantity if 'Allow Multiple Material Consumption' has enabled 2020-12-10 01:27:54 +05:30
rohitwaghchaure
b1507fdaae Merge pull request #24009 from rohitwaghchaure/shipping-charges-not-added-in-invoice
fix: shipping charges not sync from shopify
2020-12-10 01:06:18 +05:30
Prssanna Desai
ede082657f Merge pull request #24093 from prssanna/item-configurator-fix-version-12
fix: allow add to cart for any item if allow_items_not_in_stock is enabled
2020-12-09 17:54:46 +05:30
prssanna
d0303b3fb1 fix: allow add to cart for any item if allow_items_not_in_stock is enabled 2020-12-09 17:32:16 +05:30
Shivam Mishra
91a3ab8e32 Merge pull request #24084 from prssanna/item-configurator-fix
fix(Shopping Cart): allow add to cart for any item if allow_items_not_in_stock is enabled
2020-12-09 16:45:22 +05:30
prssanna
cfb6e3aa30 fix: allow add to cart for any item if allow_items_not_in_stock is enabled 2020-12-08 16:44:38 +05:30
pateljannat
4fe48a30c4 fix: sales invoice add button on sales order dashboard 2020-12-08 12:04:56 +05:30
Jannat Patel
af29bde0e8 Merge pull request #2 from frappe/version-12-hotfix
Version 12 hotfix
2020-12-08 11:39:32 +05:30
Afshan
b83e131b1f fix: throw an error when no pos profile exist (#24026)
* fix: throw an error when no pos profile exist

* fix: tests

* fix: tests

* fix:test
2020-12-08 09:45:14 +05:30
Rucha Mahabal
51015178da fix(POS): do not fetch items until POS Profile is set (#24076) 2020-12-08 09:34:22 +05:30
Afshan
e39dd079c4 fix: double exception in payroll (#24080) 2020-12-08 09:32:08 +05:30
Afshan
7459dc4105 fix: po orverride (#24023)
* fix: po orverride

* fix: po

* fix: spelling error

* fix: refactor condition

* fix: condition
2020-12-08 09:28:01 +05:30
Deepesh Garg
0796d6b5d0 Merge pull request #24071 from deepeshgarg007/gstr_3b_report_ims_v12
fix: Show tax amount in base currencies
2020-12-07 09:14:29 +05:30
Deepesh Garg
5b08241dc6 fix: Show tax amount in base currencies 2020-12-07 09:12:58 +05:30
rohitwaghchaure
5318a159a9 Merge pull request #24068 from rohitwaghchaure/delete-receive-at-warehouse-entry
fix: delete Receive at Warehouse entry on cancellation of Send to War…
2020-12-06 20:57:31 +05:30
Rohit Waghchaure
26723d10af fix: delete Receive at Warehouse entry on cancellation of Send to Warehouse entry 2020-12-06 17:21:30 +05:30
rohitwaghchaure
3ec6bc1838 Merge pull request #24064 from rohitwaghchaure/additional-product-incorrect-rate-v12
fix: pricing rule with transaction not working for additional product
2020-12-06 13:20:39 +05:30
Rohit Waghchaure
29f92e0405 fix: pricing rule with transaction not working for additional product 2020-12-05 19:30:17 +05:30
rohitwaghchaure
2c9f33a916 Merge pull request #24034 from rohitwaghchaure/fixed-job-card-cacncel-flow
fix: don't cancel job card if manufacturing entry has made
2020-12-04 14:15:19 +05:30
Rohit Waghchaure
b09da9bcfc fix: don't cancel job card if manufacturing entry has made 2020-12-04 11:37:50 +05:30
rohitwaghchaure
771a7276c9 Merge pull request #24037 from rohitwaghchaure/fixed-calculate-depreciation-table-issue
fix: Depreciation Posting Date is mandatory even if Calculate Depreci…
2020-12-03 18:24:51 +05:30
Anurag Mishra
2c6c1aa97a fix: payroll attendance error
fix: payroll attendance error
2020-12-03 16:13:07 +05:30
Afshan
482996f8d1 fix: using ORM 2020-12-03 15:14:30 +05:30
Afshan
785579e67b fix: payroll attendance error 2020-12-03 15:11:34 +05:30
Deepesh Garg
74224d90bf Merge pull request #23966 from deepeshgarg007/unpaid_subscription_fix
fix: Invoice generation for Unpaid subscriptions
2020-12-02 20:03:42 +05:30
Rohit Waghchaure
e5d4b4c1ed fix: Depreciation Posting Date is mandatory even if Calculate Depreciation has disabled 2020-11-30 17:20:51 +05:30
Saqib Ansari
39fa5e3266 fix: get formatted value in 'taxes' print template 2020-11-30 15:56:44 +05:30
Deepesh Garg
f940a3494f Merge pull request #24020 from deepeshgarg007/gstr-1-b2c_large
fix: Opening invoices in GSTR-1 report
2020-11-30 10:57:49 +05:30
Deepesh Garg
f08c2a5cef Merge branch 'version-12-hotfix' of https://github.com/frappe/erpnext into unpaid_subscription_fix 2020-11-29 22:48:46 +05:30
Deepesh Garg
d8b4044ee1 fix: Add check to generate new invoices 2020-11-29 22:48:05 +05:30
rohitwaghchaure
78e737de5a Merge pull request #24013 from rohitwaghchaure/fixed-incoming-rate-for-finished-good
fix: incoming rate for finished good
2020-11-28 19:37:21 +05:30
Deepesh Garg
02feab9f3c fix: Opening invoices in GSTR-1 report 2020-11-27 21:55:02 +05:30
Rohit Waghchaure
3ef60dbfdb fix: incoming rate for finished good 2020-11-27 17:21:05 +05:30
Rohit Waghchaure
75a54361d7 fix: shipping chanrges not sync in erpnext from shopify 2020-11-26 12:55:27 +05:30
Jannat Patel
42b24cc9eb fix: job card error handling for operations field (#23996)
Co-authored-by: pateljannat <jannatpatel@MacBook-Air.local>
2020-11-25 09:07:57 +05:30
rohitwaghchaure
ca05945e92 fix: incorrect balance value in stock balance report (#23997) 2020-11-25 08:58:58 +05:30
rohitwaghchaure
a69b9f95cc Merge pull request #23993 from rohitwaghchaure/bom-stock-project-item-color
fix: bom stock report color showing always red
2020-11-24 17:00:49 +05:30
Rohit Waghchaure
f9e62b74d0 fix: bom stock report color showing always red 2020-11-24 16:56:20 +05:30
Afshan
2b3a20ed5b fix: clear error message when approval not availab (#23972)
le
2020-11-24 08:01:43 +05:30
Jannat Patel
3d84d324d7 fix: purchase receipt to purchase invoice bill date mapping (#23968)
Co-authored-by: pateljannat <jannatpatel@MacBook-Air.local>
Co-authored-by: Rucha Mahabal <ruchamahabal2@gmail.com>
2020-11-23 16:29:42 +05:30
Anurag Mishra
47bdbf1e78 Merge pull request #23979 from rohitwaghchaure/color-not-showing-in-bom-stock-report
fix: bom stock report color issue
2020-11-23 16:14:01 +05:30
Rohit Waghchaure
0cb6ce3a89 fix: bom stock report color issue 2020-11-23 14:11:24 +05:30
rohitwaghchaure
5597737dca Merge pull request #23958 from rohitwaghchaure/incorrect-delink-serial-no-and-batch-v12-hotfix
fix: incorrect delink serial no and batch
2020-11-20 13:45:32 +05:30
Rohit Waghchaure
77b9fa0d06 fix: incorrect delink serial no and batch 2020-11-20 00:26:36 +05:30
Deepesh Garg
224006aebd fix: Invoice generation for Unpaid subscriptions 2020-11-19 19:39:08 +05:30
Saurabh
fdacb5643b Merge branch 'v12-pre-release' into version-12 2020-11-19 15:39:04 +05:30
Saurabh
ec89a65859 bumped to version 12.14.0 2020-11-19 15:59:04 +05:50
rohitwaghchaure
1e4a6e845b Merge pull request #23956 from rohitwaghchaure/split-mysql-query-to_update-quantity-hotfix
fix: Table 'tabStock Entry Detail' is specified twice
2020-11-19 14:06:09 +05:30
Rohit Waghchaure
0433fa58f3 fix: Table 'tabStock Entry Detail' is specified twice 2020-11-19 12:52:17 +05:30
rohitwaghchaure
5c72ad2498 fix: Table 'tabStock Entry Detail' is specified twice (#23952) 2020-11-19 12:45:40 +05:30
rohitwaghchaure
c976d080ea fix: stock ledger entries for stock reco (#23955) 2020-11-19 08:15:41 +05:30
Deepesh Garg
fac940042b Merge pull request #23954 from vorasmit/fix-sez-v12
fix(regional): set proper state code in ewaybill JSON when GST category is SEZ
2020-11-18 21:51:12 +05:30
Smit Vora
3e36d774d2 fix(regional): set proper state code in ewaybill JSON when GST category is SEZ 2020-11-18 21:03:45 +05:30
Marica
507c46d9a4 chore: Revert "fix: Received/Delivered Items to Billed Logic" (#23950)
This reverts commit 4f008f59fc.
2020-11-18 20:54:43 +05:30
Marica
36706b7cb0 chore: Revert "fix: Received/Delivered Items to Billed Logic" (#23948)
This reverts commit 4f008f59fc.
2020-11-18 20:54:33 +05:30
Nabin Hait
18471131cc chore: added change log for v12.14.0 (#23951) 2020-11-18 19:27:00 +05:30
rohitwaghchaure
d920f9da59 Merge pull request #23938 from rohitwaghchaure/duplicate-stock-transactions-created
fix: incorrect stock ledger entries for stock reco
2020-11-18 18:16:58 +05:30
Rohit Waghchaure
f041af53db fix: stock ledger entries for stock reco 2020-11-18 17:15:57 +05:30
Marica
5111882162 Merge pull request #23927 from marination/employee-relieving-fix
fix: Hide Ex-Employees from Employee Tree and minor message UX
2020-11-17 15:15:45 +05:30
Marica
e37604baeb Merge branch 'version-12-hotfix' into employee-relieving-fix 2020-11-17 15:15:08 +05:30
Marica
0e91805719 Merge pull request #23931 from marination/item-link-formatter-hotfix
fix: Item Link Formatter Behaviour
2020-11-17 13:28:52 +05:30
Marica
3377e74fd0 Merge branch 'version-12-hotfix' into item-link-formatter-hotfix 2020-11-17 13:27:58 +05:30
Marica
d87094ebb2 Merge pull request #23928 from marination/bank-reconciliation-hotfix
fix: Sequence Matcher shouldn't get None input
2020-11-17 13:26:58 +05:30
Marica
c7d68a7f41 Merge pull request #23930 from marination/payment-reco-mandatory-check-hotfix
fix: Payment Reconciliation client side validations
2020-11-17 13:24:11 +05:30
marination
3bbed22f04 fix: Item Link Formatter Behaviour 2020-11-17 13:19:53 +05:30
Marica
aab91990e5 Merge pull request #23929 from marination/payment-entry-list-view-hotfix
fix: Check if list view standard filter exists in Payment Entry
2020-11-17 13:14:06 +05:30
marination
2e23050338 fix: Missing semicolon 2020-11-17 13:11:18 +05:30
marination
5ea276d29d fix: Payment Reconciliation client side validations 2020-11-17 13:11:09 +05:30
marination
7e18df31bf fix: Check if list view standard filter exists in Payment Entry 2020-11-17 13:08:33 +05:30
Marica
2c29933118 fix: Sequence Matcher shouldn't get None input (#23539)
Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2020-11-17 13:05:31 +05:30
Marica
9525bffcd9 fix: Hide Ex-Employees from Employee Tree and minor message UX
* fix: Hide Ex-Employees from Employee Tree and minor message UX

* fix: translation syntax
2020-11-17 12:58:31 +05:30
Nabin Hait
6ba0b69469 Merge branch 'version-12-hotfix' into v12-pre-release 2020-11-17 12:18:55 +05:30
rohitwaghchaure
9f93a4069a Merge pull request #23926 from rohitwaghchaure/fixed-stock-ageing-report-not-working-pre-release
fix: stock ageing report not working
2020-11-17 12:18:14 +05:30
Rohit Waghchaure
a73c662a38 fix: stock ageing report not working 2020-11-17 12:16:17 +05:30
rohitwaghchaure
d3074c32fd fix: stock ageing report not working (#23924) 2020-11-17 12:10:05 +05:30
Suraj Shetty
fe56015cbf fix: Handle the "no leave_allocation found" case (#23920) 2020-11-17 12:07:53 +05:30
Saqib
789f1007b9 fix: asset finance book posting date fix (#23780)
* fix: asset finance book posting date fix

* fix: cannot save asset

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2020-11-17 11:53:37 +05:30
Suraj Shetty
f202a49d80 Revert "feat: e invoicing with JSON files" (#23925) 2020-11-17 11:44:55 +05:30
Saqib
8b7d4a3f2e feat: re-linking bank accounts with plaid (#23913) 2020-11-17 11:27:11 +05:30
Marica
b9efb4577a fix: Don't overrule Item Price via Pricing Rule Rate if 0 (#23915)
* fix: Dont overrule Item Price via Pricing Rule Rate if 0

* chore: Pricing Rule with Item Price Test
2020-11-17 11:17:05 +05:30
Marica
b5217ee9d7 fix: Don't copy terms, discount and required by from SO to PO (#23904)
* fix: Dont copy terms, discount and required by from SO to PO

* fix: Let delivery date and required by date get mapped
2020-11-17 11:14:33 +05:30
rohitwaghchaure
e8610014de fix: donot add same packing item multiple time in product bundle (#23898) 2020-11-17 11:11:23 +05:30
Suraj Shetty
780982dcc7 fix: Handle the "no leave_allocation found" case (#23921) 2020-11-17 11:02:15 +05:30
Suraj Shetty
26b802d44a fix: Typo (Enchashment > Encashment) (#23918) 2020-11-17 10:43:55 +05:30
Suraj Shetty
519f5b5411 fix: Typo (Enchashment > Encashment) (#23917) 2020-11-17 10:42:23 +05:30
Suraj Shetty
aebeb573e4 Merge branch 'version-12-hotfix' of github.com:frappe/erpnext into v12-pre-release 2020-11-17 10:15:52 +05:30
Shivam Mishra
e1b96d70db refactor: show form buttons only if permissions exist (#23889)
* refactor: show form buttons only if permissions exist

* fix: missing semicolon

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2020-11-15 16:42:55 +05:30
Marica
31e2c80e33 Merge pull request #23895 from marination/po-to-so-hotfix
fix:  SO to PO flow improvement
2020-11-13 11:26:14 +05:30
marination
09e1b5314b fix: Make sure row object has doctype so that read only property is applied to rows 2020-11-12 12:27:26 +05:30
marination
40ba013636 fix: SO to PO Mapping Issue
- removed type: GET , which made the URL longer
- Added only relevant fields from Items table to Dialog table to reduce args load
- Made separate method to set table data in dialog
- Added freeze message
2020-11-12 12:27:06 +05:30
Marica
16427c5cc8 fix: SO to PO flow improvement (#23357)
* fix: SO to PO flow improvement

* fix: Dont map shipping_address

- shipping_address is a text field in SO and link field in PO
- Drop shipping case handles its mapping
- normal case doesnt need to map

* fix: Hide/Add rows depending on Against Default Supplier

* fix: Removed Default Supplier Select field from popup

- removed Default Supplier Select field from popup
- only loop through suppliers of selected items if via default supplier
- only check for items in selected items

* fix: Sales Order Drop Shipping Test

* fix: (translation)Multi line to single line strings

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2020-11-12 12:23:27 +05:30
Deepesh Garg
7365566894 Merge pull request #23863 from rohitwaghchaure/incorrect-outstanding-amount-in-reverse-charge
fix: incorrect outstanding amount for multicurrency with Reverse Charge
2020-11-11 18:32:50 +05:30
Rohit Waghchaure
6b86586eb1 fix: incorrect outstanding amount for multicurrency with Reverse Charge 2020-11-11 17:32:42 +05:30
Marica
1ff8ae494d Merge pull request #23730 from AfshanKhan/fix-po-no-fetching-v12
fix: copying po no when mapping doc
2020-11-11 17:17:58 +05:30
Marica
02f856e968 Merge branch 'version-12-hotfix' into fix-po-no-fetching-v12 2020-11-11 12:20:05 +05:30
Afshan
38e681e8b2 fix: refactor 2020-11-11 11:47:23 +05:30
rohitwaghchaure
ecffa80216 Merge pull request #23878 from rohitwaghchaure/fix-stock-entry-consumption-issue-v12-hotfix
fix: incorrect backflush qty in manufacture entry
2020-11-10 23:23:33 +05:30
Rohit Waghchaure
cee0706a1f fix: incorrect backflush qty in manufacture entry 2020-11-10 15:55:01 +05:30
Anurag Mishra
bd49da45e3 feat: added column cost_center to receivable reports (#23837)
* feat: added column cost_center to receivable reports

* Update accounts_receivable.py

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2020-11-09 20:21:25 +05:30
Marica
04458e7413 Merge pull request #23866 from marination/purchase-invoice-payment-terms-fix
fix: Payment Terms not fetched in Purchase Invoice from Purchase Receipt
2020-11-09 18:44:40 +05:30
marination
f5e4f75fd0 chore: Test case for Payment Terms in PI from PR 2020-11-09 16:15:56 +05:30
marination
80f5734305 fix: Payment Terms not fetched in Purchase Invoice from Purchase Receipt 2020-11-09 16:15:46 +05:30
Marica
c5096e0441 Merge pull request #23804 from marination/delievered-received-items-to-bill-report-fix
fix: Received/Delivered Items to Be Billed Logic
2020-11-09 14:50:50 +05:30
Marica
20b5b30e34 Merge branch 'version-12-hotfix' into delievered-received-items-to-bill-report-fix 2020-11-09 10:34:05 +05:30
Deepesh Garg
d196f14e85 Merge pull request #23859 from deepeshgarg007/india_tax_template_fetch_v12
fix: Auto State-wise gst tax template
2020-11-08 17:49:08 +05:30
Deepesh Garg
6beee63d06 fix: Auto State-wise gst tax template 2020-11-08 17:47:32 +05:30
rohitwaghchaure
fb6534cb65 Merge pull request #23816 from rohitwaghchaure/default-cost-center-set-in-item-not-showing
fix: default cost center in item master not set in stock entry
2020-11-06 17:46:11 +05:30
Marica
9876fa8360 Merge branch 'version-12-hotfix' into delievered-received-items-to-bill-report-fix 2020-11-06 12:23:18 +05:30
rohitwaghchaure
20bd91f0d9 Merge pull request #23830 from rohitwaghchaure/incorrect-assign-to-in-asset-maintenance
fix: incorrect assign to in Maintenance Schedule
2020-11-05 18:43:39 +05:30
Rohit Waghchaure
06b6027674 fix: not able to select assign to 2020-11-05 15:35:48 +05:30
Marica
3960c49fc6 Merge branch 'version-12-hotfix' into delievered-received-items-to-bill-report-fix 2020-11-05 12:31:59 +05:30
Afshan
7e6c79819a fix: refactor and test 2020-11-05 11:59:45 +05:30
rohitwaghchaure
533954cd12 Merge pull request #23815 from Anurag810/stock_ledger_report_v12
fix:  list index out of range on incilding uom
2020-11-05 11:49:37 +05:30
Rohit Waghchaure
7ee2b0ed3a fix: default cost center in item master not set in stock entry 2020-11-05 11:47:22 +05:30
Anurag Mishra
8e37316832 fix: list index out of range on incilding uom 2020-11-04 15:27:17 +05:30
Afshan
2860f62772 Fix leave ledger patch (#23806)
* fix: leave ledger patch

* fix: modified patch date
2020-11-04 14:15:26 +05:30
marination
4f008f59fc fix: Received/Delivered Items to Billed Logic 2020-11-03 23:12:53 +05:30
Deepesh Garg
1f10da4d66 Merge pull request #23786 from deepeshgarg007/pos_v12_hotfix
fix: Place of Supply fix in Sales Invoices
2020-11-02 11:23:47 +05:30
Deepesh Garg
7036635007 fix: fieldname 2020-10-30 22:15:23 +05:30
Deepesh Garg
c1719ef54b fix: Place of Supply fix in Sales Invoices 2020-10-30 22:15:23 +05:30
Afshan
c8201eba33 fix: leave ledger entries (#23782) 2020-10-30 18:47:52 +05:30
rohitwaghchaure
b2bd8ef144 Merge pull request #23773 from rohitwaghchaure/fixed-set-po-details-in-subcontract-stock-entry
fix: po_detail field has no value for subcontracted stock entry
2020-10-30 14:19:55 +05:30
Rohit Waghchaure
e523cfbb02 fix: po_detail field has no value for subcontracted stock entry 2020-10-30 03:04:39 +05:30
Marica
d8705240a0 chore: (Production Plan) Simplify and fix translation in message popup (#23754) 2020-10-29 18:54:06 +05:30
Deepesh Garg
ab1415c0cc Merge pull request #23762 from rohitwaghchaure/fixed-subscription-test-case
fix: subscription test case
2020-10-29 17:04:12 +05:30
Rohit Waghchaure
2f12eed44d fix: subscription test case 2020-10-29 15:52:33 +05:30
rohitwaghchaure
c9e93fd9b1 Merge pull request #23740 from prssanna/job-card-gantt
fix: override field_map for job card gantt
2020-10-29 14:50:19 +05:30
Rucha Mahabal
82db751a52 fix: LMS sign-up link (#23752) 2020-10-29 11:19:34 +05:30
Marica
2d936fe5ca Merge pull request #23748 from marination/leave-type-filter
fix(HR) : Filter Leave Type based on allocation for a particular employee (#22050)
2020-10-28 17:23:45 +05:30
Abhishek Balam
d0541d77b3 Merge branch 'version-12-hotfix' into leave-type-filter 2020-10-28 16:29:06 +05:30
Anurag Mishra
5f148d3d3a fix: set_query in leave application (#22197) 2020-10-28 16:25:57 +05:30
Abhishek Balam
6c894f8f41 fix(HR) : Filter Leave Type based on allocation for a particular employee (#22050)
* table was showing empty with just headers when no leaves allocated, fixed template code

* added filters on Leave Type based on leave allocation for a particular employee and to/from dates
2020-10-28 16:12:57 +05:30
Marica
5effbeef49 Merge pull request #23733 from AfshanKhan/prod-order-reference-in-item-v12
fix: Remove Production Order reference from Item Validation
2020-10-28 16:09:52 +05:30
prssanna
1fa8dcb15b fix: override field_map for job card gantt 2020-10-28 11:02:02 +05:30
Saqib
acd5929ac3 feat: e invoicing
* feat: e-invoice

* fix: validations

* fix: add permissions on regional setup

* feat: add patch

* fix: validate document name

* fix: return date

* fix: credit note einvoice

* fix: validations

* chore: remove extras

* fix: error logging

* fix: e_invoice module not found

* fix: add missing package

* fix: travis
2020-10-27 20:37:20 +05:30
Afshan
0c511b31fd fix: Remove Production Order reference from Item Validation 2020-10-26 20:34:48 +05:30
Afshan
17a8874c50 fix: copying po no when mapping doc 2020-10-26 17:07:40 +05:30
Nabin Hait
439c4e11bf fix: Show accounts in financial statements upto level 20 (#23719) 2020-10-24 22:00:17 +05:30
Aditya Duggal
a76b1c530d fix: None type error if the Pricing Rule applicable_for is None (#23664)
* fix: None type error if the Pricing Rule applicable_for is None
* fix: sider

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
Co-authored-by: Saqib <nextchamp.saqib@gmail.com>
2020-10-24 11:20:24 +05:30
rohitwaghchaure
aef8010bc1 Merge pull request #23712 from marination/cashier-closing-type-issue-fix
fix: Cashier Closing, Type Issue
2020-10-23 16:12:41 +05:30
marination
e9b7b69435 fix: Cashier Closing Type Issue 2020-10-23 14:46:44 +05:30
Saurabh
f7f8f5c305 Merge branch 'v12-pre-release' into version-12 2020-10-22 18:28:33 +05:30
Saurabh
acf22c475e bumped to version 12.13.0 2020-10-22 18:48:33 +05:50
Nabin Hait
f74aa28752 chore: Added change log (#23707) 2020-10-22 17:52:16 +05:30
Marica
c1ffe0990b Update items add taxes v12 pre release (#23706)
* fix: Add Taxes if missing via Update Items

* chore: PO Test for adding tax row via Update Items

* chore: SO Test for adding tax row via Update Items
2020-10-22 17:04:38 +05:30
Saqib
eb6fb6fffa fix: cannot auto unlink payments for credit/debit notes (#23690) 2020-10-22 16:31:55 +05:30
Marica
ab5d596959 fix: Add Taxes if missing via Update Items (#23705)
* fix: Add Taxes if missing via Update Items

* chore: PO Test for adding tax row via Update Items

* chore: SO Test for adding tax row via Update Items
2020-10-22 16:28:41 +05:30
Afshan
203fc2b940 fix: removed extra space from label "Rate" (#23685) 2020-10-20 10:56:38 +05:30
Saqib
8e7a755aeb feat: show only available items in point of sale (#23667)
* feat: show available items in pos

* feat: show selected pos profile on pos screen

* fix: codacy

* fix: codacy
2020-10-19 11:37:22 +05:30
Sun Howwrongbum
334c282f7b fix: consider rounded_total in returns (#23631)
Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2020-10-19 11:30:48 +05:30
Saqib
3ae9bbc0a7 fix: fuel expense amount of vehicle log (#23634)
* fix: fuel expense amount of vehicle log

* fix: undefined var employee_id in test

* fix: test
2020-10-16 11:54:36 +05:30
rohitwaghchaure
8b8457c5d3 Merge pull request #23647 from rohitwaghchaure/fixed-overproduction-against-work-order
fix: overproduction, not allowed to transfer extra materials
2020-10-16 10:31:58 +05:30
rohitwaghchaure
9ba0e991d9 Merge pull request #23658 from rohitwaghchaure/fixed-overproduction-against-work-order-pre-release
fix: overproduction, not allowed to transfer extra materials
2020-10-16 10:31:38 +05:30
Rohit Waghchaure
3df4f226d5 fix: overproduction, not allowed to transfer extra materials 2020-10-15 22:28:05 +05:30
rohitwaghchaure
8701156d28 Merge pull request #23657 from rohitwaghchaure/donot-set-serial-nos-if-manually-set-pre
fix: manually set serial nos override with current available serial nos
2020-10-15 22:05:01 +05:30
Rohit Waghchaure
a2ab227240 fix: manually set serial nos override with current available serial nos 2020-10-15 22:03:42 +05:30
rohitwaghchaure
eabe1af280 Merge pull request #23651 from rohitwaghchaure/donot-set-serial-nos-if-manually-set
fix: manually set serial nos override with current available serial nos
2020-10-15 22:01:32 +05:30
rohitwaghchaure
8ba4201c7b Merge pull request #23656 from rohitwaghchaure/removed-repetative-code-v12-pre
fix: remove repetative code
2020-10-15 22:00:57 +05:30
Rohit Waghchaure
7a079d73dc fix: remove repetative code 2020-10-15 21:58:44 +05:30
rohitwaghchaure
7bbdbaa2fa Merge pull request #23655 from rohitwaghchaure/removed-repetative-code
fix: remove repetative code
2020-10-15 21:57:33 +05:30
Rohit Waghchaure
28a5169646 fix: remove repetative code 2020-10-15 21:54:53 +05:30
Rohit Waghchaure
c7ec475429 fix: manually set serial nos override with current available serial nos 2020-10-15 19:00:02 +05:30
Rohit Waghchaure
433faa705e fix: overproduction, not allowed to transfer extra materials 2020-10-15 18:53:50 +05:30
rohitwaghchaure
d445e38e6b Merge pull request #23648 from rohitwaghchaure/set-current-serial-no-in-serial-no-field-v12-pre-release
fix: serial no field is blank in stock reconciliation
2020-10-15 15:54:55 +05:30
Rohit Waghchaure
940c5f2d4b fix: serial no field is blank in stock reconciliation 2020-10-15 15:53:37 +05:30
rohitwaghchaure
2b4da0d518 Merge pull request #23646 from rohitwaghchaure/set-current-serial-no-in-serial-no-field
fix: serial no field is blank in stock reconciliation
2020-10-15 15:45:37 +05:30
Rohit Waghchaure
8d7e26c7dd fix: serial no field is blank in stock reconciliation 2020-10-15 14:29:57 +05:30
rohitwaghchaure
6ff846f9b0 Merge pull request #23645 from rohitwaghchaure/receive-at-warehouse-not-validate-for-extra-transfer-qty
fix: extra material received against send to warehouse entry
2020-10-15 13:59:45 +05:30
Rohit Waghchaure
f956a2cf72 fix: extra material received against send to warehouse entry 2020-10-15 12:59:10 +05:30
rohitwaghchaure
5cacaec52b Merge pull request #23638 from anupamvs/item-group-filter-portal-v12-pre-release
fix: added filter show in website for filtering product
2020-10-14 16:29:02 +05:30
rohitwaghchaure
1fb3a29cf9 Merge pull request #23637 from anupamvs/item-group-filter-portal-v12
fix: added filter show in website for filtering product
2020-10-14 16:28:39 +05:30
Afshan
4b8d4a1cbe fix: setting user precision instead of 2 (#23630)
* fix: setting user precision instead of default

* fix: removing unused imports
2020-10-14 15:50:26 +05:30
Anupam
3f5c4932b4 fix: added filter show in website for filtering product 2020-10-14 15:37:09 +05:30
Anupam
90eb489392 fix: added filter show in website for filtering product 2020-10-14 15:26:34 +05:30
Nabin Hait
f145a4ce58 fix: resolved conflict 2020-10-14 09:59:55 +05:30
rohitwaghchaure
bd4896b1b2 Merge pull request #23619 from rohitwaghchaure/incorrect-supplied-qty-issue
fix: incorrect supplied qty error
2020-10-14 00:24:04 +05:30
rohitwaghchaure
98b7f0a0f0 Merge pull request #23497 from frappe/fix_fiscal_year
fix: fiscal year can be shorter than 12 months
2020-10-13 23:26:41 +05:30
Rohit Waghchaure
4def9ed1c6 fix: incorrect supplied qty error 2020-10-13 22:43:18 +05:30
rohitwaghchaure
0ae4527ff8 Merge pull request #23618 from aakvatech/patch-5
feat: Add company and correct filter in bank statement reconciliation report filters
2020-10-13 16:59:42 +05:30
Raffael Meyer
e2b7ac2b0e fix: make account number length configurable (#23496)
* fix: make account number length configurable

* Update datev.py

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2020-10-13 15:09:18 +05:30
Deepesh Garg
63bbce708d Merge pull request #23552 from deepeshgarg007/gst3b_taxable_value
fix: Taxable value in GSTR 3B report
2020-10-13 14:03:44 +05:30
aakvatech
8f60d25064 feat: Add company and correct filter in bank statement reconciliation…
… report filters

If you have multi company scenario and many bank accounts that are no longer active, then it becomes difficult in bank statement reconciliation report to filter the account to reconcile and it also shows disabled accounts so futher confusion is created.

https://github.com/frappe/erpnext/issues/23613
2020-10-13 10:26:33 +03:00
rohitwaghchaure
39988c9319 fix: subscription test case (#23617) 2020-10-13 12:36:48 +05:30
rohitwaghchaure
0c1aaa440d Merge pull request #23495 from frappe/check_fiscal_year
fix: check fiscal year
2020-10-13 12:12:00 +05:30
Marica
890c5b063c Merge pull request #23608 from marination/holiday-list-fix
fix: Convert dates to datetime.date before comparing in Holiday List
2020-10-13 02:47:51 +05:30
marination
007069d495 fix: Convert dates to datetime.date before comparing in Holiday List 2020-10-13 02:42:14 +05:30
Deepesh Garg
820c77a375 Merge pull request #23477 from anupamvs/subscription-invoice-v12
fix: Payment Schedule not fetching
2020-10-12 20:35:07 +05:30
Anupam Kumar
e6adf20037 Merge branch 'version-12-hotfix' into subscription-invoice-v12 2020-10-12 19:41:49 +05:30
rohitwaghchaure
72dbabf0d2 Merge pull request #23395 from anupamvs/quality-procedure
fix: quality procedure parent
2020-10-12 18:50:43 +05:30
Anupam
984fdde692 fix: review fixes 2020-10-12 18:06:58 +05:30
rohitwaghchaure
3cdbe7c586 Merge pull request #23440 from legendleap/version-12-hotfox-itemcode
fix: include item_code in items result to allow adding product info in custom templates
2020-10-12 17:30:45 +05:30
Marica
848d78b373 Merge pull request #23591 from anupamvs/item-attribute
feat: validate if removed item attributes exist in variants
2020-10-12 17:22:29 +05:30
Marica
e1047af4bf Merge branch 'version-12-hotfix' into item-attribute 2020-10-12 17:22:01 +05:30
Saqib
79d069cbbb fix: last purchase rate in item prices report (#23507)
* fix: last purchase rate in item prices report

* fix: last purchase rate in item prices report

* fix: last purchase rate in item prices report

* chore: fetch last purchase rate from update stock purchase invoices
2020-10-12 17:09:29 +05:30
rohitwaghchaure
29c2f399e3 Merge pull request #22328 from pipech/v12-hotfix-get_pricing_rule
fix(pricing_rules): pricing rule selector is wrong
2020-10-12 15:33:13 +05:30
rohitwaghchaure
4fa06ad6a6 Merge pull request #23594 from anupamvs/item-price-v12
fix: can't save item price after adding child table
2020-10-12 15:17:34 +05:30
Rushabh Mehta
122fea8043 Merge pull request #23551 from anupamvs/procurement-tracke-v12
fix: project value is missing from procurement-tracker
2020-10-12 15:13:46 +05:30
rohitwaghchaure
660a811483 Merge pull request #23564 from rohitwaghchaure/fixed-batch-wise-stock-reco
fix: negative stock error while submitting stock reco for batch item
2020-10-12 15:11:41 +05:30
rohitwaghchaure
c351e2a03c Merge pull request #23522 from rohitwaghchaure/extra-filters-in-batchwise-balance-report
feat: added new filters in the Batch-wise balance history report
2020-10-12 15:11:21 +05:30
rohitwaghchaure
0cbe0c0b21 Merge pull request #23520 from rohitwaghchaure/feat-added-balance-serial-no-column
feat: balance serial nos in stock leder report
2020-10-12 15:09:42 +05:30
rohitwaghchaure
3ed333831d Merge pull request #23599 from deepeshgarg007/pos_return_amount
fix: Mode of payment getting overwritten by defautl mode of payment for retruns
2020-10-12 15:09:16 +05:30
rohitwaghchaure
a0ed196005 Merge pull request #23600 from rohitwaghchaure/fixed-overproduction-issue
fix: not able to do overproduction
2020-10-12 14:59:41 +05:30
Saqib
f41fe79528 fix(asset): cannot create asset if cwip disabled and account not set (#23584)
* fix: asset purchase with purchase invoice

* chore: allow enable cwip accounting only if cwip account is set

* fix: cannot create asset if cwip disabled and account not set
2020-10-12 14:56:08 +05:30
Marica
72ca041fd2 Merge pull request #23480 from rohitwaghchaure/fixed-incorrect-operation-time-calculation
fix: incorrect operation time calculation for batch size
2020-10-12 14:55:01 +05:30
Rohit Waghchaure
1270c53dea fix: not able to do overproduction 2020-10-12 14:54:54 +05:30
Marica
cedbaa5ac9 Merge branch 'version-12-hotfix' into fixed-incorrect-operation-time-calculation 2020-10-12 14:54:44 +05:30
Marica
b3f0488dca Merge branch 'version-12-hotfix' into item-attribute 2020-10-12 14:51:18 +05:30
Deepesh Garg
772ccde33f fix: Mode of payment getting overwritten by defautl mode of payment for returns 2020-10-12 13:32:49 +05:30
Deepesh Garg
3ca57e493a fix: Do not consider opening entries for TDS calculation (#23598) 2020-10-12 13:03:25 +05:30
Anupam
dc68b44596 fix: can't save item price after adding child table 2020-10-12 11:53:19 +05:30
Anupam
a784e13ac3 fix: Payment Schedule not fetching 2020-10-12 11:51:51 +05:30
Anupam
6297778a6a feat: validate if removed item attributes exist in variants 2020-10-12 11:00:28 +05:30
rohitwaghchaure
6825d5442f Merge pull request #23544 from tundebabzy/version-12-hotfix
fix: pass self.flags.ignore_permissions to the ignore_permissions argument of Address and Contact
2020-10-10 11:11:28 +05:30
rohitwaghchaure
5bbb793803 Merge pull request #23571 from nextchamp-saqib/si-dashboard-fix-v12
fix: (revert) Add Delivery Note Count in Sales Invoice Dashboard
2020-10-10 11:08:55 +05:30
Saqib
5d7c9d2f61 fix: update items after submission ignores precision (#23492)
* fix: update items after submission ignores precision

* chore: add test
2020-10-09 21:19:40 +05:30
Saqib Ansari
a7293407bd fix: (revert) Add Delivery Note Count in Sales Invoice Dashboard 2020-10-09 21:01:31 +05:30
Rohit Waghchaure
4968f162bd fix: negative stock error while submitting stock reco for batch item 2020-10-09 18:34:13 +05:30
Marica
a8f9e2ab37 Merge pull request #23565 from marination/v12-fix-financial-statement-print-format
fix: Show total row in print format of financial statement
2020-10-09 14:50:29 +05:30
Anupam
15717490fd fix: project value is missing from procurement-tracker 2020-10-09 14:18:42 +05:30
Suraj Shetty
eef5c5dad4 fix: Show total row in print format of financial statement 2020-10-09 13:52:34 +05:30
Tunde Akinyanmi
65a716dd08 Merge branch 'version-12-hotfix' of https://github.com/frappe/erpnext into version-12-hotfix 2020-10-09 07:24:23 +01:00
Deepesh Garg
0e6e7e95ba fix: Taxable value in GSTR 3B report 2020-10-08 15:30:40 +05:30
Marica
9039e29a8c Merge branch 'version-12-hotfix' into fixed-incorrect-operation-time-calculation 2020-10-08 14:06:13 +05:30
Saqib
7c760f62c3 fix: 'stock_rbnb_currency' referenced before assignment (#23528) 2020-10-08 13:49:07 +05:30
rohitwaghchaure
f64adc8acf Merge pull request #23547 from frappe/account_settings_v12
fix: Typo in Accounts Settings
2020-10-08 11:25:32 +05:30
rohitwaghchaure
5da98cce86 Update test_work_order.py 2020-10-08 11:19:41 +05:30
michellealva
5f3e5c8a7c fix: Typo in Accounts Settings 2020-10-08 09:41:44 +05:30
Tunde Akinyanmi
78a98030ef fix: pass self.flags.ignore_permissions to the ignore_permissions
argument of Address and Contact controller
2020-10-08 02:19:02 +01:00
rohitwaghchaure
41b88eafe0 Merge pull request #23536 from rohitwaghchaure/fixed-cogs-error-in-pr
fix: COGS validation in the purchase receipt
2020-10-07 19:08:49 +05:30
Rohit Waghchaure
3f505b711d fixed: COGS validation in the purchase receipt 2020-10-07 19:06:15 +05:30
Raffael Meyer
65ff74778d Merge branch 'version-12-hotfix' into v12-hotfix-get_pricing_rule 2020-10-07 09:47:53 +02:00
Deepesh Garg
81b47821b7 Merge pull request #23354 from deepeshgarg007/tax_fetch_quote_v12
fix: Taxes not getting fetched from Opportunity to Quotation
2020-10-06 19:55:38 +05:30
Raffael Meyer
b2d1ae2cb8 Merge branch 'version-12-hotfix' into fix_fiscal_year 2020-10-06 10:56:13 +02:00
Rohit Waghchaure
f0108b42fd refactor: added new filters in the Batch-wise balance history report 2020-10-06 13:47:03 +05:30
Rohit Waghchaure
20262e00df feat: balance serial nos in stock leder report 2020-10-06 12:50:21 +05:30
rohitwaghchaure
448af6a893 Merge pull request #23484 from marination/item-attr-fix
fix: Handle Blank from/to range in Numeric Item Attribute
2020-10-06 12:00:36 +05:30
Rohit Waghchaure
1c826afa01 fix: incorrect operation time calculation for batch size 2020-10-05 16:57:21 +05:30
Deepesh Garg
ad4b421251 Merge pull request #23463 from rohitwaghchaure/skip-non-apply-tds-invoices
fix: tds calculation, skip invoices with "Apply Tax Withholding Amount" has disabled
2020-10-05 14:21:48 +05:30
rohitwaghchaure
748585c9a9 Merge pull request #23512 from marination/sales-order-project-fix
fix: Show Project under Create button in SO
2020-10-05 13:17:57 +05:30
marination
6e1d818c3e fix: Show Project under Create button in SO 2020-10-05 12:36:55 +05:30
Faris Ansari
a246b1db20 Merge pull request #23508 from rohitwaghchaure/item-configure-performace-issue
fix: performance issue while adding template item in the cart
2020-10-05 11:45:49 +05:30
Rohit Waghchaure
5056fbcb9d fix: performance issue while adding template item in the cart 2020-10-04 20:14:53 +05:30
Saqib
8aad02f822 fix: naming series - cannot reset current value to zero (#23505) 2020-10-04 18:13:58 +05:30
barredterra
e1f1d5a67d fix: fiscal year can be shorter than 12 months 2020-10-03 18:28:43 +02:00
barredterra
b4c2816343 fix: check fiscal year 2020-10-03 17:25:26 +02:00
Rohit Waghchaure
feade95a26 fix: tds calculation, skip invoices with "Apply Tax Withholding Amount" has disabled 2020-10-03 16:16:24 +05:30
marination
fe0ce60d75 fix: Handle Blank from/to range in Numeric Item Attribute 2020-10-02 12:28:41 +05:30
Saurabh
3e0f488083 Merge branch 'v12-pre-release' into version-12 2020-10-01 12:54:23 +05:30
Saurabh
db4178b1e8 bumped to version 12.12.1 2020-10-01 13:14:23 +05:50
rohitwaghchaure
58598c6070 Merge pull request #23433 from rohitwaghchaure/fixed-stock-ageing-report-data
fix: stock ageing report
2020-09-30 23:37:40 +05:30
Saurabh
080ef5a2bc fix: validate theme_scss attribute (#23466) 2020-09-30 18:11:37 +05:30
Deepesh Garg
e4df9dde6b Merge pull request #23442 from prssanna/company-replace-abbr
fix: longer timeout for company replace abbreviation
2020-09-30 14:07:05 +05:30
Deepesh Garg
b217075f6b fix: Remove any taxes fetched due to unknown rules 2020-09-30 13:00:18 +05:30
Marica
7c0056be9d Merge pull request #23461 from marination/cost-center-validation-pre-release
fix: Avoid validation of group cost center on repost
2020-09-30 12:58:13 +05:30
Marica
146575b176 Merge pull request #23459 from marination/update-items-perm-v12-pre-release
fix: Check only Read and Write Permission in Update Items
2020-09-30 12:55:48 +05:30
Marica
3d254a3fe5 Merge pull request #23458 from marination/update-items-perm-fix
fix: Check only Read and Write Permission in Update Items
2020-09-30 12:55:18 +05:30
Marica
95e50b3f21 Merge branch 'version-12-hotfix' into update-items-perm-fix 2020-09-30 12:29:06 +05:30
Deepesh Garg
80379ef921 fix: Remove any taxes fetched due to unknown rules 2020-09-30 10:28:38 +05:30
marination
374fa69c54 fix: Only validate group cost center if not from repost 2020-09-29 20:48:47 +05:30
Deepesh Garg
b6ce2de666 Merge pull request #23460 from marination/cost-center-validation
fix: Avoid validation of group cost center on repost
2020-09-29 20:26:51 +05:30
marination
91e552ef3a fix: Only validate group cost center if not from repost 2020-09-29 19:33:00 +05:30
Deepesh Garg
096da540e3 fix: Add test 2020-09-29 19:06:21 +05:30
Deepesh Garg
54c993fb75 Merge branch 'version-12-hotfix' of https://github.com/frappe/erpnext into tax_fetch_quote_v12 2020-09-29 18:47:01 +05:30
marination
2949d1c355 fix: Check only Read and Write Permission in Update Items 2020-09-29 18:29:00 +05:30
marination
3fdabe75d3 fix: Check only Read and Write Permission in Update Items 2020-09-29 18:26:40 +05:30
rohitwaghchaure
103866a367 Merge pull request #23451 from rohitwaghchaure/display-item-name-instead-of-code
fix: display item name instead of item code in offline POS
2020-09-29 13:01:37 +05:30
Rohit Waghchaure
8ba98a52a0 fix: display item name instead of item code in POS 2020-09-29 13:00:00 +05:30
rohitwaghchaure
c7ef8000ac Update stock_ageing.py 2020-09-28 16:00:48 +05:30
prssanna
031502e64c fix: longer timeout for company replace abbreviation 2020-09-28 13:34:24 +05:30
Oliver Liu
572ee8b152 include item_code in query result 2020-09-28 02:24:31 +02:00
Saurabh
24e5a6172a Merge branch 'v12-pre-release' into version-12 2020-09-25 11:47:15 +05:30
Saurabh
c7689d8796 bumped to version 12.12.0 2020-09-25 12:07:15 +05:50
Nabin Hait
5e7bfa37ef chore: Added change log for v12.12.0 (#23435) 2020-09-25 10:07:07 +05:30
Rohit Waghchaure
560f513d69 fix: stock ageing report 2020-09-25 01:12:31 +05:30
rohitwaghchaure
968cb60010 Merge pull request #23430 from prssanna/mr-stock-uom
fix: set stock UOM in item while creating material request from stock entry
2020-09-24 20:05:20 +05:30
prssanna
92c1f38c33 fix: set stock uom in tem while creating material request from stock entry 2020-09-24 17:08:22 +05:30
Anurag Mishra
257927a18b fix:dash board for pre-release test (#23428) 2020-09-24 16:32:39 +05:30
Anurag Mishra
1caab44c29 fix:dash board for pre-release test (#23426) 2020-09-24 15:43:18 +05:30
Saqib
0847f257e6 chore: make asset movement transaction date match with purchase date & time (#23425) 2020-09-24 15:09:48 +05:30
Saqib
b61361f942 chore: make asset movement transaction date match with purchase date & time (#23424) 2020-09-24 15:08:52 +05:30
Marica
e45aeab291 fix: Check Company in Payment Entry before selecting values (#23421) 2020-09-24 12:07:49 +05:30
Marica
abd4b04cd9 fix: Check Company in Payment Entry before selecting values (#23420) 2020-09-24 12:07:43 +05:30
rohitwaghchaure
d7bce62c60 Merge pull request #23414 from rohitwaghchaure/book-loss-amount-in-cogs-pre-release
refactor: book loss amount in the COGS instead of stock received but not billed
2020-09-23 20:32:27 +05:30
Rohit Waghchaure
4220f1e759 refactor: book loss amount in the COGS instead of stock received but not billed 2020-09-23 20:30:26 +05:30
rohitwaghchaure
8699e82290 Merge pull request #23411 from anupamvs/leave-application-status-v12-hotfix
fix: leave application status fix
2020-09-23 20:28:40 +05:30
rohitwaghchaure
5100410e10 Merge pull request #23412 from rohitwaghchaure/book-loss-amount-in-cogs
refactor: book loss amount in the COGS instead of stock received but not billed
2020-09-23 20:28:21 +05:30
Rohit Waghchaure
9e3764ab62 refactor: book loss amount in the COGS instead of stock received but not billed 2020-09-23 19:35:49 +05:30
Anupam
f31e358df9 fix: leave application status fix 2020-09-23 19:14:31 +05:30
rohitwaghchaure
76fdc9faaa Merge pull request #23391 from anupamvs/leave-application-status-fix
fix: leave application status fix
2020-09-23 19:06:17 +05:30
Anupam
960229793b fix: conflict resolved 2020-09-23 18:58:38 +05:30
Anupam
ecfc4b3fd4 fix: review changes 2020-09-23 18:53:40 +05:30
Prssanna Desai
2984f42e2b fix: ignore permission while creating supplier scorecard period in supplier scorecard (#23405) 2020-09-23 17:16:59 +05:30
Saqib
7d9dd8601a fix: failed workflow condition error message in update items (#23394) 2020-09-23 13:01:58 +05:30
Saqib
aad4bea366 fix: failed workflow condition error message in update items (#23392) 2020-09-23 13:01:30 +05:30
rohitwaghchaure
4a154098cc Merge pull request #23404 from rohitwaghchaure/download-required-materials-not-working-pre
fix: Download Required Materials not working for production plan
2020-09-23 01:32:42 +05:30
Rohit Waghchaure
0d4fb93d71 fix: Download Required Materials not working for production plan 2020-09-23 01:31:03 +05:30
rohitwaghchaure
07b1737351 Merge pull request #23396 from anupamvs/batch-wise-filter-v12
fix: adding filters validation Batch-Wise Balance History
2020-09-23 00:58:11 +05:30
rohitwaghchaure
6dc1b423bd Merge pull request #23399 from prssanna/supplier-scorecard-perm
fix: ignore permission while creating Supplier Scorecard Period in Supplier Scorecard
2020-09-23 00:57:52 +05:30
rohitwaghchaure
5a34e2db97 Merge pull request #23403 from rohitwaghchaure/download-required-materials-not-working
fix: Download Required Materials not working for production plan
2020-09-23 00:56:58 +05:30
Anupam Kumar
134b0fd18b Merge branch 'version-12-hotfix' into quality-procedure 2020-09-23 00:38:58 +05:30
Rohit Waghchaure
b948cf204c fix: Download Required Materials not working for production plan 2020-09-22 19:47:33 +05:30
Afshan
38000aacc5 fix: warehouse address filtered based on warehouse (#23381)
Co-authored-by: Marica <maricadsouza221197@gmail.com>
2020-09-22 16:51:58 +05:30
prssanna
a78cd20e31 fix: ignore permission while creating supplier scorecard period in supplier scorecard 2020-09-22 15:04:03 +05:30
Anupam
9a7e433a9d fix: quality procedure parent 2020-09-22 14:34:48 +05:30
Anupam
ba271317c7 fix: adding filters validation Batch-Wise Balance History 2020-09-22 13:45:15 +05:30
rohitwaghchaure
d12c99fda9 Merge pull request #23389 from rohitwaghchaure/fixed-subcontract-issue-for-bacthed-raw-material
fix: incorrect consumed qty if raw material with batch
2020-09-22 11:54:46 +05:30
Anupam
d5a33f4604 fix: leave application status fix 2020-09-22 11:29:17 +05:30
rohitwaghchaure
14175a2f47 Merge pull request #23390 from rohitwaghchaure/fixed-subcontract-issue-for-bacthed-raw-material-pre
fix: incorrect consumed qty if raw material with batch
2020-09-22 10:51:46 +05:30
Rohit Waghchaure
be97f1fe7c fix: incorrect consumed qty if raw material with batch 2020-09-22 10:50:23 +05:30
Rohit Waghchaure
b53a84b07f fix: incorrect consumed qty if raw material with batch 2020-09-22 10:36:52 +05:30
rohitwaghchaure
8a776fdad4 Merge pull request #23378 from rohitwaghchaure/online-pos-print-not-working-pre
fix: online pos print not working
2020-09-22 10:30:53 +05:30
rohitwaghchaure
59a4150428 Merge pull request #23377 from rohitwaghchaure/online-pos-print-not-working
fix: online pos print not working
2020-09-22 10:29:12 +05:30
Rohit Waghchaure
3bebc58357 fix: online pos print not working 2020-09-21 18:32:08 +05:30
Rohit Waghchaure
088e1e66ac fix: online pos print not working 2020-09-21 18:26:52 +05:30
Mangesh-Khairnar
19365d6d07 fix(plaid): do not send null list in account ids (#23375) 2020-09-21 18:04:34 +05:30
Rohan
af585aae28 fix: use Plaid's new API (v12) (#23317)
* fix: use Plaid's new API

* fix: requested changes
2020-09-21 16:08:55 +05:30
Saurabh
3599024c3e Merge pull request #23372 from abhishekbalam/version-12
fix(activation): Added New DocTypes in get_level()
2020-09-21 15:38:02 +05:30
Abhishek Balam
ad5721cbf4 fix: add doctypes to activation 2020-09-21 15:28:13 +05:30
rohitwaghchaure
2ea0263221 Merge pull request #23371 from rohitwaghchaure/enabled-no-copy-for-bill-date-pre
refactor: enabled no copy property for Supplier Invoice Date to avoid…
2020-09-21 14:25:19 +05:30
Rohit Waghchaure
70fc3de817 refactor: enabled no copy property for Supplier Invoice Date to avoid due date validation 2020-09-21 14:23:46 +05:30
rohitwaghchaure
d07579a142 Merge pull request #23367 from rohitwaghchaure/enabled-no-copy-for-bill-date
refactor: enabled no copy property for Supplier Invoice Date to avoid due date validation
2020-09-21 13:46:49 +05:30
rohitwaghchaure
06ecf99609 Merge pull request #23368 from rohitwaghchaure/fix-stock-reco-with-serial-nos-pre-release
fix: stock reconciliation, incorrect serial nos fetched in the current serial no field
2020-09-21 12:55:33 +05:30
Rohit Waghchaure
b07cfd2aec fix: stock reconciliation, incorrect serial nos fetched in the current serial no field 2020-09-21 12:50:47 +05:30
rohitwaghchaure
1b8006be5c Merge pull request #23366 from rohitwaghchaure/fix-stock-reco-with-serial-nos
fix: stock reconciliation, incorrect serial nos fetched in the current serial no field
2020-09-21 12:49:31 +05:30
Rohit Waghchaure
e71e4cf8b5 refactor: enabled no copy property for Supplier Invoice Date to avoid due date validation 2020-09-21 12:26:35 +05:30
Rohit Waghchaure
f5fd2cd4a2 fix: stock reconciliation, incorrect serial nos fetched in the current serial no field 2020-09-21 01:20:00 +05:30
Deepesh Garg
a621c52ebb Merge pull request #23356 from Anurag810/accounts_recievable_v12
fix: Cost Center filter in accounts receivable and payable report
2020-09-20 19:35:26 +05:30
Saqib
3748cbb32c fix: depreciation start date ux fixes (#23340) 2020-09-20 19:31:46 +05:30
Anurag Mishra
d57a94e2f2 fix: No handlefor Cost centers in Accounts Receivable 2020-09-18 13:36:07 +05:30
Deepesh Garg
31a887f045 fix: Taxes not getting fetched from Opportunity to Quotation 2020-09-18 11:32:57 +05:30
Marica
4b2e4026c4 Merge pull request #23338 from marination/item-tax-update-items-fix
fix: Item Tax Updating via `Update Items` in SO/PO
2020-09-16 11:56:29 +05:30
marination
526814c041 fix: Fetch and set Item Tax Template via Update Items 2020-09-16 10:28:33 +05:30
Saqib
1ee7ea6ade fix: update items with workflow travis fix (#23335) 2020-09-15 21:58:36 +05:30
Nabin Hait
c9b5d78993 Merge branch 'version-12-hotfix' into v12-pre-release 2020-09-15 19:43:21 +05:30
rohitwaghchaure
783a4c7f48 fix: set_taxes() missing 1 required positional argument: 'company' (#23329) 2020-09-15 19:42:56 +05:30
Nabin Hait
5750f317c5 Merge branch 'version-12-hotfix' into v12-pre-release 2020-09-15 19:42:05 +05:30
rohitwaghchaure
bea5e5b1bc fix: consumed qty logic for subcontracted raw materials (#23314)
* fix: consumed qty logic for subcontracted raw materials

* added test case

* fix: sales order workflow test case
2020-09-15 19:40:37 +05:30
Saqib
812033b782 fix: purchase order updates are not tracked (#23325) 2020-09-15 11:21:16 +05:30
rohitwaghchaure
bb905ca4b0 fix: incorrect calculation for consumed qty for subcontract item (#23257)
* fix: incorrect calculation for consumed qty for subcontract item

* added test case
2020-09-14 21:12:16 +05:30
Rucha Mahabal
a951a59094 fix: get_transaction_entries function arguments in Bank Statement Transaction Entry (#23052) 2020-09-14 21:05:54 +05:30
rohitwaghchaure
444f657d25 fix: production plan incorrect work order qty (#23264)
* fix: production plan incorrect work order qty

* added test case

* Update test_production_plan.py
2020-09-14 20:51:20 +05:30
Saqib
1e981b50d5 Update items with workflow v12 (#23324)
* feat: validate workflow before so/po update items

* fix: incorrect workflow validation on so/po update items
2020-09-14 19:53:52 +05:30
rohitwaghchaure
279ccc56ee Merge pull request #23320 from marination/quality-inspection-fields-fix
fix: Make Reference fields mandatory in Quality Inspection
2020-09-14 14:11:35 +05:30
Marica
b67996ec42 Merge branch 'version-12-hotfix' into quality-inspection-fields-fix 2020-09-14 12:01:26 +05:30
Marica
fbee0804c3 Merge pull request #23321 from marination/pr-dn-get-items-fix
fix: Make sure Supplier/Customer is selected before fetching Items.
2020-09-14 11:37:25 +05:30
marination
a34a490e0c fix: Make sure Supplier/Customer is selected before fetching Items. 2020-09-14 11:11:39 +05:30
marination
815416adc5 fix: Make Reference fields mandatory in Quality Inspection 2020-09-14 11:07:26 +05:30
Saqib
d409f91469 fix: asset movement date for backdated asset entry (#23300) 2020-09-09 10:53:48 +05:30
rohitwaghchaure
dad5bbdaa2 Merge pull request #23131 from Anurag810/leave_application_form_dashboard_fixes
fix: Form dashboard showing wrong balance
2020-09-08 16:58:11 +05:30
Anurag Mishra
e5fbebf946 fix: update filters 2020-09-08 15:55:07 +05:30
Marica
245cd21c31 Merge pull request #23295 from AfshanKhan/reverse-je-ignore-flag-v12
fix: removed ignore permission flag
2020-09-08 14:52:19 +05:30
Marica
4d9b511bb4 Merge branch 'version-12-hotfix' into reverse-je-ignore-flag-v12 2020-09-08 13:52:54 +05:30
Afshan
f1471ecbd4 fix: removed ignore permission flag 2020-09-08 13:50:54 +05:30
Marica
00a8e2226a Merge pull request #23292 from AfshanKhan/irs-v12
fix: returned empty list if non US based company
2020-09-08 13:45:44 +05:30
Afshan
d44052441b fix: returned empty list if non US based company 2020-09-08 13:03:37 +05:30
rohitwaghchaure
8e21738238 Merge pull request #23192 from marination/batch-source-reference
fix: Unlink and delete batch created from stock reco on cancel
2020-09-08 12:12:30 +05:30
Rucha Mahabal
5096639591 fix: Lock row in subquery while setting delivered qty (#23101) 2020-09-08 11:58:07 +05:30
rohitwaghchaure
810c4250b8 Merge pull request #23286 from rohitwaghchaure/fixed-payment-entry-status-issue
fix: incorrect payment entry status
2020-09-08 10:35:52 +05:30
Deepesh Garg
47c535399c fix: Check if subscription is already created for current invoicing period (#23143)
* fix: Check if subscription is already created for current invoicing period

* fix: Test for duplicate subscription

* fix: invoice generation at the begining of period fix

* fix: invoice generation at the begining of period fix

* fix: Remove unwanted file

* fix: Generate new invoices even though current invoices are unpaid

* fix: Make invoices table read-only

* fix: Update test cases
2020-09-08 10:30:02 +05:30
rohitwaghchaure
b06c618585 Merge pull request #23247 from Anurag810/attendance_calendar_map_v12
fix: Attendance calendar map fix
2020-09-08 10:15:01 +05:30
Rohit Waghchaure
785b7b3359 fix: incorrect payment entry status 2020-09-07 21:54:57 +05:30
Marica
32179293ee Merge branch 'version-12-hotfix' into batch-source-reference 2020-09-07 19:30:36 +05:30
rohitwaghchaure
8dd72018c2 Merge pull request #23262 from rohitwaghchaure/not-able-to-make-material-request-from-so
fix: not able to make material request from SO
2020-09-06 20:49:03 +05:30
rohitwaghchaure
b2bf54cc33 Merge pull request #23260 from anupamvs/se-quantity-v12
fix: SE quantity data type issue
2020-09-04 16:07:32 +05:30
Rohit Waghchaure
4f3eb3fceb fix: not able to make material request from SO 2020-09-04 15:24:56 +05:30
Anupam K
9260cf11b6 fix: SE quantity data type issue 2020-09-04 15:10:50 +05:30
Deepesh Garg
84077676f7 Merge pull request #23254 from anupamvs/profit-loss-fix
fix: profit and loss report not working
2020-09-04 13:23:57 +05:30
Anupam K
5519824414 fix: profit and loss report not working 2020-09-04 11:09:26 +05:30
Deepesh Garg
cce13aaa65 Merge pull request #23252 from deepeshgarg007/hsn_wise_summary
fix: Stock qty in HSN wise outward summary
2020-09-03 21:29:58 +05:30
Deepesh Garg
b78d35ae1d fix: Stock qty in HSN wise outward summary 2020-09-03 21:16:31 +05:30
Marica
7c963a03cb Merge branch 'version-12-hotfix' into batch-source-reference 2020-09-03 18:01:09 +05:30
Marica
4a67da2b0b Merge pull request #23246 from marination/item-tax-query-fix
fix: Misleading filters on Item tax Template Link field
2020-09-03 17:51:42 +05:30
Anurag Mishra
053fdd91da fix: data was not properly maped 2020-09-03 17:11:59 +05:30
marination
c407bb2385 fix: Misleading filters on Item tax Template Link field 2020-09-03 16:54:43 +05:30
Marica
271c550e96 Merge pull request #23244 from marination/purchase-over-receipt-subcontracted-hotfix
fix: Raise Error on over receipt/consumption for sub-contracted PR
2020-09-03 16:45:13 +05:30
marination
8781e77132 fix: Test for Over Receipt via PRs on a PO 2020-09-03 15:48:18 +05:30
marination
5c1f11e561 fix: Raise Error on over receipt/consumption for sub-contrcated PR 2020-09-03 15:47:38 +05:30
Marica
203f78cf97 Merge branch 'version-12-hotfix' into batch-source-reference 2020-09-03 15:39:44 +05:30
rohitwaghchaure
e212537a5f Merge pull request #23186 from rohitwaghchaure/incorrect-stock-balance-issue-for-batched-item
fix: Incorrect stock balance issue for batched item
2020-09-03 15:02:38 +05:30
marination
e33b9628d3 Merge branch 'batch-source-reference' of https://github.com/marination/erpnext into batch-source-reference 2020-09-03 14:42:05 +05:30
marination
44717e3b4a fix: Item Alternative Test 2020-09-03 14:41:05 +05:30
Marica
1dbffa6ccc Merge branch 'version-12-hotfix' into batch-source-reference 2020-09-02 20:24:07 +05:30
marination
9b6326f5d4 chore: Tests for Stock Reconciliation 2020-09-02 19:21:16 +05:30
rohitwaghchaure
bd70dd02c1 Merge pull request #23236 from rohitwaghchaure/fix-pos-special-char-escape-issue
fix: pos item name special character issue
2020-09-02 17:20:43 +05:30
Rohit Waghchaure
f30181527f fix: pos item name special character issue 2020-09-02 17:08:28 +05:30
marination
6b785cf522 chore: Tests for Stock Entry 2020-09-02 15:45:02 +05:30
rohitwaghchaure
ba867d48f7 Merge pull request #23020 from prssanna/gross-profit-total-v12
feat: enable total row in Gross Profit Report
2020-09-02 12:17:33 +05:30
rohitwaghchaure
a0099a3c63 Merge pull request #23124 from ruchamahabal/fix-pos-return
fix: Update paid amount for pos return (#20543)
2020-09-02 12:16:25 +05:30
Marica
3992ddedd0 fix: General Ledger filter validation (#23230) 2020-09-02 11:10:46 +05:30
Shivam Mishra
457a909784 fix: events not deleted on cancelling maintenance schedule (#23219)
* feat: add participant to event_participant child table

* feat: add tests

* chore: update function name

Co-authored-by: Marica <maricadsouza221197@gmail.com>

Co-authored-by: Marica <maricadsouza221197@gmail.com>
2020-09-01 16:30:34 +05:30
Marica
96882f599e Merge pull request #23206 from marination/party-details-hotfix
fix: Check for Company before trying to fetch party details
2020-09-01 16:29:43 +05:30
Marica
c50b296f2d Merge branch 'version-12-hotfix' into party-details-hotfix 2020-09-01 15:36:26 +05:30
Marica
05a90baddd fix: Don't overwrite doctype while setting attributes in child row (#23228) 2020-09-01 15:29:27 +05:30
rohitwaghchaure
14ea8928f5 Merge pull request #23226 from rohitwaghchaure/fixed-job-card-time-log-issue
fix: incorrect job card timer issue
2020-09-01 14:08:29 +05:30
Rohit Waghchaure
ee4e725b37 fix: incorrect job card timer issue 2020-09-01 14:02:34 +05:30
Afshan
ab6f761753 fix:reverse journal entry (#23224) 2020-08-31 22:01:54 +05:30
Rucha Mahabal
b574353c00 fix(Payroll Entry): Set cost center for payroll payable account (#23223) 2020-08-31 20:09:48 +05:30
Deepesh Garg
3bf5820236 Merge pull request #23081 from deepeshgarg007/hsn_wise_json_v12_hotfix
feat: JSON download for HSN wise outward summary
2020-08-31 17:15:45 +05:30
Marica
0ff376fa4a fix: Better error feedback on creating SO from Quotation (#23214) 2020-08-31 13:54:10 +05:30
rohitwaghchaure
dc8de013c9 Merge pull request #23215 from rohitwaghchaure/fixed-different-workstation-not-update-qty
fix: incorrect completed qty against operation in work order if workstation is different in job card
2020-08-31 13:29:44 +05:30
Rohit Waghchaure
b73879056f fix: incorrect completed qty against operation in work order if workstation is different in job card 2020-08-31 12:27:49 +05:30
rohitwaghchaure
a2c4cc1252 Merge pull request #23126 from rohitwaghchaure/multi-operation-job-card-issue
fix: user created manual job card not linking job card operation with work order operation
2020-08-31 11:52:20 +05:30
marination
17a3af47d9 fix: Check for Company before trying to fetch party details 2020-08-29 19:28:51 +05:30
Rohit Waghchaure
e352706330 fix: user created manual job card not linking job card operations with work order operations 2020-08-28 12:29:27 +05:30
rohitwaghchaure
8dc7a43cc9 Merge pull request #23169 from ruchamahabal/fix-appointment-duration-v12
fix: don't overwrite patient appointment duration if already specified
2020-08-28 10:39:59 +05:30
rohitwaghchaure
aa795efe15 Merge pull request #23171 from anupamvs/product-contact-us
feat: Added phone field in product Inquiry
2020-08-28 10:38:07 +05:30
rohitwaghchaure
89d1990d79 Merge pull request #23179 from marination/pricing-rule-missing-fix-version-12-hotfix
fix: Pricing rule encoding missing line
2020-08-28 10:36:24 +05:30
rohitwaghchaure
c8f695c0da Merge pull request #23191 from ruchamahabal/fix-bom-update-v12
fix: BOM Update Tool failing due to Too Many Writes error
2020-08-28 10:35:47 +05:30
marination
eab2d25c6a fix: Unlink and delete batch created from stock reco on cancel 2020-08-27 20:34:51 +05:30
Rucha Mahabal
00dbbc9f5c fix: BOM Update Tool failing due to Too Many Writes error 2020-08-27 19:00:07 +05:30
Rohit Waghchaure
09cb0f33b2 added test cases 2020-08-27 14:57:37 +05:30
Rohit Waghchaure
dcd80a3f48 fix: incorrect stock balance issue 2020-08-27 13:24:33 +05:30
Saurabh
8bd9bf2be6 Merge branch 'v12-pre-release' into version-12 2020-08-27 10:04:32 +05:30
Saurabh
fc7121e38f bumped to version 12.11.2 2020-08-27 10:24:32 +05:50
rohitwaghchaure
03488f8285 Merge pull request #23177 from marination/pricing-rule-missing-fix-v12-pre-release
fix: Pricing Rule encoding missing line
2020-08-27 10:00:48 +05:30
marination
4cce4a7712 fix: get_applied_pricing_rule in taxes_and_totals 2020-08-26 20:18:37 +05:30
marination
4e3bbb8e74 fix: get_applied_pricing_rule in taxes_and_totals 2020-08-26 20:09:11 +05:30
Rucha Mahabal
a3907e1329 fix: don't overwrite appointment duration if already specified 2020-08-26 15:15:05 +05:30
Anupam K
759282651b feat: Added phone field in product Inquiry 2020-08-26 14:23:56 +05:30
rohitwaghchaure
3bae6328c5 Merge pull request #23153 from ruchamahabal/fix-conversion-factor-v12
fix: conversion factor for BOM exploded item rate
2020-08-26 13:02:48 +05:30
Deepesh Garg
45d615887a fix: Codacy fixes 2020-08-26 12:12:06 +05:30
Rucha Mahabal
ed6cbc1239 Merge pull request #23164 from frappe/michellealva-sales_invoice_dashboard
fix: Add Delivery Note link in Sales Invoice Dashboard
2020-08-25 21:09:50 +05:30
Michelle Alva
deb741bea5 fix:Add Delivery Note link in Sales Invoice Dashboard 2020-08-25 21:00:41 +05:30
Saurabh
271f8b5cfd Merge branch 'v12-pre-release' into version-12 2020-08-25 20:01:54 +05:30
Saurabh
f26e66b2b5 bumped to version 12.11.1 2020-08-25 20:21:54 +05:50
Saurabh
020534046c Merge pull request #23162 from rohitwaghchaure/pricing-rule-not-working-js-side-v12-pre-release
fix: mixed condition pricing rule not working on js side
2020-08-25 20:01:02 +05:30
Rohit Waghchaure
0407a435d7 fix: mixed condition pricing rule not working on js side 2020-08-25 19:59:17 +05:30
Saurabh
1c19050aa4 Merge pull request #23160 from rohitwaghchaure/pricing-rule-not-working-js-side
fix: mixed condition pricing rule not working on js side
2020-08-25 19:40:54 +05:30
Rohit Waghchaure
62876c708b fix: mixed condition pricing rule not working on js side 2020-08-25 18:32:46 +05:30
Rucha Mahabal
3fc00a5bfe fix: conversion factor for BOM exploded item rate 2020-08-25 18:09:14 +05:30
Saurabh
8245640ca2 Merge pull request #23149 from rohitwaghchaure/pricing-rule-encoding-pre-release-v12
fix(hot): Pricing Rule encoding fixed
2020-08-25 17:24:56 +05:30
Rohit Waghchaure
29d24cddcf fix(hot): Pricing Rule encoding fixed 2020-08-25 17:22:20 +05:30
Saurabh
9aa230c1b8 Merge pull request #23146 from rohitwaghchaure/pricing-rule-encoding-hotfix
fix(hot): Pricing Rule encoding fixed
2020-08-25 17:19:17 +05:30
Rohit Waghchaure
d223d4b829 fix(hot): Pricing Rule encoding fixed 2020-08-25 16:18:44 +05:30
Anurag Mishra
69bb85d1d0 fix: Form dashboard showing wrong balance 2020-08-25 06:55:02 +05:30
rohitwaghchaure
51c29cafee Merge pull request #23082 from ruchamahabal/fix-pos-print-v12
fix: Print Language for Customer not set for POS Invoice
2020-08-24 16:11:26 +05:30
rohitwaghchaure
6594d127cb Merge pull request #23113 from wojosc/patch-12
refactor: allow to rename lead
2020-08-24 16:09:14 +05:30
rohitwaghchaure
65d16d1ef6 Merge pull request #23117 from nabinhait/subcontracted-pr-gle-v12
fix: GLE for subcontracted PR is fg item rate is zero
2020-08-24 16:06:59 +05:30
Deepesh Garg
9b4cc0b6e9 fix: Update paid amount for pos return (#20543)
* fix: Paid amount updation for pos return

* fix: Remove console

* fix: Styling

* fix: get  default mode of payment from POS profile

* fix: Add test cases

* fix: Codacy
2020-08-24 15:01:57 +05:30
Saurabh
f843d6aa53 Merge branch 'v12-pre-release' into version-12 2020-08-24 10:11:45 +05:30
Saurabh
c6ed332903 bumped to version 12.11.0 2020-08-24 10:25:29 +05:50
Nabin Hait
ad07abeb3f chore: Added change log 2020-08-23 11:27:05 +05:30
Nabin Hait
a82d9d3182 test: Test case for GLE in subcontracted PR if FG item rate is zero 2020-08-22 20:07:19 +05:30
Nabin Hait
98fda4b8c3 fix: GLE for subcontracted PR is fg item rate is zero 2020-08-22 20:07:05 +05:30
Wolfram Schmidt
572d150925 Update lead_source.json
as requested in https://github.com/frappe/erpnext/pull/22872
2020-08-21 20:02:29 +02:00
Saqib
6c6175200c fix: cannot search items in offline pos (#23083) 2020-08-21 15:40:29 +05:30
rohitwaghchaure
6bb2038323 Merge pull request #23084 from nextchamp-saqib/pos-search-fix-pre-release
fix: cannot search items in offline pos
2020-08-21 13:13:50 +05:30
Nabin Hait
3d1df94ad2 fix:Validate Job offer against vacancies (#23108) 2020-08-20 19:39:03 +05:30
Nabin Hait
fa36a06188 fix:Validate Job offer against vacancies (#23107) 2020-08-20 19:38:55 +05:30
Deepesh Garg
c3c06c36a5 Merge pull request #23103 from deepeshgarg007/rcm_submit
fix: Unable to submit reverse charge invoice
2020-08-20 19:36:02 +05:30
Deepesh Garg
53aee98103 Merge pull request #23104 from deepeshgarg007/rcm_submit_v12
fix: Unable to submit reverse charge invoice
2020-08-20 19:35:48 +05:30
Marica
e52bd5c699 fix: Create Opoortunity without Default Company from Email (#23099)
* fix: Create Opoortunity without Default Company from Email

* fix: Add Prompt to Select Company

* Update communication.js

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2020-08-20 19:11:59 +05:30
Marica
685ca83b5e fix: Create Opoortunity without Default Company from Email (#23098)
* fix: Create Opoortunity without Default Company from Email

* fix: Add Prompt to Select Company

* Update communication.js

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2020-08-20 19:11:40 +05:30
Deepesh Garg
e1f9148351 Merge branch 'v12-pre-release' of https://github.com/frappe/erpnext into rcm_submit_v12 2020-08-20 16:49:43 +05:30
Deepesh Garg
093fb84377 fix: Unable to submit reverse charge invoice 2020-08-20 16:44:08 +05:30
Deepesh Garg
8c5bc5631a fix: Unable to submit reverse charge invoice 2020-08-20 16:31:38 +05:30
Rucha Mahabal
46456fdc19 Merge pull request #23095 from nextchamp-saqib/sr-no-selector-fix-hotfix
fix: val is not defined
2020-08-20 15:01:58 +05:30
Rucha Mahabal
737d305f45 Merge pull request #23094 from nextchamp-saqib/sr-no-selector-fix-pre-release
fix: val is not defined
2020-08-20 15:01:28 +05:30
Deepesh Garg
2aa23f91b1 Merge pull request #23092 from rohitwaghchaure/not-able-to-submit-dn-hotfix
fix: not able to submit delivery note
2020-08-20 13:35:40 +05:30
Saqib Ansari
2cc0ad51f5 fix: val is not defined 2020-08-20 12:54:36 +05:30
Saqib Ansari
193222a336 fix: val is not defined 2020-08-20 12:53:43 +05:30
rohitwaghchaure
46bea91469 Merge pull request #23093 from rohitwaghchaure/not-able-to-submit-dn
fix: not able to submit delivery note
2020-08-20 12:28:35 +05:30
Rohit Waghchaure
5e32ee8457 fix: not able to submit delivery note 2020-08-20 12:21:09 +05:30
Rohit Waghchaure
f09d472fcd fix: not able to submit delivery note 2020-08-20 12:20:23 +05:30
Suraj Shetty
4ff1a4361d refactor: Format and sanitise user inputs to search queries. (#23091)
* refactor: Sanitize whitelisted method inputs

Co-authored-by: Prssanna Desai <prssud@gmail.com>
Co-authored-by: Shivam Mishra <scmmishra@users.noreply.github.com>

* refactor: Format and sanitize tax_account_query inputs

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
Co-authored-by: Prssanna Desai <prssud@gmail.com>
Co-authored-by: Shivam Mishra <scmmishra@users.noreply.github.com>

* refactor: Validate and sanitize search inputs via decorator

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
Co-authored-by: Prssanna Desai <prssud@gmail.com>
Co-authored-by: Shivam Mishra <scmmishra@users.noreply.github.com>

* style: Minor formatting fix

* refactor: Validate and sanitize search inputs using decorator

* fix: Typo

* fix: Remove unwanted import statement

* refactor: Repalce validate_and_sanitize_search_inputs() with validate_and_sanitize_search_inputs

Co-authored-by: Prssanna Desai <prssud@gmail.com>
Co-authored-by: Shivam Mishra <scmmishra@users.noreply.github.com>

Co-authored-by: Prssanna Desai <prssud@gmail.com>
Co-authored-by: Shivam Mishra <scmmishra@users.noreply.github.com>
Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2020-08-20 11:27:19 +05:30
Suraj Shetty
bf7adb8b38 refactor: Format and sanitise user inputs to search queries. (#23064)
* refactor: Sanitize whitelisted method inputs

Co-authored-by: Prssanna Desai <prssud@gmail.com>
Co-authored-by: Shivam Mishra <scmmishra@users.noreply.github.com>

* refactor: Format and sanitize tax_account_query inputs

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
Co-authored-by: Prssanna Desai <prssud@gmail.com>
Co-authored-by: Shivam Mishra <scmmishra@users.noreply.github.com>

* refactor: Validate and sanitize search inputs via decorator

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
Co-authored-by: Prssanna Desai <prssud@gmail.com>
Co-authored-by: Shivam Mishra <scmmishra@users.noreply.github.com>

* style: Minor formatting fix

* refactor: Validate and sanitize search inputs using decorator

* fix: Typo

* fix: Remove unwanted import statement

* refactor: Repalce validate_and_sanitize_search_inputs() with validate_and_sanitize_search_inputs

Co-authored-by: Prssanna Desai <prssud@gmail.com>
Co-authored-by: Shivam Mishra <scmmishra@users.noreply.github.com>

Co-authored-by: Prssanna Desai <prssud@gmail.com>
Co-authored-by: Shivam Mishra <scmmishra@users.noreply.github.com>
Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2020-08-20 11:17:30 +05:30
Deepesh Garg
c7c72b76c6 Merge pull request #23087 from deepeshgarg007/rcm_deduction_hotfix
fix: Do not update total for RCM invvoices if net taxes are zero
2020-08-19 18:39:09 +05:30
Deepesh Garg
6aa3191cad fix: Do not update total for RCM invvoices if net taxes are zero 2020-08-19 18:36:43 +05:30
Deepesh Garg
848288ed36 Merge pull request #23086 from deepeshgarg007/rcm_deduction
fix: Do not update total for RCM invvoices if net taxes are zero
2020-08-19 18:34:27 +05:30
Deepesh Garg
1c29da32fc fix: Do not update total for RCM invvoices if net taxes are zero 2020-08-19 18:30:18 +05:30
Saqib Ansari
1fdfcc00d6 fix: cannot search items in offline pos 2020-08-19 17:26:38 +05:30
Rucha Mahabal
f61a8bc889 fix: Print Language for Customer not set for POS Invoice 2020-08-19 16:18:06 +05:30
Deepesh Garg
1bf9de1527 feat: JSON download for HSN wise outward summary 2020-08-19 15:46:15 +05:30
Deepesh Garg
dae1fad1a6 fix: Total calculations for multicurrency RCM invoices (#23070) 2020-08-18 19:32:38 +05:30
Deepesh Garg
af45eceeb2 fix: Total calculations for multicurrency RCM invoices (#23071) 2020-08-18 19:32:00 +05:30
Anupam Kumar
09b6628e53 fix: Leave application status (#23043)
* fix: leave application status update fix

* fix:adding patch
2020-08-18 14:43:34 +05:30
Deepesh Garg
693bf1309a Merge pull request #23021 from prssanna/expense-claim-list-currency-v12
fix: add company in list fields to fetch for Expense Claim
2020-08-17 23:08:27 +05:30
Afshan
df42df5246 fix: handled condition if staffing isn't created (#23057)
Co-authored-by: Marica <maricadsouza221197@gmail.com>
2020-08-17 13:48:07 +05:30
Afshan
4b6d5ef6aa fix: the JSON object must be str, bytes or bytearray, not "list" (#23053) 2020-08-17 12:25:34 +05:30
Rucha Mahabal
5e51a1fe9b Merge pull request #23037 from aakvatech/patch-5
fix: AttributeError: 'ProgramFee' object has no attribute 'course'
2020-08-14 13:21:45 +05:30
aakvatech
2cdc0c3f2d fix: AttributeError: 'ProgramFee' object has no attribute 'course'
Error occurs while program enrollment on new student.

This happens on version 12 and not on version 13.

Version 12 uses
course_list = [course.course for course in program.get_all_children()]

where as version 13 uses
course_list = [course.course for course in program.courses]

erpnext/erpnext/education/doctype/program_enrollment/program_enrollment.py
2020-08-14 10:26:54 +03:00
Rucha Mahabal
7234330db9 Merge pull request #23032 from frappe/revert-23031-patch-4
Revert "fix: AttributeError: 'ProgramFee' object has no attribute 'course'"
2020-08-14 11:21:49 +05:30
Rucha Mahabal
2fa9b3a713 Revert "fix: AttributeError: 'ProgramFee' object has no attribute 'course'" 2020-08-14 11:21:23 +05:30
Rucha Mahabal
1aec8f57f2 Merge pull request #23031 from aakvatech/patch-4
fix: AttributeError: 'ProgramFee' object has no attribute 'course'
2020-08-14 11:21:18 +05:30
aakvatech
24f350a1a8 fix: AttributeError: 'ProgramFee' object has no attribute 'course'
Error occurs while program enrollment on new student.

This happens on version 12 and not on version 13.

Version 12 uses
course_list = [course.course for course in program.get_all_children()]

where as version 13 uses
course_list = [course.course for course in program.courses]

erpnext/erpnext/education/doctype/program_enrollment/program_enrollment.py
2020-08-14 06:59:44 +03:00
prssanna
c28e37781a fix: add company in list fields to fetch for Expense Claim 2020-08-13 11:56:30 +05:30
prssanna
4d8340d7b9 feat: enable total row in Gross Profit Report 2020-08-13 11:40:56 +05:30
Nabin Hait
387e0878b6 Merge branch 'version-12-hotfix' into v12-pre-release 2020-08-13 09:28:27 +05:30
Saqib
6c536bb6e0 fix: cannot change customer fields if credit exhausted (#22838)
* fix: cannot change customer fields if credit exhausted

* fix: order based on company

* fix: sort current limits w.r.t company before compare

* fix: CustomerCreditLimit Object is not subscriptable
2020-08-13 09:27:50 +05:30
Nabin Hait
0a061d4082 Merge branch 'version-12-hotfix' into v12-pre-release 2020-08-13 09:23:22 +05:30
Nabin Hait
af9d653fb4 Inclusive tax based on item quantity v12 (#23015)
* fix: Calculate taxes if tax is based on item quantity and inclusive on item price

* git commit -m "fix: Add missing semicolon"

* fix: Calculate taxes if tax is based on item quantity

Co-authored-by: Deepesh Garg <42651287+deepeshgarg007@users.noreply.github.com>
2020-08-13 09:22:05 +05:30
Anupam Kumar
8969e19594 fix: Opportunity/Quotation Lost Reason Fix (#23016) 2020-08-13 09:19:53 +05:30
Deepesh Garg
a979fcc25b fix: Project link not set in accounts other than profit and loss accounts (#22049)
* fix: project link not set in accounts other than profilt and loss accounts

* fix: cannot find get_allow_cost_center_in_entry_of_bs_account

* fix: remove enable_allow_cost_center_in_entry_of_bs_account

* chore: add tests and remove test based on allow_cost_center_for_bs_accounts

* fix: travis

* fix: Test Cases

* fix: Patch to remove Property Setter

* fix: Test Cases

* fix: Remove v13 patch

* fix: Procurement Tracker test case

* fix: Proccurement tracker report test

* fix: Codacy

* fix: Remove duplicate project field

Co-authored-by: Saqib Ansari <nextchamp.saqib@gmail.com>
Co-authored-by: rohitwaghchaure <rohitw1991@gmail.com>
2020-08-12 21:06:25 +05:30
Rucha Mahabal
9bd041c14c fix: don't set asset maintenance log status as Overdue when Completed or Cancelled (#23012)
* fix: don't set maintenance log status as Overdue when Completed or Cancelled

* fix: set draft indicators for Asset Maintenance Log listview
2020-08-12 19:34:54 +05:30
Deepesh Garg
1bb6ef3356 fix: Update state code and union territory for Daman and Diu (#22989)
Co-authored-by: Rucha Mahabal <ruchamahabal2@gmail.com>
2020-08-12 19:34:23 +05:30
Deepesh Garg
5cc5bc246a fix: Cancellation of accounting transactions within closed accounting period (#22986) 2020-08-12 17:56:57 +05:30
Rucha Mahabal
2a0ed798aa fix: TypeError while setting transfer_qty in Stock Entry (#22931)
Co-authored-by: Marica <maricadsouza221197@gmail.com>
2020-08-12 14:32:23 +05:30
Marica
033d98cd68 Merge pull request #23002 from AfshanKhan/fix-duplicate-dropdown-PO-v12
fix: moved custom_make_buttons to PurchaseOrderController to avoid duplication of dropdown options
2020-08-11 20:57:11 +05:30
Afshan
ec3dc95e6e fix: moved custom_make_buttons to PurchaseOrderController to avoid duplication of dropdown options 2020-08-11 20:42:16 +05:30
Deepesh Garg
57d86a3bc1 Merge pull request #22973 from marination/opportunity-from-email-fix
fix: Creating opportunity from email
2020-08-10 16:12:00 +05:30
marination
265916543d fix: Creating opportunity from email 2020-08-10 14:42:30 +05:30
Deepesh Garg
f63182df5a Merge pull request #22968 from deepeshgarg007/gst_export_wopay_v12
fix: GSTR 1 report for exports without payment of Tax
2020-08-10 11:29:56 +05:30
Deepesh Garg
9d455cf4a6 fix: GSTR 1 report for exports without payment of Tax 2020-08-10 09:57:28 +05:30
Deepesh Garg
ff9c40fde6 Merge pull request #22730 from deepeshgarg007/gstr3b_cess_v12_hotfix
fix: Multiple GST fixes
2020-08-08 22:15:25 +05:30
Deepesh Garg
f0f20bb434 fix: RCM taxable value in GSTR3b report 2020-08-08 20:58:01 +05:30
Deepesh Garg
bbfd5a4cc8 fix: Test Cases 2020-08-08 19:46:09 +05:30
Deepesh Garg
3ae4a83504 fix: Add print for debug 2020-08-08 17:52:45 +05:30
Deepesh Garg
1da33f4129 fix: Test case 2020-08-07 22:51:33 +05:30
Deepesh Garg
b8eff8d141 fix: Test case 2020-08-07 22:02:14 +05:30
Deepesh Garg
67e07b69dd fix: More print statements for debugging 2020-08-07 15:59:03 +05:30
Deepesh Garg
7d262d1a08 Merge pull request #22928 from deepeshgarg007/paymemnt_reco_multi_v12
fix: Multi currency payment reconciliation
2020-08-07 15:36:37 +05:30
Deepesh Garg
5f8e8a3c29 fix: Add debug print statement 2020-08-07 10:05:22 +05:30
Deepesh Garg
2169bb7640 fix: Add print 2020-08-06 23:16:33 +05:30
Deepesh Garg
33754b9dc8 fix: add print for debug 2020-08-06 22:17:37 +05:30
Deepesh Garg
bb451360ba Merge branch 'version-12-hotfix' of https://github.com/frappe/erpnext into gstr3b_cess_v12_hotfix 2020-08-06 21:50:27 +05:30
Afshan
2cf4168009 fix: show or hide section or attributes depending on other attributes… (#22933)
* fix: show or hide section or attributes depending on other attributes for better UI

* fix:depends on: batch_no for retain sample

Co-authored-by: Marica <maricadsouza221197@gmail.com>
2020-08-06 19:04:35 +05:30
Shivam Mishra
80c016a1ad Merge pull request #22935 from scmmishra/fix-product-configurator
fix: handle product_info null in item_configure
2020-08-06 11:39:32 +00:00
Shivam Mishra
3619628e60 fix: handle product_info null 2020-08-06 17:08:14 +05:30
Marica
e2e9633ee1 Merge pull request #22927 from deepeshgarg007/price_rule_fix_v12
fix: Error due to comma in Pricing rule name
2020-08-06 16:57:18 +05:30
Shivam Mishra
abd111331e Merge pull request #22934 from scmmishra/fix-product-configurator
fix: unbound error in product configurator 61b9727
2020-08-06 11:22:39 +00:00
Shivam Mishra
61b9727fa2 fix: unbound error in product configurator 2020-08-06 16:47:43 +05:30
Marica
74643c804d Merge branch 'version-12-hotfix' into price_rule_fix_v12 2020-08-06 14:38:59 +05:30
Marica
e7162a86c6 Merge pull request #22930 from deepeshgarg007/payment_reco_cost_center_fix_v12
fix: Add default cost center in payment reconciliation JV
2020-08-06 14:31:52 +05:30
Deepesh Garg
b3cdd91d65 fix: Tests 2020-08-06 13:18:42 +05:30
Deepesh Garg
dd64cd1512 fix: Add default cost center in payment reconciliation JV 2020-08-06 11:46:25 +05:30
Deepesh Garg
024c78f522 fix: Hide currency link fields 2020-08-06 11:31:00 +05:30
Deepesh Garg
e6ec549c81 fix: Multi currency payment reconciliation 2020-08-06 11:30:46 +05:30
Deepesh Garg
579167d1de fix: Remove print statement 2020-08-06 11:27:27 +05:30
Deepesh Garg
10604664d4 fix: Error due to commma in Pricing rule name 2020-08-06 11:27:18 +05:30
Marica
97e96cec51 fix: get_regional_address_details missing positional arg 'company' (#22920) 2020-08-05 17:10:50 +05:30
Anurag Mishra
d2593f0af5 fix: set half day date None if half day is unchecked (#22905) 2020-08-04 19:29:56 +05:30
Rucha Mahabal
02fcf569e6 fix: SQL query in accounts receivable, payable reports (#22891) 2020-08-03 20:41:37 +05:30
Marica
9afebd311f fix: Reposition description in Warehouse (#22896) 2020-08-03 20:39:41 +05:30
Rucha Mahabal
4f6a25539a fix: TypeError while concatenating account number and name in COA (#22886) 2020-08-03 15:51:39 +05:30
Nabin Hait
ec46b8c73b fix: Bank Clearance of POS purchase invoice (#22884) 2020-08-03 15:39:29 +05:30
Marica
a9cfe0c95c fix: Misleading description in Warehouse (#22879) 2020-08-03 14:56:46 +05:30
Rucha Mahabal
3d2fa59e6d fix(Education): course wise assessment report labels (#22805)
* fix: add labels to chart datasets in course wise assessment

* fix: change label for final grade

Co-authored-by: Marica <maricadsouza221197@gmail.com>
2020-07-30 13:27:47 +05:30
Rucha Mahabal
b2eddedfb1 fix: change owner fieldtype to Link in Lead Owner Efficiency Report (#22840) 2020-07-29 17:19:11 +05:30
Marica
b7efef79dc fix: Exploded Item Rate (#22816) 2020-07-27 14:54:59 +05:30
bhavesh95863
ca6ec72ade fix: Add missing translation function for freeze message (#22812)
* fix[missing translation function]

missing translation function

* fix[missing translation function for message]

missing translation function for message

* fix[add missing translation function]

add missing translation function

* Update payroll_entry.js

Co-authored-by: Rucha Mahabal <ruchamahabal2@gmail.com>
2020-07-26 14:03:03 +05:30
Deepesh Garg
680f2600be Merge pull request #22303 from P-Froggy/fix-payment-entry-wrong-bank-account-fetch-v12
fix: Set Value of wrong Bank Account Field in Payment Entry
2020-07-24 19:04:51 +05:30
Mangesh-Khairnar
af9e44f059 fix(payment-request): do not set guest as administrator (#22803) 2020-07-24 18:18:49 +05:30
Deepesh Garg
dde92e0fdb Merge branch 'version-12-hotfix' of https://github.com/frappe/erpnext into gstr3b_cess_v12_hotfix 2020-07-24 14:09:02 +05:30
Deepesh Garg
d9aa115aaf fix: Remove print and add Cess account 2020-07-24 14:08:05 +05:30
rohitwaghchaure
6a48988c76 fix: incorrect stock value in return case (#22528)
Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2020-07-24 10:46:55 +05:30
Nabin Hait
e62da1455c fix: Other charges on income tax (#22798) 2020-07-24 09:20:41 +05:30
Anupam Kumar
45a3580c20 Unable to change link from new lead to existing customer (#22795) 2020-07-24 08:53:24 +05:30
Rucha Mahabal
9abb8e309e fix(Education): descriptions not copied while creating fees from fee structure (#22793) 2020-07-24 08:52:53 +05:30
Rucha Mahabal
c5b6ba7556 Merge pull request #22794 from Mangesh-Khairnar/maintainance-visit-fixes
fix(maintenance-visit): change fieldtype of status to select
2020-07-24 00:10:09 +05:30
Mangesh-Khairnar
cf902a1e2d fix(maintenance-visit): change fieldtype of status to select 2020-07-23 23:55:58 +05:30
Sun Howwrongbum
4e3df334db fix: [v12] incorrect available_qty being set (#22541)
* fix: incorrect available_qty being set

* style: descriptive variables
2020-07-23 20:06:15 +05:30
Deepesh Garg
9067adf141 fix: Add print for debug 2020-07-23 19:48:18 +05:30
Deepesh Garg
d18eb0e63e Merge pull request #22702 from pipech/v12-hotfix-transaction_pricing_rule
fix(pricing): transaction pricing rule
2020-07-23 19:19:55 +05:30
aakvatech
3adeab45ce Update transaction.js (#22788)
Added frappe.flags.hide_serial_batch_dialog = true that was missing in version-12
2020-07-23 12:14:36 +05:30
Marica
0fee76f409 fix: Dont merge items if both exist in stock reco (#22784)
* fix: incorrect stock after merging items

* fix: Readability fix

Co-authored-by: Rohit Waghchaure <rohitw1991@gmail.com>
2020-07-22 18:53:40 +05:30
Marica
74963e9711 fix: Serial No Rename does not affect Stock Ledger Entry (#22780) 2020-07-22 18:17:25 +05:30
Deepesh Garg
7d8887916e Merge pull request #22755 from deepeshgarg007/hsn_code_report_v12
fix: Tax amounts in HSN Wise Outward summary
2020-07-22 16:26:38 +05:30
Deepesh Garg
e077c0a270 fix: Randomly failing test (#22773)
* fix(travis): Item Tax tempate template test

* fix: Update tests

* fix: Test

* fix: Do not use random customers

* fix: Remove every bit of randomness from this test
2020-07-22 16:12:12 +05:30
Afshan
517108d10a fix: added set query for filters in MR (#22770)
Co-authored-by: Marica <maricadsouza221197@gmail.com>
2020-07-22 15:51:48 +05:30
Afshan
a7094641d4 style: moved parent warehouse to top section also added a section break for better look (#22772)
Co-authored-by: Marica <maricadsouza221197@gmail.com>
2020-07-22 15:45:37 +05:30
Deepesh Garg
ad94f7516b Merge pull request #22763 from DeeMysterio/fs-hotfix
fix(report): fix alignment in script report that extends financial_statements.js
2020-07-22 14:46:08 +05:30
Diksha Jadhav
1943d413a4 fix(report): fix alignment in script report that extends financial_statements.js 2020-07-21 17:59:12 +05:30
Deepesh Garg
82fbef4163 fix: Remove print statements 2020-07-21 14:54:21 +05:30
Deepesh Garg
83ad6df229 fix: Tax amounts in HSN Wise Outward summary 2020-07-21 14:25:51 +05:30
Deepesh Garg
b9ba63b0d8 fix: Test Case 2020-07-20 18:08:56 +05:30
Marica
bc248bfaed Merge pull request #22646 from rohitwaghchaure/incorrect-qty-after-transaction-stock-reco
fix: incorrect qty after transaction in stock ledger entry
2020-07-20 15:51:37 +05:30
Deepesh Garg
0b31d6f630 fix: Test Case 2020-07-20 13:34:46 +05:30
Marica
7e461ce860 Merge branch 'version-12-hotfix' into incorrect-qty-after-transaction-stock-reco 2020-07-20 11:34:29 +05:30
Deepesh Garg
6946796047 fix: Tests 2020-07-19 22:23:13 +05:30
Deepesh Garg
6d39066d86 fix: Multiple fixes in GST 2020-07-17 22:20:04 +05:30
Deepesh Garg
b6da70efec fix: Cess amount in GSTR 3B report 2020-07-17 22:19:34 +05:30
rohitwaghchaure
3068fe43c6 Merge branch 'version-12-hotfix' into v12-hotfix-transaction_pricing_rule 2020-07-17 14:46:45 +05:30
rohitwaghchaure
7709c640b5 Merge pull request #22720 from rohitwaghchaure/fixed-incorrect-currency-symbol-in-stock-balance-report
fix: currency symbol not showing as per company currency in stock bal…
2020-07-17 14:35:13 +05:30
rohitwaghchaure
8558e26648 Merge pull request #22716 from rohitwaghchaure/fixed-actual-qty-showing-as-zero
Fix: Stock Reconciliation Invalid Quantity for Batched Item
2020-07-17 12:07:45 +05:30
Rohit Waghchaure
34a91bd7e6 fix: currency symbol not showing as per company currency in stock balance 2020-07-17 11:24:40 +05:30
rohitwaghchaure
785462b513 Update stock_reconciliation.js 2020-07-17 10:55:05 +05:30
Rohit Waghchaure
0d5f8c5050 fix: for past dated stock reco, batched item showing the current available qty instead of quantity as per posting date 2020-07-17 08:57:31 +05:30
Deepesh Garg
13088173eb Merge pull request #22703 from deepeshgarg007/rcm_ountry_fix
fix: Update RCM only for indian countries
2020-07-15 23:58:16 +05:30
Deepesh Garg
c10dd29282 fix: Update RCM only for indian countries 2020-07-15 23:57:03 +05:30
Deepesh Garg
95da4157a9 Merge pull request #22699 from rohitwaghchaure/fixed-not-able-to-submit-si-hotfix
fix: not able to submit sales invoice
2020-07-15 21:50:45 +05:30
Poranut Chollavorn
1411d002f6 fix(pricing): transaction pricing rule
add tranasction type to transaction pricing rule selector
2020-07-15 14:55:20 +00:00
rohitwaghchaure
0f2601a6a6 Merge pull request #22649 from rohitwaghchaure/fixed-incorrect-balance-qty-in-stock-ledger
fix: incorrect balance qty in stock ledger report
2020-07-15 17:20:04 +05:30
Rohit Waghchaure
c785ff9874 fix: not able to submit sales invoice 2020-07-15 17:17:23 +05:30
rohitwaghchaure
ab9cbc1e2c Merge pull request #22690 from marination/pr-project-stock-ledger-fix
fix: Added Project Field in Purchase Receipt for Stock Ledger Tagging
2020-07-15 15:42:58 +05:30
rohitwaghchaure
237dc4250a Merge pull request #22667 from ruchamahabal/fix-healthcare-setup-v12
fix(Healthcare): set company in Healthcare Service Unit setup
2020-07-15 14:33:42 +05:30
marination
71fa045ba4 fix: Added Project Field in Purchase Receipt for Stock Ledger Tagging 2020-07-15 12:54:19 +05:30
rohitwaghchaure
5e5e82a9f6 Merge pull request #22684 from nabinhait/company-abbr-replace
fix: Replace company abbr
2020-07-15 12:31:19 +05:30
Deepesh Garg
898dafe748 fix: Period list fixes in financial statements (#22679) 2020-07-15 12:17:23 +05:30
Deepesh Garg
1f7e941d68 fix(GST): Do not add tax amount in grand total for reverse charge invoices (#22686)
* fix(GST): Do not add tax amount in grand total for reverse charge invoices

* fix: Code cleanup

* fix: Remove print statements
2020-07-14 22:05:45 +05:30
Nabin Hait
395f44c8b7 fix: Replace company abbr 2020-07-14 20:46:25 +05:30
Rucha Mahabal
ea1662c15b Merge pull request #22659 from bhavesh95863/patch-3
fix: Quotation list view blank if quotation_to field not set as a standard filter
2020-07-13 19:55:54 +05:30
bhavesh95863
fd8c856af2 fix:whitespace missing
Co-authored-by: Rucha Mahabal <ruchamahabal2@gmail.com>
2020-07-13 18:48:47 +05:30
Rucha Mahabal
672497ba63 Merge branch 'version-12-hotfix' into fix-healthcare-setup-v12 2020-07-13 16:39:05 +05:30
Rucha Mahabal
9c410d8a27 fix(Healthcare): set company in Healthcare Service Unit setup 2020-07-13 16:27:59 +05:30
Deepesh Garg
8317ff8bb2 Merge branch 'version-12-hotfix' into fixed-incorrect-balance-qty-in-stock-ledger 2020-07-12 17:21:25 +05:30
bhavesh95863
70eb94280e fix: Quotation list view blank if quotation_to field not set as a standard filter
fix: Quotation list view  blank if quotation_to field not set as a standard filter
2020-07-12 02:59:00 +05:30
Deepesh Garg
fef3a79bf5 Merge pull request #22656 from sagarvora/fix-ewaybill-json
fix: ewaybill json had json dump of json dump, and other related fixes
2020-07-11 21:41:44 +05:30
Sagar Vora
9bcf4eb5bc fix: ewaybill json had json dump of json dump, and other related fixes 2020-07-11 17:44:20 +05:30
Marica
1696a8982c fix: Pricing Rule breaks if no item_code (#22653) 2020-07-10 22:51:32 +05:30
rohitwaghchaure
65cc0e5200 Merge branch 'version-12-hotfix' into v12-hotfix-get_pricing_rule 2020-07-10 21:46:13 +05:30
Rohit Waghchaure
671fc7b919 fix: incorrect balance qty in stock ledger report 2020-07-10 18:11:04 +05:30
Rohit Waghchaure
335815a75d fix: incorrect qty after transaction in stock ledger entry 2020-07-10 14:23:12 +05:30
rohitwaghchaure
b856548d47 fix: incorrect delivered qty in Supplier-Wise Sales Analytics (#22642)
Co-authored-by: Marica <maricadsouza221197@gmail.com>
2020-07-10 13:19:57 +05:30
rohitwaghchaure
1c26bf5b07 fix: Due to decimal issue make purchase receipt button not showing from PO (#22643)
Co-authored-by: Marica <maricadsouza221197@gmail.com>
2020-07-10 13:17:22 +05:30
Anurag Mishra
b3041ea7cd fix: fix: not working without from_amount and percentage_deduction (#22399) 2020-07-10 13:09:21 +05:30
Marica
ea7625556c fix: General Message in previous doc validation for buying and selling (#22639) 2020-07-10 12:36:47 +05:30
Marica
8e887f39a2 fix: Skip Progress and Completed by fields on Task Duplication (#22640) 2020-07-10 12:31:08 +05:30
Marica
8f038aa832 fix: Error message in Product Bundle (#22638) 2020-07-10 12:13:14 +05:30
Rohan
fda2633e40 fix: fetch project-related info in Timesheet (#22422)
Co-authored-by: Marica <maricadsouza221197@gmail.com>
2020-07-09 11:38:20 +05:30
Rohan
817040b986 fix: setup status indicators for Job Offer and Job Applicant (#22444)
Co-authored-by: Marica <maricadsouza221197@gmail.com>
2020-07-08 15:59:44 +05:30
rohitwaghchaure
45624cae77 Merge pull request #22599 from frappe/shopping-cart-issue
refactor: shopping cart
2020-07-08 13:09:59 +05:30
Anupam K
8c48a6a865 upating shopping_cart.js 2020-07-08 12:22:45 +05:30
Deepesh Garg
adb7c16349 Merge pull request #22604 from frappe/mergify/bp/version-12-hotfix/pr-22601
fix: Payment reco error in multi-company setup (bp #22601)
2020-07-07 18:41:44 +05:30
Marica
aafd674c07 Merge pull request #22606 from Thunderbottom/whitelist-query-v12
fix: whitelist all query functions for search widget
2020-07-07 16:51:45 +05:30
Chinmay D. Pai
75c2e28788 fix: whitelist all query functions for search widget
Signed-off-by: Chinmay D. Pai <chinmaydpai@gmail.com>
2020-07-07 16:46:04 +05:30
Anupam K
321aba642d shopping cart issue fixes 2020-07-07 15:46:44 +05:30
Deepesh Garg
402b273d9b fix: Pass company
(cherry picked from commit ca351e3549)
2020-07-07 10:06:49 +00:00
Deepesh Garg
e0a9ae612e fix: Payment reco error in multicompany setup
(cherry picked from commit e2fdff5777)
2020-07-07 10:06:49 +00:00
bhavesh95863
b9e4df557b fix: Message field mandtory even after unchecking collect progress checkbox (#22594)
Message field mandtory even after unchecking collect progress checkbox
2020-07-06 18:29:37 +05:30
rohitwaghchaure
632bd3b310 Merge pull request #22587 from frappe/mergify/bp/version-12-hotfix/pr-22577
fix: Consider company fiscal year for getting balance (bp #22577)
2020-07-06 13:20:54 +05:30
Deepesh Garg
735d7f732d fix: Consider company fiscal for getting balalnce
(cherry picked from commit 96d40ec9da)
2020-07-06 07:09:00 +00:00
Deepesh Garg
455c1dda7a Merge pull request #22575 from deepeshgarg007/uae_item_tax_fix_v12
fix: Update item tax only if item code available
2020-07-03 21:33:35 +05:30
Deepesh Garg
1b18bf0388 fix: Update item tax only if item code available 2020-07-03 21:28:40 +05:30
Faris Ansari
336ca33a98 fix: Set label if domains is set (#22523) 2020-07-02 14:58:20 +05:30
Afshan
3c0f38fa02 fix: made "Subscription Section", "Auto Repeat" and Hub Publishing" collapsible by default (#22535) 2020-07-02 14:52:50 +05:30
Marica
0c12c7339c Merge pull request #22538 from frappe/mergify/bp/version-12-hotfix/pr-22496
fix: take parent cost center for child if no cost center at child (bp #22496)
2020-07-01 17:00:22 +05:30
Anurag Mishra
bf8a26c31e fix: take parent cost center for child if no cost center at child (#22496)
(cherry picked from commit ba5f571b0d)
2020-07-01 11:07:57 +00:00
Marica
fb36d01dd2 Merge pull request #22534 from frappe/mergify/bp/version-12-hotfix/pr-22512
feat: Autofill Supplier pop-up when only 1 Supplier in RFQ (bp #22512)
2020-07-01 12:09:46 +05:30
Afshan
c8d6e8f19d feat: Autofill Supplier pop-up when only 1 Supplier in RFQ
(cherry picked from commit 06f11aba0b)
2020-07-01 06:32:19 +00:00
mergify[bot]
4e17c40589 fix: Refactor dashboard links in leave policy (bp #22519) (#22529)
* fix: Refactor dashboard links in leave policy (#22519)

* fix: refactor dashboard links in leave policy

* fx: code fix

* fix: add labels to links

* fix: code change

(cherry picked from commit ec84afa86d)

* fix: remove extra lines

Co-authored-by: Michelle Alva <50285544+michellealva@users.noreply.github.com>
Co-authored-by: Rucha Mahabal <ruchamahabal2@gmail.com>
2020-06-30 18:12:47 +05:30
Marica
5d5cb0ac28 fix: Set Root as Parent if no parent in new tree view node (#22507) 2020-06-30 08:21:07 +05:30
mergify[bot]
a20957d355 fix: handle nonetype issue for packed items (#22493) (#22494)
(cherry picked from commit 73edba0e10)

Co-authored-by: Mangesh-Khairnar <mkhairnar10@gmail.com>
2020-06-29 17:36:43 +05:30
rohitwaghchaure
f8efa0508a Merge pull request #22490 from frappe/mergify/bp/version-12-hotfix/pr-22488
fix: letter head not found in opening invoice creation tool (bp #22488)
2020-06-28 21:22:04 +05:30
Rohit Waghchaure
6aa7c404f8 fix: letter head not found in opening invoice creation tool
(cherry picked from commit 04cf2e029f)
2020-06-28 14:36:56 +00:00
rohitwaghchaure
105a44e0d2 Merge pull request #22484 from frappe/mergify/bp/version-12-hotfix/pr-22450
fix: Disable Renaming in Serial No (bp #22450)
2020-06-28 16:29:45 +05:30
rohitwaghchaure
7919ced975 Merge pull request #22372 from rohitwaghchaure/fixed-completed-qty-not-updated-in-wo
fix: completed qty not updated in work order
2020-06-28 15:22:56 +05:30
rohitwaghchaure
848e7c2e0e Merge pull request #22485 from frappe/mergify/bp/version-12-hotfix/pr-22478
fix: apply filters in all transactions (bp #22478)
2020-06-28 15:17:59 +05:30
rohitwaghchaure
104b317929 fix: indentation
(cherry picked from commit d5736711ce)
2020-06-28 09:45:01 +00:00
michellealva
ad0aca2fc6 fix: apply filters in all transactions
(cherry picked from commit 08f842d12e)
2020-06-28 09:45:01 +00:00
marination
584a8f52a5 fix: Disable Renaming in Serial No
(cherry picked from commit f311f52f6e)
2020-06-28 05:48:56 +00:00
rohitwaghchaure
48e2baa903 Merge pull request #22475 from frappe/mergify/bp/version-12-hotfix/pr-22468
fix: enable show_configure_button when shopping cart is enabled (bp #22468)
2020-06-28 11:13:34 +05:30
rohitwaghchaure
43d539f321 Merge pull request #22460 from britlog/version-12-hotfix
fix: product_info
2020-06-28 11:05:55 +05:30
britlog
0e7ab9526c fix: product_info 2020-06-26 15:24:23 +02:00
rohitwaghchaure
8a542bc9df Update shopping_cart_settings.js
(cherry picked from commit 13e8c32172)
2020-06-26 11:54:16 +00:00
Anupam K
e73dec158b enable show_configure_button when shopping cart is enabled
(cherry picked from commit 27d27c924d)
2020-06-26 11:54:16 +00:00
Deepesh Garg
2155916001 Merge pull request #22457 from frappe/clarkejj-patch-2
fix: stock_ageing.py report convert string numeric to flt value
2020-06-26 17:03:56 +05:30
rohitwaghchaure
78383c3133 Merge pull request #22469 from marination/production-plan-ux-hotfix
fix: Handling Empty tables in Production Plan
2020-06-26 15:06:14 +05:30
marination
cfc47bc011 fix: Sales Order to MR test failing
- Items to Manufacture can come as doc.items from Sales Order
2020-06-26 14:06:04 +05:30
marination
6bd8c048b6 fix: Handling Empty tables in Production Plan 2020-06-26 12:53:05 +05:30
mergify[bot]
6089023df7 fix: grammatical fix on error message (#22464)
Before:

Fiscal Year: 2020 does not exists

After:

Fiscal Year 2020 Does Not Exist

(cherry picked from commit 978722621f)

Co-authored-by: Michelle Alva <50285544+michellealva@users.noreply.github.com>
2020-06-26 09:23:36 +05:30
John Clarke
3cb8173034 fix: stock_ageing.py report convert string numeric to flt value
This PR combines these two PRs below applied to develop, to be applied to version-12-hotfix

(The mergifyio process failed for some reason.)

https://github.com/frappe/erpnext/pull/22430

https://github.com/frappe/erpnext/pull/22206
2020-06-25 07:30:10 -06:00
mergify[bot]
d9e7b480eb fix: cannot cancel assets with repair pending (#22440) (#22453)
* fix: cannot cancel assets with repair pending

* fix: message

* Update asset.py

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
(cherry picked from commit 40847aeac3)

Co-authored-by: Saqib <nextchamp.saqib@gmail.com>
2020-06-25 17:11:36 +05:30
Marica
7691937e59 Merge pull request #22437 from sunhoww/patch-2
fix: [v12] UnboundLocalError when setting product_info
2020-06-25 14:23:13 +05:30
Sun Howwrongbum
99a9f98688 fix: UnboundLocalError when setting product_info 2020-06-25 10:05:00 +05:30
Deepesh Garg
7b23cb27ce Merge pull request #22435 from frappe/mergify/bp/version-12-hotfix/pr-22434
fix: change error messages in RFQ (bp #22434)
2020-06-25 09:29:10 +05:30
Michelle Alva
c28adea2d0 fix: change error messages in RFQ
Before:
1. Row {0}: For supplier {0} Email Address is required to send email
2. Email sent to supplier
3. Request for Quotation is disabled to access from portal, for more check portal settings.
4. Supplier Quotation created.


After:
1. Row {0}: For Supplier {0} Email Address is Required to Send Email
2. Email sent to Supplier
3. The Access to Request for Quotation From Portal is Disabled. To Allow Access, Enable it in Portal Settings.
4. Supplier Quotation Created.

(cherry picked from commit da0385cd39)
2020-06-25 03:52:13 +00:00
Marica
57804e9d87 Merge pull request #22427 from frappe/mergify/bp/version-12-hotfix/pr-22410
fix: add error prompt for wrong date range (bp #22410)
2020-06-24 21:32:18 +05:30
Kenneth Sequeira
bf81b42219 fix: add error prompt for wrong date range
(cherry picked from commit f5b7bd9dcb)
2020-06-24 14:06:59 +00:00
gavin
1a3fd763ac Merge pull request #22409 from revant/release-action-on-v12
ci: github release action for v12
2020-06-23 21:33:56 +05:30
Revant Nandgaonkar
0a6b5bc83f ci: github release action for v12 2020-06-23 20:11:35 +05:30
Marica
fb18f78b77 fix: Update Packed Items via Update Items in SO (#22404)
Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2020-06-23 19:19:08 +05:30
mergify[bot]
835b1b4f0d fix: Insert Supplier Group via List View (#22403) (#22407)
(cherry picked from commit 7af7bb8311)

Co-authored-by: Marica <maricadsouza221197@gmail.com>
2020-06-23 19:18:18 +05:30
mergify[bot]
3c18669057 fix: staffing Plan validation (#22379) (#22396)
(cherry picked from commit 36560c8406)

Co-authored-by: Anurag Mishra <32095923+Anurag810@users.noreply.github.com>
2020-06-23 10:49:48 +05:30
mergify[bot]
57a0fa5e87 fix: resetting lost reason in opportunity and quotation (#22378) (#22381)
(cherry picked from commit 71da90034d)

Co-authored-by: Anupam Kumar <anupamvns0099@gmail.com>
2020-06-23 10:45:08 +05:30
rohitwaghchaure
578bdff141 fix: offline pos not working for special character item (#22391) 2020-06-23 10:34:52 +05:30
rohitwaghchaure
c20b962842 Merge pull request #22389 from kennethsequeira/purchase_inv_due_12
fix: status error in purchase invoice
2020-06-22 23:47:32 +05:30
Deepesh Garg
5c4b738833 Merge pull request #22387 from AfshanKhan/V12_ISS_20_21_02455
fix: Set default reference Id for "On Previous Row Amount" and "On Previous Row Total"
2020-06-22 23:09:44 +05:30
Kenneth Sequeira
8a1f2ed65a fix:status error in purchase invoice 2020-06-22 22:40:04 +05:30
Afshan
def13f14a3 style: formate according to Codacy/PR Quality Review 2020-06-22 21:58:27 +05:30
Afshan
7e04dcae0a style: formate according to Codacy/PR Quality Review 2020-06-22 21:58:04 +05:30
Afshan
21a75eb2ba fix: set row_id by default as previous row for On Previous Row Amount and On Previous Row Total 2020-06-22 21:57:34 +05:30
rohitwaghchaure
290dbf470a Merge pull request #22384 from rohitwaghchaure/fixed-subcontract-item-for-alternative-item
fix: alternative item not working for subcontract
2020-06-22 21:52:26 +05:30
Rohit Waghchaure
171699537c fix: alternative item not working for subcontract 2020-06-22 20:48:28 +05:30
Deepesh Garg
91346d5e9e Merge pull request #22340 from frappe/mergify/bp/version-12-hotfix/pr-22312
fix: Email digest html view fix (bp #22312)
2020-06-22 19:08:56 +05:30
Marica
06ca3b5112 Purchase receipt to invoice hotfix (#22146)
* fix: Handle rows with same item code from Purchase Receipt to Invoice.

* fix: Handle rows with same item code from Purchase Receipt to Invoice.

* fix: Added patch, fixed tests, fixed delivery note behaviour

* chore: Added comments amd fixed typo

* fix: Added patch to patches.txt

* fix: Patch fix and simplification, json timestamp updation.

* fix: Set Purchase Receipt and Delivery Note detail patch (#21607)

* fix: Set Purchase Receipt and Delievry Note detail patch

* fix: Reload purchase receipt item

* fix(set_purchase_receipt_delivery_note_detail): commit after every 100 sql updates (#22016)

Co-authored-by: Deepesh Garg <42651287+deepeshgarg007@users.noreply.github.com>
Co-authored-by: sahil28297 <37302950+sahil28297@users.noreply.github.com>
Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2020-06-22 18:04:48 +05:30
Kenneth Sequeira
e220be5415 fix: Batch No label in Purchase Receipt (#22360) 2020-06-22 17:33:04 +05:30
mergify[bot]
413c2b229a fix: 'Last Purchase Rate' taking wrong on BOM (#20689) (#22370)
* fix: 'Last Purchase Rate' taking wrong on BOM. #20228

* fix: Added condition for None purchase order and purchase receipt (#20689)

* fix: fetch last purchase rate

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
(cherry picked from commit 2866617c82)

Co-authored-by: Lokesh Waingankar <59611773+lokesh-indictrans@users.noreply.github.com>
2020-06-22 17:26:42 +05:30
Anurag Mishra
1039079e37 fix: set cost center in child table (#22373) 2020-06-22 17:25:53 +05:30
Poranut Chollavorn
303639db76 fix: use name instead of title 2020-06-22 10:24:40 +00:00
rohitwaghchaure
60cb5ac419 Merge pull request #22330 from pipech/v12-hotfix-clear_pricing_rule_value
fix(pricing_rule): apply_on logic dont get cleanup
2020-06-22 14:47:29 +05:30
Rohit Waghchaure
ebbbc85fc0 added validation and clear fields for Apply Rule On Other 2020-06-22 13:44:11 +05:30
rohitwaghchaure
7f6d36cdc9 Merge pull request #22369 from frappe/mergify/bp/version-12-hotfix/pr-22241
fix: Minor fixes in cost center (bp #22241)
2020-06-22 13:00:19 +05:30
Poranut Chollavorn
850c0ff121 fix(pricing_rule): key error on apply_internal_priority
apply_internal_priority never check if pricing rule have field
2020-06-22 07:24:33 +00:00
Marica
4a9de4dc07 Merge branch 'version-12-hotfix' into v12-hotfix-clear_pricing_rule_value 2020-06-22 12:48:55 +05:30
Marica
cb555ae825 Merge pull request #22368 from frappe/mergify/bp/version-12-hotfix/pr-21582
feat: Enabled translation on html files in LMS [Proposal] (bp #21582)
2020-06-22 12:45:18 +05:30
Rohit Waghchaure
e5ffe3fea4 fix: completed qty not updated in work order 2020-06-22 12:36:23 +05:30
Marica
7fcf958d08 Merge branch 'version-12-hotfix' into mergify/bp/version-12-hotfix/pr-21582 2020-06-22 12:07:39 +05:30
Deepesh Garg
cfe9ed0dfa fix: Test
(cherry picked from commit bef80b7981)
2020-06-22 05:54:53 +00:00
Deepesh Garg
f2fe8053dc fix: Validation for group cost center
(cherry picked from commit 0d880079b1)
2020-06-22 05:54:53 +00:00
Deepesh Garg
aa22cca67a fix: Minor fixes in cost center
(cherry picked from commit 817cbc4b48)
2020-06-22 05:54:52 +00:00
rohitwaghchaure
c4893df048 Merge pull request #22088 from deepeshgarg007/rcm_version-12-hotfix
fix(India): Reverse charge mechanism for GST
2020-06-22 11:20:38 +05:30
Alvaro
b16b24fd10 feat: Enabled translation on html files in LMS [Proposal] (#21582)
* :fix:  translation fix for html files in LMS

* fix: typo in translation

* Update content.html

* Update content.html

* Update profile.html

Co-authored-by: Shivam Mishra <scmmishra@users.noreply.github.com>
Co-authored-by: Marica <maricadsouza221197@gmail.com>
(cherry picked from commit 43be163b32)
2020-06-22 05:39:42 +00:00
Deepesh Garg
2f2385b354 Merge pull request #22365 from frappe/mergify/bp/version-12-hotfix/pr-22350
fix: Skipping total row for tree-view reports (bp #22350)
2020-06-21 22:11:32 +05:30
Afshan
8a2a32820a fix: adding json for checked add total row
(cherry picked from commit 84c6973742)
2020-06-21 13:59:25 +00:00
Afshan
41462f3c36 fix: test case
(cherry picked from commit 3fbe6e9e4b)
2020-06-21 13:59:25 +00:00
Afshan
a9ff40db67 fix: Skipping*
(cherry picked from commit 65f00cea15)
2020-06-21 13:59:24 +00:00
Afshan
0d95f56474 Skiping total row for tree-view reports
(cherry picked from commit fbd66574ad)
2020-06-21 13:59:24 +00:00
rohitwaghchaure
da65ddc68a Merge pull request #22362 from rohitwaghchaure/fixed-popup-is-coming-for-non-serialized-items
fix: Serial no / batch no Popup is coming for the non serialized items
2020-06-20 20:54:55 +05:30
Rohit Waghchaure
368f5e29d2 fix: Serial no / batch no Popup is coming for the non serialized items 2020-06-20 20:48:28 +05:30
Deepesh Garg
92f97b6a68 Merge pull request #22347 from frappe/revert-21743-payment-remark-fix-v12
Revert "fix: update remark on submitting payment entry"
2020-06-19 17:29:20 +05:30
Deepesh Garg
7d035fac36 Revert "fix: update remark on submitting payment entry" 2020-06-19 17:28:58 +05:30
Marica
6c1a5e8a44 Merge branch 'version-12-hotfix' into v12-hotfix-clear_pricing_rule_value 2020-06-19 14:28:06 +05:30
rohitwaghchaure
995bdd3c48 Merge pull request #22250 from marination/rfq-multi-uom-hotfix
feat: Multi UOM support in Request for Quotation
2020-06-19 13:17:36 +05:30
mergify[bot]
5acc06dfe6 fix: Student Admission (#22280)
* Student Admission fix

* adding check for application

* adding check for application

* updating error message

* added date_diff for date comparision

(cherry picked from commit c6592c880a)

Co-authored-by: Anupam Kumar <anupamvns0099@gmail.com>
Co-authored-by: Anurag Mishra <32095923+Anurag810@users.noreply.github.com>
2020-06-19 11:58:51 +05:30
Anupam K
168d070d73 email digest html fix
(cherry picked from commit bd449c8d07)
2020-06-19 06:09:49 +00:00
mergify[bot]
6f3e5e1891 refactor: show service instead of services (#22339)
(cherry picked from commit 25702a1c55)

Co-authored-by: Shivam Mishra <scm.mymail@gmail.com>
2020-06-19 11:10:42 +05:30
rohitwaghchaure
a3e92489c2 Merge pull request #22337 from frappe/mergify/bp/version-12-hotfix/pr-22334
fix: Customer Group label in Item-wise Sales History report (bp #22334)
2020-06-19 11:00:17 +05:30
rohitwaghchaure
dd8dcd29c3 Merge pull request #22332 from marination/item-edit-hotfix
fix: Unabled to create batched item
2020-06-19 10:57:25 +05:30
Kenneth Sequeira
10624f3fa6 fix: Customer Group label in Itemwise Sales report
(cherry picked from commit 766f978858)
2020-06-19 05:26:23 +00:00
Marica
a0aa16c68c Merge branch 'version-12-hotfix' into item-edit-hotfix 2020-06-18 22:02:32 +05:30
marination
67361bef73 fix: Unabled to create batched item 2020-06-18 21:47:36 +05:30
Poranut Chollavorn
acf399c4e0 fix(pricing_rule): apply_on logic dont get cleanup 2020-06-18 14:41:26 +00:00
Marica
cce1116b4e fix: Quality procedure fixes (#22287)
* fix: Quality Procedure Fixes

- Dont prompt error message if parent is the same in child
- filter child procedure field
- Disable New button in tree view
- Editable grid for Quality Procedure Proces table.

* chore: Remove unnecessary get_doc

* fix: Codacy

Co-authored-by: Anurag Mishra <32095923+Anurag810@users.noreply.github.com>
2020-06-18 19:15:49 +05:30
Poranut Chollavorn
66806ff1b0 fix(pricing_rules): rule won't got use across [item_code, item_group, brands] 2020-06-18 13:43:15 +00:00
mergify[bot]
531ef15e30 refactor: handle exceptions when updating addresses (#22307) (#22315)
* refactor: handle exceptions when updating addresses

* refactor: fold common statements in a loop

(cherry picked from commit 34d2bfbb3e)

Co-authored-by: Shivam Mishra <scmmishra@users.noreply.github.com>
2020-06-18 17:04:36 +05:30
Deepesh Garg
6dc6da1ce2 Merge pull request #22324 from deepeshgarg007/item_tax_map_v12
fix: Do not copy Item Tax template from SO to PO
2020-06-18 17:02:56 +05:30
Deepesh Garg
f9dbcef5c9 fix: Do not copy Item Tax template from SO to PO 2020-06-18 17:01:32 +05:30
mergify[bot]
1ca4370033 fix: asset maintenance fixes (#21277) (#22294)
* fix: asset maintenance fixes

* fix: tests

(cherry picked from commit 9c494d3e72)

Co-authored-by: Saqib <nextchamp.saqib@gmail.com>
2020-06-18 15:39:13 +05:30
mergify[bot]
0c08324fab chore: add standard queries hooks to whitelist (#21939) (#22305)
standard queries are used within the search widget, and now require to
be whitelisted before they can be executed through the search widget.

Signed-off-by: Chinmay D. Pai <chinmaydpai@gmail.com>

Co-authored-by: sahil28297 <37302950+sahil28297@users.noreply.github.com>
(cherry picked from commit 96100e9507)

Co-authored-by: Chinmay Pai <chinmaydpai@gmail.com>
2020-06-18 15:29:46 +05:30
Marica
c6886e28f2 Merge branch 'version-12-hotfix' into rfq-multi-uom-hotfix 2020-06-18 14:42:27 +05:30
marination
b865d58b81 fix: Patch simplification
- Also, apply patch to all docs
2020-06-18 14:43:31 +05:30
Kenneth Sequeira
af6a0f3a9d fix(HR): typo in error message in Employee Balance Report (#22306)
* fix: typo in date error message

* fix: error message cleanup in Leave Balance report
2020-06-18 14:34:11 +05:30
rohitwaghchaure
f635a1739e Merge pull request #22308 from rohitwaghchaure/fixed-incorrect-variable-used
fix: incorrect variable used while adding new item in the submitted Sales Order
2020-06-18 14:00:51 +05:30
Rohit Waghchaure
c75236579f fix: incorrect variable used while adding items in the submitted sales order 2020-06-18 13:59:23 +05:30
mergify[bot]
5d042ad496 fix: update shopify api version (#22284) (#22299)
Co-authored-by: Saurabh <saurabh@erpnext.com>
(cherry picked from commit 53b601523b)

Co-authored-by: Mangesh-Khairnar <mkhairnar10@gmail.com>
2020-06-18 09:47:15 +05:30
mergify[bot]
59938a46eb fix: typo for language in Terms description (#22270) (#22272)
(cherry picked from commit c159556c24)

Co-authored-by: Kenneth Sequeira <33246109+kennethsequeira@users.noreply.github.com>
2020-06-18 09:46:03 +05:30
P-Froggy
1284b9b17d fix: Set Value of wrong Bank Account Field in Payment Entry
Company bank account was wrongly inserted into the field "Party Bank Account" in payment entry, instead of "Bank Account".
Adds filters for "Party Bank Account" based on selected Party (I forgot to create a PR for version-12 back in February, see commit #393a626).
Also changes the label of "Default Bank Account" to "Default Company Bank Account", like suggested in PR #20632

#### Please Note
This is kind of a revert of PR #19390. However, it seems like the function "get_party_bank_account" in Bank Account doctype changed how it worked since it is clearly pulling the default company bank account.
2020-06-18 02:11:15 +02:00
Marica
1345bc2f82 Merge pull request #22291 from marination/variant-error-msg-hotfix
fix: Typo in Item Variant error message
2020-06-17 19:23:42 +05:30
marination
e67195b0b9 fix: Typo 2020-06-17 19:06:56 +05:30
Deepesh Garg
e4eb353065 Merge branch 'version-12-hotfix' into rcm_version-12-hotfix 2020-06-17 15:33:45 +05:30
Marica
41dadba990 Merge pull request #22281 from marination/expense-account-message
fix: Message Formatting for missing Expense Account
2020-06-17 13:51:09 +05:30
marination
17ec1d6b28 fix: Message Formatting 2020-06-17 13:46:21 +05:30
rohitwaghchaure
fd3ff6be18 refactor: hide company currency fields in the routing (#22267) 2020-06-17 09:37:41 +05:30
rohitwaghchaure
03f688acd9 fix: pos, serial no popup comin two times (#22268) 2020-06-17 09:36:23 +05:30
rohitwaghchaure
fd5c577b40 Merge pull request #22248 from rohitwaghchaure/fixed-version-12-hotfix-travis
fix: v12 travis
2020-06-16 09:55:26 +05:30
Rohit Waghchaure
e4834d2a37 fix: travis 2020-06-15 22:24:56 +05:30
marination
1e76bdcc3c feat: Multi UOM support in Request for Quotation 2020-06-15 17:53:47 +05:30
Deepesh Garg
e4cd23746b fix: Consider Overseas category in RCM 2020-06-14 13:20:09 +05:30
Deepesh Garg
c417cf079c fix(India): Reverse charge mechanism for GST 2020-06-03 11:31:26 +05:30
359 changed files with 8615 additions and 6558 deletions

14
.github/workflows/docker-release.yml vendored Normal file
View File

@@ -0,0 +1,14 @@
name: Trigger Docker build on release
on:
release:
types: [released]
jobs:
curl:
runs-on: ubuntu-latest
container:
image: alpine:latest
steps:
- name: curl
run: |
apk add curl bash
curl -s -X POST -H "Content-Type: application/json" -H "Accept: application/json" -H "Travis-API-Version: 3" -H "Authorization: token ${{ secrets.TRAVIS_CI_TOKEN }}" -d '{"request":{"branch":"master"}}' https://api.travis-ci.com/repo/frappe%2Ffrappe_docker/requests

0
FETCH_HEAD Normal file
View File

View File

@@ -5,7 +5,7 @@ import frappe
from erpnext.hooks import regional_overrides
from frappe.utils import getdate
__version__ = '12.10.1'
__version__ = '12.15.0'
def get_default_company(user=None):
'''Get default company for user'''

View File

@@ -6,8 +6,8 @@ import frappe, json
from frappe import _
from frappe.utils import add_to_date, date_diff, getdate, nowdate, get_last_day, formatdate, get_link_to_form
from erpnext.accounts.report.general_ledger.general_ledger import execute
from frappe.core.page.dashboard.dashboard import cache_source, get_from_date_from_timespan
from frappe.desk.doctype.dashboard_chart.dashboard_chart import get_period_ending
from frappe.core.page.dashboard.dashboard import cache_source
from frappe.utils.dateutils import get_from_date_from_timespan, get_period_ending
from frappe.utils.nestedset import get_descendants_of

View File

@@ -244,6 +244,8 @@ class Account(NestedSet):
super(Account, self).on_trash(True)
@frappe.whitelist()
@frappe.validate_and_sanitize_search_inputs
def get_parent_account(doctype, txt, searchfield, start, page_len, filters):
return frappe.db.sql("""select name from tabAccount
where is_group = 1 and docstatus != 2 and company = %s

View File

@@ -225,7 +225,7 @@ def build_tree_from_json(chart_template, chart_data=None):
account['parent_account'] = parent
account['expandable'] = True if identify_is_group(child) else False
account['value'] = (child.get('account_number') + ' - ' + account_name) \
account['value'] = (cstr(child.get('account_number')).strip() + ' - ' + account_name) \
if child.get('account_number') else account_name
accounts.append(account)
_import_accounts(child, account['value'])

View File

@@ -1,210 +1,210 @@
{
"creation": "2013-06-24 15:49:57",
"description": "Settings for Accounts",
"doctype": "DocType",
"document_type": "Other",
"editable_grid": 1,
"engine": "InnoDB",
"field_order": [
"auto_accounting_for_stock",
"acc_frozen_upto",
"frozen_accounts_modifier",
"determine_address_tax_category_from",
"over_billing_allowance",
"column_break_4",
"credit_controller",
"check_supplier_invoice_uniqueness",
"make_payment_via_journal_entry",
"unlink_payment_on_cancellation_of_invoice",
"unlink_advance_payment_on_cancelation_of_order",
"book_asset_depreciation_entry_automatically",
"allow_cost_center_in_entry_of_bs_account",
"add_taxes_from_item_tax_template",
"automatically_fetch_payment_terms",
"print_settings",
"show_inclusive_tax_in_print",
"column_break_12",
"show_payment_schedule_in_print",
"currency_exchange_section",
"allow_stale",
"stale_days",
"report_settings_sb",
"use_custom_cash_flow"
],
"fields": [
{
"default": "1",
"description": "If enabled, the system will post accounting entries for inventory automatically.",
"fieldname": "auto_accounting_for_stock",
"fieldtype": "Check",
"hidden": 1,
"in_list_view": 1,
"label": "Make Accounting Entry For Every Stock Movement"
},
{
"description": "Accounting entry frozen up to this date, nobody can do / modify entry except role specified below.",
"fieldname": "acc_frozen_upto",
"fieldtype": "Date",
"in_list_view": 1,
"label": "Accounts Frozen Upto"
},
{
"description": "Users with this role are allowed to set frozen accounts and create / modify accounting entries against frozen accounts",
"fieldname": "frozen_accounts_modifier",
"fieldtype": "Link",
"in_list_view": 1,
"label": "Role Allowed to Set Frozen Accounts & Edit Frozen Entries",
"options": "Role"
},
{
"default": "Billing Address",
"description": "Address used to determine Tax Category in transactions.",
"fieldname": "determine_address_tax_category_from",
"fieldtype": "Select",
"label": "Determine Address Tax Category From",
"options": "Billing Address\nShipping Address"
},
{
"fieldname": "column_break_4",
"fieldtype": "Column Break"
},
{
"description": "Role that is allowed to submit transactions that exceed credit limits set.",
"fieldname": "credit_controller",
"fieldtype": "Link",
"in_list_view": 1,
"label": "Credit Controller",
"options": "Role"
},
{
"fieldname": "check_supplier_invoice_uniqueness",
"fieldtype": "Check",
"label": "Check Supplier Invoice Number Uniqueness"
},
{
"fieldname": "make_payment_via_journal_entry",
"fieldtype": "Check",
"label": "Make Payment via Journal Entry"
},
{
"default": "1",
"fieldname": "unlink_payment_on_cancellation_of_invoice",
"fieldtype": "Check",
"label": "Unlink Payment on Cancellation of Invoice"
},
{
"default": "1",
"fieldname": "unlink_advance_payment_on_cancelation_of_order",
"fieldtype": "Check",
"label": "Unlink Advance Payment on Cancelation of Order"
},
{
"default": "1",
"fieldname": "book_asset_depreciation_entry_automatically",
"fieldtype": "Check",
"label": "Book Asset Depreciation Entry Automatically"
},
{
"fieldname": "allow_cost_center_in_entry_of_bs_account",
"fieldtype": "Check",
"label": "Allow Cost Center In Entry of Balance Sheet Account"
},
{
"default": "1",
"fieldname": "add_taxes_from_item_tax_template",
"fieldtype": "Check",
"label": "Automatically Add Taxes and Charges from Item Tax Template"
},
{
"fieldname": "print_settings",
"fieldtype": "Section Break",
"label": "Print Settings"
},
{
"fieldname": "show_inclusive_tax_in_print",
"fieldtype": "Check",
"label": "Show Inclusive Tax In Print"
},
{
"fieldname": "column_break_12",
"fieldtype": "Column Break"
},
{
"fieldname": "show_payment_schedule_in_print",
"fieldtype": "Check",
"label": "Show Payment Schedule in Print"
},
{
"fieldname": "currency_exchange_section",
"fieldtype": "Section Break",
"label": "Currency Exchange Settings"
},
{
"default": "1",
"fieldname": "allow_stale",
"fieldtype": "Check",
"in_list_view": 1,
"label": "Allow Stale Exchange Rates"
},
{
"default": "1",
"depends_on": "eval:doc.allow_stale==0",
"fieldname": "stale_days",
"fieldtype": "Int",
"label": "Stale Days"
},
{
"fieldname": "report_settings_sb",
"fieldtype": "Section Break",
"label": "Report Settings"
},
{
"default": "0",
"description": "Only select if you have setup Cash Flow Mapper documents",
"fieldname": "use_custom_cash_flow",
"fieldtype": "Check",
"label": "Use Custom Cash Flow Format"
},
{
"fieldname": "automatically_fetch_payment_terms",
"fieldtype": "Check",
"label": "Automatically Fetch Payment Terms"
},
{
"description": "Percentage you are allowed to bill more against the amount ordered. For example: If the order value is $100 for an item and tolerance is set as 10% then you are allowed to bill for $110.",
"fieldname": "over_billing_allowance",
"fieldtype": "Currency",
"label": "Over Billing Allowance (%)"
}
],
"icon": "icon-cog",
"idx": 1,
"issingle": 1,
"modified": "2019-07-04 18:20:55.789946",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Accounts Settings",
"owner": "Administrator",
"permissions": [
{
"create": 1,
"email": 1,
"print": 1,
"read": 1,
"role": "Accounts Manager",
"share": 1,
"write": 1
},
{
"read": 1,
"role": "Sales User"
},
{
"read": 1,
"role": "Purchase User"
}
],
"quick_entry": 1,
"sort_order": "ASC",
"track_changes": 1
"creation": "2013-06-24 15:49:57",
"description": "Settings for Accounts",
"doctype": "DocType",
"document_type": "Other",
"editable_grid": 1,
"engine": "InnoDB",
"field_order": [
"auto_accounting_for_stock",
"acc_frozen_upto",
"frozen_accounts_modifier",
"determine_address_tax_category_from",
"over_billing_allowance",
"column_break_4",
"credit_controller",
"check_supplier_invoice_uniqueness",
"make_payment_via_journal_entry",
"unlink_payment_on_cancellation_of_invoice",
"unlink_advance_payment_on_cancelation_of_order",
"book_asset_depreciation_entry_automatically",
"add_taxes_from_item_tax_template",
"automatically_fetch_payment_terms",
"print_settings",
"show_inclusive_tax_in_print",
"column_break_12",
"show_payment_schedule_in_print",
"currency_exchange_section",
"allow_stale",
"stale_days",
"report_settings_sb",
"use_custom_cash_flow"
],
"fields": [
{
"default": "1",
"description": "If enabled, the system will post accounting entries for inventory automatically.",
"fieldname": "auto_accounting_for_stock",
"fieldtype": "Check",
"hidden": 1,
"in_list_view": 1,
"label": "Make Accounting Entry For Every Stock Movement"
},
{
"description": "Accounting entry frozen up to this date, nobody can do / modify entry except role specified below.",
"fieldname": "acc_frozen_upto",
"fieldtype": "Date",
"in_list_view": 1,
"label": "Accounts Frozen Upto"
},
{
"description": "Users with this role are allowed to set frozen accounts and create / modify accounting entries against frozen accounts",
"fieldname": "frozen_accounts_modifier",
"fieldtype": "Link",
"in_list_view": 1,
"label": "Role Allowed to Set Frozen Accounts & Edit Frozen Entries",
"options": "Role"
},
{
"default": "Billing Address",
"description": "Address used to determine Tax Category in transactions.",
"fieldname": "determine_address_tax_category_from",
"fieldtype": "Select",
"label": "Determine Address Tax Category From",
"options": "Billing Address\nShipping Address"
},
{
"fieldname": "column_break_4",
"fieldtype": "Column Break"
},
{
"description": "Role that is allowed to submit transactions that exceed credit limits set.",
"fieldname": "credit_controller",
"fieldtype": "Link",
"in_list_view": 1,
"label": "Credit Controller",
"options": "Role"
},
{
"default": "0",
"fieldname": "check_supplier_invoice_uniqueness",
"fieldtype": "Check",
"label": "Check Supplier Invoice Number Uniqueness"
},
{
"default": "0",
"fieldname": "make_payment_via_journal_entry",
"fieldtype": "Check",
"label": "Make Payment via Journal Entry"
},
{
"default": "1",
"fieldname": "unlink_payment_on_cancellation_of_invoice",
"fieldtype": "Check",
"label": "Unlink Payment on Cancellation of Invoice"
},
{
"default": "1",
"fieldname": "unlink_advance_payment_on_cancelation_of_order",
"fieldtype": "Check",
"label": "Unlink Advance Payment on Cancellation of Order"
},
{
"default": "1",
"fieldname": "book_asset_depreciation_entry_automatically",
"fieldtype": "Check",
"label": "Book Asset Depreciation Entry Automatically"
},
{
"default": "1",
"fieldname": "add_taxes_from_item_tax_template",
"fieldtype": "Check",
"label": "Automatically Add Taxes and Charges from Item Tax Template"
},
{
"fieldname": "print_settings",
"fieldtype": "Section Break",
"label": "Print Settings"
},
{
"default": "0",
"fieldname": "show_inclusive_tax_in_print",
"fieldtype": "Check",
"label": "Show Inclusive Tax In Print"
},
{
"fieldname": "column_break_12",
"fieldtype": "Column Break"
},
{
"default": "0",
"fieldname": "show_payment_schedule_in_print",
"fieldtype": "Check",
"label": "Show Payment Schedule in Print"
},
{
"fieldname": "currency_exchange_section",
"fieldtype": "Section Break",
"label": "Currency Exchange Settings"
},
{
"default": "1",
"fieldname": "allow_stale",
"fieldtype": "Check",
"in_list_view": 1,
"label": "Allow Stale Exchange Rates"
},
{
"default": "1",
"depends_on": "eval:doc.allow_stale==0",
"fieldname": "stale_days",
"fieldtype": "Int",
"label": "Stale Days"
},
{
"fieldname": "report_settings_sb",
"fieldtype": "Section Break",
"label": "Report Settings"
},
{
"default": "0",
"description": "Only select if you have setup Cash Flow Mapper documents",
"fieldname": "use_custom_cash_flow",
"fieldtype": "Check",
"label": "Use Custom Cash Flow Format"
},
{
"default": "0",
"fieldname": "automatically_fetch_payment_terms",
"fieldtype": "Check",
"label": "Automatically Fetch Payment Terms"
},
{
"description": "Percentage you are allowed to bill more against the amount ordered. For example: If the order value is $100 for an item and tolerance is set as 10% then you are allowed to bill for $110.",
"fieldname": "over_billing_allowance",
"fieldtype": "Currency",
"label": "Over Billing Allowance (%)"
}
],
"icon": "icon-cog",
"idx": 1,
"issingle": 1,
"modified": "2020-10-08 09:40:12.121145",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Accounts Settings",
"owner": "Administrator",
"permissions": [
{
"create": 1,
"email": 1,
"print": 1,
"read": 1,
"role": "Accounts Manager",
"share": 1,
"write": 1
},
{
"read": 1,
"role": "Sales User"
},
{
"read": 1,
"role": "Purchase User"
}
],
"quick_entry": 1,
"sort_field": "modified",
"sort_order": "ASC",
"track_changes": 1
}

View File

@@ -20,7 +20,6 @@ class AccountsSettings(Document):
self.validate_stale_days()
self.enable_payment_schedule_in_print()
self.enable_fields_for_cost_center_settings()
def validate_stale_days(self):
if not self.allow_stale and cint(self.stale_days) <= 0:
@@ -33,8 +32,3 @@ class AccountsSettings(Document):
for doctype in ("Sales Order", "Sales Invoice", "Purchase Order", "Purchase Invoice"):
make_property_setter(doctype, "due_date", "print_hide", show_in_print, "Check")
make_property_setter(doctype, "payment_schedule", "print_hide", 0 if show_in_print else 1, "Check")
def enable_fields_for_cost_center_settings(self):
show_field = 0 if cint(self.allow_cost_center_in_entry_of_bs_account) else 1
for doctype in ("Sales Invoice", "Purchase Invoice", "Payment Entry"):
make_property_setter(doctype, "cost_center", "hidden", show_field, "Check")

View File

@@ -1,5 +1,6 @@
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
// For license information, please see license.txt
frappe.provide('erpnext.integrations');
frappe.ui.form.on('Bank', {
onload: function(frm) {
@@ -7,6 +8,12 @@ frappe.ui.form.on('Bank', {
},
refresh: function(frm) {
add_fields_to_mapping_table(frm);
if (frm.doc.plaid_access_token) {
frm.add_custom_button(__('Refresh Plaid Link'), () => {
new erpnext.integrations.refreshPlaidLink(frm.doc.plaid_access_token);
});
}
}
});
@@ -27,4 +34,80 @@ let add_fields_to_mapping_table = function (frm) {
frm.doc.name).options = options;
frm.fields_dict.bank_transaction_mapping.grid.refresh();
};
};
erpnext.integrations.refreshPlaidLink = class refreshPlaidLink {
constructor(access_token) {
this.access_token = access_token;
this.plaidUrl = 'https://cdn.plaid.com/link/v2/stable/link-initialize.js';
this.init_config();
}
async init_config() {
this.plaid_env = await frappe.db.get_single_value('Plaid Settings', 'plaid_env');
this.token = await this.get_link_token_for_update();
this.init_plaid();
}
async get_link_token_for_update() {
const token = frappe.xcall(
'erpnext.erpnext_integrations.doctype.plaid_settings.plaid_settings.get_link_token_for_update',
{ access_token: this.access_token }
)
if (!token) {
frappe.throw(__('Cannot retrieve link token for update. Check Error Log for more information'));
}
return token;
}
init_plaid() {
const me = this;
me.loadScript(me.plaidUrl)
.then(() => {
me.onScriptLoaded(me);
})
.then(() => {
if (me.linkHandler) {
me.linkHandler.open();
}
})
.catch((error) => {
me.onScriptError(error);
});
}
loadScript(src) {
return new Promise(function (resolve, reject) {
if (document.querySelector("script[src='" + src + "']")) {
resolve();
return;
}
const el = document.createElement('script');
el.type = 'text/javascript';
el.async = true;
el.src = src;
el.addEventListener('load', resolve);
el.addEventListener('error', reject);
el.addEventListener('abort', reject);
document.head.appendChild(el);
});
}
onScriptLoaded(me) {
me.linkHandler = Plaid.create({
env: me.plaid_env,
token: me.token,
onSuccess: me.plaid_success
});
}
onScriptError(error) {
frappe.msgprint(__("There was an issue connecting to Plaid's authentication server. Check browser console for more information"));
console.log(error);
}
plaid_success(token, response) {
frappe.show_alert({ message: __('Plaid Link Updated'), indicator: 'green' });
}
};

View File

@@ -27,4 +27,4 @@ def get_vouchar_detials(column_list, doctype, docname):
for col in column_list:
sanitize_searchfield(col)
return frappe.db.sql(''' select {columns} from `tab{doctype}` where name=%s'''
.format(columns=", ".join(json.loads(column_list)), doctype=doctype), docname, as_dict=1)[0]
.format(columns=", ".join(column_list), doctype=doctype), docname, as_dict=1)[0]

View File

@@ -60,12 +60,13 @@ class BankReconciliation(Document):
""".format(condition=condition), {"account": self.account, "from":self.from_date,
"to": self.to_date, "bank_account": self.bank_account}, as_dict=1)
pos_entries = []
pos_sales_invoices, pos_purchase_invoices = [], []
if self.include_pos_transactions:
pos_entries = frappe.db.sql("""
pos_sales_invoices = frappe.db.sql("""
select
"Sales Invoice Payment" as payment_document, sip.name as payment_entry, sip.amount as debit,
si.posting_date, si.debit_to as against_account, sip.clearance_date,
si.posting_date, si.customer as against_account, sip.clearance_date,
account.account_currency, 0 as credit
from `tabSales Invoice Payment` sip, `tabSales Invoice` si, `tabAccount` account
where
@@ -75,7 +76,20 @@ class BankReconciliation(Document):
si.posting_date ASC, si.name DESC
""", {"account":self.account, "from":self.from_date, "to":self.to_date}, as_dict=1)
entries = sorted(list(payment_entries)+list(journal_entries+list(pos_entries)),
pos_purchase_invoices = frappe.db.sql("""
select
"Purchase Invoice" as payment_document, pi.name as payment_entry, pi.paid_amount as credit,
pi.posting_date, pi.supplier as against_account, pi.clearance_date,
account.account_currency, 0 as debit
from `tabPurchase Invoice` pi, `tabAccount` account
where
pi.cash_bank_account=%(account)s and pi.docstatus=1 and account.name = pi.cash_bank_account
and pi.posting_date >= %(from)s and pi.posting_date <= %(to)s
order by
pi.posting_date ASC, pi.name DESC
""", {"account": self.account, "from": self.from_date, "to": self.to_date}, as_dict=1)
entries = sorted(list(payment_entries) + list(journal_entries + list(pos_sales_invoices) + list(pos_purchase_invoices)),
key=lambda k: k['posting_date'] or getdate(nowdate()))
self.set('payment_entries', [])

View File

@@ -55,7 +55,7 @@ class BankStatementTransactionEntry(Document):
def populate_payment_entries(self):
if self.bank_statement is None: return
filename = self.bank_statement.split("/")[-1]
file_url = self.bank_statement
if (len(self.new_transaction_items + self.reconciled_transaction_items) > 0):
frappe.throw(_("Transactions already retreived from the statement"))
@@ -65,7 +65,7 @@ class BankStatementTransactionEntry(Document):
if self.bank_settings:
mapped_items = frappe.get_doc("Bank Statement Settings", self.bank_settings).mapped_items
statement_headers = self.get_statement_headers()
transactions = get_transaction_entries(filename, statement_headers)
transactions = get_transaction_entries(file_url, statement_headers)
for entry in transactions:
date = entry[statement_headers["Date"]].strip()
#print("Processing entry DESC:{0}-W:{1}-D:{2}-DT:{3}".format(entry["Particulars"], entry["Withdrawals"], entry["Deposits"], entry["Date"]))
@@ -398,20 +398,21 @@ def get_transaction_info(headers, header_index, row):
transaction[header] = ""
return transaction
def get_transaction_entries(filename, headers):
def get_transaction_entries(file_url, headers):
header_index = {}
rows, transactions = [], []
if (filename.lower().endswith("xlsx")):
if (file_url.lower().endswith("xlsx")):
from frappe.utils.xlsxutils import read_xlsx_file_from_attached_file
rows = read_xlsx_file_from_attached_file(file_id=filename)
elif (filename.lower().endswith("csv")):
rows = read_xlsx_file_from_attached_file(file_url=file_url)
elif (file_url.lower().endswith("csv")):
from frappe.utils.csvutils import read_csv_content
_file = frappe.get_doc("File", {"file_name": filename})
_file = frappe.get_doc("File", {"file_url": file_url})
filepath = _file.get_full_path()
with open(filepath,'rb') as csvfile:
rows = read_csv_content(csvfile.read())
elif (filename.lower().endswith("xls")):
elif (file_url.lower().endswith("xls")):
filename = file_url.split("/")[-1]
rows = get_rows_from_xls_file(filename)
else:
frappe.throw(_("Only .csv and .xlsx files are supported currently"))

View File

@@ -9,11 +9,13 @@ from erpnext.accounts.doctype.sales_invoice.test_sales_invoice import create_sal
from erpnext.accounts.doctype.purchase_invoice.test_purchase_invoice import make_purchase_invoice
from erpnext.accounts.doctype.payment_entry.test_payment_entry import get_payment_entry
from erpnext.accounts.page.bank_reconciliation.bank_reconciliation import reconcile, get_linked_payments
from erpnext.accounts.doctype.pos_profile.test_pos_profile import make_pos_profile
test_dependencies = ["Item", "Cost Center"]
class TestBankTransaction(unittest.TestCase):
def setUp(self):
make_pos_profile()
add_transactions()
add_payments()
@@ -27,6 +29,9 @@ class TestBankTransaction(unittest.TestCase):
frappe.db.sql("""delete from `tabPayment Entry Reference`""")
frappe.db.sql("""delete from `tabPayment Entry`""")
# Delete POS Profile
frappe.db.sql("delete from `tabPOS Profile`")
frappe.flags.test_bank_transactions_created = False
frappe.flags.test_payments_created = False

View File

@@ -23,13 +23,13 @@ class CashierClosing(Document):
where posting_date=%s and posting_time>=%s and posting_time<=%s and owner=%s
""", (self.date, self.from_time, self.time, self.user))
self.outstanding_amount = flt(values[0][0] if values else 0)
def make_calculations(self):
total = 0.00
for i in self.payments:
total += flt(i.amount)
self.net_amount = total + self.outstanding_amount + self.expense - self.custody + self.returns
self.net_amount = total + self.outstanding_amount + flt(self.expense) - flt(self.custody) + flt(self.returns)
def validate_time(self):
if self.from_time >= self.time:

View File

@@ -60,8 +60,13 @@ frappe.ui.form.on('Cost Center', {
"label": "Cost Center Number",
"fieldname": "cost_center_number",
"fieldtype": "Data",
"reqd": 1,
"default": frm.doc.cost_center_number
},
{
"label": __("Merge with existing"),
"fieldname": "merge",
"fieldtype": "Check",
"default": 0
}
],
primary_action: function() {
@@ -76,8 +81,9 @@ frappe.ui.form.on('Cost Center', {
args: {
docname: frm.doc.name,
cost_center_name: data.cost_center_name,
cost_center_number: data.cost_center_number,
company: frm.doc.company
cost_center_number: cstr(data.cost_center_number),
company: frm.doc.company,
merge: data.merge
},
callback: function(r) {
frappe.dom.unfreeze();

View File

@@ -125,7 +125,7 @@
"idx": 1,
"is_tree": 1,
"links": [],
"modified": "2020-04-29 16:09:30.025214",
"modified": "2020-06-12 16:09:30.025214",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Cost Center",

View File

@@ -1,347 +1,122 @@
{
"allow_copy": 0,
"allow_guest_to_view": 0,
"allow_import": 1,
"allow_rename": 0,
"autoname": "field:year",
"beta": 0,
"creation": "2013-01-22 16:50:25",
"custom": 0,
"description": "**Fiscal Year** represents a Financial Year. All accounting entries and other major transactions are tracked against **Fiscal Year**.",
"docstatus": 0,
"doctype": "DocType",
"document_type": "Setup",
"editable_grid": 0,
"allow_import": 1,
"autoname": "field:year",
"creation": "2013-01-22 16:50:25",
"description": "**Fiscal Year** represents a Financial Year. All accounting entries and other major transactions are tracked against **Fiscal Year**.",
"doctype": "DocType",
"document_type": "Setup",
"engine": "InnoDB",
"field_order": [
"year",
"disabled",
"is_short_year",
"year_start_date",
"year_end_date",
"companies",
"auto_created"
],
"fields": [
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"description": "For e.g. 2012, 2012-13",
"fieldname": "year",
"fieldtype": "Data",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Year Name",
"length": 0,
"no_copy": 0,
"oldfieldname": "year",
"oldfieldtype": "Data",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"description": "For e.g. 2012, 2012-13",
"fieldname": "year",
"fieldtype": "Data",
"in_list_view": 1,
"label": "Year Name",
"oldfieldname": "year",
"oldfieldtype": "Data",
"reqd": 1,
"unique": 1
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "disabled",
"fieldtype": "Check",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Disabled",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"default": "0",
"fieldname": "disabled",
"fieldtype": "Check",
"label": "Disabled"
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "year_start_date",
"fieldtype": "Date",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Year Start Date",
"length": 0,
"no_copy": 1,
"oldfieldname": "year_start_date",
"oldfieldtype": "Date",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "year_start_date",
"fieldtype": "Date",
"in_list_view": 1,
"label": "Year Start Date",
"no_copy": 1,
"oldfieldname": "year_start_date",
"oldfieldtype": "Date",
"reqd": 1
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "year_end_date",
"fieldtype": "Date",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Year End Date",
"length": 0,
"no_copy": 1,
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "year_end_date",
"fieldtype": "Date",
"in_list_view": 1,
"label": "Year End Date",
"no_copy": 1,
"reqd": 1
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "companies",
"fieldtype": "Table",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Companies",
"length": 0,
"no_copy": 0,
"options": "Fiscal Year Company",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "companies",
"fieldtype": "Table",
"label": "Companies",
"options": "Fiscal Year Company"
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"default": "0",
"fieldname": "auto_created",
"fieldtype": "Check",
"hidden": 1,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Auto Created",
"length": 0,
"no_copy": 1,
"permlevel": 0,
"precision": "",
"print_hide": 1,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
"default": "0",
"fieldname": "auto_created",
"fieldtype": "Check",
"hidden": 1,
"label": "Auto Created",
"no_copy": 1,
"print_hide": 1,
"read_only": 1
},
{
"default": "0",
"description": "Less than 12 months.",
"fieldname": "is_short_year",
"fieldtype": "Check",
"label": "Is Short Year",
"set_only_once": 1
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 0,
"icon": "fa fa-calendar",
"idx": 1,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 0,
"max_attachments": 0,
"modified": "2018-04-25 14:21:41.273354",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Fiscal Year",
"owner": "Administrator",
],
"icon": "fa fa-calendar",
"idx": 1,
"modified": "2020-10-03 18:22:04.161315",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Fiscal Year",
"owner": "Administrator",
"permissions": [
{
"amend": 0,
"cancel": 0,
"create": 1,
"delete": 1,
"email": 1,
"export": 0,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 1,
"read": 1,
"report": 1,
"role": "System Manager",
"set_user_permissions": 0,
"share": 1,
"submit": 0,
"create": 1,
"delete": 1,
"email": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "System Manager",
"share": 1,
"write": 1
},
},
{
"amend": 0,
"cancel": 0,
"create": 0,
"delete": 0,
"email": 0,
"export": 0,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 0,
"read": 1,
"report": 0,
"role": "Sales User",
"set_user_permissions": 0,
"share": 0,
"submit": 0,
"write": 0
},
"read": 1,
"role": "Sales User"
},
{
"amend": 0,
"cancel": 0,
"create": 0,
"delete": 0,
"email": 0,
"export": 0,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 0,
"read": 1,
"report": 0,
"role": "Purchase User",
"set_user_permissions": 0,
"share": 0,
"submit": 0,
"write": 0
},
"read": 1,
"role": "Purchase User"
},
{
"amend": 0,
"cancel": 0,
"create": 0,
"delete": 0,
"email": 0,
"export": 0,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 0,
"read": 1,
"report": 0,
"role": "Accounts User",
"set_user_permissions": 0,
"share": 0,
"submit": 0,
"write": 0
},
"read": 1,
"role": "Accounts User"
},
{
"amend": 0,
"cancel": 0,
"create": 0,
"delete": 0,
"email": 0,
"export": 0,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 0,
"read": 1,
"report": 0,
"role": "Stock User",
"set_user_permissions": 0,
"share": 0,
"submit": 0,
"write": 0
},
"read": 1,
"role": "Stock User"
},
{
"amend": 0,
"cancel": 0,
"create": 0,
"delete": 0,
"email": 0,
"export": 0,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 0,
"read": 1,
"report": 0,
"role": "Employee",
"set_user_permissions": 0,
"share": 0,
"submit": 0,
"write": 0
"read": 1,
"role": "Employee"
}
],
"quick_entry": 0,
"read_only": 0,
"read_only_onload": 0,
"show_name_in_global_search": 1,
"sort_field": "name",
"sort_order": "DESC",
"track_changes": 0,
"track_seen": 0
],
"show_name_in_global_search": 1,
"sort_field": "name",
"sort_order": "DESC"
}

View File

@@ -36,6 +36,11 @@ class FiscalYear(Document):
frappe.throw(_("Cannot change Fiscal Year Start Date and Fiscal Year End Date once the Fiscal Year is saved."))
def validate_dates(self):
if self.is_short_year:
# Fiscal Year can be shorter than one year, in some jurisdictions
# under certain circumstances. For example, in the USA and Germany.
return
if getdate(self.year_start_date) > getdate(self.year_end_date):
frappe.throw(_("Fiscal Year Start Date should be one year earlier than Fiscal Year End Date"),
FiscalYearIncorrectDate)

View File

@@ -58,5 +58,12 @@
"year": "_Test Fiscal Year 2021",
"year_end_date": "2021-12-31",
"year_start_date": "2021-01-01"
},
{
"doctype": "Fiscal Year",
"year": "_Test Short Fiscal Year 2021",
"is_short_year": 1,
"year_end_date": "2021-12-31",
"year_start_date": "2021-04-01"
}
]

View File

@@ -4,7 +4,7 @@
from __future__ import unicode_literals
import frappe, erpnext
from frappe import _
from frappe.utils import flt, fmt_money, getdate, formatdate
from frappe.utils import flt, fmt_money, getdate, formatdate, cint
from frappe.model.document import Document
from frappe.model.naming import set_name_from_naming_options
from frappe.model.meta import get_field_precision
@@ -75,12 +75,6 @@ class GLEntry(Document):
if not self.cost_center and self.voucher_type != 'Period Closing Voucher':
frappe.throw(_("{0} {1}: Cost Center is required for 'Profit and Loss' account {2}. Please set up a default Cost Center for the Company.")
.format(self.voucher_type, self.voucher_no, self.account))
else:
from erpnext.accounts.utils import get_allow_cost_center_in_entry_of_bs_account
if not get_allow_cost_center_in_entry_of_bs_account() and self.cost_center:
self.cost_center = None
if self.project:
self.project = None
def validate_dimensions_for_pl_and_bs(self):
@@ -137,10 +131,17 @@ class GLEntry(Document):
return self.cost_center_company[self.cost_center]
def _check_is_group():
return cint(frappe.get_cached_value('Cost Center', self.cost_center, 'is_group'))
if self.cost_center and _get_cost_center_company() != self.company:
frappe.throw(_("{0} {1}: Cost Center {2} does not belong to Company {3}")
.format(self.voucher_type, self.voucher_no, self.cost_center, self.company))
if not self.flags.from_repost and self.cost_center and _check_is_group():
frappe.throw(_("""{0} {1}: Cost Center {2} is a group cost center and group cost centers cannot
be used in transactions""").format(self.voucher_type, self.voucher_no, frappe.bold(self.cost_center)))
def validate_party(self):
validate_party_frozen_disabled(self.party_type, self.party)

View File

@@ -3,7 +3,7 @@
# For license information, please see license.txt
from __future__ import unicode_literals
import frappe, json
import frappe, json, erpnext
from frappe import _
from frappe.utils import flt, getdate, nowdate, add_days
from erpnext.controllers.accounts_controller import AccountsController
@@ -134,16 +134,19 @@ class InvoiceDiscounting(AccountsController):
je.append("accounts", {
"account": self.bank_account,
"debit_in_account_currency": flt(self.total_amount) - flt(self.bank_charges),
"cost_center": erpnext.get_default_cost_center(self.company)
})
je.append("accounts", {
"account": self.bank_charges_account,
"debit_in_account_currency": flt(self.bank_charges)
"debit_in_account_currency": flt(self.bank_charges),
"cost_center": erpnext.get_default_cost_center(self.company)
})
je.append("accounts", {
"account": self.short_term_loan,
"credit_in_account_currency": flt(self.total_amount),
"cost_center": erpnext.get_default_cost_center(self.company),
"reference_type": "Invoice Discounting",
"reference_name": self.name
})
@@ -151,6 +154,7 @@ class InvoiceDiscounting(AccountsController):
je.append("accounts", {
"account": self.accounts_receivable_discounted,
"debit_in_account_currency": flt(d.outstanding_amount),
"cost_center": erpnext.get_default_cost_center(self.company),
"reference_type": "Invoice Discounting",
"reference_name": self.name,
"party_type": "Customer",
@@ -160,6 +164,7 @@ class InvoiceDiscounting(AccountsController):
je.append("accounts", {
"account": self.accounts_receivable_credit,
"credit_in_account_currency": flt(d.outstanding_amount),
"cost_center": erpnext.get_default_cost_center(self.company),
"reference_type": "Invoice Discounting",
"reference_name": self.name,
"party_type": "Customer",
@@ -177,13 +182,15 @@ class InvoiceDiscounting(AccountsController):
je.append("accounts", {
"account": self.short_term_loan,
"debit_in_account_currency": flt(self.total_amount),
"cost_center": erpnext.get_default_cost_center(self.company),
"reference_type": "Invoice Discounting",
"reference_name": self.name,
})
je.append("accounts", {
"account": self.bank_account,
"credit_in_account_currency": flt(self.total_amount)
"credit_in_account_currency": flt(self.total_amount),
"cost_center": erpnext.get_default_cost_center(self.company)
})
if getdate(self.loan_end_date) > getdate(nowdate()):
@@ -193,6 +200,7 @@ class InvoiceDiscounting(AccountsController):
je.append("accounts", {
"account": self.accounts_receivable_discounted,
"credit_in_account_currency": flt(outstanding_amount),
"cost_center": erpnext.get_default_cost_center(self.company),
"reference_type": "Invoice Discounting",
"reference_name": self.name,
"party_type": "Customer",
@@ -202,6 +210,7 @@ class InvoiceDiscounting(AccountsController):
je.append("accounts", {
"account": self.accounts_receivable_unpaid,
"debit_in_account_currency": flt(outstanding_amount),
"cost_center": erpnext.get_default_cost_center(self.company),
"reference_type": "Invoice Discounting",
"reference_name": self.name,
"party_type": "Customer",

View File

@@ -2,6 +2,7 @@
{
"doctype": "Item Tax Template",
"title": "_Test Account Excise Duty @ 10",
"company": "_Test Company",
"taxes": [
{
"doctype": "Item Tax Template Detail",
@@ -14,6 +15,7 @@
{
"doctype": "Item Tax Template",
"title": "_Test Account Excise Duty @ 12",
"company": "_Test Company",
"taxes": [
{
"doctype": "Item Tax Template Detail",
@@ -26,6 +28,7 @@
{
"doctype": "Item Tax Template",
"title": "_Test Account Excise Duty @ 15",
"company": "_Test Company",
"taxes": [
{
"doctype": "Item Tax Template Detail",
@@ -38,6 +41,7 @@
{
"doctype": "Item Tax Template",
"title": "_Test Account Excise Duty @ 20",
"company": "_Test Company",
"taxes": [
{
"doctype": "Item Tax Template Detail",
@@ -50,6 +54,7 @@
{
"doctype": "Item Tax Template",
"title": "_Test Item Tax Template 1",
"company": "_Test Company",
"taxes": [
{
"doctype": "Item Tax Template Detail",

View File

@@ -619,20 +619,12 @@ $.extend(erpnext.journal_entry, {
return { filters: filters };
},
reverse_journal_entry: function(frm) {
var me = frm.doc;
for(var i=0; i<me.accounts.length; i++) {
me.accounts[i].credit += me.accounts[i].debit;
me.accounts[i].debit = me.accounts[i].credit - me.accounts[i].debit;
me.accounts[i].credit -= me.accounts[i].debit;
me.accounts[i].credit_in_account_currency = me.accounts[i].credit;
me.accounts[i].debit_in_account_currency = me.accounts[i].debit;
me.accounts[i].reference_type = "Journal Entry";
me.accounts[i].reference_name = me.name
}
frm.copy_doc();
cur_frm.reload_doc();
}
reverse_journal_entry: function() {
frappe.model.open_mapped_doc({
method: "erpnext.accounts.doctype.journal_entry.journal_entry.make_reverse_journal_entry",
frm: cur_frm
})
},
});
$.extend(erpnext.journal_entry, {

View File

@@ -836,13 +836,34 @@ def get_opening_accounts(company):
return [{"account": a, "balance": get_balance_on(a)} for a in accounts]
@frappe.whitelist()
@frappe.validate_and_sanitize_search_inputs
def get_against_jv(doctype, txt, searchfield, start, page_len, filters):
return frappe.db.sql("""select jv.name, jv.posting_date, jv.user_remark
from `tabJournal Entry` jv, `tabJournal Entry Account` jv_detail
where jv_detail.parent = jv.name and jv_detail.account = %s and ifnull(jv_detail.party, '') = %s
and (jv_detail.reference_type is null or jv_detail.reference_type = '')
and jv.docstatus = 1 and jv.`{0}` like %s order by jv.name desc limit %s, %s""".format(searchfield),
(filters.get("account"), cstr(filters.get("party")), "%{0}%".format(txt), start, page_len))
if not frappe.db.has_column('Journal Entry', searchfield):
return []
return frappe.db.sql("""
SELECT jv.name, jv.posting_date, jv.user_remark
FROM `tabJournal Entry` jv, `tabJournal Entry Account` jv_detail
WHERE jv_detail.parent = jv.name
AND jv_detail.account = %(account)s
AND IFNULL(jv_detail.party, '') = %(party)s
AND (
jv_detail.reference_type IS NULL
OR jv_detail.reference_type = ''
)
AND jv.docstatus = 1
AND jv.`{0}` LIKE %(txt)s
ORDER BY jv.name DESC
LIMIT %(offset)s, %(limit)s
""".format(searchfield), dict(
account=filters.get("account"),
party=cstr(filters.get("party")),
txt="%{0}%".format(txt),
offset=start,
limit=page_len
)
)
@frappe.whitelist()
@@ -996,3 +1017,34 @@ def make_inter_company_journal_entry(name, voucher_type, company):
journal_entry.posting_date = nowdate()
journal_entry.inter_company_journal_entry_reference = name
return journal_entry.as_dict()
@frappe.whitelist()
def make_reverse_journal_entry(source_name, target_doc=None):
from frappe.model.mapper import get_mapped_doc
def update_accounts(source, target, source_parent):
target.reference_type = "Journal Entry"
target.reference_name = source_parent.name
doclist = get_mapped_doc("Journal Entry", source_name, {
"Journal Entry": {
"doctype": "Journal Entry",
"validation": {
"docstatus": ["=", 1]
}
},
"Journal Entry Account": {
"doctype": "Journal Entry Account",
"field_map": {
"account_currency": "account_currency",
"exchange_rate": "exchange_rate",
"debit_in_account_currency": "credit_in_account_currency",
"debit": "credit",
"credit_in_account_currency": "debit_in_account_currency",
"credit": "debit",
},
"postprocess": update_accounts,
},
}, target_doc)
return doclist

View File

@@ -139,6 +139,49 @@ class TestJournalEntry(unittest.TestCase):
self.assertFalse(gle)
def test_reverse_journal_entry(self):
from erpnext.accounts.doctype.journal_entry.journal_entry import make_reverse_journal_entry
jv = make_journal_entry("_Test Bank USD - _TC",
"Sales - _TC", 100, exchange_rate=50, save=False)
jv.get("accounts")[1].credit_in_account_currency = 5000
jv.get("accounts")[1].exchange_rate = 1
jv.submit()
rjv = make_reverse_journal_entry(jv.name)
rjv.posting_date = nowdate()
rjv.submit()
gl_entries = frappe.db.sql("""select account, account_currency, debit, credit,
debit_in_account_currency, credit_in_account_currency
from `tabGL Entry` where voucher_type='Journal Entry' and voucher_no=%s
order by account asc""", rjv.name, as_dict=1)
self.assertTrue(gl_entries)
expected_values = {
"_Test Bank USD - _TC": {
"account_currency": "USD",
"debit": 0,
"debit_in_account_currency": 0,
"credit": 5000,
"credit_in_account_currency": 100,
},
"Sales - _TC": {
"account_currency": "INR",
"debit": 5000,
"debit_in_account_currency": 5000,
"credit": 0,
"credit_in_account_currency": 0,
}
}
for field in ("account_currency", "debit", "debit_in_account_currency", "credit", "credit_in_account_currency"):
for i, gle in enumerate(gl_entries):
self.assertEqual(expected_values[gle.account][field], gle[field])
def test_disallow_change_in_account_currency_for_a_party(self):
# create jv in USD
jv = make_journal_entry("_Test Bank USD - _TC",
@@ -204,11 +247,8 @@ class TestJournalEntry(unittest.TestCase):
self.assertEqual(jv.inter_company_journal_entry_reference, "")
self.assertEqual(jv1.inter_company_journal_entry_reference, "")
def test_jv_for_enable_allow_cost_center_in_entry_of_bs_account(self):
def test_jv_with_cost_centre(self):
from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center
accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings')
accounts_settings.allow_cost_center_in_entry_of_bs_account = 1
accounts_settings.save()
cost_center = "_Test Cost Center for BS Account - _TC"
create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company")
jv = make_journal_entry("_Test Cash - _TC", "_Test Bank - _TC", 100, cost_center = cost_center, save=False)
@@ -237,15 +277,45 @@ class TestJournalEntry(unittest.TestCase):
for gle in gl_entries:
self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center)
accounts_settings.allow_cost_center_in_entry_of_bs_account = 0
accounts_settings.save()
def test_jv_with_project(self):
from erpnext.projects.doctype.project.test_project import make_project
project = make_project({
'project_name': 'Journal Entry Project',
'project_template_name': 'Test Project Template',
'start_date': '2020-01-01'
})
def test_jv_account_and_party_balance_for_enable_allow_cost_center_in_entry_of_bs_account(self):
jv = make_journal_entry("_Test Cash - _TC", "_Test Bank - _TC", 100, save=False)
for d in jv.accounts:
d.project = project.project_name
jv.voucher_type = "Bank Entry"
jv.multi_currency = 0
jv.cheque_no = "112233"
jv.cheque_date = nowdate()
jv.insert()
jv.submit()
expected_values = {
"_Test Cash - _TC": {
"project": project.project_name
},
"_Test Bank - _TC": {
"project": project.project_name
}
}
gl_entries = frappe.db.sql("""select account, project, debit, credit
from `tabGL Entry` where voucher_type='Journal Entry' and voucher_no=%s
order by account asc""", jv.name, as_dict=1)
self.assertTrue(gl_entries)
for gle in gl_entries:
self.assertEqual(expected_values[gle.account]["project"], gle.project)
def test_jv_account_and_party_balance_with_cost_centre(self):
from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center
from erpnext.accounts.utils import get_balance_on
accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings')
accounts_settings.allow_cost_center_in_entry_of_bs_account = 1
accounts_settings.save()
cost_center = "_Test Cost Center for BS Account - _TC"
create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company")
jv = make_journal_entry("_Test Cash - _TC", "_Test Bank - _TC", 100, cost_center = cost_center, save=False)
@@ -261,9 +331,6 @@ class TestJournalEntry(unittest.TestCase):
account_balance = get_balance_on(account="_Test Bank - _TC", cost_center=cost_center)
self.assertEqual(expected_account_balance, account_balance)
accounts_settings.allow_cost_center_in_entry_of_bs_account = 0
accounts_settings.save()
def make_journal_entry(account1, account2, amount, cost_center=None, posting_date=None, exchange_rate=1, save=True, submit=False, project=None):
if not cost_center:
cost_center = "_Test Cost Center - _TC"

View File

@@ -68,6 +68,9 @@ class OpeningInvoiceCreationTool(Document):
if not self.company:
frappe.throw(_("Please select the Company"))
company_details = frappe.get_cached_value('Company', self.company,
["default_currency", "default_letter_head"], as_dict=1) or {}
for row in self.invoices:
if not row.qty:
row.qty = 1.0
@@ -99,6 +102,12 @@ class OpeningInvoiceCreationTool(Document):
if not args:
continue
if company_details:
args.update({
"currency": company_details.get("default_currency"),
"letter_head": company_details.get("default_letter_head")
})
doc = frappe.get_doc(args).insert()
doc.submit()
names.append(doc.name)
@@ -173,7 +182,7 @@ class OpeningInvoiceCreationTool(Document):
"posting_date": row.posting_date,
frappe.scrub(party_type): row.party,
"doctype": "Sales Invoice" if self.invoice_type == "Sales" else "Purchase Invoice",
"currency": frappe.get_cached_value('Company', self.company, "default_currency")
"update_stock": 0
})
accounting_dimension = get_accounting_dimensions()

View File

@@ -7,17 +7,25 @@ import frappe
import unittest
test_dependencies = ["Customer", "Supplier"]
from frappe.custom.doctype.property_setter.property_setter import make_property_setter
from erpnext.accounts.doctype.opening_invoice_creation_tool.opening_invoice_creation_tool import get_temporary_opening_account
from erpnext.controllers.accounts_controller import AccountMissingError
class TestOpeningInvoiceCreationTool(unittest.TestCase):
def make_invoices(self, invoice_type="Sales"):
def setUp(self):
if not frappe.db.exists("Company", "_Test Opening Invoice Company"):
make_company()
def make_invoices(self, invoice_type="Sales", company=None, party_1=None, party_2=None):
doc = frappe.get_single("Opening Invoice Creation Tool")
args = get_opening_invoice_creation_dict(invoice_type=invoice_type)
args = get_opening_invoice_creation_dict(invoice_type=invoice_type, company=company,
party_1=party_1, party_2=party_2)
doc.update(args)
return doc.make_invoices()
def test_opening_sales_invoice_creation(self):
invoices = self.make_invoices()
property_setter = make_property_setter("Sales Invoice", "update_stock", "default", 1, "Check")
invoices = self.make_invoices(company="_Test Opening Invoice Company")
self.assertEqual(len(invoices), 2)
expected_value = {
@@ -27,6 +35,13 @@ class TestOpeningInvoiceCreationTool(unittest.TestCase):
}
self.check_expected_values(invoices, expected_value)
si = frappe.get_doc("Sales Invoice", invoices[0])
# Check if update stock is not enabled
self.assertEqual(si.update_stock, 0)
property_setter.delete()
def check_expected_values(self, invoices, expected_value, invoice_type="Sales"):
doctype = "Sales Invoice" if invoice_type == "Sales" else "Purchase Invoice"
@@ -36,7 +51,7 @@ class TestOpeningInvoiceCreationTool(unittest.TestCase):
self.assertEqual(si.get(field, ""), expected_value[invoice_idx][field_idx])
def test_opening_purchase_invoice_creation(self):
invoices = self.make_invoices(invoice_type="Purchase")
invoices = self.make_invoices(invoice_type="Purchase", company="_Test Opening Invoice Company")
self.assertEqual(len(invoices), 2)
expected_value = {
@@ -46,6 +61,28 @@ class TestOpeningInvoiceCreationTool(unittest.TestCase):
}
self.check_expected_values(invoices, expected_value, invoice_type="Purchase", )
def test_opening_sales_invoice_creation_with_missing_debit_account(self):
company = "_Test Opening Invoice Company"
party_1, party_2 = make_customer("Customer A"), make_customer("Customer B")
old_default_receivable_account = frappe.db.get_value("Company", company, "default_receivable_account")
frappe.db.set_value("Company", company, "default_receivable_account", "")
if not frappe.db.exists("Cost Center", "_Test Opening Invoice Company - _TOIC"):
cc = frappe.get_doc({"doctype": "Cost Center", "cost_center_name": "_Test Opening Invoice Company",
"is_group": 1, "company": "_Test Opening Invoice Company"})
cc.insert(ignore_mandatory=True)
cc2 = frappe.get_doc({"doctype": "Cost Center", "cost_center_name": "Main", "is_group": 0,
"company": "_Test Opening Invoice Company", "parent_cost_center": cc.name})
cc2.insert()
frappe.db.set_value("Company", company, "cost_center", "Main - _TOIC")
self.assertRaises(AccountMissingError, self.make_invoices, company="_Test Opening Invoice Company", party_1=party_1, party_2=party_2)
# teardown
frappe.db.set_value("Company", company, "default_receivable_account", old_default_receivable_account)
def get_opening_invoice_creation_dict(**args):
party = "Customer" if args.get("invoice_type", "Sales") == "Sales" else "Supplier"
company = args.get("company", "_Test Company")
@@ -57,7 +94,7 @@ def get_opening_invoice_creation_dict(**args):
{
"qty": 1.0,
"outstanding_amount": 300,
"party": "_Test {0}".format(party),
"party": args.get("party_1") or "_Test {0}".format(party),
"item_name": "Opening Item",
"due_date": "2016-09-10",
"posting_date": "2016-09-05",
@@ -66,7 +103,7 @@ def get_opening_invoice_creation_dict(**args):
{
"qty": 2.0,
"outstanding_amount": 250,
"party": "_Test {0} 1".format(party),
"party": args.get("party_2") or "_Test {0} 1".format(party),
"item_name": "Opening Item",
"due_date": "2016-09-10",
"posting_date": "2016-09-05",
@@ -76,4 +113,31 @@ def get_opening_invoice_creation_dict(**args):
})
invoice_dict.update(args)
return invoice_dict
return invoice_dict
def make_company():
if frappe.db.exists("Company", "_Test Opening Invoice Company"):
return frappe.get_doc("Company", "_Test Opening Invoice Company")
company = frappe.new_doc("Company")
company.company_name = "_Test Opening Invoice Company"
company.abbr = "_TOIC"
company.default_currency = "INR"
company.country = "India"
company.insert()
return company
def make_customer(customer=None):
customer_name = customer or "Opening Customer"
customer = frappe.get_doc({
"doctype": "Customer",
"customer_name": customer_name,
"customer_group": "All Customer Groups",
"customer_type": "Company",
"territory": "All Territories"
})
if not frappe.db.exists("Customer", customer_name):
customer.insert(ignore_permissions=True)
return customer.name
else:
return frappe.db.exists("Customer", customer_name)

View File

@@ -12,9 +12,10 @@ frappe.ui.form.on('Payment Entry', {
setup: function(frm) {
frm.set_query("paid_from", function() {
frm.events.validate_company(frm);
var account_types = in_list(["Pay", "Internal Transfer"], frm.doc.payment_type) ?
["Bank", "Cash"] : [frappe.boot.party_account_types[frm.doc.party_type]];
return {
filters: {
"account_type": ["in", account_types],
@@ -23,27 +24,34 @@ frappe.ui.form.on('Payment Entry', {
}
}
});
frm.set_query("party_type", function() {
frm.events.validate_company(frm);
return{
"filters": {
filters: {
"name": ["in", Object.keys(frappe.boot.party_account_types)],
}
}
});
frm.set_query("party_bank_account", function() {
return {
filters: {
"is_company_account":0
is_company_account: 0,
party_type: frm.doc.party_type,
party: frm.doc.party
}
}
});
frm.set_query("bank_account", function() {
return {
filters: {
"is_company_account":1
is_company_account: 1
}
}
});
frm.set_query("contact_person", function() {
if (frm.doc.party) {
return {
@@ -55,10 +63,12 @@ frappe.ui.form.on('Payment Entry', {
};
}
});
frm.set_query("paid_to", function() {
frm.events.validate_company(frm);
var account_types = in_list(["Receive", "Internal Transfer"], frm.doc.payment_type) ?
["Bank", "Cash"] : [frappe.boot.party_account_types[frm.doc.party_type]];
return {
filters: {
"account_type": ["in", account_types],
@@ -147,6 +157,12 @@ frappe.ui.form.on('Payment Entry', {
frm.events.show_general_ledger(frm);
},
validate_company: (frm) => {
if (!frm.doc.company){
frappe.throw({message:__("Please select a Company first."), title: __("Mandatory")});
}
},
company: function(frm) {
frm.events.hide_unhide_fields(frm);
frm.events.set_dynamic_labels(frm);
@@ -326,7 +342,7 @@ frappe.ui.form.on('Payment Entry', {
() => {
frm.set_party_account_based_on_party = false;
if (r.message.bank_account) {
frm.set_value("party_bank_account", r.message.bank_account);
frm.set_value("bank_account", r.message.bank_account);
}
}
]);

View File

@@ -6,7 +6,7 @@ from __future__ import unicode_literals
import frappe, erpnext, json
from frappe import _, scrub, ValidationError
from frappe.utils import flt, comma_or, nowdate, getdate
from erpnext.accounts.utils import get_outstanding_invoices, get_account_currency, get_balance_on, get_allow_cost_center_in_entry_of_bs_account
from erpnext.accounts.utils import get_outstanding_invoices, get_account_currency, get_balance_on
from erpnext.accounts.party import get_party_account
from erpnext.accounts.doctype.journal_entry.journal_entry import get_default_bank_cash_account
from erpnext.setup.utils import get_exchange_rate
@@ -84,7 +84,7 @@ class PaymentEntry(AccountsController):
self.delink_advance_entry_references()
self.update_payment_schedule(cancel=1)
self.set_payment_req_status()
self.set_status()
self.set_status(update=True)
def set_payment_req_status(self):
from erpnext.accounts.doctype.payment_request.payment_request import update_payment_req_status
@@ -279,7 +279,7 @@ class PaymentEntry(AccountsController):
outstanding_amount, is_return = frappe.get_cached_value(d.reference_doctype, d.reference_name, ["outstanding_amount", "is_return"])
if outstanding_amount <= 0 and not is_return:
no_oustanding_refs.setdefault(d.reference_doctype, []).append(d)
for k, v in no_oustanding_refs.items():
frappe.msgprint(_("{} - {} now have {} as they had no outstanding amount left before submitting the Payment Entry.<br><br>\
If this is undesirable please cancel the corresponding Payment Entry.")
@@ -340,7 +340,7 @@ class PaymentEntry(AccountsController):
frappe.db.sql(""" UPDATE `tabPayment Schedule` SET paid_amount = `paid_amount` + %s
WHERE parent = %s and payment_term = %s""", (amount, key[1], key[0]))
def set_status(self):
def set_status(self, update=False):
if self.docstatus == 2:
self.status = 'Cancelled'
elif self.docstatus == 1:
@@ -348,6 +348,9 @@ class PaymentEntry(AccountsController):
else:
self.status = 'Draft'
if update:
self.db_set('status', self.status)
def set_amounts(self):
self.set_amounts_in_company_currency()
self.set_total_allocated_amount()
@@ -657,7 +660,7 @@ def get_outstanding_reference_documents(args):
.format(frappe.db.escape(args["voucher_type"]), frappe.db.escape(args["voucher_no"]))
# Add cost center condition
if args.get("cost_center") and get_allow_cost_center_in_entry_of_bs_account():
if args.get("cost_center"):
condition += " and cost_center='%s'" % args.get("cost_center")
date_fields_dict = {

View File

@@ -1,12 +1,14 @@
frappe.listview_settings['Payment Entry'] = {
onload: function(listview) {
listview.page.fields_dict.party_type.get_query = function() {
return {
"filters": {
"name": ["in", Object.keys(frappe.boot.party_account_types)],
}
if (listview.page.fields_dict.party_type) {
listview.page.fields_dict.party_type.get_query = function() {
return {
"filters": {
"name": ["in", Object.keys(frappe.boot.party_account_types)],
}
};
};
};
}
}
};

View File

@@ -462,11 +462,8 @@ class TestPaymentEntry(unittest.TestCase):
outstanding_amount = flt(frappe.db.get_value("Sales Invoice", si.name, "outstanding_amount"))
self.assertEqual(outstanding_amount, 0)
def test_payment_entry_against_sales_invoice_for_enable_allow_cost_center_in_entry_of_bs_account(self):
def test_payment_entry_against_sales_invoice_with_cost_centre(self):
from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center
accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings')
accounts_settings.allow_cost_center_in_entry_of_bs_account = 1
accounts_settings.save()
cost_center = "_Test Cost Center for BS Account - _TC"
create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company")
@@ -501,39 +498,8 @@ class TestPaymentEntry(unittest.TestCase):
for gle in gl_entries:
self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center)
accounts_settings.allow_cost_center_in_entry_of_bs_account = 0
accounts_settings.save()
def test_payment_entry_against_sales_invoice_for_disable_allow_cost_center_in_entry_of_bs_account(self):
accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings')
accounts_settings.allow_cost_center_in_entry_of_bs_account = 0
accounts_settings.save()
si = create_sales_invoice(debit_to="Debtors - _TC")
pe = get_payment_entry("Sales Invoice", si.name, bank_account="_Test Bank - _TC")
pe.reference_no = "112211-2"
pe.reference_date = nowdate()
pe.paid_to = "_Test Bank - _TC"
pe.paid_amount = si.grand_total
pe.insert()
pe.submit()
gl_entries = frappe.db.sql("""select account, cost_center, account_currency, debit, credit,
debit_in_account_currency, credit_in_account_currency
from `tabGL Entry` where voucher_type='Payment Entry' and voucher_no=%s
order by account asc""", pe.name, as_dict=1)
self.assertTrue(gl_entries)
for gle in gl_entries:
self.assertEqual(gle.cost_center, None)
def test_payment_entry_against_purchase_invoice_for_enable_allow_cost_center_in_entry_of_bs_account(self):
def test_payment_entry_against_purchase_invoice_with_cost_center(self):
from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center
accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings')
accounts_settings.allow_cost_center_in_entry_of_bs_account = 1
accounts_settings.save()
cost_center = "_Test Cost Center for BS Account - _TC"
create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company")
@@ -568,40 +534,9 @@ class TestPaymentEntry(unittest.TestCase):
for gle in gl_entries:
self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center)
accounts_settings.allow_cost_center_in_entry_of_bs_account = 0
accounts_settings.save()
def test_payment_entry_against_purchase_invoice_for_disable_allow_cost_center_in_entry_of_bs_account(self):
accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings')
accounts_settings.allow_cost_center_in_entry_of_bs_account = 0
accounts_settings.save()
pi = make_purchase_invoice(credit_to="Creditors - _TC")
pe = get_payment_entry("Purchase Invoice", pi.name, bank_account="_Test Bank - _TC")
pe.reference_no = "112222-2"
pe.reference_date = nowdate()
pe.paid_from = "_Test Bank - _TC"
pe.paid_amount = pi.grand_total
pe.insert()
pe.submit()
gl_entries = frappe.db.sql("""select account, cost_center, account_currency, debit, credit,
debit_in_account_currency, credit_in_account_currency
from `tabGL Entry` where voucher_type='Payment Entry' and voucher_no=%s
order by account asc""", pe.name, as_dict=1)
self.assertTrue(gl_entries)
for gle in gl_entries:
self.assertEqual(gle.cost_center, None)
def test_payment_entry_account_and_party_balance_for_enable_allow_cost_center_in_entry_of_bs_account(self):
def test_payment_entry_account_and_party_balance_with_cost_center(self):
from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center
from erpnext.accounts.utils import get_balance_on
accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings')
accounts_settings.allow_cost_center_in_entry_of_bs_account = 1
accounts_settings.save()
cost_center = "_Test Cost Center for BS Account - _TC"
create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company")
@@ -632,9 +567,6 @@ class TestPaymentEntry(unittest.TestCase):
self.assertEqual(expected_party_balance, party_balance)
self.assertEqual(expected_party_account_balance, party_account_balance)
accounts_settings.allow_cost_center_in_entry_of_bs_account = 0
accounts_settings.save()
def create_payment_terms_template():
create_payment_term('Basic Amount Receivable')

View File

@@ -26,6 +26,8 @@ class PaymentOrder(Document):
for d in self.references:
frappe.db.set_value(self.payment_order_type, d.get(frappe.scrub(self.payment_order_type)), ref_field, status)
@frappe.whitelist()
@frappe.validate_and_sanitize_search_inputs
def get_mop_query(doctype, txt, searchfield, start, page_len, filters):
return frappe.db.sql(""" select mode_of_payment from `tabPayment Order Reference`
where parent = %(parent)s and mode_of_payment like %(txt)s
@@ -36,6 +38,8 @@ def get_mop_query(doctype, txt, searchfield, start, page_len, filters):
'txt': "%%%s%%" % txt
})
@frappe.whitelist()
@frappe.validate_and_sanitize_search_inputs
def get_supplier_query(doctype, txt, searchfield, start, page_len, filters):
return frappe.db.sql(""" select supplier from `tabPayment Order Reference`
where parent = %(parent)s and supplier like %(txt)s and
@@ -86,4 +90,4 @@ def make_journal_entry(doc, supplier, mode_of_payment=None):
je.flags.ignore_mandatory = True
je.save()
frappe.msgprint(_("{0} {1} created").format(je.doctype, je.name))
frappe.msgprint(_("{0} {1} created").format(je.doctype, je.name))

View File

@@ -37,6 +37,11 @@ frappe.ui.form.on("Payment Reconciliation Payment", {
erpnext.accounts.PaymentReconciliationController = frappe.ui.form.Controller.extend({
onload: function() {
var me = this;
this.frm.set_query("party", function() {
check_mandatory(me.frm);
});
this.frm.set_query("party_type", function() {
return {
"filters": {
@@ -46,33 +51,39 @@ erpnext.accounts.PaymentReconciliationController = frappe.ui.form.Controller.ext
});
this.frm.set_query('receivable_payable_account', function() {
if(!me.frm.doc.company || !me.frm.doc.party_type) {
frappe.msgprint(__("Please select Company and Party Type first"));
} else {
return{
filters: {
"company": me.frm.doc.company,
"is_group": 0,
"account_type": frappe.boot.party_account_types[me.frm.doc.party_type]
}
};
}
check_mandatory(me.frm);
return {
filters: {
"company": me.frm.doc.company,
"is_group": 0,
"account_type": frappe.boot.party_account_types[me.frm.doc.party_type]
}
};
});
this.frm.set_query('bank_cash_account', function() {
if(!me.frm.doc.company) {
frappe.msgprint(__("Please select Company first"));
} else {
return{
filters:[
['Account', 'company', '=', me.frm.doc.company],
['Account', 'is_group', '=', 0],
['Account', 'account_type', 'in', ['Bank', 'Cash']]
]
};
}
check_mandatory(me.frm, true);
return {
filters:[
['Account', 'company', '=', me.frm.doc.company],
['Account', 'is_group', '=', 0],
['Account', 'account_type', 'in', ['Bank', 'Cash']]
]
};
});
this.frm.set_value('party_type', '');
this.frm.set_value('party', '');
this.frm.set_value('receivable_payable_account', '');
var check_mandatory = (frm, only_company=false) => {
var title = __("Mandatory");
if (only_company && !frm.doc.company) {
frappe.throw({message: __("Please Select a Company First"), title: title});
} else if (!frm.doc.company || !frm.doc.party_type) {
frappe.throw({message: __("Please Select Both Company and Party Type First"), title: title});
}
};
},
refresh: function() {
@@ -86,7 +97,7 @@ erpnext.accounts.PaymentReconciliationController = frappe.ui.form.Controller.ext
party: function() {
var me = this
if(!me.frm.doc.receivable_payable_account && me.frm.doc.party_type && me.frm.doc.party) {
if (!me.frm.doc.receivable_payable_account && me.frm.doc.party_type && me.frm.doc.party) {
return frappe.call({
method: "erpnext.accounts.party.get_party_account",
args: {
@@ -95,7 +106,7 @@ erpnext.accounts.PaymentReconciliationController = frappe.ui.form.Controller.ext
party: me.frm.doc.party
},
callback: function(r) {
if(!r.exc && r.message) {
if (!r.exc && r.message) {
me.frm.set_value("receivable_payable_account", r.message);
}
}

View File

@@ -48,7 +48,8 @@ class PaymentReconciliation(Document):
select
"Journal Entry" as reference_type, t1.name as reference_name,
t1.posting_date, t1.remark as remarks, t2.name as reference_row,
{dr_or_cr} as amount, t2.is_advance
{dr_or_cr} as amount, t2.is_advance,
t2.account_currency as currency
from
`tabJournal Entry` t1, `tabJournal Entry Account` t2
where
@@ -88,7 +89,8 @@ class PaymentReconciliation(Document):
if self.party_type == 'Customer' else "Purchase Invoice")
return frappe.db.sql(""" SELECT `tab{doc}`.name as reference_name, %(voucher_type)s as reference_type,
(sum(`tabGL Entry`.{dr_or_cr}) - sum(`tabGL Entry`.{reconciled_dr_or_cr})) as amount
(sum(`tabGL Entry`.{dr_or_cr}) - sum(`tabGL Entry`.{reconciled_dr_or_cr})) as amount,
account_currency as currency
FROM `tab{doc}`, `tabGL Entry`
WHERE
(`tab{doc}`.name = `tabGL Entry`.against_voucher or `tab{doc}`.name = `tabGL Entry`.voucher_no)
@@ -101,10 +103,10 @@ class PaymentReconciliation(Document):
Having
amount > 0
""".format(
doc=voucher_type,
dr_or_cr=dr_or_cr,
reconciled_dr_or_cr=reconciled_dr_or_cr,
party_type_field=frappe.scrub(self.party_type)),
doc=voucher_type,
dr_or_cr=dr_or_cr,
reconciled_dr_or_cr=reconciled_dr_or_cr,
party_type_field=frappe.scrub(self.party_type)),
{
'party': self.party,
'party_type': self.party_type,
@@ -141,6 +143,7 @@ class PaymentReconciliation(Document):
ent.invoice_number = e.get('voucher_no')
ent.invoice_date = e.get('posting_date')
ent.amount = flt(e.get('invoice_amount'))
ent.currency = e.get('currency')
ent.outstanding_amount = e.get('outstanding_amount')
def reconcile(self, args):
@@ -170,7 +173,7 @@ class PaymentReconciliation(Document):
reconcile_against_document(lst)
if dr_or_cr_notes:
reconcile_dr_cr_note(dr_or_cr_notes)
reconcile_dr_cr_note(dr_or_cr_notes, self.company)
msgprint(_("Successfully Reconciled"))
self.get_unreconciled_entries()
@@ -261,7 +264,7 @@ class PaymentReconciliation(Document):
return cond
def reconcile_dr_cr_note(dr_cr_notes):
def reconcile_dr_cr_note(dr_cr_notes, company):
for d in dr_cr_notes:
voucher_type = ('Credit Note'
if d.voucher_type == 'Sales Invoice' else 'Debit Note')
@@ -269,10 +272,14 @@ def reconcile_dr_cr_note(dr_cr_notes):
reconcile_dr_or_cr = ('debit_in_account_currency'
if d.dr_or_cr == 'credit_in_account_currency' else 'credit_in_account_currency')
company_currency = erpnext.get_company_currency(company)
jv = frappe.get_doc({
"doctype": "Journal Entry",
"voucher_type": voucher_type,
"posting_date": today(),
"company": company,
"multi_currency": 1 if d.currency != company_currency else 0,
"accounts": [
{
'account': d.account,
@@ -280,7 +287,8 @@ def reconcile_dr_cr_note(dr_cr_notes):
'party_type': d.party_type,
d.dr_or_cr: abs(d.allocated_amount),
'reference_type': d.against_voucher_type,
'reference_name': d.against_voucher
'reference_name': d.against_voucher,
'cost_center': erpnext.get_default_cost_center(company)
},
{
'account': d.account,
@@ -289,7 +297,8 @@ def reconcile_dr_cr_note(dr_cr_notes):
reconcile_dr_or_cr: (abs(d.allocated_amount)
if abs(d.unadjusted_amount) > abs(d.allocated_amount) else abs(d.unadjusted_amount)),
'reference_type': d.voucher_type,
'reference_name': d.voucher_no
'reference_name': d.voucher_no,
'cost_center': erpnext.get_default_cost_center(company)
}
]
})

View File

@@ -1,183 +1,80 @@
{
"allow_copy": 0,
"allow_import": 0,
"allow_rename": 0,
"beta": 0,
"creation": "2014-07-09 16:14:23.672922",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "",
"editable_grid": 1,
"actions": [],
"creation": "2014-07-09 16:14:23.672922",
"doctype": "DocType",
"editable_grid": 1,
"engine": "InnoDB",
"field_order": [
"invoice_type",
"invoice_number",
"invoice_date",
"col_break1",
"amount",
"outstanding_amount",
"currency"
],
"fields": [
{
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"fieldname": "invoice_type",
"fieldtype": "Select",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_list_view": 1,
"label": "Invoice Type",
"length": 0,
"no_copy": 0,
"options": "Sales Invoice\nPurchase Invoice\nJournal Entry",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
"fieldname": "invoice_type",
"fieldtype": "Select",
"in_list_view": 1,
"label": "Invoice Type",
"options": "Sales Invoice\nPurchase Invoice\nJournal Entry",
"read_only": 1
},
{
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"fieldname": "invoice_number",
"fieldtype": "Dynamic Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_list_view": 1,
"label": "Invoice Number",
"length": 0,
"no_copy": 0,
"options": "invoice_type",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
"fieldname": "invoice_number",
"fieldtype": "Dynamic Link",
"in_list_view": 1,
"label": "Invoice Number",
"options": "invoice_type",
"read_only": 1
},
{
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"fieldname": "invoice_date",
"fieldtype": "Date",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_list_view": 1,
"label": "Invoice Date",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
"fieldname": "invoice_date",
"fieldtype": "Date",
"in_list_view": 1,
"label": "Invoice Date",
"read_only": 1
},
{
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"fieldname": "col_break1",
"fieldtype": "Column Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_list_view": 0,
"label": "",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
"fieldname": "col_break1",
"fieldtype": "Column Break"
},
{
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"fieldname": "amount",
"fieldtype": "Currency",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_list_view": 1,
"label": "Amount",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
"fieldname": "amount",
"fieldtype": "Currency",
"in_list_view": 1,
"label": "Amount",
"options": "currency",
"read_only": 1
},
{
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"fieldname": "outstanding_amount",
"fieldtype": "Currency",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_list_view": 1,
"label": "Outstanding Amount",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
"fieldname": "outstanding_amount",
"fieldtype": "Currency",
"in_list_view": 1,
"label": "Outstanding Amount",
"options": "currency",
"read_only": 1
},
{
"fieldname": "currency",
"fieldtype": "Link",
"hidden": 1,
"label": "Currency",
"options": "Currency"
}
],
"hide_heading": 0,
"hide_toolbar": 0,
"idx": 0,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 1,
"max_attachments": 0,
"modified": "2016-07-11 03:28:03.588476",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Payment Reconciliation Invoice",
"name_case": "",
"owner": "Administrator",
"permissions": [],
"quick_entry": 1,
"read_only": 0,
"read_only_onload": 0,
"sort_field": "modified",
"sort_order": "DESC",
"track_seen": 0
],
"istable": 1,
"links": [],
"modified": "2020-07-19 18:12:27.964073",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Payment Reconciliation Invoice",
"owner": "Administrator",
"permissions": [],
"quick_entry": 1,
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 1
}

View File

@@ -1,7 +1,9 @@
{
"actions": [],
"creation": "2014-07-09 16:13:35.452759",
"doctype": "DocType",
"editable_grid": 1,
"engine": "InnoDB",
"field_order": [
"reference_type",
"reference_name",
@@ -16,7 +18,8 @@
"difference_account",
"difference_amount",
"sec_break1",
"remark"
"remark",
"currency"
],
"fields": [
{
@@ -73,6 +76,7 @@
"fieldtype": "Currency",
"in_list_view": 1,
"label": "Amount",
"options": "currency",
"read_only": 1
},
{
@@ -81,6 +85,7 @@
"fieldtype": "Currency",
"in_list_view": 1,
"label": "Allocated amount",
"options": "currency",
"reqd": 1
},
{
@@ -106,16 +111,25 @@
"fieldname": "difference_amount",
"fieldtype": "Currency",
"label": "Difference Amount",
"options": "currency",
"print_hide": 1,
"read_only": 1
},
{
"fieldname": "section_break_10",
"fieldtype": "Section Break"
},
{
"fieldname": "currency",
"fieldtype": "Link",
"hidden": 1,
"label": "Currency",
"options": "Currency"
}
],
"istable": 1,
"modified": "2019-06-24 00:08:11.150796",
"links": [],
"modified": "2020-07-19 18:12:41.682347",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Payment Reconciliation Payment",

View File

@@ -140,9 +140,6 @@ class PaymentRequest(Document):
})
def set_as_paid(self):
if frappe.session.user == "Guest":
frappe.set_user("Administrator")
payment_entry = self.create_payment_entry()
self.make_invoice()
@@ -254,7 +251,7 @@ class PaymentRequest(Document):
if status in ["Authorized", "Completed"]:
redirect_to = None
self.run_method("set_as_paid")
self.set_as_paid()
# if shopping cart enabled and in session
if (shopping_cart_settings.enabled and hasattr(frappe.local, "session")

View File

@@ -1,4 +1,5 @@
{
"actions": [],
"allow_rename": 1,
"autoname": "Prompt",
"creation": "2013-05-24 12:15:51",
@@ -22,6 +23,7 @@
"allow_user_to_edit_discount",
"allow_print_before_pay",
"display_items_in_stock",
"hide_unavailable_items",
"section_break_15",
"applicable_for_users",
"section_break_11",
@@ -389,11 +391,18 @@
"fieldtype": "Link",
"label": "Tax Category",
"options": "Tax Category"
},
{
"default": "0",
"fieldname": "hide_unavailable_items",
"fieldtype": "Check",
"label": "Hide Unavailable Items"
}
],
"icon": "icon-cog",
"idx": 1,
"modified": "2020-01-24 15:52:03.797701",
"links": [],
"modified": "2020-10-16 04:33:57.283873",
"modified_by": "Administrator",
"module": "Accounts",
"name": "POS Profile",

View File

@@ -115,6 +115,8 @@ def get_item_groups(pos_profile):
def get_series():
return frappe.get_meta("Sales Invoice").get_field("naming_series").options or ""
@frappe.whitelist()
@frappe.validate_and_sanitize_search_inputs
def pos_profile_query(doctype, txt, searchfield, start, page_len, filters):
user = frappe.session['user']
company = filters.get('company') or frappe.defaults.get_user_default('company')

View File

@@ -29,27 +29,29 @@ class TestPOSProfile(unittest.TestCase):
frappe.db.sql("delete from `tabPOS Profile`")
def make_pos_profile():
def make_pos_profile(**args):
frappe.db.sql("delete from `tabPOS Profile`")
args = frappe._dict(args)
pos_profile = frappe.get_doc({
"company": "_Test Company",
"cost_center": "_Test Cost Center - _TC",
"currency": "INR",
"company": args.company or "_Test Company",
"cost_center": args.cost_center or "_Test Cost Center - _TC",
"currency": args.currency or "INR",
"doctype": "POS Profile",
"expense_account": "_Test Account Cost for Goods Sold - _TC",
"income_account": "Sales - _TC",
"name": "_Test POS Profile",
"expense_account": args.expense_account or "_Test Account Cost for Goods Sold - _TC",
"income_account": args.income_account or "Sales - _TC",
"name": args.name or "_Test POS Profile",
"naming_series": "_T-POS Profile-",
"selling_price_list": "_Test Price List",
"territory": "_Test Territory",
"selling_price_list": args.selling_price_list or "_Test Price List",
"territory": args.territory or "_Test Territory",
"customer_group": frappe.db.get_value('Customer Group', {'is_group': 0}, 'name'),
"warehouse": "_Test Warehouse - _TC",
"write_off_account": "_Test Write Off - _TC",
"write_off_cost_center": "_Test Write Off Cost Center - _TC"
"warehouse": args.warehouse or "_Test Warehouse - _TC",
"write_off_account": args.write_off_account or "_Test Write Off - _TC",
"write_off_cost_center": args.write_off_cost_center or "_Test Write Off Cost Center - _TC"
})
if not frappe.db.exists("POS Profile", "_Test POS Profile"):
if not frappe.db.exists("POS Profile", args.name or "_Test POS Profile"):
pos_profile.insert()
return pos_profile

View File

@@ -1,123 +1,39 @@
{
"allow_copy": 0,
"allow_guest_to_view": 0,
"allow_import": 0,
"allow_rename": 0,
"beta": 0,
"creation": "2017-10-27 16:46:06.060930",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "",
"editable_grid": 1,
"engine": "InnoDB",
"actions": [],
"creation": "2017-10-27 16:46:06.060930",
"doctype": "DocType",
"editable_grid": 1,
"engine": "InnoDB",
"field_order": [
"default",
"user"
],
"fields": [
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "default",
"fieldtype": "Check",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Default",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
"default": "0",
"fieldname": "default",
"fieldtype": "Check",
"in_list_view": 1,
"label": "Default"
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "user",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "User",
"length": 0,
"no_copy": 0,
"options": "User",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"unique": 0
"fieldname": "user",
"fieldtype": "Link",
"in_list_view": 1,
"label": "User",
"options": "User"
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 0,
"idx": 0,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 0,
"max_attachments": 0,
"modified": "2017-11-23 17:13:16.005475",
"modified_by": "Administrator",
"module": "Accounts",
"name": "POS Profile User",
"name_case": "",
"owner": "Administrator",
"permissions": [
{
"amend": 0,
"apply_user_permissions": 0,
"cancel": 0,
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 1,
"read": 1,
"report": 1,
"role": "System Manager",
"set_user_permissions": 0,
"share": 1,
"submit": 0,
"write": 1
}
],
"quick_entry": 1,
"read_only": 0,
"read_only_onload": 0,
"show_name_in_global_search": 0,
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 1,
"track_seen": 0
],
"istable": 1,
"links": [],
"modified": "2020-10-16 04:33:27.594859",
"modified_by": "Administrator",
"module": "Accounts",
"name": "POS Profile User",
"owner": "Administrator",
"permissions": [],
"quick_entry": 1,
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 1
}

View File

@@ -404,6 +404,7 @@
"fieldtype": "Column Break"
},
{
"default": "0",
"depends_on": "eval:doc.rate_or_discount==\"Rate\"",
"fieldname": "rate",
"fieldtype": "Currency",
@@ -467,6 +468,7 @@
"options": "UOM"
},
{
"description": "If rate is zero them item will be treated as \"Free Item\"",
"fieldname": "free_item_rate",
"fieldtype": "Currency",
"label": "Rate"
@@ -554,7 +556,8 @@
],
"icon": "fa fa-gift",
"idx": 1,
"modified": "2019-12-18 17:29:22.957077",
"links": [],
"modified": "2020-12-04 00:36:24.698219",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Pricing Rule",

View File

@@ -17,6 +17,8 @@ from six import string_types
apply_on_dict = {"Item Code": "items",
"Item Group": "item_groups", "Brand": "brands"}
other_fields = ["other_item_code", "other_item_group", "other_brand"]
class PricingRule(Document):
def validate(self):
self.validate_mandatory()
@@ -47,9 +49,17 @@ class PricingRule(Document):
if self.apply_on == apply_on and len(self.get(field) or []) < 1:
throw(_("{0} is not added in the table").format(apply_on), frappe.MandatoryError)
tocheck = frappe.scrub(self.get("applicable_for", ""))
if tocheck and not self.get(tocheck):
throw(_("{0} is required").format(self.meta.get_label(tocheck)), frappe.MandatoryError)
if self.get("applicable_for", "") is not None:
tocheck = frappe.scrub(self.get("applicable_for", ""))
if tocheck and not self.get(tocheck):
throw(_("{0} is required").format(self.meta.get_label(tocheck)), frappe.MandatoryError)
if self.apply_rule_on_other:
o_field = 'other_' + frappe.scrub(self.apply_rule_on_other)
if not self.get(o_field) and o_field in other_fields:
frappe.throw(_("For the 'Apply Rule On Other' condition the field {0} is mandatory")
.format(frappe.bold(self.apply_rule_on_other)))
if self.price_or_product_discount == 'Price' and not self.rate_or_discount:
throw(_("Rate or Discount is required for the price discount."), frappe.MandatoryError)
@@ -84,13 +94,27 @@ class PricingRule(Document):
for f in options:
if not f: continue
f = frappe.scrub(f)
if f!=fieldname:
self.set(f, None)
scrubbed_f = frappe.scrub(f)
if logic_field == 'apply_on':
apply_on_f = apply_on_dict.get(f, f)
else:
apply_on_f = scrubbed_f
if scrubbed_f != fieldname:
self.set(apply_on_f, None)
if self.mixed_conditions and self.get("same_item"):
self.same_item = 0
apply_rule_on_other = frappe.scrub(self.apply_rule_on_other or "")
cleanup_other_fields = (other_fields if not apply_rule_on_other
else [o_field for o_field in other_fields if o_field != 'other_' + apply_rule_on_other])
for other_field in cleanup_other_fields:
self.set(other_field, None)
def validate_rate_or_discount(self):
for field in ["Rate"]:
if flt(self.get(frappe.scrub(field))) < 0:
@@ -218,7 +242,7 @@ def get_pricing_rule_for_item(args, price_list_rate=0, doc=None, for_validate=Fa
update_args_for_pricing_rule(args)
pricing_rules = (get_applied_pricing_rules(args)
pricing_rules = (get_applied_pricing_rules(args.get('pricing_rules'))
if for_validate and args.get("pricing_rules") else get_pricing_rules(args, doc))
if pricing_rules:
@@ -248,7 +272,7 @@ def get_pricing_rule_for_item(args, price_list_rate=0, doc=None, for_validate=Fa
if pricing_rule.coupon_code_based==1 and args.coupon_code==None:
return item_details
if not pricing_rule.validate_applied_rule:
if pricing_rule.price_or_product_discount == "Price":
apply_price_discount_rule(pricing_rule, item_details, args)
@@ -257,7 +281,7 @@ def get_pricing_rule_for_item(args, price_list_rate=0, doc=None, for_validate=Fa
item_details.has_pricing_rule = 1
item_details.pricing_rules = ','.join([d.pricing_rule for d in rules])
item_details.pricing_rules = frappe.as_json([d.pricing_rule for d in rules])
if not doc: return item_details
@@ -318,8 +342,14 @@ def apply_price_discount_rule(pricing_rule, item_details, args):
pricing_rule_rate = 0.0
if pricing_rule.currency == args.currency:
pricing_rule_rate = pricing_rule.rate
if pricing_rule_rate:
# Override already set price list rate (from item price)
# if pricing_rule_rate > 0
item_details.update({
"price_list_rate": pricing_rule_rate * args.get("conversion_factor", 1),
})
item_details.update({
"price_list_rate": pricing_rule_rate * args.get("conversion_factor", 1),
"discount_percentage": 0.0
})
@@ -346,8 +376,10 @@ def set_discount_amount(rate, item_details):
item_details.rate = rate
def remove_pricing_rule_for_item(pricing_rules, item_details, item_code=None):
from erpnext.accounts.doctype.pricing_rule.utils import get_pricing_rule_items
for d in pricing_rules.split(','):
from erpnext.accounts.doctype.pricing_rule.utils import (get_applied_pricing_rules,
get_pricing_rule_items)
for d in get_applied_pricing_rules(pricing_rules):
if not d or not frappe.db.exists("Pricing Rule", d): continue
pricing_rule = frappe.get_cached_doc('Pricing Rule', d)
@@ -370,7 +402,8 @@ def remove_pricing_rule_for_item(pricing_rules, item_details, item_code=None):
items = get_pricing_rule_items(pricing_rule)
item_details.apply_on = (frappe.scrub(pricing_rule.apply_rule_on_other)
if pricing_rule.apply_rule_on_other else frappe.scrub(pricing_rule.get('apply_on')))
item_details.applied_on_items = ','.join(items)
item_details.applied_on_items = json.dumps(items)
item_details.price_or_product_discount = pricing_rule.price_or_product_discount
item_details.pricing_rules = ''
@@ -413,14 +446,15 @@ def make_pricing_rule(doctype, docname):
return doc
@frappe.whitelist()
@frappe.validate_and_sanitize_search_inputs
def get_item_uoms(doctype, txt, searchfield, start, page_len, filters):
items = [filters.get('value')]
if filters.get('apply_on') != 'Item Code':
field = frappe.scrub(filters.get('apply_on'))
items = [d.name for d in frappe.db.get_all("Item", filters={field: filters.get('value')})]
items = frappe.db.sql_list("""select name
from `tabItem` where {0} = %s""".format(field), filters.get('value'))
return frappe.get_all('UOM Conversion Detail',
filters = {'parent': ('in', items), 'uom': ("like", "{0}%".format(txt))},
fields = ["distinct uom"], as_list=1)
return frappe.get_all('UOM Conversion Detail', filters={
'parent': ('in', items),
'uom': ("like", "{0}%".format(txt))
}, fields = ["distinct uom"], as_list=1)

View File

@@ -385,7 +385,7 @@ class TestPricingRule(unittest.TestCase):
so.load_from_db()
self.assertEqual(so.items[1].is_free_item, 1)
self.assertEqual(so.items[1].item_code, "_Test Item 2")
def test_cumulative_pricing_rule(self):
frappe.delete_doc_if_exists('Pricing Rule', '_Test Cumulative Pricing Rule')
test_record = {
@@ -430,6 +430,59 @@ class TestPricingRule(unittest.TestCase):
self.assertTrue(details)
def test_item_price_with_pricing_rule(self):
item = make_item("Water Flask")
make_item_price("Water Flask", "_Test Price List", 100)
pricing_rule_record = {
"doctype": "Pricing Rule",
"title": "_Test Water Flask Rule",
"apply_on": "Item Code",
"items": [{
"item_code": "Water Flask",
}],
"selling": 1,
"currency": "INR",
"rate_or_discount": "Rate",
"rate": 0,
"margin_type": "Percentage",
"margin_rate_or_amount": 2,
"company": "_Test Company"
}
rule = frappe.get_doc(pricing_rule_record)
rule.insert()
si = create_sales_invoice(do_not_save=True, item_code="Water Flask")
si.selling_price_list = "_Test Price List"
si.save()
# If rate in Rule is 0, give preference to Item Price if it exists
self.assertEqual(si.items[0].price_list_rate, 100)
self.assertEqual(si.items[0].margin_rate_or_amount, 2)
self.assertEqual(si.items[0].rate_with_margin, 102)
self.assertEqual(si.items[0].rate, 102)
si.delete()
rule.delete()
frappe.get_doc("Item Price", {"item_code": "Water Flask"}).delete()
item.delete()
def test_pricing_rule_for_transaction(self):
make_item("Water Flask 1")
frappe.delete_doc_if_exists('Pricing Rule', '_Test Pricing Rule')
make_pricing_rule(selling=1, min_qty=5, price_or_product_discount="Product",
apply_on="Transaction", free_item="Water Flask 1", free_qty=1, free_item_rate=10)
si = create_sales_invoice(qty=5, do_not_submit=True)
self.assertEquals(len(si.items), 2)
self.assertEquals(si.items[1].rate, 10)
si1 = create_sales_invoice(qty=2, do_not_submit=True)
self.assertEquals(len(si1.items), 1)
for doc in [si, si1]:
doc.delete()
def make_pricing_rule(**args):
args = frappe._dict(args)
@@ -447,15 +500,23 @@ def make_pricing_rule(**args):
"rate_or_discount": args.rate_or_discount or "Discount Percentage",
"discount_percentage": args.discount_percentage or 0.0,
"rate": args.rate or 0.0,
"margin_type": args.margin_type,
"margin_rate_or_amount": args.margin_rate_or_amount or 0.0
"margin_rate_or_amount": args.margin_rate_or_amount or 0.0,
"condition": args.condition or '',
"apply_multiple_pricing_rules": args.apply_multiple_pricing_rules or 0
})
for field in ["free_item", "free_qty", "free_item_rate", "priority",
"margin_type", "price_or_product_discount"]:
if args.get(field):
doc.set(field, args.get(field))
apply_on = doc.apply_on.replace(' ', '_').lower()
child_table = {'Item Code': 'items', 'Item Group': 'item_groups', 'Brand': 'brands'}
doc.append(child_table.get(doc.apply_on), {
apply_on: args.get(apply_on) or "_Test Item"
})
if doc.apply_on != "Transaction":
doc.append(child_table.get(doc.apply_on), {
apply_on: args.get(apply_on) or "_Test Item"
})
doc.insert(ignore_permissions=True)
if args.get(apply_on) and apply_on != "item_code":

View File

@@ -11,6 +11,7 @@ import json
from six import string_types
import frappe
from erpnext.accounts.doctype.pricing_rule.pricing_rule import set_transaction_type
from erpnext.setup.doctype.item_group.item_group import get_child_item_groups
from erpnext.stock.doctype.warehouse.warehouse import get_child_warehouses
from erpnext.stock.get_item_details import get_conversion_factor, get_default_income_account
@@ -30,13 +31,19 @@ apply_on_table = {
}
def get_pricing_rules(args, doc=None):
pricing_rules = []
values = {}
pricing_rules_all = []
values = {}
for apply_on in ['Item Code', 'Item Group', 'Brand']:
pricing_rules.extend(_get_pricing_rules(apply_on, args, values))
if pricing_rules and not apply_multiple_pricing_rules(pricing_rules):
break
pricing_rules_all.extend(_get_pricing_rules(apply_on, args, values))
# removing duplicate pricing rule
pricing_rules_name = []
pricing_rules = []
for p in pricing_rules_all:
if p['name'] not in pricing_rules_name:
pricing_rules_name.append(p['name'])
pricing_rules.append(p)
rules = []
@@ -322,7 +329,10 @@ def apply_internal_priority(pricing_rules, field_set, args):
filtered_rules = []
for field in field_set:
if args.get(field):
filtered_rules = filter(lambda x: x[field]==args[field], pricing_rules)
for rule in pricing_rules:
if rule.get(field) == args.get(field):
filtered_rules = [rule]
break
if filtered_rules: break
return filtered_rules or pricing_rules
@@ -416,14 +426,36 @@ def apply_pricing_rule_on_transaction(doc):
values = {}
conditions = get_other_conditions(conditions, values, doc)
pricing_rules = frappe.db.sql(""" Select `tabPricing Rule`.* from `tabPricing Rule`
where {conditions} and `tabPricing Rule`.disable = 0
""".format(conditions = conditions), values, as_dict=1)
args = frappe._dict({
'doctype': doc.doctype,
'transaction_type': None,
})
set_transaction_type(args)
tran_type_condition = '{} = 1'.format(args.transaction_type)
sql = """
SELECT
`tabPricing Rule`.*
FROM
`tabPricing Rule`
WHERE
{conditions} and
{tran_type_condition} and
`tabPricing Rule`.disable = 0
""".format(
conditions=conditions,
tran_type_condition=tran_type_condition,
)
pricing_rules = frappe.db.sql(sql, values, as_dict=1)
if pricing_rules:
pricing_rules = filter_pricing_rules_for_qty_amount(doc.total_qty,
doc.total, pricing_rules)
if not pricing_rules:
remove_free_item(doc)
for d in pricing_rules:
if d.price_or_product_discount == 'Price':
if d.apply_discount_on:
@@ -447,14 +479,25 @@ def apply_pricing_rule_on_transaction(doc):
get_product_discount_rule(d, item_details, doc=doc)
apply_pricing_rule_for_free_items(doc, item_details.free_item_data)
doc.set_missing_values()
doc.calculate_taxes_and_totals()
def get_applied_pricing_rules(item_row):
return (item_row.get("pricing_rules").split(',')
if item_row.get("pricing_rules") else [])
def remove_free_item(doc):
for d in doc.items:
if d.is_free_item:
doc.remove(d)
def get_applied_pricing_rules(pricing_rules):
if pricing_rules:
if pricing_rules.startswith('['):
return json.loads(pricing_rules)
else:
return pricing_rules.split(',')
return []
def get_product_discount_rule(pricing_rule, item_details, args=None, doc=None):
free_item = pricing_rule.free_item
if pricing_rule.same_item:
if pricing_rule.same_item and pricing_rule.get("apply_on") != 'Transaction':
free_item = item_details.item_code or args.item_code
if not free_item:
@@ -483,13 +526,17 @@ def get_product_discount_rule(pricing_rule, item_details, args=None, doc=None):
if item_details.get("parenttype") == 'Sales Order':
item_details.free_item_data['delivery_date'] = doc.delivery_date if doc else today()
company = args.get('company') or doc.company
item_details.free_item_data['income_account'] = get_default_income_account(
args=args,
item=get_item_defaults(free_item, company),
item_group=get_item_group_defaults(free_item, company),
brand=get_brand_defaults(free_item, company),
)
company = doc.company
if args and args.get("company"):
company = args.get("company")
if args:
item_details.free_item_data['income_account'] = get_default_income_account(
args=args,
item=get_item_defaults(free_item, company),
item_group=get_item_group_defaults(free_item, company),
brand=get_brand_defaults(free_item, company),
)
def apply_pricing_rule_for_free_items(doc, pricing_rule_args, set_missing_values=False):
if pricing_rule_args.get('item_code'):

View File

@@ -1,5 +1,4 @@
{
"actions": [],
"allow_import": 1,
"autoname": "naming_series:",
"creation": "2013-05-21 16:16:39",
@@ -26,6 +25,7 @@
"accounting_dimensions_section",
"cost_center",
"dimension_col_break",
"project",
"sb_14",
"on_hold",
"release_date",
@@ -356,6 +356,7 @@
"fieldname": "bill_date",
"fieldtype": "Date",
"label": "Supplier Invoice Date",
"no_copy": 1,
"oldfieldname": "bill_date",
"oldfieldtype": "Date",
"print_hide": 1
@@ -963,8 +964,10 @@
{
"fieldname": "clearance_date",
"fieldtype": "Date",
"hidden": 1,
"label": "Clearance Date"
"label": "Clearance Date",
"no_copy": 1,
"print_hide": 1,
"read_only": 1
},
{
"fieldname": "col_br_payments",
@@ -1233,6 +1236,7 @@
"print_hide": 1
},
{
"collapsible": 1,
"fieldname": "subscription_section",
"fieldtype": "Section Break",
"label": "Subscription Section",
@@ -1286,6 +1290,12 @@
"fieldname": "dimension_col_break",
"fieldtype": "Column Break"
},
{
"fieldname": "project",
"fieldtype": "Link",
"label": "Project",
"options": "Project"
},
{
"fieldname": "tax_withholding_category",
"fieldtype": "Link",
@@ -1298,8 +1308,7 @@
"icon": "fa fa-file-text",
"idx": 204,
"is_submittable": 1,
"links": [],
"modified": "2020-04-18 13:05:25.199832",
"modified": "2020-09-21 12:22:09.164068",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Purchase Invoice",

View File

@@ -142,6 +142,11 @@ class PurchaseInvoice(BuyingController):
throw(_("Conversion rate cannot be 0 or 1"))
def validate_credit_to_acc(self):
if not self.credit_to:
self.credit_to = get_party_account("Supplier", self.supplier, self.company)
if not self.credit_to:
self.raise_missing_debit_credit_account_error("Supplier", self.supplier)
account = frappe.db.get_value("Account", self.credit_to,
["account_type", "report_type", "account_currency"], as_dict=True)
@@ -413,6 +418,8 @@ class PurchaseInvoice(BuyingController):
self.make_tax_gl_entries(gl_entries)
gl_entries = make_regional_gl_entries(gl_entries, self)
gl_entries = merge_similar_entries(gl_entries)
self.make_payment_gl_entries(gl_entries)
@@ -451,7 +458,8 @@ class PurchaseInvoice(BuyingController):
if self.party_account_currency==self.company_currency else grand_total,
"against_voucher": self.return_against if cint(self.is_return) and self.return_against else self.name,
"against_voucher_type": self.doctype,
"cost_center": self.cost_center
"cost_center": self.cost_center,
"project": self.project
}, self.party_account_currency, item=self)
)
@@ -492,7 +500,7 @@ class PurchaseInvoice(BuyingController):
"debit": warehouse_debit_amount,
"remarks": self.get("remarks") or _("Accounting Entry for Stock"),
"cost_center": item.cost_center,
"project": item.project
"project": item.project or self.project
}, account_currency, item=item)
)
@@ -505,7 +513,7 @@ class PurchaseInvoice(BuyingController):
"cost_center": item.cost_center,
"remarks": self.get("remarks") or _("Accounting Entry for Stock"),
"credit": flt(amount),
"project": item.project
"project": item.project or self.project
}, item=item))
# sub-contracting warehouse
@@ -518,6 +526,7 @@ class PurchaseInvoice(BuyingController):
"account": supplier_warehouse_account,
"against": item.expense_account,
"cost_center": item.cost_center,
"project": item.project or self.project,
"remarks": self.get("remarks") or _("Accounting Entry for Stock"),
"credit": flt(item.rm_supp_cost)
}, warehouse_account[self.supplier_warehouse]["account_currency"], item=item))
@@ -536,7 +545,7 @@ class PurchaseInvoice(BuyingController):
"against": self.supplier,
"debit": amount,
"cost_center": item.cost_center,
"project": item.project
"project": item.project or self.project
}, account_currency, item=item))
# If asset is bought through this document and not linked to PR
@@ -549,7 +558,7 @@ class PurchaseInvoice(BuyingController):
"cost_center": item.cost_center,
"remarks": self.get("remarks") or _("Accounting Entry for Stock"),
"credit": flt(item.landed_cost_voucher_amount),
"project": item.project
"project": item.project or self.project
}, item=item))
gl_entries.append(self.get_gl_dict({
@@ -558,7 +567,7 @@ class PurchaseInvoice(BuyingController):
"cost_center": item.cost_center,
"remarks": self.get("remarks") or _("Accounting Entry for Stock"),
"debit": flt(item.landed_cost_voucher_amount),
"project": item.project
"project": item.project or self.project
}, item=item))
# update gross amount of asset bought through this document
@@ -584,7 +593,8 @@ class PurchaseInvoice(BuyingController):
"against": self.supplier,
"debit": flt(item.item_tax_amount, item.precision("item_tax_amount")),
"remarks": self.remarks or "Accounting Entry for Stock",
"cost_center": self.cost_center
"cost_center": self.cost_center,
"project": item.project or self.project
}, item=item)
)
@@ -613,7 +623,8 @@ class PurchaseInvoice(BuyingController):
"debit": base_asset_amount,
"debit_in_account_currency": (base_asset_amount
if arbnb_currency == self.company_currency else asset_amount),
"cost_center": item.cost_center
"cost_center": item.cost_center,
"project": item.project or self.project
}, item=item))
if item.item_tax_amount:
@@ -623,13 +634,15 @@ class PurchaseInvoice(BuyingController):
"against": self.supplier,
"remarks": self.get("remarks") or _("Accounting Entry for Asset"),
"cost_center": item.cost_center,
"project": item.project or self.project,
"credit": item.item_tax_amount,
"credit_in_account_currency": (item.item_tax_amount
if asset_eiiav_currency == self.company_currency else
item.item_tax_amount / self.conversion_rate)
}, item=item))
else:
cwip_account = get_asset_account("capital_work_in_progress_account", company = self.company)
cwip_account = get_asset_account("capital_work_in_progress_account",
asset_category=item.asset_category,company=self.company)
cwip_account_currency = get_account_currency(cwip_account)
gl_entries.append(self.get_gl_dict({
@@ -639,7 +652,8 @@ class PurchaseInvoice(BuyingController):
"debit": base_asset_amount,
"debit_in_account_currency": (base_asset_amount
if cwip_account_currency == self.company_currency else asset_amount),
"cost_center": self.cost_center
"cost_center": self.cost_center,
"project": item.project or self.project
}, item=item))
if item.item_tax_amount and not cint(erpnext.is_perpetual_inventory_enabled(self.company)):
@@ -650,6 +664,7 @@ class PurchaseInvoice(BuyingController):
"remarks": self.get("remarks") or _("Accounting Entry for Asset"),
"cost_center": item.cost_center,
"credit": item.item_tax_amount,
"project": item.project or self.project,
"credit_in_account_currency": (item.item_tax_amount
if asset_eiiav_currency == self.company_currency else
item.item_tax_amount / self.conversion_rate)
@@ -665,7 +680,7 @@ class PurchaseInvoice(BuyingController):
"cost_center": item.cost_center,
"remarks": self.get("remarks") or _("Accounting Entry for Stock"),
"credit": flt(item.landed_cost_voucher_amount),
"project": item.project
"project": item.project or self.project
}, item=item))
gl_entries.append(self.get_gl_dict({
@@ -674,7 +689,7 @@ class PurchaseInvoice(BuyingController):
"cost_center": item.cost_center,
"remarks": self.get("remarks") or _("Accounting Entry for Stock"),
"debit": flt(item.landed_cost_voucher_amount),
"project": item.project
"project": item.project or self.project
}, item=item))
# update gross amount of assets bought through this document
@@ -709,7 +724,7 @@ class PurchaseInvoice(BuyingController):
"debit": stock_adjustment_amt,
"remarks": self.get("remarks") or _("Stock Adjustment"),
"cost_center": item.cost_center,
"project": item.project
"project": item.project or self.project
}, account_currency, item=item)
)
@@ -801,7 +816,8 @@ class PurchaseInvoice(BuyingController):
if self.party_account_currency==self.company_currency else self.paid_amount,
"against_voucher": self.return_against if cint(self.is_return) and self.return_against else self.name,
"against_voucher_type": self.doctype,
"cost_center": self.cost_center
"cost_center": self.cost_center,
"project": self.project
}, self.party_account_currency, item=self)
)
@@ -833,7 +849,8 @@ class PurchaseInvoice(BuyingController):
if self.party_account_currency==self.company_currency else self.write_off_amount,
"against_voucher": self.return_against if cint(self.is_return) and self.return_against else self.name,
"against_voucher_type": self.doctype,
"cost_center": self.cost_center
"cost_center": self.cost_center,
"project": self.project
}, self.party_account_currency, item=self)
)
gl_entries.append(
@@ -980,7 +997,7 @@ class PurchaseInvoice(BuyingController):
# calculate totals again after applying TDS
self.calculate_taxes_and_totals()
def set_status(self, update=False, status=None, update_modified=True):
if self.is_new():
if self.get('amended_from'):
@@ -1026,6 +1043,10 @@ def get_list_context(context=None):
})
return list_context
@erpnext.allow_regional
def make_regional_gl_entries(gl_entries, doc):
return gl_entries
@frappe.whitelist()
def make_debit_note(source_name, target_doc=None):
from erpnext.controllers.sales_and_purchase_return import make_return_doc

View File

@@ -16,7 +16,7 @@ frappe.listview_settings['Purchase Invoice'] = {
} else if(frappe.datetime.get_diff(doc.due_date) < 0) {
return [__("Overdue"), "red", "outstanding_amount,>,0|due_date,<,Today"];
} else {
return [__("Unpaid"), "orange", "outstanding_amount,>,0|due,>=,Today"];
return [__("Unpaid"), "orange", "outstanding_amount,>,0|due_date,>=,Today"];
}
} else if(cint(doc.is_return)) {
return [__("Return"), "darkgrey", "is_return,=,Yes"];

View File

@@ -15,6 +15,7 @@ from erpnext.controllers.accounts_controller import get_payment_terms
from erpnext.exceptions import InvalidCurrency
from erpnext.stock.doctype.stock_entry.test_stock_entry import get_qty_after_transaction
from erpnext.accounts.doctype.account.test_account import get_inventory_account
from erpnext.projects.doctype.project.test_project import make_project
test_dependencies = ["Item", "Cost Center", "Payment Term", "Payment Terms Template"]
test_ignore = ["Serial No"]
@@ -434,6 +435,8 @@ class TestPurchaseInvoice(unittest.TestCase):
)
def test_total_purchase_cost_for_project(self):
make_project({'project_name':'_Test Project'})
existing_purchase_cost = frappe.db.sql("""select sum(base_net_amount)
from `tabPurchase Invoice Item` where project = '_Test Project' and docstatus=1""")
existing_purchase_cost = existing_purchase_cost and existing_purchase_cost[0][0] or 0
@@ -807,11 +810,8 @@ class TestPurchaseInvoice(unittest.TestCase):
pi_doc = frappe.get_doc('Purchase Invoice', pi.name)
self.assertEqual(pi_doc.outstanding_amount, 0)
def test_purchase_invoice_for_enable_allow_cost_center_in_entry_of_bs_account(self):
def test_purchase_invoice_with_cost_center(self):
from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center
accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings')
accounts_settings.allow_cost_center_in_entry_of_bs_account = 1
accounts_settings.save()
cost_center = "_Test Cost Center for BS Account - _TC"
create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company")
@@ -837,13 +837,7 @@ class TestPurchaseInvoice(unittest.TestCase):
for gle in gl_entries:
self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center)
accounts_settings.allow_cost_center_in_entry_of_bs_account = 0
accounts_settings.save()
def test_purchase_invoice_for_disable_allow_cost_center_in_entry_of_bs_account(self):
accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings')
accounts_settings.allow_cost_center_in_entry_of_bs_account = 0
accounts_settings.save()
def test_purchase_invoice_without_cost_center(self):
cost_center = "_Test Cost Center - _TC"
pi = make_purchase_invoice(credit_to="Creditors - _TC")
@@ -866,6 +860,42 @@ class TestPurchaseInvoice(unittest.TestCase):
for gle in gl_entries:
self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center)
def test_purchase_invoice_with_project_link(self):
project = make_project({
'project_name': 'Purchase Invoice Project',
'project_template_name': 'Test Project Template',
'start_date': '2020-01-01'
})
item_project = make_project({
'project_name': 'Purchase Invoice Item Project',
'project_template_name': 'Test Project Template',
'start_date': '2019-06-01'
})
pi = make_purchase_invoice(credit_to="Creditors - _TC" ,do_not_save=1)
pi.items[0].project = item_project.project_name
pi.project = project.project_name
pi.submit()
expected_values = {
"Creditors - _TC": {
"project": project.project_name
},
"_Test Account Cost for Goods Sold - _TC": {
"project": item_project.project_name
}
}
gl_entries = frappe.db.sql("""select account, cost_center, project, account_currency, debit, credit,
debit_in_account_currency, credit_in_account_currency
from `tabGL Entry` where voucher_type='Purchase Invoice' and voucher_no=%s
order by account asc""", pi.name, as_dict=1)
self.assertTrue(gl_entries)
for gle in gl_entries:
self.assertEqual(expected_values[gle.account]["project"], gle.project)
def unlink_payment_on_cancel_of_invoice(enable=1):
accounts_settings = frappe.get_doc("Accounts Settings")
@@ -909,7 +939,8 @@ def make_purchase_invoice(**args):
"cost_center": args.cost_center or "_Test Cost Center - _TC",
"project": args.project,
"rejected_warehouse": args.rejected_warehouse or "",
"rejected_serial_no": args.rejected_serial_no or ""
"rejected_serial_no": args.rejected_serial_no or "",
"asset_location": args.location or ""
})
if args.get_taxes_and_charges:

View File

@@ -1,5 +1,4 @@
{
"actions": [],
"autoname": "hash",
"creation": "2013-05-22 12:43:10",
"doctype": "DocType",
@@ -86,6 +85,7 @@
"item_tax_rate",
"bom",
"include_exploded_items",
"purchase_invoice_item",
"col_break6",
"purchase_order",
"po_detail",
@@ -764,12 +764,21 @@
"label": "Asset Category",
"options": "Asset Category",
"read_only": 1
},
{
"depends_on": "eval:parent.update_stock == 1",
"fieldname": "purchase_invoice_item",
"fieldtype": "Data",
"ignore_user_permissions": 1,
"label": "Purchase Invoice Item",
"no_copy": 1,
"print_hide": 1,
"read_only": 1
}
],
"idx": 1,
"istable": 1,
"links": [],
"modified": "2020-04-07 18:34:35.104178",
"modified": "2020-06-30 16:48:01.398356",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Purchase Invoice Item",

View File

@@ -175,6 +175,13 @@ def get_items_list(pos_profile, company):
if args_list:
cond = "and i.item_group in (%s)" % (', '.join(['%s'] * len(args_list)))
bin_join = bin_cond = ""
if pos_profile.get('hide_unavailable_items'):
bin_join = ",`tabBin` b"
bin_cond = "and i.item_code = b.item_code and ifnull(b.actual_qty, 0) > 0 "
if pos_profile.get('warehouse'):
bin_cond += "and b.warehouse = {}".format(frappe.db.escape(pos_profile.get('warehouse')))
return frappe.db.sql("""
select
i.name, i.item_code, i.item_name, i.description, i.item_group, i.has_batch_no,
@@ -186,11 +193,13 @@ def get_items_list(pos_profile, company):
left join `tabItem Default` id on id.parent = i.name and id.company = %s
left join `tabItem Tax` it on it.parent = i.name
left join `tabUOM Conversion Detail` c on i.name = c.parent and i.sales_uom = c.uom
{bin_join}
where
i.disabled = 0 and i.has_variants = 0 and i.is_sales_item = 1
{cond}
{bin_cond}
group by i.item_code
""".format(cond=cond), tuple([company] + args_list), as_dict=1)
""".format(cond=cond, bin_join=bin_join, bin_cond=bin_cond), tuple([company] + args_list), as_dict=1)
def get_item_groups(pos_profile):

View File

@@ -1,5 +1,4 @@
{
"actions": [],
"allow_import": 1,
"autoname": "naming_series:",
"creation": "2013-05-24 19:29:05",
@@ -1494,6 +1493,7 @@
"print_hide": 1
},
{
"collapsible": 1,
"fieldname": "subscription_section",
"fieldtype": "Section Break",
"label": "Subscription Section"
@@ -1569,8 +1569,7 @@
"icon": "fa fa-file-text",
"idx": 181,
"is_submittable": 1,
"links": [],
"modified": "2020-05-19 17:00:57.208696",
"modified": "2020-07-01 12:41:29.484813",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Sales Invoice",

View File

@@ -398,6 +398,8 @@ class SalesInvoice(SellingController):
from erpnext.stock.get_item_details import get_pos_profile_item_details, get_pos_profile
if not self.pos_profile:
pos_profile = get_pos_profile(self.company) or {}
if not pos_profile:
frappe.throw(_("No POS Profile found. Please create a New POS Profile first"))
self.pos_profile = pos_profile.get('name')
pos = {}
@@ -467,6 +469,11 @@ class SalesInvoice(SellingController):
return frappe.db.sql("select abbr from tabCompany where name=%s", self.company)[0][0]
def validate_debit_to_acc(self):
if not self.debit_to:
self.debit_to = get_party_account("Customer", self.customer, self.company)
if not self.debit_to:
self.raise_missing_debit_credit_account_error("Customer", self.customer)
account = frappe.get_cached_value("Account", self.debit_to,
["account_type", "report_type", "account_currency"], as_dict=True)
@@ -570,7 +577,8 @@ class SalesInvoice(SellingController):
def validate_pos(self):
if self.is_return:
if flt(self.paid_amount) + flt(self.write_off_amount) - flt(self.grand_total) > \
invoice_total = self.rounded_total or self.grand_total
if flt(self.paid_amount) + flt(self.write_off_amount) - flt(invoice_total) > \
1.0/(10.0**(self.precision("grand_total") + 1.0)):
frappe.throw(_("Paid amount + Write Off Amount can not be greater than Grand Total"))
@@ -786,7 +794,8 @@ class SalesInvoice(SellingController):
if self.party_account_currency==self.company_currency else grand_total,
"against_voucher": self.return_against if cint(self.is_return) and self.return_against else self.name,
"against_voucher_type": self.doctype,
"cost_center": self.cost_center
"cost_center": self.cost_center,
"project": self.project
}, self.party_account_currency, item=self)
)
@@ -841,7 +850,8 @@ class SalesInvoice(SellingController):
"credit_in_account_currency": (flt(item.base_net_amount, item.precision("base_net_amount"))
if account_currency==self.company_currency
else flt(item.net_amount, item.precision("net_amount"))),
"cost_center": item.cost_center
"cost_center": item.cost_center,
"project": item.project or self.project
}, account_currency, item=item)
)
@@ -922,7 +932,8 @@ class SalesInvoice(SellingController):
if self.party_account_currency==self.company_currency else flt(self.change_amount),
"against_voucher": self.return_against if cint(self.is_return) and self.return_against else self.name,
"against_voucher_type": self.doctype,
"cost_center": self.cost_center
"cost_center": self.cost_center,
"project": self.project
}, self.party_account_currency, item=self)
)
@@ -955,7 +966,8 @@ class SalesInvoice(SellingController):
else flt(self.write_off_amount, self.precision("write_off_amount"))),
"against_voucher": self.return_against if cint(self.is_return) else self.name,
"against_voucher_type": self.doctype,
"cost_center": self.cost_center
"cost_center": self.cost_center,
"project": self.project
}, self.party_account_currency, item=self)
)
gl_entries.append(
@@ -1105,7 +1117,10 @@ class SalesInvoice(SellingController):
expiry_date=self.posting_date, include_expired_entry=True)
if lp_details and getdate(lp_details.from_date) <= getdate(self.posting_date) and \
(not lp_details.to_date or getdate(lp_details.to_date) >= getdate(self.posting_date)):
points_earned = cint(eligible_amount/lp_details.collection_factor)
collection_factor = lp_details.collection_factor if lp_details.collection_factor else 1.0
points_earned = cint(eligible_amount/collection_factor)
doc = frappe.get_doc({
"doctype": "Loyalty Point Entry",
"company": self.company,
@@ -1387,6 +1402,7 @@ def make_delivery_note(source_name, target_doc=None):
def set_missing_values(source, target):
target.ignore_pricing_rule = 1
target.run_method("set_missing_values")
target.run_method("set_po_nos")
target.run_method("calculate_taxes_and_totals")
def update_item(source_doc, target_doc, source_parent):

View File

@@ -33,4 +33,4 @@ def get_data():
'items': ['Auto Repeat']
},
]
}
}

View File

@@ -3,6 +3,7 @@
"company": "_Test Company",
"conversion_rate": 1.0,
"currency": "INR",
"cost_center": "_Test Cost Center - _TC",
"customer": "_Test Customer",
"customer_name": "_Test Customer",
"debit_to": "_Test Receivable - _TC",
@@ -37,7 +38,8 @@
"charge_type": "On Net Total",
"description": "VAT",
"doctype": "Sales Taxes and Charges",
"parentfield": "taxes",
"parentfield": "taxes",
"cost_center": "_Test Cost Center - _TC",
"rate": 6
},
{
@@ -45,7 +47,8 @@
"charge_type": "On Net Total",
"description": "Service Tax",
"doctype": "Sales Taxes and Charges",
"parentfield": "taxes",
"parentfield": "taxes",
"cost_center": "_Test Cost Center - _TC",
"rate": 6.36
}
],
@@ -76,6 +79,7 @@
"customer_name": "_Test Customer",
"debit_to": "_Test Receivable - _TC",
"doctype": "Sales Invoice",
"cost_center": "_Test Cost Center - _TC",
"items": [
{
"amount": 500.0,
@@ -107,7 +111,8 @@
"charge_type": "On Net Total",
"description": "VAT",
"doctype": "Sales Taxes and Charges",
"parentfield": "taxes",
"parentfield": "taxes",
"cost_center": "_Test Cost Center - _TC",
"rate": 16
},
{
@@ -115,7 +120,8 @@
"charge_type": "On Net Total",
"description": "Service Tax",
"doctype": "Sales Taxes and Charges",
"parentfield": "taxes",
"parentfield": "taxes",
"cost_center": "_Test Cost Center - _TC",
"rate": 10
}
],
@@ -132,6 +138,7 @@
"customer_name": "_Test Customer",
"debit_to": "_Test Receivable - _TC",
"doctype": "Sales Invoice",
"cost_center": "_Test Cost Center - _TC",
"items": [
{
"cost_center": "_Test Cost Center - _TC",
@@ -259,6 +266,7 @@
"customer_name": "_Test Customer",
"debit_to": "_Test Receivable - _TC",
"doctype": "Sales Invoice",
"cost_center": "_Test Cost Center - _TC",
"items": [
{
"cost_center": "_Test Cost Center - _TC",

View File

@@ -206,10 +206,19 @@ class TestSalesInvoice(unittest.TestCase):
"rate": 14,
'included_in_print_rate': 1
})
si.append("taxes", {
"charge_type": "On Item Quantity",
"account_head": "_Test Account Education Cess - _TC",
"cost_center": "_Test Cost Center - _TC",
"description": "CESS",
"rate": 5,
'included_in_print_rate': 1
})
si.insert()
# with inclusive tax
self.assertEqual(si.net_total, 4385.96)
self.assertEqual(si.items[0].net_amount, 3947.368421052631)
self.assertEqual(si.net_total, 3947.37)
self.assertEqual(si.grand_total, 5000)
si.reload()
@@ -222,8 +231,8 @@ class TestSalesInvoice(unittest.TestCase):
si.save()
# with inclusive tax and additional discount
self.assertEqual(si.net_total, 4285.96)
self.assertEqual(si.grand_total, 4885.99)
self.assertEqual(si.net_total, 3847.37)
self.assertEqual(si.grand_total, 4886)
si.reload()
@@ -235,7 +244,7 @@ class TestSalesInvoice(unittest.TestCase):
si.save()
# with inclusive tax and additional discount
self.assertEqual(si.net_total, 4298.25)
self.assertEqual(si.net_total, 3859.65)
self.assertEqual(si.grand_total, 4900.00)
def test_sales_invoice_discount_amount(self):
@@ -681,7 +690,8 @@ class TestSalesInvoice(unittest.TestCase):
self.assertFalse(gle)
def test_pos_gl_entry_with_perpetual_inventory(self):
make_pos_profile()
make_pos_profile(company="_Test Company with perpetual inventory", income_account = "Sales - TCP1",
expense_account = "Cost of Goods Sold - TCP1", warehouse="Stores - TCP1", cost_center = "Main - TCP1", write_off_account="_Test Write Off - TCP1")
pr = make_purchase_receipt(company= "_Test Company with perpetual inventory",supplier_warehouse= "Work In Progress - TCP1", item_code= "_Test FG Item",warehouse= "Stores - TCP1",cost_center= "Main - TCP1")
@@ -705,8 +715,67 @@ class TestSalesInvoice(unittest.TestCase):
self.pos_gl_entry(si, pos, 50)
def test_pos_returns_without_repayment(self):
pos_profile = make_pos_profile()
pos = create_sales_invoice(qty = 10, do_not_save=True)
pos.is_pos = 1
pos.pos_profile = pos_profile.name
pos.append("payments", {'mode_of_payment': 'Bank Draft', 'account': '_Test Bank - _TC', 'amount': 500})
pos.append("payments", {'mode_of_payment': 'Cash', 'account': 'Cash - _TC', 'amount': 500})
pos.insert()
pos.submit()
pos_return = create_sales_invoice(is_return=1,
return_against=pos.name, qty=-5, do_not_save=True)
pos_return.is_pos = 1
pos_return.pos_profile = pos_profile.name
pos_return.insert()
pos_return.submit()
self.assertFalse(pos_return.is_pos)
self.assertFalse(pos_return.get('payments'))
def test_pos_returns_with_repayment(self):
pos_profile = make_pos_profile()
pos_profile.append('payments', {
'default': 1,
'mode_of_payment': 'Cash',
'amount': 0.0
})
pos_profile.save()
pos = create_sales_invoice(qty = 10, do_not_save=True)
pos.is_pos = 1
pos.pos_profile = pos_profile.name
pos.append("payments", {'mode_of_payment': 'Bank Draft', 'account': '_Test Bank - _TC', 'amount': 500})
pos.append("payments", {'mode_of_payment': 'Cash', 'account': 'Cash - _TC', 'amount': 500})
pos.insert()
pos.submit()
pos_return = create_sales_invoice(is_return=1,
return_against=pos.name, qty=-5, do_not_save=True)
pos_return.is_pos = 1
pos_return.pos_profile = pos_profile.name
pos_return.insert()
pos_return.submit()
self.assertEqual(pos_return.get('payments')[0].amount, -500)
pos_profile.payments = []
pos_profile.save()
def test_pos_change_amount(self):
make_pos_profile()
make_pos_profile(company="_Test Company with perpetual inventory", income_account = "Sales - TCP1",
expense_account = "Cost of Goods Sold - TCP1", warehouse="Stores - TCP1", cost_center = "Main - TCP1", write_off_account="_Test Write Off - TCP1")
pr = make_purchase_receipt(company= "_Test Company with perpetual inventory",supplier_warehouse= "Work In Progress - TCP1", item_code= "_Test FG Item",warehouse= "Stores - TCP1",cost_center= "Main - TCP1")
@@ -728,7 +797,8 @@ class TestSalesInvoice(unittest.TestCase):
def test_make_pos_invoice(self):
from erpnext.accounts.doctype.sales_invoice.pos import make_invoice
pos_profile = make_pos_profile()
pos_profile = make_pos_profile(company="_Test Company with perpetual inventory", income_account = "Sales - TCP1",
expense_account = "Cost of Goods Sold - TCP1", warehouse="Stores - TCP1", cost_center = "Main - TCP1", write_off_account="_Test Write Off - TCP1")
pr = make_purchase_receipt(company= "_Test Company with perpetual inventory",supplier_warehouse= "Work In Progress - TCP1", item_code= "_Test FG Item",warehouse= "Stores - TCP1",cost_center= "Main - TCP1")
pos = create_sales_invoice(company= "_Test Company with perpetual inventory", debit_to="Debtors - TCP1", item_code= "_Test FG Item", warehouse="Stores - TCP1", income_account = "Sales - TCP1", expense_account = "Cost of Goods Sold - TCP1", cost_center = "Main - TCP1", do_not_save=True)
@@ -1575,11 +1645,8 @@ class TestSalesInvoice(unittest.TestCase):
si_doc = frappe.get_doc('Sales Invoice', si.name)
self.assertEqual(si_doc.outstanding_amount, 0)
def test_sales_invoice_for_enable_allow_cost_center_in_entry_of_bs_account(self):
def test_sales_invoice_with_cost_center(self):
from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center
accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings')
accounts_settings.allow_cost_center_in_entry_of_bs_account = 1
accounts_settings.save()
cost_center = "_Test Cost Center for BS Account - _TC"
create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company")
@@ -1604,14 +1671,47 @@ class TestSalesInvoice(unittest.TestCase):
for gle in gl_entries:
self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center)
def test_sales_invoice_with_project_link(self):
from erpnext.projects.doctype.project.test_project import make_project
accounts_settings.allow_cost_center_in_entry_of_bs_account = 0
accounts_settings.save()
project = make_project({
'project_name': 'Sales Invoice Project',
'project_template_name': 'Test Project Template',
'start_date': '2020-01-01'
})
item_project = make_project({
'project_name': 'Sales Invoice Item Project',
'project_template_name': 'Test Project Template',
'start_date': '2019-06-01'
})
def test_sales_invoice_for_disable_allow_cost_center_in_entry_of_bs_account(self):
accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings')
accounts_settings.allow_cost_center_in_entry_of_bs_account = 1
accounts_settings.save()
sales_invoice = create_sales_invoice(do_not_save=1)
sales_invoice.items[0].project = item_project.project_name
sales_invoice.project = project.project_name
sales_invoice.submit()
expected_values = {
"Debtors - _TC": {
"project": project.project_name
},
"Sales - _TC": {
"project": item_project.project_name
}
}
gl_entries = frappe.db.sql("""select account, cost_center, project, account_currency, debit, credit,
debit_in_account_currency, credit_in_account_currency
from `tabGL Entry` where voucher_type='Sales Invoice' and voucher_no=%s
order by account asc""", sales_invoice.name, as_dict=1)
self.assertTrue(gl_entries)
for gle in gl_entries:
self.assertEqual(expected_values[gle.account]["project"], gle.project)
def test_sales_invoice_without_cost_center(self):
cost_center = "_Test Cost Center - _TC"
si = create_sales_invoice(debit_to="Debtors - _TC")
@@ -1634,9 +1734,6 @@ class TestSalesInvoice(unittest.TestCase):
for gle in gl_entries:
self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center)
accounts_settings.allow_cost_center_in_entry_of_bs_account = 0
accounts_settings.save()
def test_deferred_revenue(self):
deferred_account = create_account(account_name="Deferred Revenue",
parent_account="Current Liabilities - _TC", company="_Test Company")

View File

@@ -1,5 +1,4 @@
{
"actions": [],
"autoname": "hash",
"creation": "2013-06-04 11:02:19",
"doctype": "DocType",
@@ -87,6 +86,7 @@
"edit_references",
"sales_order",
"so_detail",
"sales_invoice_item",
"column_break_74",
"delivery_note",
"dn_detail",
@@ -94,6 +94,7 @@
"accounting_dimensions_section",
"cost_center",
"dimension_col_break",
"project",
"section_break_54",
"page_break"
],
@@ -783,12 +784,28 @@
"fieldtype": "Link",
"label": "Finance Book",
"options": "Finance Book"
},
{
"fieldname": "project",
"fieldtype": "Link",
"label": "Project",
"options": "Project"
},
{
"depends_on": "eval:parent.update_stock == 1",
"fieldname": "sales_invoice_item",
"fieldtype": "Data",
"ignore_user_permissions": 1,
"label": "Sales Invoice Item",
"no_copy": 1,
"print_hide": 1,
"read_only": 1
}
],
"idx": 1,
"istable": 1,
"links": [],
"modified": "2019-12-04 12:22:38.517710",
"modified": "2020-08-20 11:24:41.749986",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Sales Invoice Item",

View File

@@ -1,314 +1,89 @@
{
"allow_copy": 0,
"allow_events_in_timeline": 0,
"allow_guest_to_view": 0,
"allow_import": 0,
"allow_rename": 0,
"beta": 0,
"creation": "2016-05-08 23:49:38.842621",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "",
"editable_grid": 1,
"creation": "2016-05-08 23:49:38.842621",
"doctype": "DocType",
"editable_grid": 1,
"engine": "InnoDB",
"field_order": [
"default",
"mode_of_payment",
"amount",
"column_break_3",
"account",
"type",
"base_amount",
"clearance_date"
],
"fields": [
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"depends_on": "eval:parent.doctype == 'POS Profile'",
"fetch_if_empty": 0,
"fieldname": "default",
"fieldtype": "Check",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Default",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"default": "0",
"depends_on": "eval:parent.doctype == 'POS Profile'",
"fieldname": "default",
"fieldtype": "Check",
"in_list_view": 1,
"label": "Default"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fetch_if_empty": 0,
"fieldname": "mode_of_payment",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Mode of Payment",
"length": 0,
"no_copy": 0,
"options": "Mode of Payment",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "mode_of_payment",
"fieldtype": "Link",
"in_list_view": 1,
"label": "Mode of Payment",
"options": "Mode of Payment",
"reqd": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"default": "0",
"depends_on": "eval:parent.doctype == 'Sales Invoice'",
"fetch_if_empty": 0,
"fieldname": "amount",
"fieldtype": "Currency",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Amount",
"length": 0,
"no_copy": 0,
"options": "currency",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"default": "0",
"depends_on": "eval:parent.doctype == 'Sales Invoice'",
"fieldname": "amount",
"fieldtype": "Currency",
"in_list_view": 1,
"label": "Amount",
"options": "currency",
"reqd": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fetch_if_empty": 0,
"fieldname": "column_break_3",
"fieldtype": "Column Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "column_break_3",
"fieldtype": "Column Break"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fetch_if_empty": 0,
"fieldname": "account",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Account",
"length": 0,
"no_copy": 0,
"options": "Account",
"permlevel": 0,
"precision": "",
"print_hide": 1,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "account",
"fieldtype": "Link",
"label": "Account",
"options": "Account",
"print_hide": 1,
"read_only": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fetch_from": "mode_of_payment.type",
"fetch_if_empty": 0,
"fieldname": "type",
"fieldtype": "Read Only",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Type",
"length": 0,
"no_copy": 0,
"options": "",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fetch_from": "mode_of_payment.type",
"fieldname": "type",
"fieldtype": "Read Only",
"label": "Type"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fetch_if_empty": 0,
"fieldname": "base_amount",
"fieldtype": "Currency",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Base Amount (Company Currency)",
"length": 0,
"no_copy": 1,
"options": "Company:company:default_currency",
"permlevel": 0,
"precision": "",
"print_hide": 1,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "base_amount",
"fieldtype": "Currency",
"label": "Base Amount (Company Currency)",
"no_copy": 1,
"options": "Company:company:default_currency",
"print_hide": 1,
"read_only": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fetch_if_empty": 0,
"fieldname": "clearance_date",
"fieldtype": "Date",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Clearance Date",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 1,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
"fieldname": "clearance_date",
"fieldtype": "Date",
"label": "Clearance Date",
"no_copy": 1,
"print_hide": 1,
"read_only": 1
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 0,
"idx": 0,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 1,
"max_attachments": 0,
"modified": "2019-03-19 14:54:56.524556",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Sales Invoice Payment",
"name_case": "",
"owner": "Administrator",
"permissions": [],
"quick_entry": 1,
"read_only": 0,
"read_only_onload": 0,
"show_name_in_global_search": 0,
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 0,
"track_seen": 0,
"track_views": 0
],
"istable": 1,
"modified": "2020-08-03 13:07:49.260534",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Sales Invoice Payment",
"owner": "Administrator",
"permissions": [],
"quick_entry": 1,
"sort_field": "modified",
"sort_order": "DESC"
}

View File

@@ -1,5 +1,4 @@
{
"actions": [],
"autoname": "ACC-SUB-.YYYY.-.#####",
"creation": "2017-07-18 17:50:43.967266",
"doctype": "DocType",
@@ -14,6 +13,7 @@
"cancelation_date",
"trial_period_start",
"trial_period_end",
"generate_new_invoices_past_due_date",
"column_break_11",
"current_invoice_start",
"current_invoice_end",
@@ -195,10 +195,16 @@
{
"fieldname": "dimension_col_break",
"fieldtype": "Column Break"
},
{
"default": "0",
"description": "New invoices will be generated as per schedule even if current invoices are unpaid or past due date",
"fieldname": "generate_new_invoices_past_due_date",
"fieldtype": "Check",
"label": "Generate New Invoices Past Due Date"
}
],
"links": [],
"modified": "2020-01-27 14:37:32.845173",
"modified": "2020-11-29 22:46:14.879289",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Subscription",

View File

@@ -263,13 +263,14 @@ class Subscription(Document):
invoice.set_taxes()
# Due date
invoice.append(
'payment_schedule',
{
'due_date': add_days(self.current_invoice_end, cint(self.days_until_due)),
'invoice_portion': 100
}
)
if self.days_until_due:
invoice.append(
'payment_schedule',
{
'due_date': add_days(self.current_invoice_end, cint(self.days_until_due)),
'invoice_portion': 100
}
)
# Discounts
if self.additional_discount_percentage:
@@ -326,8 +327,7 @@ class Subscription(Document):
def is_postpaid_to_invoice(self):
return getdate(nowdate()) > getdate(self.current_invoice_end) or \
(getdate(nowdate()) >= getdate(self.current_invoice_end) and getdate(self.current_invoice_end) == getdate(self.current_invoice_start)) and \
not self.has_outstanding_invoice()
(getdate(nowdate()) >= getdate(self.current_invoice_end) and getdate(self.current_invoice_end) == getdate(self.current_invoice_start))
def is_prepaid_to_invoice(self):
if not self.generate_invoice_at_period_start:
@@ -337,8 +337,16 @@ class Subscription(Document):
return True
# Check invoice dates and make sure it doesn't have outstanding invoices
return getdate(nowdate()) >= getdate(self.current_invoice_start) and not self.has_outstanding_invoice()
return getdate(nowdate()) >= getdate(self.current_invoice_start)
def is_current_invoice_generated(self):
invoice = self.get_current_invoice()
if invoice and getdate(self.current_invoice_start) <= getdate(invoice.posting_date) <= getdate(self.current_invoice_end):
return True
return False
def is_current_invoice_paid(self):
if self.is_new_subscription():
return False
@@ -346,7 +354,7 @@ class Subscription(Document):
last_invoice = frappe.get_doc('Sales Invoice', self.invoices[-1].invoice)
if getdate(last_invoice.posting_date) == getdate(self.current_invoice_start) and last_invoice.status == 'Paid':
return True
return False
def process_for_active(self):
@@ -358,7 +366,8 @@ class Subscription(Document):
2. Change the `Subscription` status to 'Past Due Date'
3. Change the `Subscription` status to 'Cancelled'
"""
if not self.is_current_invoice_paid() and (self.is_postpaid_to_invoice() or self.is_prepaid_to_invoice()):
if not self.is_current_invoice_generated() and not self.is_current_invoice_paid() and \
(self.is_postpaid_to_invoice() or self.is_prepaid_to_invoice()):
self.generate_invoice()
if self.current_invoice_is_past_due():
self.status = 'Past Due Date'
@@ -369,6 +378,9 @@ class Subscription(Document):
if self.cancel_at_period_end and getdate(nowdate()) > getdate(self.current_invoice_end):
self.cancel_subscription_at_period_end()
if self.is_current_invoice_generated() and getdate() > getdate(self.current_invoice_end):
self.update_subscription_period(add_days(self.current_invoice_end, 1))
def cancel_subscription_at_period_end(self):
"""
Called when `Subscription.cancel_at_period_end` is truthy
@@ -396,6 +408,15 @@ class Subscription(Document):
else:
self.set_status_grace_period()
if getdate() > getdate(self.current_invoice_end):
self.update_subscription_period(add_days(self.current_invoice_end, 1))
# Generate invoices periodically even if current invoice are unpaid
if self.generate_new_invoices_past_due_date and not self.is_current_invoice_generated() and (self.is_postpaid_to_invoice()
or self.is_prepaid_to_invoice()):
prorate = frappe.db.get_single_value('Subscription Settings', 'prorate')
self.generate_invoice(prorate)
@staticmethod
def is_not_outstanding(invoice):
"""

View File

@@ -101,19 +101,19 @@ class TestSubscription(unittest.TestCase):
subscription.delete()
def test_invoice_is_generated_at_end_of_billing_period(self):
start_date = add_to_date(nowdate(), months=-1)
subscription = frappe.new_doc('Subscription')
subscription.customer = '_Test Customer'
subscription.start = '2018-01-01'
subscription.start = start_date
subscription.append('plans', {'plan': '_Test Plan Name', 'qty': 1})
subscription.insert()
self.assertEqual(subscription.status, 'Active')
self.assertEqual(subscription.current_invoice_start, '2018-01-01')
self.assertEqual(subscription.current_invoice_end, '2018-01-31')
self.assertEqual(subscription.current_invoice_start, start_date)
self.assertEqual(subscription.current_invoice_end, add_days(nowdate(), -1))
subscription.process()
self.assertEqual(len(subscription.invoices), 1)
self.assertEqual(subscription.current_invoice_start, '2018-01-01')
self.assertEqual(subscription.status, 'Past Due Date')
subscription.delete()
@@ -137,7 +137,6 @@ class TestSubscription(unittest.TestCase):
subscription.process()
self.assertEqual(subscription.status, 'Active')
self.assertEqual(subscription.current_invoice_start, add_months(subscription.start, 1))
self.assertEqual(len(subscription.invoices), 1)
subscription.delete()
@@ -210,7 +209,8 @@ class TestSubscription(unittest.TestCase):
subscription = frappe.new_doc('Subscription')
subscription.customer = '_Test Customer'
subscription.append('plans', {'plan': '_Test Plan Name', 'qty': 1})
subscription.start = '2018-01-01'
subscription.start = add_days(nowdate(), -1000)
subscription.days_until_due = 1
subscription.insert()
subscription.process() # generate first invoice
@@ -538,3 +538,23 @@ class TestSubscription(unittest.TestCase):
settings.save()
subscription.delete()
def test_duplicate_invoice_check(self):
subscription = frappe.new_doc('Subscription')
subscription.customer = '_Test Customer'
subscription.generate_invoice_at_period_start = True
subscription.append('plans', {'plan': '_Test Plan Name', 'qty': 1})
subscription.start = nowdate()
subscription.save()
# Generate invoice for the current invoicing period
subscription.process()
subscription.load_from_db()
self.assertEqual(len(subscription.invoices), 1)
# Proccess subscription again for the same period
subscription.process()
subscription.load_from_db()
# No new invoice should be created for current period
self.assertEqual(len(subscription.invoices), 1)

View File

@@ -6,6 +6,8 @@ from __future__ import unicode_literals
import frappe
import unittest
from erpnext.accounts.doctype.tax_rule.tax_rule import IncorrectCustomerGroup, IncorrectSupplierType, ConflictingTaxRule, get_tax_template
from erpnext.crm.doctype.opportunity.test_opportunity import make_opportunity
from erpnext.crm.doctype.opportunity.opportunity import make_quotation
test_records = frappe.get_test_records('Tax Rule')
@@ -144,6 +146,23 @@ class TestTaxRule(unittest.TestCase):
self.assertEqual(get_tax_template("2015-01-01", {"customer":"_Test Customer", "billing_city": "Test City 1"}),
"_Test Sales Taxes and Charges Template 1 - _TC")
def test_taxes_fetch_via_tax_rule(self):
make_tax_rule(customer= "_Test Customer", billing_city = "_Test City",
sales_tax_template = "_Test Sales Taxes and Charges Template - _TC", save=1)
# create opportunity for customer
opportunity = make_opportunity(with_items=1)
# make quotation from opportunity
quotation = make_quotation(opportunity.name)
quotation.save()
self.assertEqual(quotation.taxes_and_charges, "_Test Sales Taxes and Charges Template - _TC")
# Check if accounts heads and rate fetched are also fetched from tax template or not
self.assertTrue(len(quotation.taxes) > 0)
def make_tax_rule(**args):
args = frappe._dict(args)

View File

@@ -106,6 +106,7 @@ def get_tds_amount(suppliers, net_total, company, tax_details, fiscal_year_detai
from `tabGL Entry`
where company = %s and
party in %s and fiscal_year=%s and credit > 0
and is_opening = 'No'
""", (company, tuple(suppliers), fiscal_year), as_dict=1)
vouchers = [d.voucher_no for d in entries]
@@ -139,9 +140,9 @@ def get_tds_amount(suppliers, net_total, company, tax_details, fiscal_year_detai
else:
tds_amount = _get_tds(net_total, tax_details.rate)
else:
supplier_credit_amount = frappe.get_all('Purchase Invoice Item',
fields = ['sum(net_amount)'],
filters = {'parent': ('in', vouchers), 'docstatus': 1}, as_list=1)
supplier_credit_amount = frappe.get_all('Purchase Invoice',
fields = ['sum(net_total)'],
filters = {'name': ('in', vouchers), 'docstatus': 1, "apply_tds": 1}, as_list=1)
supplier_credit_amount = (supplier_credit_amount[0][0]
if supplier_credit_amount and supplier_credit_amount[0][0] else 0)
@@ -192,6 +193,7 @@ def get_advance_vouchers(suppliers, fiscal_year=None, company=None, from_date=No
select distinct voucher_no
from `tabGL Entry`
where party in %s and %s and debit > 0
and is_opening = 'No'
""", (tuple(suppliers), condition)) or []
def get_debit_note_amount(suppliers, year_start_date, year_end_date, company=None):

View File

@@ -101,6 +101,29 @@ class TestTaxWithholdingCategory(unittest.TestCase):
for d in invoices:
d.cancel()
def test_single_threshold_tds_with_previous_vouchers_and_no_tds(self):
invoices = []
frappe.db.set_value("Supplier", "Test TDS Supplier2", "tax_withholding_category", "Single Threshold TDS")
pi = create_purchase_invoice(supplier="Test TDS Supplier2")
pi.submit()
invoices.append(pi)
# TDS not applied
pi = create_purchase_invoice(supplier="Test TDS Supplier2", do_not_apply_tds=True)
pi.submit()
invoices.append(pi)
pi = create_purchase_invoice(supplier="Test TDS Supplier2")
pi.submit()
invoices.append(pi)
self.assertEqual(pi.taxes_and_charges_deducted, 2000)
self.assertEqual(pi.grand_total, 8000)
# delete invoices to avoid clashing
for d in invoices:
d.cancel()
def create_purchase_invoice(**args):
# return sales invoice doc object
item = frappe.get_doc('Item', {'item_name': 'TDS Item'})
@@ -109,7 +132,7 @@ def create_purchase_invoice(**args):
pi = frappe.get_doc({
"doctype": "Purchase Invoice",
"posting_date": today(),
"apply_tds": 1,
"apply_tds": 0 if args.do_not_apply_tds else 1,
"supplier": args.supplier,
"company": '_Test Company',
"taxes_and_charges": "",

View File

@@ -45,8 +45,8 @@ def validate_accounting_period(gl_map):
}, as_dict=1)
if accounting_periods:
frappe.throw(_("You can't create accounting entries in the closed accounting period {0}")
.format(accounting_periods[0].name), ClosedAccountingPeriod)
frappe.throw(_("You cannot create or cancel any accounting entries within in the closed Accounting Period {0}")
.format(frappe.bold(accounting_periods[0].name)), ClosedAccountingPeriod)
def process_gl_map(gl_map, merge_entries=True):
if merge_entries:
@@ -296,6 +296,7 @@ def delete_gl_entries(gl_entries=None, voucher_type=None, voucher_no=None,
where voucher_type=%s and voucher_no=%s""", (voucher_type, voucher_no), as_dict=True)
if gl_entries:
validate_accounting_period(gl_entries)
check_freezing_date(gl_entries[0]["posting_date"], adv_adj)
frappe.db.sql("""delete from `tabGL Entry` where voucher_type=%s and voucher_no=%s""",

View File

@@ -72,7 +72,7 @@ erpnext.accounts.bankReconciliation = class BankReconciliation {
check_plaid_status() {
const me = this;
frappe.db.get_value("Plaid Settings", "Plaid Settings", "enabled", (r) => {
if (r && r.enabled == "1") {
if (r && r.enabled === "1") {
me.plaid_status = "active"
} else {
me.plaid_status = "inactive"
@@ -139,7 +139,7 @@ erpnext.accounts.bankTransactionUpload = class bankTransactionUpload {
}
make() {
const me = this;
const me = this;
new frappe.ui.FileUploader({
method: 'erpnext.accounts.doctype.bank_transaction.bank_transaction_upload.upload_bank_statement',
allow_multiple: 0,
@@ -214,31 +214,35 @@ erpnext.accounts.bankTransactionSync = class bankTransactionSync {
init_config() {
const me = this;
frappe.xcall('erpnext.erpnext_integrations.doctype.plaid_settings.plaid_settings.plaid_configuration')
.then(result => {
me.plaid_env = result.plaid_env;
me.plaid_public_key = result.plaid_public_key;
me.client_name = result.client_name;
me.sync_transactions()
})
frappe.xcall('erpnext.erpnext_integrations.doctype.plaid_settings.plaid_settings.get_plaid_configuration')
.then(result => {
me.plaid_env = result.plaid_env;
me.client_name = result.client_name;
me.link_token = result.link_token;
me.sync_transactions();
})
}
sync_transactions() {
const me = this;
frappe.db.get_value("Bank Account", me.parent.bank_account, "bank", (v) => {
frappe.db.get_value("Bank Account", me.parent.bank_account, "bank", (r) => {
frappe.xcall('erpnext.erpnext_integrations.doctype.plaid_settings.plaid_settings.sync_transactions', {
bank: v['bank'],
bank: r.bank,
bank_account: me.parent.bank_account,
freeze: true
})
.then((result) => {
let result_title = (result.length > 0) ? __("{0} bank transaction(s) created", [result.length]) : __("This bank account is already synchronized")
let result_title = (result && result.length > 0)
? __("{0} bank transaction(s) created", [result.length])
: __("This bank account is already synchronized");
let result_msg = `
<div class="flex justify-center align-center text-muted" style="height: 50vh; display: flex;">
<h5 class="text-muted">${result_title}</h5>
</div>`
<div class="flex justify-center align-center text-muted" style="height: 50vh; display: flex;">
<h5 class="text-muted">${result_title}</h5>
</div>`
this.parent.$main_section.append(result_msg)
frappe.show_alert({message:__("Bank account '{0}' has been synchronized", [me.parent.bank_account]), indicator:'green'});
frappe.show_alert({ message: __("Bank account '{0}' has been synchronized", [me.parent.bank_account]), indicator: 'green' });
})
})
}
@@ -384,7 +388,7 @@ erpnext.accounts.ReconciliationRow = class ReconciliationRow {
})
frappe.xcall('erpnext.accounts.page.bank_reconciliation.bank_reconciliation.get_linked_payments',
{bank_transaction: data, freeze:true, freeze_message:__("Finding linked payments")}
{ bank_transaction: data, freeze: true, freeze_message: __("Finding linked payments") }
).then((result) => {
me.make_dialog(result)
})

View File

@@ -260,7 +260,11 @@ def check_amount_vs_description(amount_matching, description_matching):
continue
if "reference_no" in am_match and "reference_no" in des_match:
if difflib.SequenceMatcher(lambda x: x == " ", am_match["reference_no"], des_match["reference_no"]).ratio() > 70:
# Sequence Matcher does not handle None as input
am_reference = am_match["reference_no"] or ""
des_reference = des_match["reference_no"] or ""
if difflib.SequenceMatcher(lambda x: x == " ", am_reference, des_reference).ratio() > 70:
if am_match not in result:
result.append(am_match)
if result:
@@ -285,6 +289,8 @@ def get_matching_transactions_payments(description_matching):
else:
return []
@frappe.whitelist()
@frappe.validate_and_sanitize_search_inputs
def payment_entry_query(doctype, txt, searchfield, start, page_len, filters):
account = frappe.db.get_value("Bank Account", filters.get("bank_account"), "account")
if not account:
@@ -313,6 +319,8 @@ def payment_entry_query(doctype, txt, searchfield, start, page_len, filters):
}
)
@frappe.whitelist()
@frappe.validate_and_sanitize_search_inputs
def journal_entry_query(doctype, txt, searchfield, start, page_len, filters):
account = frappe.db.get_value("Bank Account", filters.get("bank_account"), "account")
@@ -348,6 +356,8 @@ def journal_entry_query(doctype, txt, searchfield, start, page_len, filters):
}
)
@frappe.whitelist()
@frappe.validate_and_sanitize_search_inputs
def sales_invoices_query(doctype, txt, searchfield, start, page_len, filters):
return frappe.db.sql("""
SELECT
@@ -373,4 +383,4 @@ def sales_invoices_query(doctype, txt, searchfield, start, page_len, filters):
'start': start,
'page_len': page_len
}
)
)

View File

@@ -81,7 +81,7 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
me.page.set_indicator(__("Online"), "green")
}
}
})
});
},
onload: function () {
@@ -278,6 +278,14 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
})
},
set_pos_profile_title(pos_profile) {
this.page.set_title_sub(
`<span class="indicator blue">
<a class="text-muted" href="#Form/POS Profile/${pos_profile}">${pos_profile}</a>
</span>`
);
},
get_data_from_server: function (callback) {
var me = this;
frappe.call({
@@ -286,6 +294,7 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
freeze_message: __("Master data syncing, it might take some time"),
callback: function (r) {
localStorage.setItem('doc', JSON.stringify(r.message.doc));
me.set_pos_profile_title(r.message.pos_profile.name);
me.init_master_data(r)
me.set_interval_for_si_sync();
me.check_internet_connection();
@@ -1062,8 +1071,9 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
}
if(index < me.page_len) {
$(frappe.render_template("pos_item", {
item_code: obj.name,
item_code: escape(obj.name),
item_price: item_price,
title: obj.name === obj.item_name ? obj.name : obj.item_name,
item_name: obj.name === obj.item_name ? "" : obj.item_name,
item_image: obj.image,
item_stock: __('Stock Qty') + ": " + me.get_actual_qty(obj),
@@ -1098,7 +1108,8 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
get_items: function (item_code) {
// To search item as per the key enter
item_code = unescape(item_code);
item_code = item_code === "undefined" ? undefined : item_code;
var me = this;
this.item_serial_no = {};
this.item_batch_no = {};
@@ -1164,7 +1175,7 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
$(this).addClass('active');
me.numeric_val = "";
me.numeric_id = ""
me.item_code = $(this).attr("data-item-code");
me.item_code = unescape($(this).attr("data-item-code"));
me.render_selected_item()
me.bind_qty_event()
me.update_rate()
@@ -1176,33 +1187,33 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
var me = this;
$(this.wrapper).on("change", ".pos-item-qty", function () {
var item_code = $(this).parents(".pos-selected-item-action").attr("data-item-code");
var item_code = unescape($(this).parents(".pos-selected-item-action").attr("data-item-code"));
var qty = $(this).val();
me.update_qty(item_code, qty);
me.update_value();
})
$(this.wrapper).on("focusout", ".pos-item-qty", function () {
var item_code = $(this).parents(".pos-selected-item-action").attr("data-item-code");
var item_code = unescape($(this).parents(".pos-selected-item-action").attr("data-item-code"));
var qty = $(this).val();
me.update_qty(item_code, qty, true);
me.update_value();
})
$(this.wrapper).find("[data-action='increase-qty']").on("click", function () {
var item_code = $(this).parents(".pos-bill-item").attr("data-item-code");
var item_code = unescape($(this).parents(".pos-bill-item").attr("data-item-code"));
var qty = flt($(this).parents(".pos-bill-item").find('.pos-item-qty').val()) + 1;
me.update_qty(item_code, qty);
})
$(this.wrapper).find("[data-action='decrease-qty']").on("click", function () {
var item_code = $(this).parents(".pos-bill-item").attr("data-item-code");
var item_code = unescape($(this).parents(".pos-bill-item").attr("data-item-code"));
var qty = flt($(this).parents(".pos-bill-item").find('.pos-item-qty').val()) - 1;
me.update_qty(item_code, qty);
})
$(this.wrapper).on("change", ".pos-item-disc", function () {
var item_code = $(this).parents(".pos-selected-item-action").attr("data-item-code");
var item_code = unescape($(this).parents(".pos-selected-item-action").attr("data-item-code"));
var discount = $(this).val();
if(discount > 100){
discount = $(this).val('');
@@ -1253,7 +1264,7 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
update_rate: function () {
var me = this;
$(this.wrapper).on("change", ".pos-item-price", function () {
var item_code = $(this).parents(".pos-selected-item-action").attr("data-item-code");
var item_code = unescape($(this).parents(".pos-selected-item-action").attr("data-item-code"));
me.set_item_details(item_code, "rate", $(this).val());
me.update_value()
})
@@ -1282,9 +1293,17 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
this.child_doc = this.get_child_item(this.item_code);
$(this.wrapper).find('.selected-item').empty();
if(this.child_doc.length) {
this.child_doc[0]["allow_user_to_edit_rate"] = this.pos_profile_data["allow_user_to_edit_rate"] ? true : false,
this.child_doc[0]["allow_user_to_edit_discount"] = this.pos_profile_data["allow_user_to_edit_discount"] ? true : false;
this.selected_row = $(frappe.render_template("pos_selected_item", this.child_doc[0]))
this.selected_row = $(frappe.render_template("pos_selected_item", {
idx: this.child_doc[0].idx,
item_code: escape(this.child_doc[0].item_code),
qty: this.child_doc[0].qty,
price_list_rate: this.child_doc[0].price_list_rate,
allow_user_to_edit_rate: this.pos_profile_data["allow_user_to_edit_rate"] ? true : false,
allow_user_to_edit_discount: this.pos_profile_data["allow_user_to_edit_discount"] ? true : false,
discount_percentage: this.child_doc[0].discount_percentage,
rate: this.child_doc[0].rate,
amount: this.child_doc[0].amount
}))
$(this.wrapper).find('.selected-item').html(this.selected_row)
}
@@ -1535,7 +1554,8 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
$.each(this.frm.doc.items || [], function (i, d) {
$(frappe.render_template("pos_bill_item_new", {
item_code: d.item_code,
item_code: escape(d.item_code),
title: d.item_code === d.item_name ? d.item_code : d.item_name,
item_name: (d.item_name === d.item_code || !d.item_name) ? "" : ("<br>" + d.item_name),
qty: d.qty,
discount_percentage: d.discount_percentage || 0.0,

View File

@@ -60,7 +60,7 @@ def _get_party_details(party=None, account=None, party_type="Customer", company=
billing_address=party_address, shipping_address=shipping_address)
if fetch_payment_terms_template:
party_details["payment_terms_template"] = get_pyt_term_template(party.name, party_type, company)
party_details["payment_terms_template"] = get_payment_terms_template(party.name, party_type, company)
if not party_details.get("currency"):
party_details["currency"] = currency
@@ -204,7 +204,7 @@ def set_account_and_due_date(party, account, party_type, company, posting_date,
return out
@frappe.whitelist()
def get_party_account(party_type, party, company):
def get_party_account(party_type, party, company=None):
"""Returns the account for the given `party`.
Will first search in party (Customer / Supplier) record, if not found,
will search in group (Customer Group / Supplier Group),
@@ -318,7 +318,7 @@ def get_due_date(posting_date, party_type, party, company=None, bill_date=None):
due_date = None
if (bill_date or posting_date) and party:
due_date = bill_date or posting_date
template_name = get_pyt_term_template(party, party_type, company)
template_name = get_payment_terms_template(party, party_type, company)
if template_name:
due_date = get_due_date_from_template(template_name, posting_date, bill_date).strftime("%Y-%m-%d")
@@ -391,7 +391,7 @@ def set_taxes(party, party_type, posting_date, company, customer_group=None, sup
from erpnext.accounts.doctype.tax_rule.tax_rule import get_tax_template, get_party_details
args = {
party_type.lower(): party,
"company": company
"company": company
}
if tax_category:
@@ -425,7 +425,7 @@ def set_taxes(party, party_type, posting_date, company, customer_group=None, sup
@frappe.whitelist()
def get_pyt_term_template(party_name, party_type, company=None):
def get_payment_terms_template(party_name, party_type, company=None):
if party_type not in ("Customer", "Supplier"):
return
template = None

View File

@@ -61,7 +61,7 @@ def make_sales_invoice():
debit_to = 'Debtors - _TC2',
income_account = 'Sales - _TC2',
expense_account = 'Cost of Goods Sold - _TC2',
cost_center = '_Test Company 2 - _TC2')
cost_center = 'Main - _TC2')

View File

@@ -42,11 +42,13 @@
{% if(filters.show_future_payments) { %}
{% var balance_row = data.slice(-1).pop();
var range1 = report.columns[11].label;
var range2 = report.columns[12].label;
var range3 = report.columns[13].label;
var range4 = report.columns[14].label;
var range5 = report.columns[15].label;
var start = filters.based_on_payment_terms ? 13 : 11;
var range1 = report.columns[start].label;
var range2 = report.columns[start+1].label;
var range3 = report.columns[start+2].label;
var range4 = report.columns[start+3].label;
var range5 = report.columns[start+4].label;
var range6 = report.columns[start+5].label;
%}
{% if(balance_row) { %}
<table class="table table-bordered table-condensed">
@@ -70,20 +72,34 @@
<th>{%= __(range3) %}</th>
<th>{%= __(range4) %}</th>
<th>{%= __(range5) %}</th>
<th>{%= __(range6) %}</th>
<th>{%= __("Total") %}</th>
</tr>
</thead>
<tbody>
<tr>
<td>{%= __("Total Outstanding") %}</td>
<td class="text-right">{%= format_number(balance_row["range1"], null, 2) %}</td>
<td class="text-right">{%= format_currency(balance_row["range2"]) %}</td>
<td class="text-right">{%= format_currency(balance_row["range3"]) %}</td>
<td class="text-right">{%= format_currency(balance_row["range4"]) %}</td>
<td class="text-right">{%= format_currency(balance_row["range5"]) %}</td>
<td class="text-right">
{%= format_number(balance_row["age"], null, 2) %}
</td>
<td class="text-right">
{%= format_currency(balance_row["range1"], data[data.length-1]["currency"]) %}
</td>
<td class="text-right">
{%= format_currency(balance_row["range2"], data[data.length-1]["currency"]) %}
</td>
<td class="text-right">
{%= format_currency(balance_row["range3"], data[data.length-1]["currency"]) %}
</td>
<td class="text-right">
{%= format_currency(balance_row["range4"], data[data.length-1]["currency"]) %}
</td>
<td class="text-right">
{%= format_currency(balance_row["range5"], data[data.length-1]["currency"]) %}
</td>
<td class="text-right">
{%= format_currency(flt(balance_row["outstanding"]), data[data.length-1]["currency"]) %}
</td>
</td>
</tr>
<td>{%= __("Future Payments") %}</td>
<td></td>
@@ -91,6 +107,7 @@
<td></td>
<td></td>
<td></td>
<td></td>
<td class="text-right">
{%= format_currency(flt(balance_row[("future_amount")]), data[data.length-1]["currency"]) %}
</td>
@@ -101,6 +118,7 @@
<th></th>
<th></th>
<th></th>
<th></th>
<th class="text-right">
{%= format_currency(flt(balance_row["outstanding"] - balance_row[("future_amount")]), data[data.length-1]["currency"]) %}</th>
</tr>
@@ -218,15 +236,15 @@
<td></td>
<td style="text-align: right"><b>{%= __("Total") %}</b></td>
<td style="text-align: right">
{%= format_currency(data[i]["invoiced"], data[0]["currency"] ) %}</td>
{%= format_currency(data[i]["invoiced"], data[i]["currency"] ) %}</td>
{% if(!filters.show_future_payments) { %}
<td style="text-align: right">
{%= format_currency(data[i]["paid"], data[0]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i]["credit_note"], data[0]["currency"]) %} </td>
{%= format_currency(data[i]["paid"], data[i]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i]["credit_note"], data[i]["currency"]) %} </td>
{% } %}
<td style="text-align: right">
{%= format_currency(data[i]["outstanding"], data[0]["currency"]) %}</td>
{%= format_currency(data[i]["outstanding"], data[i]["currency"]) %}</td>
{% if(filters.show_future_payments) { %}
{% if(report.report_name === "Accounts Receivable") { %}
@@ -234,8 +252,8 @@
{%= data[i]["po_no"] %}</td>
{% } %}
<td style="text-align: right">{%= data[i]["future_ref"] %}</td>
<td style="text-align: right">{%= format_currency(data[i]["future_amount"], data[0]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i]["remaining_balance"], data[0]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i]["future_amount"], data[i]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i]["remaining_balance"], data[i]["currency"]) %}</td>
{% } %}
{% } %}
{% } else { %}
@@ -256,10 +274,10 @@
{% } else { %}
<td><b>{%= __("Total") %}</b></td>
{% } %}
<td style="text-align: right">{%= format_currency(data[i]["invoiced"], data[0]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i]["paid"], data[0]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i]["credit_note"], data[0]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i]["outstanding"], data[0]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i]["invoiced"], data[i]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i]["paid"], data[i]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i]["credit_note"], data[i]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i]["outstanding"], data[i]["currency"]) %}</td>
{% } %}
{% } %}
</tr>

View File

@@ -69,7 +69,7 @@ frappe.query_reports["Accounts Receivable"] = {
filters: {
'company': company
}
}
};
}
},
{

View File

@@ -160,6 +160,8 @@ class ReceivablePayableReport(object):
else:
# advance / unlinked payment or other adjustment
row.paid -= gle_balance
if gle.cost_center:
row.cost_center = gle.cost_center
def update_sub_total_row(self, row, party):
total_row = self.total_row_map.get(party)
@@ -210,7 +212,6 @@ class ReceivablePayableReport(object):
for key, row in self.voucher_balance.items():
row.outstanding = flt(row.invoiced - row.paid - row.credit_note, self.currency_precision)
row.invoice_grand_total = row.invoiced
if abs(row.outstanding) > 1.0/10 ** self.currency_precision:
# non-zero oustanding, we must consider this row
@@ -577,7 +578,7 @@ class ReceivablePayableReport(object):
self.gl_entries = frappe.db.sql("""
select
name, posting_date, account, party_type, party, voucher_type, voucher_no,
name, posting_date, account, party_type, party, voucher_type, voucher_no, cost_center,
against_voucher_type, against_voucher, account_currency, remarks, {0}
from
`tabGL Entry`
@@ -617,9 +618,19 @@ class ReceivablePayableReport(object):
elif party_type_field=="supplier":
self.add_supplier_filters(conditions, values)
if self.filters.cost_center:
self.get_cost_center_conditions(conditions)
self.add_accounting_dimensions_filters(conditions, values)
return " and ".join(conditions), values
def get_cost_center_conditions(self, conditions):
lft, rgt = frappe.db.get_value("Cost Center", self.filters.cost_center, ["lft", "rgt"])
cost_center_list = [center.name for center in frappe.get_list("Cost Center", filters = {'lft': (">=", lft), 'rgt': ("<=", rgt)})]
cost_center_string = '", "'.join(cost_center_list)
conditions.append('cost_center in ("{0}")'.format(cost_center_string))
def get_order_by_condition(self):
if self.filters.get('group_by_party'):
return "order by party, posting_date"
@@ -643,8 +654,10 @@ class ReceivablePayableReport(object):
account_type = "Receivable" if self.party_type == "Customer" else "Payable"
accounts = [d.name for d in frappe.get_all("Account",
filters={"account_type": account_type, "company": self.filters.company})]
conditions.append("account in (%s)" % ','.join(['%s'] *len(accounts)))
values += accounts
if accounts:
conditions.append("account in (%s)" % ','.join(['%s'] *len(accounts)))
values += accounts
def add_customer_filters(self, conditions, values):
if self.filters.get("customer_group"):
@@ -729,6 +742,7 @@ class ReceivablePayableReport(object):
self.add_column(_("Customer Contact"), fieldname='customer_primary_contact',
fieldtype='Link', options='Contact')
self.add_column(label=_('Cost Center'), fieldname='cost_center', fieldtype='Data')
self.add_column(label=_('Voucher Type'), fieldname='voucher_type', fieldtype='Data')
self.add_column(label=_('Voucher No'), fieldname='voucher_no', fieldtype='Dynamic Link',
options='voucher_type', width=180)

View File

@@ -63,7 +63,7 @@ def make_sales_invoice():
debit_to = 'Debtors - _TC2',
income_account = 'Sales - _TC2',
expense_account = 'Cost of Goods Sold - _TC2',
cost_center = '_Test Company 2 - _TC2',
cost_center = 'Main - _TC2',
do_not_save=1)
si.append('payment_schedule', dict(due_date=getdate(add_days(today(), 30)), invoice_portion=30.00, payment_amount=30))
@@ -83,14 +83,14 @@ def make_payment(docname):
def make_credit_note(docname):
create_sales_invoice(company="_Test Company 2",
customer = '_Test Customer 2',
currency = 'EUR',
qty = -1,
warehouse = 'Finished Goods - _TC2',
debit_to = 'Debtors - _TC2',
income_account = 'Sales - _TC2',
expense_account = 'Cost of Goods Sold - _TC2',
cost_center = '_Test Company 2 - _TC2',
is_return = 1,
return_against = docname)
customer = '_Test Customer 2',
currency = 'EUR',
qty = -1,
warehouse = 'Finished Goods - _TC2',
debit_to = 'Debtors - _TC2',
income_account = 'Sales - _TC2',
expense_account = 'Cost of Goods Sold - _TC2',
cost_center = 'Main - _TC2',
is_return = 1,
return_against = docname)

View File

@@ -3,6 +3,14 @@
frappe.query_reports["Bank Reconciliation Statement"] = {
"filters": [
{
"fieldname":"company",
"label": __("Company"),
"fieldtype": "Link",
"options": "Company",
"reqd": 1,
"default": frappe.defaults.get_user_default("Company")
},
{
"fieldname":"account",
"label": __("Bank Account"),
@@ -12,11 +20,14 @@ frappe.query_reports["Bank Reconciliation Statement"] = {
locals[":Company"][frappe.defaults.get_user_default("Company")]["default_bank_account"]: "",
"reqd": 1,
"get_query": function() {
var company = frappe.query_report.get_filter_value('company')
return {
"query": "erpnext.controllers.queries.get_account_list",
"filters": [
['Account', 'account_type', 'in', 'Bank, Cash'],
['Account', 'is_group', '=', 0],
['Account', 'disabled', '=', 0],
['Account', 'company', '=', company],
]
}
}
@@ -34,4 +45,4 @@ frappe.query_reports["Bank Reconciliation Statement"] = {
"fieldtype": "Check"
},
]
}
}

View File

@@ -44,7 +44,7 @@
</tr>
</thead>
<tbody>
{% for(let j=0, k=data.length-1; j<k; j++) { %}
{% for(let j=0, k=data.length; j<k; j++) { %}
{%
var row = data[j];
var row_class = data[j].parent_account ? "" : "financial-statements-important";

View File

@@ -8,12 +8,13 @@ from __future__ import unicode_literals
import re
from past.builtins import cmp
import functools
import math
import frappe, erpnext
from erpnext.accounts.report.utils import get_currency, convert_to_presentation_currency
from erpnext.accounts.utils import get_fiscal_year
from frappe import _
from frappe.utils import (flt, getdate, get_first_day, add_months, add_days, formatdate, cstr)
from frappe.utils import (flt, getdate, get_first_day, add_months, add_days, formatdate, cstr, cint)
from six import itervalues
from erpnext.accounts.doctype.accounting_dimension.accounting_dimension import get_accounting_dimensions, get_dimension_with_children
@@ -42,7 +43,7 @@ def get_period_list(from_fiscal_year, to_fiscal_year, periodicity, accumulated_v
start_date = year_start_date
months = get_months(year_start_date, year_end_date)
for i in range(months // months_to_add):
for i in range(cint(math.ceil(months / months_to_add))):
period = frappe._dict({
"from_date": start_date
})
@@ -293,7 +294,7 @@ def get_accounts(company, root_type):
where company=%s and root_type=%s order by lft""", (company, root_type), as_dict=True)
def filter_accounts(accounts, depth=10):
def filter_accounts(accounts, depth=20):
parent_children_map = {}
accounts_by_name = {}
for d in accounts:

View File

@@ -43,8 +43,11 @@ def execute(filters=None):
def validate_filters(filters, account_details):
if not filters.get('company'):
frappe.throw(_('{0} is mandatory').format(_('Company')))
if not filters.get("company"):
frappe.throw(_("{0} is mandatory").format(_("Company")))
if not filters.get("from_date") and not filters.get("to_date"):
frappe.throw(_("{0} and {1} are mandatory").format(frappe.bold(_("From Date")), frappe.bold(_("To Date"))))
if filters.get("account") and not account_details.get(filters.account):
frappe.throw(_("Account {0} does not exists").format(filters.account))

View File

@@ -1,24 +1,23 @@
{
"add_total_row": 0,
"apply_user_permissions": 1,
"creation": "2013-02-25 17:03:34",
"disabled": 0,
"docstatus": 0,
"doctype": "Report",
"idx": 3,
"is_standard": "Yes",
"modified": "2017-02-24 20:12:22.464240",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Gross Profit",
"owner": "Administrator",
"ref_doctype": "Sales Invoice",
"report_name": "Gross Profit",
"report_type": "Script Report",
"add_total_row": 1,
"creation": "2013-02-25 17:03:34",
"disabled": 0,
"docstatus": 0,
"doctype": "Report",
"idx": 3,
"is_standard": "Yes",
"modified": "2020-08-13 11:26:39.112352",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Gross Profit",
"owner": "Administrator",
"ref_doctype": "Sales Invoice",
"report_name": "Gross Profit",
"report_type": "Script Report",
"roles": [
{
"role": "Accounts Manager"
},
},
{
"role": "Accounts User"
}

View File

@@ -113,7 +113,7 @@ def get_balance_on(account=None, date=None, party_type=None, party=None, company
acc = frappe.get_doc("Account", account)
try:
year_start_date = get_fiscal_year(date, verbose=0)[1]
year_start_date = get_fiscal_year(date, company=company, verbose=0)[1]
except FiscalYearError:
if getdate(date) > getdate(nowdate()):
# if fiscal year not found and the date is greater than today
@@ -124,14 +124,12 @@ def get_balance_on(account=None, date=None, party_type=None, party=None, company
# hence, assuming balance as 0.0
return 0.0
allow_cost_center_in_entry_of_bs_account = get_allow_cost_center_in_entry_of_bs_account()
if account:
report_type = acc.report_type
else:
report_type = ""
if cost_center and (allow_cost_center_in_entry_of_bs_account or report_type =='Profit and Loss'):
if cost_center and report_type == 'Profit and Loss':
cc = frappe.get_doc("Cost Center", cost_center)
if cc.is_group:
cond.append(""" exists (
@@ -658,7 +656,8 @@ def get_outstanding_invoices(party_type, party, account, condition=None, filters
invoice_list = frappe.db.sql("""
select
voucher_no, voucher_type, posting_date, due_date,
ifnull(sum({dr_or_cr}), 0) as invoice_amount
ifnull(sum({dr_or_cr}), 0) as invoice_amount,
account_currency as currency
from
`tabGL Entry`
where
@@ -715,7 +714,8 @@ def get_outstanding_invoices(party_type, party, account, condition=None, filters
'invoice_amount': flt(d.invoice_amount),
'payment_amount': payment_amount,
'outstanding_amount': outstanding_amount,
'due_date': d.due_date
'due_date': d.due_date,
'currency': d.currency
})
)
@@ -767,10 +767,10 @@ def get_children(doctype, parent, company, is_root=False):
company_currency = frappe.get_cached_value('Company', company, "default_currency")
for each in acc:
each["company_currency"] = company_currency
each["balance"] = flt(get_balance_on(each.get("value"), in_account_currency=False))
each["balance"] = flt(get_balance_on(each.get("value"), in_account_currency=False, company=company))
if each.account_currency != company_currency:
each["balance_in_account_currency"] = flt(get_balance_on(each.get("value")))
each["balance_in_account_currency"] = flt(get_balance_on(each.get("value"), company=company))
return acc
@@ -817,7 +817,7 @@ def create_payment_gateway_account(gateway):
pass
@frappe.whitelist()
def update_cost_center(docname, cost_center_name, cost_center_number, company):
def update_cost_center(docname, cost_center_name, cost_center_number, company, merge):
'''
Renames the document by adding the number as a prefix to the current name and updates
all transaction where it was present.
@@ -833,7 +833,7 @@ def update_cost_center(docname, cost_center_name, cost_center_number, company):
new_name = get_autoname_with_number(cost_center_number, cost_center_name, docname, company)
if docname != new_name:
frappe.rename_doc("Cost Center", docname, new_name, force=1)
frappe.rename_doc("Cost Center", docname, new_name, force=1, merge=merge)
return new_name
def validate_field_number(doctype_name, docname, number_value, company, field_name):
@@ -877,11 +877,6 @@ def get_coa(doctype, parent, is_root, chart=None):
return accounts
def get_allow_cost_center_in_entry_of_bs_account():
def generator():
return cint(frappe.db.get_value('Accounts Settings', None, 'allow_cost_center_in_entry_of_bs_account'))
return frappe.local_cache("get_allow_cost_center_in_entry_of_bs_account", (), generator, regenerate_if_none=True)
def get_stock_accounts(company):
return frappe.get_all("Account", filters = {
"account_type": "Stock",

View File

@@ -232,7 +232,7 @@ frappe.ui.form.on('Asset', {
item_code: function(frm) {
if(frm.doc.item_code) {
if(frm.doc.item_code && frm.doc.calculate_depreciation) {
frm.trigger('set_finance_book');
}
},
@@ -252,13 +252,6 @@ frappe.ui.form.on('Asset', {
})
},
available_for_use_date: function(frm) {
$.each(frm.doc.finance_books || [], function(i, d) {
if(!d.depreciation_start_date) d.depreciation_start_date = frm.doc.available_for_use_date;
});
refresh_field("finance_books");
},
is_existing_asset: function(frm) {
frm.trigger("toggle_reference_doc");
// frm.toggle_reqd("next_depreciation_date", (!frm.doc.is_existing_asset && frm.doc.calculate_depreciation));
@@ -330,6 +323,10 @@ frappe.ui.form.on('Asset', {
calculate_depreciation: function(frm) {
frm.toggle_reqd("finance_books", frm.doc.calculate_depreciation);
if (frm.doc.calculate_depreciation) {
frm.trigger('set_finance_book');
}
},
gross_purchase_amount: function(frm) {
@@ -437,6 +434,15 @@ frappe.ui.form.on('Asset Finance Book', {
}
frappe.flags.dont_change_rate = false;
},
depreciation_start_date: function(frm, cdt, cdn) {
const book = locals[cdt][cdn];
if (frm.doc.available_for_use_date && book.depreciation_start_date == frm.doc.available_for_use_date) {
frappe.msgprint(__(`Depreciation Posting Date should not be equal to Available for Use Date.`));
book.depreciation_start_date = "";
frm.refresh_field("finance_books");
}
}
});

View File

@@ -6,7 +6,7 @@ from __future__ import unicode_literals
import frappe, erpnext, math, json
from frappe import _
from six import string_types
from frappe.utils import flt, add_months, cint, nowdate, getdate, today, date_diff, month_diff, add_days
from frappe.utils import flt, add_months, cint, nowdate, getdate, today, date_diff, month_diff, add_days, get_last_day, get_datetime
from frappe.model.document import Document
from erpnext.assets.doctype.asset_category.asset_category import get_asset_category_account
from erpnext.assets.doctype.asset.depreciation \
@@ -84,6 +84,11 @@ class Asset(AccountsController):
if not self.available_for_use_date:
frappe.throw(_("Available for use date is required"))
for d in self.finance_books:
if d.depreciation_start_date == self.available_for_use_date:
frappe.throw(_("Row #{}: Depreciation Posting Date should not be equal to Available for Use Date.").format(d.idx),
title=_("Incorrect Date"))
def set_missing_values(self):
if not self.asset_category:
self.asset_category = frappe.get_cached_value("Item", self.item_code, "asset_category")
@@ -149,6 +154,10 @@ class Asset(AccountsController):
def make_asset_movement(self):
reference_doctype = 'Purchase Receipt' if self.purchase_receipt else 'Purchase Invoice'
reference_docname = self.purchase_receipt or self.purchase_invoice
transaction_date = getdate(self.purchase_date)
if reference_docname:
posting_date, posting_time = frappe.db.get_value(reference_doctype, reference_docname, ["posting_date", "posting_time"])
transaction_date = get_datetime("{} {}".format(posting_date, posting_time))
assets = [{
'asset': self.name,
'asset_name': self.asset_name,
@@ -160,7 +169,7 @@ class Asset(AccountsController):
'assets': assets,
'purpose': 'Receipt',
'company': self.company,
'transaction_date': getdate(nowdate()),
'transaction_date': transaction_date,
'reference_doctype': reference_doctype,
'reference_name': reference_docname
}).insert()
@@ -308,7 +317,7 @@ class Asset(AccountsController):
if not row.depreciation_start_date:
if not self.available_for_use_date:
frappe.throw(_("Row {0}: Depreciation Start Date is required").format(row.idx))
row.depreciation_start_date = self.available_for_use_date
row.depreciation_start_date = get_last_day(self.available_for_use_date)
if not self.is_existing_asset:
self.opening_accumulated_depreciation = 0
@@ -407,6 +416,8 @@ class Asset(AccountsController):
row.expected_value_after_useful_life = asset_value_after_full_schedule
def validate_cancellation(self):
if self.status in ("In Maintenance", "Out of Order"):
frappe.throw(_("There are active maintenance or repairs against the asset. You must complete all of them before cancelling the asset."))
if self.status not in ("Submitted", "Partially Depreciated", "Fully Depreciated"):
frappe.throw(_("Asset cannot be cancelled, as it is already {0}").format(self.status))
@@ -459,29 +470,37 @@ class Asset(AccountsController):
def validate_make_gl_entry(self):
purchase_document = self.get_purchase_document()
asset_bought_with_invoice = purchase_document == self.purchase_invoice
fixed_asset_account, cwip_account = self.get_asset_accounts()
cwip_enabled = is_cwip_accounting_enabled(self.asset_category)
# check if expense already has been booked in case of cwip was enabled after purchasing asset
expense_booked = False
cwip_booked = False
if asset_bought_with_invoice:
expense_booked = frappe.db.sql("""SELECT name FROM `tabGL Entry` WHERE voucher_no = %s and account = %s""",
(purchase_document, fixed_asset_account), as_dict=1)
else:
cwip_booked = frappe.db.sql("""SELECT name FROM `tabGL Entry` WHERE voucher_no = %s and account = %s""",
(purchase_document, cwip_account), as_dict=1)
if cwip_enabled and (expense_booked or not cwip_booked):
# if expense has already booked from invoice or cwip is booked from receipt
if not purchase_document:
return False
elif not cwip_enabled and (not expense_booked or cwip_booked):
# if cwip is disabled but expense hasn't been booked yet
return True
elif cwip_enabled:
# default condition
return True
asset_bought_with_invoice = (purchase_document == self.purchase_invoice)
fixed_asset_account = self.get_fixed_asset_account()
cwip_enabled = is_cwip_accounting_enabled(self.asset_category)
cwip_account = self.get_cwip_account(cwip_enabled=cwip_enabled)
query = """SELECT name FROM `tabGL Entry` WHERE voucher_no = %s and account = %s"""
if asset_bought_with_invoice:
# with invoice purchase either expense or cwip has been booked
expense_booked = frappe.db.sql(query, (purchase_document, fixed_asset_account), as_dict=1)
if expense_booked:
# if expense is already booked from invoice then do not make gl entries regardless of cwip enabled/disabled
return False
cwip_booked = frappe.db.sql(query, (purchase_document, cwip_account), as_dict=1)
if cwip_booked:
# if cwip is booked from invoice then make gl entries regardless of cwip enabled/disabled
return True
else:
# with receipt purchase either cwip has been booked or no entries have been made
if not cwip_account:
# if cwip account isn't available do not make gl entries
return False
cwip_booked = frappe.db.sql(query, (purchase_document, cwip_account), as_dict=1)
# if cwip is not booked from receipt then do not make gl entries
# if cwip is booked from receipt then make gl entries
return cwip_booked
def get_purchase_document(self):
asset_bought_with_invoice = self.purchase_invoice and frappe.db.get_value('Purchase Invoice', self.purchase_invoice, 'update_stock')
@@ -489,20 +508,25 @@ class Asset(AccountsController):
return purchase_document
def get_asset_accounts(self):
fixed_asset_account = get_asset_category_account('fixed_asset_account', asset=self.name,
asset_category = self.asset_category, company = self.company)
def get_fixed_asset_account(self):
return get_asset_category_account('fixed_asset_account', None, self.name, None, self.asset_category, self.company)
def get_cwip_account(self, cwip_enabled=False):
cwip_account = None
try:
cwip_account = get_asset_account("capital_work_in_progress_account", self.name, self.asset_category, self.company)
except:
# if no cwip account found in category or company and "cwip is enabled" then raise else silently pass
if cwip_enabled:
raise
cwip_account = get_asset_account("capital_work_in_progress_account",
self.name, self.asset_category, self.company)
return fixed_asset_account, cwip_account
return cwip_account
def make_gl_entries(self):
gl_entries = []
purchase_document = self.get_purchase_document()
fixed_asset_account, cwip_account = self.get_asset_accounts()
fixed_asset_account, cwip_account = self.get_fixed_asset_account(), self.get_cwip_account()
if (purchase_document and self.purchase_receipt_amount and self.available_for_use_date <= nowdate()):

View File

@@ -58,7 +58,8 @@ def make_depreciation_entry(asset_name, date=None):
"account": accumulated_depreciation_account,
"credit_in_account_currency": d.depreciation_amount,
"reference_type": "Asset",
"reference_name": asset.name
"reference_name": asset.name,
"cost_center": ""
}
debit_entry = {
@@ -196,12 +197,14 @@ def get_gl_entries_on_asset_disposal(asset, selling_amount=0, finance_book=None)
{
"account": fixed_asset_account,
"credit_in_account_currency": asset.gross_purchase_amount,
"credit": asset.gross_purchase_amount
"credit": asset.gross_purchase_amount,
"cost_center": depreciation_cost_center
},
{
"account": accumulated_depr_account,
"debit_in_account_currency": accumulated_depr_amount,
"debit": accumulated_depr_amount
"debit": accumulated_depr_amount,
"cost_center": depreciation_cost_center
}
]

View File

@@ -9,6 +9,7 @@ from frappe.utils import cstr, nowdate, getdate, flt, get_last_day, add_days, ad
from erpnext.assets.doctype.asset.depreciation import post_depreciation_entries, scrap_asset, restore_asset
from erpnext.assets.doctype.asset.asset import make_sales_invoice
from erpnext.stock.doctype.purchase_receipt.test_purchase_receipt import make_purchase_receipt
from erpnext.accounts.doctype.purchase_invoice.test_purchase_invoice import make_purchase_invoice
from erpnext.stock.doctype.purchase_receipt.purchase_receipt import make_purchase_invoice as make_invoice
class TestAsset(unittest.TestCase):
@@ -374,19 +375,18 @@ class TestAsset(unittest.TestCase):
asset_name = frappe.db.get_value("Asset", {"purchase_receipt": pr.name}, 'name')
asset = frappe.get_doc('Asset', asset_name)
asset.calculate_depreciation = 1
asset.available_for_use_date = nowdate()
asset.purchase_date = nowdate()
asset.available_for_use_date = '2020-01-01'
asset.purchase_date = '2020-01-01'
asset.append("finance_books", {
"expected_value_after_useful_life": 10000,
"depreciation_method": "Straight Line",
"total_number_of_depreciations": 3,
"frequency_of_depreciation": 10,
"depreciation_start_date": nowdate()
"total_number_of_depreciations": 10,
"frequency_of_depreciation": 1
})
asset.insert()
asset.submit()
post_depreciation_entries(date=add_months(nowdate(), 10))
post_depreciation_entries(date=add_months('2020-01-01', 4))
scrap_asset(asset.name)
@@ -395,9 +395,9 @@ class TestAsset(unittest.TestCase):
self.assertTrue(asset.journal_entry_for_scrap)
expected_gle = (
("_Test Accumulated Depreciations - _TC", 30000.0, 0.0),
("_Test Accumulated Depreciations - _TC", 36000.0, 0.0),
("_Test Fixed Asset - _TC", 0.0, 100000.0),
("_Test Gain/Loss on Asset Disposal - _TC", 70000.0, 0.0)
("_Test Gain/Loss on Asset Disposal - _TC", 64000.0, 0.0)
)
gle = frappe.db.sql("""select account, debit, credit from `tabGL Entry`
@@ -469,8 +469,7 @@ class TestAsset(unittest.TestCase):
"expected_value_after_useful_life": 10000,
"depreciation_method": "Straight Line",
"total_number_of_depreciations": 3,
"frequency_of_depreciation": 10,
"depreciation_start_date": "2020-06-06"
"frequency_of_depreciation": 10
})
asset.insert()
accumulated_depreciation_after_full_schedule = \
@@ -563,81 +562,6 @@ class TestAsset(unittest.TestCase):
self.assertEqual(gle, expected_gle)
def test_gle_with_cwip_toggling(self):
# TEST: purchase an asset with cwip enabled and then disable cwip and try submitting the asset
frappe.db.set_value("Asset Category", "Computers", "enable_cwip_accounting", 1)
pr = make_purchase_receipt(item_code="Macbook Pro",
qty=1, rate=5000, do_not_submit=True, location="Test Location")
pr.set('taxes', [{
'category': 'Total',
'add_deduct_tax': 'Add',
'charge_type': 'On Net Total',
'account_head': '_Test Account Service Tax - _TC',
'description': '_Test Account Service Tax',
'cost_center': 'Main - _TC',
'rate': 5.0
}, {
'category': 'Valuation and Total',
'add_deduct_tax': 'Add',
'charge_type': 'On Net Total',
'account_head': '_Test Account Shipping Charges - _TC',
'description': '_Test Account Shipping Charges',
'cost_center': 'Main - _TC',
'rate': 5.0
}])
pr.submit()
expected_gle = (
("Asset Received But Not Billed - _TC", 0.0, 5250.0),
("CWIP Account - _TC", 5250.0, 0.0)
)
pr_gle = frappe.db.sql("""select account, debit, credit from `tabGL Entry`
where voucher_type='Purchase Receipt' and voucher_no = %s
order by account""", pr.name)
self.assertEqual(pr_gle, expected_gle)
pi = make_invoice(pr.name)
pi.submit()
expected_gle = (
("_Test Account Service Tax - _TC", 250.0, 0.0),
("_Test Account Shipping Charges - _TC", 250.0, 0.0),
("Asset Received But Not Billed - _TC", 5250.0, 0.0),
("Creditors - _TC", 0.0, 5500.0),
("Expenses Included In Asset Valuation - _TC", 0.0, 250.0),
)
pi_gle = frappe.db.sql("""select account, debit, credit from `tabGL Entry`
where voucher_type='Purchase Invoice' and voucher_no = %s
order by account""", pi.name)
self.assertEqual(pi_gle, expected_gle)
asset = frappe.db.get_value('Asset', {'purchase_receipt': pr.name, 'docstatus': 0}, 'name')
asset_doc = frappe.get_doc('Asset', asset)
month_end_date = get_last_day(nowdate())
asset_doc.available_for_use_date = nowdate() if nowdate() != month_end_date else add_days(nowdate(), -15)
self.assertEqual(asset_doc.gross_purchase_amount, 5250.0)
asset_doc.append("finance_books", {
"expected_value_after_useful_life": 200,
"depreciation_method": "Straight Line",
"total_number_of_depreciations": 3,
"frequency_of_depreciation": 10,
"depreciation_start_date": month_end_date
})
# disable cwip and try submitting
frappe.db.set_value("Asset Category", "Computers", "enable_cwip_accounting", 0)
asset_doc.submit()
# asset should have gl entries even if cwip is disabled
expected_gle = (
("_Test Fixed Asset - _TC", 5250.0, 0.0),
("CWIP Account - _TC", 0.0, 5250.0)
)
gle = frappe.db.sql("""select account, debit, credit from `tabGL Entry`
where voucher_type='Asset' and voucher_no = %s
order by account""", asset_doc.name)
self.assertEqual(gle, expected_gle)
frappe.db.set_value("Asset Category", "Computers", "enable_cwip_accounting", 1)
def test_expense_head(self):
pr = make_purchase_receipt(item_code="Macbook Pro",
qty=2, rate=200000.0, location="Test Location")
@@ -645,6 +569,74 @@ class TestAsset(unittest.TestCase):
doc = make_invoice(pr.name)
self.assertEquals('Asset Received But Not Billed - _TC', doc.items[0].expense_account)
def test_asset_cwip_toggling_cases(self):
cwip = frappe.db.get_value("Asset Category", "Computers", "enable_cwip_accounting")
name = frappe.db.get_value("Asset Category Account", filters={"parent": "Computers"}, fieldname=["name"])
cwip_acc = "CWIP Account - _TC"
frappe.db.set_value("Asset Category", "Computers", "enable_cwip_accounting", 0)
frappe.db.set_value("Asset Category Account", name, "capital_work_in_progress_account", "")
frappe.db.get_value("Company", "_Test Company", "capital_work_in_progress_account", "")
# case 0 -- PI with cwip disable, Asset with cwip disabled, No cwip account set
pi = make_purchase_invoice(item_code="Macbook Pro", qty=1, rate=200000.0, location="Test Location", update_stock=1)
asset = frappe.db.get_value('Asset', {'purchase_invoice': pi.name, 'docstatus': 0}, 'name')
asset_doc = frappe.get_doc('Asset', asset)
asset_doc.available_for_use_date = nowdate()
asset_doc.calculate_depreciation = 0
asset_doc.submit()
gle = frappe.db.sql("""select name from `tabGL Entry` where voucher_type='Asset' and voucher_no = %s""", asset_doc.name)
self.assertFalse(gle)
# case 1 -- PR with cwip disabled, Asset with cwip enabled
pr = make_purchase_receipt(item_code="Macbook Pro", qty=1, rate=200000.0, location="Test Location")
frappe.db.set_value("Asset Category", "Computers", "enable_cwip_accounting", 1)
frappe.db.set_value("Asset Category Account", name, "capital_work_in_progress_account", cwip_acc)
asset = frappe.db.get_value('Asset', {'purchase_receipt': pr.name, 'docstatus': 0}, 'name')
asset_doc = frappe.get_doc('Asset', asset)
asset_doc.available_for_use_date = nowdate()
asset_doc.calculate_depreciation = 0
asset_doc.submit()
gle = frappe.db.sql("""select name from `tabGL Entry` where voucher_type='Asset' and voucher_no = %s""", asset_doc.name)
self.assertFalse(gle)
# case 2 -- PR with cwip enabled, Asset with cwip disabled
pr = make_purchase_receipt(item_code="Macbook Pro", qty=1, rate=200000.0, location="Test Location")
frappe.db.set_value("Asset Category", "Computers", "enable_cwip_accounting", 0)
asset = frappe.db.get_value('Asset', {'purchase_receipt': pr.name, 'docstatus': 0}, 'name')
asset_doc = frappe.get_doc('Asset', asset)
asset_doc.available_for_use_date = nowdate()
asset_doc.calculate_depreciation = 0
asset_doc.submit()
gle = frappe.db.sql("""select name from `tabGL Entry` where voucher_type='Asset' and voucher_no = %s""", asset_doc.name)
self.assertTrue(gle)
# case 3 -- PI with cwip disabled, Asset with cwip enabled
pi = make_purchase_invoice(item_code="Macbook Pro", qty=1, rate=200000.0, location="Test Location", update_stock=1)
frappe.db.set_value("Asset Category", "Computers", "enable_cwip_accounting", 1)
asset = frappe.db.get_value('Asset', {'purchase_invoice': pi.name, 'docstatus': 0}, 'name')
asset_doc = frappe.get_doc('Asset', asset)
asset_doc.available_for_use_date = nowdate()
asset_doc.calculate_depreciation = 0
asset_doc.submit()
gle = frappe.db.sql("""select name from `tabGL Entry` where voucher_type='Asset' and voucher_no = %s""", asset_doc.name)
self.assertFalse(gle)
# case 4 -- PI with cwip enabled, Asset with cwip disabled
pi = make_purchase_invoice(item_code="Macbook Pro", qty=1, rate=200000.0, location="Test Location", update_stock=1)
frappe.db.set_value("Asset Category", "Computers", "enable_cwip_accounting", 0)
asset = frappe.db.get_value('Asset', {'purchase_invoice': pi.name, 'docstatus': 0}, 'name')
asset_doc = frappe.get_doc('Asset', asset)
asset_doc.available_for_use_date = nowdate()
asset_doc.calculate_depreciation = 0
asset_doc.submit()
gle = frappe.db.sql("""select name from `tabGL Entry` where voucher_type='Asset' and voucher_no = %s""", asset_doc.name)
self.assertTrue(gle)
frappe.db.set_value("Asset Category", "Computers", "enable_cwip_accounting", cwip)
frappe.db.set_value("Asset Category Account", name, "capital_work_in_progress_account", cwip_acc)
frappe.db.get_value("Company", "_Test Company", "capital_work_in_progress_account", cwip_acc)
def create_asset_data():
if not frappe.db.exists("Asset Category", "Computers"):

View File

@@ -5,7 +5,7 @@
from __future__ import unicode_literals
import frappe
from frappe import _
from frappe.utils import cint
from frappe.utils import cint, get_link_to_form
from frappe.model.document import Document
class AssetCategory(Document):
@@ -13,6 +13,7 @@ class AssetCategory(Document):
self.validate_finance_books()
self.validate_account_types()
self.validate_account_currency()
self.valide_cwip_account()
def validate_finance_books(self):
for d in self.finance_books:
@@ -58,6 +59,21 @@ class AssetCategory(Document):
frappe.throw(_("Row #{}: {} of {} should be {}. Please modify the account or select a different account.")
.format(d.idx, frappe.unscrub(key_to_match), frappe.bold(selected_account), frappe.bold(expected_key_type)),
title=_("Invalid Account"))
def valide_cwip_account(self):
if self.enable_cwip_accounting:
missing_cwip_accounts_for_company = []
for d in self.accounts:
if (not d.capital_work_in_progress_account and
not frappe.db.get_value("Company", d.company_name, "capital_work_in_progress_account")):
missing_cwip_accounts_for_company.append(get_link_to_form("Company", d.company_name))
if missing_cwip_accounts_for_company:
msg = _("""To enable Capital Work in Progress Accounting, """)
msg += _("""you must select Capital Work in Progress Account in accounts table""")
msg += "<br><br>"
msg += _("You can also set default CWIP account in Company {}").format(", ".join(missing_cwip_accounts_for_company))
frappe.throw(msg, title=_("Missing Account"))
@frappe.whitelist()

View File

@@ -26,4 +26,22 @@ class TestAssetCategory(unittest.TestCase):
asset_category.insert()
except frappe.DuplicateEntryError:
pass
def test_cwip_accounting(self):
company_cwip_acc = frappe.db.get_value("Company", "_Test Company", "capital_work_in_progress_account")
frappe.db.set_value("Company", "_Test Company", "capital_work_in_progress_account", "")
asset_category = frappe.new_doc("Asset Category")
asset_category.asset_category_name = "Computers"
asset_category.enable_cwip_accounting = 1
asset_category.total_number_of_depreciations = 3
asset_category.frequency_of_depreciation = 3
asset_category.append("accounts", {
"company_name": "_Test Company",
"fixed_asset_account": "_Test Fixed Asset - _TC",
"accumulated_depreciation_account": "_Test Accumulated Depreciations - _TC",
"depreciation_expense_account": "_Test Depreciations - _TC"
})
self.assertRaises(frappe.ValidationError, asset_category.insert)

View File

@@ -1,347 +1,100 @@
{
"allow_copy": 0,
"allow_events_in_timeline": 0,
"allow_guest_to_view": 0,
"allow_import": 0,
"allow_rename": 0,
"beta": 0,
"creation": "2018-05-08 14:44:37.095570",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "",
"editable_grid": 1,
"engine": "InnoDB",
"actions": [],
"creation": "2018-05-08 14:44:37.095570",
"doctype": "DocType",
"editable_grid": 1,
"engine": "InnoDB",
"field_order": [
"finance_book",
"depreciation_method",
"total_number_of_depreciations",
"column_break_5",
"frequency_of_depreciation",
"depreciation_start_date",
"expected_value_after_useful_life",
"value_after_depreciation",
"rate_of_depreciation"
],
"fields": [
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"depends_on": "",
"fetch_if_empty": 0,
"fieldname": "finance_book",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Finance Book",
"length": 0,
"no_copy": 0,
"options": "Finance Book",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "finance_book",
"fieldtype": "Link",
"in_list_view": 1,
"label": "Finance Book",
"options": "Finance Book"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fetch_if_empty": 0,
"fieldname": "depreciation_method",
"fieldtype": "Select",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Depreciation Method",
"length": 0,
"no_copy": 0,
"options": "\nStraight Line\nDouble Declining Balance\nWritten Down Value\nManual",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "depreciation_method",
"fieldtype": "Select",
"in_list_view": 1,
"label": "Depreciation Method",
"options": "\nStraight Line\nDouble Declining Balance\nWritten Down Value\nManual",
"reqd": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fetch_if_empty": 0,
"fieldname": "total_number_of_depreciations",
"fieldtype": "Int",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Total Number of Depreciations",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "total_number_of_depreciations",
"fieldtype": "Int",
"in_list_view": 1,
"label": "Total Number of Depreciations",
"reqd": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fetch_if_empty": 0,
"fieldname": "column_break_5",
"fieldtype": "Column Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "column_break_5",
"fieldtype": "Column Break"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fetch_if_empty": 0,
"fieldname": "frequency_of_depreciation",
"fieldtype": "Int",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Frequency of Depreciation (Months)",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "frequency_of_depreciation",
"fieldtype": "Int",
"in_list_view": 1,
"label": "Frequency of Depreciation (Months)",
"reqd": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"depends_on": "eval:parent.doctype == 'Asset'",
"fetch_if_empty": 0,
"fieldname": "depreciation_start_date",
"fieldtype": "Date",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Depreciation Start Date",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"depends_on": "eval:parent.doctype == 'Asset'",
"fieldname": "depreciation_start_date",
"fieldtype": "Date",
"in_list_view": 1,
"label": "Depreciation Posting Date",
"mandatory_depends_on": "eval:parent.doctype == 'Asset'",
"reqd": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"default": "0",
"depends_on": "eval:parent.doctype == 'Asset'",
"fetch_if_empty": 0,
"fieldname": "expected_value_after_useful_life",
"fieldtype": "Currency",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Expected Value After Useful Life",
"length": 0,
"no_copy": 0,
"options": "Company:company:default_currency",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"default": "0",
"depends_on": "eval:parent.doctype == 'Asset'",
"fieldname": "expected_value_after_useful_life",
"fieldtype": "Currency",
"label": "Expected Value After Useful Life",
"options": "Company:company:default_currency"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fetch_if_empty": 0,
"fieldname": "value_after_depreciation",
"fieldtype": "Currency",
"hidden": 1,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Value After Depreciation",
"length": 0,
"no_copy": 1,
"options": "Company:company:default_currency",
"permlevel": 0,
"precision": "",
"print_hide": 1,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "value_after_depreciation",
"fieldtype": "Currency",
"hidden": 1,
"label": "Value After Depreciation",
"no_copy": 1,
"options": "Company:company:default_currency",
"print_hide": 1,
"read_only": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"depends_on": "eval:doc.depreciation_method == 'Written Down Value'",
"description": "In Percentage",
"fetch_if_empty": 0,
"fieldname": "rate_of_depreciation",
"fieldtype": "Percent",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Rate of Depreciation",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
"depends_on": "eval:doc.depreciation_method == 'Written Down Value'",
"description": "In Percentage",
"fieldname": "rate_of_depreciation",
"fieldtype": "Percent",
"label": "Rate of Depreciation"
}
],
"has_web_view": 0,
"hide_toolbar": 0,
"idx": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 1,
"max_attachments": 0,
"modified": "2019-04-09 19:45:14.523488",
"modified_by": "Administrator",
"module": "Assets",
"name": "Asset Finance Book",
"name_case": "",
"owner": "Administrator",
"permissions": [],
"quick_entry": 1,
"read_only": 0,
"show_name_in_global_search": 0,
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 1,
"track_seen": 0,
"track_views": 0
],
"index_web_pages_for_search": 1,
"istable": 1,
"links": [],
"modified": "2020-10-30 15:22:29.119868",
"modified_by": "Administrator",
"module": "Assets",
"name": "Asset Finance Book",
"owner": "Administrator",
"permissions": [],
"quick_entry": 1,
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 1
}

View File

@@ -106,8 +106,9 @@ def update_maintenance_log(asset_maintenance, item_code, item_name, task):
maintenance_log.save()
@frappe.whitelist()
@frappe.validate_and_sanitize_search_inputs
def get_team_members(doctype, txt, searchfield, start, page_len, filters):
return frappe.db.get_values('Maintenance Team Member', { 'parent': filters.get("maintenance_team") })
return frappe.db.get_values('Maintenance Team Member', { 'parent': filters.get("maintenance_team") }, "team_member")
@frappe.whitelist()
def get_maintenance_log(asset_name):

View File

@@ -11,7 +11,7 @@ from erpnext.assets.doctype.asset_maintenance.asset_maintenance import calculate
class AssetMaintenanceLog(Document):
def validate(self):
if getdate(self.due_date) < getdate(nowdate()):
if getdate(self.due_date) < getdate(nowdate()) and self.maintenance_status not in ["Completed", "Cancelled"]:
self.maintenance_status = "Overdue"
if self.maintenance_status == "Completed" and not self.completion_date:
@@ -41,6 +41,7 @@ class AssetMaintenanceLog(Document):
asset_maintenance_doc.save()
@frappe.whitelist()
@frappe.validate_and_sanitize_search_inputs
def get_maintenance_tasks(doctype, txt, searchfield, start, page_len, filters):
asset_maintenance_tasks = frappe.db.get_values('Asset Maintenance Task', {'parent':filters.get("asset_maintenance")}, 'maintenance_task')
return asset_maintenance_tasks

View File

@@ -1,14 +1,15 @@
frappe.listview_settings['Asset Maintenance Log'] = {
add_fields: ["maintenance_status"],
has_indicator_for_draft: 1,
get_indicator: function(doc) {
if(doc.maintenance_status=="Pending") {
return [__("Pending"), "orange"];
} else if(doc.maintenance_status=="Completed") {
return [__("Completed"), "green"];
} else if(doc.maintenance_status=="Cancelled") {
return [__("Cancelled"), "red"];
} else if(doc.maintenance_status=="Overdue") {
return [__("Overdue"), "red"];
if (doc.maintenance_status=="Planned") {
return [__(doc.maintenance_status), "orange", "status,=," + doc.maintenance_status];
} else if (doc.maintenance_status=="Completed") {
return [__(doc.maintenance_status), "green", "status,=," + doc.maintenance_status];
} else if (doc.maintenance_status=="Cancelled") {
return [__(doc.maintenance_status), "red", "status,=," + doc.maintenance_status];
} else if (doc.maintenance_status=="Overdue") {
return [__(doc.maintenance_status), "red", "status,=," + doc.maintenance_status];
}
}
};

View File

@@ -32,8 +32,7 @@ class TestAssetMovement(unittest.TestCase):
"next_depreciation_date": "2020-12-31",
"depreciation_method": "Straight Line",
"total_number_of_depreciations": 3,
"frequency_of_depreciation": 10,
"depreciation_start_date": "2020-06-06"
"frequency_of_depreciation": 10
})
if asset.docstatus == 0:
@@ -82,8 +81,7 @@ class TestAssetMovement(unittest.TestCase):
"next_depreciation_date": "2020-12-31",
"depreciation_method": "Straight Line",
"total_number_of_depreciations": 3,
"frequency_of_depreciation": 10,
"depreciation_start_date": "2020-06-06"
"frequency_of_depreciation": 10
})
if asset.docstatus == 0:
asset.submit()

View File

@@ -148,24 +148,23 @@ def get_data(filters):
for asset in assets_record:
asset_value = asset.gross_purchase_amount - flt(asset.opening_accumulated_depreciation) \
- flt(depreciation_amount_map.get(asset.name))
if asset_value:
row = {
"asset_id": asset.name,
"asset_name": asset.asset_name,
"status": asset.status,
"department": asset.department,
"cost_center": asset.cost_center,
"vendor_name": pr_supplier_map.get(asset.purchase_receipt) or pi_supplier_map.get(asset.purchase_invoice),
"gross_purchase_amount": asset.gross_purchase_amount,
"opening_accumulated_depreciation": asset.opening_accumulated_depreciation,
"depreciated_amount": depreciation_amount_map.get(asset.name) or 0.0,
"available_for_use_date": asset.available_for_use_date,
"location": asset.location,
"asset_category": asset.asset_category,
"purchase_date": asset.purchase_date,
"asset_value": asset_value
}
data.append(row)
row = {
"asset_id": asset.asset_id,
"asset_name": asset.asset_name,
"status": asset.status,
"department": asset.department,
"cost_center": asset.cost_center,
"vendor_name": pr_supplier_map.get(asset.purchase_receipt) or pi_supplier_map.get(asset.purchase_invoice),
"gross_purchase_amount": asset.gross_purchase_amount,
"opening_accumulated_depreciation": asset.opening_accumulated_depreciation,
"depreciated_amount": depreciation_amount_map.get(asset.asset_id) or 0.0,
"available_for_use_date": asset.available_for_use_date,
"location": asset.location,
"asset_category": asset.asset_category,
"purchase_date": asset.purchase_date,
"asset_value": asset_value
}
data.append(row)
return data

View File

@@ -7,12 +7,6 @@ frappe.provide("erpnext.buying");
frappe.ui.form.on("Purchase Order", {
setup: function(frm) {
frm.custom_make_buttons = {
'Purchase Receipt': 'Receipt',
'Purchase Invoice': 'Invoice',
'Stock Entry': 'Material to Supplier',
'Payment Entry': 'Payment'
}
frm.set_query("reserve_warehouse", "supplied_items", function() {
return {
@@ -36,20 +30,6 @@ frappe.ui.form.on("Purchase Order", {
},
refresh: function(frm) {
if(frm.doc.docstatus === 1 && frm.doc.status !== 'Closed'
&& flt(frm.doc.per_received) < 100 && flt(frm.doc.per_billed) < 100) {
frm.add_custom_button(__('Update Items'), () => {
erpnext.utils.update_child_items({
frm: frm,
child_docname: "items",
child_doctype: "Purchase Order Detail",
cannot_add_row: false,
})
});
}
},
onload: function(frm) {
set_schedule_date(frm);
if (!frm.doc.transaction_date){
@@ -76,6 +56,18 @@ frappe.ui.form.on("Purchase Order Item", {
});
erpnext.buying.PurchaseOrderController = erpnext.buying.BuyingController.extend({
setup: function() {
this.frm.custom_make_buttons = {
'Purchase Receipt': 'Receipt',
'Purchase Invoice': 'Invoice',
'Stock Entry': 'Material to Supplier',
'Payment Entry': 'Payment',
}
this._super();
},
refresh: function(doc, cdt, cdn) {
var me = this;
this._super();
@@ -99,6 +91,16 @@ erpnext.buying.PurchaseOrderController = erpnext.buying.BuyingController.extend(
if(doc.docstatus == 1) {
if(!in_list(["Closed", "Delivered"], doc.status)) {
if(this.frm.doc.status !== 'Closed' && flt(this.frm.doc.per_received) < 100 && flt(this.frm.doc.per_billed) < 100) {
this.frm.add_custom_button(__('Update Items'), () => {
erpnext.utils.update_child_items({
frm: this.frm,
child_docname: "items",
child_doctype: "Purchase Order Detail",
cannot_add_row: false,
})
});
}
if (this.frm.has_perm("submit")) {
if(flt(doc.per_billed, 6) < 100 || flt(doc.per_received, 6) < 100) {
if (doc.status != "On Hold") {
@@ -123,14 +125,14 @@ erpnext.buying.PurchaseOrderController = erpnext.buying.BuyingController.extend(
}
if(doc.status != "Closed") {
if (doc.status != "On Hold") {
if(flt(doc.per_received, 2) < 100 && allow_receipt) {
if(flt(doc.per_received) < 100 && allow_receipt) {
cur_frm.add_custom_button(__('Receipt'), this.make_purchase_receipt, __('Create'));
if(doc.is_subcontracted==="Yes" && me.has_unsupplied_items()) {
cur_frm.add_custom_button(__('Material to Supplier'),
function() { me.make_stock_entry(); }, __("Transfer"));
}
}
if(flt(doc.per_billed, 2) < 100)
if(flt(doc.per_billed) < 100)
cur_frm.add_custom_button(__('Invoice'),
this.make_purchase_invoice, __('Create'));

View File

@@ -1,5 +1,4 @@
{
"actions": [],
"allow_import": 1,
"autoname": "naming_series:",
"creation": "2013-05-21 16:16:39",
@@ -998,6 +997,7 @@
"print_hide": 1
},
{
"collapsible": 1,
"fieldname": "subscription_section",
"fieldtype": "Section Break",
"label": "Subscription Section"
@@ -1056,7 +1056,7 @@
"idx": 105,
"is_submittable": 1,
"links": [],
"modified": "2020-06-12 14:08:11.777120",
"modified": "2020-09-14 14:36:12.418690",
"modified_by": "Administrator",
"module": "Buying",
"name": "Purchase Order",
@@ -1113,5 +1113,6 @@
"sort_field": "modified",
"sort_order": "DESC",
"timeline_field": "supplier",
"title_field": "title"
"title_field": "supplier",
"track_changes": 1
}

View File

@@ -17,6 +17,8 @@ from erpnext.stock.doctype.material_request.material_request import make_purchas
from erpnext.stock.doctype.stock_entry.test_stock_entry import make_stock_entry
from erpnext.controllers.accounts_controller import update_child_qty_rate
from erpnext.controllers.status_updater import OverAllowanceError
from erpnext.stock.doctype.batch.test_batch import make_new_batch
from erpnext.controllers.buying_controller import get_backflushed_subcontracted_raw_materials
class TestPurchaseOrder(unittest.TestCase):
def test_make_purchase_receipt(self):
@@ -200,6 +202,91 @@ class TestPurchaseOrder(unittest.TestCase):
self.assertRaises(frappe.ValidationError, update_child_qty_rate,'Purchase Order', trans_item, po.name)
frappe.set_user("Administrator")
def test_update_child_with_tax_template(self):
"""
Test Action: Create a PO with one item having its tax account head already in the PO.
Add the same item + new item with tax template via Update Items.
Expected result: First Item's tax row is updated. New tax row is added for second Item.
"""
if not frappe.db.exists("Item", "Test Item with Tax"):
make_item("Test Item with Tax", {
'is_stock_item': 1,
})
if not frappe.db.exists("Item Tax Template", {"title": 'Test Update Items Template'}):
frappe.get_doc({
'doctype': 'Item Tax Template',
'title': 'Test Update Items Template',
'company': '_Test Company',
'taxes': [
{
'tax_type': "_Test Account Service Tax - _TC",
'tax_rate': 10,
}
]
}).insert()
new_item_with_tax = frappe.get_doc("Item", "Test Item with Tax")
new_item_with_tax.append("taxes", {
"item_tax_template": "Test Update Items Template",
"valid_from": nowdate()
})
new_item_with_tax.save()
tax_template = "_Test Account Excise Duty @ 10"
item = "_Test Item Home Desktop 100"
if not frappe.db.exists("Item Tax", {"parent":item, "item_tax_template":tax_template}):
item_doc = frappe.get_doc("Item", item)
item_doc.append("taxes", {
"item_tax_template": tax_template,
"valid_from": nowdate()
})
item_doc.save()
else:
# update valid from
frappe.db.sql("""UPDATE `tabItem Tax` set valid_from = CURDATE()
where parent = %(item)s and item_tax_template = %(tax)s""",
{"item": item, "tax": tax_template})
po = create_purchase_order(item_code=item, qty=1, do_not_save=1)
po.append("taxes", {
"account_head": "_Test Account Excise Duty - _TC",
"charge_type": "On Net Total",
"cost_center": "_Test Cost Center - _TC",
"description": "Excise Duty",
"doctype": "Purchase Taxes and Charges",
"rate": 10
})
po.insert()
po.submit()
self.assertEqual(po.taxes[0].tax_amount, 50)
self.assertEqual(po.taxes[0].total, 550)
items = json.dumps([
{'item_code' : item, 'rate' : 500, 'qty' : 1, 'docname': po.items[0].name},
{'item_code' : item, 'rate' : 100, 'qty' : 1}, # added item whose tax account head already exists in PO
{'item_code' : new_item_with_tax.name, 'rate' : 100, 'qty' : 1} # added item whose tax account head is missing in PO
])
update_child_qty_rate('Purchase Order', items, po.name)
po.reload()
self.assertEqual(po.taxes[0].tax_amount, 70)
self.assertEqual(po.taxes[0].total, 770)
self.assertEqual(po.taxes[1].account_head, "_Test Account Service Tax - _TC")
self.assertEqual(po.taxes[1].tax_amount, 70)
self.assertEqual(po.taxes[1].total, 840)
# teardown
frappe.db.sql("""UPDATE `tabItem Tax` set valid_from = NULL
where parent = %(item)s and item_tax_template = %(tax)s""", {"item": item, "tax": tax_template})
po.cancel()
po.delete()
new_item_with_tax.delete()
frappe.get_doc("Item Tax Template", "Test Update Items Template").delete()
def test_update_qty(self):
po = create_purchase_order()
@@ -580,7 +667,7 @@ class TestPurchaseOrder(unittest.TestCase):
def test_exploded_items_in_subcontracted(self):
item_code = "_Test Subcontracted FG Item 1"
make_subcontracted_item(item_code)
make_subcontracted_item(item_code=item_code)
po = create_purchase_order(item_code=item_code, qty=1,
is_subcontracted="Yes", supplier_warehouse="_Test Warehouse 1 - _TC")
@@ -602,7 +689,7 @@ class TestPurchaseOrder(unittest.TestCase):
def test_backflush_based_on_stock_entry(self):
item_code = "_Test Subcontracted FG Item 1"
make_subcontracted_item(item_code)
make_subcontracted_item(item_code=item_code)
make_item('Sub Contracted Raw Material 1', {
'is_stock_item': 1,
'is_sub_contracted_item': 1
@@ -661,6 +748,133 @@ class TestPurchaseOrder(unittest.TestCase):
update_backflush_based_on("BOM")
def test_backflushed_based_on_for_multiple_batches(self):
item_code = "_Test Subcontracted FG Item 2"
make_item('Sub Contracted Raw Material 2', {
'is_stock_item': 1,
'is_sub_contracted_item': 1
})
make_subcontracted_item(item_code=item_code, has_batch_no=1, create_new_batch=1,
raw_materials=["Sub Contracted Raw Material 2"])
update_backflush_based_on("Material Transferred for Subcontract")
order_qty = 500
po = create_purchase_order(item_code=item_code, qty=order_qty,
is_subcontracted="Yes", supplier_warehouse="_Test Warehouse 1 - _TC")
make_stock_entry(target="_Test Warehouse - _TC",
item_code = "Sub Contracted Raw Material 2", qty=552, basic_rate=100)
rm_items = [
{"item_code":item_code,"rm_item_code":"Sub Contracted Raw Material 2","item_name":"_Test Item",
"qty":552,"warehouse":"_Test Warehouse - _TC", "stock_uom":"Nos"}]
rm_item_string = json.dumps(rm_items)
se = frappe.get_doc(make_subcontract_transfer_entry(po.name, rm_item_string))
se.submit()
for batch in ["ABCD1", "ABCD2", "ABCD3", "ABCD4"]:
make_new_batch(batch_id=batch, item_code=item_code)
pr = make_purchase_receipt(po.name)
# partial receipt
pr.get('items')[0].qty = 30
pr.get('items')[0].batch_no = "ABCD1"
purchase_order = po.name
purchase_order_item = po.items[0].name
for batch_no, qty in {"ABCD2": 60, "ABCD3": 70, "ABCD4":40}.items():
pr.append("items", {
"item_code": pr.get('items')[0].item_code,
"item_name": pr.get('items')[0].item_name,
"uom": pr.get('items')[0].uom,
"stock_uom": pr.get('items')[0].stock_uom,
"warehouse": pr.get('items')[0].warehouse,
"conversion_factor": pr.get('items')[0].conversion_factor,
"cost_center": pr.get('items')[0].cost_center,
"rate": pr.get('items')[0].rate,
"qty": qty,
"batch_no": batch_no,
"purchase_order": purchase_order,
"purchase_order_item": purchase_order_item
})
pr.submit()
pr1 = make_purchase_receipt(po.name)
pr1.get('items')[0].qty = 300
pr1.get('items')[0].batch_no = "ABCD1"
pr1.save()
pr_key = ("Sub Contracted Raw Material 2", po.name)
consumed_qty = get_backflushed_subcontracted_raw_materials([po.name]).get(pr_key)
self.assertTrue(pr1.supplied_items[0].consumed_qty > 0)
self.assertTrue(pr1.supplied_items[0].consumed_qty, flt(552.0) - flt(consumed_qty))
update_backflush_based_on("BOM")
def test_supplied_qty_against_subcontracted_po(self):
item_code = "_Test Subcontracted FG Item 5"
make_item('Sub Contracted Raw Material 4', {
'is_stock_item': 1,
'is_sub_contracted_item': 1
})
make_subcontracted_item(item_code=item_code, raw_materials=["Sub Contracted Raw Material 4"])
update_backflush_based_on("Material Transferred for Subcontract")
order_qty = 250
po = create_purchase_order(item_code=item_code, qty=order_qty,
is_subcontracted="Yes", supplier_warehouse="_Test Warehouse 1 - _TC", do_not_save=True)
# Add same subcontracted items multiple times
po.append("items", {
"item_code": item_code,
"qty": order_qty,
"schedule_date": add_days(nowdate(), 1),
"warehouse": "_Test Warehouse - _TC"
})
po.set_missing_values()
po.submit()
# Material receipt entry for the raw materials which will be send to supplier
make_stock_entry(target="_Test Warehouse - _TC",
item_code = "Sub Contracted Raw Material 4", qty=500, basic_rate=100)
rm_items = [
{
"item_code":item_code,"rm_item_code":"Sub Contracted Raw Material 4","item_name":"_Test Item",
"qty":250,"warehouse":"_Test Warehouse - _TC", "stock_uom":"Nos", "name": po.supplied_items[0].name
},
{
"item_code":item_code,"rm_item_code":"Sub Contracted Raw Material 4","item_name":"_Test Item",
"qty":250,"warehouse":"_Test Warehouse - _TC", "stock_uom":"Nos"
},
]
# Raw Materials transfer entry from stores to supplier's warehouse
rm_item_string = json.dumps(rm_items)
se = frappe.get_doc(make_subcontract_transfer_entry(po.name, rm_item_string))
se.submit()
# Test po_detail field has value or not
for item_row in se.items:
self.assertEqual(item_row.po_detail, po.supplied_items[item_row.idx - 1].name)
po_doc = frappe.get_doc("Purchase Order", po.name)
for row in po_doc.supplied_items:
# Valid that whether transferred quantity is matching with supplied qty or not in the purchase order
self.assertEqual(row.supplied_qty, 250.0)
update_backflush_based_on("BOM")
def test_advance_payment_entry_unlink_against_purchase_order(self):
from erpnext.accounts.doctype.payment_entry.test_payment_entry import get_payment_entry
frappe.db.set_value("Accounts Settings", "Accounts Settings",
@@ -712,27 +926,33 @@ def make_pr_against_po(po, received_qty=0):
pr.submit()
return pr
def make_subcontracted_item(item_code):
def make_subcontracted_item(**args):
from erpnext.manufacturing.doctype.production_plan.test_production_plan import make_bom
if not frappe.db.exists('Item', item_code):
make_item(item_code, {
args = frappe._dict(args)
if not frappe.db.exists('Item', args.item_code):
make_item(args.item_code, {
'is_stock_item': 1,
'is_sub_contracted_item': 1
'is_sub_contracted_item': 1,
'has_batch_no': args.get("has_batch_no") or 0
})
if not frappe.db.exists('Item', "Test Extra Item 1"):
make_item("Test Extra Item 1", {
'is_stock_item': 1,
})
if not args.raw_materials:
if not frappe.db.exists('Item', "Test Extra Item 1"):
make_item("Test Extra Item 1", {
'is_stock_item': 1,
})
if not frappe.db.exists('Item', "Test Extra Item 2"):
make_item("Test Extra Item 2", {
'is_stock_item': 1,
})
if not frappe.db.exists('Item', "Test Extra Item 2"):
make_item("Test Extra Item 2", {
'is_stock_item': 1,
})
if not frappe.db.get_value('BOM', {'item': item_code}, 'name'):
make_bom(item = item_code, raw_materials = ['_Test FG Item', 'Test Extra Item 1'])
args.raw_materials = ['_Test FG Item', 'Test Extra Item 1']
if not frappe.db.get_value('BOM', {'item': args.item_code}, 'name'):
make_bom(item = args.item_code, raw_materials = args.get("raw_materials"))
def update_backflush_based_on(based_on):
doc = frappe.get_doc('Buying Settings')

View File

@@ -166,7 +166,8 @@ frappe.ui.form.on("Request for Quotation",{
{ "fieldtype": "Select", "label": __("Supplier"),
"fieldname": "supplier",
"options": doc.suppliers.map(d => d.supplier),
"reqd": 1 },
"reqd": 1,
"default": doc.suppliers.length === 1 ? doc.suppliers[0].supplier_name : "" },
{ "fieldtype": "Button", "label": __('Create Supplier Quotation'),
"fieldname": "make_supplier_quotation", "cssClass": "btn-primary" },
]

View File

@@ -25,6 +25,7 @@ class RequestforQuotation(BuyingController):
self.validate_duplicate_supplier()
self.validate_supplier_list()
validate_for_items(self)
super(RequestforQuotation, self).set_qty_as_per_stock_uom()
self.update_email_id()
def validate_duplicate_supplier(self):
@@ -50,7 +51,7 @@ class RequestforQuotation(BuyingController):
def validate_email_id(self, args):
if not args.email_id:
frappe.throw(_("Row {0}: For supplier {0} Email Address is required to send email").format(args.idx, args.supplier))
frappe.throw(_("Row {0}: For Supplier {0}, Email Address is Required to Send Email").format(args.idx, args.supplier))
def on_submit(self):
frappe.db.set(self, 'status', 'Submitted')
@@ -153,7 +154,7 @@ class RequestforQuotation(BuyingController):
sender=sender,attachments = attachments, send_email=True,
doctype=self.doctype, name=self.name)["name"]
frappe.msgprint(_("Email sent to supplier {0}").format(data.supplier))
frappe.msgprint(_("Email Sent to Supplier {0}").format(data.supplier))
def get_attachments(self):
attachments = [d.name for d in get_attachments(self.doctype, self.name)]
@@ -192,7 +193,7 @@ def send_supplier_emails(rfq_name):
def check_portal_enabled(reference_doctype):
if not frappe.db.get_value('Portal Menu Item',
{'reference_doctype': reference_doctype}, 'enabled'):
frappe.throw(_("Request for Quotation is disabled to access from portal, for more check portal settings."))
frappe.throw(_("The Access to Request for Quotation From Portal is Disabled. To Allow Access, Enable it in Portal Settings."))
def get_list_context(context=None):
from erpnext.controllers.website_list_for_contact import get_list_context
@@ -205,6 +206,8 @@ def get_list_context(context=None):
})
return list_context
@frappe.whitelist()
@frappe.validate_and_sanitize_search_inputs
def get_supplier_contacts(doctype, txt, searchfield, start, page_len, filters):
return frappe.db.sql("""select `tabContact`.name from `tabContact`, `tabDynamic Link`
where `tabDynamic Link`.link_doctype = 'Supplier' and (`tabDynamic Link`.link_name=%(name)s
@@ -258,7 +261,7 @@ def create_supplier_quotation(doc):
sq_doc.flags.ignore_permissions = True
sq_doc.run_method("set_missing_values")
sq_doc.save()
frappe.msgprint(_("Supplier Quotation {0} created").format(sq_doc.name))
frappe.msgprint(_("Supplier Quotation {0} Created").format(sq_doc.name))
return sq_doc.name
except Exception:
return None
@@ -278,6 +281,7 @@ def create_rfq_items(sq_doc, supplier, data):
"description": data.description,
"qty": data.qty,
"rate": data.rate,
"conversion_factor": data.conversion_factor if data.conversion_factor else None,
"supplier_part_no": frappe.db.get_value("Item Supplier", {'parent': data.item_code, 'supplier': supplier}, "supplier_part_no"),
"warehouse": data.warehouse or '',
"request_for_quotation_item": data.name,

View File

@@ -6,12 +6,14 @@ from __future__ import unicode_literals
import unittest
import frappe
from erpnext.templates.pages.rfq import check_supplier_has_docname_access
from frappe.utils import nowdate
from erpnext.stock.doctype.item.test_item import make_item
from erpnext.templates.pages.rfq import check_supplier_has_docname_access
from erpnext.buying.doctype.request_for_quotation.request_for_quotation import make_supplier_quotation
from erpnext.buying.doctype.request_for_quotation.request_for_quotation import create_supplier_quotation
class TestRequestforQuotation(unittest.TestCase):
def test_quote_status(self):
from erpnext.buying.doctype.request_for_quotation.request_for_quotation import make_supplier_quotation
rfq = make_request_for_quotation()
self.assertEqual(rfq.get('suppliers')[0].quote_status, 'Pending')
@@ -31,7 +33,6 @@ class TestRequestforQuotation(unittest.TestCase):
self.assertEqual(rfq.get('suppliers')[1].quote_status, 'No Quote')
def test_make_supplier_quotation(self):
from erpnext.buying.doctype.request_for_quotation.request_for_quotation import make_supplier_quotation
rfq = make_request_for_quotation()
sq = make_supplier_quotation(rfq.name, rfq.get('suppliers')[0].supplier)
@@ -51,15 +52,13 @@ class TestRequestforQuotation(unittest.TestCase):
self.assertEqual(sq1.get('items')[0].qty, 5)
def test_make_supplier_quotation_with_special_characters(self):
from erpnext.buying.doctype.request_for_quotation.request_for_quotation import make_supplier_quotation
frappe.delete_doc_if_exists("Supplier", "_Test Supplier '1", force=1)
supplier = frappe.new_doc("Supplier")
supplier.supplier_name = "_Test Supplier '1"
supplier.supplier_group = "_Test Supplier Group"
supplier.insert()
rfq = make_request_for_quotation(supplier_wt_appos)
rfq = make_request_for_quotation(supplier_data=supplier_wt_appos)
sq = make_supplier_quotation(rfq.name, supplier_wt_appos[0].get("supplier"))
sq.submit()
@@ -76,7 +75,6 @@ class TestRequestforQuotation(unittest.TestCase):
frappe.form_dict.name = None
def test_make_supplier_quotation_from_portal(self):
from erpnext.buying.doctype.request_for_quotation.request_for_quotation import create_supplier_quotation
rfq = make_request_for_quotation()
rfq.get('items')[0].rate = 100
rfq.supplier = rfq.suppliers[0].supplier
@@ -90,12 +88,34 @@ class TestRequestforQuotation(unittest.TestCase):
self.assertEqual(supplier_quotation_doc.get('items')[0].qty, 5)
self.assertEqual(supplier_quotation_doc.get('items')[0].amount, 500)
def test_make_multi_uom_supplier_quotation(self):
item_code = "_Test Multi UOM RFQ Item"
if not frappe.db.exists('Item', item_code):
item = make_item(item_code, {'stock_uom': '_Test UOM'})
row = item.append('uoms', {
'uom': 'Kg',
'conversion_factor': 2
})
row.db_update()
def make_request_for_quotation(supplier_data=None):
rfq = make_request_for_quotation(item_code="_Test Multi UOM RFQ Item", uom="Kg", conversion_factor=2)
rfq.get('items')[0].rate = 100
rfq.supplier = rfq.suppliers[0].supplier
self.assertEqual(rfq.items[0].stock_qty, 10)
supplier_quotation_name = create_supplier_quotation(rfq)
supplier_quotation = frappe.get_doc('Supplier Quotation', supplier_quotation_name)
self.assertEqual(supplier_quotation.items[0].qty, 5)
self.assertEqual(supplier_quotation.items[0].stock_qty, 10)
def make_request_for_quotation(**args):
"""
:param supplier_data: List containing supplier data
"""
supplier_data = supplier_data if supplier_data else get_supplier_data()
args = frappe._dict(args)
supplier_data = args.get("supplier_data") if args.get("supplier_data") else get_supplier_data()
rfq = frappe.new_doc('Request for Quotation')
rfq.transaction_date = nowdate()
rfq.status = 'Draft'
@@ -106,11 +126,13 @@ def make_request_for_quotation(supplier_data=None):
rfq.append('suppliers', data)
rfq.append("items", {
"item_code": "_Test Item",
"item_code": args.item_code or "_Test Item",
"description": "_Test Item",
"uom": "_Test UOM",
"qty": 5,
"warehouse": "_Test Warehouse - _TC",
"uom": args.uom or "_Test UOM",
"stock_uom": args.stock_uom or "_Test UOM",
"qty": args.qty or 5,
"conversion_factor": args.conversion_factor or 1.0,
"warehouse": args.warehouse or "_Test Warehouse - _TC",
"schedule_date": nowdate()
})

View File

@@ -1,4 +1,5 @@
{
"actions": [],
"autoname": "hash",
"creation": "2016-02-25 08:04:02.452958",
"doctype": "DocType",
@@ -9,6 +10,7 @@
"supplier_part_no",
"column_break_3",
"item_name",
"schedule_date",
"section_break_5",
"description",
"item_group",
@@ -18,9 +20,11 @@
"image_view",
"quantity",
"qty",
"stock_uom",
"col_break2",
"schedule_date",
"uom",
"conversion_factor",
"stock_qty",
"warehouse_and_reference",
"warehouse",
"project_name",
@@ -33,7 +37,7 @@
"fields": [
{
"bold": 1,
"columns": 3,
"columns": 2,
"fieldname": "item_code",
"fieldtype": "Link",
"in_list_view": 1,
@@ -98,7 +102,7 @@
{
"fieldname": "quantity",
"fieldtype": "Section Break",
"label": "Quantity"
"label": "Quantity & Stock"
},
{
"bold": 1,
@@ -129,12 +133,12 @@
{
"fieldname": "uom",
"fieldtype": "Link",
"in_list_view": 1,
"label": "UOM",
"oldfieldname": "uom",
"oldfieldtype": "Link",
"options": "UOM",
"print_width": "100px",
"read_only": 1,
"reqd": 1,
"width": "100px"
},
@@ -144,7 +148,7 @@
"label": "Warehouse and Reference"
},
{
"columns": 3,
"columns": 2,
"fieldname": "warehouse",
"fieldtype": "Link",
"in_list_view": 1,
@@ -202,6 +206,7 @@
},
{
"allow_on_submit": 1,
"default": "0",
"fieldname": "page_break",
"fieldtype": "Check",
"label": "Page Break",
@@ -219,10 +224,36 @@
{
"fieldname": "section_break_23",
"fieldtype": "Section Break"
},
{
"fieldname": "stock_uom",
"fieldtype": "Link",
"label": "Stock UOM",
"options": "UOM",
"print_hide": 1,
"read_only": 1,
"reqd": 1
},
{
"fieldname": "conversion_factor",
"fieldtype": "Float",
"label": "UOM Conversion Factor",
"print_hide": 1,
"read_only": 1,
"reqd": 1
},
{
"fieldname": "stock_qty",
"fieldtype": "Float",
"label": "Qty as per Stock UOM",
"no_copy": 1,
"print_hide": 1,
"read_only": 1
}
],
"istable": 1,
"modified": "2019-05-01 17:50:23.703801",
"links": [],
"modified": "2020-06-12 19:10:36.333441",
"modified_by": "Administrator",
"module": "Buying",
"name": "Request for Quotation Item",

View File

@@ -97,7 +97,7 @@
{
"fieldname": "default_bank_account",
"fieldtype": "Link",
"label": "Default Bank Account",
"label": "Default Company Bank Account",
"options": "Bank Account"
},
{
@@ -385,7 +385,7 @@
"idx": 370,
"image_field": "image",
"links": [],
"modified": "2020-03-17 09:48:30.578242",
"modified": "2020-06-17 23:28:30",
"modified_by": "Administrator",
"module": "Buying",
"name": "Supplier",

Some files were not shown because too many files have changed in this diff Show More