Compare commits

..

636 Commits

Author SHA1 Message Date
Saurabh
19a27d3f46 Merge branch 'v12-pre-release' into version-12 2021-02-19 12:44:24 +05:30
Saurabh
d5fa3a2b8f bumped to version 12.18.0 2021-02-19 13:04:23 +05:50
Nabin Hait
d7bf38842b core: Added change log 2021-02-18 20:14:31 +05:30
Deepesh Garg
be65ae7c86 fix: Prorata factor fixes in subscription (#24638)
* fix: Prorata factor fixes in subscription

* fix: Test Case
2021-02-16 07:50:05 +05:30
Deepesh Garg
f452ab56c6 Merge pull request #24635 from ankush/ladakh_gst_addition-v12pr
fix(India): Add GST state code for Ladakh
2021-02-15 21:12:39 +05:30
Ankush Menat
c1c8bb6d98 fix(India): Add GST state code for Ladakh 2021-02-15 15:35:32 +05:30
rohitwaghchaure
472bad352d Merge pull request #24620 from rohitwaghchaure/fixed-incorrect-incoming-rate-for-sales-return-pre
fix: incorrect incoming rate for the sales return
2021-02-12 14:22:37 +05:30
Rohit Waghchaure
eea1ec42f4 fix: incorrect incoming rate for the sales return 2021-02-12 14:21:51 +05:30
Nabin Hait
ddd85334a3 Removed debug flag 2021-02-12 09:54:04 +05:30
Nabin Hait
2f20ef0f4c Merge branch 'version-12-hotfix' into v12-pre-release 2021-02-11 21:59:04 +05:30
Jannat Patel
e8935457a0 Item group on update items v12 (#24535)
* fix: item_group on update items

* fix: code cleanup

* Update accounts_controller.py

* Update accounts_controller.py

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2021-02-11 21:56:48 +05:30
Nabin Hait
64ec1728ab fix: merge conflict 2021-02-11 21:48:49 +05:30
Tropicalrambler (Alain Berger)
dbb6721412 fix: remove max 5 file attachment limit in task (#24056)
Co-authored-by: alain <fogliasana@gmail.com>
2021-02-11 20:14:14 +05:30
Afshan
afbbdcb802 fix: calculate discount amount (#24511) 2021-02-11 20:11:30 +05:30
Jannat Patel
37adbe5a85 fix: Dynamic Links for reports (#24461)
* fix: dynamic links in reports

* fix: reverting changes for payment period report

* fix: link fields
2021-02-11 20:09:49 +05:30
Rucha Mahabal
d7a5853587 fix: Issues with packing items (#24606) 2021-02-11 20:08:22 +05:30
Saqib
6b799dbef0 fix: validate cancellation only if irn generated (#24609) 2021-02-11 17:51:41 +05:30
Marica
be8ecdf3d6 Merge pull request #24486 from frappe/rfq-contact-email-set-v12
fix: Rfq contact email set v12
2021-02-11 13:50:06 +05:30
Wolfram Schmidt
85f1561e5e Update question.json (#24487)
according to: https://github.com/frappe/erpnext/pull/23402
2021-02-11 13:39:23 +05:30
Richard Case
2bf8610698 fix: plaid client version to support latest API (#24532) 2021-02-11 13:29:59 +05:30
Marica
23364b374e Merge pull request #24546 from pateljannat/validation-for-disabled-warehouse-v12
Validation for disabled warehouse v12
2021-02-11 13:09:29 +05:30
Marica
82c162dfe7 Merge branch 'version-12-hotfix' into validation-for-disabled-warehouse-v12 2021-02-11 13:04:49 +05:30
Saqib
7fea8a95e6 fix: NoneType has no len() (#24604) 2021-02-11 11:57:05 +05:30
rohitwaghchaure
85a2d27736 fix: Consolidated Financial Statement report not works if child company account not present in parent company (#24580) 2021-02-11 11:07:59 +05:30
Ankush Menat
106e0f885a fix: Update total in words after updating items (#24592)
* fix: Update total in words after Updating items

Update total in words after Updating items in sales/purchase orders.

Closes ISS-20-21-09425

* test: Add test for total & words after update item

Add test for total & words after updating items in sales order.
2021-02-11 11:05:08 +05:30
Anuja Pawar
c37ce8b8d3 fix: fix filters for IRS 1099 report (#24597) 2021-02-11 11:02:13 +05:30
pateljannat
5ac5d86d84 fix: vadd validation in stock ledger entry 2021-02-10 18:44:38 +05:30
Marica
a180d2baa8 Merge pull request #24400 from pateljannat/item-wise-purchase-register-item-name-error-v-12
fix: Item wise purchase register item name error v12
2021-02-10 12:04:40 +05:30
pateljannat
14717eeac6 fix: better function name 2021-02-09 14:12:20 +05:30
Deepesh Garg
179d82615f Merge pull request #24579 from marination/acc-dimension-update-hotfix
fix: Avoid changing Ref. Doctype in Accounting Dimension after creation
2021-02-09 06:52:45 +05:30
Saqib
1618c92142 fix: fetching of standalone cr/dr notes for reconciliation (#24576) 2021-02-08 20:19:18 +05:30
marination
1118949867 fix: frm.doc instead of doc 2021-02-08 17:55:26 +05:30
marination
31cd9dcee1 fix: Avoid changing Ref. Doctype in Accounting Dimension after creation 2021-02-08 17:37:14 +05:30
Saqib
e42e75178a fix(e-invoice): skip e-invoice generation for non-taxable invoices (#24568) (#24569) 2021-02-08 11:43:29 +05:30
Saqib
078e154966 fix(e-invoice): do not validate gstin for exports (#24564) 2021-02-07 18:58:25 +05:30
Anuja Pawar
3365f01963 fix: fixing item_code not found error (#24484) 2021-02-05 23:35:42 +05:30
pateljannat
469827da85 fix: validation for disabled warehouse 2021-02-03 15:34:57 +05:30
pateljannat
d3240f9510 Merge branch 'version-12-hotfix' of https://github.com/frappe/erpnext into version-12-hotfix 2021-02-03 12:05:12 +05:30
Rohan
2341f47631 fix: use supplied year for IRS 1099 forms (#24425)
* fix: use supplied year for IRS 1099 forms

* fix: don't use f-strings

Co-authored-by: Afshan <33727827+AfshanKhan@users.noreply.github.com>
2021-02-01 11:55:40 +05:30
Saqib
b57a523dfe fix: discount amount calculation on net total (#24498) 2021-01-29 14:24:18 +05:30
pateljannat
8d101d362d fix: rfq contact email set 2021-01-28 15:01:25 +05:30
pateljannat
a9cfe1cfa4 Merge branch 'version-12-hotfix' of https://github.com/frappe/erpnext into version-12-hotfix 2021-01-28 14:49:19 +05:30
Afshan
dccd2ca69f fix: validate tax template for tax category (#24403)
* fix: validate tax template for tax category

* Update erpnext/accounts/doctype/sales_taxes_and_charges_template/sales_taxes_and_charges_template.py

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

Co-authored-by: Marica <maricadsouza221197@gmail.com>
2021-01-28 12:23:08 +05:30
Anuja Pawar
314e151f1d fix: adding UOM in update items (#24479)
* fix: adding UOM in update items

* fix: sider fixes
2021-01-28 12:19:03 +05:30
Kaviya Periyasamy
c002465903 fix(einvoice): QRCode generation and eway bill live url (#24459) 2021-01-27 19:43:41 +05:30
Saqib
859a5f4dbe fix: e_invoice print format not showing other charges (#24473) 2021-01-27 12:33:59 +05:30
Saurabh
58d7fb5c94 Merge branch 'v12-pre-release' into version-12 2021-01-27 09:42:08 +05:30
Saurabh
744a7b1bad bumped to version 12.17.0 2021-01-27 10:02:08 +05:50
Saqib
d9719fe41d fix: einvoice test (#24463) 2021-01-26 19:19:51 +05:30
Saqib
50c1d24ee9 fix: einvoice test (#24435) 2021-01-25 17:59:52 +05:30
Suraj Shetty
ea221f7e63 chore: Add release notes for v12.17.0 (#24450)
* chore: Add release notes for v12.17.0

* Chore: Fix formatting

* chore: Fix links
2021-01-25 15:36:43 +05:30
David Angulo
3799c1a662 feat: Make patient age translateable (#24416)
* feat: Make patient age translateable

* Make patient age translatable in patient encounter

* Translate all occurrences of age calculation

* Comply to uniform translation syntax
2021-01-22 08:29:16 +05:30
rohitwaghchaure
56a8b90598 Merge pull request #24438 from AfshanKhan/fix-stock-ageing-v12
fix: stock ageing should not take cancelled stock entries.
2021-01-21 23:10:50 +05:30
Afshan
044ad91481 fix: stock ageing should not take cancelled stock entries. 2021-01-21 18:29:43 +05:30
Anuja Pawar
39a5e5abd1 fix: missing asset id in the Fixed Asset Register (#24429) 2021-01-21 15:14:24 +05:30
Saqib
407b351d55 fix: (e-invoicing) qrcode image generation (#24422) 2021-01-20 13:24:49 +05:30
Saqib
6f64ec3574 fix: (e-invoicing) qrcode image generation (#24421) 2021-01-20 13:22:58 +05:30
Prssanna Desai
e17ad9e620 Merge pull request #24419 from prssanna/chart-imports-v12
fix: function imports in accounts dashboard
2021-01-20 11:21:38 +05:30
Prssanna Desai
505b69f6b2 Merge pull request #24380 from prssanna/chart-imports
fix: function imports in accounts dashboard
2021-01-20 11:18:31 +05:30
prssanna
485ef74c58 fix: function imports in accounts dashboard 2021-01-20 11:18:10 +05:30
Anuja Pawar
5cf9fbc27b fix: missing asset id in the report (#24391) 2021-01-18 17:05:01 +05:30
Saqib
4ef49eab66 fix: add check for allowing access to european region (#24393) 2021-01-18 16:40:28 +05:30
Saqib
f6d61f2dec fix: add check for allowing access to european region (#24394) 2021-01-18 16:40:10 +05:30
pateljannat
7aaf3a71e8 fix: item wise purchase register item_name error 2021-01-18 16:15:01 +05:30
Jannat Patel
c51ac1c68b Merge pull request #5 from frappe/version-12-hotfix
Version 12 hotfix
2021-01-18 15:58:26 +05:30
rohitwaghchaure
04b106a515 Merge pull request #24384 from rohitwaghchaure/donot-check-previous-qty-for-batch-pre-release
fix: stock ledger entry was not created against stock reco
2021-01-16 15:03:08 +05:30
Rohit Waghchaure
e79f3e67ed fix: stock ledger entry was not created against stock reco 2021-01-16 15:01:14 +05:30
rohitwaghchaure
f8d24b803c Merge pull request #24382 from rohitwaghchaure/donot-check-previous-qty-for-batch
fix: stock ledger entry was not created against stock reco
2021-01-15 21:25:00 +05:30
Rohit Waghchaure
c516fc7ca4 fix: stock ledger entry was not created against stock reco 2021-01-15 18:18:17 +05:30
prssanna
c9b8423007 fix: function imports in accounts dashboard 2021-01-15 18:05:19 +05:30
Nabin Hait
42675929fa fix:merge conflict 2021-01-15 17:09:43 +05:30
Anuja Pawar
a8de2321a5 fix: Payment Period based on invoice date report fix/refactor (#24377)
* fix: Payment Period based on invoice date report fix/refactor

* fix: minor
2021-01-14 21:21:12 +05:30
Saqib
748f8145b6 feat: show transporter address in sales invoice (#23731)
* feat: show transporter address in sales invoice

* feat: multiple transporter address

* fix: update all eway-bill fields

* fix: travis

* fix: travis

* fix: travis

* fix: travis

* fix: travis

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2021-01-14 19:53:51 +05:30
Jannat Patel
7a40a2b2e2 fix: subscription prepaid date validation (#24373) 2021-01-14 19:46:19 +05:30
Deepesh Garg
35c2d2324d fix: Ignore group cost center validation for period closing voucher (#24374) 2021-01-14 19:45:13 +05:30
Anuja Pawar
f2b5f3a842 fix: for not having fiscal year while creating new company (#24161)
* fix: Fiscal year fix while creating new company

* minor fix

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2021-01-14 19:25:40 +05:30
Mohammad Hasnain Mohsin Rajan
d2442da6f2 fix: last purchase rate not updating when voucher cancelled if only one voucher is present - v12 (#24323)
* fix: update last purchase rate

* chore: use orm for update

Co-authored-by: Afshan <33727827+AfshanKhan@users.noreply.github.com>
2021-01-14 19:22:47 +05:30
Anuja Pawar
32bdb691df fix: bom stock report UoM correction (#24363) 2021-01-14 19:21:27 +05:30
rohitwaghchaure
5050541401 Merge pull request #24188 from iRaySpace/loyalty-program-fix
fix: loyalty program
2021-01-14 17:11:20 +05:30
rohitwaghchaure
87f0ed6477 Merge pull request #24364 from rohitwaghchaure/fixed-extra-trasnferred_qty_issue
fix: extra transferred qty has not consumed against work order
2021-01-14 16:36:24 +05:30
Marica
6df18856db Merge pull request #24295 from marination/mr-se-warehouse-validation-hotfix
fix: Dont validate warehouse values between MR to Stock Entry
2021-01-14 16:34:26 +05:30
Marica
288b384ab5 Merge pull request #24368 from marination/qc-back-update-se-hotfix
fix: Back Update from QC based on Batch No
2021-01-14 15:14:06 +05:30
Marica
cffcbf7c47 Merge pull request #24367 from marination/bom-rm-rate-company-based-hotfix
fix: Company Wise Valuation Rate for RM in BOM
2021-01-14 15:13:35 +05:30
Marica
c69fda4440 Merge branch 'version-12-hotfix' into mr-se-warehouse-validation-hotfix 2021-01-14 15:10:01 +05:30
Anurag Mishra
507ec2184c fix: calculation of remaining_sub_periods if relieving date before month start date
fix: calculation of remaining_sub_periods if relieving date before the month start date
2021-01-14 14:51:13 +05:30
Afshan
75cfbe132b fix: calculation of remaining_sub_periods if relieving date before month start date 2021-01-14 13:51:01 +05:30
marination
f88e908598 fix: Remove QI link on cancel wherever same QI name exists 2021-01-14 13:05:40 +05:30
marination
8791d11359 fix: Back Update from QC based on Batch No 2021-01-14 13:03:32 +05:30
marination
bbec5ccc83 fix: Company Wise Valuation Rate for RM in BOM 2021-01-14 12:53:57 +05:30
Saqib
8862166223 fix(e-invoicing): minor ux fixes (#24366) 2021-01-14 12:22:23 +05:30
marination
2eea0f003f fix: test for raising MR-SE mismatch error
- Make test add mismatched item code instead of warehouse, since warehouse can be different.
2021-01-14 12:20:39 +05:30
Rohit Waghchaure
a250d415aa fix: extra transferred qty has not consumed against work order 2021-01-14 11:47:57 +05:30
Jannat Patel
4d83564188 fix: check for tax_rate (#24348) 2021-01-13 20:57:15 +05:30
rohitwaghchaure
7e01cacf8c Merge pull request #24353 from rohitwaghchaure/fixed-incorrect-key-in-subcontract
fix: incorrect serial no in the subcontracted purchase receipt
2021-01-13 09:21:57 +05:30
Rohit Waghchaure
830626d86a fix: incorrect key 2021-01-13 00:05:29 +05:30
Marica
78e413aaaa Merge branch 'version-12-hotfix' into mr-se-warehouse-validation-hotfix 2021-01-12 20:17:41 +05:30
rohitwaghchaure
f9da40e9af Merge pull request #24331 from rohitwaghchaure/fixed-payment-entry-multi-currency-issue
fix: payment entry multi-currency issue
2021-01-11 12:32:30 +05:30
Rucha Mahabal
e6a8e1a23b Merge pull request #24333 from ruchamahabal/fix-item-details-in-reports-v12
feat(reports): get item details from Item document instead of the Transactions
2021-01-08 15:25:02 +05:30
Rucha Mahabal
e0e5783b3e fix: import statement 2021-01-08 14:37:23 +05:30
Rucha Mahabal
0abed806a3 feat(reports): get item details from Item doctype instead of the Transaction 2021-01-08 14:37:07 +05:30
Rohit Waghchaure
79e3700499 fix: payment entry multi-currency issue 2021-01-08 12:36:51 +05:30
Saqib
e898ce1f20 refactor: fetch & validate address from erpnext rather than gst portal (#24305) 2021-01-06 10:49:50 +05:30
Saqib
3ddebae3fb refactor: fetch & validate address from erpnext rather than gst portal (#24299) 2021-01-06 10:49:27 +05:30
Nabin Hait
d5abab4208 fix: tax calculation on salary slip for the first month (#24272) (#24309)
* fix: tax calculation on salary slip for the first month

* fix: net pay precision issue

* fix: net pay precision issue

Co-authored-by: Anurag Mishra <32095923+Anurag810@users.noreply.github.com>

Co-authored-by: Anurag Mishra <32095923+Anurag810@users.noreply.github.com>
2021-01-06 09:34:44 +05:30
Nabin Hait
00a40c95ea Merge branch 'version-12-hotfix' into mr-se-warehouse-validation-hotfix 2021-01-06 09:33:56 +05:30
rohitwaghchaure
750da2f946 Merge pull request #24302 from rohitwaghchaure/allow-to-set-basic-rate-manually-for-manufacture-entry
fix: 'Set Basic Rate Manually' field is now available for Manufacture type stock entry
2021-01-05 17:01:27 +05:30
Rohit Waghchaure
ff524e676f fix: 'Set Basic Rate Manually' field is now available for Manufacure type stock entry 2021-01-05 15:09:54 +05:30
rohitwaghchaure
d8fc6ec471 Merge pull request #24301 from rohitwaghchaure/fixed-allow-to-override-basic-rate-for-fg
fix: allow to override the basic rate for the finished good
2021-01-05 14:55:42 +05:30
Rohit Waghchaure
4e12c70897 fix: allow to override the basic rate for the finished good 2021-01-05 14:54:52 +05:30
Saqib
7e97138beb fix(e-invoicing): minor calculation fixes (#24284) 2021-01-05 13:32:56 +05:30
Saqib
00865b9af3 fix(e-invoicing): minor calculation fixes (#24283) 2021-01-05 13:32:46 +05:30
Deepesh Garg
7d1a431d9c Merge pull request #23963 from vorasmit/remarks-fix-v12
fix: add remarks to sales invoice
2021-01-05 09:57:58 +05:30
Deepesh Garg
fe9e2ec008 Merge branch 'version-12-hotfix' of https://github.com/frappe/erpnext into remarks-fix-v12 2021-01-05 09:56:58 +05:30
Nabin Hait
ca4c12b44e Merge branch 'version-12-hotfix' into mr-se-warehouse-validation-hotfix 2021-01-05 09:30:09 +05:30
Nabin Hait
cdd950dee5 fix: Ignore customer and supplier while deleting company transactions (#24280) 2021-01-05 09:25:50 +05:30
rohitwaghchaure
21b17cf407 Merge pull request #24289 from rohitwaghchaure/fixed-source-warehouse-if-material-transfer-is-skip
fix: incorrect source warehouse in stock entry
2021-01-05 09:01:39 +05:30
rohitwaghchaure
6324cc238e Merge pull request #24288 from rohitwaghchaure/fixed-pricing-rule-not-working-in-offline-pos
fix: pricing rule not working for offline POS
2021-01-05 09:01:05 +05:30
marination
cdc0b8e435 fix: Dont validate warehouse values between MR to Stock Entry
- Remove validation that checks if warehouse in Stock Entry is the same as MR that it was pulled from
2021-01-04 18:59:48 +05:30
Prssanna Desai
7049cca855 Merge pull request #24290 from frappe/revert-24097-chart-imports
Revert "fix: function imports in account_balance_timeline.py"
2021-01-04 17:16:48 +05:30
Prssanna Desai
ba95d32876 Revert "fix: function imports in account_balance_timeline.py" 2021-01-04 17:14:50 +05:30
Rohit Waghchaure
bf1e0139e2 fix: incorrect source warehouse in stock entry 2021-01-04 16:23:14 +05:30
Rohit Waghchaure
bf490c3a27 fix: pricing rule not working for offline POS 2021-01-04 15:32:13 +05:30
Saqib
40b37f09fd fix: cannot save asset category withouut depr posting date 2021-01-04 11:48:45 +05:30
vorasmit
04e0b35154 Update patches.txt 2021-01-01 17:14:14 +05:30
vorasmit
82b4749166 Update patches.txt 2021-01-01 10:49:48 +05:30
vorasmit
ef06f3288f Delete update_sales_invoice_remarks.py 2021-01-01 10:48:44 +05:30
Saqib
945c0e86de fix: cannot submit e-invoice if legal name not found 2020-12-31 13:17:59 +05:30
Saqib
2cae3d7b38 fix: cannot submit e-invoice if legal name not found 2020-12-31 13:16:59 +05:30
Saurabh
03933f8461 Merge branch 'v12-pre-release' into version-12 2020-12-31 11:20:28 +05:30
Saurabh
ba398bc779 bumped to version 12.16.2 2020-12-31 11:40:28 +05:50
Saqib
022a46fdcd fix: item value & invoice value calculations (#24241) 2020-12-31 11:17:27 +05:30
Deepesh Garg
d092b6c25a Merge pull request #24244 from deepeshgarg007/template_company_filter
fix: Add company filter in tax template query
2020-12-31 11:06:25 +05:30
Karthikeyan S
5add3ea210 fix(GST E Invoice): update live URLs for adaequare GSP (#24249) 2020-12-30 19:21:40 +05:30
Deepesh Garg
909346f222 fix: Add company filter in tax template query 2020-12-30 18:05:52 +05:30
Saurabh
d9a0e0c708 Merge branch 'v12-pre-release' into version-12 2020-12-30 17:45:38 +05:30
Saurabh
839edaf613 bumped to version 12.16.1 2020-12-30 18:05:38 +05:50
Deepesh Garg
11f2da72b1 fix: Error on submitting sales invoice (#24243)
* fix: Error on submitting sales invoice

* fix: remove return_taxes
2020-12-30 17:44:23 +05:30
Saurabh
61298c3489 Merge branch 'v12-pre-release' into version-12 2020-12-30 13:12:30 +05:30
Saurabh
2cf2697e74 bumped to version 12.16.0 2020-12-30 13:32:29 +05:50
rohitwaghchaure
1b0870a440 Merge pull request #24240 from saurabh6790/v12_16_change_log
feat: change log for version 12.16.0
2020-12-30 13:09:39 +05:30
Saurabh
5c107b99bd feat: change log for version 12.16.0 2020-12-30 13:07:05 +05:30
Saqib Ansari
edec82bb9e fix: unit rate & gross amount calculation 2020-12-30 11:57:16 +05:30
Saqib Ansari
45dbfaa7f9 fix: invoice value set to zero if rounded total disabled 2020-12-30 11:57:16 +05:30
Rohit Waghchaure
7d666ccfb4 fix: do not override the manually added valuation rate in stock entry 2020-12-30 11:57:16 +05:30
Saqib Ansari
246ef881a0 fix: e invoice request log permissions 2020-12-30 11:57:16 +05:30
Saqib Ansari
5f3635fbaf fix: travis 2020-12-30 11:57:16 +05:30
Rohit Waghchaure
ec59c6cebc fix: do not manufacture same serial no multiple times 2020-12-30 11:57:16 +05:30
Saqib Ansari
be58194678 fix: sider issues 2020-12-30 11:57:16 +05:30
Saqib Ansari
00306d8fd0 chore: code cleanup 2020-12-30 11:57:16 +05:30
Saqib Ansari
da83ec0f0d fix: cannot cancel irn without submitting sales invoice 2020-12-30 11:57:16 +05:30
Saqib Ansari
709d50ad21 fix: remove test pincode 2020-12-30 11:57:16 +05:30
Saqib Ansari
7f69820f04 fix: uncomment test condition 2020-12-30 11:57:16 +05:30
Saqib Ansari
a0c8106342 feat: multiple gstins for e invoicing 2020-12-30 11:57:16 +05:30
Saqib Ansari
8c8ab4140e fix: remove test supplier pincode 2020-12-30 11:57:16 +05:30
pateljannat
2274162107 fix: modified 2020-12-30 11:57:16 +05:30
Shivam Mishra
6f2a34f6d4 fix: replace pin code with postal code 2020-12-30 11:57:16 +05:30
pateljannat
e512118320 fix: indentation 2020-12-30 11:57:16 +05:30
pateljannat
aa2a7abe4e fix: linter issue for translation syntax 2020-12-30 11:57:16 +05:30
pateljannat
79ff4d0e8f fix: reversing previous commits and adding condition in regional controller 2020-12-30 11:56:50 +05:30
pateljannat
37a64b6485 fix: place of supply change on address change 2020-12-30 11:56:50 +05:30
Deepesh Garg
9f848fe65c fix: Tax template update on supplier 2020-12-30 11:56:50 +05:30
Marica
65680ada87 Revert "fix: po_not retaining on save" 2020-12-30 11:56:09 +05:30
Mohammad Hasnain
a8cda3f013 fix: po_no not cleaned up on save 2020-12-30 11:56:09 +05:30
Mohammad Hasnain
c51b4d0416 fix: po_no getting removed on save 2020-12-30 11:56:09 +05:30
Rucha Mahabal
67cfb6c370 fix(Asset): set current asset value before calculating difference amount (#24119) 2020-12-30 11:56:09 +05:30
Saqib Ansari
54e9063215 feat: add docs link to e invoice settings 2020-12-30 11:56:09 +05:30
Saqib Ansari
554ce04e0d fix: error handling 2020-12-30 11:56:09 +05:30
Saqib Ansari
08f082089e fix: dialog is undefined 2020-12-30 11:56:09 +05:30
Saqib Ansari
d22279ba38 fix: minor ux issues 2020-12-30 11:56:09 +05:30
Saqib Ansari
d01cae95d9 feat: show e-invoice preview before IRN generation 2020-12-30 11:56:09 +05:30
Saqib Ansari
b510d20805 fix: adjust qr code image size 2020-12-30 11:56:09 +05:30
Saqib Ansari
b1054a3ddc fix: sider issues 2020-12-30 11:56:09 +05:30
Saqib Ansari
f454ab4ce2 chore: add ack date and ack no field for print formats 2020-12-30 11:56:09 +05:30
Saqib Ansari
5c68fe4d86 feat: log e-invocing requests 2020-12-30 11:56:09 +05:30
Saqib Ansari
68e476c7fe fix: returning condition 2020-12-30 11:56:08 +05:30
Saqib Ansari
8f5425d99b chore: add tests 2020-12-30 11:56:08 +05:30
Saqib Ansari
6af53a645a fix: ewaybill mandatory conditions 2020-12-30 11:56:08 +05:30
Saqib Ansari
b9cbdeaa95 fix: eway bill test 2020-12-30 11:56:08 +05:30
Saqib Ansari
0ce03cc36d fix: exclude intra company transactions 2020-12-30 11:56:08 +05:30
pateljannat
4ee433a51c fix: indentation 2020-12-30 11:56:08 +05:30
Anuja P
e33179d130 fix: Added TDS account number and an error message 2020-12-30 11:56:08 +05:30
barredterra
53bcf704b3 feat: separate equity tree in CoA SKR04 2020-12-30 11:56:08 +05:30
pateljannat
f4f05dd5ad fix: enabling track changes for stock settings 2020-12-30 11:56:08 +05:30
pateljannat
5b554a5e20 fix: enabling track changes for stock settings 2020-12-30 11:56:08 +05:30
pateljannat
79ac9dc486 fix: enabling track changes for stock settings 2020-12-30 11:56:08 +05:30
pateljannat
f0d591351b fix: enabling track changes for stock settings 2020-12-30 11:56:08 +05:30
Saqib Ansari
c6143c4542 fix: qrcode image size 2020-12-30 11:56:08 +05:30
Saqib Ansari
5a56b63eed feat: update timeline on einvoice actions 2020-12-30 11:56:08 +05:30
Saqib Ansari
5d92e2481d fix: ewaybill could be modified after ewaybill generation 2020-12-30 11:56:08 +05:30
Saqib Ansari
ac603a895d fix: error handling 2020-12-30 11:56:08 +05:30
Saqib Ansari
9f0d567ea5 fix: imports 2020-12-30 11:56:08 +05:30
Saqib Ansari
4ea03c23a4 fix: import format_date 2020-12-30 11:56:08 +05:30
Saqib Ansari
209aa447f7 chore: remove fetch token from e invocie settings 2020-12-30 11:56:08 +05:30
Saqib Ansari
eabaa16f13 feat: cess non advolem on einvoice item 2020-12-30 11:56:08 +05:30
Saqib Ansari
27b68be854 fix: patch 2020-12-30 11:56:08 +05:30
Saqib Ansari
85cc1d68f0 fix: invalid syntax 2020-12-30 11:56:08 +05:30
Saqib Ansari
61e6760a6b fix: invalid syntax 2020-12-30 11:56:08 +05:30
Saqib Ansari
16e879bc1a chore: remove test pincode 2020-12-30 11:56:08 +05:30
Saqib Ansari
8866801932 feat: header & footer in GST E Invoice 2020-12-30 11:56:08 +05:30
Saqib Ansari
4965af2321 chore: error logging 2020-12-30 11:56:08 +05:30
Saqib Ansari
fb65644026 chore: remove unwanted imports 2020-12-30 11:56:08 +05:30
Saqib Ansari
2e1f56e117 feat: generate eway bill from IRN 2020-12-30 11:56:08 +05:30
Saqib Ansari
3b62e05a5c fix: valiations 2020-12-30 11:56:08 +05:30
Saqib Ansari
988fd97625 fix: show/hide eway bill fields 2020-12-30 11:56:08 +05:30
Saqib Ansari
628dcb1ff9 fix: generate & cancel IRN 2020-12-30 11:56:08 +05:30
Saqib Ansari
e6cd9ccea0 fix: attach qrcode on irn generation 2020-12-30 11:56:08 +05:30
Saqib Ansari
ac2fc8470b chore: clean up einvoice actions 2020-12-30 11:56:08 +05:30
Saqib Ansari
6dcf334199 chore: remove unwanted fuctions 2020-12-30 11:56:08 +05:30
Saqib Ansari
5822cfb454 feat: cancel eway bill 2020-12-30 11:56:08 +05:30
Saqib Ansari
a15c02ec71 feat: generate & cancel IRN 2020-12-30 11:56:08 +05:30
Saqib Ansari
0938db8730 feat: fetch and cache GSTIN details 2020-12-30 11:56:08 +05:30
Saqib Ansari
537a236dc9 fix: qr code generation 2020-12-30 11:56:08 +05:30
Saqib Ansari
68d2a1f02b chore: remove unwanted fields 2020-12-30 11:56:08 +05:30
Saqib Ansari
4dad6742e1 feat: initialize GSP connector 2020-12-30 11:56:08 +05:30
Saqib Ansari
44877d5a60 fix: qr code image string 2020-12-30 11:56:08 +05:30
Saqib Ansari
05589e9651 chore: improve document name validation message 2020-12-30 11:56:08 +05:30
Saqib Ansari
9958639a9a fix: other charges calculation 2020-12-30 11:56:08 +05:30
Saqib Ansari
df1686611b fix: invoice totals calculation 2020-12-30 11:56:07 +05:30
Saqib Ansari
1041aef097 fix: patch 2020-12-30 11:56:07 +05:30
Saqib Ansari
0e00bff182 fix: einvoice field validation 2020-12-30 11:56:07 +05:30
Saqib Ansari
160585321d fix: rename e_invoice_utils.py 2020-12-30 11:56:07 +05:30
Saqib Ansari
965bc9bb80 fix: add missing package 2020-12-30 11:56:07 +05:30
Saqib Ansari
bfb68e4e80 fix: e_invoice module not found 2020-12-30 11:56:07 +05:30
Saqib Ansari
3d7f833899 fix: error logging 2020-12-30 11:56:07 +05:30
Saqib Ansari
1866965508 fix: validations 2020-12-30 11:56:07 +05:30
Saqib Ansari
a874587156 fix: credit note einvoice 2020-12-30 11:56:07 +05:30
Saqib Ansari
e7ea94ae6f fix: return date 2020-12-30 11:56:07 +05:30
Saqib Ansari
7015609f7f fix: validate document name 2020-12-30 11:56:07 +05:30
Saqib Ansari
53b05c2850 feat: add patch 2020-12-30 11:56:07 +05:30
Saqib Ansari
e14bb5e978 fix: add permissions on regional setup 2020-12-30 11:56:07 +05:30
Saqib Ansari
4db3ff1673 fix: validations 2020-12-30 11:56:07 +05:30
Saqib Ansari
03cd4135d2 fix: print format 2020-12-30 11:56:07 +05:30
Saqib Ansari
e984632221 fix: download & upload e-invoice 2020-12-30 11:56:07 +05:30
Saqib Ansari
65289334e3 chore: clean up e invoice actions 2020-12-30 11:56:07 +05:30
Saqib Ansari
2e38f73732 chore: code cleanup 2020-12-30 11:56:07 +05:30
Saqib Ansari
52b983eb8f fix: invalid syntax 2020-12-30 11:56:07 +05:30
Saqib Ansari
2e16dcc8fa fix: bug 2020-12-30 11:56:07 +05:30
Saqib Ansari
4e12466bef feat: QRCode Image and E-Invoice Print Format 2020-12-30 11:56:07 +05:30
Saqib Ansari
e0ea4265a8 chore: move einvoicing stuff to seperate folder 2020-12-30 11:56:07 +05:30
Saqib Ansari
233cad9e02 fix: fetch token if not valid 2020-12-30 11:56:07 +05:30
Saqib Ansari
718e517144 chore: save signed invoice and qrcode after uplaoding irn 2020-12-30 11:56:07 +05:30
Saqib Ansari
4f3f935a7a fix: fn name 2020-12-30 11:56:07 +05:30
Saqib Ansari
94db0bba44 chore: group e-invoicing actions 2020-12-30 11:56:07 +05:30
Saqib Ansari
acc79f739b feat: manual download / upload json 2020-12-30 11:56:07 +05:30
Saqib Ansari
bdf4bfe98f feat: cancel e-way bill before cancelling IRN 2020-12-30 11:56:07 +05:30
Saqib Ansari
9e5388ac53 chore: no copy on e invoice custom fields 2020-12-30 11:56:07 +05:30
Saqib Ansari
a6666dbf97 fix: save e-way bill no on irn generation 2020-12-30 11:56:07 +05:30
Saqib Ansari
4b969a5b9b feat: e-way bill details in e-invoice 2020-12-30 11:56:07 +05:30
Saqib Ansari
b6faadab8d chore: show irn field for proper gst_category 2020-12-30 11:56:07 +05:30
Saqib Ansari
38f06a1a26 fix: update irn_cancelled after cancelling irn 2020-12-30 11:56:07 +05:30
Saqib Ansari
b54df979c4 fix: do not show generate irn for invalid supply type 2020-12-30 11:56:07 +05:30
Saqib Ansari
1b969ff140 fix: validation if e invoicing is disabled 2020-12-30 11:56:07 +05:30
Saqib Ansari
bf2b4bc6f7 fix: cannot find attached key file 2020-12-30 11:56:07 +05:30
Saqib Ansari
9d805272be fix: public key is required on validate 2020-12-30 11:56:07 +05:30
Saqib Ansari
d4255d77f4 fix: hide cancel irn dialog on error 2020-12-30 11:56:07 +05:30
Saqib Ansari
13467e42f3 chore: show irn cancelled check after cancellation 2020-12-30 11:56:07 +05:30
Saqib Ansari
1679b0adbb fix: item discount 2020-12-30 11:56:07 +05:30
Saqib Ansari
e7a129dde8 chore: minor fixes 2020-12-30 11:56:07 +05:30
Saqib Ansari
b12d08a85b feat: Generate & Cancel IRN from Sales Invoice 2020-12-30 11:56:07 +05:30
Saqib Ansari
fe054511c8 feat: make IRN field on regional setup 2020-12-30 11:56:07 +05:30
Saqib Ansari
c3e0ff93d7 chore: rename schema to template & js cleanup 2020-12-30 11:56:07 +05:30
Saqib Ansari
4d15506791 chore: split einvoice settings and operations 2020-12-30 11:56:07 +05:30
Saqib Ansari
a367cc5c99 chore: move e-invoice settings to regional 2020-12-30 11:56:07 +05:30
Saqib Ansari
9599420878 feat: complete e-invoice schema 2020-12-30 11:56:07 +05:30
Saqib Ansari
c9b6db27cf feat: cancel IRN 2020-12-30 11:56:06 +05:30
Saqib Ansari
d72d2367ab chore: validations 2020-12-30 11:56:06 +05:30
Saqib Ansari
d9e4ebc00c feat: decode signed json and QR code 2020-12-30 11:56:06 +05:30
Saqib Ansari
a4bd8ba6f9 feat: generate IRN 2020-12-30 11:56:06 +05:30
Saqib Ansari
6f5a9c8049 feat: make e invoice from erpnext sales invoice 2020-12-30 11:56:06 +05:30
Saqib Ansari
48449e6d0a feat: decrypt json data with SEK 2020-12-30 11:56:06 +05:30
Saqib Ansari
31596228ff feat: AES decryption of SEK with appkey 2020-12-30 11:56:06 +05:30
Saqib Ansari
017543d59d chore: handle error response 2020-12-30 11:56:06 +05:30
Saqib Ansari
cca0eaaa29 feat: save token and sek from auth request 2020-12-30 11:56:06 +05:30
Saqib Ansari
b52a9283bb feat: rsa encryption with public key 2020-12-30 11:56:06 +05:30
Saqib Ansari
39dabe7381 feat: read public key file 2020-12-30 11:56:06 +05:30
Saqib Ansari
1c213a3dbb feat: init e-invoice settings 2020-12-30 11:56:06 +05:30
rohitwaghchaure
e7eb9d4e20 Merge pull request #24184 from nextchamp-saqib/e-invoicing-version-12
feat: GST E-Invoicing
2020-12-30 11:15:37 +05:30
Saqib Ansari
d94a97b6ad fix: unit rate & gross amount calculation 2020-12-29 17:56:14 +05:30
Saqib Ansari
d819330443 fix: invoice value set to zero if rounded total disabled 2020-12-29 17:56:08 +05:30
rohitwaghchaure
86bbb3e9a0 Merge pull request #24221 from rohitwaghchaure/donot-override-valuation-rate
fix: do not override the manually added valuation rate in stock entry
2020-12-28 16:43:49 +05:30
Rohit Waghchaure
b9d62d7f8e fix: do not override the manually added valuation rate in stock entry 2020-12-28 15:20:23 +05:30
rohitwaghchaure
44dd9f6fe5 Merge pull request #24163 from rohitwaghchaure/do-not-manufacture-same-serial-no-two
fix: do not manufacture same serial no multiple times
2020-12-24 22:54:30 +05:30
Saqib Ansari
a683b14c64 fix: e invoice request log permissions 2020-12-24 21:12:13 +05:30
Saqib Ansari
becae59af0 fix: travis 2020-12-24 21:12:06 +05:30
Rohit Waghchaure
e6d300e35c fix: do not manufacture same serial no multiple times 2020-12-24 17:47:48 +05:30
Saqib Ansari
c2a41371d2 fix: sider issues 2020-12-24 10:39:41 +05:30
Saqib Ansari
6d3fc0d020 chore: code cleanup 2020-12-23 15:43:51 +05:30
Saqib Ansari
81cbd0dc50 fix: cannot cancel irn without submitting sales invoice 2020-12-23 15:43:31 +05:30
Saqib Ansari
1bbda81c9f fix: remove test pincode 2020-12-23 15:19:51 +05:30
Saqib Ansari
21461823f1 fix: uncomment test condition 2020-12-23 14:36:40 +05:30
Rohit Waghchaure
e9b580aba6 fix: pos not working 2020-12-22 19:03:39 +08:00
Sun Howwrongbum
7f794e5bb6 fix(pos): loyalty details not rendering in cart area 2020-12-22 19:02:08 +08:00
Saqib Ansari
6db07c0278 feat: multiple gstins for e invoicing 2020-12-22 15:56:18 +05:30
Saqib Ansari
c28379075a fix: remove test supplier pincode 2020-12-21 18:41:40 +05:30
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
Marica
64f4f86948 Merge pull request #23983 from pateljannat/track-changes-for-stock-settings-v12
fix: enabling track changes for stock settings
2020-12-19 16:25:54 +05:30
pateljannat
983df4463a fix: modified 2020-12-18 20:18:17 +05:30
Shivam Mishra
b9c71e59e0 Merge pull request #24180 from scmmishra/chore-rename-pin-code 2020-12-18 13:32:34 +05:30
Shivam Mishra
8427dd2ca8 fix: replace pin code with postal code 2020-12-18 13:30:25 +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
105a9fdff1 Merge pull request #24174 from deepeshgarg007/tax_category_typo_v12
fix: Typo in tax category doctype query
2020-12-17 19:01:01 +05:30
Deepesh Garg
bd0cb9d2ed Typo in tax category doctype query 2020-12-17 18:59:42 +05:30
pateljannat
ffbb767072 Merge branch 'track-changes-for-stock-settings-v12' of https://github.com/pateljannat/erpnext into track-changes-for-stock-settings-v12 2020-12-17 13:26:21 +05:30
pateljannat
723e4f2a22 fix: indentation 2020-12-17 13:26:11 +05:30
Deepesh Garg
a738e8ca87 Merge pull request #24128 from ruchamahabal/fix-asset-value-adjustment-v12
fix(Asset): set current asset value before calculating difference amount
2020-12-17 12:36:35 +05:30
Deepesh Garg
b0b36d2caa Merge pull request #24094 from frappe/skr04_equity
feat: separate equity tree in CoA SKR04
2020-12-17 09:15:11 +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
0de091a749 Merge pull request #24159 from deepeshgarg007/template_update_v12
fix(India): Taxation fixes
2020-12-17 09:11:20 +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
Deepesh Garg
2d073016ee Merge branch 'version-12-hotfix' of https://github.com/frappe/erpnext into template_update_v12 2020-12-16 20:43:11 +05:30
Deepesh Garg
12f95c41b9 fix: Tax template update on customer address change 2020-12-16 20:38:54 +05:30
pateljannat
7fb22fd652 fix: removing return_taxes condition 2020-12-16 20:13:22 +05:30
pateljannat
284a19c99d fix: company filter added again 2020-12-16 20:12:38 +05:30
pateljannat
1a401b1427 fix: linter issue for translation syntax 2020-12-16 20:12:24 +05:30
pateljannat
b2db8031d5 fix: reversing previous commits and adding condition in regional controller 2020-12-16 20:12:04 +05:30
pateljannat
58fae20ff9 fix: place of supply change on address change 2020-12-16 20:10:16 +05:30
pateljannat
2cf9cc02e1 fix: place of supply change when address changes 2020-12-16 20:10:06 +05:30
Deepesh Garg
9b893643c0 fix: Tax template update on supplier 2020-12-16 20:09:39 +05:30
Marica
126de4d0e5 Merge pull request #24156 from frappe/revert-24131-version-12-hotfix
fix: Revert "fix: po_not retaining on save"
2020-12-16 18:13:16 +05:30
Marica
18635e4dd1 Revert "fix: po_not retaining on save" 2020-12-16 17:02:41 +05:30
Marica
4b75d528c9 Merge pull request #24131 from hasnain2808/version-12-hotfix
fix: po_not retaining on save
2020-12-16 16:42:57 +05:30
Mohammad Hasnain Mohsin Rajan
5220e9201b Merge branch 'version-12-hotfix' into version-12-hotfix 2020-12-16 15:29:53 +05:30
Anurag Mishra
ee7bcc0350 fix: Added TDS Payable account number and an error message
fix: Added TDS Payable account number and an error message
2020-12-16 13:49:41 +05:30
Mohammad Hasnain
1f2ec25493 fix: po_no not cleaned up on save 2020-12-15 14:48:44 +05:30
Mohammad Hasnain
e46a72b101 fix: po_no getting removed on save 2020-12-15 14:41:35 +05:30
Rucha Mahabal
b4dfba54b6 fix(Asset): set current asset value before calculating difference amount (#24119) 2020-12-15 12:50:15 +05:30
Saqib Ansari
9daf4418ea feat: add docs link to e invoice settings 2020-12-14 19:14:43 +05:30
Saqib Ansari
695e551972 fix: error handling 2020-12-14 18:59:01 +05:30
Saqib Ansari
e6a07d5508 fix: dialog is undefined 2020-12-14 17:31:31 +05:30
Saqib Ansari
d67affdfae fix: minor ux issues 2020-12-14 17:15:36 +05:30
Saqib Ansari
cde452add7 feat: show e-invoice preview before IRN generation 2020-12-14 16:51:25 +05:30
Saqib Ansari
5c74cdd0d2 fix: adjust qr code image size 2020-12-14 16:40:23 +05:30
Marica
58b1e3b866 Merge branch 'version-12-hotfix' into track-changes-for-stock-settings-v12 2020-12-14 13:14:05 +05:30
Anurag Mishra
b16d625b4f Merge pull request #24118 from deepeshgarg007/unique_tax_category_v12
fix: Validation for duplicate Tax Category
2020-12-14 12:39:08 +05:30
Saqib Ansari
96f0b0e30a Merge branch 'version-12-hotfix' into e-invoicing-version-12 2020-12-14 12:25:00 +05:30
Saqib Ansari
390cac2160 fix: sider issues 2020-12-14 12:19:30 +05:30
Saqib Ansari
64e9275c4a chore: add ack date and ack no field for print formats 2020-12-14 12:19:24 +05:30
Saqib Ansari
42b028a3ba feat: log e-invocing requests 2020-12-14 12:19:19 +05:30
Saqib Ansari
5327637b37 fix: returning condition 2020-12-14 12:19:12 +05:30
Saqib Ansari
5d6849ac7f chore: add tests 2020-12-14 12:19:06 +05:30
Saqib Ansari
57e6759088 fix: ewaybill mandatory conditions 2020-12-14 12:18:54 +05:30
Saqib Ansari
9760eb9d57 fix: eway bill test 2020-12-14 12:15:04 +05:30
Saqib Ansari
ee0b08ae9c fix: exclude intra company transactions 2020-12-14 12:14:55 +05:30
Nabin Hait
22e770353f fix: Translation issue 2020-12-14 11:00:59 +05:30
Deepesh Garg
bbce16e00c fix: Validation for duplicate Tax Category 2020-12-14 10:57:29 +05:30
Nabin Hait
2bd620fac8 fix: Fixed merge conflict 2020-12-11 22:34:34 +05:30
pateljannat
3dbf88ba6f fix: indentation 2020-12-11 10:25:08 +05:30
Anuja P
1cd57a324c fix: Added TDS account number and an error message 2020-12-10 22:05:09 +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
Raffael Meyer
e8f4eb02be Merge branch 'version-12-hotfix' into skr04_equity 2020-12-10 10:52:26 +01:00
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
barredterra
f76b0dea44 feat: separate equity tree in CoA SKR04 2020-12-09 17:45:00 +01:00
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
pateljannat
3252d9d943 fix: enabling track changes for stock settings 2020-11-23 16:41:51 +05:30
pateljannat
9655edabd9 fix: enabling track changes for stock settings 2020-11-23 16:37:00 +05:30
pateljannat
2704327029 fix: enabling track changes for stock settings 2020-11-23 16:34:40 +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
pateljannat
3e526b8ca8 fix: enabling track changes for stock settings 2020-11-23 16:19:50 +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
Smit Vora
c630be6781 fix: remove unused imports 2020-11-19 19:13:06 +05:30
Smit Vora
51a153d8c2 fix: removed unused code 2020-11-19 19:03:22 +05:30
Smit Vora
707b630851 fix: add remarks to sales invoice 2020-11-19 18:42:39 +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
Saqib Ansari
c82c955bc2 fix: qrcode image size 2020-11-08 13:03:00 +05:30
Saqib Ansari
dc4b0921f6 feat: update timeline on einvoice actions 2020-11-07 21:15:19 +05:30
Saqib Ansari
72ed0fbbb4 fix: ewaybill could be modified after ewaybill generation 2020-11-07 21:00:38 +05:30
Saqib Ansari
020e6e980a fix: error handling 2020-11-07 19:44:37 +05:30
Saqib Ansari
70e0711893 fix: imports 2020-11-07 19:43:47 +05:30
Saqib Ansari
8693ac81a2 fix: import format_date 2020-11-07 17:53:22 +05:30
Saqib Ansari
56116f28af Merge branch 'version-12-hotfix' into e-invoicing-version-12 2020-11-07 17:49:44 +05:30
Saqib Ansari
eeb99d1b98 chore: remove fetch token from e invocie settings 2020-11-07 17:47:34 +05:30
Saqib Ansari
5d23c0ce8e feat: cess non advolem on einvoice item 2020-11-07 17:47:28 +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
Saqib Ansari
91580258d7 fix: patch 2020-11-05 13:56:04 +05:30
Saqib Ansari
51ddf376da fix: invalid syntax 2020-11-05 13:51:11 +05:30
Saqib Ansari
db4fec0314 fix: invalid syntax 2020-11-05 13:48:12 +05:30
Saqib Ansari
6d63a1e90a chore: remove test pincode 2020-11-05 13:18:26 +05:30
Saqib Ansari
589a49a38a feat: header & footer in GST E Invoice 2020-11-05 13:18:25 +05:30
Saqib Ansari
464fc1f087 chore: error logging 2020-11-05 13:18:25 +05:30
Saqib Ansari
e3c2f0a221 chore: remove unwanted imports 2020-11-05 13:18:25 +05:30
Saqib Ansari
77b8ced4a4 feat: generate eway bill from IRN 2020-11-05 13:18:24 +05:30
Saqib Ansari
fb9dde38f6 fix: valiations 2020-11-05 13:18:24 +05:30
Saqib Ansari
ca944316b4 fix: show/hide eway bill fields 2020-11-05 13:18:20 +05:30
Saqib Ansari
6d5a8aea9a fix: generate & cancel IRN 2020-11-05 13:17:59 +05:30
Saqib Ansari
eb9f216b40 fix: attach qrcode on irn generation 2020-11-05 13:17:59 +05:30
Saqib Ansari
63bfa30bc1 chore: clean up einvoice actions 2020-11-05 13:17:59 +05:30
Saqib Ansari
778141c569 chore: remove unwanted fuctions 2020-11-05 13:17:58 +05:30
Saqib Ansari
b7ee2a44a0 feat: cancel eway bill 2020-11-05 13:17:58 +05:30
Saqib Ansari
3f9390c077 feat: generate & cancel IRN 2020-11-05 13:17:58 +05:30
Saqib Ansari
495ac7ba6b feat: fetch and cache GSTIN details 2020-11-05 13:17:57 +05:30
Saqib Ansari
ad19268b4c fix: qr code generation 2020-11-05 13:17:57 +05:30
Saqib Ansari
54405a4b64 chore: remove unwanted fields 2020-11-05 13:17:57 +05:30
Saqib Ansari
86f87e9b53 feat: initialize GSP connector 2020-11-05 13:17:57 +05:30
Saqib Ansari
049836dff8 fix: qr code image string 2020-11-05 13:17:56 +05:30
Saqib Ansari
c313f05a8e chore: improve document name validation message 2020-11-05 13:17:56 +05:30
Saqib Ansari
b77375c72b fix: other charges calculation 2020-11-05 13:17:56 +05:30
Saqib Ansari
6c064a1f95 fix: invoice totals calculation 2020-11-05 13:17:55 +05:30
Saqib Ansari
9182c2e09d fix: patch 2020-11-05 13:17:55 +05:30
Saqib Ansari
271f35fef5 fix: einvoice field validation 2020-11-05 13:17:55 +05:30
Saqib Ansari
37e4c91ec2 fix: rename e_invoice_utils.py 2020-11-05 13:17:54 +05:30
Saqib Ansari
12d9bc3787 fix: add missing package 2020-11-05 13:17:54 +05:30
Saqib Ansari
5eb430fe51 fix: e_invoice module not found 2020-11-05 13:17:54 +05:30
Saqib Ansari
31ee8b4011 fix: error logging 2020-11-05 13:17:53 +05:30
Saqib Ansari
9363725342 fix: validations 2020-11-05 13:17:53 +05:30
Saqib Ansari
e1e3dbcae2 fix: credit note einvoice 2020-11-05 13:17:53 +05:30
Saqib Ansari
8616684c24 fix: return date 2020-11-05 13:17:52 +05:30
Saqib Ansari
90a57c1f8c fix: validate document name 2020-11-05 13:17:52 +05:30
Saqib Ansari
ba1cd74189 feat: add patch 2020-11-05 13:17:46 +05:30
Saqib Ansari
c3719b46b2 fix: add permissions on regional setup 2020-11-05 13:17:14 +05:30
Saqib Ansari
e50804fb9d fix: validations 2020-11-05 13:17:14 +05:30
Saqib Ansari
cc704044bd fix: print format 2020-11-05 13:17:14 +05:30
Saqib Ansari
e6646efef3 fix: download & upload e-invoice 2020-11-05 13:17:13 +05:30
Saqib Ansari
57dd4689e0 chore: clean up e invoice actions 2020-11-05 13:17:13 +05:30
Saqib Ansari
08b4736ee0 chore: code cleanup 2020-11-05 13:17:13 +05:30
Saqib Ansari
662a0fcfe9 fix: invalid syntax 2020-11-05 13:17:12 +05:30
Saqib Ansari
d6f3be0fc1 fix: bug 2020-11-05 13:17:12 +05:30
Saqib Ansari
154c433a86 feat: QRCode Image and E-Invoice Print Format 2020-11-05 13:17:12 +05:30
Saqib Ansari
d3a6b9ed81 chore: move einvoicing stuff to seperate folder 2020-11-05 13:17:12 +05:30
Saqib Ansari
9c00b22703 fix: fetch token if not valid 2020-11-05 13:17:11 +05:30
Saqib Ansari
b3e0f482ac chore: save signed invoice and qrcode after uplaoding irn 2020-11-05 13:17:11 +05:30
Saqib Ansari
61824d3735 fix: fn name 2020-11-05 13:17:11 +05:30
Saqib Ansari
ada41295bb chore: group e-invoicing actions 2020-11-05 13:17:11 +05:30
Saqib Ansari
08e89b88f4 feat: manual download / upload json 2020-11-05 13:17:10 +05:30
Saqib Ansari
cc43805f25 feat: cancel e-way bill before cancelling IRN 2020-11-05 13:17:10 +05:30
Saqib Ansari
ec28262988 chore: no copy on e invoice custom fields 2020-11-05 13:17:10 +05:30
Saqib Ansari
22754a9c58 fix: save e-way bill no on irn generation 2020-11-05 13:17:10 +05:30
Saqib Ansari
6a9af076e5 feat: e-way bill details in e-invoice 2020-11-05 13:17:10 +05:30
Saqib Ansari
816235e99c chore: show irn field for proper gst_category 2020-11-05 13:17:09 +05:30
Saqib Ansari
dfbdd0b2ee fix: update irn_cancelled after cancelling irn 2020-11-05 13:17:09 +05:30
Saqib Ansari
59a757b3e3 fix: do not show generate irn for invalid supply type 2020-11-05 13:17:09 +05:30
Saqib Ansari
389610fb45 fix: validation if e invoicing is disabled 2020-11-05 13:17:09 +05:30
Saqib Ansari
175b26e6e8 fix: cannot find attached key file 2020-11-05 13:17:08 +05:30
Saqib Ansari
cea1a15dcd fix: public key is required on validate 2020-11-05 13:17:08 +05:30
Saqib Ansari
7a40ad340f fix: hide cancel irn dialog on error 2020-11-05 13:17:08 +05:30
Saqib Ansari
db13eb56c4 chore: show irn cancelled check after cancellation 2020-11-05 13:17:08 +05:30
Saqib Ansari
cf2ebc0d6f fix: item discount 2020-11-05 13:17:07 +05:30
Saqib Ansari
9003718481 chore: minor fixes 2020-11-05 13:17:07 +05:30
Saqib Ansari
18666b6a74 feat: Generate & Cancel IRN from Sales Invoice 2020-11-05 13:17:07 +05:30
Saqib Ansari
395ecf2392 feat: make IRN field on regional setup 2020-11-05 13:17:07 +05:30
Saqib Ansari
221e5993a8 chore: rename schema to template & js cleanup 2020-11-05 13:17:06 +05:30
Saqib Ansari
8eda5aca09 chore: split einvoice settings and operations 2020-11-05 13:17:06 +05:30
Saqib Ansari
bdfd30760a chore: move e-invoice settings to regional 2020-11-05 13:17:06 +05:30
Saqib Ansari
418818f0ec feat: complete e-invoice schema 2020-11-05 13:17:05 +05:30
Saqib Ansari
d971917ecf feat: cancel IRN 2020-11-05 13:17:05 +05:30
Saqib Ansari
dda44bb1f5 chore: validations 2020-11-05 13:17:05 +05:30
Saqib Ansari
448ab6e3df feat: decode signed json and QR code 2020-11-05 13:17:04 +05:30
Saqib Ansari
cc3e0bf806 feat: generate IRN 2020-11-05 13:17:04 +05:30
Saqib Ansari
93b3c2ce06 feat: make e invoice from erpnext sales invoice 2020-11-05 13:17:04 +05:30
Saqib Ansari
7c427aa890 feat: decrypt json data with SEK 2020-11-05 13:17:03 +05:30
Saqib Ansari
b6509ead64 feat: AES decryption of SEK with appkey 2020-11-05 13:17:03 +05:30
Saqib Ansari
f8346ce62f chore: handle error response 2020-11-05 13:17:03 +05:30
Saqib Ansari
e73a9deb42 feat: save token and sek from auth request 2020-11-05 13:17:02 +05:30
Saqib Ansari
5669a5f618 feat: rsa encryption with public key 2020-11-05 13:17:02 +05:30
Saqib Ansari
18afbc0617 feat: read public key file 2020-11-05 13:17:02 +05:30
Saqib Ansari
f396b35622 feat: init e-invoice settings 2020-11-05 13:17:02 +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
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
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
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
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
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
90eb489392 fix: added filter show in website for filtering product 2020-10-14 15:26:34 +05:30
185 changed files with 6424 additions and 1738 deletions

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.13.0'
__version__ = '12.18.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

@@ -910,75 +910,8 @@
},
"is_group": 1
},
"Passiva": {
"Passiva - Verbindlichkeiten": {
"root_type": "Liability",
"A - Eigenkapital": {
"account_type": "Equity",
"is_group": 1,
"I - Gezeichnetes Kapital": {
"account_type": "Equity",
"is_group": 1
},
"II - Kapitalr\u00fccklage": {
"account_type": "Equity",
"is_group": 1
},
"III - Gewinnr\u00fccklagen": {
"account_type": "Equity",
"1 - gesetzliche R\u00fccklage": {
"account_type": "Equity",
"is_group": 1
},
"2 - R\u00fccklage f. Anteile an einem herrschenden oder mehrheitlich beteiligten Unternehmen": {
"account_type": "Equity",
"is_group": 1
},
"3 - satzungsm\u00e4\u00dfige R\u00fccklagen": {
"account_type": "Equity",
"is_group": 1
},
"4 - andere Gewinnr\u00fccklagen": {
"account_type": "Equity",
"is_group": 1,
"Gewinnr\u00fccklagen aus den \u00dcbergangsvorschriften BilMoG": {
"is_group": 1,
"Gewinnr\u00fccklagen (BilMoG)": {
"account_number": "2963"
},
"Gewinnr\u00fccklagen aus Zuschreibung Sachanlageverm\u00f6gen (BilMoG)": {
"account_number": "2964"
},
"Gewinnr\u00fccklagen aus Zuschreibung Finanzanlageverm\u00f6gen (BilMoG)": {
"account_number": "2965"
},
"Gewinnr\u00fccklagen aus Aufl\u00f6sung der Sonderposten mit R\u00fccklageanteil (BilMoG)": {
"account_number": "2966"
}
},
"Latente Steuern (Gewinnr\u00fccklage Haben) aus erfolgsneutralen Verrechnungen": {
"account_number": "2967"
},
"Latente Steuern (Gewinnr\u00fccklage Soll) aus erfolgsneutralen Verrechnungen": {
"account_number": "2968"
},
"Rechnungsabgrenzungsposten (Gewinnr\u00fccklage Soll) aus erfolgsneutralen Verrechnungen": {
"account_number": "2969"
}
},
"is_group": 1
},
"IV - Gewinnvortrag/Verlustvortrag": {
"account_type": "Equity",
"is_group": 1
},
"V - Jahres\u00fcberschu\u00df/Jahresfehlbetrag": {
"account_type": "Equity",
"is_group": 1
},
"Einlagen stiller Gesellschafter": {
"account_number": "9295"
}
},
"B - R\u00fcckstellungen": {
"is_group": 1,
"1 - R\u00fcckstellungen f. Pensionen und \u00e4hnliche Verplicht.": {
@@ -1595,6 +1528,143 @@
},
"is_group": 1
},
"Passiva - Eigenkapital": {
"root_type": "Equity",
"A - Eigenkapital": {
"account_type": "Equity",
"is_group": 1,
"I - Gezeichnetes Kapital": {
"account_type": "Equity",
"is_group": 1,
"Gezeichnetes Kapital": {
"account_number": "2900",
"account_type": "Equity"
},
"Gesch\u00e4ftsguthaben der verbleibenden Mitglieder": {
"account_number": "2901"
},
"Gesch\u00e4ftsguthaben der ausscheidenden Mitglieder": {
"account_number": "2902"
},
"Gesch\u00e4ftsguthaben aus gek\u00fcndigten Gesch\u00e4ftsanteilen": {
"account_number": "2903"
},
"R\u00fcckst\u00e4ndige f\u00e4llige Einzahlungen auf Gesch\u00e4ftsanteile, vermerkt": {
"account_number": "2906"
},
"Gegenkonto R\u00fcckst\u00e4ndige f\u00e4llige Einzahlungen auf Gesch\u00e4ftsanteile, vermerkt": {
"account_number": "2907"
},
"Kapitalerh\u00f6hung aus Gesellschaftsmitteln": {
"account_number": "2908"
},
"Ausstehende Einlagen auf das gezeichnete Kapital, nicht eingefordert": {
"account_number": "2910"
}
},
"II - Kapitalr\u00fccklage": {
"account_type": "Equity",
"is_group": 1,
"Kapitalr\u00fccklage": {
"account_number": "2920"
},
"Kapitalr\u00fccklage durch Ausgabe von Anteilen \u00fcber Nennbetrag": {
"account_number": "2925"
},
"Kapitalr\u00fccklage durch Ausgabe von Schuldverschreibungen": {
"account_number": "2926"
},
"Kapitalr\u00fccklage durch Zuzahlungen gegen Gew\u00e4hrung eines Vorzugs": {
"account_number": "2927"
},
"Kapitalr\u00fccklage durch Zuzahlungen in das Eigenkapital": {
"account_number": "2928"
},
"Nachschusskapital (Gegenkonto 1299)": {
"account_number": "2929"
}
},
"III - Gewinnr\u00fccklagen": {
"account_type": "Equity",
"1 - gesetzliche R\u00fccklage": {
"account_type": "Equity",
"is_group": 1,
"Gesetzliche R\u00fccklage": {
"account_number": "2930"
}
},
"2 - R\u00fccklage f. Anteile an einem herrschenden oder mehrheitlich beteiligten Unternehmen": {
"account_type": "Equity",
"is_group": 1,
"R\u00fccklage f. Anteile an einem herrschenden oder mehrheitlich beteiligten Unternehmen": {
"account_number": "2935"
}
},
"3 - satzungsm\u00e4\u00dfige R\u00fccklagen": {
"account_type": "Equity",
"is_group": 1,
"Satzungsm\u00e4\u00dfige R\u00fccklagen": {
"account_number": "2950"
}
},
"4 - andere Gewinnr\u00fccklagen": {
"account_type": "Equity",
"is_group": 1,
"Andere Gewinnr\u00fccklagen": {
"account_number": "2960"
},
"Andere Gewinnr\u00fccklagen aus dem Erwerb eigener Anteile": {
"account_number": "2961"
},
"Eigenkapitalanteil von Wertaufholungen": {
"account_number": "2962"
},
"Gewinnr\u00fccklagen aus den \u00dcbergangsvorschriften BilMoG": {
"is_group": 1,
"Gewinnr\u00fccklagen (BilMoG)": {
"account_number": "2963"
},
"Gewinnr\u00fccklagen aus Zuschreibung Sachanlageverm\u00f6gen (BilMoG)": {
"account_number": "2964"
},
"Gewinnr\u00fccklagen aus Zuschreibung Finanzanlageverm\u00f6gen (BilMoG)": {
"account_number": "2965"
},
"Gewinnr\u00fccklagen aus Aufl\u00f6sung der Sonderposten mit R\u00fccklageanteil (BilMoG)": {
"account_number": "2966"
}
},
"Latente Steuern (Gewinnr\u00fccklage Haben) aus erfolgsneutralen Verrechnungen": {
"account_number": "2967"
},
"Latente Steuern (Gewinnr\u00fccklage Soll) aus erfolgsneutralen Verrechnungen": {
"account_number": "2968"
},
"Rechnungsabgrenzungsposten (Gewinnr\u00fccklage Soll) aus erfolgsneutralen Verrechnungen": {
"account_number": "2969"
}
},
"is_group": 1
},
"IV - Gewinnvortrag/Verlustvortrag": {
"account_type": "Equity",
"is_group": 1,
"Gewinnvortrag vor Verwendung": {
"account_number": "2970"
},
"Verlustvortrag vor Verwendung": {
"account_number": "2978"
}
},
"V - Jahres\u00fcberschu\u00df/Jahresfehlbetrag": {
"account_type": "Equity",
"is_group": 1
},
"Einlagen stiller Gesellschafter": {
"account_number": "9295"
}
}
},
"1 - Umsatzerl\u00f6se": {
"root_type": "Income",
"is_group": 1,

View File

@@ -245,6 +245,9 @@ def get():
"account_number": "2200"
},
_("Duties and Taxes"): {
_("TDS Payable"): {
"account_number": "2310"
},
"account_type": "Tax",
"is_group": 1,
"account_number": "2300"

View File

@@ -41,6 +41,8 @@ frappe.ui.form.on('Accounting Dimension', {
});
});
}
frm.toggle_enable('document_type', frm.doc.__islocal);
},
document_type: function(frm) {

View File

@@ -29,6 +29,16 @@ class AccountingDimension(Document):
if exists and self.is_new():
frappe.throw("Document Type already used as a dimension")
if not self.is_new():
self.validate_document_type_change()
def validate_document_type_change(self):
doctype_before_save = frappe.db.get_value("Accounting Dimension", self.name, "document_type")
if doctype_before_save != self.document_type:
message = _("Cannot change Reference Document Type.")
message += _("Please create a new Accounting Dimension if required.")
frappe.throw(message)
def after_insert(self):
if frappe.flags.in_test:
make_dimension_in_accounting_doctypes(doc=self)

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

@@ -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

@@ -138,7 +138,8 @@ class GLEntry(Document):
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():
if not self.flags.from_repost and not self.voucher_type == 'Period Closing Voucher' \
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)))

View File

@@ -38,7 +38,10 @@ def get_loyalty_details(customer, loyalty_program, expiry_date=None, company=Non
@frappe.whitelist()
def get_loyalty_program_details_with_points(customer, loyalty_program=None, expiry_date=None, company=None, silent=False, include_expired_entry=False, current_transaction_amount=0):
lp_details = get_loyalty_program_details(customer, loyalty_program, company=company, silent=silent)
loyalty_program = frappe.get_doc("Loyalty Program", loyalty_program)
loyalty_program_name = loyalty_program or lp_details.loyalty_program
if not loyalty_program_name: return
loyalty_program = frappe.get_doc("Loyalty Program", loyalty_program_name)
lp_details.update(get_loyalty_details(customer, loyalty_program.name, expiry_date, company, include_expired_entry))
# sort collection rule, first item on list will be lowest min_spent

View File

@@ -181,7 +181,8 @@ class OpeningInvoiceCreationTool(Document):
"due_date": row.due_date,
"posting_date": row.posting_date,
frappe.scrub(party_type): row.party,
"doctype": "Sales Invoice" if self.invoice_type == "Sales" else "Purchase Invoice"
"doctype": "Sales Invoice" if self.invoice_type == "Sales" else "Purchase Invoice",
"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

@@ -187,7 +187,7 @@ frappe.ui.form.on('Payment Entry', {
frm.toggle_display("base_received_amount", (
frm.doc.paid_to_account_currency != company_currency &&
frm.doc.paid_from_account_currency != frm.doc.paid_to_account_currency
frm.doc.paid_from_account_currency != frm.doc.paid_to_account_currency
&& frm.doc.base_paid_amount != frm.doc.base_received_amount
));
@@ -386,6 +386,8 @@ frappe.ui.form.on('Payment Entry', {
set_account_currency_and_balance: function(frm, account, currency_field,
balance_field, callback_function) {
var company_currency = frappe.get_doc(":Company", frm.doc.company).default_currency;
if (frm.doc.posting_date && account) {
frappe.call({
method: "erpnext.accounts.doctype.payment_entry.payment_entry.get_account_details",
@@ -412,6 +414,14 @@ frappe.ui.form.on('Payment Entry', {
if(!frm.doc.paid_amount && frm.doc.received_amount)
frm.events.received_amount(frm);
if (frm.doc.paid_from_account_currency == frm.doc.paid_to_account_currency
&& frm.doc.paid_amount != frm.doc.received_amount) {
if (company_currency != frm.doc.paid_from_account_currency &&
frm.doc.payment_type == "Pay") {
frm.doc.paid_amount = frm.doc.received_amount;
}
}
}
},
() => {

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

@@ -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,37 +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() {
@@ -90,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: {
@@ -99,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

@@ -88,18 +88,18 @@ class PaymentReconciliation(Document):
voucher_type = ('Sales Invoice'
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,
return frappe.db.sql(""" SELECT doc.name as reference_name, %(voucher_type)s as reference_type,
(sum(gl.{dr_or_cr}) - sum(gl.{reconciled_dr_or_cr})) as amount,
account_currency as currency
FROM `tab{doc}`, `tabGL Entry`
FROM `tab{doc}` doc, `tabGL Entry` gl
WHERE
(`tab{doc}`.name = `tabGL Entry`.against_voucher or `tab{doc}`.name = `tabGL Entry`.voucher_no)
and `tab{doc}`.{party_type_field} = %(party)s
and `tab{doc}`.is_return = 1 and `tab{doc}`.return_against IS NULL
and `tabGL Entry`.against_voucher_type = %(voucher_type)s
and `tab{doc}`.docstatus = 1 and `tabGL Entry`.party = %(party)s
and `tabGL Entry`.party_type = %(party_type)s and `tabGL Entry`.account = %(account)s
GROUP BY `tab{doc}`.name
(doc.name = gl.against_voucher or doc.name = gl.voucher_no)
and doc.{party_type_field} = %(party)s
and doc.is_return = 1 and ifnull(doc.return_against, "") = ""
and gl.against_voucher_type = %(voucher_type)s
and doc.docstatus = 1 and gl.party = %(party)s
and gl.party_type = %(party_type)s and gl.account = %(account)s
GROUP BY doc.name
Having
amount > 0
""".format(
@@ -303,4 +303,4 @@ def reconcile_dr_cr_note(dr_cr_notes, company):
]
})
jv.submit()
jv.submit()

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

@@ -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

@@ -49,9 +49,10 @@ 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)
@@ -341,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
})

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

@@ -453,6 +453,9 @@ def apply_pricing_rule_on_transaction(doc):
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:
@@ -476,6 +479,12 @@ 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 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:
@@ -488,7 +497,7 @@ def get_applied_pricing_rules(pricing_rules):
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:
@@ -517,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

@@ -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)

View File

@@ -153,8 +153,8 @@ def update_multi_mode_option(doc, pos_profile):
def get_mode_of_payment(doc):
return frappe.db.sql("""
select mpa.default_account, mpa.parent, mp.type as type
from `tabMode of Payment Account` mpa,`tabMode of Payment` mp
select mpa.default_account, mpa.parent, mp.type as type
from `tabMode of Payment Account` mpa,`tabMode of Payment` mp
where mpa.parent = mp.name and mpa.company = %(company)s and mp.enabled = 1""",
{'company': doc.company}, as_dict=1)
@@ -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):
@@ -385,6 +394,14 @@ def get_pricing_rule_data(doc):
between ifnull(valid_from, '2000-01-01') and ifnull(valid_upto, '2500-12-31')
order by priority desc, name desc""",
{'company': doc.company, 'price_list': doc.selling_price_list, 'date': nowdate()}, as_dict=1)
for row in pricing_rules:
if row.apply_on:
doctype = "Pricing Rule " + row.apply_on
apply_on = frappe.scrub(row.apply_on)
row[apply_on] = [d.get(apply_on) for d in frappe.get_all(doctype,
filters = {"parent": row.name}, fields = [apply_on])]
return pricing_rules
@@ -425,10 +442,10 @@ def make_invoice(pos_profile, doc_list={}, email_queue_list={}, customers_list={
name_list.append(name)
email_queue = make_email_queue(email_queue_list)
if isinstance(pos_profile, string_types):
pos_profile = json.loads(pos_profile)
customers = get_customers_list(pos_profile)
return {
'invoice': name_list,

View File

@@ -1,6 +1,8 @@
{% include "erpnext/regional/india/taxes.js" %}
{% include "erpnext/regional/india/e_invoice/einvoice.js" %}
erpnext.setup_auto_gst_taxation('Sales Invoice');
erpnext.setup_einvoice_actions('Sales Invoice')
frappe.ui.form.on("Sales Invoice", {
setup: function(frm) {
@@ -12,6 +14,16 @@ frappe.ui.form.on("Sales Invoice", {
};
});
frm.set_query('transporter_address', function (doc) {
return {
query: 'frappe.contacts.doctype.address.address.address_query',
filters: {
link_doctype: 'Supplier',
link_name: doc.transporter
}
}
});
frm.set_query('driver', function(doc) {
return {
filters: {

View File

@@ -4,7 +4,7 @@
from __future__ import unicode_literals
import frappe, erpnext
import frappe.defaults
from frappe.utils import cint, flt, add_months, today, date_diff, getdate, add_days, cstr, nowdate
from frappe.utils import cint, flt, getdate, add_days, cstr, nowdate, formatdate
from frappe import _, msgprint, throw
from erpnext.accounts.party import get_party_account, get_due_date
from erpnext.controllers.stock_controller import update_gl_entries_after
@@ -225,9 +225,9 @@ class SalesInvoice(SellingController):
frappe.throw(_("At least one mode of payment is required for POS invoice."))
def before_cancel(self):
super(SalesInvoice, self).before_cancel()
self.update_time_sheet(None)
def on_cancel(self):
super(SalesInvoice, self).on_cancel()
@@ -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)
@@ -530,7 +537,12 @@ class SalesInvoice(SellingController):
self.against_income_account = ','.join(against_acc)
def add_remarks(self):
if not self.remarks: self.remarks = 'No Remarks'
if not self.remarks:
if self.po_no and self.po_date:
self.remarks = _("Against Customer Order {0} dated {1}").format(self.po_no,
formatdate(self.po_date))
else:
self.remarks = _("No Remarks")
def validate_auto_set_posting_time(self):
# Don't auto set the posting date and time if invoice is amended
@@ -570,7 +582,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"))
@@ -1394,6 +1407,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

@@ -690,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")
@@ -773,7 +774,8 @@ class TestSalesInvoice(unittest.TestCase):
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")
@@ -795,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)
@@ -1838,93 +1841,7 @@ class TestSalesInvoice(unittest.TestCase):
self.assertEqual(target_doc.supplier, "_Test Internal Supplier")
def test_eway_bill_json(self):
if not frappe.db.exists('Address', '_Test Address for Eway bill-Billing'):
address = frappe.get_doc({
"address_line1": "_Test Address Line 1",
"address_title": "_Test Address for Eway bill",
"address_type": "Billing",
"city": "_Test City",
"state": "Test State",
"country": "India",
"doctype": "Address",
"is_primary_address": 1,
"phone": "+91 0000000000",
"gstin": "27AAECE4835E1ZR",
"gst_state": "Maharashtra",
"gst_state_number": "27",
"pincode": "401108"
}).insert()
address.append("links", {
"link_doctype": "Company",
"link_name": "_Test Company"
})
address.save()
if not frappe.db.exists('Address', '_Test Customer-Address for Eway bill-Shipping'):
address = frappe.get_doc({
"address_line1": "_Test Address Line 1",
"address_title": "_Test Customer-Address for Eway bill",
"address_type": "Shipping",
"city": "_Test City",
"state": "Test State",
"country": "India",
"doctype": "Address",
"is_primary_address": 1,
"phone": "+91 0000000000",
"gst_state": "Maharashtra",
"gst_state_number": "27",
"pincode": "410038"
}).insert()
address.append("links", {
"link_doctype": "Customer",
"link_name": "_Test Customer"
})
address.save()
gst_settings = frappe.get_doc("GST Settings")
gst_account = frappe.get_all(
"GST Account",
fields=["cgst_account", "sgst_account", "igst_account"],
filters = {"company": "_Test Company"})
if not gst_account:
gst_settings.append("gst_accounts", {
"company": "_Test Company",
"cgst_account": "CGST - _TC",
"sgst_account": "SGST - _TC",
"igst_account": "IGST - _TC",
})
gst_settings.save()
si = create_sales_invoice(do_not_save =1, rate = '60000')
si.distance = 2000
si.company_address = "_Test Address for Eway bill-Billing"
si.customer_address = "_Test Customer-Address for Eway bill-Shipping"
si.vehicle_no = "KA12KA1234"
si.gst_category = "Registered Regular"
si.append("taxes", {
"charge_type": "On Net Total",
"account_head": "CGST - _TC",
"cost_center": "Main - _TC",
"description": "CGST @ 9.0",
"rate": 9
})
si.append("taxes", {
"charge_type": "On Net Total",
"account_head": "SGST - _TC",
"cost_center": "Main - _TC",
"description": "SGST @ 9.0",
"rate": 9
})
si = make_sales_invoice_for_ewaybill()
si.submit()
@@ -1940,27 +1857,195 @@ class TestSalesInvoice(unittest.TestCase):
self.assertEqual(data['billLists'][0]['sgstValue'], 5400)
self.assertEqual(data['billLists'][0]['vehicleNo'], 'KA12KA1234')
self.assertEqual(data['billLists'][0]['itemList'][0]['taxableAmount'], 60000)
def test_einvoice_submission_without_irn(self):
# init
frappe.db.set_value('E Invoice Settings', 'E Invoice Settings', 'enable', 1)
country = frappe.flags.country
frappe.flags.country = 'India'
def test_item_tax_validity(self):
item = frappe.get_doc("Item", "_Test Item 2")
si = make_sales_invoice_for_ewaybill()
self.assertRaises(frappe.ValidationError, si.submit)
if item.taxes:
item.taxes = []
item.save()
si.irn = 'test_irn'
si.submit()
item.append("taxes", {
"item_tax_template": "_Test Item Tax Template 1",
"valid_from": add_days(nowdate(), 1)
# reset
frappe.db.set_value('E Invoice Settings', 'E Invoice Settings', 'enable', 0)
frappe.flags.country = country
def test_einvoice_json(self):
from erpnext.regional.india.e_invoice.utils import make_einvoice
si = make_sales_invoice_for_ewaybill()
si.naming_series = 'INV-2020-.#####'
si.items = []
si.append("items", {
"item_code": "_Test Item",
"uom": "Nos",
"warehouse": "_Test Warehouse - _TC",
"qty": 2000,
"rate": 12,
"income_account": "Sales - _TC",
"expense_account": "Cost of Goods Sold - _TC",
"cost_center": "_Test Cost Center - _TC",
})
si.append("items", {
"item_code": "_Test Item 2",
"uom": "Nos",
"warehouse": "_Test Warehouse - _TC",
"qty": 420,
"rate": 15,
"income_account": "Sales - _TC",
"expense_account": "Cost of Goods Sold - _TC",
"cost_center": "_Test Cost Center - _TC",
})
si.discount_amount = 100
si.save()
einvoice = make_einvoice(si)
total_item_ass_value = 0
total_item_cgst_value = 0
total_item_sgst_value = 0
total_item_igst_value = 0
total_item_value = 0
for item in einvoice['ItemList']:
total_item_ass_value += item['AssAmt']
total_item_cgst_value += item['CgstAmt']
total_item_sgst_value += item['SgstAmt']
total_item_igst_value += item['IgstAmt']
total_item_value += item['TotItemVal']
self.assertTrue(item['AssAmt'], item['TotAmt'] - item['Discount'])
self.assertTrue(item['TotItemVal'], item['AssAmt'] + item['CgstAmt'] + item['SgstAmt'] + item['IgstAmt'])
value_details = einvoice['ValDtls']
self.assertEqual(einvoice['Version'], '1.1')
self.assertTrue(abs(value_details['AssVal'] - total_item_ass_value) <= 1)
self.assertTrue(abs(value_details['CgstVal'] - total_item_cgst_value) <= 1)
self.assertTrue(abs(value_details['SgstVal'] - total_item_sgst_value) <= 1)
self.assertTrue(abs(value_details['IgstVal'] - total_item_igst_value) <= 1)
calculated_invoice_value = \
value_details['AssVal'] + value_details['CgstVal'] \
+ value_details['SgstVal'] + value_details['IgstVal'] \
+ value_details['OthChrg'] - value_details['Discount']
self.assertTrue(abs(value_details['TotInvVal'] - calculated_invoice_value) <= 1)
self.assertTrue(einvoice['EwbDtls'])
def make_test_address_for_ewaybill():
if not frappe.db.exists('Address', '_Test Address for Eway bill-Billing'):
address = frappe.get_doc({
"address_line1": "_Test Address Line 1",
"address_title": "_Test Address for Eway bill",
"address_type": "Billing",
"city": "_Test City",
"state": "Test State",
"country": "India",
"doctype": "Address",
"is_primary_address": 1,
"phone": "+910000000000",
"gstin": "27AAECE4835E1ZR",
"gst_state": "Maharashtra",
"gst_state_number": "27",
"pincode": "401108"
}).insert()
address.append("links", {
"link_doctype": "Company",
"link_name": "_Test Company"
})
item.save()
address.save()
sales_invoice = create_sales_invoice(item = "_Test Item 2", do_not_save=1)
sales_invoice.items[0].item_tax_template = "_Test Item Tax Template 1"
self.assertRaises(frappe.ValidationError, sales_invoice.save)
if not frappe.db.exists('Address', '_Test Customer-Address for Eway bill-Shipping'):
address = frappe.get_doc({
"address_line1": "_Test Address Line 1",
"address_title": "_Test Customer-Address for Eway bill",
"address_type": "Shipping",
"city": "_Test City",
"state": "Test State",
"country": "India",
"doctype": "Address",
"is_primary_address": 1,
"phone": "+910000000000",
"gstin": "27AACCM7806M1Z3",
"gst_state": "Maharashtra",
"gst_state_number": "27",
"pincode": "410038"
}).insert()
item.taxes = []
item.save()
address.append("links", {
"link_doctype": "Customer",
"link_name": "_Test Customer"
})
address.save()
def make_test_transporter_for_ewaybill():
if not frappe.db.exists('Supplier', '_Test Transporter'):
frappe.get_doc({
"doctype": "Supplier",
"supplier_name": "_Test Transporter",
"country": "India",
"supplier_group": "_Test Supplier Group",
"supplier_type": "Company",
"is_transporter": 1
}).insert()
def make_sales_invoice_for_ewaybill():
make_test_address_for_ewaybill()
make_test_transporter_for_ewaybill()
gst_settings = frappe.get_doc("GST Settings")
gst_account = frappe.get_all(
"GST Account",
fields=["cgst_account", "sgst_account", "igst_account"],
filters = {"company": "_Test Company"}
)
if not gst_account:
gst_settings.append("gst_accounts", {
"company": "_Test Company",
"cgst_account": "CGST - _TC",
"sgst_account": "SGST - _TC",
"igst_account": "IGST - _TC",
})
gst_settings.save()
si = create_sales_invoice(do_not_save=1, rate='60000')
si.distance = 2000
si.company_address = "_Test Address for Eway bill-Billing"
si.customer_address = "_Test Customer-Address for Eway bill-Shipping"
si.vehicle_no = "KA12KA1234"
si.gst_category = "Registered Regular"
si.mode_of_transport = 'Road'
si.transporter = '_Test Transporter'
si.append("taxes", {
"charge_type": "On Net Total",
"account_head": "CGST - _TC",
"cost_center": "Main - _TC",
"description": "CGST @ 9.0",
"rate": 9
})
si.append("taxes", {
"charge_type": "On Net Total",
"account_head": "SGST - _TC",
"cost_center": "Main - _TC",
"description": "SGST @ 9.0",
"rate": 9
})
return si
def create_sales_invoice(**args):
si = frappe.new_doc("Sales Invoice")

View File

@@ -34,6 +34,9 @@ def valdiate_taxes_and_charges_template(doc):
validate_disabled(doc)
# Validate with existing taxes and charges template for unique tax category
validate_for_tax_category(doc)
for tax in doc.get("taxes"):
validate_taxes_and_charges(tax)
validate_inclusive_tax(tax, doc)
@@ -41,3 +44,7 @@ def valdiate_taxes_and_charges_template(doc):
def validate_disabled(doc):
if doc.is_default and doc.disabled:
frappe.throw(_("Disabled template must not be default template"))
def validate_for_tax_category(doc):
if frappe.db.exists(doc.doctype, {"company": doc.company, "tax_category": doc.tax_category, "disabled": 0}):
frappe.throw(_("A template with tax category {0} already exists. Only one template is allowed with each tax category").format(frappe.bold(doc.tax_category)))

View File

@@ -13,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",
@@ -183,8 +184,7 @@
"fieldname": "invoices",
"fieldtype": "Table",
"label": "Invoices",
"options": "Subscription Invoice",
"read_only": 1
"options": "Subscription Invoice"
},
{
"collapsible": 1,
@@ -195,9 +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"
}
],
"modified": "2020-08-27 23:30:02.504042",
"modified": "2020-11-29 22:46:14.879289",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Subscription",

View File

@@ -298,7 +298,8 @@ class Subscription(Document):
Returns the `Item`s linked to `Subscription Plan`
"""
if prorate:
prorate_factor = get_prorata_factor(self.current_invoice_end, self.current_invoice_start)
prorate_factor = get_prorata_factor(self.current_invoice_end, self.current_invoice_start,
self.generate_invoice_at_period_start)
items = []
customer = self.customer
@@ -333,7 +334,7 @@ class Subscription(Document):
if not self.generate_invoice_at_period_start:
return False
if self.is_new_subscription():
if self.is_new_subscription() and getdate(nowdate()) >= getdate(self.current_invoice_start):
return True
# Check invoice dates and make sure it doesn't have outstanding invoices
@@ -408,6 +409,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):
"""
@@ -459,11 +469,13 @@ class Subscription(Document):
if invoice:
return invoice.precision('grand_total')
def get_prorata_factor(period_end, period_start):
diff = flt(date_diff(nowdate(), period_start) + 1)
plan_days = flt(date_diff(period_end, period_start) + 1)
prorate_factor = diff / plan_days
def get_prorata_factor(period_end, period_start, is_prepaid):
if is_prepaid:
prorate_factor = 1
else:
diff = flt(date_diff(nowdate(), period_start) + 1)
plan_days = flt(date_diff(period_end, period_start) + 1)
prorate_factor = diff / plan_days
return prorate_factor

View File

@@ -209,7 +209,7 @@ 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
@@ -291,7 +291,8 @@ class TestSubscription(unittest.TestCase):
self.assertEqual(
flt(
get_prorata_factor(subscription.current_invoice_end, subscription.current_invoice_start),
get_prorata_factor(subscription.current_invoice_end, subscription.current_invoice_start,
subscription.generate_invoice_at_period_start),
2),
flt(prorate_factor, 2)
)
@@ -528,9 +529,7 @@ class TestSubscription(unittest.TestCase):
current_inv = subscription.get_current_invoice()
self.assertEqual(current_inv.status, "Unpaid")
diff = flt(date_diff(nowdate(), subscription.current_invoice_start) + 1)
plan_days = flt(date_diff(subscription.current_invoice_end, subscription.current_invoice_start) + 1)
prorate_factor = flt(diff / plan_days)
prorate_factor = 1
self.assertEqual(flt(current_inv.grand_total, 2), flt(prorate_factor * 900, 2))

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:

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();
@@ -2009,34 +2018,57 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
apply_pricing_rule: function () {
var me = this;
var remove_item = false;
$.each(this.frm.doc["items"], function (n, item) {
var pricing_rule = me.get_pricing_rule(item)
me.validate_pricing_rule(pricing_rule)
if (pricing_rule.length) {
item.pricing_rule = pricing_rule[0].name;
item.margin_type = pricing_rule[0].margin_type;
item.price_list_rate = pricing_rule[0].price || item.price_list_rate;
item.margin_rate_or_amount = pricing_rule[0].margin_rate_or_amount;
item.discount_percentage = pricing_rule[0].discount_percentage || 0.0;
me.apply_pricing_rule_on_item(item)
if (pricing_rule[0].price_or_product_discount == "Price") {
item.pricing_rule = pricing_rule[0].name;
item.margin_type = pricing_rule[0].margin_type;
item.price_list_rate = pricing_rule[0].price || item.price_list_rate;
item.margin_rate_or_amount = pricing_rule[0].margin_rate_or_amount;
item.discount_percentage = pricing_rule[0].discount_percentage || 0.0;
me.apply_pricing_rule_on_item(item)
} else {
me.child = frappe.model.add_child(me.frm.doc, me.frm.doc.doctype + " Item", "items");
me.child.item_code = pricing_rule[0].same_item ? item.item_code : pricing_rule[0].free_item;
me.child.item_name = pricing_rule[0].same_item ? item.item_name : pricing_rule[0].free_item;
me.child.stock_uom = pricing_rule[0].same_item ? item.stock_uom : pricing_rule[0].free_item_uom;
me.child.uom = pricing_rule[0].same_item ? item.uom : pricing_rule[0].free_item_uom;
me.child.conversion_factor = 1;
me.child.qty = pricing_rule.qty || 1;
me.child.is_free_item = 1;
me.child.brand = pricing_rule[0].same_item ? item.brand : "";
me.child.description = pricing_rule[0].same_item ? item.description : pricing_rule[0].free_item;
}
} else if (item.pricing_rule) {
item.price_list_rate = me.price_list_data[item.item_code]
item.margin_rate_or_amount = 0.0;
item.discount_percentage = 0.0;
item.pricing_rule = null;
me.apply_pricing_rule_on_item(item)
} else if (item.is_free_item) {
remove_item = true;
item.qty = 0
}
if(item.discount_percentage > 0) {
me.apply_pricing_rule_on_item(item)
}
})
});
if (remove_item) {
this.remove_zero_qty_items_from_cart();
}
},
get_pricing_rule: function (item) {
var me = this;
return $.grep(this.pricing_rules, function (data) {
if (item.qty >= data.min_qty && (item.qty <= (data.max_qty ? data.max_qty : item.qty))) {
me.get_mixed_min_max_qty_and_amt(data, item);
if (data.mixed_qty >= data.min_qty && (data.mixed_qty <= (data.max_qty ? data.max_qty : data.mixed_qty))) {
if (me.validate_item_condition(data, item)) {
if (in_list(['Customer', 'Customer Group', 'Territory', 'Campaign'], data.applicable_for)) {
return me.validate_condition(data)
@@ -2048,11 +2080,26 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
})
},
get_mixed_min_max_qty_and_amt: function(data, item) {
var apply_on = frappe.model.scrub(data.apply_on);
data.mixed_qty = 0.0
if (data.mixed_conditions && in_list(data[apply_on], item[apply_on])) {
this.frm.doc.items.forEach(d => {
if (in_list(data[apply_on], d[apply_on])) {
data.mixed_qty += d.qty;
data.mixed_amt += d.amount;
}
});
} else {
data.mixed_qty = item.qty;
data.mixed_amt = item.amount;
}
},
validate_item_condition: function (data, item) {
var apply_on = frappe.model.scrub(data.apply_on);
return (data.apply_on == 'Item Group')
? this.validate_item_group(data.item_group, item.item_group) : (data[apply_on] == item[apply_on]);
return in_list(data[apply_on], item[apply_on]);
},
validate_item_group: function (pr_item_group, cart_item_group) {

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")
@@ -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

@@ -0,0 +1,166 @@
{%- from "templates/print_formats/standard_macros.html" import add_header, render_field, print_value -%}
{%- set einvoice = json.loads(doc.signed_einvoice) -%}
<div class="page-break">
<div {% if print_settings.repeat_header_footer %} id="header-html" class="hidden-pdf" {% endif %}>
{% if letter_head and not no_letterhead %}
<div class="letter-head">{{ letter_head }}</div>
{% endif %}
<div class="print-heading">
<h2>E Invoice<br><small>{{ doc.name }}</small></h2>
</div>
</div>
{% if print_settings.repeat_header_footer %}
<div id="footer-html" class="visible-pdf">
{% if not no_letterhead and footer %}
<div class="letter-head-footer">
{{ footer }}
</div>
{% endif %}
<p class="text-center small page-number visible-pdf">
{{ _("Page {0} of {1}").format('<span class="page"></span>', '<span class="topage"></span>') }}
</p>
</div>
{% endif %}
<div class="row section-break" style="border-bottom: 1px solid #d1d8dd; padding-bottom: 10px;">
<h5 class="font-bold" style="margin-left: 15px; margin-top: 0px;">1. Transaction Details</h5>
<div class="col-xs-7 column-break">
<div class="row data-field">
<div class="col-xs-4"><label>IRN</label></div>
<div class="col-xs-8 value">{{ einvoice.Irn }}</div>
</div>
<div class="row data-field">
<div class="col-xs-4"><label>Ack. No</label></div>
<div class="col-xs-8 value">{{ einvoice.AckNo }}</div>
</div>
<div class="row data-field">
<div class="col-xs-4"><label>Ack. Date</label></div>
<div class="col-xs-8 value">{{ frappe.utils.format_datetime(einvoice.AckDt, "dd/MM/yyyy hh:mm:ss") }}</div>
</div>
<div class="row data-field">
<div class="col-xs-4"><label>Category</label></div>
<div class="col-xs-8 value">{{ einvoice.TranDtls.SupTyp }}</div>
</div>
<div class="row data-field">
<div class="col-xs-4"><label>Document Type</label></div>
<div class="col-xs-8 value">{{ einvoice.DocDtls.Typ }}</div>
</div>
<div class="row data-field">
<div class="col-xs-4"><label>Document No</label></div>
<div class="col-xs-8 value">{{ einvoice.DocDtls.No }}</div>
</div>
</div>
<div class="col-xs-5 column-break">
<img src="{{ doc.qrcode_image }}" alt="QRCode Image" style="
width: 175px; height: 175px;
float: right; border: 1px solid gray;
display: flex; align-items: center; justify-content: center;
">
</div>
</div>
<div class="row section-break" style="border-bottom: 1px solid #d1d8dd; padding-bottom: 10px;">
<h5 class="font-bold" style="margin-left: 15px; margin-bottom: 0px;">2. Party Details</h5>
{%- set seller = einvoice.SellerDtls -%}
<div class="col-xs-6 column-break">
<h5 style="margin-bottom: 5px;">Seller</h5>
<p>{{ seller.Gstin }}</p>
<p>{{ seller.LglNm }}</p>
<p>{{ seller.Addr1 }}</p>
{%- if seller.Addr2 -%} <p>{{ seller.Addr2 }}</p> {% endif %}
<p>{{ seller.Loc }}</p>
<p>{{ frappe.db.get_value("Address", doc.company_address, "gst_state") }} - {{ seller.Pin }}</p>
{%- if einvoice.ShipDtls -%}
{%- set shipping = einvoice.ShipDtls -%}
<h5 style="margin-bottom: 5px;">Shipping</h5>
<p>{{ shipping.Gstin }}</p>
<p>{{ shipping.LglNm }}</p>
<p>{{ shipping.Addr1 }}</p>
{%- if shipping.Addr2 -%} <p>{{ shipping.Addr2 }}</p> {% endif %}
<p>{{ shipping.Loc }}</p>
<p>{{ frappe.db.get_value("Address", doc.shipping_address_name, "gst_state") }} - {{ shipping.Pin }}</p>
{% endif %}
</div>
{%- set buyer = einvoice.BuyerDtls -%}
<div class="col-xs-6 column-break">
<h5 style="margin-bottom: 5px;">Buyer</h5>
<p>{{ buyer.Gstin }}</p>
<p>{{ buyer.LglNm }}</p>
<p>{{ buyer.Addr1 }}</p>
{%- if buyer.Addr2 -%} <p>{{ buyer.Addr2 }}</p> {% endif %}
<p>{{ buyer.Loc }}</p>
<p>{{ frappe.db.get_value("Address", doc.customer_address, "gst_state") }} - {{ buyer.Pin }}</p>
</div>
</div>
<div style="overflow-x: auto;">
<h5 class="font-bold" style="margin-bottom: 0px;">3. Item Details</h5>
<table class="table table-bordered">
<thead>
<tr>
<th class="text-left" style="width: 3%;">Sr. No.</th>
<th class="text-left">Item</th>
<th class="text-left" style="width: 10%;">HSN Code</th>
<th class="text-left" style="width: 5%;">Qty</th>
<th class="text-left" style="width: 5%;">UOM</th>
<th class="text-left">Rate</th>
<th class="text-left" style="width: 5%;">Discount</th>
<th class="text-left">Taxable Amount</th>
<th class="text-left" style="width: 7%;">Tax Rate</th>
<th class="text-left" style="width: 5%;">Other Charges</th>
<th class="text-left">Total</th>
</tr>
</thead>
<tbody>
{% for item in einvoice.ItemList %}
<tr>
<td class="text-left" style="width: 3%;">{{ item.SlNo }}</td>
<td class="text-left">{{ item.PrdDesc }}</td>
<td class="text-left" style="width: 10%;">{{ item.HsnCd }}</td>
<td class="text-right" style="width: 5%;">{{ item.Qty }}</td>
<td class="text-left" style="width: 5%;">{{ item.Unit }}</td>
<td class="text-right">{{ frappe.utils.fmt_money(item.UnitPrice, None, "INR") }}</td>
<td class="text-right" style="width: 5%;">{{ frappe.utils.fmt_money(item.Discount, None, "INR") }}</td>
<td class="text-right">{{ frappe.utils.fmt_money(item.AssAmt, None, "INR") }}</td>
<td class="text-right" style="width: 7%;">{{ item.GstRt + item.CesRt }} %</td>
<td class="text-right" style="width: 5%;">{{ frappe.utils.fmt_money(0, None, "INR") }}</td>
<td class="text-right">{{ frappe.utils.fmt_money(item.TotItemVal, None, "INR") }}</td>
</tr>
{% endfor %}
</tbody>
</table>
</div>
<div style="overflow-x: auto;">
<h5 class="font-bold" style="margin-bottom: 0px;">4. Value Details</h5>
<table class="table table-bordered">
<thead>
<tr>
<th class="text-left">Taxable Amount</th>
<th class="text-left">CGST</th>
<th class="text-left"">SGST</th>
<th class="text-left">IGST</th>
<th class="text-left">CESS</th>
<th class="text-left" style="width: 10%;">State CESS</th>
<th class="text-left">Discount</th>
<th class="text-left" style="width: 10%;">Other Charges</th>
<th class="text-left" style="width: 10%;">Round Off</th>
<th class="text-left">Total Value</th>
</tr>
</thead>
<tbody>
{%- set value_details = einvoice.ValDtls -%}
<tr>
<td class="text-right">{{ frappe.utils.fmt_money(value_details.AssVal, None, "INR") }}</td>
<td class="text-right">{{ frappe.utils.fmt_money(value_details.CgstVal, None, "INR") }}</td>
<td class="text-right">{{ frappe.utils.fmt_money(value_details.SgstVal, None, "INR") }}</td>
<td class="text-right">{{ frappe.utils.fmt_money(value_details.IgstVal, None, "INR") }}</td>
<td class="text-right">{{ frappe.utils.fmt_money(value_details.CesVal, None, "INR") }}</td>
<td class="text-right">{{ frappe.utils.fmt_money(0, None, "INR") }}</td>
<td class="text-right">{{ frappe.utils.fmt_money(value_details.Discount, None, "INR") }}</td>
<td class="text-right">{{ frappe.utils.fmt_money(value_details.OthChrg, None, "INR") }}</td>
<td class="text-right">{{ frappe.utils.fmt_money(value_details.RndOffAmt, None, "INR") }}</td>
<td class="text-right">{{ frappe.utils.fmt_money(value_details.TotInvVal, None, "INR") }}</td>
</tr>
</tbody>
</table>
</div>
</div>

View File

@@ -0,0 +1,24 @@
{
"align_labels_right": 1,
"creation": "2020-10-10 18:01:21.032914",
"custom_format": 0,
"default_print_language": "en-US",
"disabled": 1,
"doc_type": "Sales Invoice",
"docstatus": 0,
"doctype": "Print Format",
"font": "Default",
"html": "",
"idx": 0,
"line_breaks": 1,
"modified": "2020-10-23 19:54:40.634936",
"modified_by": "Administrator",
"module": "Accounts",
"name": "GST E-Invoice",
"owner": "Administrator",
"print_format_builder": 0,
"print_format_type": "Jinja",
"raw_printing": 0,
"show_section_headings": 1,
"standard": "Yes"
}

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

@@ -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`
@@ -741,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

@@ -15,15 +15,51 @@ def execute(filters=None):
return columns, data
def get_columns():
return [
_("Payment Document") + "::130",
_("Payment Entry") + ":Dynamic Link/"+_("Payment Document")+":110",
_("Posting Date") + ":Date:100",
_("Cheque/Reference No") + "::120",
_("Clearance Date") + ":Date:100",
_("Against Account") + ":Link/Account:170",
_("Amount") + ":Currency:120"
]
columns = [{
"label": _("Payment Document Type"),
"fieldname": "payment_document_type",
"fieldtype": "Link",
"options": "Doctype",
"width": 130
},
{
"label": _("Payment Entry"),
"fieldname": "payment_entry",
"fieldtype": "Dynamic Link",
"options": "payment_document_type",
"width": 140
},
{
"label": _("Posting Date"),
"fieldname": "posting_date",
"fieldtype": "Date",
"width": 100
},
{
"label": _("Cheque/Reference No"),
"fieldname": "cheque_no",
"width": 120
},
{
"label": _("Clearance Date"),
"fieldname": "clearance_date",
"fieldtype": "Date",
"width": 100
},
{
"label": _("Against Account"),
"fieldname": "against",
"fieldtype": "Link",
"options": "Account",
"width": 170
},
{
"label": _("Amount"),
"fieldname": "amount",
"width": 120
}]
return columns
def get_conditions(filters):
conditions = ""

View File

@@ -206,7 +206,7 @@ def get_data(companies, root_type, balance_must_be, fiscal_year, filters=None, i
set_gl_entries_by_account(fiscal_year.year_start_date,
fiscal_year.year_end_date, root.lft, root.rgt, filters,
gl_entries_by_account, accounts_by_name, ignore_closing_entries=False)
gl_entries_by_account, accounts_by_name, accounts, ignore_closing_entries=False)
calculate_values(accounts_by_name, gl_entries_by_account, companies, fiscal_year, filters)
accumulate_values_into_parents(accounts, accounts_by_name, companies)
@@ -325,7 +325,7 @@ def prepare_data(accounts, fiscal_year, balance_must_be, companies, company_curr
return data
def set_gl_entries_by_account(from_date, to_date, root_lft, root_rgt, filters, gl_entries_by_account,
accounts_by_name, ignore_closing_entries=False):
accounts_by_name, accounts, ignore_closing_entries=False):
"""Returns a dict like { "account": [gl entries], ... }"""
company_lft, company_rgt = frappe.get_cached_value('Company',
@@ -368,15 +368,31 @@ def set_gl_entries_by_account(from_date, to_date, root_lft, root_rgt, filters, g
for entry in gl_entries:
key = entry.account_number or entry.account_name
validate_entries(key, entry, accounts_by_name)
validate_entries(key, entry, accounts_by_name, accounts)
gl_entries_by_account.setdefault(key, []).append(entry)
return gl_entries_by_account
def validate_entries(key, entry, accounts_by_name):
def get_account_details(account):
return frappe.get_cached_value('Account', account, ['name', 'report_type', 'root_type', 'company',
'is_group', 'account_name', 'account_number', 'parent_account', 'lft', 'rgt'], as_dict=1)
def validate_entries(key, entry, accounts_by_name, accounts):
if key not in accounts_by_name:
field = "Account number" if entry.account_number else "Account name"
frappe.throw(_("{0} {1} is not present in the parent company").format(field, key))
args = get_account_details(entry.account)
if args.parent_account:
parent_args = get_account_details(args.parent_account)
args.update({
'lft': parent_args.lft + 1,
'rgt': parent_args.rgt - 1,
'root_type': parent_args.root_type,
'report_type': parent_args.report_type
})
accounts_by_name.setdefault(key, args)
accounts.append(args)
def get_additional_conditions(from_date, ignore_closing_entries, filters):
additional_conditions = []

View File

@@ -294,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

@@ -8,6 +8,7 @@ from frappe.utils import flt
from erpnext.accounts.report.item_wise_sales_register.item_wise_sales_register import (get_tax_accounts,
get_grand_total, add_total_row, get_display_value, get_group_by_and_display_fields, add_sub_total_row,
get_group_by_conditions)
from erpnext.selling.report.item_wise_sales_history.item_wise_sales_history import get_item_details
def execute(filters=None):
return _execute(filters)
@@ -23,7 +24,7 @@ def _execute(filters=None, additional_table_columns=None, additional_query_colum
aii_account_map = get_aii_accounts()
if item_list:
itemised_tax, tax_columns = get_tax_accounts(item_list, columns, company_currency,
doctype="Purchase Invoice", tax_doctype="Purchase Taxes and Charges")
doctype='Purchase Invoice', tax_doctype='Purchase Taxes and Charges')
po_pr_map = get_purchase_receipts_against_purchase_order(item_list)
@@ -35,10 +36,14 @@ def _execute(filters=None, additional_table_columns=None, additional_query_colum
if filters.get('group_by'):
grand_total = get_grand_total(filters, 'Purchase Invoice')
item_details = get_item_details()
for d in item_list:
if not d.stock_qty:
continue
item_record = item_details.get(d.item_code)
purchase_receipt = None
if d.purchase_receipt:
purchase_receipt = d.purchase_receipt
@@ -49,8 +54,8 @@ def _execute(filters=None, additional_table_columns=None, additional_query_colum
row = {
'item_code': d.item_code,
'item_name': d.item_name,
'item_group': d.item_group,
'item_name': item_record.item_name if item_record else d.item_name,
'item_group': item_record.item_group if item_record else d.item_group,
'description': d.description,
'invoice': d.parent,
'posting_date': d.posting_date,
@@ -82,10 +87,10 @@ def _execute(filters=None, additional_table_columns=None, additional_query_colum
for tax in tax_columns:
item_tax = itemised_tax.get(d.name, {}).get(tax, {})
row.update({
frappe.scrub(tax + ' Rate'): item_tax.get("tax_rate", 0),
frappe.scrub(tax + ' Amount'): item_tax.get("tax_amount", 0),
frappe.scrub(tax + ' Rate'): item_tax.get('tax_rate', 0),
frappe.scrub(tax + ' Amount'): item_tax.get('tax_amount', 0),
})
total_tax += flt(item_tax.get("tax_amount"))
total_tax += flt(item_tax.get('tax_amount'))
row.update({
'total_tax': total_tax,
@@ -317,8 +322,9 @@ def get_items(filters, additional_query_columns):
select
`tabPurchase Invoice Item`.`name`, `tabPurchase Invoice Item`.`parent`,
`tabPurchase Invoice`.posting_date, `tabPurchase Invoice`.credit_to, `tabPurchase Invoice`.company,
`tabPurchase Invoice`.supplier, `tabPurchase Invoice`.remarks, `tabPurchase Invoice`.base_net_total, `tabPurchase Invoice Item`.`item_code`,
`tabPurchase Invoice Item`.`item_name`, `tabPurchase Invoice Item`.`item_group`, `tabPurchase Invoice Item`.description,
`tabPurchase Invoice`.supplier, `tabPurchase Invoice`.remarks, `tabPurchase Invoice`.base_net_total,
`tabPurchase Invoice Item`.`item_code`, `tabPurchase Invoice Item`.description,
`tabPurchase Invoice Item`.`item_name`, `tabPurchase Invoice Item`.`item_group`,
`tabPurchase Invoice Item`.`project`, `tabPurchase Invoice Item`.`purchase_order`,
`tabPurchase Invoice Item`.`purchase_receipt`, `tabPurchase Invoice Item`.`po_detail`,
`tabPurchase Invoice Item`.`expense_account`, `tabPurchase Invoice Item`.`stock_qty`,

View File

@@ -8,6 +8,7 @@ from frappe.utils import flt, cstr
from frappe.model.meta import get_field_precision
from frappe.utils.xlsxutils import handle_html
from erpnext.accounts.report.sales_register.sales_register import get_mode_of_payments
from erpnext.selling.report.item_wise_sales_history.item_wise_sales_history import get_item_details, get_customer_details
def execute(filters=None):
return _execute(filters)
@@ -17,7 +18,7 @@ def _execute(filters=None, additional_table_columns=None, additional_query_colum
filters.update({"from_date": filters.get("date_range") and filters.get("date_range")[0], "to_date": filters.get("date_range") and filters.get("date_range")[1]})
columns = get_columns(additional_table_columns, filters)
company_currency = frappe.get_cached_value('Company', filters.get("company"), "default_currency")
company_currency = frappe.get_cached_value('Company', filters.get('company'), 'default_currency')
item_list = get_items(filters, additional_query_columns)
if item_list:
@@ -34,7 +35,13 @@ def _execute(filters=None, additional_table_columns=None, additional_query_colum
if filters.get('group_by'):
grand_total = get_grand_total(filters, 'Sales Invoice')
customer_details = get_customer_details()
item_details = get_item_details()
for d in item_list:
customer_record = customer_details.get(d.customer)
item_record = item_details.get(d.item_code)
delivery_note = None
if d.delivery_note:
delivery_note = d.delivery_note
@@ -46,14 +53,14 @@ def _execute(filters=None, additional_table_columns=None, additional_query_colum
row = {
'item_code': d.item_code,
'item_name': d.item_name,
'item_group': d.item_group,
'item_name': item_record.item_name if item_record else d.item_name,
'item_group': item_record.item_group if item_record else d.item_group,
'description': d.description,
'invoice': d.parent,
'posting_date': d.posting_date,
'customer': d.customer,
'customer_name': d.customer_name,
'customer_group': d.customer_group,
'customer_name': customer_record.customer_name,
'customer_group': customer_record.customer_group,
}
if additional_query_columns:
@@ -91,10 +98,10 @@ def _execute(filters=None, additional_table_columns=None, additional_query_colum
for tax in tax_columns:
item_tax = itemised_tax.get(d.name, {}).get(tax, {})
row.update({
frappe.scrub(tax + ' Rate'): item_tax.get("tax_rate", 0),
frappe.scrub(tax + ' Amount'): item_tax.get("tax_amount", 0),
frappe.scrub(tax + ' Rate'): item_tax.get('tax_rate', 0),
frappe.scrub(tax + ' Amount'): item_tax.get('tax_amount', 0),
})
total_tax += flt(item_tax.get("tax_amount"))
total_tax += flt(item_tax.get('tax_amount'))
row.update({
'total_tax': total_tax,
@@ -227,7 +234,7 @@ def get_columns(additional_table_columns, filters):
if filters.get('group_by') != 'Terriotory':
columns.extend([
{
'label': _("Territory"),
'label': _('Territory'),
'fieldname': 'territory',
'fieldtype': 'Link',
'options': 'Territory',
@@ -382,13 +389,13 @@ def get_items(filters, additional_query_columns):
`tabSales Invoice`.posting_date, `tabSales Invoice`.debit_to,
`tabSales Invoice`.project, `tabSales Invoice`.customer, `tabSales Invoice`.remarks,
`tabSales Invoice`.territory, `tabSales Invoice`.company, `tabSales Invoice`.base_net_total,
`tabSales Invoice Item`.item_code, `tabSales Invoice Item`.item_name,
`tabSales Invoice Item`.item_group, `tabSales Invoice Item`.description, `tabSales Invoice Item`.sales_order,
`tabSales Invoice Item`.delivery_note, `tabSales Invoice Item`.income_account,
`tabSales Invoice Item`.cost_center, `tabSales Invoice Item`.stock_qty,
`tabSales Invoice Item`.stock_uom, `tabSales Invoice Item`.base_net_rate,
`tabSales Invoice Item`.base_net_amount, `tabSales Invoice`.customer_name,
`tabSales Invoice`.customer_group, `tabSales Invoice Item`.so_detail,
`tabSales Invoice Item`.item_code, `tabSales Invoice Item`.description,
`tabSales Invoice Item`.`item_name`, `tabSales Invoice Item`.`item_group`,
`tabSales Invoice Item`.sales_order, `tabSales Invoice Item`.delivery_note,
`tabSales Invoice Item`.income_account, `tabSales Invoice Item`.cost_center,
`tabSales Invoice Item`.stock_qty, `tabSales Invoice Item`.stock_uom,
`tabSales Invoice Item`.base_net_rate, `tabSales Invoice Item`.base_net_amount,
`tabSales Invoice`.customer_name, `tabSales Invoice`.customer_group, `tabSales Invoice Item`.so_detail,
`tabSales Invoice`.update_stock, `tabSales Invoice Item`.uom, `tabSales Invoice Item`.qty {0}
from `tabSales Invoice`, `tabSales Invoice Item`
where `tabSales Invoice`.name = `tabSales Invoice Item`.parent
@@ -425,14 +432,14 @@ def get_deducted_taxes():
return frappe.db.sql_list("select name from `tabPurchase Taxes and Charges` where add_deduct_tax = 'Deduct'")
def get_tax_accounts(item_list, columns, company_currency,
doctype="Sales Invoice", tax_doctype="Sales Taxes and Charges"):
doctype='Sales Invoice', tax_doctype='Sales Taxes and Charges'):
import json
item_row_map = {}
tax_columns = []
invoice_item_row = {}
itemised_tax = {}
tax_amount_precision = get_field_precision(frappe.get_meta(tax_doctype).get_field("tax_amount"),
tax_amount_precision = get_field_precision(frappe.get_meta(tax_doctype).get_field('tax_amount'),
currency=company_currency) or 2
for d in item_list:
@@ -477,8 +484,8 @@ def get_tax_accounts(item_list, columns, company_currency,
tax_rate = tax_data
tax_amount = 0
if charge_type == "Actual" and not tax_rate:
tax_rate = "NA"
if charge_type == 'Actual' and not tax_rate:
tax_rate = 'NA'
item_net_amount = sum([flt(d.base_net_amount)
for d in item_row_map.get(parent, {}).get(item_code, [])])
@@ -492,17 +499,17 @@ def get_tax_accounts(item_list, columns, company_currency,
if (doctype == 'Purchase Invoice' and name in deducted_tax) else tax_value)
itemised_tax.setdefault(d.name, {})[description] = frappe._dict({
"tax_rate": tax_rate,
"tax_amount": tax_value
'tax_rate': tax_rate,
'tax_amount': tax_value
})
except ValueError:
continue
elif charge_type == "Actual" and tax_amount:
elif charge_type == 'Actual' and tax_amount:
for d in invoice_item_row.get(parent, []):
itemised_tax.setdefault(d.name, {})[description] = frappe._dict({
"tax_rate": "NA",
"tax_amount": flt((tax_amount * d.base_net_amount) / d.base_net_total,
'tax_rate': 'NA',
'tax_amount': flt((tax_amount * d.base_net_amount) / d.base_net_total,
tax_amount_precision)
})
@@ -564,7 +571,7 @@ def add_total_row(data, filters, prev_group_by_value, item, total_row_map,
})
total_row_map.setdefault('total_row', {
subtotal_display_field: "Total",
subtotal_display_field: 'Total',
'stock_qty': 0.0,
'amount': 0.0,
'bold': 1,

View File

@@ -59,23 +59,111 @@ def validate_filters(filters):
def get_columns(filters):
return [
_("Payment Document") + ":: 100",
_("Payment Entry") + ":Dynamic Link/"+_("Payment Document")+":140",
_("Party Type") + "::100",
_("Party") + ":Dynamic Link/Party Type:140",
_("Posting Date") + ":Date:100",
_("Invoice") + (":Link/Purchase Invoice:130" if filters.get("payment_type") == _("Outgoing") else ":Link/Sales Invoice:130"),
_("Invoice Posting Date") + ":Date:130",
_("Payment Due Date") + ":Date:130",
_("Debit") + ":Currency:120",
_("Credit") + ":Currency:120",
_("Remarks") + "::150",
_("Age") +":Int:40",
"0-30:Currency:100",
"30-60:Currency:100",
"60-90:Currency:100",
_("90-Above") + ":Currency:100",
_("Delay in payment (Days)") + "::150"
{
"fieldname": "payment_document",
"label": _("Payment Document Type"),
"fieldtype": "Data",
"width": 100
},
{
"fieldname": "payment_entry",
"label": _("Payment Document"),
"fieldtype": "Dynamic Link",
"options": "payment_document",
"width": 160
},
{
"fieldname": "party_type",
"label": _("Party Type"),
"fieldtype": "Data",
"width": 100
},
{
"fieldname": "party",
"label": _("Party"),
"fieldtype": "Dynamic Link",
"options": "party_type",
"width": 160
},
{
"fieldname": "posting_date",
"label": _("Posting Date"),
"fieldtype": "Date",
"width": 100
},
{
"fieldname": "invoice",
"label": _("Invoice"),
"fieldtype": "Link",
"options": "Purchase Invoice" if filters.get("payment_type") == _("Outgoing") else "Sales Invoice",
"width": 160
},
{
"fieldname": "invoice_posting_date",
"label": _("Invoice Posting Date"),
"fieldtype": "Date",
"width": 100
},
{
"fieldname": "due_date",
"label": _("Payment Due Date"),
"fieldtype": "Date",
"width": 100
},
{
"fieldname": "debit",
"label": _("Debit"),
"fieldtype": "Currency",
"width": 140
},
{
"fieldname": "credit",
"label": _("Credit"),
"fieldtype": "Currency",
"width": 140
},
{
"fieldname": "remarks",
"label": _("Remarks"),
"fieldtype": "Data",
"width": 200
},
{
"fieldname": "age",
"label": _("Age"),
"fieldtype": "Int",
"width": 50
},
{
"fieldname": "range1",
"label": _("0-30"),
"fieldtype": "Currency",
"width": 140
},
{
"fieldname": "range2",
"label": _("30-60"),
"fieldtype": "Currency",
"width": 140
},
{
"fieldname": "range3",
"label": _("60-90"),
"fieldtype": "Currency",
"width": 140
},
{
"fieldname": "range4",
"label": _("90 Above"),
"fieldtype": "Currency",
"width": 140
},
{
"fieldname": "delay_in_payment",
"label": _("Delay in payment (Days)"),
"fieldtype": "Int",
"width": 100
}
]
def get_conditions(filters):

View File

@@ -75,7 +75,10 @@ def get_fiscal_years(transaction_date=None, fiscal_year=None, label="Date", verb
else:
return ((fy.name, fy.year_start_date, fy.year_end_date),)
error_msg = _("""{0} {1} not in any active Fiscal Year.""").format(label, formatdate(transaction_date))
error_msg = _("""{0} {1} is not in any active Fiscal Year""").format(label, formatdate(transaction_date))
if company:
error_msg = _("""{0} for {1}""").format(error_msg, frappe.bold(company))
if verbose==1: frappe.msgprint(error_msg)
raise FiscalYearError(error_msg)

View File

@@ -136,6 +136,8 @@ frappe.ui.form.on('Asset', {
if (frm.doc.docstatus == 0) {
frm.toggle_reqd("finance_books", frm.doc.calculate_depreciation);
frm.set_df_property('depreciation_start_date', 'reqd', 1, frm.doc.name, 'finance_books');
frm.refresh_field('finance_books');
}
},
@@ -232,7 +234,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');
}
},
@@ -323,6 +325,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) {

View File

@@ -50,6 +50,5 @@ frappe.ui.form.on('Asset Category', {
}
};
});
}
});

View File

@@ -1,5 +1,4 @@
{
"actions": [],
"creation": "2018-05-08 14:44:37.095570",
"doctype": "DocType",
"editable_grid": 1,
@@ -54,8 +53,7 @@
"fieldname": "depreciation_start_date",
"fieldtype": "Date",
"in_list_view": 1,
"label": "Depreciation Posting Date",
"reqd": 1
"label": "Depreciation Posting Date"
},
{
"default": "0",
@@ -83,10 +81,8 @@
"label": "Rate of Depreciation"
}
],
"index_web_pages_for_search": 1,
"istable": 1,
"links": [],
"modified": "2020-09-16 12:11:30.631788",
"modified": "2020-12-30 15:43:03.188256",
"modified_by": "Administrator",
"module": "Assets",
"name": "Asset Finance Book",

View File

@@ -108,7 +108,7 @@ def update_maintenance_log(asset_maintenance, item_code, item_name, task):
@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

@@ -12,8 +12,8 @@ from frappe.model.document import Document
class AssetValueAdjustment(Document):
def validate(self):
self.validate_date()
self.set_difference_amount()
self.set_current_asset_value()
self.set_difference_amount()
def on_submit(self):
self.make_depreciation_entry()

View File

@@ -141,31 +141,30 @@ def get_data(filters):
assets_record = frappe.db.get_all("Asset",
filters=conditions,
fields=["name", "asset_name", "department", "cost_center", "purchase_receipt",
fields=["name as asset_id", "asset_name", "department", "cost_center", "purchase_receipt",
"asset_category", "purchase_date", "gross_purchase_amount", "location",
"available_for_use_date", "status", "purchase_invoice", "opening_accumulated_depreciation"])
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

@@ -1056,7 +1056,7 @@
"idx": 105,
"is_submittable": 1,
"links": [],
"modified": "2020-09-14 14:36:12.418690",
"modified": "2021-01-22 20:27:11.418690",
"modified_by": "Administrator",
"module": "Buying",
"name": "Purchase Order",

View File

@@ -89,7 +89,7 @@ class TestPurchaseOrder(unittest.TestCase):
frappe.db.set_value("Accounts Settings", None, "over_billing_allowance", 0)
def test_update_child_qty_rate(self):
def test_update_child(self):
mr = make_material_request(qty=10)
po = make_purchase_order(mr.name)
po.supplier = "_Test Supplier"
@@ -119,7 +119,7 @@ class TestPurchaseOrder(unittest.TestCase):
self.assertEqual(get_ordered_qty(), existing_ordered_qty + 3)
def test_add_new_item_in_update_child_qty_rate(self):
def test_update_child_adding_new_item(self):
po = create_purchase_order(do_not_save=1)
po.items[0].qty = 4
po.save()
@@ -145,7 +145,7 @@ class TestPurchaseOrder(unittest.TestCase):
self.assertEqual(po.status, 'To Receive and Bill')
def test_remove_item_in_update_child_qty_rate(self):
def test_update_child_removing_item(self):
po = create_purchase_order(do_not_save=1)
po.items[0].qty = 4
po.save()
@@ -185,7 +185,7 @@ class TestPurchaseOrder(unittest.TestCase):
self.assertEquals(len(po.get('items')), 1)
self.assertEqual(po.status, 'To Receive and Bill')
def test_update_child_qty_rate_perm(self):
def test_update_child_perm(self):
po = create_purchase_order(item_code= "_Test Item", qty=4)
user = 'test@example.com'
@@ -855,7 +855,7 @@ class TestPurchaseOrder(unittest.TestCase):
},
{
"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[1].name
"qty":250,"warehouse":"_Test Warehouse - _TC", "stock_uom":"Nos"
},
]
@@ -864,6 +864,10 @@ class TestPurchaseOrder(unittest.TestCase):
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

View File

@@ -108,6 +108,10 @@ class RequestforQuotation(BuyingController):
'link_doctype': 'Supplier',
'link_name': rfq_supplier.supplier
})
contact.append('email_ids', {
'email_id': user.name,
'is_primary': 1
})
if not contact.email_id and not contact.user:
contact.email_id = user.name

View File

@@ -1,5 +1,4 @@
{
"actions": [],
"autoname": "hash",
"creation": "2013-05-22 12:43:10",
"doctype": "DocType",
@@ -237,7 +236,7 @@
"fieldname": "rate",
"fieldtype": "Currency",
"in_list_view": 1,
"label": "Rate ",
"label": "Rate",
"oldfieldname": "import_rate",
"oldfieldtype": "Currency",
"options": "currency"
@@ -531,9 +530,9 @@
}
],
"idx": 1,
"index_web_pages_for_search": 1,
"istable": 1,
"links": [],
"modified": "2020-04-07 18:35:51.175947",
"modified": "2020-10-19 17:16:06.731729",
"modified_by": "Administrator",
"module": "Buying",
"name": "Supplier Quotation Item",

View File

@@ -35,9 +35,7 @@ def update_last_purchase_rate(doc, is_submit):
frappe.throw(_("UOM Conversion factor is required in row {0}").format(d.idx))
# update last purchsae rate
if last_purchase_rate:
frappe.db.sql("""update `tabItem` set last_purchase_rate = %s where name = %s""",
(flt(last_purchase_rate), d.item_code))
frappe.db.set_value('Item', d.item_code, 'last_purchase_rate', flt(last_purchase_rate))
def validate_for_items(doc):
items = []

View File

@@ -0,0 +1,36 @@
## ERPNext v12.14.0 Release Note
### Fixes and Enhancements
- Incorrect backflush qty in manufacture entry ([#23878](https://github.com/frappe/erpnext/pull/23878))
- Fuel expense amount of vehicle log ([#23634](https://github.com/frappe/erpnext/pull/23634))
- Extra material received against send to warehouse entry ([#23645](https://github.com/frappe/erpnext/pull/23645))
- Show accounts in financial statements upto level 20 ([#23719](https://github.com/frappe/erpnext/pull/23719))
- Remove Production Order reference from Item Validation ([#23733](https://github.com/frappe/erpnext/pull/23733))
- Place of Supply fix in Sales Invoices ([#23786](https://github.com/frappe/erpnext/pull/23786))
- Filter Leave Type based on allocation for a particular employee ([#22050](https://github.com/frappe/erpnext/pull/22050))
- Incorrect assign to in Maintenance Schedule ([#23830](https://github.com/frappe/erpnext/pull/23830))
- Manually set serial nos override with current available serial nos ([#23651](https://github.com/frappe/erpnext/pull/23651))
- SO to PO flow improvement ([#23357](https://github.com/frappe/erpnext/pull/23357))
- Payment Terms not fetched in Purchase Invoice from Purchase Receipt ([#23866](https://github.com/frappe/erpnext/pull/23866))
- Re-linking bank accounts with plaid ([#23913](https://github.com/frappe/erpnext/pull/23913))
- Incorrect outstanding amount for multicurrency with Reverse Charge ([#23863](https://github.com/frappe/erpnext/pull/23863))
- Overproduction, not allowed to transfer extra materials ([#23647](https://github.com/frappe/erpnext/pull/23647))
- Consider rounded_total in returns ([#23631](https://github.com/frappe/erpnext/pull/23631))
- Default cost center in item master not set in stock entry ([#23816](https://github.com/frappe/erpnext/pull/23816))
- Asset finance book posting date fix ([#23780](https://github.com/frappe/erpnext/pull/23780))
- Added column cost_center to receivable reports ([#23837](https://github.com/frappe/erpnext/pull/23837))
- Override field_map for job card gantt ([#23740](https://github.com/frappe/erpnext/pull/23740))
- Added filter show in website for filtering product ([#23637](https://github.com/frappe/erpnext/pull/23637))
- Serial no field is blank in stock reconciliation ([#23646](https://github.com/frappe/erpnext/pull/23646))
- Copying po no when mapping doc ([#23730](https://github.com/frappe/erpnext/pull/23730))
- Show form buttons only if permissions exist ([#23889](https://github.com/frappe/erpnext/pull/23889))
- Cannot auto unlink payments for credit/debit notes ([#23690](https://github.com/frappe/erpnext/pull/23690))
- None type error if the Pricing Rule applicable_for is None ([#23664](https://github.com/frappe/erpnext/pull/23664))
- Don't copy terms, discount and required by from SO to PO ([#23904](https://github.com/frappe/erpnext/pull/23904))
- Add Taxes if missing via Update Items ([#23705](https://github.com/frappe/erpnext/pull/23705))
- Don't overrule Item Price via Pricing Rule Rate if 0 ([#23915](https://github.com/frappe/erpnext/pull/23915))
- Show only available items in point of sale ([#23667](https://github.com/frappe/erpnext/pull/23667))
- Auto State-wise gst tax template ([#23859](https://github.com/frappe/erpnext/pull/23859))
- Stock ageing report not working ([#23924](https://github.com/frappe/erpnext/pull/23924))
- Validate duplicate packing item in Product Bundle ([#23898](https://github.com/frappe/erpnext/pull/23898))

View File

@@ -0,0 +1,40 @@
## ERPNext v12.15.0 Release Note
### Fixes and Enhancements
- BOM stock report color showing always red ([#23993](https://github.com/frappe/erpnext/pull/23993))
- Clear error message when approval not availab ([#23972](https://github.com/frappe/erpnext/pull/23972))
- Show tax amount in base currencies ([#24071](https://github.com/frappe/erpnext/pull/24071))
- Depreciation Posting Date is mandatory even if Calculate Depreciation is not checked ([#24037](https://github.com/frappe/erpnext/pull/24037))
- Handle Account and Item None not found in Opening Invoice Creation Tool ([#24103](https://github.com/frappe/erpnext/pull/24103))
- Opening invoices in GSTR-1 report ([#24020](https://github.com/frappe/erpnext/pull/24020))
- Incorrect balance value in stock balance report ([#23997](https://github.com/frappe/erpnext/pull/23997))
- Columns mismatch in AR report([#24085](https://github.com/frappe/erpnext/pull/24085))
- Job card error handling for operations field ([#23996](https://github.com/frappe/erpnext/pull/23996))
- Set proper state code in ewaybill JSON when GST category is SEZ ([#23954](https://github.com/frappe/erpnext/pull/23954))
- PO orverride ([#24023](https://github.com/frappe/erpnext/pull/24023))
- Invoice generation for Unpaid subscriptions ([#23966](https://github.com/frappe/erpnext/pull/23966))
- Throw an error when no pos profile exist ([#24026](https://github.com/frappe/erpnext/pull/24026))
- Purchase receipt to purchase invoice bill date mapping ([#23968](https://github.com/frappe/erpnext/pull/23968))
- Validation for duplicate Tax Category ([#24175](https://github.com/frappe/erpnext/pull/24175))
- Double exception in payroll ([#24080](https://github.com/frappe/erpnext/pull/24080))
- Sales invoice add button on sales order dashboard ([#24081](https://github.com/frappe/erpnext/pull/24081))
- Hide Ex-Employees from Employee Tree and minor message UX ([#23927](https://github.com/frappe/erpnext/pull/23927))
- Get value of allow_items_in_stock even if not an exact match ([#24099](https://github.com/frappe/erpnext/pull/24099))
- Incorrect delink serial no and batch ([#23958](https://github.com/frappe/erpnext/pull/23958))
- Pricing rule with transaction not working for additional product ([#24064](https://github.com/frappe/erpnext/pull/24064))
- Check if list view standard filter exists in Payment Entry ([#23929](https://github.com/frappe/erpnext/pull/23929))
- Do not fetch items until POS Profile is set ([#24076](https://github.com/frappe/erpnext/pull/24076))
- Taxation fixes for India ([#24162](https://github.com/frappe/erpnext/pull/24162))
- Don't cancel job card if manufacturing entry has made ([#24034](https://github.com/frappe/erpnext/pull/24034))
- Payment Reconciliation client side validations ([#23930](https://github.com/frappe/erpnext/pull/23930))
- Item Link Formatter Behaviour ([#23931](https://github.com/frappe/erpnext/pull/23931))
- Asset with value zero doesn't show up in fixed asset register ([#24098](https://github.com/frappe/erpnext/pull/24098))
- Allow add to cart for any item if allow_items_not_in_stock is enabled ([#24084](https://github.com/frappe/erpnext/pull/24084))
- Incoming rate for finished good ([#24013](https://github.com/frappe/erpnext/pull/24013))
- Incorrect stock ledger entries for stock reco ([#23938](https://github.com/frappe/erpnext/pull/23938))
- Function imports in account_balance_timeline.py ([#24097](https://github.com/frappe/erpnext/pull/24097))
- Sequence Matcher error in Bank Reconciliation ([#23539](https://github.com/frappe/erpnext/pull/23539))
- Shipping charges not sync from shopify ([#24009](https://github.com/frappe/erpnext/pull/24009))
- Delete Receive at Warehouse entry on cancellation of Send to War… ([#24068](https://github.com/frappe/erpnext/pull/24068))
- Get formatted value in 'taxes' print template ([#24036](https://github.com/frappe/erpnext/pull/24036))

View File

@@ -0,0 +1,11 @@
## ERPNext v12.16.0 Release Note
### Feature
- GST E-invoicing for India ([#24184](https://github.com/frappe/erpnext/pull/24184))
### Fixes
- Do not override the manually added valuation rate in stock entry ([#24221](https://github.com/frappe/erpnext/pull/24221))
- Do not manufacture same serial no multiple times ([#24163](https://github.com/frappe/erpnext/pull/24163))

View File

@@ -0,0 +1,24 @@
## ERPNext v12.17.0 Release Notes
### Features
- Separated equity tree in COA SKR04 ([#24094](https://github.com/frappe/erpnext/pull/24094))
- Display transporter address in sales invoice ([#23731](https://github.com/frappe/erpnext/pull/23731))
- Introduced GST E-Invoicing ([#24184](https://github.com/frappe/erpnext/pull/24184))
### Fixes
- Fixed Payment Entry multi-currency issue ([#24331](https://github.com/frappe/erpnext/pull/24331))
- Fixed an issue where user could have manufactured same serial no multiple times ([#24163](https://github.com/frappe/erpnext/pull/24163))
- Back Update from QC based on Batch No ([#24368](https://github.com/frappe/erpnext/pull/24368))
- Fixed tax calculation on salary slip for the first month ([#24309](https://github.com/frappe/erpnext/pull/24309)) ([#24272](https://github.com/frappe/erpnext/pull/24272))
- Fixed issues related to e-invoicing ([#24366](https://github.com/frappe/erpnext/pull/24366)) ([#24421](https://github.com/frappe/erpnext/pull/24421)) ([#24284](https://github.com/frappe/erpnext/pull/24284))
- Added a validation to restrict manual overriding of valuation rate in Stock Entry ([#24221](https://github.com/frappe/erpnext/pull/24221))
- Fixed incorrect serial no. in the subcontracted Purchase Receipt ([#24353](https://github.com/frappe/erpnext/pull/24353))
- Fixed an issue where Stock Ledger entry was not getting created against Stock Reconciliation ([#24384](https://github.com/frappe/erpnext/pull/24384))
- Fixed company wise Valuation Rate for raw material in BOM ([#24367](https://github.com/frappe/erpnext/pull/24367))
- Fixed Taxation related issue ([#24159](https://github.com/frappe/erpnext/pull/24159))
- Allowed to override the basic rate for the finished good ([#24301](https://github.com/frappe/erpnext/pull/24301))
- Fixed Loyalty Program related issues ([#24188](https://github.com/frappe/erpnext/pull/24188))
- Fixed an issue where last purchase rate was not getting updated on canceling last voucher ([#24323](https://github.com/frappe/erpnext/pull/24323))
- Fixed issue with pricing rule for offline POS ([#24288](https://github.com/frappe/erpnext/pull/24288))

View File

@@ -0,0 +1,37 @@
## ERPNext v12.18.0 Release Notes
### Enhancements
- Make patient age translatable ([#24416](https://github.com/frappe/erpnext/pull/24416))
- Adding UOM, Item Group via Update Items ([#24479](https://github.com/frappe/erpnext/pull/24479))
### Fixes
- Incorrect incoming rate for the sales return ([#24620](https://github.com/frappe/erpnext/pull/24620))
- Prorata factor fixes in subscription ([#24638](https://github.com/frappe/erpnext/pull/24638))
- QR code image generation for e-invoicing ([#24422](https://github.com/frappe/erpnext/pull/24422))
- Validation for disabled warehouse ([#24546](https://github.com/frappe/erpnext/pull/24546))
- Update total in words after updating items ([#24592](https://github.com/frappe/erpnext/pull/24592))
- Set contact email in RFQ ([#24486](https://github.com/frappe/erpnext/pull/24486))
- Plaid client version to support latest API ([#24532](https://github.com/frappe/erpnext/pull/24532))
- Dynamic Links for reports ([#24461](https://github.com/frappe/erpnext/pull/24461))
- Use supplied year for IRS 1099 forms ([#24425](https://github.com/frappe/erpnext/pull/24425))
- Add check for allowing access to european region ([#24393](https://github.com/frappe/erpnext/pull/24393))
- Item-wise Sales Register item_name error ([#24484](https://github.com/frappe/erpnext/pull/24484))
- Skip e-invoice generation for non-taxable invoices (India) ([#24569](https://github.com/frappe/erpnext/pull/24569))
- Issues with packing items ([#24606](https://github.com/frappe/erpnext/pull/24606))
- Remove max 5 file attachment limit in task ([#24056](https://github.com/frappe/erpnext/pull/24056))
- Calculate discount amount ([#24511](https://github.com/frappe/erpnext/pull/24511))
- Validate tax template for tax category ([#24403](https://github.com/frappe/erpnext/pull/24403))
- Do not validate gstin for exports (India) ([#24564](https://github.com/frappe/erpnext/pull/24564))
- Stock ageing should not take cancelled stock entries. ([#24438](https://github.com/frappe/erpnext/pull/24438))
- Discount amount calculation on net total ([#24498](https://github.com/frappe/erpnext/pull/24498))
- Fetching of standalone cr/dr notes for reconciliation ([#24576](https://github.com/frappe/erpnext/pull/24576))
- Avoid changing Ref. Doctype in Accounting Dimension after creation ([#24579](https://github.com/frappe/erpnext/pull/24579))
- Add GST state code for Ladakh (India) ([#24635](https://github.com/frappe/erpnext/pull/24635))
- Consolidated Financial Statement report not works if child company accounts not present in the parent company ([#24580](https://github.com/frappe/erpnext/pull/24580))
- Missing Asset Id in the Fixed Asset Register Report ([#24391](https://github.com/frappe/erpnext/pull/24391))
- e_invoice print format not showing other charges ([#24473](https://github.com/frappe/erpnext/pull/24473))
- Fix filters for report IRS 1099 ([#24597](https://github.com/frappe/erpnext/pull/24597))
- Stock ledger entry was not created against stock reconciliation ([#24382](https://github.com/frappe/erpnext/pull/24382))
- Validate cancellation only if irn generated (India) ([#24609](https://github.com/frappe/erpnext/pull/24609))

View File

@@ -23,6 +23,8 @@ from erpnext.accounts.doctype.accounting_dimension.accounting_dimension import g
from erpnext.stock.get_item_details import get_item_warehouse, _get_item_tax_template, get_item_tax_map
from erpnext.stock.doctype.packed_item.packed_item import make_packing_list
class AccountMissingError(frappe.ValidationError): pass
force_item_fields = ("item_group", "brand", "stock_uom", "is_fixed_asset", "item_tax_rate", "pricing_rules")
class AccountsController(TransactionBase):
@@ -106,8 +108,14 @@ class AccountsController(TransactionBase):
self.validate_deferred_start_and_end_date()
validate_regional(self)
validate_einvoice_fields(self)
if self.doctype != 'Material Request':
apply_pricing_rule_on_transaction(self)
def before_cancel(self):
validate_einvoice_fields(self)
def validate_deferred_start_and_end_date(self):
for d in self.items:
@@ -601,8 +609,6 @@ class AccountsController(TransactionBase):
from erpnext.accounts.utils import unlink_ref_doc_from_payment_entries
if self.doctype in ["Sales Invoice", "Purchase Invoice"]:
if self.is_return: return
if frappe.db.get_single_value('Accounts Settings', 'unlink_payment_on_cancellation_of_invoice'):
unlink_ref_doc_from_payment_entries(self)
@@ -713,6 +719,21 @@ class AccountsController(TransactionBase):
return self._abbr
def raise_missing_debit_credit_account_error(self, party_type, party):
"""Raise an error if debit to/credit to account does not exist."""
db_or_cr = frappe.bold("Debit To") if self.doctype == "Sales Invoice" else frappe.bold("Credit To")
rec_or_pay = "Receivable" if self.doctype == "Sales Invoice" else "Payable"
link_to_party = frappe.utils.get_link_to_form(party_type, party)
link_to_company = frappe.utils.get_link_to_form("Company", self.company)
message = _("{0} Account not found against Customer {1}.").format(db_or_cr, frappe.bold(party) or '')
message += "<br>" + _("Please set one of the following:") + "<br>"
message += "<br><ul><li>" + _("'Account' in the Accounting section of Customer {0}").format(link_to_party) + "</li>"
message += "<li>" + _("'Default {0} Account' in Company {1}").format(rec_or_pay, link_to_company) + "</li></ul>"
frappe.throw(message, title=_("Account Missing"), exc=AccountMissingError)
def validate_party(self):
party_type, party = self.get_party()
validate_party_frozen_disabled(party_type, party)
@@ -1164,43 +1185,28 @@ def add_taxes_from_tax_template(child_item, parent_doc):
})
tax_row.db_insert()
def set_sales_order_defaults(parent_doctype, parent_doctype_name, child_docname, trans_item):
def set_order_defaults(parent_doctype, parent_doctype_name, child_doctype, child_docname, trans_item):
"""
Returns a Sales Order Item child item containing the default values
Returns a Sales/Purchase Order Item child item containing the default values
"""
p_doc = frappe.get_doc(parent_doctype, parent_doctype_name)
child_item = frappe.new_doc('Sales Order Item', p_doc, child_docname)
child_item = frappe.new_doc(child_doctype, p_doc, child_docname)
item = frappe.get_doc("Item", trans_item.get('item_code'))
child_item.item_code = item.item_code
child_item.item_name = item.item_name
child_item.description = item.description
child_item.delivery_date = trans_item.get('delivery_date') or p_doc.delivery_date
child_item.conversion_factor = flt(trans_item.get('conversion_factor')) or get_conversion_factor(item.item_code, item.stock_uom).get("conversion_factor") or 1.0
child_item.uom = item.stock_uom
set_child_tax_template_and_map(item, child_item, p_doc)
add_taxes_from_tax_template(child_item, p_doc)
child_item.warehouse = get_item_warehouse(item, p_doc, overwrite_warehouse=True)
if not child_item.warehouse:
frappe.throw(_("Cannot find {} for item {}. Please set the same in Item Master or Stock Settings.")
.format(frappe.bold("default warehouse"), frappe.bold(item.item_code)))
return child_item
def set_purchase_order_defaults(parent_doctype, parent_doctype_name, child_docname, trans_item):
"""
Returns a Purchase Order Item child item containing the default values
"""
p_doc = frappe.get_doc(parent_doctype, parent_doctype_name)
child_item = frappe.new_doc('Purchase Order Item', p_doc, child_docname)
item = frappe.get_doc("Item", trans_item.get('item_code'))
child_item.item_code = item.item_code
child_item.item_name = item.item_name
child_item.description = item.description
child_item.schedule_date = trans_item.get('schedule_date') or p_doc.schedule_date
child_item.conversion_factor = flt(trans_item.get('conversion_factor')) or get_conversion_factor(item.item_code, item.stock_uom).get("conversion_factor") or 1.0
child_item.uom = item.stock_uom
child_item.base_rate = 1 # Initiallize value will update in parent validation
child_item.base_amount = 1 # Initiallize value will update in parent validation
for field in ("item_code", "item_name", "description", "item_group"):
child_item.update({field: item.get(field)})
date_fieldname = "delivery_date" if child_doctype == "Sales Order Item" else "schedule_date"
child_item.update({date_fieldname: trans_item.get(date_fieldname) or p_doc.get(date_fieldname)})
child_item.uom = trans_item.get("uom") or item.stock_uom
conversion_factor = flt(get_conversion_factor(item.item_code, child_item.uom).get("conversion_factor"))
child_item.conversion_factor = flt(trans_item.get('conversion_factor')) or conversion_factor
if child_doctype == "Purchase Order Item":
child_item.base_rate = 1 # Initiallize value will update in parent validation
child_item.base_amount = 1 # Initiallize value will update in parent validation
if child_doctype == "Sales Order Item":
child_item.warehouse = get_item_warehouse(item, p_doc, overwrite_warehouse=True)
if not child_item.warehouse:
frappe.throw(_("Cannot find {} for item {}. Please set the same in Item Master or Stock Settings.")
.format(frappe.bold("default warehouse"), frappe.bold(item.item_code)))
set_child_tax_template_and_map(item, child_item, p_doc)
add_taxes_from_tax_template(child_item, p_doc)
return child_item
@@ -1264,8 +1270,8 @@ def update_child_qty_rate(parent_doctype, trans_items, parent_doctype_name, chil
)
def get_new_child_item(item_row):
new_child_function = set_sales_order_defaults if parent_doctype == "Sales Order" else set_purchase_order_defaults
return new_child_function(parent_doctype, parent_doctype_name, child_docname, item_row)
child_doctype = "Sales Order Item" if parent_doctype == "Sales Order" else "Purchase Order Item"
return set_order_defaults(parent_doctype, parent_doctype_name, child_doctype, child_docname, item_row)
def validate_quantity(child_item, d):
if parent_doctype == "Sales Order" and flt(d.get("qty")) < flt(child_item.delivered_qty):
@@ -1295,6 +1301,7 @@ def update_child_qty_rate(parent_doctype, trans_items, parent_doctype_name, chil
prev_rate, new_rate = flt(child_item.get("rate")), flt(d.get("rate"))
prev_qty, new_qty = flt(child_item.get("qty")), flt(d.get("qty"))
prev_con_fac, new_con_fac = flt(child_item.get("conversion_factor")), flt(d.get("conversion_factor"))
prev_uom, new_uom = child_item.get("uom"), d.get("uom")
if parent_doctype == 'Sales Order':
prev_date, new_date = child_item.get("delivery_date"), d.get("delivery_date")
@@ -1303,9 +1310,10 @@ def update_child_qty_rate(parent_doctype, trans_items, parent_doctype_name, chil
rate_unchanged = prev_rate == new_rate
qty_unchanged = prev_qty == new_qty
uom_unchanged = prev_uom == new_uom
conversion_factor_unchanged = prev_con_fac == new_con_fac
date_unchanged = prev_date == new_date if prev_date and new_date else False # in case of delivery note etc
if rate_unchanged and qty_unchanged and conversion_factor_unchanged and date_unchanged:
if rate_unchanged and qty_unchanged and conversion_factor_unchanged and uom_unchanged and date_unchanged:
continue
validate_quantity(child_item, d)
@@ -1326,6 +1334,11 @@ def update_child_qty_rate(parent_doctype, trans_items, parent_doctype_name, chil
child_item.conversion_factor = 1
else:
child_item.conversion_factor = flt(d.get('conversion_factor'), conv_fac_precision)
if d.get("uom"):
child_item.uom = d.get("uom")
conversion_factor = flt(get_conversion_factor(child_item.item_code, child_item.uom).get("conversion_factor"))
child_item.conversion_factor = flt(d.get('conversion_factor')) or conversion_factor
if d.get("delivery_date") and parent_doctype == 'Sales Order':
child_item.delivery_date = d.get('delivery_date')
@@ -1367,6 +1380,7 @@ def update_child_qty_rate(parent_doctype, trans_items, parent_doctype_name, chil
parent.flags.ignore_validate_update_after_submit = True
parent.set_qty_as_per_stock_uom()
parent.calculate_taxes_and_totals()
parent.set_total_in_words()
if parent_doctype == "Sales Order":
make_packing_list(parent)
parent.set_gross_profit()
@@ -1392,6 +1406,8 @@ def update_child_qty_rate(parent_doctype, trans_items, parent_doctype_name, chil
parent.update_receiving_percentage()
if parent.is_subcontracted == "Yes":
parent.update_reserved_qty_for_subcontract()
parent.create_raw_materials_supplied("supplied_items")
parent.save()
else:
parent.update_reserved_qty()
parent.update_project()
@@ -1408,3 +1424,7 @@ def update_child_qty_rate(parent_doctype, trans_items, parent_doctype_name, chil
@erpnext.allow_regional
def validate_regional(doc):
pass
@erpnext.allow_regional
def validate_einvoice_fields(doc):
pass

View File

@@ -292,11 +292,11 @@ class BuyingController(StockController):
# backflushed_batch_qty_map = get_backflushed_batch_qty_map(item.purchase_order, item.item_code)
for raw_material in transferred_raw_materials + non_stock_items:
rm_item_key = (raw_material.rm_item_code, item.purchase_order)
rm_item_key = (raw_material.rm_item_code, item.item_code, item.purchase_order)
raw_material_data = backflushed_raw_materials_map.get(rm_item_key, {})
consumed_qty = raw_material_data.get('qty', 0)
consumed_serial_nos = raw_material_data.get('serial_nos', '')
consumed_serial_nos = raw_material_data.get('serial_no', '')
consumed_batch_nos = raw_material_data.get('batch_nos', '')
transferred_qty = raw_material.qty
@@ -881,7 +881,7 @@ def get_backflushed_subcontracted_raw_materials(purchase_orders):
purchase_receipt_supplied_items = get_supplied_items(args[1], args[2], references)
for data in purchase_receipt_supplied_items:
pr_key = (data.rm_item_code, args[0])
pr_key = (data.rm_item_code, data.main_item_code, args[0])
if pr_key not in backflushed_raw_materials_map:
backflushed_raw_materials_map.setdefault(pr_key, frappe._dict({
"qty": 0.0,
@@ -907,7 +907,7 @@ def get_backflushed_subcontracted_raw_materials(purchase_orders):
def get_supplied_items(item_code, purchase_receipt, references):
return frappe.get_all("Purchase Receipt Item Supplied",
fields=["rm_item_code", "consumed_qty", "serial_no", "batch_no"],
fields=["rm_item_code", "main_item_code", "consumed_qty", "serial_no", "batch_no"],
filters={"main_item_code": item_code, "parent": purchase_receipt, "reference_name": ("in", references)})
def get_asset_item_details(asset_items):

View File

@@ -279,6 +279,7 @@ def make_return_doc(doctype, source_name, target_doc=None):
target_doc.po_detail = source_doc.po_detail
target_doc.pr_detail = source_doc.pr_detail
target_doc.purchase_invoice_item = source_doc.name
target_doc.price_list_rate = 0
elif doctype == "Delivery Note":
target_doc.against_sales_order = source_doc.against_sales_order
@@ -297,6 +298,7 @@ def make_return_doc(doctype, source_name, target_doc=None):
target_doc.dn_detail = source_doc.dn_detail
target_doc.expense_account = source_doc.expense_account
target_doc.sales_invoice_item = source_doc.name
target_doc.price_list_rate = 0
if default_warehouse_for_sales_return:
target_doc.warehouse = default_warehouse_for_sales_return

View File

@@ -42,7 +42,7 @@ class SellingController(StockController):
self.validate_max_discount()
self.validate_selling_price()
self.set_qty_as_per_stock_uom()
self.set_po_nos()
self.set_po_nos(for_validate=True)
self.set_gross_profit()
set_default_income_account_for_item(self)
self.set_customer_address()
@@ -310,12 +310,27 @@ class SellingController(StockController):
if flt(d.conversion_factor)==0.0:
d.conversion_factor = get_conversion_factor(d.item_code, d.uom).get("conversion_factor") or 1.0
return_rate = 0
if cint(self.is_return) and self.return_against and self.docstatus==1:
against_document_no = (d.get("sales_invoice_item")
if self.doctype == "Sales Invoice" else d.get("delivery_note_item"))
if cint(self.is_return) and self.docstatus==1:
if self.return_against:
against_document_no = (d.get("sales_invoice_item")
if self.doctype == "Sales Invoice" else d.get("delivery_note_item"))
return_rate = self.get_incoming_rate_for_sales_return(d.item_code,
self.return_against, against_document_no)
return_rate = self.get_incoming_rate_for_sales_return(d.item_code,
self.return_against, against_document_no)
else:
# For standalone credit note
args = frappe._dict({
"item_code": d.item_code,
"warehouse": d.warehouse,
"posting_date": self.posting_date,
"posting_time": self.posting_time,
"qty": flt(d.qty),
"serial_no": d.serial_no,
"company": d.company,
"allow_zero_valuation": d.allow_zero_valuation
})
return_rate = get_incoming_rate(args)
# On cancellation or if return entry submission, make stock ledger entry for
# target warehouse first, to update serial no values properly
@@ -364,14 +379,36 @@ class SellingController(StockController):
}))
self.make_sl_entries(sl_entries)
def set_po_nos(self):
if self.doctype in ("Delivery Note", "Sales Invoice") and hasattr(self, "items"):
ref_fieldname = "against_sales_order" if self.doctype == "Delivery Note" else "sales_order"
sales_orders = list(set([d.get(ref_fieldname) for d in self.items if d.get(ref_fieldname)]))
if sales_orders:
po_nos = frappe.get_all('Sales Order', 'po_no', filters = {'name': ('in', sales_orders)})
if po_nos and po_nos[0].get('po_no'):
self.po_no = ', '.join(list(set([d.po_no for d in po_nos if d.po_no])))
def set_po_nos(self, for_validate=False):
if self.doctype == 'Sales Invoice' and hasattr(self, "items"):
if for_validate and self.po_no:
return
self.set_pos_for_sales_invoice()
if self.doctype == 'Delivery Note' and hasattr(self, "items"):
if for_validate and self.po_no:
return
self.set_pos_for_delivery_note()
def set_pos_for_sales_invoice(self):
po_nos = []
if self.po_no:
po_nos.append(self.po_no)
self.get_po_nos('Sales Order', 'sales_order', po_nos)
self.get_po_nos('Delivery Note', 'delivery_note', po_nos)
self.po_no = ', '.join(list(set(x.strip() for x in ','.join(po_nos).split(','))))
def set_pos_for_delivery_note(self):
po_nos = []
if self.po_no:
po_nos.append(self.po_no)
self.get_po_nos('Sales Order', 'against_sales_order', po_nos)
self.get_po_nos('Sales Invoice', 'against_sales_invoice', po_nos)
self.po_no = ', '.join(list(set(x.strip() for x in ','.join(po_nos).split(','))))
def get_po_nos(self, ref_doctype, ref_fieldname, po_nos):
doc_list = list(set([d.get(ref_fieldname) for d in self.items if d.get(ref_fieldname)]))
if doc_list:
po_nos += [d.po_no for d in frappe.get_all(ref_doctype, 'po_no', filters = {'name': ('in', doc_list)}) if d.get('po_no')]
def set_gross_profit(self):
if self.doctype == "Sales Order":

View File

@@ -246,22 +246,26 @@ class StatusUpdater(Document):
if not args.get("second_source_extra_cond"):
args["second_source_extra_cond"] = ""
args['second_source_condition'] = """ + ifnull((select sum(%(second_source_field)s)
args['second_source_condition'] = frappe.db.sql(""" select ifnull((select sum(%(second_source_field)s)
from `tab%(second_source_dt)s`
where `%(second_join_field)s`="%(detail_id)s"
and (`tab%(second_source_dt)s`.docstatus=1) %(second_source_extra_cond)s FOR UPDATE), 0) """ % args
and (`tab%(second_source_dt)s`.docstatus=1)
%(second_source_extra_cond)s), 0) """ % args)[0][0]
if args['detail_id']:
if not args.get("extra_cond"): args["extra_cond"] = ""
frappe.db.sql("""update `tab%(target_dt)s`
set %(target_field)s = (
args["source_dt_value"] = frappe.db.sql("""
(select ifnull(sum(%(source_field)s), 0)
from `tab%(source_dt)s` where `%(join_field)s`="%(detail_id)s"
and (docstatus=1 %(cond)s) %(extra_cond)s)
%(second_source_condition)s
)
%(update_modified)s
""" % args)[0][0] or 0.0
if args['second_source_condition']:
args["source_dt_value"] += flt(args['second_source_condition'])
frappe.db.sql("""update `tab%(target_dt)s`
set %(target_field)s = %(source_dt_value)s %(update_modified)s
where name='%(detail_id)s'""" % args)
def _update_percent_field_in_targets(self, args, update_modified=True):

View File

@@ -227,9 +227,9 @@ class StockController(AccountsController):
def check_expense_account(self, item):
if not item.get("expense_account"):
frappe.throw(_("Row #{0}: Expense Account not set for Item {1}. Please set an Expense \
Account in the Items table").format(item.idx, frappe.bold(item.item_code)),
title=_("Expense Account Missing"))
msg = _("Please set an Expense Account in the Items table")
frappe.throw(_("Row #{0}: Expense Account not set for the Item {1}. {2}")
.format(item.idx, frappe.bold(item.item_code), msg), title=_("Expense Account Missing"))
else:
is_expense_account = frappe.db.get_value("Account",
@@ -242,11 +242,12 @@ class StockController(AccountsController):
_(self.doctype), self.name, item.get("item_code")))
def delete_auto_created_batches(self):
from erpnext.stock.doctype.serial_no.serial_no import get_serial_nos
for d in self.items:
if not d.batch_no: continue
serial_nos = get_serial_nos(d.serial_no)
serial_nos = [sr.name for sr in frappe.get_all("Serial No",
{'batch_no': d.batch_no, 'status': 'Inactive'})]
if serial_nos:
frappe.db.set_value("Serial No", { 'name': ['in', serial_nos] }, "batch_no", None)
@@ -318,12 +319,13 @@ class StockController(AccountsController):
return incoming_rate
def validate_warehouse(self):
from erpnext.stock.utils import validate_warehouse_company
from erpnext.stock.utils import validate_warehouse_company, validate_disabled_warehouse
warehouses = list(set([d.warehouse for d in
self.get("items") if getattr(d, "warehouse", None)]))
for w in warehouses:
validate_disabled_warehouse(w)
validate_warehouse_company(w, self.company)
def update_billing_percentage(self, update_modified=True):

View File

@@ -531,16 +531,6 @@ class calculate_taxes_and_totals(object):
self._set_in_company_currency(self.doc, ['write_off_amount'])
if self.doc.doctype in ["Sales Invoice", "Purchase Invoice"]:
grand_total = self.doc.rounded_total or self.doc.grand_total
if self.doc.party_account_currency == self.doc.currency:
total_amount_to_pay = flt(grand_total - self.doc.total_advance
- flt(self.doc.write_off_amount), self.doc.precision("grand_total"))
else:
total_amount_to_pay = flt(flt(grand_total *
self.doc.conversion_rate, self.doc.precision("grand_total")) - self.doc.total_advance
- flt(self.doc.base_write_off_amount), self.doc.precision("grand_total"))
self.doc.round_floats_in(self.doc, ["paid_amount"])
change_amount = 0
if self.doc.doctype == "Sales Invoice" and not self.doc.get('is_return'):
@@ -549,14 +539,10 @@ class calculate_taxes_and_totals(object):
change_amount = self.doc.change_amount \
if self.doc.party_account_currency == self.doc.currency else self.doc.base_change_amount
paid_amount = self.doc.paid_amount \
if self.doc.party_account_currency == self.doc.currency else self.doc.base_paid_amount
self.doc.outstanding_amount = flt(total_amount_to_pay - flt(paid_amount) + flt(change_amount),
self.doc.precision("outstanding_amount"))
calculate_outstanding_amount(self.doc, change_amount)
if self.doc.doctype == 'Sales Invoice' and self.doc.get('is_pos') and self.doc.get('is_return'):
self.update_paid_amount_for_return(total_amount_to_pay)
self.update_paid_amount_for_return(self.doc.total_amount_to_pay)
def calculate_paid_amount(self):
@@ -751,3 +737,20 @@ def get_rounded_tax_amount(itemised_tax, precision):
for taxes in itemised_tax.values():
for tax_account in taxes:
taxes[tax_account]["tax_amount"] = flt(taxes[tax_account]["tax_amount"], precision)
def calculate_outstanding_amount(doc, change_amount=None):
grand_total = doc.rounded_total or doc.grand_total
if doc.party_account_currency == doc.currency:
doc.total_amount_to_pay = flt(grand_total - doc.total_advance
- flt(doc.write_off_amount), doc.precision("grand_total"))
else:
doc.total_amount_to_pay = flt(flt(grand_total *
doc.conversion_rate, doc.precision("grand_total")) - doc.total_advance
- flt(doc.base_write_off_amount), doc.precision("grand_total"))
doc.round_floats_in(doc, ["paid_amount"])
paid_amount = doc.paid_amount \
if doc.party_account_currency == doc.currency else doc.base_paid_amount
doc.outstanding_amount = flt(doc.total_amount_to_pay - flt(paid_amount) + flt(change_amount),
doc.precision("outstanding_amount"))

View File

@@ -19,15 +19,50 @@ def set_defaut_value_for_filters(filters):
if not filters.get('lead_age'): filters["lead_age"] = 60
def get_columns():
return [
_("Lead") + ":Link/Lead:100",
_("Name") + "::100",
_("Organization") + "::100",
_("Reference Document") + "::150",
_("Reference Name") + ":Dynamic Link/"+_("Reference Document")+":120",
_("Last Communication") + ":Data:200",
_("Last Communication Date") + ":Date:180"
]
columns = [{
"label": _("Lead"),
"fieldname": "lead",
"fieldtype": "Link",
"options": "Lead",
"width": 130
},
{
"label": _("Name"),
"fieldname": "name",
"width": 120
},
{
"label": _("Organization"),
"fieldname": "organization",
"width": 120
},
{
"label": _("Reference Document Type"),
"fieldname": "reference_document_type",
"fieldtype": "Link",
"options": "Doctype",
"width": 100
},
{
"label": _("Reference Name"),
"fieldname": "reference_name",
"fieldtype": "Dynamic Link",
"options": "reference_document_type",
"width": 140
},
{
"label": _("Last Communication"),
"fieldname": "last_communication",
"fieldtype": "Data",
"width": 200
},
{
"label": _("Last Communication Date"),
"fieldname": "last_communication_date",
"fieldtype": "Date",
"width": 100
}]
return columns
def get_data(filters):
lead_details = []

View File

@@ -13,7 +13,7 @@
"fields": [
{
"fieldname": "question",
"fieldtype": "Small Text",
"fieldtype": "Text Editor",
"in_list_view": 1,
"label": "Question",
"reqd": 1
@@ -34,7 +34,7 @@
"read_only": 1
}
],
"modified": "2019-05-30 18:39:21.880974",
"modified": "2021-01-28 18:39:21.880974",
"modified_by": "Administrator",
"module": "Education",
"name": "Question",
@@ -77,4 +77,4 @@
"quick_entry": 1,
"sort_field": "modified",
"sort_order": "DESC"
}
}

View File

@@ -244,6 +244,15 @@ def update_taxes_with_shipping_lines(taxes, shipping_lines, shopify_settings):
"""Shipping lines represents the shipping details,
each such shipping detail consists of a list of tax_lines"""
for shipping_charge in shipping_lines:
if shipping_charge.get("price"):
taxes.append({
"charge_type": _("Actual"),
"account_head": get_tax_account_head(shipping_charge),
"description": shipping_charge["title"],
"tax_amount": shipping_charge["price"],
"cost_center": shopify_settings.cost_center
})
for tax in shipping_charge.get("tax_lines"):
taxes.append({
"charge_type": _("Actual"),

View File

@@ -20,7 +20,7 @@ class PlaidConnector():
client_id=self.settings.plaid_client_id,
secret=self.settings.get_password("plaid_secret"),
environment=self.settings.plaid_env,
api_version="2019-05-29"
api_version="2020-09-14"
)
def get_access_token(self, public_token):
@@ -30,20 +30,32 @@ class PlaidConnector():
access_token = response["access_token"]
return access_token
def get_link_token(self):
token_request = {
def get_token_request(self, update_mode=False):
country_codes = ["US", "CA", "FR", "IE", "NL", "ES", "GB"] if self.settings.enable_european_access else ["US", "CA"]
args = {
"client_name": self.client_name,
"client_id": self.settings.plaid_client_id,
"secret": self.settings.plaid_secret,
"products": self.products,
# only allow Plaid-supported languages and countries (LAST: Sep-19-2020)
"language": frappe.local.lang if frappe.local.lang in ["en", "fr", "es", "nl"] else "en",
"country_codes": ["US", "CA", "FR", "IE", "NL", "ES", "GB"],
"country_codes": country_codes,
"user": {
"client_user_id": frappe.generate_hash(frappe.session.user, length=32)
}
}
if update_mode:
args["access_token"] = self.access_token
else:
args.update({
"client_id": self.settings.plaid_client_id,
"secret": self.settings.plaid_secret,
"products": self.products,
})
return args
def get_link_token(self, update_mode=False):
token_request = self.get_token_request(update_mode)
try:
response = self.client.LinkToken.create(token_request)
except InvalidRequestError:

View File

@@ -12,7 +12,7 @@ frappe.ui.form.on('Plaid Settings', {
refresh: function (frm) {
if (frm.doc.enabled) {
frm.add_custom_button('Link a new bank account', () => {
frm.add_custom_button(__('Link a new bank account'), () => {
new erpnext.integrations.plaidLink(frm);
});
}
@@ -30,10 +30,18 @@ erpnext.integrations.plaidLink = class plaidLink {
this.product = ["auth", "transactions"];
this.plaid_env = this.frm.doc.plaid_env;
this.client_name = frappe.boot.sitename;
this.token = await this.frm.call("get_link_token").then(resp => resp.message);
this.token = await this.get_link_token();
this.init_plaid();
}
async get_link_token() {
const token = await this.frm.call("get_link_token").then(resp => resp.message);
if (!token) {
frappe.throw(__('Cannot retrieve link token. Check Error Log for more information'));
}
return token;
}
init_plaid() {
const me = this;
me.loadScript(me.plaidUrl)
@@ -78,8 +86,8 @@ erpnext.integrations.plaidLink = class plaidLink {
}
onScriptError(error) {
frappe.msgprint("There was an issue connecting to Plaid's authentication server");
frappe.msgprint(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) {
@@ -107,4 +115,4 @@ erpnext.integrations.plaidLink = class plaidLink {
});
}, __("Select a company"), __("Continue"));
}
};
};

View File

@@ -1,4 +1,5 @@
{
"actions": [],
"creation": "2018-10-25 10:02:48.656165",
"doctype": "DocType",
"editable_grid": 1,
@@ -11,7 +12,8 @@
"plaid_client_id",
"plaid_secret",
"column_break_7",
"plaid_env"
"plaid_env",
"enable_european_access"
],
"fields": [
{
@@ -58,10 +60,17 @@
{
"fieldname": "column_break_7",
"fieldtype": "Column Break"
},
{
"default": "0",
"fieldname": "enable_european_access",
"fieldtype": "Check",
"label": "Enable European Access"
}
],
"issingle": 1,
"modified": "2020-09-12 02:31:44.542385",
"links": [],
"modified": "2020-10-29 20:24:56.916104",
"modified_by": "Administrator",
"module": "ERPNext Integrations",
"name": "Plaid Settings",

View File

@@ -239,3 +239,8 @@ def automatic_synchronization():
bank=plaid_account.bank,
bank_account=plaid_account.name
)
@frappe.whitelist()
def get_link_token_for_update(access_token):
plaid = PlaidConnector(access_token)
return plaid.get_link_token(update_mode=True)

View File

@@ -308,7 +308,7 @@ var calculate_age = function(birth) {
var age = new Date();
age.setTime(ageMS);
var years = age.getFullYear() - 1970;
return years + " Year(s) " + age.getMonth() + " Month(s) " + age.getDate() + " Day(s)";
return `${years} ${__('Years(s)')} ${age.getMonth()} ${__('Month(s)')} ${age.getDate()} ${__('Day(s)')}`;
};
// List Stock items

View File

@@ -7,6 +7,7 @@ import frappe
import unittest
from frappe.utils.make_random import get_random
from frappe.utils import nowdate, add_days, getdate
from erpnext.accounts.doctype.pos_profile.test_pos_profile import make_pos_profile
test_dependencies = ["Company"]
@@ -14,6 +15,7 @@ class TestFeeValidity(unittest.TestCase):
def test_fee_validity(self):
frappe.db.sql("""delete from `tabPatient Appointment`""")
frappe.db.sql("""delete from `tabFee Validity`""")
make_pos_profile()
patient = get_random("Patient")
practitioner = get_random("Healthcare Practitioner")
department = get_random("Medical Department")

View File

@@ -293,5 +293,5 @@ var calculate_age = function(birth) {
var age = new Date();
age.setTime(ageMS);
var years = age.getFullYear() - 1970;
return years + " Year(s) " + age.getMonth() + " Month(s) " + age.getDate() + " Day(s)";
return `${years} ${__('Years(s)')} ${age.getMonth()} ${__('Month(s)')} ${age.getDate()} ${__('Day(s)')}`;
};

View File

@@ -43,7 +43,7 @@ frappe.ui.form.on('Patient', {
$(frm.fields_dict['age_html'].wrapper).html("");
}
if(frm.doc.dob){
$(frm.fields_dict['age_html'].wrapper).html("AGE : " + get_age(frm.doc.dob));
$(frm.fields_dict['age_html'].wrapper).html(`${__('AGE')} : ${get_age(frm.doc.dob)}`);
}
}
});
@@ -58,7 +58,7 @@ frappe.ui.form.on("Patient", "dob", function(frm) {
}
else{
var age_str = get_age(frm.doc.dob);
$(frm.fields_dict['age_html'].wrapper).html("AGE : " + age_str);
$(frm.fields_dict['age_html'].wrapper).html(`${__('AGE')} : ${age_str}`);
}
}
else {
@@ -81,7 +81,7 @@ var get_age = function (birth) {
var age = new Date();
age.setTime(ageMS);
var years = age.getFullYear() - 1970;
return years + " Year(s) " + age.getMonth() + " Month(s) " + age.getDate() + " Day(s)";
return `${years} ${__('Years(s)')} ${age.getMonth()} ${__('Month(s)')} ${age.getDate()} ${__('Day(s)')}`;
};
var btn_create_vital_signs = function (frm) {

View File

@@ -58,7 +58,7 @@ class Patient(Document):
if self.dob:
born = getdate(self.dob)
age = dateutil.relativedelta.relativedelta(getdate(), born)
age_str = str(age.years) + " year(s) " + str(age.months) + " month(s) " + str(age.days) + " day(s)"
age_str = str(age.years) + ' ' + _("Years(s)") + ' ' + str(age.months) + ' ' + _("Month(s)") + ' ' + str(age.days) + ' ' + _("Day(s)")
return age_str
def invoice_patient_registration(self):

View File

@@ -468,5 +468,5 @@ var calculate_age = function(birth) {
var age = new Date();
age.setTime(ageMS);
var years = age.getFullYear() - 1970;
return years + " Year(s) " + age.getMonth() + " Month(s) " + age.getDate() + " Day(s)";
return `${years} ${__('Years(s)')} ${age.getMonth()} ${__('Month(s)')} ${age.getDate()} ${__('Day(s)')}`;
};

View File

@@ -311,5 +311,5 @@ var calculate_age = function(birth) {
var age = new Date();
age.setTime(ageMS);
var years = age.getFullYear() - 1970;
return years + " Year(s) " + age.getMonth() + " Month(s) " + age.getDate() + " Day(s)";
return `${years} ${__('Years(s)')} ${age.getMonth()} ${__('Month(s)')} ${age.getDate()} ${__('Day(s)')}`;
};

View File

@@ -36,5 +36,5 @@ var calculate_age = function(birth) {
var age = new Date();
age.setTime(ageMS);
var years = age.getFullYear() - 1970;
return years + " Year(s) " + age.getMonth() + " Month(s) " + age.getDate() + " Day(s)";
return `${years} ${__('Years(s)')} ${age.getMonth()} ${__('Month(s)')} ${age.getDate()} ${__('Day(s)')}`;
};

View File

@@ -239,10 +239,14 @@ doc_events = {
"Website Settings": {
"validate": "erpnext.portal.doctype.products_settings.products_settings.home_page_is_products"
},
"Tax Category": {
"validate": "erpnext.regional.india.utils.validate_tax_category"
},
"Sales Invoice": {
"on_submit": ["erpnext.regional.create_transaction_log", "erpnext.regional.italy.utils.sales_invoice_on_submit"],
"on_cancel": "erpnext.regional.italy.utils.sales_invoice_on_cancel",
"on_trash": "erpnext.regional.check_deletion_permission"
"on_trash": "erpnext.regional.check_deletion_permission",
"validate": "erpnext.regional.india.utils.set_transporter_address"
},
"Purchase Invoice": {
"validate": "erpnext.regional.india.utils.update_grand_total_for_rcm"
@@ -357,7 +361,8 @@ regional_overrides = {
'erpnext.accounts.party.get_regional_address_details': 'erpnext.regional.india.utils.get_regional_address_details',
'erpnext.hr.utils.calculate_annual_eligible_hra_exemption': 'erpnext.regional.india.utils.calculate_annual_eligible_hra_exemption',
'erpnext.hr.utils.calculate_hra_exemption_for_period': 'erpnext.regional.india.utils.calculate_hra_exemption_for_period',
'erpnext.accounts.doctype.purchase_invoice.purchase_invoice.make_regional_gl_entries': 'erpnext.regional.india.utils.make_regional_gl_entries'
'erpnext.accounts.doctype.purchase_invoice.purchase_invoice.make_regional_gl_entries': 'erpnext.regional.india.utils.make_regional_gl_entries',
'erpnext.controllers.accounts_controller.validate_einvoice_fields': 'erpnext.regional.india.e_invoice.utils.validate_einvoice_fields'
},
'United Arab Emirates': {
'erpnext.controllers.taxes_and_totals.update_itemised_tax_data': 'erpnext.regional.united_arab_emirates.utils.update_itemised_tax_data'

View File

@@ -20,7 +20,7 @@ def get_approvers(doctype, txt, searchfield, start, page_len, filters):
approvers = []
department_details = {}
department_list = []
employee = frappe.get_value("Employee", filters.get("employee"), ["department", "leave_approver"], as_dict=True)
employee = frappe.get_value("Employee", filters.get("employee"), ["employee_name","department", "leave_approver"], as_dict=True)
employee_department = filters.get("department") or employee.department
if employee_department:
@@ -36,8 +36,10 @@ def get_approvers(doctype, txt, searchfield, start, page_len, filters):
if filters.get("doctype") == "Leave Application":
parentfield = "leave_approvers"
else:
field_name = "Leave Approver"
elif filters.get("doctype") == "Expense Claim":
parentfield = "expense_approvers"
field_name = "Expense Approver"
if department_list:
for d in department_list:
approvers += frappe.db.sql("""select user.name, user.first_name, user.last_name from
@@ -47,4 +49,10 @@ def get_approvers(doctype, txt, searchfield, start, page_len, filters):
and approver.parentfield = %s
and approver.approver=user.name""",(d, "%" + txt + "%", parentfield), as_list=True)
if len(approvers) == 0:
error_msg = _("Please set {0} for the Employee: {1}").format(field_name, frappe.bold(employee.employee_name))
if department_list:
error_msg += _(" or for Department: {0}").format(frappe.bold(employee_department))
frappe.throw(error_msg, title=_(field_name + " Missing"))
return set(tuple(approver) for approver in approvers)

View File

@@ -782,7 +782,7 @@
"icon": "fa fa-user",
"idx": 24,
"image_field": "image",
"modified": "2020-01-09 04:23:55.611366",
"modified": "2020-01-09 05:23:55.611366",
"modified_by": "Administrator",
"module": "HR",
"name": "Employee",
@@ -824,7 +824,6 @@
"write": 1
}
],
"quick_entry": 1,
"search_fields": "employee_name",
"show_name_in_global_search": 1,
"sort_field": "modified",

View File

@@ -172,8 +172,11 @@ class Employee(NestedSet):
)
if reports_to:
link_to_employees = [frappe.utils.get_link_to_form('Employee', employee.name, label=employee.employee_name) for employee in reports_to]
throw(_("Employee status cannot be set to 'Left' as following employees are currently reporting to this employee:&nbsp;")
+ ', '.join(link_to_employees), EmployeeLeftValidationError)
message = _("The following employees are currently still reporting to {0}:").format(frappe.bold(self.employee_name))
message += "<br><br><ul><li>" + "</li><li>".join(link_to_employees)
message += "</li></ul><br>"
message += _("Please make sure the employees above report to another Active employee.")
throw(message, EmployeeLeftValidationError, _("Cannot Relieve Employee"))
if not self.relieving_date:
throw(_("Please enter relieving date."))
@@ -206,7 +209,7 @@ class Employee(NestedSet):
def validate_preferred_email(self):
if self.prefered_contact_email and not self.get(scrub(self.prefered_contact_email)):
frappe.msgprint(_("Please enter " + self.prefered_contact_email))
frappe.msgprint(_("Please enter {0}").format(self.prefered_contact_email))
def validate_onboarding_process(self):
employee_onboarding = frappe.get_all("Employee Onboarding",
@@ -407,7 +410,11 @@ def get_employee_emails(employee_list):
@frappe.whitelist()
def get_children(doctype, parent=None, company=None, is_root=False, is_tree=False):
filters = [['company', '=', company]]
filters = [['status', '!=', 'Left']]
if company and company != 'All Companies':
filters.append(['company', '=', company])
fields = ['name as value', 'employee_name as title']
if is_root:

View File

@@ -46,6 +46,7 @@ frappe.ui.form.on("Leave Application", {
make_dashboard: function(frm) {
var leave_details;
let lwps;
if (frm.doc.employee) {
frappe.call({
method: "erpnext.hr.doctype.leave_application.leave_application.get_leave_details",
@@ -61,6 +62,7 @@ frappe.ui.form.on("Leave Application", {
if (!r.exc && r.message['leave_approver']) {
frm.set_value('leave_approver', r.message['leave_approver']);
}
lwps = r.message["lwps"];
}
});
$("div").remove(".form-dashboard-section");
@@ -70,6 +72,18 @@ frappe.ui.form.on("Leave Application", {
})
);
frm.dashboard.show();
let allowed_leave_types = Object.keys(leave_details);
// lwps should be allowed, lwps don't have any allocation
allowed_leave_types = allowed_leave_types.concat(lwps);
frm.set_query('leave_type', function(){
return {
filters : [
['leave_type_name', 'in', allowed_leave_types]
]
};
});
}
},

View File

@@ -19,7 +19,6 @@ class NotAnOptionalHoliday(frappe.ValidationError): pass
from frappe.model.document import Document
class LeaveApplication(Document):
def get_feed(self):
return _("{0}: From {0} of type {1}").format(self.employee_name, self.leave_type)
@@ -451,9 +450,14 @@ def get_leave_details(employee, date):
"pending_leaves": leaves_pending,
"remaining_leaves": remaining_leaves}
#is used in set query
lwps = frappe.get_list("Leave Type", filters = {"is_lwp": 1})
lwps = [lwp.name for lwp in lwps]
ret = {
'leave_allocation': leave_allocation,
'leave_approver': get_leave_approver(employee)
'leave_approver': get_leave_approver(employee),
'lwps': lwps
}
return ret

View File

@@ -1,5 +1,5 @@
{% if data %}
{% if not jQuery.isEmptyObject(data) %}
<h5 style="margin-top: 20px;"> {{ __("Allocated Leaves") }} </h5>
<table class="table table-bordered small">
<thead>
@@ -11,7 +11,6 @@
<th style="width: 16%" class="text-right">{{ __("Pending Leaves") }}</th>
<th style="width: 16%" class="text-right">{{ __("Available Leaves") }}</th>
</tr>
</thead>
<tbody>
{% for(const [key, value] of Object.entries(data)) { %}
@@ -26,6 +25,6 @@
{% } %}
</tbody>
</table>
{% } else { %}
{% else %}
<p style="margin-top: 30px;"> No Leaves have been allocated. </p>
{% } %}
{% endif %}

View File

@@ -95,7 +95,11 @@ class LeaveEncashment(Document):
create_leave_ledger_entry(self, args, submit)
# create reverse entry for expired leaves
to_date = self.get_leave_allocation().get('to_date')
leave_allocation = self.get_leave_allocation()
if not leave_allocation:
return
to_date = leave_allocation.get('to_date')
if to_date < getdate(nowdate()):
args = frappe._dict(
leaves=self.encashable_days,

View File

@@ -302,7 +302,9 @@ class PayrollEntry(Document):
jv_name = journal_entry.name
self.update_salary_slip_status(jv_name = jv_name)
except Exception as e:
frappe.msgprint(e)
if type(e) in (str, list, tuple):
frappe.msgprint(e)
raise
return jv_name
@@ -379,9 +381,13 @@ class PayrollEntry(Document):
employees_to_mark_attendance = []
days_in_payroll, days_holiday, days_attendance_marked = 0, 0, 0
for employee_detail in self.employees:
days_holiday = self.get_count_holidays_of_employee(employee_detail.employee)
days_attendance_marked = self.get_count_employee_attendance(employee_detail.employee)
days_in_payroll = date_diff(self.end_date, self.start_date) + 1
employee_joining_date = frappe.db.get_value("Employee", employee_detail.employee, 'date_of_joining')
start_date = self.start_date
if employee_joining_date > getdate(self.start_date):
start_date = employee_joining_date
days_holiday = self.get_count_holidays_of_employee(employee_detail.employee, start_date)
days_attendance_marked = self.get_count_employee_attendance(employee_detail.employee, start_date)
days_in_payroll = date_diff(self.end_date, start_date) + 1
if days_in_payroll > days_holiday + days_attendance_marked:
employees_to_mark_attendance.append({
"employee": employee_detail.employee,
@@ -389,22 +395,25 @@ class PayrollEntry(Document):
})
return employees_to_mark_attendance
def get_count_holidays_of_employee(self, employee):
def get_count_holidays_of_employee(self, employee, start_date):
holiday_list = get_holiday_list_for_employee(employee)
holidays = 0
if holiday_list:
days = frappe.db.sql("""select count(*) from tabHoliday where
parent=%s and holiday_date between %s and %s""", (holiday_list,
self.start_date, self.end_date))
start_date, self.end_date))
if days and days[0][0]:
holidays = days[0][0]
return holidays
def get_count_employee_attendance(self, employee):
def get_count_employee_attendance(self, employee, start_date):
marked_days = 0
attendances = frappe.db.sql("""select count(*) from tabAttendance where
employee=%s and docstatus=1 and attendance_date between %s and %s""",
(employee, self.start_date, self.end_date))
attendances = frappe.get_all("Attendance",
fields = ["count(*)"],
filters = {
"employee": employee,
"attendance_date": ('between', [start_date, self.end_date])
}, as_list=1)
if attendances and attendances[0][0]:
marked_days = attendances[0][0]
return marked_days

View File

@@ -5,7 +5,7 @@
from __future__ import unicode_literals
import frappe
from frappe import _
from frappe.utils import date_diff, getdate, formatdate, cint, month_diff, flt
from frappe.utils import date_diff, getdate, formatdate, cint, month_diff, flt, add_months
from frappe.model.document import Document
from erpnext.hr.utils import get_holidays_for_employee
@@ -88,6 +88,8 @@ def get_period_factor(employee, start_date, end_date, payroll_frequency, payroll
period_start = joining_date
if relieving_date and getdate(relieving_date) < getdate(period_end):
period_end = relieving_date
if month_diff(period_end, start_date) > 1:
start_date = add_months(start_date, - (month_diff(period_end, start_date)+1))
total_sub_periods, remaining_sub_periods = 0.0, 0.0

View File

@@ -299,14 +299,17 @@ class SalarySlip(TransactionBase):
def calculate_net_pay(self):
if self.salary_structure:
self.calculate_component_amounts("earnings")
self.gross_pay = self.get_component_totals("earnings")
self.gross_pay = self.get_component_totals("earnings", depends_on_payment_days=1)
if self.salary_structure:
self.calculate_component_amounts("deductions")
self.total_deduction = self.get_component_totals("deductions")
self.set_loan_repayment()
self.set_component_amounts_based_on_payment_days()
self.set_net_pay()
def set_net_pay(self):
self.total_deduction = self.get_component_totals("deductions")
self.net_pay = flt(self.gross_pay) - (flt(self.total_deduction) + flt(self.total_loan_repayment))
self.rounded_total = rounded(self.net_pay)
@@ -323,8 +326,6 @@ class SalarySlip(TransactionBase):
else:
self.add_tax_components(payroll_period)
self.set_component_amounts_based_on_payment_days(component_type)
def add_structure_components(self, component_type):
data = self.get_data_for_eval()
for struct_row in self._salary_structure_doc.get(component_type):
@@ -679,7 +680,7 @@ class SalarySlip(TransactionBase):
cint(row.depends_on_payment_days) and cint(self.total_working_days) and
(not self.salary_slip_based_on_timesheet or
getdate(self.start_date) < joining_date or
getdate(self.end_date) > relieving_date
(relieving_date and getdate(self.end_date) > relieving_date)
)):
additional_amount = flt((flt(row.additional_amount) * flt(self.payment_days)
/ cint(self.total_working_days)), row.precision("additional_amount"))
@@ -812,15 +813,21 @@ class SalarySlip(TransactionBase):
struct_row['variable_based_on_taxable_salary'] = component.variable_based_on_taxable_salary
return struct_row
def get_component_totals(self, component_type):
def get_component_totals(self, component_type, depends_on_payment_days=0):
joining_date, relieving_date = frappe.get_cached_value("Employee", self.employee,
["date_of_joining", "relieving_date"])
total = 0.0
for d in self.get(component_type):
if not d.do_not_include_in_total:
d.amount = flt(d.amount, d.precision("amount"))
total += d.amount
if depends_on_payment_days:
amount = self.get_amount_based_on_payment_days(d, joining_date, relieving_date)[0]
else:
amount = flt(d.amount, d.precision("amount"))
total += amount
return total
def set_component_amounts_based_on_payment_days(self, component_type):
def set_component_amounts_based_on_payment_days(self):
joining_date, relieving_date = frappe.get_cached_value("Employee", self.employee,
["date_of_joining", "relieving_date"])
@@ -830,8 +837,9 @@ class SalarySlip(TransactionBase):
if not joining_date:
frappe.throw(_("Please set the Date Of Joining for employee {0}").format(frappe.bold(self.employee_name)))
for d in self.get(component_type):
d.amount = self.get_amount_based_on_payment_days(d, joining_date, relieving_date)[0]
for component_type in ("earnings", "deductions"):
for d in self.get(component_type):
d.amount = flt(self.get_amount_based_on_payment_days(d, joining_date, relieving_date)[0], d.precision("amount"))
def set_loan_repayment(self):
self.set('loans', [])

View File

@@ -6,18 +6,28 @@ from __future__ import unicode_literals
import frappe
import unittest
from frappe.utils import nowdate,flt, cstr,random_string
from erpnext.hr.doctype.employee.test_employee import make_employee
from erpnext.hr.doctype.vehicle_log.vehicle_log import make_expense_claim
class TestVehicleLog(unittest.TestCase):
def setUp(self):
employee_id = frappe.db.sql("""select name from `tabEmployee` where name='testdriver@example.com'""")
self.employee_id = employee_id[0][0] if employee_id else None
if not self.employee_id:
self.employee_id = make_employee("testdriver@example.com", company="_Test Company")
self.license_plate = get_vehicle(self.employee_id)
def tearDown(self):
frappe.delete_doc("Vehicle", self.license_plate, force=1)
frappe.delete_doc("Employee", self.employee_id, force=1)
def test_make_vehicle_log_and_syncing_of_odometer_value(self):
employee_id = frappe.db.sql("""select name from `tabEmployee` where status='Active' order by modified desc limit 1""")
employee_id = employee_id[0][0] if employee_id else None
license_plate = get_vehicle(employee_id)
vehicle_log = frappe.get_doc({
"doctype": "Vehicle Log",
"license_plate": cstr(license_plate),
"employee":employee_id,
"license_plate": cstr(self.license_plate),
"employee": self.employee_id,
"date":frappe.utils.nowdate(),
"odometer":5010,
"fuel_qty":frappe.utils.flt(50),
@@ -27,7 +37,7 @@ class TestVehicleLog(unittest.TestCase):
vehicle_log.submit()
#checking value of vehicle odometer value on submit.
vehicle = frappe.get_doc("Vehicle", license_plate)
vehicle = frappe.get_doc("Vehicle", self.license_plate)
self.assertEqual(vehicle.last_odometer, vehicle_log.odometer)
#checking value vehicle odometer on vehicle log cancellation.
@@ -40,6 +50,28 @@ class TestVehicleLog(unittest.TestCase):
self.assertEqual(vehicle.last_odometer, current_odometer - distance_travelled)
vehicle_log.delete()
def test_vehicle_log_fuel_expense(self):
vehicle_log = frappe.get_doc({
"doctype": "Vehicle Log",
"license_plate": cstr(self.license_plate),
"employee": self.employee_id,
"date": frappe.utils.nowdate(),
"odometer":5010,
"fuel_qty":frappe.utils.flt(50),
"price": frappe.utils.flt(500)
})
vehicle_log.save()
vehicle_log.submit()
expense_claim = make_expense_claim(vehicle_log.name)
fuel_expense = expense_claim.expenses[0].amount
self.assertEqual(fuel_expense, 50*500)
vehicle_log.cancel()
frappe.delete_doc("Expense Claim", expense_claim.name)
frappe.delete_doc("Vehicle Log", vehicle_log.name)
def get_vehicle(employee_id):
license_plate=random_string(10).upper()

View File

@@ -32,7 +32,7 @@ def make_expense_claim(docname):
vehicle_log = frappe.get_doc("Vehicle Log", docname)
service_expense = sum([flt(d.expense_amount) for d in vehicle_log.service_detail])
claim_amount = service_expense + flt(vehicle_log.price)
claim_amount = service_expense + (flt(vehicle_log.price) * flt(vehicle_log.fuel_qty) or 1)
if not claim_amount:
frappe.throw(_("No additional expenses has been added"))

View File

@@ -253,7 +253,7 @@ cur_frm.cscript.hour_rate = function(doc) {
cur_frm.cscript.time_in_mins = cur_frm.cscript.hour_rate;
cur_frm.cscript.bom_no = function(doc, cdt, cdn) {
cur_frm.cscript.bom_no = function(doc, cdt, cdn) {
get_bom_material_detail(doc, cdt, cdn, false);
};
@@ -261,17 +261,22 @@ cur_frm.cscript.is_default = function(doc) {
if (doc.is_default) cur_frm.set_value("is_active", 1);
};
var get_bom_material_detail= function(doc, cdt, cdn, scrap_items) {
var get_bom_material_detail = function(doc, cdt, cdn, scrap_items) {
if (!doc.company) {
frappe.throw({message: __("Please select a Company first."), title: __("Mandatory")});
}
var d = locals[cdt][cdn];
if (d.item_code) {
return frappe.call({
doc: doc,
method: "get_bom_material_detail",
args: {
'item_code': d.item_code,
'bom_no': d.bom_no != null ? d.bom_no: '',
"company": doc.company,
"item_code": d.item_code,
"bom_no": d.bom_no != null ? d.bom_no: '',
"scrap_items": scrap_items,
'qty': d.qty,
"qty": d.qty,
"stock_qty": d.stock_qty,
"include_item_in_manufacturing": d.include_item_in_manufacturing,
"uom": d.uom,
@@ -309,7 +314,7 @@ cur_frm.cscript.rate = function(doc, cdt, cdn) {
}
if (d.bom_no) {
frappe.msgprint(__("You can not change rate if BOM mentioned agianst any item"));
frappe.msgprint(__("You cannot change the rate if BOM is mentioned against any Item."));
get_bom_material_detail(doc, cdt, cdn, scrap_items);
} else {
erpnext.bom.calculate_rm_cost(doc);

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