Compare commits

..

759 Commits

Author SHA1 Message Date
Sahil Khan
50e591b815 Merge branch 'develop' into version-12 2019-09-17 17:11:15 +05:30
Sahil Khan
4f96ec1b6c bumped to version 12.1.3 2019-09-17 17:31:14 +05:50
sahil28297
0816c0bd5e Merge pull request #19093 from Aerele/fix_indentation
fix: indentation error in stock ageing
2019-09-17 17:08:35 +05:30
sahil28297
c1930fa64d Merge branch 'develop' into fix_indentation 2019-09-17 17:08:16 +05:30
kaviya
9e4f674fb9 fix: indentation error in stock ageing
fixes https://travis-ci.com/frappe/erpnext/jobs/235815591#L1720
2019-09-17 16:02:11 +05:30
Suraj Shetty
627a3dcd6d feat: Default energy point rules (#19003)
* feat: Add default energy point rules during install

* fix: Add completed_by field to task doctype

* fix: Rule data

* fix: Add default rules for opportunity

* fix: Add a patch to create default energy point rules

* fix: Default success action message

* fix: Use .items() instead of .iteritems()

* fix: Add "create_default_energy_points" patch entry

* fix: Reload Energy Point Rule to fix patch

* fix: Import frappe
2019-09-17 15:54:41 +05:30
Suraj Shetty
af2eac4334 fix: Create error log if something goes wrong while call log creation (#19055)
* fix: Create error log if something goes wrong while call log creation

- For better debbugging

* fix: Rollback if any error occurs during call log creation
2019-09-17 15:53:23 +05:30
Suraj Shetty
f9069a9873 fix: Return employee_emails instead of employee (#19085)
fix: Return employee_emails instead of employee
2019-09-17 13:50:42 +05:30
Suraj Shetty
7563bdf6f8 Merge branch 'develop' into fix-exotel-call-log 2019-09-17 13:28:59 +05:30
rohitwaghchaure
ad5fc07652 Merge pull request #19084 from rohitwaghchaure/offline_pos_currency_conversion_issue_for_v11
fix: plc conversion issue for offline pos
2019-09-17 13:24:41 +05:30
Suraj Shetty
6b9b92afb0 fix: Return employee emails instead of employee 2019-09-17 13:22:40 +05:30
Rohit Waghchaure
094612dc02 fix: plc conversion issue for offline pos 2019-09-17 13:04:28 +05:30
Faris Ansari
4fe67236ed fix: Python 3 fixes for MWS Connector (#18986) 2019-09-17 12:57:51 +05:30
Deepesh Garg
c5c3860c5c fix: Mandatory accounting dimensions while creating asset depreciation entry (#19073)
* fix: Mandatory accounting dimensions while creating asset depreciation entry

* fix: Consider account types while assigning accounting dimensions
2019-09-17 12:50:28 +05:30
rohitwaghchaure
6de526ff42 fix: not able to change the account type in parent company account head (#19083) 2019-09-17 12:49:52 +05:30
Mangesh-Khairnar
5d41e3848d fix: do not submit depreciation journal entry when workflow is enabled (#19000) 2019-09-17 12:45:14 +05:30
Frappe PR Bot
abd434f656 feat: Updated translation (#19077) 2019-09-16 19:57:27 +05:30
Suraj Shetty
bc001d2d9a feat: Add stock ageing data to stock balance report (#19036)
* feat: Add stock ageing data to stock balance report

* fix: Use fifo queue warehouse wise

* fix: "Stock Ledger Entry" get query

* fix: Remove unwanted quotes in item details query

* fix: Check if no SLE was passed

* fix: Codacy

* fix: Add logic to include additional UOM columns

* fix: Show stock ageing data optionally
2019-09-16 19:57:04 +05:30
Nabin Hait
b50b5095ad fix: Added field disabled instead of enabled in cost center (#19065) 2019-09-16 19:44:37 +05:30
Marica
bac4b93639 fix: Displaying manufacturer part no along with manufacturer and added Manufacturers validation in Item master (#19066)
Manufacturer Link field options in Items Table of transactions will also display manufacturer part no.
Manufacturers table in Item master will check for duplicate entries.
2019-09-16 19:44:28 +05:30
rohitwaghchaure
76df782006 fix: Decimal point issue for e-invoice (#19068) 2019-09-16 19:43:17 +05:30
Mangesh-Khairnar
dce04b7335 fix: filter for payment order (#19070) 2019-09-16 19:40:27 +05:30
Chinmay Pai
7e8e4783a1 fix: remove function call from kwarg (#19072)
this commit fixes mail not being sent for leave applications

Signed-off-by: Chinmay D. Pai <chinmaydpai@gmail.com>
2019-09-16 19:14:42 +05:30
rohitwaghchaure
bb5f99a34d Merge pull request #19071 from rohitwaghchaure/naming_series_added_for_the_asset_movement_develop
minor: naming series added in the asset movement
2019-09-16 19:10:54 +05:30
Rohit Waghchaure
40c5bf9e94 fix: naming series added in the asset movement 2019-09-16 16:42:42 +05:30
Faris Ansari
8beca68948 feat: Scan Barcode using Camera in mobile (#19033)
* feat: Scan Barcode using Camera in mobile

* fix: Use input-group for scan button

* fix: Muted camera button
2019-09-16 15:20:10 +05:30
Rucha Mahabal
2818b5bbe7 fix: 'link to material request' button not showing any message if no Material Request found (#19064) 2019-09-16 15:16:38 +05:30
Deepesh Garg
8cc2f83bd5 fix: Fetch scrap items from BOM if purpose is repack (#19056) 2019-09-16 14:49:12 +05:30
Nabin Hait
57835f0a37 fix: Company is required to get bin details (#19058) 2019-09-16 14:48:16 +05:30
Rushabh Mehta
72dcb51177 fix(minor): opportunity_from may not be selected (#19063) 2019-09-16 14:47:43 +05:30
Sammish Thundiyil
a2a9b39794 modified: erpnext/accounts/doctype/account/account.json (#19032) 2019-09-16 13:29:25 +05:30
Nabin Hait
c2a9b14c96 fix: Invalid reference doctypes for accounting dimensions (#19027)
* fix: Invalid reference doctypes for accounting dimensions

* fix: Add server side validation for accounting doctypes

* fix: set fieldname and label before insert
2019-09-16 13:26:37 +05:30
Nabin Hait
74fdfff5b5 fix: Set todo status as Closed if task completed (#19059) 2019-09-16 13:06:37 +05:30
rohitwaghchaure
87000977d5 Merge pull request #19061 from rohitwaghchaure/user_can_edit_rate_and_discount_in_offline_pos_develop
fix: user can able to change rate and discount even if they don't have permissions
2019-09-16 11:50:52 +05:30
Rohit Waghchaure
a9435cc6b0 fix: user can able to change rate and discount even if they don't have permission 2019-09-16 11:15:22 +05:30
rohitwaghchaure
4a323463f7 fix: for pos, paid amount has not considered the tax amount due to which outstanding amount showing for the pos invoices (#19039) 2019-09-13 18:36:57 +05:30
Deepesh Garg
9c3fd8dbc3 Merge pull request #19044 from marination/gstr-error
fix: Changed error message in GSTR-1 Report
2019-09-13 18:04:38 +05:30
marination
3d433efdfe fix[minor]: Changed error message in GSTR-1 Report
Error message didn't prompt where the user has to add the missing value(GSTIN No.)
2019-09-13 16:28:11 +05:30
Nabin Hait
93a9c08116 fix: Allocate payment amount in reference table on change of payment amount (#19041) 2019-09-13 15:48:50 +05:30
Chinmay Pai
b3c732daf5 refactor(plaid): move configuration from site_config to doctype (#18712)
* feat(plaid): move plaid from site_config to doctype

plaid requires accessing site_config and cloud users cannot access
site_config and hence, plaid integration doesn't work on the cloud.
Moving all the configuration from site_config to the Plaid Settings
doctype fixes this issue.

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

* feat(plaid): make changes to plaid_settings and add patch

* remove all references for get()-ing plaid variables from frappe.conf
  and replace them with values from doctype
* add patch to move all existing plaid settings variable values from
  frappe.conf to plaid_settings doctype

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

* fix(plaid): use get_single_value for Plaid Settings

Co-Authored-By: Himanshu <himanshuwarekar@yahoo.com>

* chore: reload plaid_settings before running patch

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

* chore: remove useless semicolon

fuck codacy

Signed-off-by: Chinmay D. Pai <chinmaydpai@gmail.com>
2019-09-13 15:48:08 +05:30
Suraj Shetty
f8899827e0 fix: Add Exotel Settings to integration module (#19025)
* fix: Add Exotel Settings to integration module

* fix: Add description
2019-09-13 12:27:00 +05:30
Suraj Shetty
6996c2d17d fix: Fetch image from user if available (#19030) 2019-09-13 12:25:06 +05:30
Mangesh-Khairnar
755020843b fix: leave balance reports (#18984)
* fix: process allocation expiry

* fix: leave balance summary filter

* fix: opening and closing balance

* fix: check for department leave approvers

* fix: minor changes

* fix: consider leave approver in employee

* Update employee_leave_balance_summary.py
2019-09-13 11:07:09 +05:30
Rucha Mahabal
72949e7f73 fix: share transfer validations for journal entry (#19018)
* fix share transfer validations for journal entry

* fix: share transfer test

* fix: tests
2019-09-13 11:05:40 +05:30
Suraj Shetty
e4f8bda1ea Merge pull request #19031 from surajshetty3416/fix-call-popup-name
fix: Make -> Create in call popup
2019-09-12 22:14:24 +05:30
Suraj Shetty
cdce6c746f fix: Make -> Create 2019-09-12 22:04:49 +05:30
Himanshu
d51f7af9ab fix: add contact phone to sales order (#19012) 2019-09-12 19:19:17 +05:30
Suraj Shetty
3b0ec48b0c fix: Naming series check to avoid duplicate entry error (#19015)
* fix: Naming series check to avoid duplicate key error

* fix: Check for existence of naming series
2019-09-12 19:18:44 +05:30
Nabin Hait
a5dfe0725f fix: payment against shareholder (#19019) 2019-09-12 19:17:24 +05:30
Shivam Mishra
a3095c987a fix: optimized query (#19026)
Co-authored-by: nabinhait
Co-authored-by: sahil28297 <sahilkhan28297@gmail.com>
2019-09-12 17:28:37 +05:30
Sammish Thundiyil
504e52ff46 refactor: cost center (#19011)
* 	modified:   erpnext/accounts/doctype/cost_center/cost_center.json

* fix: removed unique property from cost_center_name
2019-09-12 13:48:41 +05:30
sahil28297
b1604a24ed fix(add_to_cart): show add_to_card button only if specific conditions are satisfied (#19007) 2019-09-12 11:20:55 +05:30
Himanshu
e3ef56804c fix(Issue): track split from in issue (#18994)
* fix: track split from in issue

* fix: rename field name

* fix: remove first_mins to response
2019-09-11 19:20:20 +05:30
Fisher Yu
cd38ba4833 fix: several bugs and improvement ideas for education module #18599 (#18600)
* Update student_report_generation_tool.py

bug fix

* Update student_applicant.json

* Update program_course.json

* Update course_activity.json
2019-09-11 19:10:39 +05:30
Nabin Hait
1d1858a8b0 Show draft future payments as well 2019-09-11 18:39:49 +05:30
Nabin Hait
ff09b412f4 feat: Allowed multiple payment requests against a reference document (#18988) 2019-09-11 12:43:27 +05:30
Mangesh-Khairnar
7bcb24efbf fix(purchase-invoice): Update paid amount on creation of debit note (#18830)
* fix(purchase-invoice): set paid amount for purchase return

* fix(purchase-invoice): remove payment schedule on creation of debit note
2019-09-11 10:49:33 +05:30
rohitwaghchaure
bb736248a2 fix: incorrect qty calculation in the production plan fopr the sub assembely work orders (#18970) 2019-09-11 10:20:49 +05:30
Saurabh
e919388ee6 fix: do not cache value while creating item group, in setup wizard it will raise link validation error (#18992) 2019-09-11 10:07:50 +05:30
rohitwaghchaure
358a01a226 fix: Quotation Trends report not working for filter group by customer (#18989) 2019-09-10 19:18:30 +05:30
Nabin Hait
a035428d43 fix: handling of key does not exists error 2019-09-10 14:51:02 +05:30
Sahil Khan
d2315e5c5c Merge branch 'develop' into version-12 2019-09-10 14:38:39 +05:30
Sahil Khan
a2fd1f22da bumped to version 12.1.2 2019-09-10 14:58:39 +05:50
Sammish Thundiyil
bcda12f4bb modified: erpnext/accounts/doctype/mode_of_payment/mode_of_payment.json (#18829) 2019-09-10 14:11:02 +05:30
Shivam Mishra
e851346b4c fix: dont make dashboards if company is not set (#18975)
* fix: dont make dashboardss if company is not set

* fix: function call

* Update dashboard_charts.py
2019-09-10 14:08:31 +05:30
Nabin Hait
88e8688a4b fix: set raw material's batch based on main item's batch only if RM has batch no (#18977) 2019-09-10 14:07:45 +05:30
Suraj Shetty
0254217314 fix: Make address fields mandatory (#18979) 2019-09-10 14:07:05 +05:30
Mangesh-Khairnar
1853a83453 fix(packing-slip): add a descriptive message (#18981) 2019-09-10 13:21:01 +05:30
rohitwaghchaure
d312d11062 fix: port from hotfix (#18974)
* fix: '>' not supported between instances of 'int' and 'str'

* fix: not able to save item because price list has disabled
2019-09-10 10:47:36 +05:30
Deepesh Garg
69aeff15ef Merge pull request #18971 from Anurag810/sales_invoice_print_format_fixes_v13
fix: sales invoice return print format overriding the meta default print format
2019-09-09 18:35:05 +05:30
Anurag Mishra
89d3bc0b54 fix: sales invoice return print format overideing the meta default print format 2019-09-09 15:58:25 +05:30
Mangesh-Khairnar
cbcede79b1 Merge pull request #18964 from nabinhait/max_carry_forwarded_leaves
feat: Added input field for max carry forwarded leaves
2019-09-09 14:38:06 +05:30
Faris Ansari
32eccb8fb2 fix: Rename duplicate label Image to Website Image (#18912) 2019-09-09 14:29:01 +05:30
Nabin Hait
632fc6af79 feat: Added input field for max carry forwarded leaves 2019-09-09 13:33:00 +05:30
Suraj Shetty
f43825e4dd fix: convert dict to list for iteration (#18963) 2019-09-09 13:23:01 +05:30
Shivam Mishra
5f59c2ae75 fix: reload account timeline before creating dashboards (#18934)
* fix: sync account balance timeline.json before running patch

* fix: reload account timeline before creating dashboards
2019-09-09 13:20:53 +05:30
Mangesh-Khairnar
fd312be79f Merge pull request #18958 from surajshetty3416/employee-leave-balance-summary
feat: Employee Leave Balance Summary report
2019-09-09 13:18:41 +05:30
Nabin Hait
fb7c7b53ba feat: Added input field for max carry forwarded leaves 2019-09-09 12:08:58 +05:30
Suraj Shetty
d2f22b52a5 Merge branch 'develop' into employee-leave-balance-summary 2019-09-09 10:21:06 +05:30
MorezMartin
ffc4f8f2a5 feat: [stock -> packed_items] Enable modification of Description on packed items (#18907)
* Change packed item

* Remove description field on update_packed_items

* add possibility to modify description on packed items
2019-09-09 10:16:23 +05:30
rohitwaghchaure
cdcff6c26d Multiple port from v11 hotfix (#18954)
* fix: circular dependency during asset cancellation

* fix: ImponibileImporto for On Previous Row Total

* fix: PrezzoUnitario decimal issue
2019-09-09 10:15:01 +05:30
Faris Ansari
e352fb754b fix: Reload doctype in variants patch (#18962) 2019-09-08 21:25:33 +05:30
Suraj Shetty
5ae40a9500 fix: Use absolute import instead of relative import
Co-Authored-By: Mangesh-Khairnar <mkhairnar10@gmail.com>
2019-09-08 15:16:35 +05:30
Suraj Shetty
40dbb63042 Merge branch 'develop' into employee-leave-balance-summary 2019-09-08 14:15:47 +05:30
Faris Ansari
594918bd3a fix: Include Item variant patch in patches.txt (#18961) 2019-09-08 13:13:05 +05:30
Deepesh Garg
5343631708 Merge pull request #18960 from deepeshgarg007/gstr-1-remove-customer
fix: Minor fix in GSTR-1
2019-09-08 09:52:38 +05:30
deepeshgarg007
366451fc62 fix: Minor fix in GSTR-1 2019-09-08 09:51:15 +05:30
Suraj Shetty
a14ee7f1fe Merge branch 'develop' of github.com:frappe/erpnext into employee-leave-balance-summary 2019-09-07 22:02:02 +05:30
Suraj Shetty
c5588a9b93 fix: Column value and data indentation 2019-09-07 21:26:43 +05:30
Suraj Shetty
21a4f82f69 fix: Re-arrange filters 2019-09-07 20:21:56 +05:30
Nabin Hait
3b366c30a8 feat: Added default Leave Approver in Employee (#18953) 2019-09-07 12:31:07 +05:30
Saurabh
8e67a3a8a8 fix: check if 'All Item Group' exists before settings it as parent_item_group (#18956)
* fix: check if 'All Item Group' exists before settings it as parent_item_group

* feat: get cached value to avoid db call on each insert
2019-09-07 12:29:29 +05:30
Nabin Hait
4726fc4893 fix: Deleted unwanted production order files 2019-09-06 15:45:17 +05:30
Shivam Mishra
c69cc13c85 fix: updated footer message (#18949) 2019-09-06 15:40:15 +05:30
Prssanna Desai
ddfbb07c3b fix: fix accounts balance timeline dashboard chart source (#18942)
* fix: fix accounts balance timeline dashboard chart source

* fix: pass chart_name to get function instead of chart object
2019-09-06 15:38:06 +05:30
Nabin Hait
d30f87bbdf Merge branch 'Mangesh-Khairnar-feat-customer-credit-limit' into develop 2019-09-06 14:39:59 +05:30
Nabin Hait
4ce38059ac feat: Company wise credit limit 2019-09-06 14:33:10 +05:30
Anurag Mishra
bbc1b5cdcf feat: added date filter based on billing date and based date (#18935) 2019-09-06 12:10:37 +05:30
Anurag Mishra
ac0c1edd23 feat: added date filter based on billing date and based date (#18936) 2019-09-06 12:10:10 +05:30
Marica
a93b665427 fix: Print Format 'Point of Sale' removed from Sales invoice Print Format List (#18937)
'Point of Sale' Print Format for offline POS ,now doesn't appear in the Print Format Labels List in Sales Invoice for v12.
2019-09-05 18:26:45 +05:30
Sahil Khan
ede7050afe Merge branch 'develop' into version-12 2019-09-05 17:30:44 +05:30
Sahil Khan
0906bc8430 bumped to version 12.1.1 2019-09-05 17:50:44 +05:50
Nabin Hait
ac2b5ed84f fix: credit limit patch 2019-09-05 16:57:26 +05:30
Nabin Hait
b847731482 Merge branch 'feat-customer-credit-limit' of https://github.com/Mangesh-Khairnar/erpnext into Mangesh-Khairnar-feat-customer-credit-limit 2019-09-05 16:47:08 +05:30
Nabin Hait
b5bd91417d fix: Print/PDF of AR/AP report after refactoring (#18931) 2019-09-05 16:43:20 +05:30
Himanshu
6298da4458 fix: treeview fixes (#18803) 2019-09-05 16:12:33 +05:30
Deepesh Garg
cffe577028 fix: Add UOM in anlytics report when viewing based on item (#18902) 2019-09-05 16:03:15 +05:30
Raffael Meyer
48d1463825 fix(CoA): SKR04 (#18820)
- move debitors into receivables
- move creditors into payables
- rename "C - Verb." to "C-Verbindlichkeiten" for consitency
- move "Erlösschmälerungen" into a root of type "Expense"
-  move "Erhaltene Boni" and "Erhaltene Rabatte" into a root of type "Income"
2019-09-05 15:15:28 +05:30
hendrik
c257ce82c5 Party accounts if don't have default company (#18771)
Add check for get_default company
2019-09-05 15:14:09 +05:30
Anurag Mishra
867ac10ffd fix: handle for product bundle (#18420)
* fix: handle for product bundle

* fix: Requested changes and some general fixes
2019-09-05 15:13:21 +05:30
KanchanChauhan
d114c8f88f fix(Purchase Order): Status updater (#18612) 2019-09-05 15:11:43 +05:30
Karthikeyan S
1d1427de60 fix(auto attendance): handling None case for IN/OUT Logs (#18867) 2019-09-05 15:02:33 +05:30
Andy Zhu
91596f2467 Change the field name for Payment Entry (#18874)
In the Payment Entry Form, the field name for customer name is 'party' instead of 'party_name'. 
Need to change the customer_dashboard file accordingly.
2019-09-05 15:01:38 +05:30
John Clarke
a7d448dcba fix: Error "TypeError: unorderable types: int() > str()" When Trying to Create Packing Slip (#18913)
User report here https://discuss.erpnext.com/t/error-typeerror-unorderable-types-int-str-when-trying-to-create-packing-slip/52445

This has not been noted to github issues and is just a suggested fix, an expert may need to refactor more here?

User and traceback does not state whether Python 2 or 3 but perhaps 3 since that apparently does not 'guess' when types do not match?

See also https://stackoverflow.com/questions/14886881/unorderable-types-int-str
2019-09-05 14:55:35 +05:30
Rohan
77da3b4347 fix: pull project from task (#18776) 2019-09-05 14:53:43 +05:30
Rohan
9d77e9f719 fix: error while trying to get directions (#18827) 2019-09-05 14:51:22 +05:30
Govind S Menokee
c901d6322c fix(18837): Student creation error (#18838)
Academic user not able to create student
2019-09-05 14:50:23 +05:30
rohitwaghchaure
7496548c39 fix: not able to create invoice against patient (#18858) 2019-09-05 14:48:51 +05:30
rohitwaghchaure
f1fab871b8 fix: mismatch between warehouse tree value and warehouse based stock balance report value (#18879) 2019-09-05 14:47:43 +05:30
rohitwaghchaure
5aaf15d145 fix: healthcare practitioner not showing in the dropdown (#18929) 2019-09-05 14:42:28 +05:30
Nabin Hait
16a7ec95dc fix: tax category is optional argument 2019-09-05 13:01:15 +05:30
Suraj Shetty
607a21e02a feat: Init Employee Leave Balance Summary report 2019-09-05 12:42:29 +05:30
Nabin Hait
b03fa8a441 Merge branch 'develop' into feat-customer-credit-limit 2019-09-05 12:34:34 +05:30
Nabin Hait
f4fde51bba Update customer.py 2019-09-05 12:33:29 +05:30
Nabin Hait
c78c86663d Update customer_credit_balance.py 2019-09-05 12:24:37 +05:30
Nabin Hait
7834a0182b Update move_credit_limit_to_customer_credit_limit.py 2019-09-05 12:22:48 +05:30
sahil28297
1e0b0da7ad fix(patch): add company in filters to get proper parent account (#18905) 2019-09-05 12:21:44 +05:30
Faris Ansari
a2db94761a fix: Honor Shopping Cart Price List (#18885) 2019-09-05 12:19:50 +05:30
rohitwaghchaure
805b8634da fix: incorrect stock value difference when stock move from negative to positive (#18887) 2019-09-05 12:18:33 +05:30
Rohan
1635967c4e fix: attribute error when trying to fetch items (#18900) 2019-09-05 12:16:49 +05:30
Nabin Hait
a5907e17d5 Update accounts_receivable.py 2019-09-04 11:04:27 +05:30
Suraj Shetty
0252c1478e Merge pull request #18917 from surajshetty3416/fix-call-popup
fix: Use medium instead of to number to get schedule
2019-09-04 11:04:14 +05:30
Suraj Shetty
f5bece1afa Merge branch 'develop' into fix-call-popup 2019-09-04 11:03:58 +05:30
Suraj Shetty
e46c56bfe8 fix: Use medium instead of to number to get schedule 2019-09-04 11:02:52 +05:30
Nabin Hait
561a2e966e Update accounts_receivable.py 2019-09-04 11:02:48 +05:30
rohitwaghchaure
a9b0c55bcb Merge pull request #18914 from rohitwaghchaure/pos_search_item_not_working
fix: offline pos item search not working
2019-09-04 06:02:34 +05:30
Rohit Waghchaure
93bad51659 fix: offline pos item search not working 2019-09-03 23:29:41 +05:30
Rucha Mahabal
1e2dc2c8f1 feat: Employee Incentive and Retention Bonus added in Salary Slip (Additional Salary) (#18647)
* feat: employee incentive and retention bonus added in additional salary

* fix: added salary component field, logic improved

* fix: codacy review
2019-09-03 20:45:52 +05:30
Sahil Khan
2691991d9a Merge branch 'develop' into version-12 2019-09-03 16:33:06 +05:30
Sahil Khan
e8b1c82531 bumped to version 12.1.0 2019-09-03 16:53:06 +05:50
Saurabh
67e4186360 Merge pull request #18909 from sahil28297/changelog_v12_1_0
fix(change_log): add v12_1_0 changelog
2019-09-03 16:26:07 +05:30
Saurabh
3f8f8d36b7 Merge branch 'develop' into changelog_v12_1_0 2019-09-03 16:25:44 +05:30
Sahil Khan
a70e2bdbc9 fix(change_log): add v12_1_0 changelog 2019-09-03 16:20:01 +05:30
Nabin Hait
1ab75db0ac refactor: Accounts Receivable / Payable report (#18906) 2019-09-03 16:07:46 +05:30
Nabin Hait
e85c320501 Merge branch 'develop' into feat-customer-credit-limit 2019-09-03 14:20:17 +05:30
Mangesh-Khairnar
cb44f3a7c3 fix(purchase-invoice): add rounded total property setter for purchase invoice (#18841) 2019-09-03 14:18:15 +05:30
Deepesh Garg
c174e4d01a fix: Default message from Payment Gateway Account not fetching (#18848) 2019-09-03 14:17:41 +05:30
Rohan
7fa3f3fe98 fix: include start and end date for contract status (#18866) 2019-09-03 14:16:12 +05:30
Mangesh-Khairnar
4bcc221ee3 Merge branch 'develop' of https://github.com/frappe/erpnext into feat-customer-credit-limit 2019-09-02 23:18:56 +05:30
Mangesh-Khairnar
cf901da25d test: create customer credit limit on change 2019-09-02 23:18:36 +05:30
Suraj Shetty
496f8e966f Merge pull request #18889 from deepeshgarg007/contacts-ref
fix: Travis
2019-09-02 18:32:28 +05:30
deepeshgarg007
4dd8895133 Merge branch 'contacts-ref' of https://github.com/deepeshgarg007/erpnext into contacts-ref 2019-09-02 17:42:27 +05:30
deepeshgarg007
8666ecc26f fix: Purchase receipt test 2019-09-02 17:41:12 +05:30
Suraj Shetty
152360d999 Merge branch 'develop' into contacts-ref 2019-09-02 16:24:57 +05:30
Mangesh-Khairnar
e7c7a0e648 fix: loan application (#18882)
* fix: loan application

* Update loan_application.py
2019-09-02 15:59:44 +05:30
Nabin Hait
4d553b7a84 Merge branch 'develop' into contacts-ref 2019-09-02 15:58:06 +05:30
Himanshu
fffdb6f575 feat(Contacts): Multiple Emails in a Contact (#18675)
* feat: render multiple addresses

* feat: move to newer contacts structure

* fix: iterate over valid variable

* fix: use primary label instead of bold letters

* fix: call popup get contact name from number

* fix: make contact structure  call popup compatible

* fix: query

* fix: add city, state and country

* fix: display address

* fix: get address in single line

* fix: review fixes

* fix: translation strings

* fix: fix query for contacts

* fix: remove references of mobile_no
2019-09-02 15:57:45 +05:30
Suraj Shetty
063144c514 fix: Check in_patch before adding 'All Item Group' 2019-09-02 15:53:28 +05:30
deepeshgarg007
402d82b4c5 fix: Remove delete_doc from tests 2019-09-02 14:37:18 +05:30
Himanshu Warekar
711d1acffd fix: remove references of mobile_no 2019-09-02 13:31:10 +05:30
Himanshu Warekar
81472e4c08 Merge branch 'contacts-ref' of https://github.com/hrwx/erpnext into contacts-ref 2019-09-02 13:21:29 +05:30
Himanshu Warekar
b8f23c2657 fix: fix query for contacts 2019-09-02 13:20:27 +05:30
Suraj Shetty
f33dfc2121 Merge branch 'develop' into contacts-ref 2019-09-02 12:38:45 +05:30
Deepesh Garg
e26b55265f Merge pull request #18840 from netchampfaris/missing-parent-item-group
fix: Set default Parent Item Group
2019-09-02 12:22:49 +05:30
Himanshu Warekar
26dfd5b314 fix: translation strings 2019-09-02 12:21:41 +05:30
Himanshu Warekar
e31c6964f3 Merge branch 'contacts-ref' of https://github.com/hrwx/erpnext into contacts-ref 2019-09-02 12:11:15 +05:30
Himanshu Warekar
fd85b1689d fix: review fixes 2019-09-02 12:10:15 +05:30
Suraj Shetty
4a8710ef75 Merge pull request #18611 from surajshetty3416/fix-paid-amount
fix: Paid amount 0 while creating advanced payment entry
2019-09-02 08:38:34 +05:30
Suraj Shetty
58e6b67886 Merge pull request #18613 from surajshetty3416/fix-timesheet-creation
fix(timesheet): Hours automatically used to set 0
2019-09-02 08:38:12 +05:30
Suraj Shetty
f268562256 Merge branch 'develop' into contacts-ref 2019-09-02 06:32:11 +05:30
Mangesh-Khairnar
86720deeae fix: bypass credit limit check 2019-09-01 10:15:23 +05:30
Suraj Shetty
ae587dbd83 Merge pull request #18524 from surajshetty3416/feature-pick-list
feat: Pick List
2019-08-31 19:44:45 +05:30
Suraj Shetty
72bea0dff4 test: Add test to check creation of pick list from multiple sales order 2019-08-31 18:34:25 +05:30
Suraj Shetty
736b5e07cc fix: Maintain the order of Item List 2019-08-31 18:33:23 +05:30
Suraj Shetty
ca58fde552 test: Enable basic tests 2019-08-31 16:58:51 +05:30
Mangesh-Khairnar
bb3cec1556 test: fetch data from customer credit limit 2019-08-31 14:32:07 +05:30
Mangesh-Khairnar
42d0da8f5a Revert "fix: process allocation expiry"
This reverts commit b654dc0e28.
2019-08-31 14:28:10 +05:30
Mangesh-Khairnar
dbc69da409 fix: minor fixes 2019-08-31 14:28:02 +05:30
Mangesh-Khairnar
e3bb247868 fix: check column in credit limit 2019-08-31 13:16:14 +05:30
Mangesh-Khairnar
f856b3b559 fix: fetch customer group of the customer 2019-08-31 01:40:58 +05:30
Mangesh-Khairnar
89433b4bea fix: get credit limit 2019-08-30 22:57:51 +05:30
Suraj Shetty
bcfec77e2c style: Use single quotes 2019-08-30 19:44:37 +05:30
Suraj Shetty
744b92d233 fix: Commonify item not available alert
- Reorganise code
- UX fixes
2019-08-30 19:39:28 +05:30
Suraj Shetty
0eed0a9abe test: Temporarily comment out tests 2019-08-30 19:12:16 +05:30
Mangesh-Khairnar
b3e5d11e1d fix: multiple fixes 2019-08-30 18:18:48 +05:30
Suraj Shetty
0df38891a1 fix: Update pick list print format 2019-08-30 15:59:35 +05:30
Suraj Shetty
f75481fa23 Merge branch 'develop' of github.com:frappe/erpnext into feature-pick-list 2019-08-30 15:45:18 +05:30
Suraj Shetty
5e84ce55ae fix: Add is_stock_item filter for item in locations table 2019-08-30 10:01:49 +05:30
Suraj Shetty
effe53d4ae fix: Set default value for qty 2019-08-30 09:52:08 +05:30
Suraj Shetty
88885184dc fix: Show separate button for pick list creation in work order 2019-08-30 09:30:18 +05:30
Suraj Shetty
9641edc562 fix: Set item locations before save 2019-08-29 22:23:13 +05:30
Suraj Shetty
9b42682575 fix: Check parent warehouse for batch as well 2019-08-29 21:14:26 +05:30
Mangesh-Khairnar
dcd5be0d07 patch: move credit limit in customer to child table 2019-08-29 20:53:51 +05:30
Mangesh-Khairnar
c059bc3e36 fix: grid view of customer credit limit 2019-08-29 20:51:31 +05:30
Deepesh Garg
52c61904c8 Merge pull request #18870 from rohitwaghchaure/not_able_to_save_sales_order_develop
fix: not able to save sales order
2019-08-29 20:32:06 +05:30
Suraj Shetty
a6ab00162e style: Remove commented code 2019-08-29 20:17:04 +05:30
Suraj Shetty
9e4282e130 Merge branch 'develop' of github.com:frappe/erpnext into feature-pick-list 2019-08-29 20:09:55 +05:30
Rohit Waghchaure
13c7e183a6 fix: not able to save sales order 2019-08-29 20:03:52 +05:30
Mangesh-Khairnar
5755d2d32f fix: customer credit limit report 2019-08-29 19:51:38 +05:30
Mangesh-Khairnar
79525327f0 feat: bypass credit limit check 2019-08-29 19:50:23 +05:30
Suraj Shetty
3e11338ed5 fix: Validate count of serial numbers 2019-08-29 19:46:49 +05:30
Mangesh-Khairnar
233ee277ef Merge pull request #18853 from Mangesh-Khairnar/fix-allocation-expiry
fix: process allocation expiry
2019-08-29 18:29:07 +05:30
Mangesh-Khairnar
36b30911a8 feat: customer credit limit 2019-08-29 18:06:23 +05:30
Suraj Shetty
acd00df8fb Merge branch 'develop' of github.com:frappe/erpnext into feature-pick-list 2019-08-29 17:24:23 +05:30
Suraj Shetty
ed1ec82d2f refactor: Item picking logic
- Fix serial number selection
- Get limited item location based on required qty
- Store total item count to properly track available locations
- Pass missing serial no.
2019-08-29 17:23:09 +05:30
Mangesh-Khairnar
232b5dab81 Merge pull request #18854 from ruchamahabal/fixes
fix: exception in Shopify Settings
2019-08-29 16:33:46 +05:30
Deepesh Garg
dbe8dab3ce Merge pull request #18794 from deepeshgarg007/supplier_items
fix: Enhancement in Purchase Order
2019-08-29 16:29:02 +05:30
Rucha Mahabal
f5b2db76cb Merge branch 'develop' into fixes 2019-08-29 13:32:30 +05:30
Suraj Shetty
1c29c520bd Merge branch 'develop' of github.com:frappe/erpnext into feature-pick-list 2019-08-29 13:18:57 +05:30
Mangesh-Khairnar
2f322609d7 Merge pull request #18852 from mbhavesh95863/patch-1
fix(selling): remove redundant listing
2019-08-29 13:12:38 +05:30
Mangesh-Khairnar
74c7b04b29 Merge branch 'develop' into fixes 2019-08-29 12:31:38 +05:30
rohitwaghchaure
c20e66e0be Merge pull request #18860 from rohitwaghchaure/added_purchase_invoice_in_buying_module
fix: added purchase invoice in buying module
2019-08-29 12:13:50 +05:30
rohitwaghchaure
445a93e5f5 Merge pull request #18859 from rohitwaghchaure/incorrect_valuation_rate_calculated_for_serial_no_develop
fix: incorrect valuation rate calculated because of string replacement
2019-08-29 12:13:02 +05:30
Suraj Shetty
66f2bc69a6 fix: Item mapping of stock entry with no reference 2019-08-29 09:23:31 +05:30
Suraj Shetty
55a2699f4c fix: Update dashboard of doctypes that are linked with pick list 2019-08-29 09:14:27 +05:30
Rohit Waghchaure
354d0af44e fix: added purchase invoice in buying module 2019-08-28 17:51:31 +05:30
Suraj Shetty
f455c92d02 fix: Remove Pick List Reference Item use Item locations table instead 2019-08-28 17:44:22 +05:30
Mangesh-Khairnar
b654dc0e28 fix: process allocation expiry 2019-08-28 17:22:56 +05:30
Rohit Waghchaure
d03d8204ab fix: incorrect valuation rate calculated because of string replacement issue 2019-08-28 17:22:50 +05:30
Rucha Mahabal
1707c3da95 fix: exception
Co-Authored-By: Himanshu <himanshuwarekar@yahoo.com>
2019-08-28 13:55:26 +05:30
Rucha Mahabal
b606d4d2ad Merge branch 'develop' into fixes 2019-08-28 13:50:31 +05:30
Rucha Mahabal
9fa5dbd6e4 fix: raised exception in shopify 2019-08-28 13:29:03 +05:30
Suraj Shetty
1cf7270049 fix: Add picklist dashboard config 2019-08-28 12:40:58 +05:30
Suraj Shetty
be0ae7a430 fix: Doctype changes
- Check no copy for work order series field
- Add dashboard
- Set naming_series for pick list
2019-08-28 12:40:26 +05:30
Shivam Mishra
0aeccbf4b2 feat: added dashboard fixtures (#18812)
* feat: add dashboard charts fixture

* fix: remove return statement

* feat: added patch for creating default dashboards

* chore: renamed dashboard charts

* feat: add add_dashboard function to install fixtures

* fix: reload doctype issue in patches

* fix (travis): reloaded dashboard chart source

* fix (travis): reloaded dashboard chart source

* fix (travis): reloaded dashboard doctype

* fix (travis): reloaded dashboard chart link doctype
2019-08-28 11:39:45 +05:30
Suraj Shetty
8f32ac0edd fix: Batch selection logic 2019-08-28 10:16:20 +05:30
Himanshu Warekar
a5b78f3c0d fix: get address in single line 2019-08-28 00:04:05 +05:30
Mangesh-Khairnar
671c20ec56 Merge branch 'develop' into patch-1 2019-08-27 22:42:35 +05:30
Mangesh-Khairnar
17d3de1821 fix: process allocation expiry 2019-08-27 22:37:12 +05:30
mbhavesh95863
cfec328c74 Same report 2 times in list 2019-08-27 19:17:19 +05:30
Suraj Shetty
c5e0838890 fix: Import get_conversion factor method 2019-08-27 12:14:17 +05:30
Suraj Shetty
974ac3e6ad fix: Update item detail for items without reference 2019-08-27 10:17:16 +05:30
Suraj Shetty
dc675b1eb0 fix: Re-order stock qty field 2019-08-27 08:06:22 +05:30
Himanshu Warekar
9057239c3c fix: display address 2019-08-26 22:40:54 +05:30
Suraj Shetty
d6be8989e4 fix: Remove "Material Issue" purpose from pick list
- Because in material issue we already define source warehouse
2019-08-26 22:11:49 +05:30
Faris Ansari
8ac2a2f0c4 fix: Set default Parent Item Group 2019-08-26 13:00:17 +05:30
Himanshu Warekar
1c538b9b43 Merge branch 'develop' of https://github.com/frappe/erpnext into contacts-ref 2019-08-26 12:51:51 +05:30
Himanshu Warekar
ba6fe6cde5 Merge branch 'contacts-ref' of https://github.com/hrwx/erpnext into contacts-ref 2019-08-26 12:49:45 +05:30
Himanshu Warekar
7243e774c2 fix: add city, state and country 2019-08-26 12:49:20 +05:30
Shivam Mishra
db3bb793e9 feat: added domain info on footer (#18839) 2019-08-26 11:29:18 +05:30
Suraj Shetty
8de8a78235 Merge branch 'develop' of github.com:frappe/erpnext into feature-pick-list 2019-08-26 10:51:12 +05:30
Mangesh-Khairnar
5dd1b50802 fix: update show in website on disabling item (#18831) 2019-08-26 10:27:25 +05:30
Suraj Shetty
00f9930fbf style: Remove leftout print statements 2019-08-26 10:09:07 +05:30
Suraj Shetty
457da47dba fix: set for_qty instead of pick_list 2019-08-26 10:05:35 +05:30
Suraj Shetty
2b9e256002 fix: Rename method name 2019-08-26 10:05:01 +05:30
Suraj Shetty
a1aa85712b Merge branch 'develop' into fix-timesheet-creation 2019-08-26 10:01:45 +05:30
Suraj Shetty
05f243590d fix: Show option to create pick list or work order 2019-08-26 09:29:31 +05:30
Suraj Shetty
94d7096c8c fix: Show create button only if target doc does not exists 2019-08-26 08:40:02 +05:30
Suraj Shetty
ecc801d3d8 fix: Add pick list field to delivery note 2019-08-26 08:39:11 +05:30
Suraj Shetty
be9f4ea487 fix: Add button to create pick list from material request 2019-08-26 08:38:37 +05:30
Suraj Shetty
a1dc152695 fix: Move get items location button below items table 2019-08-26 06:57:43 +05:30
Suraj Shetty
9209570937 feat: Add option to create pick list from material request 2019-08-26 06:33:27 +05:30
Nabin Hait
d8c262fd5c fix: Translations of strings (#18825) 2019-08-23 16:32:58 +05:30
Mangesh-Khairnar
fe579c2efd fix: show a descriptive message on submission of duplicate account (#18486)
* fix: show a descriptive message on submission of duplicate account

* Update account.py
2019-08-23 16:31:20 +05:30
Mangesh-Khairnar
d94a389dd3 chore: remove unwanted code (#18645) 2019-08-23 16:31:09 +05:30
Deepesh Garg
98b86ecbc2 Merge branch 'develop' into supplier_items 2019-08-23 15:41:30 +05:30
Himanshu
dc0fb08ec7 Merge branch 'develop' into contacts-ref 2019-08-23 15:03:03 +05:30
Tufan Kaynak
a7ab51c5ba Update vehicle_expenses.py (#18768) 2019-08-23 12:50:52 +05:30
deepeshgarg007
59432418c6 fix: Consider multiple stock entry against a purchase order 2019-08-23 12:45:48 +05:30
Nabin Hait
6e7b9b5cb7 Update sales_invoice.py 2019-08-23 12:27:05 +05:30
Suraj Shetty
8b4d604cfd fix: Use purpose field and remove item_base_on field 2019-08-23 11:57:16 +05:30
Suraj Shetty
4affe4b939 Merge branch 'develop' into fix-timesheet-creation 2019-08-23 11:51:59 +05:30
Michelle Alva
c890401fec fix: added payroll period in HR module (#18543) 2019-08-23 11:50:48 +05:30
Suraj Shetty
7f94a58bf1 Merge branch 'develop' into fix-timesheet-creation 2019-08-23 11:46:01 +05:30
Deepesh Garg
f3d78dd29c fix: Duplicate items check in Sales Invoice (#18660)
* fix: Duplicate items check in sales Invoice

* fix: Commonified function for duplicate items check in selling controller

* fix: Set valuation rate and transaction date in child tabel
2019-08-23 11:42:35 +05:30
KanchanChauhan
23b5f4ec99 fix: Leave Application status filter (#18770)
When we click on Status Open in list view it throws an error.


After fix, it filters the results on Open status
2019-08-23 11:40:09 +05:30
Nabin Hait
bdfd69a2fe Merge branch 'develop' into contacts-ref 2019-08-23 11:34:42 +05:30
Harshit
56d03a456b fix: add contract to CRM module (#18817) 2019-08-23 11:34:25 +05:30
Michelle Alva
680e098b87 fix(dash): Added Tax exemption category and sub category in Employee Tax and Benefits (#18545)
section
2019-08-23 11:32:43 +05:30
Anurag Mishra
db88476f8b feat: refactor invoice_discounting (#18629)
* feat: refactor invoice_discountig

* Update invoice_discounting.py

* Update invoice_discounting.js
2019-08-23 11:27:00 +05:30
rohitwaghchaure
88ee7d8dbe fix: POS Sync Issue (#18807) 2019-08-23 11:13:58 +05:30
Suraj Shetty
6689ed543a Merge branch 'develop' into fix-paid-amount 2019-08-23 10:42:23 +05:30
deepeshgarg007
f2798eab50 fix: Conside multiple stock entry against a purchase order 2019-08-23 10:07:52 +05:30
Anurag Mishra
210317c0b5 fix: division by zero in asset Depereciation (#18637)
* fix: division by zero in asset Depereciation

* fix: requested changes
2019-08-23 00:21:26 +05:30
Himanshu Warekar
362c89ca73 Merge branch 'develop' of https://github.com/frappe/erpnext into contacts-ref 2019-08-22 17:29:38 +05:30
Suraj Shetty
687b1a5b1f fix: Make pick list submittable and add few fields
- Add material request & item fields
- Add pick_list field to Stock Entry
- Add purpose field to pick list
2019-08-22 16:41:14 +05:30
Suraj Shetty
8d55f81baa fix: Fix raw matterial selection based on finished item qty 2019-08-22 16:37:44 +05:30
Sahil Khan
7ff82fccf3 Merge branch 'develop' into version-12 2019-08-22 13:10:17 +05:30
Sahil Khan
cd25d6dc7f bumped to version 12.0.8 2019-08-22 13:30:17 +05:50
Suraj Shetty
c1f25ff9e3 fix: Add option to select qty of finished goods Item 2019-08-22 09:53:44 +05:30
Himanshu Warekar
447134d308 Merge develop into contacts-ref 2019-08-22 09:21:30 +05:30
rohitwaghchaure
224d857928 Merge pull request #18703 from rohitwaghchaure/reconciled_entry_still_has_no_clearance_date_develop
fix: reconciled entry has not clearance date set
2019-08-21 23:36:06 +05:30
rohitwaghchaure
a23fc327df Merge pull request #18785 from rohitwaghchaure/payment_recon_for_debit_entry_not_working_properly_develop
fix: debit note not reconciled with another purchase invoice using pa…
2019-08-21 23:35:35 +05:30
Suraj Shetty
ec92486377 fix: Add option to create Stock Entry from Pick List 2019-08-21 22:10:27 +05:30
Anastes Mp
a6c6e02c49 Incorrect database table (#18558)
Fixed Unknow Column tax_type error on offline pos
2019-08-21 16:53:06 +05:30
Suraj Shetty
298d38cde3 test: Fix existing tests 2019-08-21 16:37:49 +05:30
Himanshu Warekar
81f20891c1 fix: query 2019-08-21 16:09:35 +05:30
Suraj Shetty
109a07b834 fix: Fix get_employees_with_number query
if the passed number is 7039392929 then it should match 
with the employee cell_number set as `7039392929, 0288382222`
2019-08-21 15:19:08 +05:30
Mangesh-Khairnar
5619db28cb fix: fetch capital work in progress as expense account (#18780) 2019-08-21 14:49:24 +05:30
Nabin Hait
bcb0f6038e fix: Single gl entry should only be considered once either in opening or closing entry (#18792) 2019-08-21 14:47:33 +05:30
Deepesh Garg
e9e0c0e7d4 fix: Minor fix in GSTR-1 report (#18797) 2019-08-21 14:40:35 +05:30
Suraj Shetty
e84de50147 fix: check if number exists after striping '0' (#18805)
fix: check if number exists after striping '0'
2019-08-21 14:22:59 +05:30
Himanshu Warekar
c6e02e2a74 fix: make contact structure call popup compatible 2019-08-21 13:36:41 +05:30
Himanshu Warekar
ea97a6cb5b Merge develop into contacts-ref 2019-08-21 13:19:22 +05:30
Suraj Shetty
da2a623e38 Merge branch 'develop' of github.com:frappe/erpnext into feature-pick-list 2019-08-21 11:48:27 +05:30
Suraj Shetty
6affeaa9c1 fix: check if number exists after striping '0'
- Absract number striping logic to separate method
- Rename a confusing variable name
- Remove leftout print statement
2019-08-21 09:14:56 +05:30
Suraj Shetty
d79a16c9f3 fix: Warehouse selection login
- Rename item_loactions -> locations, reference_items -> items
- Add customer and work_order field
- fix "Get Items" button UX
- fix get_pending_work_orders query

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2019-08-21 09:03:26 +05:30
rohitwaghchaure
d36ff39498 Merge pull request #18799 from scmmishra/cart-fix
fix: shopping cart item availability
2019-08-21 08:58:47 +05:30
Himanshu Warekar
9f4dc3fcd4 fix: call popup get contact name from number 2019-08-20 22:20:02 +05:30
Himanshu Warekar
128f5dbff1 Merge branch 'version-12-hotfix' of https://github.com/frappe/erpnext into contacts-ref 2019-08-20 20:38:18 +05:30
Mangesh-Khairnar
576f51d89e Merge pull request #18791 from Mangesh-Khairnar/fix-ledger-entry
fix: ledger entries
2019-08-20 19:57:50 +05:30
Shivam Mishra
eab5be1110 fix: shopping cart item availability 2019-08-20 19:31:54 +05:30
Mangesh-Khairnar
c9b6c9bb61 fix: calculate opening leave balance 2019-08-20 19:18:45 +05:30
Mangesh-Khairnar
6d549b03f1 Merge branch 'develop' into fix-ledger-entry 2019-08-20 17:58:44 +05:30
Saurabh
128db172f0 Merge pull request #18796 from sahil28297/merge_v12_hotfix_1
Merge version-12-hotfix into develop
2019-08-20 17:49:24 +05:30
Suraj Shetty
dd63b656c7 Merge branch 'develop' of github.com:frappe/erpnext into feature-pick-list 2019-08-20 16:59:43 +05:30
Sahil Khan
5f2c030ddc Merge branch 'version-12-hotfix' into merge_v12_hotfix_1 2019-08-20 16:22:49 +05:30
deepeshgarg007
9e6abc4948 fix: Test case fixes 2019-08-20 16:14:44 +05:30
Sahil Khan
bf2b712f4b Merge branch 'version-12-hotfix' into version-12 2019-08-20 16:00:26 +05:30
Sahil Khan
a8403cde16 bumped to version 12.0.7 2019-08-20 16:20:26 +05:50
deepeshgarg007
cb38cc96c3 fix: Enhancement in Purchase Order 2019-08-20 15:00:48 +05:30
Mangesh-Khairnar
79414a8d36 fix: fetch employee name on leave ledger creation 2019-08-20 14:45:57 +05:30
Mangesh-Khairnar
5cdda19494 fix: ledger entries after expiry 2019-08-20 14:45:57 +05:30
rohitwaghchaure
16dda1a991 fix: group by voucher consolidated showing incorrect data for deferred entries (#18779) 2019-08-20 12:37:32 +05:30
rohitwaghchaure
d5b4b1fdaf fix: group by voucher consolidated showing incorrect data for deferred entries (#18777) 2019-08-20 12:35:15 +05:30
Mangesh-Khairnar
b69595904a Merge pull request #18786 from Mangesh-Khairnar/payment-order-fetch-fix
fix: restrict the payment order to non received type payment entries
2019-08-20 12:21:24 +05:30
Suraj Shetty
5124b2806d Merge branch 'develop' of github.com:frappe/erpnext into feature-pick-list 2019-08-20 12:05:51 +05:30
Suraj Shetty
060ff62178 Merge branch 'feature-pick-list' of github.com:surajshetty3416/erpnext into feature-pick-list 2019-08-20 12:04:11 +05:30
Suraj Shetty
1a090432d9 fix: Quantity while creating pick list from work order
- Fix get_mapped_doc config to filter items
- Fix erroneous condition in get_mapped_doc used for creation of pick_list
in sales order

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2019-08-20 12:04:07 +05:30
Suraj Shetty
a251267dd7 fix: Quantity while creating pick list from work order
- Fix get_mapped_doc config to filter items
- Fix erroneous condition in get_mapped_doc used for creation of pick_list
in sales order
2019-08-20 12:03:03 +05:30
rohitwaghchaure
9ef7d5edaf Merge pull request #18789 from rohitwaghchaure/asset_pro_rata_cal_for_wdv_remaining_amt_develop
Asset pro rata cal for wdv remaining amt develop
2019-08-20 10:33:15 +05:30
Rohit Waghchaure
5d3dee206f fixed test cases and the logic for pro rata calculation 2019-08-20 10:30:56 +05:30
Rohit Waghchaure
1583925080 fix: Pro rata calculation is not working for WDV depreciation method 2019-08-20 10:30:38 +05:30
Mangesh-Khairnar
c97a7fb845 fix: restrict the payment order to non received type payment entries 2019-08-20 00:27:43 +05:30
Mangesh-Khairnar
becb89213f Merge pull request #18737 from Mangesh-Khairnar/fix-payment-order
fix: restrict the payment order to non received type payment entries
2019-08-20 00:13:32 +05:30
Rohit Waghchaure
1008e6e450 fix: debit note not reconciled with another purchase invoice using payment reconciliation 2019-08-19 20:27:15 +05:30
Mangesh-Khairnar
09ddc84c3a Merge pull request #18774 from deepeshgarg007/test_case_fix
fix: Failing sales and purchase return test cases
2019-08-19 19:20:52 +05:30
Deepesh Garg
33b392ac2b Update erpnext/controllers/sales_and_purchase_return.py
Co-Authored-By: Mangesh-Khairnar <mkhairnar10@gmail.com>
2019-08-19 17:43:10 +05:30
Deepesh Garg
3965451c7a Update erpnext/controllers/sales_and_purchase_return.py
Co-Authored-By: Mangesh-Khairnar <mkhairnar10@gmail.com>
2019-08-19 17:40:29 +05:30
deepeshgarg007
0487ad5515 fix: Code cleanup 2019-08-19 16:40:29 +05:30
deepeshgarg007
e2acc748c8 fix: Check for return against delivery noteas well 2019-08-19 16:38:04 +05:30
Mangesh-Khairnar
4645727163 Merge branch 'develop' into fix-payment-order 2019-08-19 16:29:30 +05:30
deepeshgarg007
7d288437d8 fix: Assignment 2019-08-19 16:19:48 +05:30
deepeshgarg007
c80e5fe7a1 fix: Failing sales and purchase return test cases 2019-08-19 14:38:15 +05:30
Deepesh Garg
5efedd7a60 fix: Travis (#18772) 2019-08-19 12:56:22 +05:30
Deepesh Garg
960a1cbd8f fix: Party dashboard heatmap not capturing sales, purchase and other activities (#18753) 2019-08-19 11:51:16 +05:30
Suraj Shetty
6450be5e58 fix: Get Items button 2019-08-19 10:48:21 +05:30
Suraj Shetty
669cff88d1 fix: Get items button 2019-08-19 10:38:01 +05:30
Anurag Mishra
19c3cb0d5b fix: removed filters(not required) (#18729) 2019-08-19 10:31:02 +05:30
Anurag Mishra
bc5712a1b3 fix: validated cost center in financial_statement (#18733)
* fix: validated cost center in financial_statement

* Update financial_statements.py
2019-08-19 10:24:44 +05:30
Mangesh-Khairnar
0df513434e fix: valuation rate in stock ledger (#18744)
* fix: valuation rate in stock ledger

* test: allow zero valuation rate for items
2019-08-19 10:04:52 +05:30
Karthikeyan S
d5e5e22adb Merge pull request #18523 from Vigneshsekar/attendance_grace_period
feat(Auto Attendance): Add grace period
2019-08-18 13:25:48 +05:30
Deepesh Garg
77ec3cf402 Merge pull request #18757 from deepeshgarg007/accounting_dimension_fix
fix: Default dimensions in child doctypes
2019-08-16 17:27:14 +05:30
deepeshgarg007
0a2ed6da37 fix: Add missing semicolon 2019-08-16 15:50:17 +05:30
Deepesh Garg
6e80cbfd1e Merge pull request #18761 from deepeshgarg007/symbol_fix_develop
fix: Symbol fix in chart of accounts
2019-08-16 15:48:17 +05:30
Faris Ansari
ac3579d2c6 Merge pull request #17624 from Mangesh-Khairnar/leave-management
feat: Carry Forward Leave Expiry
2019-08-16 15:39:24 +05:30
deepeshgarg007
8d0b6f9a60 fix: Handling if no default dimension exists 2019-08-16 14:00:26 +05:30
deepeshgarg007
42d9298318 fix: Remove extra space 2019-08-16 13:06:47 +05:30
Mangesh-Khairnar
4b71d9ca9f Merge branch 'develop' into fix-payment-order 2019-08-16 12:42:26 +05:30
Suraj Shetty
ec1fe9e2ca Merge branch 'develop' of github.com:frappe/erpnext into feature-pick-list 2019-08-16 08:17:26 +05:30
Suraj Shetty
182f4def00 fix: Delivery note creation from pick list
- Changes in serial no and batch no seletion
- Changes in warehouse overrwite logic

Co-authored-by: Nabin Hait <nabinhait@gmail.com>
2019-08-16 08:16:22 +05:30
deepeshgarg007
2fb6bc9867 fix: Default dimensions in child doctypes 2019-08-15 17:06:32 +05:30
Deepesh Garg
98a6e5cb6c Merge pull request #18742 from rohitwaghchaure/incorrect_sequnce_between_name_and_contact
fix: sequence of customer name and contact in the AR report
2019-08-14 23:20:55 +05:30
Rohit Waghchaure
c5d41af10f fix: sequence of customer name and contact in the AR report 2019-08-14 18:49:19 +05:30
Mangesh-Khairnar
dbb44c8950 fix: restrict the payment order to non received type payment entries 2019-08-14 17:38:44 +05:30
Mangesh-Khairnar
ae2a0fb4c7 chore: remove unused code 2019-08-14 16:50:31 +05:30
Mangesh-Khairnar
2e1d7cbdc2 Merge pull request #18736 from Mangesh-Khairnar/fix-travis
fix: travis
2019-08-14 16:33:34 +05:30
Mangesh-Khairnar
ca55af836b fix: travis 2019-08-14 16:32:02 +05:30
Mangesh-Khairnar
3a42631e65 Merge branch 'develop' of https://github.com/frappe/erpnext into leave-management 2019-08-14 16:11:08 +05:30
Mangesh-Khairnar
107b2768fd refactor: replace raw sql with orm 2019-08-14 16:09:16 +05:30
Anurag Mishra
78690d7b8b fix:payment ammount validation for pos invoices (#18663) 2019-08-14 15:03:58 +05:30
Mangesh-Khairnar
760b078dc9 fix(payroll-entry): commit submitted salary slip check on change (#18694)
* fix(payroll-entry): commit submitted salary slip check onchange

* fix: track submitted ss via flags
2019-08-14 14:40:00 +05:30
Deepesh Garg
2c5dcbe819 fix: Error handling in payment entry (#18720) 2019-08-14 14:26:37 +05:30
Mangesh-Khairnar
06ce1f5a40 fix(quality-inspection): fetch all items for inspection type in process (#18716)
* fix(quality-inspection): fetch all items for inspection type in process

* fix(quality-inspection): add server side validation for in process items
2019-08-14 14:25:59 +05:30
Vignesh S
4454630549 feat(Auto Attendance): Add grace period
Co-authored-by: Karthikeyan S <skarthikeyan1410@gmail.com>
2019-08-14 13:40:02 +05:30
Deepesh Garg
612b0ff9cd Merge pull request #18719 from Anurag810/company_fix_v13
fix: removed hard coded string
2019-08-14 12:12:26 +05:30
Deepesh Garg
5a7f26f4d2 Merge pull request #18717 from Anurag810/company_fix
fix: removed hard coded string form company
2019-08-14 12:11:33 +05:30
Anurag Mishra
de20b083a0 Merge branch 'develop' into company_fix_v13 2019-08-14 12:10:02 +05:30
Anurag Mishra
904cbef4dc fix: removed hard coded string 2019-08-13 19:48:42 +05:30
Anurag Mishra
81d5265385 fix: removed hard coded string 2019-08-13 19:40:36 +05:30
Sagar Vora
33d00bfeae fix: v12 patches sequence (#18610) 2019-08-13 19:39:48 +05:30
rohitwaghchaure
4d7a0aaee1 Merge pull request #18705 from surajshetty3416/fix-payment-entry-account-permission
fix: Check if account passed is accessible under Payment Entry
2019-08-13 18:37:17 +05:30
Sagar Vora
e14a00b887 fix: v12 patches sequence (#18609) 2019-08-13 17:26:56 +05:30
Sahil Khan
77ec5cc8d5 Merge branch 'version-12-hotfix' into version-12 2019-08-13 14:44:18 +05:30
Sahil Khan
f841afd48d bumped to version 12.0.6 2019-08-13 15:04:18 +05:50
Mangesh-Khairnar
dab5b1f319 Merge branch 'develop' of https://github.com/frappe/erpnext into leave-management 2019-08-13 13:33:26 +05:30
Mangesh-Khairnar
8b9b77959d fix: fetch min date when carry forward expiry is greater than leave allocation expiry 2019-08-13 13:20:10 +05:30
Anurag Mishra
d2f13fe0a6 fix: query (#18709) 2019-08-13 13:19:24 +05:30
Suraj Shetty
469e430d38 Merge branch 'fix-payment-entry-account-permission' of github.com:surajshetty3416/erpnext into fix-payment-entry-account-permission 2019-08-13 12:12:03 +05:30
Suraj Shetty
64a962ce97 fix: Re-organise code 2019-08-13 12:10:00 +05:30
Suraj Shetty
1a2600c9ea fix: Ignore account permission check 2019-08-13 12:09:06 +05:30
Himanshu
7df50b6ec7 fix(QMS): TreeView fixes (#18595)
* fix: TreeView fixes

* test: test case fix
2019-08-13 11:58:42 +05:30
Suraj Shetty
80afee04a4 fix: Set address while creating Opportunity from Lead (#18702)
* fix: Set address while creating Opportunity from Lead

* fix: Setting of address in opportunity from Lead
2019-08-13 10:58:29 +05:30
Suraj Shetty
bd2e7c0e53 fix: Comment description 2019-08-12 16:32:14 +05:30
Suraj Shetty
3234f0d299 fix: Check if account passed is accessible under Payment Entry 2019-08-12 16:18:36 +05:30
Faris Ansari
9002a6c195 Merge pull request #18353 from surajshetty3416/refactor-call-popup
fix(call popup): Multiple changes
2019-08-12 15:56:59 +05:30
Faris Ansari
9eda500dbc Merge branch 'develop' into refactor-call-popup 2019-08-12 15:56:35 +05:30
Rohit Waghchaure
fb23773935 fix: reconciled entry has not clearance date set 2019-08-12 15:35:19 +05:30
Frappe PR Bot
037caf096b feat: Updated translation (#18597) 2019-08-12 15:32:37 +05:30
Suraj Shetty
f81b6c7cfb fix: Set address while creating Opportunity from Lead (#18700) 2019-08-12 13:05:22 +05:30
DeeMysterio
1c728a7cf8 fix(delivery note): change the text invoice to sales invoice on make button (#18658) 2019-08-12 13:04:25 +05:30
DeeMysterio
cfce53103b fix(delivery note): change the text invoice to sales invoice on make button (#18666) 2019-08-12 13:03:55 +05:30
Michelle Alva
af969d664f Added Employee Tax Exxxemption category and sub-category links (#18659) 2019-08-12 12:59:59 +05:30
Himanshu
19199baf29 fix: miscellaneous fixes (#18615) 2019-08-12 12:17:28 +05:30
Himanshu
ebf38c5ebd fix: misc fixes (#18616) 2019-08-12 12:17:16 +05:30
Andrew McLeod
c97ffaeac3 fix: Python3 urllib use in item_group.py (now uses six.moves) (#18643) 2019-08-12 12:06:30 +05:30
Andrew McLeod
677c522f01 fix: Python3 urllib use in item_group.py (now uses six.moves) (#18642) 2019-08-12 12:06:23 +05:30
Shivam Mishra
8363a6e585 refactor: remove from date and to date from standard filter (#18696) 2019-08-12 11:58:14 +05:30
Suraj Shetty
83705af0b3 fix: Filters for portal quotation list (#18689)
* fix: Filters for portal quotation list

* fix: Remove unwanted import
2019-08-12 11:51:27 +05:30
sahil28297
214815eb62 fix(patch): force reload child docs (#18672) 2019-08-12 11:49:21 +05:30
sahil28297
a0b9b3cef5 fix(patch): force reload child docs (#18671) 2019-08-12 11:49:14 +05:30
Deepesh Garg
cd7a89da32 Merge pull request #18691 from deepeshgarg007/gstr-3b-non-gst-v12
fix: GSTR 3B report fixes
2019-08-11 19:50:44 +05:30
Deepesh Garg
43dc351209 Merge pull request #18692 from deepeshgarg007/gstr-3b-non-gst-develop
fix: GSTR 3B report fixes
2019-08-11 19:50:29 +05:30
deepeshgarg007
9db6471fae fix: Test Case 2019-08-11 17:29:09 +05:30
deepeshgarg007
4b28b3216b fix: Test Cases 2019-08-11 17:28:55 +05:30
deepeshgarg007
db01743885 fix: Test Case 2019-08-11 15:47:35 +05:30
deepeshgarg007
b87c5d83de fix: Test Cases 2019-08-11 12:40:45 +05:30
Deepesh Garg
8f706399a0 Merge pull request #18631 from netchampfaris/fix-item-template-description
fix(Item Template): Fallback description string
2019-08-11 11:20:46 +05:30
deepeshgarg007
c36abbcda3 fix: GSTR 3B report fixes 2019-08-11 11:01:02 +05:30
deepeshgarg007
dabcb6b531 fix: GSTR 3B report fixes 2019-08-11 10:58:16 +05:30
Deepesh Garg
1fb21cd9e5 Merge branch 'version-12-hotfix' into fix-item-template-description 2019-08-10 17:36:00 +05:30
Deepesh Garg
e6b076cb34 Merge pull request #18632 from netchampfaris/fix-item-template-description-fp
fix(Item Template): Fallback description string
2019-08-10 17:33:59 +05:30
Deepesh Garg
7f0f0d0559 Merge pull request #18685 from marination/fixes_v12_hotfix
fix: Fixed error message in Payment Entry for outstanding invoices not found via filters
2019-08-10 17:27:45 +05:30
Deepesh Garg
0b711d1f8a Merge pull request #18684 from marination/fixes_v12
fix: Fixed error message in Payment Entry for outstanding invoices not found via filters
2019-08-10 17:26:54 +05:30
Suraj Shetty
3f7a757e80 Merge branch 'refactor-call-popup' of github.com:surajshetty3416/erpnext into refactor-call-popup 2019-08-09 19:23:09 +05:30
Suraj Shetty
d4edd284e6 fix: Set Contact or Lead for call log
- Set contact or lead to call log on new Contact or Lead creation
2019-08-09 19:23:04 +05:30
Suraj Shetty
b282f1f154 Merge branch 'develop' into refactor-call-popup 2019-08-09 18:18:17 +05:30
Himanshu Warekar
3fbfac64c2 Merge contacts-ref into contacts-ref 2019-08-09 17:51:14 +05:30
Himanshu Warekar
12fbecf48b fix: use primary label instead of bold letters 2019-08-09 17:50:03 +05:30
Himanshu
59a6821299 Merge branch 'version-12-hotfix' into contacts-ref 2019-08-09 16:52:39 +05:30
marination
9839a9afb0 fix: Fixed error message in Payment Entry for outstanding invoices not found via filters 2019-08-09 15:54:18 +05:30
marination
4583100537 fix: Fixed error message in Payment Entry for outstanding invoices not found via filters 2019-08-09 15:30:05 +05:30
Deepesh Garg
ca5fdeb9bb Merge pull request #18683 from Mangesh-Khairnar/fix-translation-test
test: Translation in search
2019-08-09 15:29:33 +05:30
rohitwaghchaure
5790fabd54 Merge pull request #18669 from rohitwaghchaure/removed_stock_item_condition_for_sub_contract_v12
fix: allow to subcontract service raw materials
2019-08-09 15:18:38 +05:30
rohitwaghchaure
208eb05519 Merge pull request #18682 from Anurag810/get-item-from-product-bundle-v13
fix: get item from product bundle
2019-08-09 15:18:15 +05:30
rohitwaghchaure
ed6fb66a90 Merge pull request #18679 from Anurag810/get-item-from-product-bundle
fix: get item from product bundle
2019-08-09 15:17:42 +05:30
Mangesh-Khairnar
7c7e9ecfcd test: translation fix 2019-08-09 14:48:36 +05:30
Anurag Mishra
8d4b04e719 fix: get item from product bundle 2019-08-09 14:34:09 +05:30
Mangesh-Khairnar
e173d54054 Merge branch 'develop' of https://github.com/frappe/erpnext into leave-management 2019-08-09 13:37:51 +05:30
Anurag Mishra
24c3b4e00f fix: get item from product bundle 2019-08-09 13:27:59 +05:30
Mangesh-Khairnar
261d132f3a fix: calculate earned leaves based on annual allocation 2019-08-09 13:18:52 +05:30
Himanshu
fa3af74179 Merge pull request #18596 from hrwX/qms-fixes
fix(QMS): TreeView fixes
2019-08-09 11:53:23 +05:30
Himanshu
0184c981ee Merge branch 'version-12-hotfix' into contacts-ref 2019-08-09 11:15:28 +05:30
Suraj Shetty
e047de854b Merge branch 'develop' of github.com:frappe/erpnext into feature-pick-list 2019-08-09 11:14:14 +05:30
Himanshu
ffddcb0526 Merge branch 'version-12-hotfix' into qms-fixes 2019-08-09 11:06:36 +05:30
Himanshu Warekar
86f3310ac1 fix: iterate over valid variable 2019-08-09 11:05:04 +05:30
Himanshu Warekar
f94d183297 feat: move to newer contacts structure 2019-08-08 23:50:03 +05:30
Himanshu Warekar
224c2ddaf4 feat: render multiple addresses 2019-08-08 23:34:34 +05:30
Mangesh-Khairnar
3662ed50d2 fix: multiple changes 2019-08-08 19:47:17 +05:30
Suraj Shetty
7e818067eb Merge branch 'develop' into refactor-call-popup 2019-08-08 19:18:03 +05:30
Suraj Shetty
44b906a43d Merge branch 'refactor-call-popup' of github.com:surajshetty3416/erpnext into refactor-call-popup 2019-08-08 19:16:37 +05:30
Suraj Shetty
429bfcfd83 fix: Make requested changes 2019-08-08 19:16:32 +05:30
Rohit Waghchaure
10e8073204 fix: allow to subcotract service raw materials 2019-08-08 18:20:53 +05:30
Faris Ansari
99c26e068d fix: Set Maintenance Status fields as Read Only (#18634)
Maintenance Status is set based on warranty_expiry_date and
amc_expiry_date. Even if they are editable they are set programmatically
server side. Better to make them as read only.
2019-08-08 17:45:49 +05:30
Faris Ansari
cfd19afabf fix: Set Maintenance Status fields as Read Only (#18633)
Maintenance Status is set based on warranty_expiry_date and
amc_expiry_date. Even if they are editable they are set programmatically
server side. Better to make them as read only.
2019-08-08 17:45:44 +05:30
Mangesh-Khairnar
bafc89f439 refactor: convert raw sql to orm 2019-08-08 17:43:23 +05:30
rohitwaghchaure
9f9184c908 fix: not able to transfer raw materials for subcontracted items (#18650) 2019-08-08 17:41:38 +05:30
rohitwaghchaure
536e6bf57c fix: group by condition in the payment reconciliation (#18657) 2019-08-08 17:40:57 +05:30
Mangesh-Khairnar
f3a5188bec fix: accounting period (#18477)
* fix: accounting period

* test: accounting period

* fix: account period creation

* fix: remove status field from accounting period
2019-08-08 17:39:13 +05:30
Mangesh-Khairnar
9bc4232af6 feat: calculate remaining leaves both multiple simultaneous allocation 2019-08-08 17:11:08 +05:30
Mangesh-Khairnar
5cbe6160ca feat: consider carry forwarded leaves on creation of encashment 2019-08-08 17:06:15 +05:30
Deepesh Garg
f2bf76a2ef fix: Show Cr or Dr symbol in chart of accounts based on balance (#18653)
* fix: Show Cr or Dr symbol in chart of accounts based on balance

* fix: Typo fix in comment
2019-08-08 15:52:39 +05:30
Deepesh Garg
f729eed035 fix: Show Cr or Dr symbol in chart of accounts based on balance (#18654)
* fix: Show Cr or Dr symbol in chart of accounts based on balance

* fix: Typo fix in comment
2019-08-08 15:52:25 +05:30
Deepesh Garg
065e8f3650 fix: Changes in print format due to attribute name changes in frappe (#18639) 2019-08-08 15:51:56 +05:30
Deepesh Garg
04b42600b0 fix: Changes in print format due to attribute name changes in frappe (#18641) 2019-08-08 15:51:50 +05:30
Faris Ansari
df7644a96d fix: Show created serial nos as links in message (#18635)
Fixes #18623
2019-08-08 15:50:24 +05:30
Faris Ansari
afae8a0c46 fix: Show created serial nos as links in message (#18636)
Fixes #18623
2019-08-08 15:50:17 +05:30
Aditya Hase
472050bb8a fix(quickbooks): Do not build global search for QuickBooks Migrator (#18628) 2019-08-08 15:48:35 +05:30
Aditya Hase
f19b7b9122 fix(quickbooks): Do not build global search for QuickBooks Migrator (#18627) 2019-08-08 15:48:09 +05:30
Mangesh-Khairnar
e5c733bdb3 fix: Accounting period (#18630)
* fix: accounting period

* test: accounting period

* fix: account period creation

* fix: remove status field from accounting period
2019-08-08 15:44:11 +05:30
Suraj Shetty
c7716f0bbc Merge branch 'develop' into refactor-call-popup 2019-08-08 12:50:20 +05:30
Himanshu Warekar
b9f2a6048b test: fix test cases 2019-08-07 18:21:38 +05:30
Faris Ansari
3623452839 fix(Item Template): Fallback description string
Fixes #18572
2019-08-07 17:21:51 +05:30
Faris Ansari
2260838933 fix(Item Template): Fallback description string
Fixes #18572
2019-08-07 17:21:22 +05:30
Himanshu
1b48448b7b Merge branch 'version-12-hotfix' into qms-fixes 2019-08-07 11:32:06 +00:00
Rushabh Mehta
6276f1adc5 fix(minor): don't update modified timestamp for overdue tasks 2019-08-07 16:32:44 +05:30
Sahil Khan
9335cdd536 Merge branch 'version-12-hotfix' into version-12 2019-08-07 16:21:14 +05:30
Sahil Khan
c5ae3cc120 bumped to version 12.0.5 2019-08-07 16:41:13 +05:50
Suraj Shetty
cab8e9be89 fix(timesheet): Hours automatically used to set 0
- Case: If the company had standard working hour set
and when the user creates a timesheet with same date for
"To" and "From" then the hours field automatically used to
get reset to 0 after saving the form.
2019-08-07 10:40:29 +05:30
Suraj Shetty
0c699f0726 fix: Paid amount 0 while creating advanced payment entry
Paid amount is set 0 while creating advanced payment entry
against multi-currency purchase order.

Solution: Populate paid amount value after applying conversion rate
2019-08-07 10:17:05 +05:30
Suraj Shetty
9f4b270116 fix: prev_doc 2019-08-06 09:03:23 +05:30
Suraj Shetty
4ca82f9308 fix: Show contact and lead name in list view 2019-08-06 05:49:01 +05:30
Suraj Shetty
207f218db3 Merge branch 'refactor-call-popup' of github.com:surajshetty3416/erpnext into refactor-call-popup 2019-08-06 05:44:28 +05:30
Suraj Shetty
89d8a0b6fd fix: reset_employee_emails_cache method 2019-08-06 05:44:13 +05:30
Himanshu
76c6a050af Merge branch 'version-12-hotfix' into qms-fixes 2019-08-05 17:12:44 +00:00
Deepesh Garg
235166ec41 Merge pull request #18592 from deepeshgarg007/utils_fix_v12
fix: Ambigious column in query
2019-08-05 22:38:45 +05:30
Suraj Shetty
f6f849226e Merge branch 'develop' into refactor-call-popup 2019-08-05 21:25:12 +05:30
Suraj Shetty
7d3f1fef1c fix: Employee selection for call popup
- Check if employee with matched number is also
 scheduled to receive popup
2019-08-05 21:21:45 +05:30
Mangesh-Khairnar
314647572c fix: check for old unexpired allocation 2019-08-05 15:35:19 +05:30
Mangesh-Khairnar
6bed870dfa feat: pro-rata leave allocation 2019-08-05 14:47:53 +05:30
Mangesh-Khairnar
f281f00d43 feat: auto leave encashment 2019-08-05 14:47:53 +05:30
Deepesh Garg
e4abaa7cdd Merge pull request #18591 from deepeshgarg007/utils_fix_develop
fix: Ambigious column in query
2019-08-05 14:45:30 +05:30
Himanshu Warekar
e8f95a2adf fix: TreeView fixes 2019-08-05 14:21:09 +05:30
Rucha Mahabal
d9fa83b196 fix: added Company by default in session defaults (#18471) 2019-08-05 14:15:16 +05:30
deepeshgarg007
23f30cdb8b fix: Aambigious column in query 2019-08-05 12:42:35 +05:30
deepeshgarg007
043f70e9a6 fix: Aambigious column in query 2019-08-05 12:40:50 +05:30
Faris Ansari
9983d90e24 chore: Remove package-lock.json (#18565)
Yarn uses yarn.lock
2019-08-05 12:32:41 +05:30
Deepesh Garg
7638301d01 Merge pull request #18527 from netchampfaris/bom-comparison-tool
feat: BOM Comparison Tool
2019-08-05 11:58:46 +05:30
Suraj Shetty
0957480305 fix: Show popup to employees with same phone number 2019-08-05 11:32:51 +05:30
rohitwaghchaure
9601b6c601 feat: added checkbox 'Update Consumed Material Cost In Project' in work order to don't update the consumed material cost in the project for the subassembely work orders (#18533) 2019-08-05 10:40:23 +05:30
Frappe PR Bot
833afea3e3 feat: Updated translation (#18542) 2019-08-05 10:38:37 +05:30
Anurag Mishra
08df6bda41 fix: query (#18468) 2019-08-05 10:27:25 +05:30
Mangesh-Khairnar
31c5c1e562 fix(payroll-entry): show make bank entry button (#18497)
* fix(payroll-entry): show make bank entry button when manually submitting salary slip

* Update payroll_entry.py
2019-08-05 10:21:19 +05:30
Anurag Mishra
7e1987ed48 feat: validate cwip accounts for journal Entry (#18518) 2019-08-05 10:18:57 +05:30
Anurag Mishra
f9fb92ebb0 feat: validate cwip accoutns in journal entry (#18519) 2019-08-05 10:18:37 +05:30
Mangesh-Khairnar
a3d5200194 fix(sales-order): update items (#18535)
* fix(sales-order): update items

* fix: minor changes

* Update: accounts controller
2019-08-05 10:16:40 +05:30
Mangesh-Khairnar
9accae3ddc fix(sales-order): update items (#18536)
* fix(sales-order): update items

* fix: minor changes
2019-08-05 10:16:25 +05:30
Deepesh Garg
8b0302bab9 fix: Make conversion rate optional for non itemized items (#18540) 2019-08-05 10:14:19 +05:30
Deepesh Garg
cfb899451f fix: Make conversion rate optional for non itemized items (#18541) 2019-08-05 10:14:05 +05:30
Deepesh Garg
fb5aa43e77 fix: Type error handling while getting material request items (#18549)
* fix: Type error handling while getting material request items

* fix: Remove flt
2019-08-05 10:12:42 +05:30
Deepesh Garg
713d4bb1ba fix: Type error handling while getting material request items (#18550)
* fix: Type error handling while getting material request items

* fix: Remove flt
2019-08-05 10:12:17 +05:30
Deepesh Garg
a7eaa4de14 fix: Customer price list not honored in shopping cart (#18556) 2019-08-05 10:10:53 +05:30
Deepesh Garg
65ad4287b6 fix: Customer price list not honored in shopping cart (#18557) 2019-08-05 10:10:38 +05:30
Faris Ansari
b4678d3f21 chore: Remove package-lock.json (#18564)
Yarn uses yarn.lock
2019-08-05 10:09:32 +05:30
Suraj Shetty
580fa48642 fix: Quotation list in customer portal (#18579)
* fix: Quotation list in customer portal

Customers were not able to see their quotations because of
 the recent customer field removal from quotation

* fix: Remove duplicate code
2019-08-05 10:08:35 +05:30
Mangesh-Khairnar
06a0afa039 Feat: Notify by email feature (#18587)
* feat: notify user by email in employee onboarding control

* fix: create task on update after submit
2019-08-05 10:07:05 +05:30
Nabin Hait
a813571c17 Update employee_advance.py 2019-08-05 10:05:28 +05:30
Mangesh-Khairnar
d66396f4e9 fix(employee-advance): update employee advance on change in expense claim (#18588)
* fix(employee-advance): update employee advance on rejection/cancellation of expense claim

* fix(expense-claim): display appropriate buttons only if linked transactions are valid

* Update employee_advance.py
2019-08-05 10:04:05 +05:30
Mangesh-Khairnar
c92e823651 fix(employee-advance): update employee advance on change in expense claim (#18590)
* fix(employee-advance): update employee advance on rejection/cancellation of expense claim

* fix(expense-claim): display appropriate buttons only if linked transactions are valid
2019-08-05 10:02:32 +05:30
Suraj Shetty
35c4b78e66 Merge branch 'develop' of github.com:frappe/erpnext into refactor-call-popup 2019-08-04 22:23:03 +05:30
rohitwaghchaure
ed7e074985 Merge pull request #18570 from rohitwaghchaure/add_serial_no_button_not_working
fix: add serial no button not working for the delivery note
2019-08-04 12:02:43 +05:30
Deepesh Garg
6f39db6a18 Merge pull request #18576 from deepeshgarg007/taxes_and_totals_v12
fix: Error handling in taxes and totals
2019-08-03 18:27:14 +05:30
Deepesh Garg
7668cd7053 Merge pull request #18577 from deepeshgarg007/taxes_and_totals_v13
fix: Error handling in taxes and totals
2019-08-03 18:26:54 +05:30
deepeshgarg007
b656529818 fix: Error handling in taxes and totals 2019-08-03 13:49:33 +05:30
deepeshgarg007
8bf19ce81a fix: Error handling in taxes and totals 2019-08-03 13:44:44 +05:30
Deepesh Garg
4d38a5043f Merge pull request #18573 from deepeshgarg007/error_report_develop
fix: Remove payment order from bank dashboard
2019-08-03 12:17:13 +05:30
Deepesh Garg
2f1633bf41 Merge pull request #18574 from deepeshgarg007/error_report_v12
fix: Remove payment order from bank dashboard
2019-08-03 12:16:52 +05:30
deepeshgarg007
a499079250 fix: Remove non standard fieldname 2019-08-03 10:27:33 +05:30
deepeshgarg007
75465775b4 Merge branch 'version-12-hotfix' of https://github.com/frappe/erpnext into error_report_v12 2019-08-03 10:26:46 +05:30
deepeshgarg007
b0916a35dc fix: Remove payment order from bank dashboard 2019-08-03 10:24:04 +05:30
deepeshgarg007
93e46310b8 fix: Remove payment order from bank dashboard 2019-08-03 10:17:44 +05:30
Suraj Shetty
4b3b358ac6 fix: Show correct label instead of showing undefined (#18559) 2019-08-02 21:46:38 +05:30
Suraj Shetty
e45102b913 fix: Show correct label instead of showing undefined (#18560) 2019-08-02 21:46:28 +05:30
Rohit Waghchaure
dadd049cbf fix: add serial no button not working for the delivery note 2019-08-02 19:11:31 +05:30
Suraj Shetty
6fd3a86012 fix: Option to create pick list from work order 2019-08-02 16:48:31 +05:30
Sahil Khan
8426ff726a Merge branch 'version-12-hotfix' into version-12 2019-08-02 14:27:59 +05:30
Sahil Khan
968da1cd21 bumped to version 12.0.4 2019-08-02 14:47:59 +05:50
sahil28297
7d7e4534dd Merge pull request #18566 from scmmishra/task-fix
fix: task not updated issue
2019-08-02 14:15:19 +05:30
sahil28297
c7abc025ff Merge branch 'develop' into task-fix 2019-08-02 14:14:52 +05:30
sahil28297
77313685da Merge pull request #18567 from scmmishra/task-fix-patch1
fix: task not updated issue
2019-08-02 14:14:27 +05:30
Shivam Mishra
0313dc0f8c fix: task not updated issue 2019-08-02 14:12:36 +05:30
Shivam Mishra
dc53e8ebb0 fix: task not updated issue 2019-08-02 13:56:49 +05:30
Suraj Shetty
117161401a fix: Check zero valuation rate only for valid doctypes (#18528)
fix: Check zero valuation rate only for valid doctypes
2019-08-02 11:22:47 +05:30
Suraj Shetty
c6857e562b fix: Check zero valuation rate only for valid doctypes (#18529)
fix: Check zero valuation rate only for valid doctypes
2019-08-02 11:22:31 +05:30
Suraj Shetty
3f31a56fb3 feat(customer): Add report to show item prices per Customer (#17930)
feat(customer): Add report to show item prices per Customer
2019-08-02 11:11:51 +05:30
Suraj Shetty
c154e57603 Merge branch 'develop' into stock-ledger-fix_develop 2019-08-02 08:44:21 +05:30
Suraj Shetty
b559bf6de6 Merge branch 'version-12-hotfix' into stock-ledger-fix 2019-08-02 08:43:54 +05:30
Suraj Shetty
c57328669a feat: Add pick list print format 2019-08-02 08:14:27 +05:30
Suraj Shetty
b35c0410b1 fix: Add option to get items from work order 2019-08-02 08:12:30 +05:30
Rohan
fc04d334da Merge branch 'develop' into develop-customer-item-price-report 2019-08-01 17:51:03 +05:30
Suraj Shetty
a7dc3735ae fix: Move folders to right location 2019-08-01 15:49:29 +05:30
Deepesh Garg
4be00502cc Merge pull request #18546 from deepeshgarg007/bank_dashboard_fix
fix: Payment Order link fix in bank dashboard
2019-08-01 15:24:53 +05:30
Deepesh Garg
097cc13072 Merge pull request #18547 from deepeshgarg007/bank_dashboard_v12
fix: Payment Order link fix in bank dashboard
2019-08-01 15:24:37 +05:30
deepeshgarg007
c16ef32b6b fix: Payment Order link fix in bank dashboard 2019-08-01 14:10:03 +05:30
deepeshgarg007
8704bc6f39 fix: Payment Order link fix in bank dashboard 2019-08-01 13:24:48 +05:30
Suraj Shetty
31e3dada0e Merge branch 'version-12-hotfix' into bom-comparison-tool 2019-08-01 12:59:19 +05:30
Suraj Shetty
e06f486aee fix: Rename methods 2019-08-01 12:54:33 +05:30
Faris Ansari
d9e482759c style: Missing semicolon 2019-08-01 12:53:19 +05:30
Suraj Shetty
bb7a2dbb6a fix: Rename file 2019-08-01 12:38:26 +05:30
Suraj Shetty
0c1dbb116f Merge branch 'develop' of github.com:frappe/erpnext into feature-pick-list 2019-08-01 12:06:20 +05:30
Suraj Shetty
fbcc56536b fix: Rename Pick TIcket -> Pick List 2019-08-01 12:05:20 +05:30
Suraj Shetty
fa9111ebe2 fix: Add and rename some fields
- Add ability to create delivery note from pick ticket
- Minor fix related to create button
2019-08-01 11:07:14 +05:30
Mangesh-Khairnar
8fb600162e fix: remove all leaves via scheduler 2019-07-31 19:31:26 +05:30
Mangesh-Khairnar
5eac8703da fix: create reverse expiry for back dated leaves 2019-07-31 19:28:21 +05:30
Deepesh Garg
d301d26fda fix: Enhancement in credit note (#18511)
* fix: Credit note enhancement

* Fix: Print format for Sales Invoice Return

* fix: Zero quantity validation fix for credit note
2019-07-31 15:58:19 +05:30
Deepesh Garg
b65c761b16 fix: Enhancement in credit note (#18510)
* fix: Credit note enhancement

* Fix: Print format for Sales Invoice Return

* fix: Zero quantity validation fix for credit note
2019-07-31 15:58:01 +05:30
rohitwaghchaure
fdb5e6b2e5 Merge pull request #18531 from rohitwaghchaure/scrap_item_not_adding_v12_hotfix
fix: scrap item not adding while doing finished good entry
2019-07-31 00:47:01 +05:30
Rohit Waghchaure
862363521b fix: scrap item not adding while doing finished good entry 2019-07-30 23:57:58 +05:30
deepeshgarg007
f9c0ef3eb3 fix: Check zero valuation rate only for valid doctypes 2019-07-30 19:01:53 +05:30
deepeshgarg007
548293ad08 fix: Check zero valuation rate only for valid doctypes 2019-07-30 18:49:19 +05:30
Faris Ansari
f650cb8e4b style: Indent and missing semicolon 2019-07-30 17:46:15 +05:30
Faris Ansari
a4ada93834 fix: Field labels 2019-07-30 17:11:34 +05:30
Faris Ansari
66064c7827 fix: Add BOM Comparison Tool to module view 2019-07-30 17:11:18 +05:30
Faris Ansari
1214e2d2a4 feat: BOM Comparison Tool 2019-07-30 16:54:46 +05:30
Suraj Shetty
72d03464dc fix: Show "Get Item Location" only if there are reference items 2019-07-30 11:56:24 +05:30
Suraj Shetty
14fb1600ec fix: Select location based on group warehouse 2019-07-30 11:47:21 +05:30
Suraj Shetty
341f7733d1 fix: Make item read-only in item location table 2019-07-30 10:02:50 +05:30
Suraj Shetty
e260e8239f fix: Batch number selection code 2019-07-30 10:02:10 +05:30
Suraj Shetty
55ab31314c fix: Add code to set batch no
- And split item based on batch availibility
2019-07-30 09:02:03 +05:30
Suraj Shetty
36c724d7b5 fix(Issue): reset issue fulfilled indicator (#18454)
fix(Issue): reset issue fulfilled indicator
2019-07-29 18:27:53 +05:30
Suraj Shetty
9ad10cb425 test: Add basic tests 2019-07-29 16:52:26 +05:30
Deepesh Garg
62daa43a4c Merge pull request #18513 from deepeshgarg007/trail_balance_fix
fix: Opening balance not getting calculated in trail balance report
2019-07-29 15:38:39 +05:30
rohitwaghchaure
a55e4e2c03 Merge pull request #18452 from rohitwaghchaure/scrap_item_not_adding
fix: scrap item not adding while doing finished good entry
2019-07-29 15:30:24 +05:30
deepeshgarg007
4c652396d0 fix: Opening balance not getting calculated in trail_balance_report 2019-07-29 14:57:33 +05:30
Deepesh Garg
8d00ee4f81 Merge pull request #18403 from deepeshgarg007/defaut_accounting_dimension
fix: Company specific default accounting dimensions
2019-07-29 12:12:40 +05:30
Suraj Shetty
7e20324776 Merge branch 'develop' of github.com:frappe/erpnext into feature-pick-list 2019-07-29 09:41:08 +05:30
deepeshgarg007
ec421df4e4 fix: Code cleanup 2019-07-29 08:58:56 +05:30
Suraj Shetty
27bdba49d4 test: Add test case statements 2019-07-28 22:04:07 +05:30
Suraj Shetty
d43764c8e5 fix: Use .set method to set serial no. 2019-07-28 22:03:28 +05:30
deepeshgarg007
6a43f6718a fix: Reload doc in patch 2019-07-28 10:30:32 +05:30
deepeshgarg007
a65ad10c62 fix: GL entry validation fix 2019-07-27 19:06:36 +05:30
deepeshgarg007
4fce891241 Merge branch 'develop' of https://github.com/frappe/erpnext into defaut_accounting_dimension 2019-07-27 18:11:34 +05:30
Himanshu
9443e8e85f Merge branch 'develop' into iss_ful_fix_v13 2019-07-26 12:51:09 +00:00
Deepesh Garg
ce63b1f669 Merge pull request #18317 from deepeshgarg007/stock_ageing_fix
fix: Enhancement in stock ageing report
2019-07-26 15:45:48 +05:30
Saurabh
af19347376 Merge branch 'develop' into scrap_item_not_adding 2019-07-26 15:10:17 +05:30
Suraj Shetty
64f174fcaa feat: Get item location from reference items
- Add option to get items from multiple sales order
- Add some required fiels to Pick TIcket Reference Item
2019-07-26 13:22:05 +05:30
Himanshu
e87fbcc286 Merge branch 'develop' into iss_ful_fix_v13 2019-07-26 07:31:44 +00:00
Deepesh Garg
941e21092c Merge branch 'develop' into stock_ageing_fix 2019-07-26 12:47:05 +05:30
Deepesh Garg
c391d65dc3 Merge pull request #18488 from adityahase/faster
perf(travis): Faster builds
2019-07-26 12:41:01 +05:30
Himanshu
0162d0a2ea Merge branch 'develop' into iss_ful_fix_v13 2019-07-26 06:58:55 +00:00
rohitwaghchaure
ad89b029c2 Merge pull request #18494 from netchampfaris/parent-account-child-account-currency-fp
fix(Account): Pass parent currency to child currency
2019-07-26 12:13:27 +05:30
deepeshgarg007
15154d4bd0 Merge branch 'develop' of https://github.com/frappe/erpnext into stock_ageing_fix 2019-07-26 10:30:22 +05:30
deepeshgarg007
dda6b5cd53 fix: Add accounting dimensions to subscription and opening invoice tool 2019-07-26 09:14:42 +05:30
deepeshgarg007
aa92df4ddc fix: Test cases for accounting dimensions 2019-07-26 09:14:42 +05:30
deepeshgarg007
0ce2afc9bc fix: Test Cases for accounting dimensions 2019-07-26 09:14:42 +05:30
deepeshgarg007
41a1cd954c fix: Set query fix 2019-07-26 09:14:42 +05:30
deepeshgarg007
b124aff0bb fix: Codacy Fixes 2019-07-26 09:14:42 +05:30
deepeshgarg007
703fc08467 fix: Patch 2019-07-26 09:14:42 +05:30
deepeshgarg007
6dd5f74671 fix: Remove dimensions from boot 2019-07-26 09:14:42 +05:30
deepeshgarg007
ada1ac8013 fix: Added default dimension and filter in bootinfo 2019-07-26 09:14:42 +05:30
deepeshgarg007
efd6307bc4 fix: Default Accounting Dimensions in doctypes 2019-07-26 09:14:42 +05:30
Faris Ansari
0ec747f57c fix(Account): Pass parent currency to child currency
In a scenario where Parent Company Account's Currency is different
from it's default currency, the Account Currency of Child would be set
from the default currency of Company which might be wrong
2019-07-26 08:55:34 +05:30
Deepesh Garg
059c568f08 Merge pull request #18482 from deepeshgarg007/bank_reco_develop
fix: Dynamic link issue fix in Bank reconciliation statement
2019-07-26 08:48:49 +05:30
Deepesh Garg
641e8fea02 Merge branch 'develop' into bank_reco_develop 2019-07-26 08:48:02 +05:30
Deepesh Garg
cd645de4f9 Merge pull request #18474 from deepeshgarg007/gstr-1-query-v13
fix: GSTR-1 query fix
2019-07-26 08:45:59 +05:30
Aditya Hase
96eec7e2cd chore: Empty commit 2019-07-26 05:06:42 +05:30
Aditya Hase
1e82638ae8 perf(tests): Remove unnecessary tearDown code 2019-07-26 03:52:17 +05:30
Aditya Hase
ff79463e36 perf(travis): Use setUpClass instead of setUp 2019-07-26 03:08:45 +05:30
Aditya Hase
6bc2988623 fix(stock): Fix travis builds 2019-07-26 03:08:45 +05:30
Aditya Hase
0f072d7d40 perf(tests): Use country with lesser fixtures 2019-07-26 01:11:57 +05:30
Aditya Hase
0ae786adec perf(tests): Do not unnecessarily create companies 2019-07-26 00:38:51 +05:30
Aditya Hase
6a5b7f751c perf(tests): Use setUpClass and tearDownClass instead of setUp and tearDown 2019-07-26 00:23:13 +05:30
Aditya Hase
a630a24040 fix(travis): Install wkhtmltopdf 2019-07-25 22:40:26 +05:30
Aditya Hase
fdb395c977 fix(travis): Remove redundant arguments 2019-07-25 21:51:12 +05:30
Aditya Hase
dac46ed6e1 fix(travis): Use --site parameter 2019-07-25 21:50:46 +05:30
Aditya Hase
6002fd7820 fix(travis): Merge install and before_script 2019-07-25 21:39:30 +05:30
Aditya Hase
4b680178be fix(travis): Execute get-app before bench start 2019-07-25 21:38:07 +05:30
Aditya Hase
5542af9be8 perf(travis): Use travis optimizations 2019-07-25 21:36:22 +05:30
Aditya Hase
1de45877b1 perf(travis): Do not build assets 2019-07-25 21:28:15 +05:30
Aditya Hase
13919440a7 perf(travis): Remove unnecessary processes from Procfile 2019-07-25 21:27:20 +05:30
Aditya Hase
543996652b fix(travis): Use MariaDB credentials from site_config.json 2019-07-25 21:25:53 +05:30
Aditya Hase
6f978d2497 perf(travis): Do not waste 10 seconds 2019-07-25 21:23:43 +05:30
Aditya Hase
97ad6352af fix(travis): Execute get-app and reinstall after bench start 2019-07-25 21:23:24 +05:30
Aditya Hase
6e2fa02c56 fix(travis): Do not disable scheduler using CLI 2019-07-25 21:21:54 +05:30
Aditya Hase
6f025e7b4f fix(travis): Do not use use_site 2019-07-25 21:21:19 +05:30
Aditya Hase
8005022508 fix(travis): Setup MariaDB 2019-07-25 21:19:30 +05:30
Aditya Hase
06ca6f7705 fix(travis): Remove unused files 2019-07-25 21:18:05 +05:30
Aditya Hase
ac185989ff fix(travis): Remove travis/bench_init.sh 2019-07-25 21:15:30 +05:30
Aditya Hase
306a410b77 fix(travis): Do not execute install.py 2019-07-25 21:11:18 +05:30
Aditya Hase
c49d45497c fix(travis): Install coverall after tests 2019-07-25 21:10:06 +05:30
Aditya Hase
828699f26a fix(travis): Use MariaDB 10.3 2019-07-25 21:09:34 +05:30
Aditya Hase
7204bcb932 fix(travis): Restructure build matrix 2019-07-25 17:48:17 +05:30
Mangesh-Khairnar
5ca3e83a00 feat: add ledger link in hr config 2019-07-25 14:35:39 +05:30
deepeshgarg007
f56284b0c1 Dynamic link issue fix in Bank reconciliation statement 2019-07-25 12:47:32 +05:30
Suraj Shetty
3b31800533 fix: Add logic to set batch no [WIP]
- Add pick ticket reference item
2019-07-25 11:22:45 +05:30
deepeshgarg007
b1f3e0224c fix: GSTR-1 query fix 2019-07-24 21:36:56 +05:30
Anurag Mishra
0505135f90 Merge branch 'develop' into refactor-call-popup 2019-07-24 18:33:14 +05:30
Aditya Hase
14600e6a3e fix(travis): Remove unnecessary commands 2019-07-24 15:18:52 +05:30
Suraj Shetty
0576ad5ef9 fix: Move pick list creation code to picklist.py file 2019-07-24 15:16:03 +05:30
Suraj Shetty
778b4926bf fix: Fetch warehouse location from Bin 2019-07-24 11:27:32 +05:30
Himanshu Warekar
20e1a3e199 fix: reset issue fulfilled indicator 2019-07-23 17:00:23 +05:30
Rohit Waghchaure
bcfbc792b4 fix: scrap item not adding while doing finished good entry 2019-07-23 16:05:29 +05:30
Suraj Shetty
ed4f8cf65d Merge branch 'develop' of github.com:frappe/erpnext into feature-pick-list 2019-07-23 13:29:41 +05:30
Mangesh-Khairnar
bb1be2e2ee chore: change fieldname for carried forward leave expiry 2019-07-23 13:18:40 +05:30
Aditya Hase
48d9cfe304 fix(website): Remove references to Product Settings.products_a… (#18448)
This was accidentally added back in 34c551d9a5 (diff-f0a387cdb305471e74e523ecc4e646ac)
2019-07-23 12:05:31 +05:30
deepeshgarg007
a19d1d6926 fix: Fixes in stock ageing report 2019-07-23 08:30:09 +05:30
Mangesh-Khairnar
fd1d4c2927 chore: split expire allocation 2019-07-22 18:05:27 +05:30
Mangesh-Khairnar
08c02287dd fix: expiry allocaton after creating all the transactions 2019-07-22 17:47:03 +05:30
deepeshgarg007
d9cc84892b fix: Use get_serial_no and remove batch 2019-07-22 15:56:41 +05:30
Mangesh-Khairnar
f6cf58fa8c fix: change get all to sql list 2019-07-22 15:32:41 +05:30
deepeshgarg007
3877b5407c fix: Remove batch 2019-07-22 15:30:18 +05:30
Suraj Shetty
1e9a6e6b7e Merge branch 'refactor-call-popup' of github.com:surajshetty3416/erpnext into refactor-call-popup 2019-07-22 15:19:31 +05:30
Suraj Shetty
4177ecb6b2 Merge branch 'develop' of github.com:frappe/erpnext into refactor-call-popup 2019-07-22 15:18:03 +05:30
Mangesh-Khairnar
cbc22e6369 Merge branch 'develop' of https://github.com/frappe/erpnext into leave-management 2019-07-22 13:57:04 +05:30
Mangesh-Khairnar
29e9f14f95 fix: minor changes 2019-07-22 13:54:39 +05:30
deepeshgarg007
55ca054cb4 Merge branch 'develop' of https://github.com/frappe/erpnext into stock_ageing_fix 2019-07-22 12:46:30 +05:30
Suraj Shetty
4bf65dd0d9 Merge branch 'develop' into develop-customer-item-price-report 2019-07-18 10:15:20 +05:30
Suraj Shetty
06b56adc71 Merge branch 'develop' into develop-customer-item-price-report 2019-07-17 17:29:42 +05:30
Suraj Shetty
6824838ab0 Merge branch 'develop' of github.com:frappe/erpnext into feature-pick-list 2019-07-17 15:39:09 +05:30
Suraj Shetty
9eb091162a Merge branch 'develop' into refactor-call-popup 2019-07-17 13:23:54 +05:30
Suraj Shetty
82cfccab2f fix: Get user_id of employee instead of name
- Remove caching from lead
2019-07-17 11:52:35 +05:30
deepeshgarg007
4a7f370b15 fix: Consider serial no and batches in Stock ageing report 2019-07-16 16:08:50 +05:30
Suraj Shetty
2295921821 Merge branch 'develop' into refactor-call-popup 2019-07-16 13:54:07 +05:30
Suraj Shetty
e7d277d51e fix: Last communication query 2019-07-16 13:53:41 +05:30
Suraj Shetty
f5dd494716 fix(call popup): Multiple changes
- Remove summary from call log use comments instead
- Add contact and lead if matched to the call log
- Add received by field with Employee Link
- DocPerm to allow Employees to have read access on call log
- Remove unwanted code
- Add a method to get lead just by providing phone number
- Show popup only to Employee to which the system is trying to connect.
- Remove custom code from call popup dialog and replace it with
 standard fields
- Increase timeout to hide popup after the call has been disconnected.
2019-07-16 11:07:25 +05:30
deepeshgarg007
6ecbd97fbe Merge branch 'develop' of https://github.com/frappe/erpnext into stock_ageing_fix 2019-07-16 09:02:48 +05:30
deepeshgarg007
581d931031 fix: Enhancement in stock ageing report 2019-07-13 21:58:32 +05:30
deepeshgarg007
d43d19acfd Merge branch 'develop' of https://github.com/frappe/erpnext into stock_ageing_fix 2019-07-13 11:40:05 +05:30
Suraj Shetty
ca872381a1 Merge branch 'develop' of github.com:frappe/erpnext into feature-pick-list 2019-07-12 12:13:09 +05:30
Suraj Shetty
32371c8755 feat: Init Pick Ticket and Pick Ticket Item 2019-07-12 11:56:42 +05:30
deepeshgarg007
1dc124cf75 fix: Changed columns to new dict form 2019-07-10 14:49:25 +05:30
Mangesh-Khairnar
80fb0bf520 fix: add employee leave balance report to the dashboard 2019-07-03 13:06:46 +05:30
Mangesh-Khairnar
8d19faa598 Merge branch 'develop' of https://github.com/frappe/erpnext into leave-management 2019-07-03 11:44:00 +05:30
Mangesh-Khairnar
0d4db95d99 fix: skip expired leaves on allocation end date 2019-07-03 11:35:51 +05:30
Mangesh-Khairnar
bd999b0908 fix: minor changes 2019-06-21 00:49:48 +05:30
Mangesh-Khairnar
439313e524 Merge branch 'develop' of https://github.com/frappe/erpnext into leave-management 2019-06-19 13:10:53 +05:30
Mangesh-Khairnar
12a2b21465 fix: track status for pending leaves 2019-06-19 13:00:52 +05:30
Rohan Bansal
0426636a32 fix(customer): Improve performance by reducing queries 2019-06-17 12:16:12 +05:30
Mangesh-Khairnar
1db0fc91a5 fix: check generated ledger entries to avoid overlap 2019-06-14 15:48:31 +05:30
Mangesh-Khairnar
fefdac432c refactor: add json changes 2019-06-14 15:39:50 +05:30
Mangesh-Khairnar
24fbe23c8d fix: add indicators for expire in the leave allocation list 2019-06-14 15:36:26 +05:30
Mangesh-Khairnar
87adaed933 fix: generate ledger entries for all leave transactions 2019-06-14 15:13:53 +05:30
Mangesh-Khairnar
4e1b60d401 style: change formatting 2019-06-14 11:15:54 +05:30
Rohan Bansal
e3a3306b30 feat(customer): Add report to show item prices per Customer 2019-06-13 14:53:33 +05:30
Mangesh-Khairnar
283d2c5ca2 fix: only create leave application ledger on intermediate allocation expiry 2019-06-11 16:35:29 +05:30
Mangesh-Khairnar
b16d395a8f Merge branch 'develop' of https://github.com/frappe/erpnext into leave-management 2019-06-07 11:33:06 +05:30
Mangesh-Khairnar
e4d03bf0d0 fix: consider expiry in leaves 2019-06-07 11:30:27 +05:30
Mangesh-Khairnar
368a974368 style: change formatting 2019-06-06 20:43:32 +05:30
Mangesh-Khairnar
86e0f4c617 Merge branch 'develop' of https://github.com/frappe/erpnext into leave-management 2019-06-06 20:41:28 +05:30
Mangesh-Khairnar
c7b9ae9c5e fix: get leave balance based on the ledger entries 2019-06-06 20:38:59 +05:30
Mangesh-Khairnar
b840ba4407 feat: show dashboard on submit 2019-06-06 20:38:23 +05:30
Mangesh-Khairnar
00c607116b fix: handle negative leaves without allocation 2019-06-06 20:37:34 +05:30
Mangesh-Khairnar
f13243a92e feat: fetch annual allocation based on leave policy 2019-06-06 20:35:10 +05:30
Mangesh-Khairnar
3863fc5fb2 feat: create ledger entry for each earned leave 2019-06-06 20:34:10 +05:30
Mangesh-Khairnar
050f65beb4 feat: fetch leave allocation from ledger entry 2019-06-06 20:32:01 +05:30
Mangesh-Khairnar
351f4d53a0 feat: add employee filter to employee leave balance 2019-06-05 21:22:07 +05:30
Mangesh-Khairnar
62011c9dc4 feat: add link to policy 2019-06-05 21:16:27 +05:30
Mangesh-Khairnar
afa1dc4ffa feat: expire current allocation 2019-06-03 20:09:22 +05:30
Mangesh-Khairnar
c5385e141b fix: add mandatory reason fields in leave application 2019-05-31 00:53:28 +05:30
Mangesh-Khairnar
95e5d812fe fix: UX changes 2019-05-30 22:22:15 +05:30
Mangesh-Khairnar
91e62f575e fix: department filters in employee leave balance 2019-05-30 13:38:35 +05:30
Mangesh-Khairnar
2124d9884b fix: pass positional arguments on creation of leave application 2019-05-30 13:21:34 +05:30
Mangesh-Khairnar
aafb5cb6f6 fix: ignore expired non-carry forwarded allocation on calculating leaves taken 2019-05-30 13:13:14 +05:30
Mangesh-Khairnar
ded33a7e2e fix: ledger entries creation 2019-05-29 19:12:19 +05:30
Mangesh-Khairnar
7cc6a67c18 add department filter to employee leave balance 2019-05-29 15:59:20 +05:30
Mangesh-Khairnar
8f47bffa0e fix: create an instance 2019-05-29 15:54:14 +05:30
Mangesh-Khairnar
ae4228aed4 fix: fetch queries 2019-05-28 13:24:15 +05:30
Mangesh-Khairnar
9d6151d200 patch: add reload doc for leave ledger entry 2019-05-28 11:45:51 +05:30
Mangesh-Khairnar
c6d6adcbf3 fix: ledger entry creation for encashment 2019-05-28 09:44:38 +05:30
Mangesh-Khairnar
61bb236cfa test: delete ledger entry after each test to maintain balance 2019-05-27 19:36:40 +05:30
Mangesh-Khairnar
35786c0067 Merge branch 'leave-management' of https://github.com/Mangesh-Khairnar/erpnext into leave-management 2019-05-27 15:42:11 +05:30
Mangesh-Khairnar
6f69bbe1d7 test: leave ledger balance 2019-05-27 15:40:36 +05:30
Mangesh-Khairnar
7fbaef5de3 fix: expiry ledger creation 2019-05-27 15:39:48 +05:30
Nabin Hait
c9a4111f4d Merge branch 'develop' into leave-management 2019-05-27 13:59:27 +05:30
Mangesh-Khairnar
705b7dc9c2 Merge branch 'develop' of https://github.com/frappe/erpnext into leave-management 2019-05-27 11:21:06 +05:30
Mangesh-Khairnar
71cdcb3593 style: add a more descriptive method name 2019-05-27 11:00:04 +05:30
Mangesh-Khairnar
24248f687b patch: create entries for only missing transactions 2019-05-27 10:58:42 +05:30
Mangesh-Khairnar
45197965d7 fix: give cancellation permission to hr manager 2019-05-27 03:26:48 +05:30
Mangesh-Khairnar
d751281fa7 fix: application and leave encashment test cases 2019-05-27 03:23:58 +05:30
Mangesh-Khairnar
e7d307e6bf fix: only expire carry forwarded allocation via scheduler 2019-05-27 03:21:32 +05:30
Mangesh-Khairnar
2417c93d0e feat: create expiry and carry forward calculation on leave allocation creation 2019-05-27 03:20:10 +05:30
Mangesh-Khairnar
c99f644ffe test: carry forward and expiry allocation 2019-05-27 03:13:47 +05:30
Mangesh-Khairnar
7a7f4bd822 fix: leave balance calculation 2019-05-27 03:12:57 +05:30
Mangesh-Khairnar
9e3b688333 test: create leave policy 2019-05-27 03:10:39 +05:30
Mangesh-Khairnar
f3926d0fcb patch: leave ledger entries 2019-05-26 20:17:16 +05:30
Mangesh-Khairnar
45cf02308e fix: prevent manual creation of ledger entries 2019-05-23 20:29:18 +05:30
Mangesh-Khairnar
8ef81870bb test: create leave ledger entry for encashment 2019-05-23 20:28:16 +05:30
Mangesh-Khairnar
5ba17c87e5 feat: remove update allocation after submit 2019-05-22 18:29:22 +05:30
Mangesh-Khairnar
afb0c4aa43 fix: delete entry on cancellation of transaction 2019-05-15 21:50:34 +05:30
Mangesh-Khairnar
f8f02c508d feat: create leave ledger entry on leave encashment creation 2019-05-15 21:50:06 +05:30
Mangesh-Khairnar
50037f8609 fix: consider min days remaining as remaining leaves 2019-05-15 21:49:27 +05:30
Mangesh-Khairnar
6ba9a128e7 feat: calculate leave balance using ledger entries 2019-05-15 15:53:54 +05:30
Mangesh-Khairnar
964deaca96 test: creation of ledger entries on application submit 2019-05-15 15:53:53 +05:30
Mangesh-Khairnar
201aeeb20d test: creation of ledger entries on allocation submit 2019-05-15 15:53:53 +05:30
Mangesh-Khairnar
170b8dded8 fix: expiry logic for carry forwarded allocation 2019-05-15 15:53:53 +05:30
Mangesh-Khairnar
9bb4b8e8b2 feat: create expiry ledger entry on allocation period completion 2019-05-15 15:53:53 +05:30
Mangesh-Khairnar
cf8f4bda8f fix: skip application fetch for non allocation records 2019-05-15 15:53:53 +05:30
Mangesh-Khairnar
783bd89413 feat: handle cancellation workflow for leave application 2019-05-15 15:53:53 +05:30
Mangesh-Khairnar
5448edff2c feat: delete cancelled allocation from ledger 2019-05-15 15:53:53 +05:30
Mangesh-Khairnar
01490f1560 feat: add cancellation workflow for leave allocation ledger entry 2019-05-15 15:53:53 +05:30
Mangesh-Khairnar
5ad83c06c2 feat: add ledger entries on leave addition 2019-05-15 15:53:53 +05:30
Mangesh-Khairnar
679371e397 feat: get carry forwarded leaves via ledger entries 2019-05-15 15:53:53 +05:30
Mangesh-Khairnar
2b421c39b5 feat: add transaction details in ledger 2019-05-15 15:53:53 +05:30
Mangesh-Khairnar
1de990b2ac feat: create leave ledger entry 2019-05-15 15:53:53 +05:30
Mangesh-Khairnar
5e2b067107 feat: display carry forwarded allocation days and total leaves allocated 2019-05-15 15:53:52 +05:30
Mangesh-Khairnar
0abf5d340c fix: carry forwarded allocation period validation 2019-05-15 15:53:52 +05:30
Mangesh-Khairnar
d01863707c test: pass leave type as params 2019-05-15 15:53:52 +05:30
Mangesh-Khairnar
70cf4a6796 feat: validate leave allocation period to be within expiry limits 2019-05-15 15:53:52 +05:30
Mangesh-Khairnar
99c9cfaaed feat: generate leave allocation for carry forwarded leaves 2019-05-15 15:53:52 +05:30
Mangesh-Khairnar
4badca54af feat: validate leave expiry days 2019-05-15 15:53:52 +05:30
Mangesh-Khairnar
0c0bfb1ef0 feat: calculate carry forward leaves allocation 2019-05-15 15:53:52 +05:30
Mangesh-Khairnar
d6c5b6320f feat: add a field for conditionally displaying carry forwarded leave 2019-05-15 15:53:52 +05:30
Mangesh-Khairnar
e46d3a87ea feat: set carry forwarded leave allocation 2019-05-15 15:53:52 +05:30
Mangesh-Khairnar
c28d2e4b2a test: create leave allocation check 2019-05-15 15:53:51 +05:30
Mangesh-Khairnar
bd3b3ea12c test: create leave type 2019-05-15 15:53:51 +05:30
Mangesh-Khairnar
7c6b6eae5b feat: set leave allocation on carry forward check 2019-05-15 15:53:51 +05:30
Mangesh-Khairnar
1208ca6a36 feat: add old leaves to track carry forward leave allocation 2019-05-15 15:53:51 +05:30
Mangesh-Khairnar
c182a5687e feat: add validation for carry forward leave expiry 2019-05-15 15:53:51 +05:30
Mangesh-Khairnar
fd53c64d5d feat: create carried forward leave expiry option 2019-05-15 15:53:51 +05:30
394 changed files with 501791 additions and 490221 deletions

View File

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

View File

@@ -12,11 +12,14 @@ from frappe.utils.nestedset import get_descendants_of
@frappe.whitelist()
@cache_source
def get(chart_name=None, from_date = None, to_date = None):
chart = frappe.get_doc('Dashboard Chart', chart_name)
def get(chart_name = None, chart = None, no_cache = None, from_date = None, to_date = None):
if chart_name:
chart = frappe.get_doc('Dashboard Chart', chart_name)
else:
chart = frappe._dict(frappe.parse_json(chart))
timespan = chart.timespan
timegrain = chart.time_interval
filters = json.loads(chart.filters_json)
filters = frappe.parse_json(chart.filters_json)
account = filters.get("account")
company = filters.get("company")

File diff suppressed because it is too large Load Diff

View File

@@ -100,7 +100,10 @@ class Account(NestedSet):
if ancestors:
if frappe.get_value("Company", self.company, "allow_account_creation_against_child_company"):
return
frappe.throw(_("Please add the account to root level Company - %s" % ancestors[0]))
if not frappe.db.get_value("Account",
{'account_name': self.account_name, 'company': ancestors[0]}, 'name'):
frappe.throw(_("Please add the account to root level Company - %s" % ancestors[0]))
else:
descendants = get_descendants_of('Company', self.company)
if not descendants: return
@@ -114,23 +117,7 @@ class Account(NestedSet):
if not parent_acc_name_map: return
for company in descendants:
if not parent_acc_name_map.get(company):
frappe.throw(_("While creating account for child Company {0}, parent account {1} not found. Please create the parent account in corresponding COA")
.format(company, parent_acc_name))
doc = frappe.copy_doc(self)
doc.flags.ignore_root_company_validation = True
doc.update({
"company": company,
# parent account's currency should be passed down to child account's curreny
# if it is None, it picks it up from default company currency, which might be unintended
"account_currency": self.account_currency,
"parent_account": parent_acc_name_map[company]
})
doc.save()
frappe.msgprint(_("Account {0} is added in the child company {1}")
.format(doc.name, company))
self.create_account_for_child_company(parent_acc_name_map, descendants)
def validate_group_or_ledger(self):
if self.get("__islocal"):
@@ -172,6 +159,49 @@ class Account(NestedSet):
if frappe.db.get_value("GL Entry", {"account": self.name}):
frappe.throw(_("Currency can not be changed after making entries using some other currency"))
def create_account_for_child_company(self, parent_acc_name_map, descendants):
for company in descendants:
if not parent_acc_name_map.get(company):
frappe.throw(_("While creating account for child Company {0}, parent account {1} not found. Please create the parent account in corresponding COA")
.format(company, parent_acc_name))
filters = {
"account_name": self.account_name,
"company": company
}
if self.account_number:
filters["account_number"] = self.account_number
child_account = frappe.db.get_value("Account", filters, 'name')
if not child_account:
doc = frappe.copy_doc(self)
doc.flags.ignore_root_company_validation = True
doc.update({
"company": company,
# parent account's currency should be passed down to child account's curreny
# if it is None, it picks it up from default company currency, which might be unintended
"account_currency": self.account_currency,
"parent_account": parent_acc_name_map[company]
})
doc.save()
frappe.msgprint(_("Account {0} is added in the child company {1}")
.format(doc.name, company))
elif child_account:
# update the parent company's value in child companies
doc = frappe.get_doc("Account", child_account)
parent_value_changed = False
for field in ['account_type', 'account_currency',
'freeze_account', 'balance_must_be']:
if doc.get(field) != self.get(field):
parent_value_changed = True
doc.set(field, self.get(field))
if parent_value_changed:
doc.save()
def convert_group_to_ledger(self):
if self.check_if_child_exists():
throw(_("Account with child nodes cannot be converted to ledger"))

View File

@@ -121,7 +121,11 @@ frappe.treeview_settings["Account"] = {
},
onrender: function(node) {
if(frappe.boot.user.can_read.indexOf("GL Entry") !== -1){
var dr_or_cr = in_list(["Liability", "Income", "Equity"], node.data.root_type) ? "Cr" : "Dr";
// show Dr if positive since balance is calculated as debit - credit else show Cr
let balance = node.data.balance_in_account_currency || node.data.balance;
let dr_or_cr = balance > 0 ? "Dr": "Cr";
if (node.data && node.data.balance!==undefined) {
$('<span class="balance-area pull-right text-muted small">'
+ (node.data.balance_in_account_currency ?

View File

@@ -406,7 +406,11 @@
"is_group": 1,
"Bewertungskorrektur zu Forderungen aus Lieferungen und Leistungen": {
"account_number": "9960"
},
},
"Debitoren": {
"is_group": 1,
"account_number": "10000"
},
"Forderungen aus Lieferungen und Leistungen": {
"account_number": "1200",
"account_type": "Receivable"
@@ -1077,7 +1081,7 @@
}
}
},
"C - Verb.": {
"C - Verbindlichkeiten": {
"account_type": "Payable",
"1 - Anleihen": {
"is_group": 1,
@@ -1193,7 +1197,15 @@
"is_group": 1,
"Bewertungskorrektur zu Verb. aus Lieferungen und Leistungen": {
"account_number": "9964"
},
},
"Kreditoren": {
"account_number": "70000",
"is_group": 1,
"Wareneingangs-­Verrechnungskonto" : {
"account_number": "70001",
"account_type": "Stock Received But Not Billed"
}
},
"Verb. aus Lieferungen und Leistungen": {
"account_number": "3300",
"account_type": "Payable"
@@ -1682,90 +1694,6 @@
"account_type": "Income Account"
}
},
"Erl\u00f6sschm\u00e4lerungen (Gruppe)": {
"is_group": 1,
"Erl\u00f6sschm\u00e4lerungen": {
"account_number": "4700"
},
"Erl\u00f6sschm\u00e4lerungen aus steuerfreien Ums\u00e4tzen \u00a7 4 Nr. 1a UStG": {
"account_number": "4705"
},
"Erl\u00f6sschm\u00e4lerungen 7 % USt": {
"account_number": "4710"
},
"Erl\u00f6sschm\u00e4lerungen 19 % USt": {
"account_number": "4720"
},
"Erl\u00f6sschm\u00e4lerungen 16 % USt": {
"account_number": "4723"
},
"Erl\u00f6sschm\u00e4lerungen aus steuerfreien innergem. Lieferungen": {
"account_number": "4724"
},
"Erl\u00f6sschm\u00e4lerungen aus im Inland steuerpfl. EU-Lieferungen 7 % USt": {
"account_number": "4725"
},
"Erl\u00f6sschm\u00e4lerungen aus im Inland steuerpfl. EU-Lieferungen 19 % USt": {
"account_number": "4726"
},
"Erl\u00f6sschm\u00e4lerungen aus im anderen EU-Land steuerpfl. Lieferungen": {
"account_number": "4727"
},
"Erl\u00f6sschm\u00e4lerungen aus im Inland steuerpfl. EU-Lieferungen 16 % USt": {
"account_number": "4729"
},
"Gew\u00e4hrte Skonti (Gruppe)": {
"is_group": 1,
"Gew. Skonti": {
"account_number": "4730"
},
"Gew. Skonti 7 % USt": {
"account_number": "4731"
},
"Gew. Skonti 19 % USt": {
"account_number": "4736"
},
"Gew. Skonti aus Lieferungen von Mobilfunkger./Schaltkr., f. die der Leistungsempf. die Ust. schuldet": {
"account_number": "4738"
},
"Gew. Skonti aus Leistungen, f. die der Leistungsempf. die Umsatzsteuer nach \u00a7 13b UStG schuldet": {
"account_number": "4741"
},
"Gew. Skonti aus Erl\u00f6sen aus im anderen EU-Land steuerpfl. Leistungen, f. die der Leistungsempf. die Ust. schuldet": {
"account_number": "4742"
},
"Gew. Skonti aus steuerfreien innergem. Lieferungen \u00a7 4 Nr. 1b UStG": {
"account_number": "4743"
},
"Gew. Skonti aus im Inland steuerpfl. EU-Lieferungen": {
"account_number": "4745"
},
"Gew. Skonti aus im Inland steuerpfl. EU-Lieferungen 7% USt": {
"account_number": "4746"
},
"Gew. Skonti aus im Inland steuerpfl. EU-Lieferungen 19% USt": {
"account_number": "4748"
}
},
"Gew\u00e4hrte Boni 7 % USt": {
"account_number": "4750"
},
"Gew\u00e4hrte Boni 19 % USt": {
"account_number": "4760"
},
"Gew\u00e4hrte Boni": {
"account_number": "4769"
},
"Gew\u00e4hrte Rabatte": {
"account_number": "4770"
},
"Gew\u00e4hrte Rabatte 7 % USt": {
"account_number": "4780"
},
"Gew\u00e4hrte Rabatte 19 % USt": {
"account_number": "4790"
}
},
"Grundst\u00fccksertr\u00e4ge (Gruppe)": {
"is_group": 1,
"Grundst\u00fccksertr\u00e4ge": {
@@ -2049,48 +1977,6 @@
"Erh. Skonti aus Erwerb Waren als letzter Abnehmer innerh. Dreiecksgesch. 19% Vorst. u. 19% Ust.": {
"account_number": "5793"
}
},
"Erhaltene Boni (Gruppe)": {
"is_group": 1,
"Erhaltene Boni 7 % Vorsteuer": {
"account_number": "5750"
},
"Erhaltene Boni aus Einkauf Roh-, Hilfs- und Betriebsstoffe": {
"account_number": "5753"
},
"Erhaltene Boni aus Einkauf Roh-, Hilfs- und Betriebsstoffe 7% Vorsteuer": {
"account_number": "5754"
},
"Erhaltene Boni aus Einkauf Roh-, Hilfs- und Betriebsstoffe 19% Vorsteuer": {
"account_number": "5755"
},
"Erhaltene Boni 19 % Vorsteuer": {
"account_number": "5760"
},
"Erhaltene Boni": {
"account_number": "5769"
}
},
"Erhaltene Rabatte (Gruppe)": {
"is_group": 1,
"Erhaltene Rabatte": {
"account_number": "5770"
},
"Erhaltene Rabatte 7 % Vorsteuer": {
"account_number": "5780"
},
"Erhaltene Rabatte aus Einkauf Roh-, Hilfs- und Betriebsstoffe": {
"account_number": "5783"
},
"Erhaltene Rabatte aus Einkauf Roh-, Hilfs- und Betriebsstoffe 7% Vorsteuer": {
"account_number": "5784"
},
"Erhaltene Rabatte aus Einkauf Roh-, Hilfs- und Betriebsstoffe 19% Vorsteuer": {
"account_number": "5785"
},
"Erhaltene Rabatte 19 % Vorsteuer": {
"account_number": "5790"
}
}
},
"Bezugsnebenkosten (Gruppe)": {
@@ -2409,7 +2295,49 @@
},
"6 - sonstige betriebliche Ertr\u00e4ge": {
"root_type": "Income",
"is_group": 1,
"is_group": 1,
"Erhaltene Boni (Gruppe)": {
"is_group": 1,
"Erhaltene Boni 7 % Vorsteuer": {
"account_number": "5750"
},
"Erhaltene Boni aus Einkauf Roh-, Hilfs- und Betriebsstoffe": {
"account_number": "5753"
},
"Erhaltene Boni aus Einkauf Roh-, Hilfs- und Betriebsstoffe 7% Vorsteuer": {
"account_number": "5754"
},
"Erhaltene Boni aus Einkauf Roh-, Hilfs- und Betriebsstoffe 19% Vorsteuer": {
"account_number": "5755"
},
"Erhaltene Boni 19 % Vorsteuer": {
"account_number": "5760"
},
"Erhaltene Boni": {
"account_number": "5769"
}
},
"Erhaltene Rabatte (Gruppe)": {
"is_group": 1,
"Erhaltene Rabatte": {
"account_number": "5770"
},
"Erhaltene Rabatte 7 % Vorsteuer": {
"account_number": "5780"
},
"Erhaltene Rabatte aus Einkauf Roh-, Hilfs- und Betriebsstoffe": {
"account_number": "5783"
},
"Erhaltene Rabatte aus Einkauf Roh-, Hilfs- und Betriebsstoffe 7% Vorsteuer": {
"account_number": "5784"
},
"Erhaltene Rabatte aus Einkauf Roh-, Hilfs- und Betriebsstoffe 19% Vorsteuer": {
"account_number": "5785"
},
"Erhaltene Rabatte 19 % Vorsteuer": {
"account_number": "5790"
}
},
"Andere aktivierte Eigenleistungen": {
"account_number": "4820"
},
@@ -2732,7 +2660,91 @@
},
"7 - sonstige betriebliche Aufwendungen": {
"root_type": "Expense",
"is_group": 1,
"is_group": 1,
"Erl\u00f6sschm\u00e4lerungen (Gruppe)": {
"is_group": 1,
"Erl\u00f6sschm\u00e4lerungen": {
"account_number": "4700"
},
"Erl\u00f6sschm\u00e4lerungen aus steuerfreien Ums\u00e4tzen \u00a7 4 Nr. 1a UStG": {
"account_number": "4705"
},
"Erl\u00f6sschm\u00e4lerungen 7 % USt": {
"account_number": "4710"
},
"Erl\u00f6sschm\u00e4lerungen 19 % USt": {
"account_number": "4720"
},
"Erl\u00f6sschm\u00e4lerungen 16 % USt": {
"account_number": "4723"
},
"Erl\u00f6sschm\u00e4lerungen aus steuerfreien innergem. Lieferungen": {
"account_number": "4724"
},
"Erl\u00f6sschm\u00e4lerungen aus im Inland steuerpfl. EU-Lieferungen 7 % USt": {
"account_number": "4725"
},
"Erl\u00f6sschm\u00e4lerungen aus im Inland steuerpfl. EU-Lieferungen 19 % USt": {
"account_number": "4726"
},
"Erl\u00f6sschm\u00e4lerungen aus im anderen EU-Land steuerpfl. Lieferungen": {
"account_number": "4727"
},
"Erl\u00f6sschm\u00e4lerungen aus im Inland steuerpfl. EU-Lieferungen 16 % USt": {
"account_number": "4729"
},
"Gew\u00e4hrte Skonti (Gruppe)": {
"is_group": 1,
"Gew. Skonti": {
"account_number": "4730"
},
"Gew. Skonti 7 % USt": {
"account_number": "4731"
},
"Gew. Skonti 19 % USt": {
"account_number": "4736"
},
"Gew. Skonti aus Lieferungen von Mobilfunkger./Schaltkr., f. die der Leistungsempf. die Ust. schuldet": {
"account_number": "4738"
},
"Gew. Skonti aus Leistungen, f. die der Leistungsempf. die Umsatzsteuer nach \u00a7 13b UStG schuldet": {
"account_number": "4741"
},
"Gew. Skonti aus Erl\u00f6sen aus im anderen EU-Land steuerpfl. Leistungen, f. die der Leistungsempf. die Ust. schuldet": {
"account_number": "4742"
},
"Gew. Skonti aus steuerfreien innergem. Lieferungen \u00a7 4 Nr. 1b UStG": {
"account_number": "4743"
},
"Gew. Skonti aus im Inland steuerpfl. EU-Lieferungen": {
"account_number": "4745"
},
"Gew. Skonti aus im Inland steuerpfl. EU-Lieferungen 7% USt": {
"account_number": "4746"
},
"Gew. Skonti aus im Inland steuerpfl. EU-Lieferungen 19% USt": {
"account_number": "4748"
}
},
"Gew\u00e4hrte Boni 7 % USt": {
"account_number": "4750"
},
"Gew\u00e4hrte Boni 19 % USt": {
"account_number": "4760"
},
"Gew\u00e4hrte Boni": {
"account_number": "4769"
},
"Gew\u00e4hrte Rabatte": {
"account_number": "4770"
},
"Gew\u00e4hrte Rabatte 7 % USt": {
"account_number": "4780"
},
"Gew\u00e4hrte Rabatte 19 % USt": {
"account_number": "4790"
}
},
"Sonstige betriebliche Aufwendungen": {
"account_number": "6300"
},
@@ -3609,18 +3621,6 @@
"Ertr\u00e4ge aus der Aufl\u00f6sung von R\u00fcckstellungen f. sonstige Steuern": {
"account_number": "7694"
}
},
"Debitoren": {
"root_type": "Asset",
"is_group": 1
},
"Kreditoren": {
"root_type": "Liability",
"is_group": 1,
"Wareneingangs-­Verrechnungskonto" : {
"account_number": "70001",
"account_type": "Stock Received But Not Billed"
}
}
}
}

View File

@@ -5,9 +5,13 @@ frappe.ui.form.on('Accounting Dimension', {
refresh: function(frm) {
frm.set_query('document_type', () => {
let invalid_doctypes = frappe.model.core_doctypes_list;
invalid_doctypes.push('Accounting Dimension', 'Project',
'Cost Center', 'Accounting Dimension Detail');
return {
filters: {
name: ['not in', ['Accounting Dimension', 'Project', 'Cost Center', 'Accounting Dimension Detail']]
name: ['not in', invalid_doctypes]
}
};
});

View File

@@ -11,10 +11,20 @@ from frappe.custom.doctype.custom_field.custom_field import create_custom_field
from frappe import scrub
from frappe.utils import cstr
from frappe.utils.background_jobs import enqueue
from frappe.model import core_doctypes_list
class AccountingDimension(Document):
def before_insert(self):
self.set_fieldname_and_label()
def validate(self):
if self.document_type in core_doctypes_list + ('Accounting Dimension', 'Project',
'Cost Center', 'Accounting Dimension Detail') :
msg = _("Not allowed to create accounting dimension for {0}").format(self.document_type)
frappe.throw(msg)
def after_insert(self):
if frappe.flags.in_test:
make_dimension_in_accounting_doctypes(doc=self)
else:
@@ -164,7 +174,7 @@ def get_accounting_dimensions(as_list=True):
return accounting_dimensions
def get_checks_for_pl_and_bs_accounts():
dimensions = frappe.db.sql("""SELECT p.label, p.disabled, p.fieldname, c.company, c.mandatory_for_pl, c.mandatory_for_bs
dimensions = frappe.db.sql("""SELECT p.label, p.disabled, p.fieldname, c.default_dimension, c.company, c.mandatory_for_pl, c.mandatory_for_bs
FROM `tabAccounting Dimension`p ,`tabAccounting Dimension Detail` c
WHERE p.name = c.parent""", as_dict=1)

View File

@@ -17,8 +17,7 @@
"fieldtype": "Link",
"in_list_view": 1,
"label": "Company",
"options": "Company",
"reqd": 1
"options": "Company"
},
{
"fieldname": "reference_document",
@@ -34,8 +33,7 @@
"fieldtype": "Dynamic Link",
"in_list_view": 1,
"label": "Default Dimension",
"options": "reference_document",
"reqd": 1
"options": "reference_document"
},
{
"columns": 3,
@@ -55,7 +53,7 @@
}
],
"istable": 1,
"modified": "2019-07-17 23:34:33.026883",
"modified": "2019-08-15 11:59:09.389891",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Accounting Dimension Detail",

View File

@@ -167,39 +167,7 @@
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "status",
"fieldtype": "Select",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Status",
"length": 0,
"no_copy": 0,
"options": "Open\nClosed",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
@@ -273,7 +241,7 @@
"issingle": 0,
"istable": 0,
"max_attachments": 0,
"modified": "2018-04-13 19:14:47.593753",
"modified": "2019-08-01 19:14:47.593753",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Accounting Period",

View File

@@ -7,6 +7,8 @@ import frappe
from frappe.model.document import Document
from frappe import _
class OverlapError(frappe.ValidationError): pass
class AccountingPeriod(Document):
def validate(self):
self.validate_overlap()
@@ -34,12 +36,13 @@ class AccountingPeriod(Document):
}, as_dict=True)
if len(existing_accounting_period) > 0:
frappe.throw(_("Accounting Period overlaps with {0}".format(existing_accounting_period[0].get("name"))))
frappe.throw(_("Accounting Period overlaps with {0}")
.format(existing_accounting_period[0].get("name")), OverlapError)
def get_doctypes_for_closing(self):
docs_for_closing = []
#if not self.closed_documents or len(self.closed_documents) == 0:
doctypes = ["Sales Invoice", "Purchase Invoice", "Journal Entry", "Payroll Entry", "Bank Reconciliation", "Asset", "Purchase Order", "Sales Order", "Leave Application", "Leave Allocation", "Stock Entry"]
doctypes = ["Sales Invoice", "Purchase Invoice", "Journal Entry", "Payroll Entry", "Bank Reconciliation",
"Asset", "Purchase Order", "Sales Order", "Leave Application", "Leave Allocation", "Stock Entry"]
closed_doctypes = [{"document_type": doctype, "closed": 1} for doctype in doctypes]
for closed_doctype in closed_doctypes:
docs_for_closing.append(closed_doctype)
@@ -52,4 +55,4 @@ class AccountingPeriod(Document):
self.append('closed_documents', {
"document_type": doctype_for_closing.document_type,
"closed": doctype_for_closing.closed
})
})

View File

@@ -5,23 +5,42 @@ from __future__ import unicode_literals
import frappe
import unittest
from frappe.utils import nowdate, add_months
from erpnext.accounts.general_ledger import ClosedAccountingPeriod
from erpnext.accounts.doctype.accounting_period.accounting_period import OverlapError
from erpnext.accounts.doctype.sales_invoice.test_sales_invoice import create_sales_invoice
# class TestAccountingPeriod(unittest.TestCase):
# def test_overlap(self):
# ap1 = create_accounting_period({"start_date":"2018-04-01", "end_date":"2018-06-30", "company":"Wind Power LLC"})
# ap1.save()
# ap2 = create_accounting_period({"start_date":"2018-06-30", "end_date":"2018-07-10", "company":"Wind Power LLC"})
# self.assertRaises(frappe.OverlapError, accounting_period_2.save())
#
# def tearDown(self):
# pass
#
#
# def create_accounting_period(**args):
# accounting_period = frappe.new_doc("Accounting Period")
# accounting_period.start_date = args.start_date or frappe.utils.datetime.date(2018, 4, 1)
# accounting_period.end_date = args.end_date or frappe.utils.datetime.date(2018, 6, 30)
# accounting_period.company = args.company
# accounting_period.period_name = "_Test_Period_Name_1"
#
# return accounting_period
class TestAccountingPeriod(unittest.TestCase):
def test_overlap(self):
ap1 = create_accounting_period(start_date = "2018-04-01",
end_date = "2018-06-30", company = "Wind Power LLC")
ap1.save()
ap2 = create_accounting_period(start_date = "2018-06-30",
end_date = "2018-07-10", company = "Wind Power LLC", period_name = "Test Accounting Period 1")
self.assertRaises(OverlapError, ap2.save)
def test_accounting_period(self):
ap1 = create_accounting_period(period_name = "Test Accounting Period 2")
ap1.save()
doc = create_sales_invoice(do_not_submit=1, cost_center = "_Test Company - _TC", warehouse = "Stores - _TC")
self.assertRaises(ClosedAccountingPeriod, doc.submit)
def tearDown(self):
for d in frappe.get_all("Accounting Period"):
frappe.delete_doc("Accounting Period", d.name)
def create_accounting_period(**args):
args = frappe._dict(args)
accounting_period = frappe.new_doc("Accounting Period")
accounting_period.start_date = args.start_date or nowdate()
accounting_period.end_date = args.end_date or add_months(nowdate(), 1)
accounting_period.company = args.company or "_Test Company"
accounting_period.period_name =args.period_name or "_Test_Period_Name_1"
accounting_period.append("closed_documents", {
"document_type": 'Sales Invoice', "closed": 1
})
return accounting_period

View File

@@ -8,11 +8,8 @@ def get_data():
'fieldname': 'bank',
'transactions': [
{
'label': _('Bank Deatils'),
'label': _('Bank Details'),
'items': ['Bank Account', 'Bank Guarantee']
},
{
'items': ['Payment Order']
}
]
}

View File

@@ -50,7 +50,7 @@ class BankTransaction(StatusUpdater):
if paid_amount and allocated_amount:
if flt(allocated_amount[0]["allocated_amount"]) > flt(paid_amount):
frappe.throw(_("The total allocated amount ({0}) is greated than the paid amount ({1}).".format(flt(allocated_amount[0]["allocated_amount"]), flt(paid_amount))))
elif flt(allocated_amount[0]["allocated_amount"]) == flt(paid_amount):
else:
if payment_entry.payment_document in ["Payment Entry", "Journal Entry", "Purchase Invoice", "Expense Claim"]:
self.clear_simple_entry(payment_entry)

View File

@@ -11,32 +11,32 @@ from erpnext.buying.doctype.purchase_order.test_purchase_order import create_pur
from erpnext.accounts.doctype.budget.budget import get_actual_expense, BudgetError
from erpnext.accounts.doctype.journal_entry.test_journal_entry import make_journal_entry
class TestBudget(unittest.TestCase):
class TestBudget(unittest.TestCase):
def test_monthly_budget_crossed_ignore(self):
set_total_expense_zero("2013-02-28", "Cost Center")
budget = make_budget(budget_against="Cost Center")
jv = make_journal_entry("_Test Account Cost for Goods Sold - _TC",
"_Test Bank - _TC", 40000, "_Test Cost Center - _TC", posting_date="2013-02-28", submit=True)
self.assertTrue(frappe.db.get_value("GL Entry",
{"voucher_type": "Journal Entry", "voucher_no": jv.name}))
budget.cancel()
def test_monthly_budget_crossed_stop1(self):
set_total_expense_zero("2013-02-28", "Cost Center")
budget = make_budget(budget_against="Cost Center")
frappe.db.set_value("Budget", budget.name, "action_if_accumulated_monthly_budget_exceeded", "Stop")
jv = make_journal_entry("_Test Account Cost for Goods Sold - _TC",
"_Test Bank - _TC", 40000, "_Test Cost Center - _TC", posting_date="2013-02-28")
self.assertRaises(BudgetError, jv.submit)
budget.load_from_db()
budget.cancel()
@@ -46,7 +46,7 @@ class TestBudget(unittest.TestCase):
budget = make_budget(budget_against="Cost Center")
frappe.db.set_value("Budget", budget.name, "action_if_accumulated_monthly_budget_exceeded", "Stop")
jv = make_journal_entry("_Test Account Cost for Goods Sold - _TC",
"_Test Bank - _TC", 40000, "_Test Cost Center - _TC", posting_date="2013-03-02")
@@ -117,14 +117,14 @@ class TestBudget(unittest.TestCase):
set_total_expense_zero("2013-02-28", "Project")
budget = make_budget(budget_against="Project")
frappe.db.set_value("Budget", budget.name, "action_if_accumulated_monthly_budget_exceeded", "Stop")
jv = make_journal_entry("_Test Account Cost for Goods Sold - _TC",
"_Test Bank - _TC", 40000, "_Test Cost Center - _TC", project="_Test Project", posting_date="2013-02-28")
self.assertRaises(BudgetError, jv.submit)
budget.load_from_db()
budget.cancel()
@@ -132,31 +132,31 @@ class TestBudget(unittest.TestCase):
set_total_expense_zero("2013-02-28", "Cost Center")
budget = make_budget(budget_against="Cost Center")
jv = make_journal_entry("_Test Account Cost for Goods Sold - _TC",
"_Test Bank - _TC", 150000, "_Test Cost Center - _TC", posting_date="2013-03-28")
self.assertRaises(BudgetError, jv.submit)
budget.cancel()
def test_yearly_budget_crossed_stop2(self):
set_total_expense_zero("2013-02-28", "Project")
budget = make_budget(budget_against="Project")
jv = make_journal_entry("_Test Account Cost for Goods Sold - _TC",
"_Test Bank - _TC", 150000, "_Test Cost Center - _TC", project="_Test Project", posting_date="2013-03-28")
self.assertRaises(BudgetError, jv.submit)
budget.cancel()
def test_monthly_budget_on_cancellation1(self):
set_total_expense_zero("2013-02-28", "Cost Center")
budget = make_budget(budget_against="Cost Center")
jv1 = make_journal_entry("_Test Account Cost for Goods Sold - _TC",
"_Test Bank - _TC", 20000, "_Test Cost Center - _TC", posting_date="2013-02-28", submit=True)
@@ -170,9 +170,9 @@ class TestBudget(unittest.TestCase):
{"voucher_type": "Journal Entry", "voucher_no": jv2.name}))
frappe.db.set_value("Budget", budget.name, "action_if_accumulated_monthly_budget_exceeded", "Stop")
self.assertRaises(BudgetError, jv1.cancel)
budget.load_from_db()
budget.cancel()
@@ -180,7 +180,7 @@ class TestBudget(unittest.TestCase):
set_total_expense_zero("2013-02-28", "Project")
budget = make_budget(budget_against="Project")
jv1 = make_journal_entry("_Test Account Cost for Goods Sold - _TC",
"_Test Bank - _TC", 20000, "_Test Cost Center - _TC", posting_date="2013-02-28", submit=True, project="_Test Project")
@@ -194,16 +194,16 @@ class TestBudget(unittest.TestCase):
{"voucher_type": "Journal Entry", "voucher_no": jv2.name}))
frappe.db.set_value("Budget", budget.name, "action_if_accumulated_monthly_budget_exceeded", "Stop")
self.assertRaises(BudgetError, jv1.cancel)
budget.load_from_db()
budget.cancel()
def test_monthly_budget_against_group_cost_center(self):
set_total_expense_zero("2013-02-28", "Cost Center")
set_total_expense_zero("2013-02-28", "Cost Center", "_Test Cost Center 2 - _TC")
budget = make_budget(budget_against="Cost Center", cost_center="_Test Company - _TC")
frappe.db.set_value("Budget", budget.name, "action_if_accumulated_monthly_budget_exceeded", "Stop")
@@ -211,7 +211,7 @@ class TestBudget(unittest.TestCase):
"_Test Bank - _TC", 40000, "_Test Cost Center 2 - _TC", posting_date="2013-02-28")
self.assertRaises(BudgetError, jv.submit)
budget.load_from_db()
budget.cancel()
@@ -239,8 +239,6 @@ class TestBudget(unittest.TestCase):
budget.cancel()
jv.cancel()
frappe.delete_doc('Journal Entry', jv.name)
frappe.delete_doc('Cost Center', cost_center)
def set_total_expense_zero(posting_date, budget_against_field=None, budget_against_CC=None):
if budget_against_field == "Project":
@@ -256,7 +254,7 @@ def set_total_expense_zero(posting_date, budget_against_field=None, budget_again
"budget_against_field": budget_against_field,
"budget_against": budget_against
}))
if existing_expense:
if budget_against_field == "Cost Center":
make_journal_entry("_Test Account Cost for Goods Sold - _TC",
@@ -281,13 +279,13 @@ def make_budget(**args):
frappe.db.sql("delete from `tabBudget Account` where parent = %(name)s", d)
budget = frappe.new_doc("Budget")
if budget_against == "Project":
budget.project = "_Test Project"
else:
budget.cost_center =cost_center or "_Test Cost Center - _TC"
budget.fiscal_year = "_Test Fiscal Year 2013"
budget.monthly_distribution = "_Test Distribution"
budget.company = "_Test Company"
@@ -299,7 +297,7 @@ def make_budget(**args):
"account": "_Test Account Cost for Goods Sold - _TC",
"budget_amount": 100000
})
if args.applicable_on_material_request:
budget.applicable_on_material_request = 1
budget.action_if_annual_budget_exceeded_on_mr = args.action_if_annual_budget_exceeded_on_mr or 'Warn'

View File

@@ -150,7 +150,7 @@ def validate_accounts(file_name):
accounts_dict = {}
for account in accounts:
accounts_dict.setdefault(account["account_name"], account)
if account["parent_account"] and accounts_dict[account["parent_account"]]:
if account["parent_account"] and accounts_dict.get(account["parent_account"]):
accounts_dict[account["parent_account"]]["is_group"] = 1
message = validate_root(accounts_dict)

View File

@@ -1,457 +1,170 @@
{
"allow_copy": 1,
"allow_guest_to_view": 0,
"allow_import": 1,
"allow_rename": 1,
"autoname": "field:cost_center_name",
"beta": 0,
"creation": "2013-01-23 19:57:17",
"custom": 0,
"description": "Track separate Income and Expense for product verticals or divisions.",
"docstatus": 0,
"doctype": "DocType",
"document_type": "Setup",
"editable_grid": 0,
"allow_copy": 1,
"allow_import": 1,
"allow_rename": 1,
"creation": "2013-01-23 19:57:17",
"description": "Track separate Income and Expense for product verticals or divisions.",
"doctype": "DocType",
"document_type": "Setup",
"engine": "InnoDB",
"field_order": [
"sb0",
"cost_center_name",
"cost_center_number",
"parent_cost_center",
"company",
"cb0",
"is_group",
"disabled",
"lft",
"rgt",
"old_parent"
],
"fields": [
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "sb0",
"fieldtype": "Section Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "sb0",
"fieldtype": "Section Break"
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "cost_center_name",
"fieldtype": "Data",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Cost Center Name",
"length": 0,
"no_copy": 1,
"oldfieldname": "cost_center_name",
"oldfieldtype": "Data",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "cost_center_name",
"fieldtype": "Data",
"in_list_view": 1,
"label": "Cost Center Name",
"no_copy": 1,
"oldfieldname": "cost_center_name",
"oldfieldtype": "Data",
"reqd": 1
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "cost_center_number",
"fieldtype": "Data",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 1,
"label": "Cost Center Number",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "cost_center_number",
"fieldtype": "Data",
"in_list_view": 1,
"in_standard_filter": 1,
"label": "Cost Center Number",
"read_only": 1
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "parent_cost_center",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 1,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Parent Cost Center",
"length": 0,
"no_copy": 0,
"oldfieldname": "parent_cost_center",
"oldfieldtype": "Link",
"options": "Cost Center",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "parent_cost_center",
"fieldtype": "Link",
"ignore_user_permissions": 1,
"in_list_view": 1,
"label": "Parent Cost Center",
"oldfieldname": "parent_cost_center",
"oldfieldtype": "Link",
"options": "Cost Center",
"reqd": 1
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "company",
"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": 1,
"label": "Company",
"length": 0,
"no_copy": 0,
"oldfieldname": "company_name",
"oldfieldtype": "Link",
"options": "Company",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 1,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "company",
"fieldtype": "Link",
"in_list_view": 1,
"in_standard_filter": 1,
"label": "Company",
"oldfieldname": "company_name",
"oldfieldtype": "Link",
"options": "Company",
"remember_last_selected_value": 1,
"reqd": 1
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "cb0",
"fieldtype": "Column Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"length": 0,
"no_copy": 0,
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0,
"fieldname": "cb0",
"fieldtype": "Column Break",
"width": "50%"
},
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"default": "0",
"fieldname": "is_group",
"fieldtype": "Check",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Is Group",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"default": "0",
"fieldname": "is_group",
"fieldtype": "Check",
"label": "Is Group"
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "lft",
"fieldtype": "Int",
"hidden": 1,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "lft",
"length": 0,
"no_copy": 1,
"oldfieldname": "lft",
"oldfieldtype": "Int",
"permlevel": 0,
"print_hide": 1,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 1,
"reqd": 0,
"search_index": 1,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "lft",
"fieldtype": "Int",
"hidden": 1,
"label": "lft",
"no_copy": 1,
"oldfieldname": "lft",
"oldfieldtype": "Int",
"print_hide": 1,
"report_hide": 1,
"search_index": 1
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "rgt",
"fieldtype": "Int",
"hidden": 1,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "rgt",
"length": 0,
"no_copy": 1,
"oldfieldname": "rgt",
"oldfieldtype": "Int",
"permlevel": 0,
"print_hide": 1,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 1,
"reqd": 0,
"search_index": 1,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "rgt",
"fieldtype": "Int",
"hidden": 1,
"label": "rgt",
"no_copy": 1,
"oldfieldname": "rgt",
"oldfieldtype": "Int",
"print_hide": 1,
"report_hide": 1,
"search_index": 1
},
{
"allow_bulk_edit": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "old_parent",
"fieldtype": "Link",
"hidden": 1,
"ignore_user_permissions": 1,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "old_parent",
"length": 0,
"no_copy": 1,
"oldfieldname": "old_parent",
"oldfieldtype": "Data",
"options": "Cost Center",
"permlevel": 0,
"print_hide": 1,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 1,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
"fieldname": "old_parent",
"fieldtype": "Link",
"hidden": 1,
"ignore_user_permissions": 1,
"label": "old_parent",
"no_copy": 1,
"oldfieldname": "old_parent",
"oldfieldtype": "Data",
"options": "Cost Center",
"print_hide": 1,
"report_hide": 1
},
{
"default": "0",
"fieldname": "disabled",
"fieldtype": "Check",
"label": "Disabled"
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 0,
"icon": "fa fa-money",
"idx": 1,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 0,
"max_attachments": 0,
"menu_index": 0,
"modified": "2018-04-26 15:26:25.325778",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Cost Center",
"owner": "Administrator",
],
"icon": "fa fa-money",
"idx": 1,
"modified": "2019-09-16 14:44:17.103548",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Cost Center",
"owner": "Administrator",
"permissions": [
{
"amend": 0,
"cancel": 0,
"create": 1,
"delete": 1,
"email": 1,
"export": 0,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 1,
"read": 1,
"report": 1,
"role": "Accounts Manager",
"set_user_permissions": 0,
"share": 1,
"submit": 0,
"create": 1,
"delete": 1,
"email": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "Accounts Manager",
"share": 1,
"write": 1
},
},
{
"amend": 0,
"cancel": 0,
"create": 0,
"delete": 0,
"email": 0,
"export": 1,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 0,
"read": 1,
"report": 1,
"role": "Auditor",
"set_user_permissions": 0,
"share": 0,
"submit": 0,
"write": 0
},
"export": 1,
"read": 1,
"report": 1,
"role": "Auditor"
},
{
"amend": 0,
"cancel": 0,
"create": 0,
"delete": 0,
"email": 1,
"export": 0,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 1,
"read": 1,
"report": 1,
"role": "Accounts User",
"set_user_permissions": 0,
"share": 0,
"submit": 0,
"write": 0
},
"email": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "Accounts User"
},
{
"amend": 0,
"cancel": 0,
"create": 0,
"delete": 0,
"email": 0,
"export": 0,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 0,
"read": 1,
"report": 0,
"role": "Sales User",
"set_user_permissions": 0,
"share": 0,
"submit": 0,
"write": 0
},
"read": 1,
"role": "Sales User"
},
{
"amend": 0,
"cancel": 0,
"create": 0,
"delete": 0,
"email": 0,
"export": 0,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 0,
"read": 1,
"report": 0,
"role": "Purchase User",
"set_user_permissions": 0,
"share": 0,
"submit": 0,
"write": 0
"read": 1,
"role": "Purchase User"
}
],
"quick_entry": 1,
"read_only": 0,
"read_only_onload": 0,
"search_fields": "parent_cost_center, is_group",
"show_name_in_global_search": 1,
"sort_order": "ASC",
"track_changes": 0,
"track_seen": 0
],
"quick_entry": 1,
"search_fields": "parent_cost_center, is_group",
"show_name_in_global_search": 1,
"sort_field": "modified",
"sort_order": "ASC"
}

View File

@@ -8,7 +8,8 @@
"customer",
"column_break_3",
"posting_date",
"outstanding_amount"
"outstanding_amount",
"debit_to"
],
"fields": [
{
@@ -48,10 +49,18 @@
{
"fieldname": "column_break_3",
"fieldtype": "Column Break"
},
{
"fetch_from": "sales_invoice.debit_to",
"fieldname": "debit_to",
"fieldtype": "Link",
"label": "Debit to",
"options": "Account",
"read_only": 1
}
],
"istable": 1,
"modified": "2019-05-30 19:27:29.436153",
"modified": "2019-08-07 15:13:55.808349",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Discounted Invoice",

View File

@@ -13,41 +13,57 @@ frappe.ui.form.on('Invoice Discounting', {
};
});
frm.events.filter_accounts("bank_account", frm, {"account_type": "Bank"});
frm.events.filter_accounts("bank_charges_account", frm, {"root_type": "Expense"});
frm.events.filter_accounts("short_term_loan", frm, {"root_type": "Liability"});
frm.events.filter_accounts("accounts_receivable_credit", frm, {"account_type": "Receivable"});
frm.events.filter_accounts("accounts_receivable_discounted", frm, {"account_type": "Receivable"});
frm.events.filter_accounts("accounts_receivable_unpaid", frm, {"account_type": "Receivable"});
frm.events.filter_accounts("bank_account", frm, [["account_type", "=", "Bank"]]);
frm.events.filter_accounts("bank_charges_account", frm, [["root_type", "=", "Expense"]]);
frm.events.filter_accounts("short_term_loan", frm, [["root_type", "=", "Liability"]]);
frm.events.filter_accounts("accounts_receivable_discounted", frm, [["account_type", "=", "Receivable"]]);
frm.events.filter_accounts("accounts_receivable_credit", frm, [["account_type", "=", "Receivable"]]);
frm.events.filter_accounts("accounts_receivable_unpaid", frm, [["account_type", "=", "Receivable"]]);
},
filter_accounts: (fieldname, frm, addl_filters) => {
let filters = {
"company": frm.doc.company,
"is_group": 0
};
if(addl_filters) Object.assign(filters, addl_filters);
let filters = [
["company", "=", frm.doc.company],
["is_group", "=", 0]
];
if(addl_filters){
filters = $.merge(filters , addl_filters);
}
frm.set_query(fieldname, () => { return { "filters": filters }; });
},
refresh_filters: (frm) =>{
let invoice_accounts = Object.keys(frm.doc.invoices).map(function(key) {
return frm.doc.invoices[key].debit_to;
});
let filters = [
["account_type", "=", "Receivable"],
["name", "not in", invoice_accounts]
];
frm.events.filter_accounts("accounts_receivable_credit", frm, filters);
frm.events.filter_accounts("accounts_receivable_discounted", frm, filters);
frm.events.filter_accounts("accounts_receivable_unpaid", frm, filters);
},
refresh: (frm) => {
frm.events.show_general_ledger(frm);
if(frm.doc.docstatus === 0) {
if (frm.doc.docstatus === 0) {
frm.add_custom_button(__('Get Invoices'), function() {
frm.events.get_invoices(frm);
});
}
if(frm.doc.docstatus === 1 && frm.doc.status !== "Settled") {
if(frm.doc.status == "Sanctioned") {
if (frm.doc.docstatus === 1 && frm.doc.status !== "Settled") {
if (frm.doc.status == "Sanctioned") {
frm.add_custom_button(__('Disburse Loan'), function() {
frm.events.create_disbursement_entry(frm);
}).addClass("btn-primary");
}
if(frm.doc.status == "Disbursed") {
if (frm.doc.status == "Disbursed") {
frm.add_custom_button(__('Close Loan'), function() {
frm.events.close_loan(frm);
}).addClass("btn-primary");
@@ -64,7 +80,7 @@ frappe.ui.form.on('Invoice Discounting', {
},
set_end_date: (frm) => {
if(frm.doc.loan_start_date && frm.doc.loan_period) {
if (frm.doc.loan_start_date && frm.doc.loan_period) {
let end_date = frappe.datetime.add_days(frm.doc.loan_start_date, frm.doc.loan_period);
frm.set_value("loan_end_date", end_date);
}
@@ -132,6 +148,7 @@ frappe.ui.form.on('Invoice Discounting', {
frm.doc.invoices = frm.doc.invoices.filter(row => row.sales_invoice);
let row = frm.add_child("invoices");
$.extend(row, v);
frm.events.refresh_filters(frm);
});
refresh_field("invoices");
}
@@ -190,8 +207,10 @@ frappe.ui.form.on('Invoice Discounting', {
frappe.ui.form.on('Discounted Invoice', {
sales_invoice: (frm) => {
frm.events.calculate_total_amount(frm);
frm.events.refresh_filters(frm);
},
invoices_remove: (frm) => {
frm.events.calculate_total_amount(frm);
frm.events.refresh_filters(frm);
}
});
});

View File

@@ -12,6 +12,7 @@ from erpnext.accounts.general_ledger import make_gl_entries
class InvoiceDiscounting(AccountsController):
def validate(self):
self.validate_mandatory()
self.validate_invoices()
self.calculate_total_amount()
self.set_status()
self.set_end_date()
@@ -24,6 +25,15 @@ class InvoiceDiscounting(AccountsController):
if self.docstatus == 1 and not (self.loan_start_date and self.loan_period):
frappe.throw(_("Loan Start Date and Loan Period are mandatory to save the Invoice Discounting"))
def validate_invoices(self):
discounted_invoices = [record.sales_invoice for record in
frappe.get_all("Discounted Invoice",fields = ["sales_invoice"], filters= {"docstatus":1})]
for record in self.invoices:
if record.sales_invoice in discounted_invoices:
frappe.throw("Row({0}): {1} is already discounted in {2}"
.format(record.idx, frappe.bold(record.sales_invoice), frappe.bold(record.parent)))
def calculate_total_amount(self):
self.total_amount = sum([flt(d.outstanding_amount) for d in self.invoices])
@@ -212,7 +222,8 @@ def get_invoices(filters):
name as sales_invoice,
customer,
posting_date,
outstanding_amount
outstanding_amount,
debit_to
from `tabSales Invoice` si
where
docstatus = 1

View File

@@ -49,7 +49,6 @@ class TestLoyaltyProgram(unittest.TestCase):
# cancel and delete
for d in [si_redeem, si_original]:
d.cancel()
frappe.delete_doc('Sales Invoice', d.name)
def test_loyalty_points_earned_multiple_tier(self):
frappe.db.set_value("Customer", "Test Loyalty Customer", "loyalty_program", "Test Multiple Loyalty")
@@ -91,7 +90,6 @@ class TestLoyaltyProgram(unittest.TestCase):
# cancel and delete
for d in [si_redeem, si_original]:
d.cancel()
frappe.delete_doc('Sales Invoice', d.name)
def test_cancel_sales_invoice(self):
''' cancelling the sales invoice should cancel the earned points'''
@@ -143,7 +141,6 @@ class TestLoyaltyProgram(unittest.TestCase):
d.cancel()
except frappe.TimestampMismatchError:
frappe.get_doc('Sales Invoice', d.name).cancel()
frappe.delete_doc('Sales Invoice', d.name)
def test_loyalty_points_for_dashboard(self):
doc = frappe.get_doc('Customer', 'Test Loyalty Customer')

View File

@@ -1,171 +1,74 @@
{
"allow_copy": 0,
"allow_import": 1,
"allow_rename": 1,
"autoname": "field:mode_of_payment",
"beta": 0,
"creation": "2012-12-04 17:49:20",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "Setup",
"editable_grid": 0,
"engine": "InnoDB",
"allow_import": 1,
"allow_rename": 1,
"autoname": "field:mode_of_payment",
"creation": "2012-12-04 17:49:20",
"doctype": "DocType",
"document_type": "Setup",
"engine": "InnoDB",
"field_order": [
"mode_of_payment",
"enabled",
"type",
"accounts"
],
"fields": [
{
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "mode_of_payment",
"fieldtype": "Data",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Mode of Payment",
"length": 0,
"no_copy": 0,
"oldfieldname": "mode_of_payment",
"oldfieldtype": "Data",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"unique": 0
},
"fieldname": "mode_of_payment",
"fieldtype": "Data",
"in_list_view": 1,
"label": "Mode of Payment",
"oldfieldname": "mode_of_payment",
"oldfieldtype": "Data",
"reqd": 1,
"unique": 1
},
{
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "type",
"fieldtype": "Select",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 1,
"label": "Type",
"length": 0,
"no_copy": 0,
"options": "Cash\nBank\nGeneral",
"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": "type",
"fieldtype": "Select",
"in_standard_filter": 1,
"label": "Type",
"options": "Cash\nBank\nGeneral"
},
{
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "accounts",
"fieldtype": "Table",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Accounts",
"length": 0,
"no_copy": 0,
"options": "Mode of Payment Account",
"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": "accounts",
"fieldtype": "Table",
"label": "Accounts",
"options": "Mode of Payment Account"
},
{
"default": "1",
"fieldname": "enabled",
"fieldtype": "Check",
"label": "Enabled"
}
],
"hide_heading": 0,
"hide_toolbar": 0,
"icon": "fa fa-credit-card",
"idx": 1,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 0,
"max_attachments": 0,
"modified": "2017-02-17 16:31:34.207683",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Mode of Payment",
"owner": "harshada@webnotestech.com",
],
"icon": "fa fa-credit-card",
"idx": 1,
"modified": "2019-08-14 14:58:42.079115",
"modified_by": "sammish.thundiyil@gmail.com",
"module": "Accounts",
"name": "Mode of Payment",
"owner": "harshada@webnotestech.com",
"permissions": [
{
"amend": 0,
"apply_user_permissions": 0,
"cancel": 0,
"create": 1,
"delete": 0,
"email": 1,
"export": 0,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 1,
"read": 1,
"report": 1,
"role": "Accounts Manager",
"set_user_permissions": 0,
"share": 1,
"submit": 0,
"create": 1,
"email": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "Accounts Manager",
"share": 1,
"write": 1
},
},
{
"amend": 0,
"apply_user_permissions": 0,
"cancel": 0,
"create": 0,
"delete": 0,
"email": 0,
"export": 0,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 0,
"read": 1,
"report": 1,
"role": "Accounts User",
"set_user_permissions": 0,
"share": 0,
"submit": 0,
"write": 0
"read": 1,
"report": 1,
"role": "Accounts User"
}
],
"quick_entry": 1,
"read_only": 0,
"read_only_onload": 0,
"show_name_in_global_search": 1,
"sort_order": "ASC",
"track_changes": 0,
"track_seen": 0
],
"quick_entry": 1,
"show_name_in_global_search": 1,
"sort_field": "modified",
"sort_order": "ASC"
}

View File

@@ -720,7 +720,7 @@ frappe.ui.form.on('Payment Entry', {
$.each(frm.doc.references || [], function(i, row) {
row.allocated_amount = 0 //If allocate payment amount checkbox is unchecked, set zero to allocate amount
if(frappe.flags.allocate_payment_amount){
if(frappe.flags.allocate_payment_amount != 0){
if(row.outstanding_amount > 0 && allocated_positive_outstanding > 0) {
if(row.outstanding_amount >= allocated_positive_outstanding) {
row.allocated_amount = allocated_positive_outstanding;

View File

@@ -126,7 +126,7 @@ class PaymentEntry(AccountsController):
if not self.party:
frappe.throw(_("Party is mandatory"))
_party_name = "title" if self.party_type == "Student" else self.party_type.lower() + "_name"
_party_name = "title" if self.party_type in ("Student", "Shareholder") else self.party_type.lower() + "_name"
self.party_name = frappe.db.get_value(self.party_type, self.party, _party_name)
if self.party:
@@ -624,8 +624,8 @@ def get_outstanding_reference_documents(args):
data = negative_outstanding_invoices + outstanding_invoices + orders_to_be_billed
if not data:
frappe.msgprint(_("No outstanding invoices found for the {0} <b>{1}</b>.")
.format(args.get("party_type").lower(), args.get("party")))
frappe.msgprint(_("No outstanding invoices found for the {0} {1} which qualify the filters you have specified.")
.format(args.get("party_type").lower(), frappe.bold(args.get("party"))))
return data
@@ -648,13 +648,18 @@ def get_orders_to_be_billed(posting_date, party_type, party,
orders = []
if voucher_type:
ref_field = "base_grand_total" if party_account_currency == company_currency else "grand_total"
if party_account_currency == company_currency:
grand_total_field = "base_grand_total"
rounded_total_field = "base_rounded_total"
else:
grand_total_field = "grand_total"
rounded_total_field = "rounded_total"
orders = frappe.db.sql("""
select
name as voucher_no,
{ref_field} as invoice_amount,
({ref_field} - advance_paid) as outstanding_amount,
if({rounded_total_field}, {rounded_total_field}, {grand_total_field}) as invoice_amount,
(if({rounded_total_field}, {rounded_total_field}, {grand_total_field}) - advance_paid) as outstanding_amount,
transaction_date as posting_date
from
`tab{voucher_type}`
@@ -663,13 +668,14 @@ def get_orders_to_be_billed(posting_date, party_type, party,
and docstatus = 1
and company = %s
and ifnull(status, "") != "Closed"
and {ref_field} > advance_paid
and if({rounded_total_field}, {rounded_total_field}, {grand_total_field}) > advance_paid
and abs(100 - per_billed) > 0.01
{condition}
order by
transaction_date, name
""".format(**{
"ref_field": ref_field,
"rounded_total_field": rounded_total_field,
"grand_total_field": grand_total_field,
"voucher_type": voucher_type,
"party_type": scrub(party_type),
"condition": condition
@@ -677,8 +683,8 @@ def get_orders_to_be_billed(posting_date, party_type, party,
order_list = []
for d in orders:
if not (d.outstanding_amount >= filters.get("outstanding_amt_greater_than")
and d.outstanding_amount <= filters.get("outstanding_amt_less_than")):
if not (flt(d.outstanding_amount) >= flt(filters.get("outstanding_amt_greater_than"))
and flt(d.outstanding_amount) <= flt(filters.get("outstanding_amt_less_than"))):
continue
d["voucher_type"] = voucher_type
@@ -755,9 +761,23 @@ def get_party_details(company, party_type, party, date, cost_center=None):
@frappe.whitelist()
def get_account_details(account, date, cost_center=None):
frappe.has_permission('Payment Entry', throw=True)
# to check if the passed account is accessible under reference doctype Payment Entry
account_list = frappe.get_list('Account', {
'name': account
}, reference_doctype='Payment Entry', limit=1)
# There might be some user permissions which will allow account under certain doctypes
# except for Payment Entry, only in such case we should throw permission error
if not account_list:
frappe.throw(_('Account: {0} is not permitted under Payment Entry').format(account))
account_balance = get_balance_on(account, date, cost_center=cost_center,
ignore_account_permission=True)
return frappe._dict({
"account_currency": get_account_currency(account),
"account_balance": get_balance_on(account, date, cost_center=cost_center),
"account_balance": account_balance,
"account_type": frappe.db.get_value("Account", account, "account_type")
})
@@ -927,10 +947,15 @@ def get_payment_entry(dt, dn, party_amount=None, bank_account=None, bank_amount=
paid_amount = abs(outstanding_amount)
if bank_amount:
received_amount = bank_amount
else:
received_amount = paid_amount * doc.conversion_rate
else:
received_amount = abs(outstanding_amount)
if bank_amount:
paid_amount = bank_amount
else:
# if party account currency and bank currency is different then populate paid amount as well
paid_amount = received_amount * doc.conversion_rate
pe = frappe.new_doc("Payment Entry")
pe.payment_type = payment_type

View File

@@ -66,9 +66,10 @@ frappe.ui.form.on('Payment Order', {
get_query_filters: {
bank: frm.doc.bank,
docstatus: 1,
payment_type: ["!=", "Receive"],
bank_account: frm.doc.company_bank_account,
paid_from: frm.doc.account,
payment_order_status: ["=", "Initiated"],
payment_order_status: ["=", "Initiated"]
}
});
},

View File

@@ -1,29 +0,0 @@
frappe.ui.form.on('Payment Order', {
refresh: function(frm) {
if (frm.doc.docstatus==1 && frm.doc.payment_order_type==='Payment Entry') {
frm.add_custom_button(__('Generate Text File'), function() {
frm.trigger("generate_text_and_download_file");
});
}
},
generate_text_and_download_file: (frm) => {
return frappe.call({
method: "erpnext.regional.india.bank_remittance.generate_report",
args: {
name: frm.doc.name
},
freeze: true,
callback: function(r) {
{
frm.reload_doc();
const a = document.createElement('a');
let file_obj = r.message;
a.href = file_obj.file_url;
a.target = '_blank';
a.download = file_obj.file_name;
a.click();
}
}
});
}
});

View File

@@ -93,7 +93,7 @@ class PaymentReconciliation(Document):
and `tab{doc}`.is_return = 1 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 `tabSales Invoice`.name
GROUP BY `tab{doc}`.name
Having
amount > 0
""".format(doc=voucher_type, dr_or_cr=dr_or_cr, reconciled_dr_or_cr=reconciled_dr_or_cr), {
@@ -257,11 +257,8 @@ def reconcile_dr_cr_note(dr_cr_notes):
voucher_type = ('Credit Note'
if d.voucher_type == 'Sales Invoice' else 'Debit Note')
dr_or_cr = ('credit_in_account_currency'
if d.reference_type == 'Sales Invoice' else 'debit_in_account_currency')
reconcile_dr_or_cr = ('debit_in_account_currency'
if dr_or_cr == 'credit_in_account_currency' else 'credit_in_account_currency')
if d.dr_or_cr == 'credit_in_account_currency' else 'credit_in_account_currency')
jv = frappe.get_doc({
"doctype": "Journal Entry",
@@ -272,8 +269,7 @@ def reconcile_dr_cr_note(dr_cr_notes):
'account': d.account,
'party': d.party,
'party_type': d.party_type,
reconcile_dr_or_cr: (abs(d.allocated_amount)
if abs(d.unadjusted_amount) > abs(d.allocated_amount) else abs(d.unadjusted_amount)),
d.dr_or_cr: abs(d.allocated_amount),
'reference_type': d.against_voucher_type,
'reference_name': d.against_voucher
},
@@ -281,7 +277,8 @@ def reconcile_dr_cr_note(dr_cr_notes):
'account': d.account,
'party': d.party,
'party_type': d.party_type,
dr_or_cr: abs(d.allocated_amount),
reconcile_dr_or_cr: (abs(d.allocated_amount)
if abs(d.unadjusted_amount) > abs(d.allocated_amount) else abs(d.unadjusted_amount)),
'reference_type': d.voucher_type,
'reference_name': d.voucher_no
}

View File

@@ -1,7 +1,6 @@
cur_frm.add_fetch("payment_gateway", "payment_account", "payment_account")
cur_frm.add_fetch("payment_gateway", "payment_gateway", "payment_gateway")
cur_frm.add_fetch("payment_gateway", "message", "message")
cur_frm.add_fetch("payment_gateway", "payment_url_message", "payment_url_message")
cur_frm.add_fetch("payment_gateway_account", "payment_account", "payment_account")
cur_frm.add_fetch("payment_gateway_account", "payment_gateway", "payment_gateway")
cur_frm.add_fetch("payment_gateway_account", "message", "message")
frappe.ui.form.on("Payment Request", "onload", function(frm, dt, dn){
if (frm.doc.reference_doctype) {

View File

@@ -20,7 +20,7 @@ class PaymentRequest(Document):
if self.get("__islocal"):
self.status = 'Draft'
self.validate_reference_document()
self.validate_payment_request()
self.validate_payment_request_amount()
self.validate_currency()
self.validate_subscription_details()
@@ -28,10 +28,19 @@ class PaymentRequest(Document):
if not self.reference_doctype or not self.reference_name:
frappe.throw(_("To create a Payment Request reference document is required"))
def validate_payment_request(self):
if frappe.db.get_value("Payment Request", {"reference_name": self.reference_name,
"name": ("!=", self.name), "status": ("not in", ["Initiated", "Paid"]), "docstatus": 1}, "name"):
frappe.throw(_("Payment Request already exists {0}".format(self.reference_name)))
def validate_payment_request_amount(self):
existing_payment_request_amount = \
get_existing_payment_request_amount(self.reference_doctype, self.reference_name)
if existing_payment_request_amount:
ref_doc = frappe.get_doc(self.reference_doctype, self.reference_name)
if (hasattr(ref_doc, "order_type") \
and getattr(ref_doc, "order_type") != "Shopping Cart"):
ref_amount = get_amount(ref_doc)
if existing_payment_request_amount + flt(self.grand_total)> ref_amount:
frappe.throw(_("Total Payment Request amount cannot be greater than {0} amount"
.format(self.reference_doctype)))
def validate_currency(self):
ref_doc = frappe.get_doc(self.reference_doctype, self.reference_name)
@@ -271,7 +280,7 @@ def make_payment_request(**args):
args = frappe._dict(args)
ref_doc = frappe.get_doc(args.dt, args.dn)
grand_total = get_amount(ref_doc, args.dt)
grand_total = get_amount(ref_doc)
if args.loyalty_points and args.dt == "Sales Order":
from erpnext.accounts.doctype.loyalty_program.loyalty_program import validate_loyalty_points
loyalty_amount = validate_loyalty_points(ref_doc, int(args.loyalty_points))
@@ -281,17 +290,25 @@ def make_payment_request(**args):
gateway_account = get_gateway_details(args) or frappe._dict()
existing_payment_request = frappe.db.get_value("Payment Request",
{"reference_doctype": args.dt, "reference_name": args.dn, "docstatus": ["!=", 2]})
bank_account = (get_party_bank_account(args.get('party_type'), args.get('party'))
if args.get('party_type') else '')
existing_payment_request = None
if args.order_type == "Shopping Cart":
existing_payment_request = frappe.db.get_value("Payment Request",
{"reference_doctype": args.dt, "reference_name": args.dn, "docstatus": ("!=", 2)})
if existing_payment_request:
frappe.db.set_value("Payment Request", existing_payment_request, "grand_total", grand_total, update_modified=False)
pr = frappe.get_doc("Payment Request", existing_payment_request)
else:
if args.order_type != "Shopping Cart":
existing_payment_request_amount = \
get_existing_payment_request_amount(args.dt, args.dn)
if existing_payment_request_amount:
grand_total -= existing_payment_request_amount
pr = frappe.new_doc("Payment Request")
pr.update({
"payment_gateway_account": gateway_account.get("name"),
@@ -327,8 +344,9 @@ def make_payment_request(**args):
return pr.as_dict()
def get_amount(ref_doc, dt):
def get_amount(ref_doc):
"""get amount based on doctype"""
dt = ref_doc.doctype
if dt in ["Sales Order", "Purchase Order"]:
grand_total = flt(ref_doc.grand_total) - flt(ref_doc.advance_paid)
@@ -347,6 +365,17 @@ def get_amount(ref_doc, dt):
else:
frappe.throw(_("Payment Entry is already created"))
def get_existing_payment_request_amount(ref_dt, ref_dn):
existing_payment_request_amount = frappe.db.sql("""
select sum(grand_total)
from `tabPayment Request`
where
reference_doctype = %s
and reference_name = %s
and docstatus = 1
""", (ref_dt, ref_dn))
return flt(existing_payment_request_amount[0][0]) if existing_payment_request_amount else 0
def get_gateway_details(args):
"""return gateway and payment account of default payment gateway"""
if args.get("payment_gateway"):

View File

@@ -37,12 +37,12 @@ class TestPaymentRequest(unittest.TestCase):
def setUp(self):
if not frappe.db.get_value("Payment Gateway", payment_gateway["gateway"], "name"):
frappe.get_doc(payment_gateway).insert(ignore_permissions=True)
for method in payment_method:
if not frappe.db.get_value("Payment Gateway Account", {"payment_gateway": method["payment_gateway"],
if not frappe.db.get_value("Payment Gateway Account", {"payment_gateway": method["payment_gateway"],
"currency": method["currency"]}, "name"):
frappe.get_doc(method).insert(ignore_permissions=True)
def test_payment_request_linkings(self):
so_inr = make_sales_order(currency="INR")
pr = make_payment_request(dt="Sales Order", dn=so_inr.name, recipient_id="saurabh@erpnext.com")
@@ -100,3 +100,23 @@ class TestPaymentRequest(unittest.TestCase):
self.assertEqual(expected_gle[gle.account][1], gle.debit)
self.assertEqual(expected_gle[gle.account][2], gle.credit)
self.assertEqual(expected_gle[gle.account][3], gle.against_voucher)
def test_multiple_payment_entries_against_sales_order(self):
# Make Sales Order, grand_total = 1000
so = make_sales_order()
# Payment Request amount = 200
pr1 = make_payment_request(dt="Sales Order", dn=so.name,
recipient_id="nabin@erpnext.com", return_doc=1)
pr1.grand_total = 200
pr1.submit()
# Make a 2nd Payment Request
pr2 = make_payment_request(dt="Sales Order", dn=so.name,
recipient_id="nabin@erpnext.com", return_doc=1)
self.assertEqual(pr2.grand_total, 800)
# Try to make Payment Request more than SO amount, should give validation
pr2.grand_total = 900
self.assertRaises(frappe.ValidationError, pr2.save)

View File

@@ -382,7 +382,7 @@ def get_qty_amount_data_for_cumulative(pr_doc, doc, items=[]):
`tab{child_doc}`.amount
FROM `tab{child_doc}`, `tab{parent_doc}`
WHERE
`tab{child_doc}`.parent = `tab{parent_doc}`.name and {date_field}
`tab{child_doc}`.parent = `tab{parent_doc}`.name and `tab{parent_doc}`.{date_field}
between %s and %s and `tab{parent_doc}`.docstatus = 1
{condition} group by `tab{child_doc}`.name
""".format(parent_doc = doctype,

View File

@@ -41,6 +41,8 @@ def get_pos_data():
items_list = get_items_list(pos_profile, doc.company)
customers = get_customers_list(pos_profile)
doc.plc_conversion_rate = update_plc_conversion_rate(doc, pos_profile)
return {
'doc': doc,
'default_customer': pos_profile.get('customer'),
@@ -53,7 +55,7 @@ def get_pos_data():
'batch_no_data': get_batch_no_data(),
'barcode_data': get_barcode_data(items_list),
'tax_data': get_item_tax_data(),
'price_list_data': get_price_list_data(doc.selling_price_list),
'price_list_data': get_price_list_data(doc.selling_price_list, doc.plc_conversion_rate),
'customer_wise_price_list': get_customer_wise_price_list(),
'bin_data': get_bin_data(pos_profile),
'pricing_rules': get_pricing_rule_data(doc),
@@ -62,6 +64,15 @@ def get_pos_data():
'meta': get_meta()
}
def update_plc_conversion_rate(doc, pos_profile):
conversion_rate = 1.0
price_list_currency = frappe.get_cached_value("Price List", doc.selling_price_list, "currency")
if pos_profile.get("currency") != price_list_currency:
conversion_rate = get_exchange_rate(price_list_currency,
pos_profile.get("currency"), nowdate(), args="for_selling") or 1.0
return conversion_rate
def get_meta():
doctype_meta = {
@@ -227,8 +238,8 @@ def get_contacts(customers):
customers = [frappe._dict({'name': customers})]
for data in customers:
contact = frappe.db.sql(""" select email_id, phone, mobile_no from `tabContact`
where is_primary_contact =1 and name in
contact = frappe.db.sql(""" select email_id, phone from `tabContact`
where is_primary_contact=1 and name in
(select parent from `tabDynamic Link` where link_doctype = 'Customer' and link_name = %s
and parenttype = 'Contact')""", data.name, as_dict=1)
if contact:
@@ -307,7 +318,7 @@ def get_item_tax_data():
# example: {'Consulting Services': {'Excise 12 - TS': '12.000'}}
itemwise_tax = {}
taxes = frappe.db.sql(""" select parent, tax_type, tax_rate from `tabItem Tax`""", as_dict=1)
taxes = frappe.db.sql(""" select parent, tax_type, tax_rate from `tabItem Tax Template Detail`""", as_dict=1)
for tax in taxes:
if tax.parent not in itemwise_tax:
@@ -317,14 +328,14 @@ def get_item_tax_data():
return itemwise_tax
def get_price_list_data(selling_price_list):
def get_price_list_data(selling_price_list, conversion_rate):
itemwise_price_list = {}
price_lists = frappe.db.sql("""Select ifnull(price_list_rate, 0) as price_list_rate,
item_code from `tabItem Price` ip where price_list = %(price_list)s""",
{'price_list': selling_price_list}, as_dict=1)
for item in price_lists:
itemwise_price_list[item.item_code] = item.price_list_rate
itemwise_price_list[item.item_code] = item.price_list_rate * conversion_rate
return itemwise_price_list
@@ -432,7 +443,6 @@ def get_customer_id(doc, customer=None):
return cust_id
def make_customer_and_address(customers):
customers_list = []
for customer, data in iteritems(customers):
@@ -449,7 +459,6 @@ def make_customer_and_address(customers):
frappe.db.commit()
return customers_list
def add_customer(data):
customer = data.get('full_name') or data.get('customer')
if frappe.db.exists("Customer", customer.strip()):
@@ -466,21 +475,18 @@ def add_customer(data):
frappe.db.commit()
return customer_doc.name
def get_territory(data):
if data.get('territory'):
return data.get('territory')
return frappe.db.get_single_value('Selling Settings','territory') or _('All Territories')
def get_customer_group(data):
if data.get('customer_group'):
return data.get('customer_group')
return frappe.db.get_single_value('Selling Settings', 'customer_group') or frappe.db.get_value('Customer Group', {'is_group': 0}, 'name')
def make_contact(args, customer):
if args.get('email_id') or args.get('phone'):
name = frappe.db.get_value('Dynamic Link',
@@ -506,7 +512,6 @@ def make_contact(args, customer):
doc.flags.ignore_mandatory = True
doc.save(ignore_permissions=True)
def make_address(args, customer):
if not args.get('address_line1'):
return
@@ -521,7 +526,10 @@ def make_address(args, customer):
address = frappe.get_doc('Address', name)
else:
address = frappe.new_doc('Address')
address.country = frappe.get_cached_value('Company', args.get('company'), 'country')
if args.get('company'):
address.country = frappe.get_cached_value('Company',
args.get('company'), 'country')
address.append('links', {
'link_doctype': 'Customer',
'link_name': customer
@@ -533,7 +541,6 @@ def make_address(args, customer):
address.flags.ignore_mandatory = True
address.save(ignore_permissions=True)
def make_email_queue(email_queue):
name_list = []
for key, data in iteritems(email_queue):
@@ -550,7 +557,6 @@ def make_email_queue(email_queue):
return name_list
def validate_item(doc):
for item in doc.get('items'):
if not frappe.db.exists('Item', item.get('item_code')):
@@ -569,7 +575,6 @@ def validate_item(doc):
item_doc.save(ignore_permissions=True)
frappe.db.commit()
def submit_invoice(si_doc, name, doc, name_list):
try:
si_doc.insert()
@@ -585,7 +590,6 @@ def submit_invoice(si_doc, name, doc, name_list):
return name_list
def save_invoice(doc, name, name_list):
try:
if not frappe.db.exists('Sales Invoice', {'offline_pos_name': name}):

View File

@@ -44,6 +44,10 @@ erpnext.accounts.SalesInvoiceController = erpnext.selling.SellingController.exte
this.frm.toggle_reqd("due_date", !this.frm.doc.is_return);
if (this.frm.doc.is_return) {
this.frm.return_print_format = "Sales Invoice Return";
}
this.show_general_ledger();
if(doc.update_stock) this.show_stock_ledger();
@@ -148,16 +152,24 @@ erpnext.accounts.SalesInvoiceController = erpnext.selling.SellingController.exte
},
set_default_print_format: function() {
// set default print format to POS type
// set default print format to POS type or Credit Note
if(cur_frm.doc.is_pos) {
if(cur_frm.pos_print_format) {
cur_frm.meta._default_print_format = cur_frm.meta.default_print_format;
cur_frm.meta.default_print_format = cur_frm.pos_print_format;
}
} else if(cur_frm.doc.is_return && !cur_frm.meta.default_print_format) {
if(cur_frm.return_print_format) {
cur_frm.meta._default_print_format = cur_frm.meta.default_print_format;
cur_frm.meta.default_print_format = cur_frm.return_print_format;
}
} else {
if(cur_frm.meta._default_print_format) {
cur_frm.meta.default_print_format = cur_frm.meta._default_print_format;
cur_frm.meta._default_print_format = null;
} else if(in_list([cur_frm.pos_print_format, cur_frm.return_print_format], cur_frm.meta.default_print_format)) {
cur_frm.meta.default_print_format = null;
cur_frm.meta._default_print_format = null;
}
}
},

View File

@@ -78,6 +78,7 @@ class SalesInvoice(SellingController):
self.so_dn_required()
self.validate_proj_cust()
self.validate_pos_return()
self.validate_with_previous_doc()
self.validate_uom_is_integer("stock_uom", "stock_qty")
self.validate_uom_is_integer("uom", "qty")
@@ -199,6 +200,16 @@ class SalesInvoice(SellingController):
if "Healthcare" in active_domains:
manage_invoice_submit_cancel(self, "on_submit")
def validate_pos_return(self):
if self.is_pos and self.is_return:
total_amount_in_payments = 0
for payment in self.payments:
total_amount_in_payments += payment.amount
invoice_total = self.rounded_total or self.grand_total
if total_amount_in_payments < invoice_total:
frappe.throw(_("Total payments amount can't be greater than {}".format(-invoice_total)))
def validate_pos_paid_amount(self):
if len(self.payments) == 0 and self.is_pos:
frappe.throw(_("At least one mode of payment is required for POS invoice."))
@@ -293,8 +304,10 @@ class SalesInvoice(SellingController):
from erpnext.selling.doctype.customer.customer import check_credit_limit
validate_against_credit_limit = False
bypass_credit_limit_check_at_sales_order = cint(frappe.get_cached_value("Customer", self.customer,
"bypass_credit_limit_check_at_sales_order"))
bypass_credit_limit_check_at_sales_order = frappe.db.get_value("Customer Credit Limit",
filters={'parent': self.customer, 'parenttype': 'Customer', 'company': self.company},
fieldname=["bypass_credit_limit_check"])
if bypass_credit_limit_check_at_sales_order:
validate_against_credit_limit = True
@@ -1499,4 +1512,4 @@ def create_invoice_discounting(source_name, target_doc=None):
"outstanding_amount": invoice.outstanding_amount
})
return invoice_discounting
return invoice_discounting

View File

@@ -818,7 +818,6 @@ class TestSalesInvoice(unittest.TestCase):
self.assertEqual(expected_gl_entries[i][2], gle.credit)
si.cancel()
frappe.delete_doc('Sales Invoice', si.name)
gle = frappe.db.sql("""select * from `tabGL Entry`
where voucher_type='Sales Invoice' and voucher_no=%s""", si.name)

View File

@@ -86,17 +86,23 @@ class ShareTransfer(Document):
frappe.throw(_('The field From Shareholder cannot be blank'))
if self.from_folio_no is None or self.from_folio_no is '':
self.to_folio_no = self.autoname_folio(self.to_shareholder)
if self.asset_account is None:
frappe.throw(_('The field Asset Account cannot be blank'))
elif (self.transfer_type == 'Issue'):
self.from_shareholder = ''
if self.to_shareholder is None or self.to_shareholder == '':
frappe.throw(_('The field To Shareholder cannot be blank'))
if self.to_folio_no is None or self.to_folio_no is '':
self.to_folio_no = self.autoname_folio(self.to_shareholder)
if self.asset_account is None:
frappe.throw(_('The field Asset Account cannot be blank'))
else:
if self.from_shareholder is None or self.to_shareholder is None:
frappe.throw(_('The fields From Shareholder and To Shareholder cannot be blank'))
if self.to_folio_no is None or self.to_folio_no is '':
self.to_folio_no = self.autoname_folio(self.to_shareholder)
if self.equity_or_liability_account is None:
frappe.throw(_('The field Equity/Liability Account cannot be blank'))
if self.from_shareholder == self.to_shareholder:
frappe.throw(_('The seller and the buyer cannot be the same'))
if self.no_of_shares != self.to_no - self.from_no + 1:

View File

@@ -15,67 +15,74 @@ class TestShareTransfer(unittest.TestCase):
frappe.db.sql("delete from `tabShare Balance`")
share_transfers = [
{
"doctype" : "Share Transfer",
"transfer_type" : "Issue",
"date" : "2018-01-01",
"to_shareholder" : "SH-00001",
"share_type" : "Equity",
"from_no" : 1,
"to_no" : 500,
"no_of_shares" : 500,
"rate" : 10,
"company" : "_Test Company"
"doctype" : "Share Transfer",
"transfer_type" : "Issue",
"date" : "2018-01-01",
"to_shareholder" : "SH-00001",
"share_type" : "Equity",
"from_no" : 1,
"to_no" : 500,
"no_of_shares" : 500,
"rate" : 10,
"company" : "_Test Company",
"asset_account" : "Cash - _TC",
"equity_or_liability_account": "Creditors - _TC"
},
{
"doctype" : "Share Transfer",
"transfer_type" : "Transfer",
"date" : "2018-01-02",
"from_shareholder" : "SH-00001",
"to_shareholder" : "SH-00002",
"share_type" : "Equity",
"from_no" : 101,
"to_no" : 200,
"no_of_shares" : 100,
"rate" : 15,
"company" : "_Test Company"
"doctype" : "Share Transfer",
"transfer_type" : "Transfer",
"date" : "2018-01-02",
"from_shareholder" : "SH-00001",
"to_shareholder" : "SH-00002",
"share_type" : "Equity",
"from_no" : 101,
"to_no" : 200,
"no_of_shares" : 100,
"rate" : 15,
"company" : "_Test Company",
"equity_or_liability_account": "Creditors - _TC"
},
{
"doctype" : "Share Transfer",
"transfer_type" : "Transfer",
"date" : "2018-01-03",
"from_shareholder" : "SH-00001",
"to_shareholder" : "SH-00003",
"share_type" : "Equity",
"from_no" : 201,
"to_no" : 500,
"no_of_shares" : 300,
"rate" : 20,
"company" : "_Test Company"
"doctype" : "Share Transfer",
"transfer_type" : "Transfer",
"date" : "2018-01-03",
"from_shareholder" : "SH-00001",
"to_shareholder" : "SH-00003",
"share_type" : "Equity",
"from_no" : 201,
"to_no" : 500,
"no_of_shares" : 300,
"rate" : 20,
"company" : "_Test Company",
"equity_or_liability_account": "Creditors - _TC"
},
{
"doctype" : "Share Transfer",
"transfer_type" : "Transfer",
"date" : "2018-01-04",
"from_shareholder" : "SH-00003",
"to_shareholder" : "SH-00002",
"share_type" : "Equity",
"from_no" : 201,
"to_no" : 400,
"no_of_shares" : 200,
"rate" : 15,
"company" : "_Test Company"
"doctype" : "Share Transfer",
"transfer_type" : "Transfer",
"date" : "2018-01-04",
"from_shareholder" : "SH-00003",
"to_shareholder" : "SH-00002",
"share_type" : "Equity",
"from_no" : 201,
"to_no" : 400,
"no_of_shares" : 200,
"rate" : 15,
"company" : "_Test Company",
"equity_or_liability_account": "Creditors - _TC"
},
{
"doctype" : "Share Transfer",
"transfer_type" : "Purchase",
"date" : "2018-01-05",
"from_shareholder" : "SH-00003",
"share_type" : "Equity",
"from_no" : 401,
"to_no" : 500,
"no_of_shares" : 100,
"rate" : 25,
"company" : "_Test Company"
"doctype" : "Share Transfer",
"transfer_type" : "Purchase",
"date" : "2018-01-05",
"from_shareholder" : "SH-00003",
"share_type" : "Equity",
"from_no" : 401,
"to_no" : 500,
"no_of_shares" : 100,
"rate" : 25,
"company" : "_Test Company",
"asset_account" : "Cash - _TC",
"equity_or_liability_account": "Creditors - _TC"
}
]
for d in share_transfers:
@@ -84,30 +91,33 @@ class TestShareTransfer(unittest.TestCase):
def test_invalid_share_transfer(self):
doc = frappe.get_doc({
"doctype" : "Share Transfer",
"transfer_type" : "Transfer",
"date" : "2018-01-05",
"from_shareholder" : "SH-00003",
"to_shareholder" : "SH-00002",
"share_type" : "Equity",
"from_no" : 1,
"to_no" : 100,
"no_of_shares" : 100,
"rate" : 15,
"company" : "_Test Company"
"doctype" : "Share Transfer",
"transfer_type" : "Transfer",
"date" : "2018-01-05",
"from_shareholder" : "SH-00003",
"to_shareholder" : "SH-00002",
"share_type" : "Equity",
"from_no" : 1,
"to_no" : 100,
"no_of_shares" : 100,
"rate" : 15,
"company" : "_Test Company",
"equity_or_liability_account": "Creditors - _TC"
})
self.assertRaises(ShareDontExists, doc.insert)
doc = frappe.get_doc({
"doctype" : "Share Transfer",
"transfer_type" : "Purchase",
"date" : "2018-01-02",
"from_shareholder" : "SH-00001",
"share_type" : "Equity",
"from_no" : 1,
"to_no" : 200,
"no_of_shares" : 200,
"rate" : 15,
"company" : "_Test Company"
"doctype" : "Share Transfer",
"transfer_type" : "Purchase",
"date" : "2018-01-02",
"from_shareholder" : "SH-00001",
"share_type" : "Equity",
"from_no" : 1,
"to_no" : 200,
"no_of_shares" : 200,
"rate" : 15,
"company" : "_Test Company",
"asset_account" : "Cash - _TC",
"equity_or_liability_account": "Creditors - _TC"
})
self.assertRaises(ShareDontExists, doc.insert)

View File

@@ -48,7 +48,6 @@ class TestTaxWithholdingCategory(unittest.TestCase):
#delete invoices to avoid clashing
for d in invoices:
d.cancel()
frappe.delete_doc("Purchase Invoice", d.name)
def test_single_threshold_tds(self):
invoices = []
@@ -83,7 +82,6 @@ class TestTaxWithholdingCategory(unittest.TestCase):
# delete invoices to avoid clashing
for d in invoices:
d.cancel()
frappe.delete_doc("Purchase Invoice", d.name)
def test_single_threshold_tds_with_previous_vouchers(self):
invoices = []
@@ -102,7 +100,6 @@ class TestTaxWithholdingCategory(unittest.TestCase):
# delete invoices to avoid clashing
for d in invoices:
d.cancel()
frappe.delete_doc("Purchase Invoice", d.name)
def create_purchase_invoice(**args):
# return sales invoice doc object

View File

@@ -10,11 +10,13 @@ from erpnext.accounts.doctype.budget.budget import validate_expense_against_budg
from erpnext.accounts.doctype.accounting_dimension.accounting_dimension import get_accounting_dimensions
class ClosedAccountingPeriod(frappe.ValidationError): pass
class StockAccountInvalidTransaction(frappe.ValidationError): pass
def make_gl_entries(gl_map, cancel=False, adv_adj=False, merge_entries=True, update_outstanding='Yes', from_repost=False):
if gl_map:
if not cancel:
validate_accounting_period(gl_map)
gl_map = process_gl_map(gl_map, merge_entries)
if gl_map and len(gl_map) > 1:
save_entries(gl_map, adv_adj, update_outstanding, from_repost)
@@ -23,6 +25,27 @@ def make_gl_entries(gl_map, cancel=False, adv_adj=False, merge_entries=True, upd
else:
delete_gl_entries(gl_map, adv_adj=adv_adj, update_outstanding=update_outstanding)
def validate_accounting_period(gl_map):
accounting_periods = frappe.db.sql(""" SELECT
ap.name as name
FROM
`tabAccounting Period` ap, `tabClosed Document` cd
WHERE
ap.name = cd.parent
AND ap.company = %(company)s
AND cd.closed = 1
AND cd.document_type = %(voucher_type)s
AND %(date)s between ap.start_date and ap.end_date
""", {
'date': gl_map[0].posting_date,
'company': gl_map[0].company,
'voucher_type': gl_map[0].voucher_type
}, as_dict=1)
if accounting_periods:
frappe.throw(_("You can't create accounting entries in the closed accounting period {0}")
.format(accounting_periods[0].name), ClosedAccountingPeriod)
def process_gl_map(gl_map, merge_entries=True):
if merge_entries:
gl_map = merge_similar_entries(gl_map)
@@ -93,6 +116,7 @@ def check_if_in_list(gle, gl_map, dimensions=None):
def save_entries(gl_map, adv_adj, update_outstanding, from_repost=False):
if not from_repost:
validate_account_for_perpetual_inventory(gl_map)
validate_cwip_accounts(gl_map)
round_off_debit_credit(gl_map)
@@ -123,6 +147,16 @@ def validate_account_for_perpetual_inventory(gl_map):
frappe.throw(_("Account: {0} can only be updated via Stock Transactions")
.format(entry.account), StockAccountInvalidTransaction)
def validate_cwip_accounts(gl_map):
if not cint(frappe.db.get_value("Asset Settings", None, "disable_cwip_accounting")) \
and gl_map[0].voucher_type == "Journal Entry":
cwip_accounts = [d[0] for d in frappe.db.sql("""select name from tabAccount
where account_type = 'Capital Work in Progress' and is_group=0""")]
for entry in gl_map:
if entry.account in cwip_accounts:
frappe.throw(_("Account: <b>{0}</b> is capital Work in progress and can not be updated by Journal Entry").format(entry.account))
def round_off_debit_credit(gl_map):
precision = get_field_precision(frappe.get_meta("GL Entry").get_field("debit"),
currency=frappe.get_cached_value('Company', gl_map[0].company, "default_currency"))

View File

@@ -816,7 +816,6 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
contact = me.contacts[data.name];
if(reg.test(data.name.toLowerCase())
|| reg.test(data.customer_name.toLowerCase())
|| (contact && reg.test(contact["mobile_no"]))
|| (contact && reg.test(contact["phone"]))
|| (data.customer_group && reg.test(data.customer_group.toLowerCase()))){
return data;
@@ -834,7 +833,6 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
if(contact && !c['phone']) {
c["phone"] = contact["phone"];
c["email_id"] = contact["email_id"];
c["mobile_no"] = contact["mobile_no"];
}
me.customers_mapper.push({
@@ -844,10 +842,9 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
customer_group: c.customer_group,
territory: c.territory,
phone: contact ? contact["phone"] : '',
mobile_no: contact ? contact["mobile_no"] : '',
email_id: contact ? contact["email_id"] : '',
searchtext: ['customer_name', 'customer_group', 'name', 'value',
'label', 'email_id', 'phone', 'mobile_no']
'label', 'email_id', 'phone']
.map(key => c[key]).join(' ')
.toLowerCase()
});
@@ -1121,7 +1118,8 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
if (key) {
return $.grep(this.items_list, function (item) {
if (search_status) {
if (in_list(me.batch_no_data[item.item_code], me.search_item.$input.val())) {
if (me.batch_no_data[item.item_code] &&
in_list(me.batch_no_data[item.item_code], me.search_item.$input.val())) {
search_status = false;
return me.item_batch_no[item.item_code] = me.search_item.$input.val()
} else if (me.serial_no_data[item.item_code]
@@ -1129,7 +1127,8 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
search_status = false;
me.item_serial_no[item.item_code] = [me.search_item.$input.val(), me.serial_no_data[item.item_code][me.search_item.$input.val()]]
return true
} else if (in_list(me.barcode_data[item.item_code], me.search_item.$input.val())) {
} else if (me.barcode_data[item.item_code] &&
in_list(me.barcode_data[item.item_code], me.search_item.$input.val())) {
search_status = false;
return true;
} else if (reg.test(item.item_code.toLowerCase()) || (item.description && reg.test(item.description.toLowerCase())) ||
@@ -1625,7 +1624,7 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
setTimeout(function () {
w.print();
w.close();
}, 1000)
}, 1000);
},
submit_invoice: function () {
@@ -1682,6 +1681,12 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
$(this.wrapper).find('.pos-bill').css('pointer-events', pointer_events);
$(this.wrapper).find('.pos-items-section').css('pointer-events', pointer_events);
this.set_primary_action();
$(this.wrapper).find('#pos-item-disc').prop('disabled',
this.pos_profile_data.allow_user_to_edit_discount ? false : true);
$(this.wrapper).find('#pos-item-price').prop('disabled',
this.pos_profile_data.allow_user_to_edit_rate ? false : true);
},
create_invoice: function () {
@@ -1692,20 +1697,13 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
if(this.si_docs) {
this.si_docs.forEach((row) => {
existing_pos_list.push(Object.keys(row));
existing_pos_list.push(Object.keys(row)[0]);
});
}
if (this.frm.doc.offline_pos_name
&& in_list(existing_pos_list, this.frm.doc.offline_pos_name)) {
&& in_list(existing_pos_list, cstr(this.frm.doc.offline_pos_name))) {
this.update_invoice()
//to retrieve and set the default payment
invoice_data[this.frm.doc.offline_pos_name] = this.frm.doc;
invoice_data[this.frm.doc.offline_pos_name].payments[0].amount = this.frm.doc.net_total
invoice_data[this.frm.doc.offline_pos_name].payments[0].base_amount = this.frm.doc.net_total
this.frm.doc.paid_amount = this.frm.doc.net_total
this.frm.doc.outstanding_amount = 0
} else if(!this.frm.doc.offline_pos_name) {
this.frm.doc.offline_pos_name = frappe.datetime.now_datetime();
this.frm.doc.posting_date = frappe.datetime.get_today();
@@ -1762,18 +1760,11 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
this.si_docs = this.get_submitted_invoice() || [];
this.email_queue_list = this.get_email_queue() || {};
this.customers_list = this.get_customers_details() || {};
if(this.customer_doc) {
this.freeze = this.customer_doc.display
}
freeze_screen = this.freeze_screen || false;
if ((this.si_docs.length || this.email_queue_list || this.customers_list) && !this.freeze) {
this.freeze = true;
if (this.si_docs.length || this.email_queue_list || this.customers_list) {
frappe.call({
method: "erpnext.accounts.doctype.sales_invoice.pos.make_invoice",
freeze: freeze_screen,
freeze: true,
args: {
doc_list: me.si_docs,
email_queue_list: me.email_queue_list,
@@ -1906,7 +1897,7 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
serial_no = me.item_serial_no[key][0];
}
if (this.items[0].has_serial_no && serial_no == "") {
if (this.items && this.items[0].has_serial_no && serial_no == "") {
this.refresh();
frappe.throw(__(repl("Error: Serial no is mandatory for item %(item)s", {
'item': this.items[0].item_code

View File

@@ -292,8 +292,11 @@ def validate_party_accounts(doc):
party_account_currency = frappe.db.get_value("Account", account.account, "account_currency", cache=True)
existing_gle_currency = get_party_gle_currency(doc.doctype, doc.name, account.company)
company_default_currency = frappe.get_cached_value('Company',
frappe.db.get_default("Company"), "default_currency")
if frappe.db.get_default("Company"):
company_default_currency = frappe.get_cached_value('Company',
frappe.db.get_default("Company"), "default_currency")
else:
company_default_currency = frappe.db.get_value('Company', account.company, "default_currency")
if existing_gle_currency and party_account_currency != existing_gle_currency:
frappe.throw(_("Accounting entries have already been made in currency {0} for company {1}. Please select a receivable or payable account with currency {0}.").format(existing_gle_currency, account.company))
@@ -365,7 +368,7 @@ def validate_due_date(posting_date, due_date, party_type, party, company=None, b
.format(formatdate(default_due_date)))
@frappe.whitelist()
def get_address_tax_category(tax_category, billing_address=None, shipping_address=None):
def get_address_tax_category(tax_category=None, billing_address=None, shipping_address=None):
addr_tax_category_from = frappe.db.get_single_value("Accounts Settings", "determine_address_tax_category_from")
if addr_tax_category_from == "Shipping Address":
if shipping_address:
@@ -469,7 +472,9 @@ def get_timeline_data(doctype, name):
# fetch and append data from Activity Log
data += frappe.db.sql("""select {fields}
from `tabActivity Log`
where reference_doctype={doctype} and reference_name={name}
where (reference_doctype="{doctype}" and reference_name="{name}")
or (timeline_doctype in ("{doctype}") and timeline_name="{name}")
or (reference_doctype in ("Quotation", "Opportunity") and timeline_name="{name}")
and status!='Success' and creation > {after}
{group_by} order by creation desc
""".format(doctype=frappe.db.escape(doctype), name=frappe.db.escape(name), fields=fields,
@@ -605,4 +610,4 @@ def get_partywise_advanced_payment_amount(party_type, posting_date = None):
.format(("credit") if party_type == "Customer" else "debit", cond) , party_type)
if data:
return frappe._dict(data)
return frappe._dict(data)

View File

@@ -1,22 +1,23 @@
{
"align_labels_right": 0,
"creation": "2016-05-05 17:16:18.564460",
"custom_format": 1,
"disabled": 0,
"doc_type": "Sales Invoice",
"docstatus": 0,
"doctype": "Print Format",
"font": "Default",
"html": "<style>\n\t.print-format table, .print-format tr, \n\t.print-format td, .print-format div, .print-format p {\n\t\tfont-family: Monospace;\n\t\tline-height: 200%;\n\t\tvertical-align: middle;\n\t}\n\t@media screen {\n\t\t.print-format {\n\t\t\twidth: 4in;\n\t\t\tpadding: 0.25in;\n\t\t\tmin-height: 8in;\n\t\t}\n\t}\n</style>\n\n<p class=\"text-center\">\n\t{{ company }}<br>\n\t{{ __(\"POS No : \") }} {{ offline_pos_name }}<br>\n</p>\n<p>\n\t<b>{{ __(\"Customer\") }}:</b> {{ customer }}<br>\n</p>\n\n<p>\n\t<b>{{ __(\"Date\") }}:</b> {{ dateutil.global_date_format(posting_date) }}<br>\n</p>\n\n<hr>\n<table class=\"table table-condensed cart no-border\">\n\t<thead>\n\t\t<tr>\n\t\t\t<th width=\"50%\">{{ __(\"Item\") }}</b></th>\n\t\t\t<th width=\"25%\" class=\"text-right\">{{ __(\"Qty\") }}</th>\n\t\t\t<th width=\"25%\" class=\"text-right\">{{ __(\"Amount\") }}</th>\n\t\t</tr>\n\t</thead>\n\t<tbody>\n\t\t{% for item in items %}\n\t\t<tr>\n\t\t\t<td>\n\t\t\t\t{{ item.item_name }}\n\t\t\t</td>\n\t\t\t<td class=\"text-right\">{{ format_number(item.qty, null,precision(\"difference\")) }}<br>@ {{ format_currency(item.rate, currency) }}</td>\n\t\t\t<td class=\"text-right\">{{ format_currency(item.amount, currency) }}</td>\n\t\t</tr>\n\t\t{% endfor %}\n\t</tbody>\n</table>\n\n<table class=\"table table-condensed no-border\">\n\t<tbody>\n\t\t<tr>\n\t\t\t<td class=\"text-right\" style=\"width: 70%\">\n\t\t\t\t{{ __(\"Net Total\") }}\n\t\t\t</td>\n\t\t\t<td class=\"text-right\">\n\t\t\t\t{{ format_currency(total, currency) }}\n\t\t\t</td>\n\t\t</tr>\n\t\t{% for row in taxes %}\n\t\t{% if not row.included_in_print_rate %}\n\t\t<tr>\n\t\t\t<td class=\"text-right\" style=\"width: 70%\">\n\t\t\t\t{{ row.description }}\n\t\t\t</td>\n\t\t\t<td class=\"text-right\">\n\t\t\t\t{{ format_currency(row.tax_amount, currency) }}\n\t\t\t</td>\n\t\t</tr>\n\t\t{% endif %}\n\t\t{% endfor %}\n\t\t{% if discount_amount %}\n\t\t<tr>\n\t\t\t<td class=\"text-right\" style=\"width: 75%\">\n\t\t\t\t{{ __(\"Discount\") }}\n\t\t\t</td>\n\t\t\t<td class=\"text-right\">\n\t\t\t\t{{ format_currency(discount_amount, currency) }}\n\t\t\t</td>\n\t\t</tr>\n\t\t{% endif %}\n\t\t<tr>\n\t\t\t<td class=\"text-right\" style=\"width: 75%\">\n\t\t\t\t<b>{{ __(\"Grand Total\") }}</b>\n\t\t\t</td>\n\t\t\t<td class=\"text-right\">\n\t\t\t\t{{ format_currency(grand_total, currency) }}\n\t\t\t</td>\n\t\t</tr>\n\t\t<tr>\n\t\t\t<td class=\"text-right\" style=\"width: 75%\">\n\t\t\t\t<b>{{ __(\"Paid Amount\") }}</b>\n\t\t\t</td>\n\t\t\t<td class=\"text-right\">\n\t\t\t\t{{ format_currency(paid_amount, currency) }}\n\t\t\t</td>\n\t\t</tr>\n\t\t<tr>\n\t\t\t<td class=\"text-right\" style=\"width: 75%\">\n\t\t\t\t<b>{{ __(\"Qty Total\") }}</b>\n\t\t\t</td>\n\t\t\t<td class=\"text-right\">\n\t\t\t\t{{ qty_total }}\n\t\t\t</td>\n\t\t</tr>\n\t</tbody>\n</table>\n\n\n<hr>\n<p>{{ terms }}</p>\n<p class=\"text-center\">{{ __(\"Thank you, please visit again.\") }}</p>",
"idx": 0,
"line_breaks": 0,
"modified": "2018-03-21 09:10:16.693732",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Point of Sale",
"owner": "Administrator",
"print_format_builder": 0,
"print_format_type": "Js",
"show_section_headings": 0,
"align_labels_right": 0,
"creation": "2016-05-05 17:16:18.564460",
"custom_format": 1,
"disabled": 0,
"doc_type": "Sales Invoice",
"docstatus": 0,
"doctype": "Print Format",
"font": "Default",
"html": "<style>\n\t.print-format table, .print-format tr, \n\t.print-format td, .print-format div, .print-format p {\n\t\tfont-family: Monospace;\n\t\tline-height: 200%;\n\t\tvertical-align: middle;\n\t}\n\t@media screen {\n\t\t.print-format {\n\t\t\twidth: 4in;\n\t\t\tpadding: 0.25in;\n\t\t\tmin-height: 8in;\n\t\t}\n\t}\n</style>\n\n<p class=\"text-center\">\n\t{{ company }}<br>\n\t{{ __(\"POS No : \") }} {{ offline_pos_name }}<br>\n</p>\n<p>\n\t<b>{{ __(\"Customer\") }}:</b> {{ customer }}<br>\n</p>\n\n<p>\n\t<b>{{ __(\"Date\") }}:</b> {{ dateutil.global_date_format(posting_date) }}<br>\n</p>\n\n<hr>\n<table class=\"table table-condensed cart no-border\">\n\t<thead>\n\t\t<tr>\n\t\t\t<th width=\"50%\">{{ __(\"Item\") }}</b></th>\n\t\t\t<th width=\"25%\" class=\"text-right\">{{ __(\"Qty\") }}</th>\n\t\t\t<th width=\"25%\" class=\"text-right\">{{ __(\"Amount\") }}</th>\n\t\t</tr>\n\t</thead>\n\t<tbody>\n\t\t{% for item in items %}\n\t\t<tr>\n\t\t\t<td>\n\t\t\t\t{{ item.item_name }}\n\t\t\t</td>\n\t\t\t<td class=\"text-right\">{{ format_number(item.qty, null,precision(\"difference\")) }}<br>@ {{ format_currency(item.rate, currency) }}</td>\n\t\t\t<td class=\"text-right\">{{ format_currency(item.amount, currency) }}</td>\n\t\t</tr>\n\t\t{% endfor %}\n\t</tbody>\n</table>\n\n<table class=\"table table-condensed no-border\">\n\t<tbody>\n\t\t<tr>\n\t\t\t<td class=\"text-right\" style=\"width: 70%\">\n\t\t\t\t{{ __(\"Net Total\") }}\n\t\t\t</td>\n\t\t\t<td class=\"text-right\">\n\t\t\t\t{{ format_currency(total, currency) }}\n\t\t\t</td>\n\t\t</tr>\n\t\t{% for row in taxes %}\n\t\t{% if not row.included_in_print_rate %}\n\t\t<tr>\n\t\t\t<td class=\"text-right\" style=\"width: 70%\">\n\t\t\t\t{{ row.description }}\n\t\t\t</td>\n\t\t\t<td class=\"text-right\">\n\t\t\t\t{{ format_currency(row.tax_amount, currency) }}\n\t\t\t</td>\n\t\t</tr>\n\t\t{% endif %}\n\t\t{% endfor %}\n\t\t{% if discount_amount %}\n\t\t<tr>\n\t\t\t<td class=\"text-right\" style=\"width: 75%\">\n\t\t\t\t{{ __(\"Discount\") }}\n\t\t\t</td>\n\t\t\t<td class=\"text-right\">\n\t\t\t\t{{ format_currency(discount_amount, currency) }}\n\t\t\t</td>\n\t\t</tr>\n\t\t{% endif %}\n\t\t<tr>\n\t\t\t<td class=\"text-right\" style=\"width: 75%\">\n\t\t\t\t<b>{{ __(\"Grand Total\") }}</b>\n\t\t\t</td>\n\t\t\t<td class=\"text-right\">\n\t\t\t\t{{ format_currency(grand_total, currency) }}\n\t\t\t</td>\n\t\t</tr>\n\t\t<tr>\n\t\t\t<td class=\"text-right\" style=\"width: 75%\">\n\t\t\t\t<b>{{ __(\"Paid Amount\") }}</b>\n\t\t\t</td>\n\t\t\t<td class=\"text-right\">\n\t\t\t\t{{ format_currency(paid_amount, currency) }}\n\t\t\t</td>\n\t\t</tr>\n\t\t<tr>\n\t\t\t<td class=\"text-right\" style=\"width: 75%\">\n\t\t\t\t<b>{{ __(\"Qty Total\") }}</b>\n\t\t\t</td>\n\t\t\t<td class=\"text-right\">\n\t\t\t\t{{ qty_total }}\n\t\t\t</td>\n\t\t</tr>\n\t</tbody>\n</table>\n\n\n<hr>\n<p>{{ terms }}</p>\n<p class=\"text-center\">{{ __(\"Thank you, please visit again.\") }}</p>",
"idx": 0,
"line_breaks": 0,
"modified": "2019-09-05 17:20:30.726659",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Point of Sale",
"owner": "Administrator",
"print_format_builder": 0,
"print_format_type": "JS",
"raw_printing": 0,
"show_section_headings": 0,
"standard": "Yes"
}

View File

@@ -0,0 +1,129 @@
{%- from "templates/print_formats/standard_macros.html" import add_header, render_field, print_value, fieldmeta,
get_width, get_align_class -%}
{%- macro render_currency(df, doc) -%}
<div class="row {% if df.bold %}important{% endif %} data-field">
<div class="col-xs-{{ "9" if df.fieldtype=="Check" else "5" }}
{%- if doc.align_labels_right %} text-right{%- endif -%}">
<label>{{ _(df.label) }}</label>
</div>
<div class="col-xs-{{ "3" if df.fieldtype=="Check" else "7" }} value">
{% if doc.get(df.fieldname) != None -%}
{{ frappe.utils.fmt_money((doc[df.fieldname])|int|abs, currency=doc.currency) }}
{% endif %}
</div>
</div>
{%- endmacro -%}
{%- macro render_taxes(df, doc) -%}
{%- set data = doc.get(df.fieldname)[df.start:df.end] -%}
<div class="row">
<div class="col-xs-6"></div>
<div class="col-xs-6">
{%- for charge in data -%}
{%- if (charge.tax_amount or doc.flags.print_taxes_with_zero_amount) and (not charge.included_in_print_rate or doc.flags.show_inclusive_tax_in_print) -%}
<div class="row">
<div class="col-xs-5 {%- if doc.align_labels_right %} text-right{%- endif -%}">
<label>{{ charge.get_formatted("description") }}</label></div>
<div class="col-xs-7 text-right">
{{ frappe.utils.fmt_money((charge.tax_amount)|int|abs, currency=doc.currency) }}
</div>
</div>
{%- endif -%}
{%- endfor -%}
</div>
</div>
{%- endmacro -%}
{%- macro render_table(df, doc) -%}
{%- set table_meta = frappe.get_meta(df.options) -%}
{%- set data = doc.get(df.fieldname)[df.start:df.end] -%}
{%- if doc.print_templates and
doc.print_templates.get(df.fieldname) -%}
{% include doc.print_templates[df.fieldname] %}
{%- else -%}
{%- if data -%}
{%- set visible_columns = get_visible_columns(doc.get(df.fieldname),
table_meta, df) -%}
<div {{ fieldmeta(df) }}>
<table class="table table-bordered table-condensed">
<thead>
<tr>
<th style="width: 40px" class="table-sr">{{ _("Sr") }}</th>
{% for tdf in visible_columns %}
{% if (data and not data[0].flags.compact_item_print) or tdf.fieldname in doc.get(df.fieldname)[0].flags.compact_item_fields %}
<th style="width: {{ get_width(tdf) }};" class="{{ get_align_class(tdf) }}" {{ fieldmeta(df) }}>
{{ _(tdf.label) }}</th>
{% endif %}
{% endfor %}
</tr>
</thead>
<tbody>
{% for d in data %}
<tr>
<td class="table-sr">{{ d.idx }}</td>
{% for tdf in visible_columns %}
{% if not d.flags.compact_item_print or tdf.fieldname in doc.get(df.fieldname)[0].flags.compact_item_fields %}
<td class="{{ get_align_class(tdf) }}" {{ fieldmeta(df) }}>
{% if tdf.fieldtype == 'Currency' %}
<div class="value">{{ frappe.utils.fmt_money((d[tdf.fieldname])|int|abs, currency=doc.currency) }}</div></td>
{% else %}
<div class="value">{{ print_value(tdf, d, doc, visible_columns) }}</div></td>
{% endif %}
{% endif %}
{% endfor %}
</tr>
{% endfor %}
</tbody>
</table>
</div>
{%- endif -%}
{%- endif -%}
{%- endmacro -%}
{% for page in layout %}
<div class="page-break">
<div {% if print_settings.repeat_header_footer %} id="header-html" class="hidden-pdf" {% endif %}>
{{ add_header(loop.index, layout|len, doc, letter_head, no_letterhead, footer, print_settings) }}
</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 %}
{% for section in page %}
<div class="row section-break">
{% if section.columns.fields %}
{%- if doc.print_line_breaks and loop.index != 1 -%}<hr>{%- endif -%}
{%- if doc.print_section_headings and section.label and section.has_data -%}
<h4 class='col-sm-12'>{{ _(section.label) }}</h4>
{% endif %}
{%- endif -%}
{% for column in section.columns %}
<div class="col-xs-{{ (12 / section.columns|len)|int }} column-break">
{% for df in column.fields %}
{% if df.fieldname == 'taxes' %}
{{ render_taxes(df, doc) }}
{% elif df.fieldtype == 'Currency' %}
{{ render_currency(df, doc) }}
{% elif df.fieldtype =='Table' %}
{{ render_table(df, doc)}}
{% elif doc[df.fieldname] %}
{{ render_field(df, doc) }}
{% endif %}
{% endfor %}
</div>
{% endfor %}
</div>
{% endfor %}
</div>
{% endfor %}

View File

@@ -0,0 +1,24 @@
{
"align_labels_right": 1,
"creation": "2019-07-24 20:13:30.259953",
"custom_format": 0,
"default_print_language": "en-US",
"disabled": 0,
"doc_type": "Sales Invoice",
"docstatus": 0,
"doctype": "Print Format",
"font": "Default",
"html": "",
"idx": 0,
"line_breaks": 1,
"modified": "2019-07-24 20:13:30.259953",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Sales Invoice Return",
"owner": "Administrator",
"print_format_builder": 0,
"print_format_type": "Jinja",
"raw_printing": 0,
"show_section_headings": 1,
"standard": "Yes"
}

View File

@@ -1,275 +1,269 @@
<style>
.print-format {
padding: 4mm;
font-size: 8.0pt !important;
}
.print-format td {
vertical-align:middle !important;
}
</style>
.print-format {
padding: 4mm;
font-size: 8.0pt !important;
}
.print-format td {
vertical-align:middle !important;
}
</style>
<h2 class="text-center" style="margin-top:0">{%= __(report.report_name) %}</h2>
<h4 class="text-center">
{% if (filters.customer_name) { %}
{%= filters.customer_name %}
{% } else { %}
{%= filters.customer || filters.supplier %}
{% } %}
</h4>
<h6 class="text-center">
{% if (filters.tax_id) { %}
{%= __("Tax Id: ")%} {%= filters.tax_id %}
<h2 class="text-center" style="margin-top:0">{%= __(report.report_name) %}</h2>
<h4 class="text-center">
{% if (filters.customer_name) { %}
{%= filters.customer_name %}
{% } else { %}
{%= filters.customer || filters.supplier %}
{% } %}
</h6>
<h5 class="text-center">
{%= __(filters.ageing_based_on) %}
{%= __("Until") %}
{%= frappe.datetime.str_to_user(filters.report_date) %}
</h5>
</h4>
<h6 class="text-center">
{% if (filters.tax_id) { %}
{%= __("Tax Id: ")%} {%= filters.tax_id %}
{% } %}
</h6>
<h5 class="text-center">
{%= __(filters.ageing_based_on) %}
{%= __("Until") %}
{%= frappe.datetime.str_to_user(filters.report_date) %}
</h5>
<div class="clearfix">
<div class="pull-left">
{% if(filters.payment_terms) { %}
<strong>{%= __("Payment Terms") %}:</strong> {%= filters.payment_terms %}
{% } %}
<div class="clearfix">
<div class="pull-left">
{% if(filters.payment_terms) { %}
<strong>{%= __("Payment Terms") %}:</strong> {%= filters.payment_terms %}
{% } %}
</div>
<div class="pull-right">
{% if(filters.credit_limit) { %}
<strong>{%= __("Credit Limit") %}:</strong> {%= format_currency(filters.credit_limit) %}
{% } %}
</div>
</div>
<div class="pull-right">
{% if(filters.credit_limit) { %}
<strong>{%= __("Credit Limit") %}:</strong> {%= format_currency(filters.credit_limit) %}
{% 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;
%}
{% if(balance_row) { %}
<table class="table table-bordered table-condensed">
<caption class="text-right">(Amount in {%= data[0]["currency"] || "" %})</caption>
<colgroup>
<col style="width: 30mm;">
<col style="width: 18mm;">
<col style="width: 18mm;">
<col style="width: 18mm;">
<col style="width: 18mm;">
<col style="width: 18mm;">
<col style="width: 18mm;">
<col style="width: 18mm;">
</colgroup>
<thead>
<tr>
<th>{%= __(" ") %}</th>
<th>{%= __(range1) %}</th>
<th>{%= __(range2) %}</th>
<th>{%= __(range3) %}</th>
<th>{%= __(range4) %}</th>
<th>{%= __(range5) %}</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_currency(flt(balance_row["outstanding"]), data[data.length-1]["currency"]) %}
</td>
</tr>
<td>{%= __("Future Payments") %}</td>
<td></td>
<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>
<tr class="cvs-footer">
<th class="text-left">{%= __("Cheques Required") %}</th>
<th></th>
<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>
</tbody>
</table>
{% } %}
{% } %}
</div>
</div>
{% if(filters.show_pdc_in_print) { %}
{% 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 range6 = report.columns[16].label;
%}
{% if(balance_row) { %}
<table class="table table-bordered table-condensed">
<caption class="text-right">(Amount in {%= data[0][__("currency")] || "" %})</caption>
<colgroup>
<col style="width: 30mm;">
<col style="width: 18mm;">
<col style="width: 18mm;">
<col style="width: 18mm;">
<col style="width: 18mm;">
<col style="width: 18mm;">
<col style="width: 18mm;">
<col style="width: 18mm;">
<col style="width: 18mm;">
</colgroup>
<table class="table table-bordered">
<thead>
<tr>
<th>{%= __(" ") %}</th>
<th>{%= __(range1) %}</th>
<th>{%= __(range2) %}</th>
<th>{%= __(range3) %}</th>
<th>{%= __(range4) %}</th>
<th>{%= __(range5) %}</th>
<th>{%= __(range6) %}</th>
<th>{%= __("Total") %}</th>
{% if(report.report_name === "Accounts Receivable" || report.report_name === "Accounts Payable") { %}
<th style="width: 10%">{%= __("Date") %}</th>
<th style="width: 4%">{%= __("Age (Days)") %}</th>
{% if(report.report_name === "Accounts Receivable" && filters.show_sales_person) { %}
<th style="width: 14%">{%= __("Reference") %}</th>
<th style="width: 10%">{%= __("Sales Person") %}</th>
{% } else { %}
<th style="width: 24%">{%= __("Reference") %}</th>
{% } %}
{% if(!filters.show_future_payments) { %}
<th style="width: 20%">{%= (filters.customer || filters.supplier) ? __("Remarks"): __("Party") %}</th>
{% } %}
<th style="width: 10%; text-align: right">{%= __("Invoiced Amount") %}</th>
{% if(!filters.show_future_payments) { %}
<th style="width: 10%; text-align: right">{%= __("Paid Amount") %}</th>
<th style="width: 10%; text-align: right">{%= report.report_name === "Accounts Receivable" ? __('Credit Note') : __('Debit Note') %}</th>
{% } %}
<th style="width: 10%; text-align: right">{%= __("Outstanding Amount") %}</th>
{% if(filters.show_future_payments) { %}
{% if(report.report_name === "Accounts Receivable") { %}
<th style="width: 12%">{%= __("Customer LPO No.") %}</th>
{% } %}
<th style="width: 10%">{%= __("Future Payment Ref") %}</th>
<th style="width: 10%">{%= __("Future Payment Amount") %}</th>
<th style="width: 10%">{%= __("Remaining Balance") %}</th>
{% } %}
{% } else { %}
<th style="width: 40%">{%= (filters.customer || filters.supplier) ? __("Remarks"): __("Party") %}</th>
<th style="width: 15%">{%= __("Total Invoiced Amount") %}</th>
<th style="width: 15%">{%= __("Total Paid Amount") %}</th>
<th style="width: 15%">{%= report.report_name === "Accounts Receivable Summary" ? __('Credit Note Amount') : __('Debit Note Amount') %}</th>
<th style="width: 15%">{%= __("Total Outstanding Amount") %}</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_currency(balance_row[range6]) %}</td>
<td class="text-right">
{%= format_currency(flt(balance_row[("outstanding_amount")]), data[data.length-1]["currency"]) %}
</td>
</tr>
<td>{%= __("PDC/LC") %}</td>
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
<td class="text-right">
{%= format_currency(flt(balance_row[("pdc/lc_amount")]), data[data.length-1]["currency"]) %}
</td>
<tr class="cvs-footer">
<th class="text-left">{%= __("Cheques Required") %}</th>
<th></th>
<th></th>
<th></th>
<th></th>
<th></th>
<th></th>
<th class="text-right">
{%= format_currency(flt(balance_row[("outstanding_amount")]-balance_row[("pdc/lc_amount")]), data[data.length-1]["currency"]) %}</th>
</tr>
</tbody>
</table>
{% } %}
{% } %}
<table class="table table-bordered">
<thead>
<tr>
{% if(report.report_name === "Accounts Receivable" || report.report_name === "Accounts Payable") { %}
<th style="width: 10%">{%= __("Date") %}</th>
<th style="width: 4%">{%= __("Age (Days)") %}</th>
{% if(report.report_name === "Accounts Receivable" && filters.show_sales_person_in_print) { %}
<th style="width: 14%">{%= __("Reference") %}</th>
<th style="width: 10%">{%= __("Sales Person") %}</th>
{% } else { %}
<th style="width: 24%">{%= __("Reference") %}</th>
{% } %}
{% if(!filters.show_pdc_in_print) { %}
<th style="width: 20%">{%= (filters.customer || filters.supplier) ? __("Remarks"): __("Party") %}</th>
{% } %}
<th style="width: 10%; text-align: right">{%= __("Invoiced Amount") %}</th>
{% if(!filters.show_pdc_in_print) { %}
<th style="width: 10%; text-align: right">{%= __("Paid Amount") %}</th>
<th style="width: 10%; text-align: right">{%= report.report_name === "Accounts Receivable" ? __('Credit Note') : __('Debit Note') %}</th>
{% } %}
<th style="width: 10%; text-align: right">{%= __("Outstanding Amount") %}</th>
{% if(filters.show_pdc_in_print) { %}
{% if(report.report_name === "Accounts Receivable") { %}
<th style="width: 12%">{%= __("Customer LPO No.") %}</th>
{% } %}
<th style="width: 10%">{%= __("PDC/LC Ref") %}</th>
<th style="width: 10%">{%= __("PDC/LC Amount") %}</th>
<th style="width: 10%">{%= __("Remaining Balance") %}</th>
{% } %}
{% } else { %}
<th style="width: 40%">{%= (filters.customer || filters.supplier) ? __("Remarks"): __("Party") %}</th>
<th style="width: 15%">{%= __("Total Invoiced Amount") %}</th>
<th style="width: 15%">{%= __("Total Paid Amount") %}</th>
<th style="width: 15%">{%= report.report_name === "Accounts Receivable Summary" ? __('Credit Note Amount') : __('Debit Note Amount') %}</th>
<th style="width: 15%">{%= __("Total Outstanding Amount") %}</th>
{% } %}
</tr>
</thead>
<tbody>
{% for(var i=0, l=data.length; i<l; i++) { %}
<tr>
{% if(report.report_name === "Accounts Receivable" || report.report_name === "Accounts Payable") { %}
{% if(data[i][__("Customer")] || data[i][__("Supplier")]) { %}
<td>{%= frappe.datetime.str_to_user(data[i]["posting_date"]) %}</td>
<td style="text-align: right">{%= data[i][__("Age (Days)")] %}</td>
<td>
{% if(!filters.show_pdc_in_print) { %}
{%= data[i]["voucher_type"] %}
<br>
{% } %}
{%= data[i]["voucher_no"] %}
</td>
{% if(report.report_name === "Accounts Receivable" && filters.show_sales_person_in_print) { %}
<td>{%= data[i]["sales_person"] %}</td>
{% } %}
{% if(!filters.show_pdc_in_print) { %}
<td>
{% if(!(filters.customer || filters.supplier)) { %}
{%= data[i][__("Customer")] || data[i][__("Supplier")] %}
{% if(data[i][__("Customer Name")] && data[i][__("Customer Name")] != data[i][__("Customer")]) { %}
<br> {%= data[i][__("Customer Name")] %}
{% } else if(data[i][__("Supplier Name")] != data[i][__("Supplier")]) { %}
<br> {%= data[i][__("Supplier Name")] %}
{% for(var i=0, l=data.length; i<l; i++) { %}
<tr>
{% if(report.report_name === "Accounts Receivable" || report.report_name === "Accounts Payable") { %}
{% if(data[i]["party"]) { %}
<td>{%= frappe.datetime.str_to_user(data[i]["posting_date"]) %}</td>
<td style="text-align: right">{%= data[i]["age"] %}</td>
<td>
{% if(!filters.show_future_payments) { %}
{%= data[i]["voucher_type"] %}
<br>
{% } %}
{%= data[i]["voucher_no"] %}
</td>
{% if(report.report_name === "Accounts Receivable" && filters.show_sales_person) { %}
<td>{%= data[i]["sales_person"] %}</td>
{% } %}
<div>
{% if data[i][__("Remarks")] %}
{%= __("Remarks") %}:
{%= data[i][__("Remarks")] %}
{% } %}
</div>
</td>
{% } %}
<td style="text-align: right">
{%= format_currency(data[i]["invoiced_amount"], data[i]["currency"]) %}</td>
{% if(!filters.show_pdc_in_print) { %}
<td style="text-align: right">
{%= format_currency(data[i]["paid_amount"], data[i]["currency"]) %}</td>
<td style="text-align: right">
{%= report.report_name === "Accounts Receivable" ? format_currency(data[i]["credit_note"], data[i]["currency"]) : format_currency(data[i]["debit_note"], data[i]["currency"]) %}</td>
{% } %}
<td style="text-align: right">
{%= format_currency(data[i]["outstanding_amount"], data[i]["currency"]) %}</td>
{% if(filters.show_pdc_in_print) { %}
{% if(report.report_name === "Accounts Receivable") { %}
<td style="text-align: right">
{%= data[i]["po_no"] %}</td>
{% } %}
<td style="text-align: right">{%= data[i][("pdc/lc_ref")] %}</td>
<td style="text-align: right">{%= format_currency(data[i][("pdc/lc_amount")], data[i]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i][("remaining_balance")], data[i]["currency"]) %}</td>
{% } %}
{% } else { %}
<td></td>
{% if(!filters.show_pdc_in_print) { %}
<td></td>
{% } %}
{% if(report.report_name === "Accounts Receivable" && filters.show_sales_person_in_print) { %}
<td></td>
{% } %}
<td></td>
<td style="text-align: right"><b>{%= __("Total") %}</b></td>
<td style="text-align: right">
{%= format_currency(data[i]["invoiced_amount"], data[i]["currency"] ) %}</td>
{% if(!filters.show_pdc_in_print) { %}
<td style="text-align: right">
{%= format_currency(data[i]["paid_amount"], data[i]["currency"]) %}</td>
<td style="text-align: right">{%= report.report_name === "Accounts Receivable" ? format_currency(data[i]["credit_note"], data[i]["currency"]) : format_currency(data[i]["debit_note"], data[i]["currency"]) %} </td>
{% } %}
<td style="text-align: right">
{%= format_currency(data[i]["outstanding_amount"], data[i]["currency"]) %}</td>
{% if(filters.show_pdc_in_print) { %}
{% if(report.report_name === "Accounts Receivable") { %}
<td style="text-align: right">
{%= data[i][__("Customer LPO")] %}</td>
{% } %}
<td style="text-align: right">{%= data[i][("pdc/lc_ref")] %}</td>
<td style="text-align: right">{%= format_currency(data[i][("pdc/lc_amount")], data[i]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i][("remaining_balance")], data[i]["currency"]) %}</td>
{% } %}
{% } %}
{% } else { %}
{% if(data[i][__("Customer")] || data[i][__("Supplier")]|| "&nbsp;") { %}
{% if((data[i][__("Customer")] || data[i][__("Supplier")]) != __("'Total'")) { %}
{% if(!filters.show_future_payments) { %}
<td>
{% if(!(filters.customer || filters.supplier)) { %}
{%= data[i][__("Customer")] || data[i][__("Supplier")] %}
{% if(data[i][__("Customer Name")] && data[i][__("Customer Name")] != data[i][__("Customer")]) { %}
<br> {%= data[i][__("Customer Name")] %}
{% } else if(data[i][__("Supplier Name")] != data[i][__("Supplier")]) { %}
<br> {%= data[i][__("Supplier Name")] %}
{%= data[i]["party"] %}
{% if(data[i]["customer_name"] && data[i]["customer_name"] != data[i]["party"]) { %}
<br> {%= data[i]["customer_name"] %}
{% } else if(data[i]["supplier_name"] != data[i]["party"]) { %}
<br> {%= data[i]["supplier_name"] %}
{% } %}
{% } %}
<br>{%= __("Remarks") %}:
{%= data[i][__("Remarks")] %}
<div>
{% if data[i]["remarks"] %}
{%= __("Remarks") %}:
{%= data[i]["remarks"] %}
{% } %}
</div>
</td>
{% } %}
<td style="text-align: right">
{%= 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[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>
{% if(filters.show_future_payments) { %}
{% if(report.report_name === "Accounts Receivable") { %}
<td style="text-align: right">
{%= 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[i]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i]["remaining_balance"], data[i]["currency"]) %}</td>
{% } %}
{% } else { %}
<td><b>{%= __("Total") %}</b></td>
<td></td>
{% if(!filters.show_future_payments) { %}
<td></td>
{% } %}
{% if(report.report_name === "Accounts Receivable" && filters.show_sales_person) { %}
<td></td>
{% } %}
<td></td>
<td style="text-align: right"><b>{%= __("Total") %}</b></td>
<td style="text-align: right">
{%= 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[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>
{% if(filters.show_future_payments) { %}
{% if(report.report_name === "Accounts Receivable") { %}
<td style="text-align: right">
{%= 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[i]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i]["remaining_balance"], data[i]["currency"]) %}</td>
{% } %}
{% } %}
{% } else { %}
{% if(data[i]["party"]|| "&nbsp;") { %}
{% if((data[i]["party"]) != __("'Total'")) { %}
<td>
{% if(!(filters.customer || filters.supplier)) { %}
{%= data[i]["party"] %}
{% if(data[i]["customer_name"] && data[i]["customer_name"] != data[i]["party"]) { %}
<br> {%= data[i]["customer_name"] %}
{% } else if(data[i]["supplier_name"] != data[i]["party"]) { %}
<br> {%= data[i]["supplier_name"] %}
{% } %}
{% } %}
<br>{%= __("Remarks") %}:
{%= data[i]["remarks"] %}
</td>
{% } else { %}
<td><b>{%= __("Total") %}</b></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>
{% } %}
<td style="text-align: right">{%= format_currency(data[i][("total_invoiced_amt")], data[i]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i][("total_paid_amt")], data[i]["currency"]) %}</td>
<td style="text-align: right">{%= report.report_name === "Accounts Receivable Summary" ? format_currency(data[i][__("credit_note_amt")], data[i]["currency"]) : format_currency(data[i][__("debit_note_amt")], data[i]["currency"]) %}</td>
<td style="text-align: right">{%= format_currency(data[i][("total_outstanding_amt")], data[i]["currency"]) %}</td>
{% } %}
</tr>
{% } %}
</tr>
{% } %}
</tbody>
</table>
<p class="text-right text-muted">{{ __("Printed On ") }}{%= frappe.datetime.str_to_user(frappe.datetime.get_datetime_as_string()) %}</p>
</tbody>
</table>
<p class="text-right text-muted">{{ __("Printed On ") }}{%= frappe.datetime.str_to_user(frappe.datetime.get_datetime_as_string()) %}</p>

View File

@@ -130,13 +130,18 @@ frappe.query_reports["Accounts Receivable"] = {
"fieldtype": "Check",
},
{
"fieldname":"show_pdc_in_print",
"label": __("Show PDC in Print"),
"fieldname":"show_future_payments",
"label": __("Show Future Payments"),
"fieldtype": "Check",
},
{
"fieldname":"show_sales_person_in_print",
"label": __("Show Sales Person in Print"),
"fieldname":"show_delivery_notes",
"label": __("Show Delivery Notes"),
"fieldtype": "Check",
},
{
"fieldname":"show_sales_person",
"label": __("Show Sales Person"),
"fieldtype": "Check",
},
{

View File

@@ -14,33 +14,44 @@ class TestAccountsReceivable(unittest.TestCase):
filters = {
'company': '_Test Company 2',
'based_on_payment_terms': 1
'based_on_payment_terms': 1,
'report_date': today(),
'range1': 30,
'range2': 60,
'range3': 90,
'range4': 120
}
# check invoice grand total and invoiced column's value for 3 payment terms
name = make_sales_invoice()
report = execute(filters)
expected_data = [[100,30], [100,50], [100,20]]
expected_data = [[100, 30], [100, 50], [100, 20]]
self.assertEqual(expected_data[0], report[1][0][7:9])
self.assertEqual(expected_data[1], report[1][1][7:9])
self.assertEqual(expected_data[2], report[1][2][7:9])
for i in range(3):
row = report[1][i-1]
self.assertEqual(expected_data[i-1], [row.invoice_grand_total, row.invoiced])
# check invoice grand total, invoiced, paid and outstanding column's value after payment
make_payment(name)
report = execute(filters)
expected_data_after_payment = [[100,50], [100,20]]
expected_data_after_payment = [[100, 50, 10, 40], [100, 20, 0, 20]]
self.assertEqual(expected_data_after_payment[0], report[1][0][7:9])
self.assertEqual(expected_data_after_payment[1], report[1][1][7:9])
for i in range(2):
row = report[1][i-1]
self.assertEqual(expected_data_after_payment[i-1],
[row.invoice_grand_total, row.invoiced, row.paid, row.outstanding])
# check invoice grand total, invoiced, paid and outstanding column's value after credit note
make_credit_note(name)
report = execute(filters)
expected_data_after_credit_note = [[100,100,30,100,-30]]
self.assertEqual(expected_data_after_credit_note[0], report[1][0][7:12])
expected_data_after_credit_note = [100, 0, 0, 40, -40]
row = report[1][0]
self.assertEqual(expected_data_after_credit_note,
[row.invoice_grand_total, row.invoiced, row.paid, row.credit_note, row.outstanding])
def make_sales_invoice():
frappe.set_user("Administrator")
@@ -64,7 +75,7 @@ def make_sales_invoice():
return si.name
def make_payment(docname):
pe = get_payment_entry("Sales Invoice", docname, bank_account="Cash - _TC2", party_amount=30)
pe = get_payment_entry("Sales Invoice", docname, bank_account="Cash - _TC2", party_amount=40)
pe.paid_from = "Debtors - _TC2"
pe.insert()
pe.submit()

View File

@@ -3,236 +3,11 @@
from __future__ import unicode_literals
import frappe
from frappe import _, scrub
from frappe.utils import flt
from frappe import _
from frappe.utils import flt, cint
from erpnext.accounts.party import get_partywise_advanced_payment_amount
from erpnext.accounts.report.accounts_receivable.accounts_receivable import ReceivablePayableReport
from six import iteritems
from six.moves import zip
class AccountsReceivableSummary(ReceivablePayableReport):
def run(self, args):
party_naming_by = frappe.db.get_value(args.get("naming_by")[0], None, args.get("naming_by")[1])
return self.get_columns(party_naming_by, args), self.get_data(party_naming_by, args)
def get_columns(self, party_naming_by, args):
columns = [_(args.get("party_type")) + ":Link/" + args.get("party_type") + ":200"]
if party_naming_by == "Naming Series":
columns += [ args.get("party_type") + " Name::140"]
credit_debit_label = "Credit Note Amt" if args.get('party_type') == 'Customer' else "Debit Note Amt"
columns += [{
"label": _("Advance Amount"),
"fieldname": "advance_amount",
"fieldtype": "Currency",
"options": "currency",
"width": 100
},{
"label": _("Total Invoiced Amt"),
"fieldname": "total_invoiced_amt",
"fieldtype": "Currency",
"options": "currency",
"width": 100
},
{
"label": _("Total Paid Amt"),
"fieldname": "total_paid_amt",
"fieldtype": "Currency",
"options": "currency",
"width": 100
}]
columns += [
{
"label": _(credit_debit_label),
"fieldname": scrub(credit_debit_label),
"fieldtype": "Currency",
"options": "currency",
"width": 140
},
{
"label": _("Total Outstanding Amt"),
"fieldname": "total_outstanding_amt",
"fieldtype": "Currency",
"options": "currency",
"width": 160
},
{
"label": _("0-" + str(self.filters.range1)),
"fieldname": scrub("0-" + str(self.filters.range1)),
"fieldtype": "Currency",
"options": "currency",
"width": 160
},
{
"label": _(str(self.filters.range1) + "-" + str(self.filters.range2)),
"fieldname": scrub(str(self.filters.range1) + "-" + str(self.filters.range2)),
"fieldtype": "Currency",
"options": "currency",
"width": 160
},
{
"label": _(str(self.filters.range2) + "-" + str(self.filters.range3)),
"fieldname": scrub(str(self.filters.range2) + "-" + str(self.filters.range3)),
"fieldtype": "Currency",
"options": "currency",
"width": 160
},
{
"label": _(str(self.filters.range3) + "-" + str(self.filters.range4)),
"fieldname": scrub(str(self.filters.range3) + "-" + str(self.filters.range4)),
"fieldtype": "Currency",
"options": "currency",
"width": 160
},
{
"label": _(str(self.filters.range4) + _("-Above")),
"fieldname": scrub(str(self.filters.range4) + _("-Above")),
"fieldtype": "Currency",
"options": "currency",
"width": 160
}
]
if args.get("party_type") == "Customer":
columns += [{
"label": _("Territory"),
"fieldname": "territory",
"fieldtype": "Link",
"options": "Territory",
"width": 80
},
{
"label": _("Customer Group"),
"fieldname": "customer_group",
"fieldtype": "Link",
"options": "Customer Group",
"width": 80
},
{
"label": _("Sales Person"),
"fieldtype": "Data",
"fieldname": "sales_person",
"width": 120,
}]
if args.get("party_type") == "Supplier":
columns += [{
"label": _("Supplier Group"),
"fieldname": "supplier_group",
"fieldtype": "Link",
"options": "Supplier Group",
"width": 80
}]
columns.append({
"fieldname": "currency",
"label": _("Currency"),
"fieldtype": "Link",
"options": "Currency",
"width": 80
})
return columns
def get_data(self, party_naming_by, args):
data = []
partywise_total = self.get_partywise_total(party_naming_by, args)
partywise_advance_amount = get_partywise_advanced_payment_amount(args.get("party_type"),
self.filters.get("report_date")) or {}
for party, party_dict in iteritems(partywise_total):
row = [party]
if party_naming_by == "Naming Series":
row += [self.get_party_name(args.get("party_type"), party)]
row += [partywise_advance_amount.get(party, 0)]
paid_amt = 0
if party_dict.paid_amt > 0:
paid_amt = flt(party_dict.paid_amt - partywise_advance_amount.get(party, 0))
row += [
party_dict.invoiced_amt, paid_amt, party_dict.credit_amt, party_dict.outstanding_amt,
party_dict.range1, party_dict.range2, party_dict.range3, party_dict.range4, party_dict.range5
]
if args.get("party_type") == "Customer":
row += [self.get_territory(party), self.get_customer_group(party), ", ".join(set(party_dict.sales_person))]
if args.get("party_type") == "Supplier":
row += [self.get_supplier_group(party)]
row.append(party_dict.currency)
data.append(row)
return data
def get_partywise_total(self, party_naming_by, args):
party_total = frappe._dict()
for d in self.get_voucherwise_data(party_naming_by, args):
party_total.setdefault(d.party,
frappe._dict({
"invoiced_amt": 0,
"paid_amt": 0,
"credit_amt": 0,
"outstanding_amt": 0,
"range1": 0,
"range2": 0,
"range3": 0,
"range4": 0,
"range5": 0,
"sales_person": []
})
)
for k in list(party_total[d.party]):
if k not in ["currency", "sales_person"]:
party_total[d.party][k] += flt(d.get(k, 0))
party_total[d.party].currency = d.currency
if d.sales_person:
party_total[d.party].sales_person.append(d.sales_person)
return party_total
def get_voucherwise_data(self, party_naming_by, args):
voucherwise_data = ReceivablePayableReport(self.filters).run(args)[1]
cols = ["posting_date", "party"]
if party_naming_by == "Naming Series":
cols += ["party_name"]
if args.get("party_type") == 'Customer':
cols += ["contact"]
cols += ["voucher_type", "voucher_no", "due_date"]
if args.get("party_type") == "Supplier":
cols += ["bill_no", "bill_date"]
cols += ["invoiced_amt", "paid_amt", "credit_amt",
"outstanding_amt", "age", "range1", "range2", "range3", "range4", "range5", "currency", "pdc/lc_date", "pdc/lc_ref",
"pdc/lc_amount"]
if args.get("party_type") == "Supplier":
cols += ["supplier_group", "remarks"]
if args.get("party_type") == "Customer":
cols += ["po_no", "do_no", "territory", "customer_group", "sales_person", "remarks"]
return self.make_data_dict(cols, voucherwise_data)
def make_data_dict(self, cols, data):
data_dict = []
for d in data:
data_dict.append(frappe._dict(zip(cols, d)))
return data_dict
def execute(filters=None):
args = {
@@ -241,3 +16,119 @@ def execute(filters=None):
}
return AccountsReceivableSummary(filters).run(args)
class AccountsReceivableSummary(ReceivablePayableReport):
def run(self, args):
self.party_type = args.get('party_type')
self.party_naming_by = frappe.db.get_value(args.get("naming_by")[0], None, args.get("naming_by")[1])
self.get_columns()
self.get_data(args)
return self.columns, self.data
def get_data(self, args):
self.data = []
self.receivables = ReceivablePayableReport(self.filters).run(args)[1]
self.get_party_total(args)
party_advance_amount = get_partywise_advanced_payment_amount(self.party_type,
self.filters.report_date) or {}
for party, party_dict in iteritems(self.party_total):
row = frappe._dict()
row.party = party
if self.party_naming_by == "Naming Series":
row.party_name = frappe.get_cached_value(self.party_type, party, [self.party_type + "_name"])
row.update(party_dict)
# Advance against party
row.advance = party_advance_amount.get(party, 0)
# In AR/AP, advance shown in paid columns,
# but in summary report advance shown in separate column
row.paid -= row.advance
self.data.append(row)
def get_party_total(self, args):
self.party_total = frappe._dict()
for d in self.receivables:
self.init_party_total(d)
# Add all amount columns
for k in list(self.party_total[d.party]):
if k not in ["currency", "sales_person"]:
self.party_total[d.party][k] += d.get(k, 0.0)
# set territory, customer_group, sales person etc
self.set_party_details(d)
def init_party_total(self, row):
self.party_total.setdefault(row.party, frappe._dict({
"invoiced": 0.0,
"paid": 0.0,
"credit_note": 0.0,
"outstanding": 0.0,
"range1": 0.0,
"range2": 0.0,
"range3": 0.0,
"range4": 0.0,
"range5": 0.0,
"sales_person": []
}))
def set_party_details(self, row):
self.party_total[row.party].currency = row.currency
for key in ('territory', 'customer_group', 'supplier_group'):
if row.get(key):
self.party_total[row.party][key] = row.get(key)
if row.sales_person:
self.party_total[row.party].sales_person.append(row.sales_person)
def get_columns(self):
self.columns = []
self.add_column(label=_(self.party_type), fieldname='party',
fieldtype='Link', options=self.party_type, width=180)
if self.party_naming_by == "Naming Series":
self.add_column(_('{0} Name').format(self.party_type),
fieldname = 'party_name', fieldtype='Data')
credit_debit_label = "Credit Note" if self.party_type == 'Customer' else "Debit Note"
self.add_column(_('Advance Amount'), fieldname='advance')
self.add_column(_('Invoiced Amount'), fieldname='invoiced')
self.add_column(_('Paid Amount'), fieldname='paid')
self.add_column(_(credit_debit_label), fieldname='credit_note')
self.add_column(_('Outstanding Amount'), fieldname='outstanding')
self.setup_ageing_columns()
if self.party_type == "Customer":
self.add_column(label=_('Territory'), fieldname='territory', fieldtype='Link',
options='Territory')
self.add_column(label=_('Customer Group'), fieldname='customer_group', fieldtype='Link',
options='Customer Group')
if self.filters.show_sales_person:
self.add_column(label=_('Sales Person'), fieldname='sales_person', fieldtype='Data')
else:
self.add_column(label=_('Supplier Group'), fieldname='supplier_group', fieldtype='Link',
options='Supplier Group')
self.add_column(label=_('Currency'), fieldname='currency', fieldtype='Link',
options='Currency', width=80)
def setup_ageing_columns(self):
for i, label in enumerate(["0-{range1}".format(range1=self.filters["range1"]),
"{range1}-{range2}".format(range1=cint(self.filters["range1"])+ 1, range2=self.filters["range2"]),
"{range2}-{range3}".format(range2=cint(self.filters["range2"])+ 1, range3=self.filters["range3"]),
"{range3}-{range4}".format(range3=cint(self.filters["range3"])+ 1, range4=self.filters["range4"]),
"{range4}-{above}".format(range4=cint(self.filters["range4"])+ 1, above=_("Above"))]):
self.add_column(label=label, fieldname='range' + str(i+1))

View File

@@ -135,11 +135,11 @@ def get_chart_data(filters, columns, asset, liability, equity):
datasets = []
if asset_data:
datasets.append({'name':'Assets', 'values': asset_data})
datasets.append({'name': _('Assets'), 'values': asset_data})
if liability_data:
datasets.append({'name':'Liabilities', 'values': liability_data})
datasets.append({'name': _('Liabilities'), 'values': liability_data})
if equity_data:
datasets.append({'name':'Equity', 'values': equity_data})
datasets.append({'name': _('Equity'), 'values': equity_data})
chart = {
"data": {

View File

@@ -425,9 +425,12 @@ def get_cost_centers_with_children(cost_centers):
all_cost_centers = []
for d in cost_centers:
lft, rgt = frappe.db.get_value("Cost Center", d, ["lft", "rgt"])
children = frappe.get_all("Cost Center", filters={"lft": [">=", lft], "rgt": ["<=", rgt]})
all_cost_centers += [c.name for c in children]
if frappe.db.exists("Cost Center", d):
lft, rgt = frappe.db.get_value("Cost Center", d, ["lft", "rgt"])
children = frappe.get_all("Cost Center", filters={"lft": [">=", lft], "rgt": ["<=", rgt]})
all_cost_centers += [c.name for c in children]
else:
frappe.throw(_("Cost Center: {0} does not exist".format(d)))
return list(set(all_cost_centers))

View File

@@ -119,19 +119,11 @@ def get_gl_entries(filters):
select_fields = """, debit, credit, debit_in_account_currency,
credit_in_account_currency """
group_by_statement = ''
order_by_statement = "order by posting_date, account"
if filters.get("group_by") == _("Group by Voucher"):
order_by_statement = "order by posting_date, voucher_type, voucher_no"
if filters.get("group_by") == _("Group by Voucher (Consolidated)"):
group_by_statement = "group by voucher_type, voucher_no, account, cost_center"
select_fields = """, sum(debit) as debit, sum(credit) as credit,
sum(debit_in_account_currency) as debit_in_account_currency,
sum(credit_in_account_currency) as credit_in_account_currency"""
if filters.get("include_default_book_entries"):
filters['company_fb'] = frappe.db.get_value("Company",
filters.get("company"), 'default_finance_book')
@@ -144,11 +136,10 @@ def get_gl_entries(filters):
against_voucher_type, against_voucher, account_currency,
remarks, against, is_opening {select_fields}
from `tabGL Entry`
where company=%(company)s {conditions} {group_by_statement}
where company=%(company)s {conditions}
{order_by_statement}
""".format(
select_fields=select_fields, conditions=get_conditions(filters),
group_by_statement=group_by_statement,
order_by_statement=order_by_statement
),
filters, as_dict=1)
@@ -185,7 +176,8 @@ def get_conditions(filters):
if not (filters.get("account") or filters.get("party") or
filters.get("group_by") in ["Group by Account", "Group by Party"]):
conditions.append("posting_date >=%(from_date)s")
conditions.append("posting_date <=%(to_date)s")
conditions.append("(posting_date <=%(to_date)s or is_opening = 'Yes')")
if filters.get("project"):
conditions.append("project in %(project)s")
@@ -286,6 +278,7 @@ def initialize_gle_map(gl_entries, filters):
def get_accountwise_gle(filters, gl_entries, gle_map):
totals = get_totals_dict()
entries = []
consolidated_gle = OrderedDict()
group_by = group_by_field(filters.get('group_by'))
def update_value_in_dict(data, key, gle):
@@ -310,12 +303,20 @@ def get_accountwise_gle(filters, gl_entries, gle_map):
update_value_in_dict(totals, 'total', gle)
if filters.get("group_by") != _('Group by Voucher (Consolidated)'):
gle_map[gle.get(group_by)].entries.append(gle)
else:
entries.append(gle)
elif filters.get("group_by") == _('Group by Voucher (Consolidated)'):
key = (gle.get("voucher_type"), gle.get("voucher_no"),
gle.get("account"), gle.get("cost_center"))
if key not in consolidated_gle:
consolidated_gle.setdefault(key, gle)
else:
update_value_in_dict(consolidated_gle, key, gle)
update_value_in_dict(gle_map[gle.get(group_by)].totals, 'closing', gle)
update_value_in_dict(totals, 'closing', gle)
for key, value in consolidated_gle.items():
entries.append(value)
return totals, entries
def get_result_as_list(data, filters):

View File

@@ -27,8 +27,8 @@ frappe.query_reports["Payment Period Based On Invoice Date"] = {
fieldname:"payment_type",
label: __("Payment Type"),
fieldtype: "Select",
options: "Incoming\nOutgoing",
default: "Incoming"
options: __("Incoming") + "\n" + __("Outgoing"),
default: __("Incoming")
},
{
"fieldname":"party_type",

View File

@@ -39,8 +39,8 @@ def execute(filters=None):
return columns, data
def validate_filters(filters):
if (filters.get("payment_type") == "Incoming" and filters.get("party_type") == "Supplier") or \
(filters.get("payment_type") == "Outgoing" and filters.get("party_type") == "Customer"):
if (filters.get("payment_type") == _("Incoming") and filters.get("party_type") == "Supplier") or \
(filters.get("payment_type") == _("Outgoing") and filters.get("party_type") == "Customer"):
frappe.throw(_("{0} payment entries can not be filtered by {1}")\
.format(filters.payment_type, filters.party_type))
@@ -51,7 +51,7 @@ def get_columns(filters):
_("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") + (":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",
@@ -69,7 +69,7 @@ def get_conditions(filters):
conditions = []
if not filters.party_type:
if filters.payment_type == "Outgoing":
if filters.payment_type == _("Outgoing"):
filters.party_type = "Supplier"
else:
filters.party_type = "Customer"
@@ -101,7 +101,7 @@ def get_entries(filters):
def get_invoice_posting_date_map(filters):
invoice_details = {}
dt = "Sales Invoice" if filters.get("payment_type") == "Incoming" else "Purchase Invoice"
dt = "Sales Invoice" if filters.get("payment_type") == _("Incoming") else "Purchase Invoice"
for t in frappe.db.sql("select name, posting_date, due_date from `tab{0}`".format(dt), as_dict=1):
invoice_details[t.name] = t

View File

@@ -75,11 +75,11 @@ def get_chart_data(filters, columns, income, expense, net_profit_loss):
datasets = []
if income_data:
datasets.append({'name': 'Income', 'values': income_data})
datasets.append({'name': _('Income'), 'values': income_data})
if expense_data:
datasets.append({'name': 'Expense', 'values': expense_data})
datasets.append({'name': _('Expense'), 'values': expense_data})
if net_profit:
datasets.append({'name': 'Net Profit/Loss', 'values': net_profit})
datasets.append({'name': _('Net Profit/Loss'), 'values': net_profit})
chart = {
"data": {

View File

@@ -84,7 +84,8 @@ def validate_fiscal_year(date, fiscal_year, company, label="Date", doc=None):
throw(_("{0} '{1}' not in Fiscal Year {2}").format(label, formatdate(date), fiscal_year))
@frappe.whitelist()
def get_balance_on(account=None, date=None, party_type=None, party=None, company=None, in_account_currency=True, cost_center=None):
def get_balance_on(account=None, date=None, party_type=None, party=None, company=None,
in_account_currency=True, cost_center=None, ignore_account_permission=False):
if not account and frappe.form_dict.get("account"):
account = frappe.form_dict.get("account")
if not date and frappe.form_dict.get("date"):
@@ -140,7 +141,8 @@ def get_balance_on(account=None, date=None, party_type=None, party=None, company
if account:
if not frappe.flags.ignore_account_permission:
if not (frappe.flags.ignore_account_permission
or ignore_account_permission):
acc.check_permission("read")
if report_type == 'Profit and Loss':

View File

@@ -255,9 +255,15 @@ class Asset(AccountsController):
precision = self.precision("gross_purchase_amount")
if row.depreciation_method in ("Straight Line", "Manual"):
depreciation_left = (cint(row.total_number_of_depreciations) - cint(self.number_of_depreciations_booked))
if not depreciation_left:
frappe.msgprint(_("All the depreciations has been booked"))
depreciation_amount = flt(row.expected_value_after_useful_life)
return depreciation_amount
depreciation_amount = (flt(row.value_after_depreciation) -
flt(row.expected_value_after_useful_life)) / (cint(row.total_number_of_depreciations) -
cint(self.number_of_depreciations_booked))
flt(row.expected_value_after_useful_life)) / depreciation_left
else:
depreciation_amount = flt(depreciable_value * (flt(row.rate_of_depreciation) / 100), precision)
@@ -275,7 +281,7 @@ class Asset(AccountsController):
flt(accumulated_depreciation_after_full_schedule),
self.precision('gross_purchase_amount'))
if (row.expected_value_after_useful_life and
if (row.expected_value_after_useful_life and
row.expected_value_after_useful_life < asset_value_after_full_schedule):
frappe.throw(_("Depreciation Row {0}: Expected value after useful life must be greater than or equal to {1}")
.format(row.idx, asset_value_after_full_schedule))
@@ -286,12 +292,6 @@ class Asset(AccountsController):
if self.status not in ("Submitted", "Partially Depreciated", "Fully Depreciated"):
frappe.throw(_("Asset cannot be cancelled, as it is already {0}").format(self.status))
if self.purchase_invoice:
frappe.throw(_("Please cancel Purchase Invoice {0} first").format(self.purchase_invoice))
if self.purchase_receipt:
frappe.throw(_("Please cancel Purchase Receipt {0} first").format(self.purchase_receipt))
def delete_depreciation_entries(self):
for d in self.get("schedules"):
if d.journal_entry:
@@ -345,6 +345,7 @@ class Asset(AccountsController):
if asset_movement:
doc = frappe.get_doc('Asset Movement', asset_movement)
doc.naming_series = 'ACC-ASM-.YYYY.-'
doc.submit()
def make_gl_entries(self):

View File

@@ -6,6 +6,7 @@ from __future__ import unicode_literals
import frappe
from frappe import _
from frappe.utils import flt, today, getdate, cint
from erpnext.accounts.doctype.accounting_dimension.accounting_dimension import get_checks_for_pl_and_bs_accounts
def post_depreciation_entries(date=None):
# Return if automatic booking of asset depreciation is disabled
@@ -41,6 +42,8 @@ def make_depreciation_entry(asset_name, date=None):
depreciation_cost_center = asset.cost_center or depreciation_cost_center
accounting_dimensions = get_checks_for_pl_and_bs_accounts()
for d in asset.get("schedules"):
if not d.journal_entry and getdate(d.schedule_date) <= getdate(date):
je = frappe.new_doc("Journal Entry")
@@ -51,23 +54,40 @@ def make_depreciation_entry(asset_name, date=None):
je.finance_book = d.finance_book
je.remark = "Depreciation Entry against {0} worth {1}".format(asset_name, d.depreciation_amount)
je.append("accounts", {
credit_entry = {
"account": accumulated_depreciation_account,
"credit_in_account_currency": d.depreciation_amount,
"reference_type": "Asset",
"reference_name": asset.name
})
}
je.append("accounts", {
debit_entry = {
"account": depreciation_expense_account,
"debit_in_account_currency": d.depreciation_amount,
"reference_type": "Asset",
"reference_name": asset.name,
"cost_center": depreciation_cost_center
})
}
for dimension in accounting_dimensions:
if (asset.get(dimension['fieldname']) or dimension.get('mandatory_for_bs')):
credit_entry.update({
dimension['fieldname']: asset.get(dimension['fieldname']) or dimension.get('default_dimension')
})
if (asset.get(dimension['fieldname']) or dimension.get('mandatory_for_pl')):
debit_entry.update({
dimension['fieldname']: asset.get(dimension['fieldname']) or dimension.get('default_dimension')
})
je.append("accounts", credit_entry)
je.append("accounts", debit_entry)
je.flags.ignore_permissions = True
je.submit()
je.save()
if not je.meta.get_workflow():
je.submit()
d.db_set("journal_entry", je.name)

View File

@@ -456,8 +456,6 @@ class TestAsset(unittest.TestCase):
self.assertEqual(gle, expected_gle)
si.cancel()
frappe.delete_doc("Sales Invoice", si.name)
self.assertEqual(frappe.db.get_value("Asset", asset.name, "status"), "Partially Depreciated")
def test_asset_expected_value_after_useful_life(self):

View File

@@ -1,685 +1,211 @@
{
"allow_copy": 0,
"allow_guest_to_view": 0,
"allow_import": 1,
"allow_rename": 0,
"autoname": "ACC-ASM-.YYYY.-.#####",
"beta": 0,
"creation": "2016-04-25 18:00:23.559973",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"document_type": "",
"editable_grid": 0,
"allow_import": 1,
"autoname": "naming_series:",
"creation": "2016-04-25 18:00:23.559973",
"doctype": "DocType",
"field_order": [
"naming_series",
"company",
"purpose",
"asset",
"transaction_date",
"column_break_4",
"quantity",
"select_serial_no",
"serial_no",
"section_break_7",
"source_location",
"target_location",
"column_break_10",
"from_employee",
"to_employee",
"reference",
"reference_doctype",
"reference_name",
"amended_from"
],
"fields": [
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "company",
"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": 1,
"label": "Company",
"length": 0,
"no_copy": 0,
"options": "Company",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 1,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "company",
"fieldtype": "Link",
"in_list_view": 1,
"in_standard_filter": 1,
"label": "Company",
"options": "Company",
"remember_last_selected_value": 1,
"reqd": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"default": "Transfer",
"fieldname": "purpose",
"fieldtype": "Select",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Purpose",
"length": 0,
"no_copy": 0,
"options": "\nIssue\nReceipt\nTransfer",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"default": "Transfer",
"fieldname": "purpose",
"fieldtype": "Select",
"label": "Purpose",
"options": "\nIssue\nReceipt\nTransfer",
"reqd": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "asset",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 1,
"in_list_view": 1,
"in_standard_filter": 1,
"label": "Asset",
"length": 0,
"no_copy": 0,
"options": "Asset",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "asset",
"fieldtype": "Link",
"in_global_search": 1,
"in_list_view": 1,
"in_standard_filter": 1,
"label": "Asset",
"options": "Asset",
"reqd": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "transaction_date",
"fieldtype": "Datetime",
"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": "Transaction Date",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "transaction_date",
"fieldtype": "Datetime",
"in_list_view": 1,
"label": "Transaction Date",
"reqd": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "column_break_4",
"fieldtype": "Column Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "column_break_4",
"fieldtype": "Column Break"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "quantity",
"fieldtype": "Float",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Quantity",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "quantity",
"fieldtype": "Float",
"label": "Quantity"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "select_serial_no",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Select Serial No",
"length": 0,
"no_copy": 0,
"options": "Serial No",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "select_serial_no",
"fieldtype": "Link",
"label": "Select Serial No",
"options": "Serial No"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "serial_no",
"fieldtype": "Small Text",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Serial No",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "serial_no",
"fieldtype": "Small Text",
"label": "Serial No"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "section_break_7",
"fieldtype": "Section Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "section_break_7",
"fieldtype": "Section Break"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fetch_from": "",
"fieldname": "source_location",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Source Location",
"length": 0,
"no_copy": 0,
"options": "Location",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "source_location",
"fieldtype": "Link",
"label": "Source Location",
"options": "Location"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "target_location",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Target Location",
"length": 0,
"no_copy": 0,
"options": "Location",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "target_location",
"fieldtype": "Link",
"label": "Target Location",
"options": "Location"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "column_break_10",
"fieldtype": "Column Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "column_break_10",
"fieldtype": "Column Break"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "from_employee",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 1,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "From Employee",
"length": 0,
"no_copy": 0,
"options": "Employee",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "from_employee",
"fieldtype": "Link",
"ignore_user_permissions": 1,
"label": "From Employee",
"options": "Employee"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "to_employee",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 1,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "To Employee",
"length": 0,
"no_copy": 0,
"options": "Employee",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "to_employee",
"fieldtype": "Link",
"ignore_user_permissions": 1,
"label": "To Employee",
"options": "Employee"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "reference",
"fieldtype": "Section Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Reference",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "reference",
"fieldtype": "Section Break",
"label": "Reference"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "reference_doctype",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Reference DocType",
"length": 0,
"no_copy": 1,
"options": "DocType",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "reference_doctype",
"fieldtype": "Link",
"label": "Reference DocType",
"no_copy": 1,
"options": "DocType",
"read_only": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "reference_name",
"fieldtype": "Dynamic Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Reference Name",
"length": 0,
"no_copy": 1,
"options": "reference_doctype",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "reference_name",
"fieldtype": "Dynamic Link",
"label": "Reference Name",
"no_copy": 1,
"options": "reference_doctype",
"read_only": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "amended_from",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Amended From",
"length": 0,
"no_copy": 1,
"options": "Asset Movement",
"permlevel": 0,
"print_hide": 1,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
"fieldname": "amended_from",
"fieldtype": "Link",
"label": "Amended From",
"no_copy": 1,
"options": "Asset Movement",
"print_hide": 1,
"read_only": 1
},
{
"default": "ACC-ASM-.YYYY.-",
"fieldname": "naming_series",
"fieldtype": "Select",
"label": "Series",
"options": "ACC-ASM-.YYYY.-",
"reqd": 1
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 0,
"idx": 0,
"image_view": 0,
"in_create": 0,
"is_submittable": 1,
"issingle": 0,
"istable": 0,
"max_attachments": 0,
"modified": "2018-08-21 16:15:40.563655",
"modified_by": "Administrator",
"module": "Assets",
"name": "Asset Movement",
"name_case": "",
"owner": "Administrator",
],
"is_submittable": 1,
"modified": "2019-09-16 16:27:53.887634",
"modified_by": "Administrator",
"module": "Assets",
"name": "Asset Movement",
"owner": "Administrator",
"permissions": [
{
"amend": 1,
"cancel": 1,
"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": 1,
"amend": 1,
"cancel": 1,
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "System Manager",
"share": 1,
"submit": 1,
"write": 1
},
},
{
"amend": 1,
"cancel": 1,
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 1,
"read": 1,
"report": 1,
"role": "Accounts Manager",
"set_user_permissions": 0,
"share": 1,
"submit": 1,
"amend": 1,
"cancel": 1,
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "Accounts Manager",
"share": 1,
"submit": 1,
"write": 1
},
},
{
"amend": 1,
"cancel": 1,
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 1,
"read": 1,
"report": 1,
"role": "Stock Manager",
"set_user_permissions": 0,
"share": 1,
"submit": 1,
"amend": 1,
"cancel": 1,
"create": 1,
"delete": 1,
"email": 1,
"export": 1,
"print": 1,
"read": 1,
"report": 1,
"role": "Stock Manager",
"share": 1,
"submit": 1,
"write": 1
}
],
"quick_entry": 0,
"read_only": 0,
"read_only_onload": 0,
"show_name_in_global_search": 0,
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 0,
"track_seen": 0,
"track_views": 0
],
"sort_field": "modified",
"sort_order": "DESC"
}

View File

@@ -0,0 +1,8 @@
// Copyright (c) 2019, Frappe Technologies Pvt. Ltd. and contributors
// For license information, please see license.txt
frappe.ui.form.on('Buying Settings', {
// refresh: function(frm) {
// }
});

View File

@@ -1,379 +1,111 @@
{
"allow_copy": 0,
"allow_guest_to_view": 0,
"allow_import": 0,
"allow_rename": 0,
"beta": 0,
"creation": "2013-06-25 11:04:03",
"custom": 0,
"description": "Settings for Buying Module",
"docstatus": 0,
"doctype": "DocType",
"document_type": "Other",
"editable_grid": 0,
"creation": "2013-06-25 11:04:03",
"description": "Settings for Buying Module",
"doctype": "DocType",
"document_type": "Other",
"field_order": [
"supp_master_name",
"supplier_group",
"buying_price_list",
"column_break_3",
"po_required",
"pr_required",
"maintain_same_rate",
"allow_multiple_items",
"subcontract",
"backflush_raw_materials_of_subcontract_based_on",
"column_break_11",
"over_transfer_allowance"
],
"fields": [
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"default": "Supplier Name",
"fieldname": "supp_master_name",
"fieldtype": "Select",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Supplier Naming By",
"length": 0,
"no_copy": 0,
"options": "Supplier Name\nNaming Series",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "supplier_group",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Default Supplier Group",
"length": 0,
"no_copy": 0,
"options": "Supplier Group",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "buying_price_list",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Default Buying Price List",
"length": 0,
"no_copy": 0,
"options": "Price List",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "column_break_3",
"fieldtype": "Column Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"length": 0,
"no_copy": 0,
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "po_required",
"fieldtype": "Select",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Purchase Order Required",
"length": 0,
"no_copy": 0,
"options": "No\nYes",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "pr_required",
"fieldtype": "Select",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Purchase Receipt Required",
"length": 0,
"no_copy": 0,
"options": "No\nYes",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "maintain_same_rate",
"fieldtype": "Check",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Maintain same rate throughout purchase cycle",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "allow_multiple_items",
"fieldtype": "Check",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Allow Item to be added multiple times in a transaction",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
"default": "Supplier Name",
"fieldname": "supp_master_name",
"fieldtype": "Select",
"label": "Supplier Naming By",
"options": "Supplier Name\nNaming Series"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "subcontract",
"fieldtype": "Section Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Subcontract",
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "supplier_group",
"fieldtype": "Link",
"label": "Default Supplier Group",
"options": "Supplier Group"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"default": "Material Transferred for Subcontract",
"fieldname": "backflush_raw_materials_of_subcontract_based_on",
"fieldtype": "Select",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Backflush Raw Materials of Subcontract Based On",
"length": 0,
"no_copy": 0,
"options": "BOM\nMaterial Transferred for Subcontract",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
"fieldname": "buying_price_list",
"fieldtype": "Link",
"label": "Default Buying Price List",
"options": "Price List"
},
{
"fieldname": "column_break_3",
"fieldtype": "Column Break"
},
{
"fieldname": "po_required",
"fieldtype": "Select",
"label": "Purchase Order Required",
"options": "No\nYes"
},
{
"fieldname": "pr_required",
"fieldtype": "Select",
"label": "Purchase Receipt Required",
"options": "No\nYes"
},
{
"default": "0",
"fieldname": "maintain_same_rate",
"fieldtype": "Check",
"label": "Maintain same rate throughout purchase cycle"
},
{
"default": "0",
"fieldname": "allow_multiple_items",
"fieldtype": "Check",
"label": "Allow Item to be added multiple times in a transaction"
},
{
"fieldname": "subcontract",
"fieldtype": "Section Break",
"label": "Subcontract"
},
{
"default": "Material Transferred for Subcontract",
"fieldname": "backflush_raw_materials_of_subcontract_based_on",
"fieldtype": "Select",
"label": "Backflush Raw Materials of Subcontract Based On",
"options": "BOM\nMaterial Transferred for Subcontract"
},
{
"depends_on": "eval:doc.backflush_raw_materials_of_subcontract_based_on == \"BOM\"",
"description": "Percentage you are allowed to transfer more against the quantity ordered. For example: If you have ordered 100 units. and your Allowance is 10% then you are allowed to transfer 110 units.",
"fieldname": "over_transfer_allowance",
"fieldtype": "Float",
"label": "Over Transfer Allowance (%)"
},
{
"fieldname": "column_break_11",
"fieldtype": "Column Break"
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 0,
"icon": "fa fa-cog",
"idx": 1,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 1,
"istable": 0,
"max_attachments": 0,
"modified": "2018-07-31 07:52:38.062488",
"modified_by": "Administrator",
"module": "Buying",
"name": "Buying Settings",
"owner": "Administrator",
],
"icon": "fa fa-cog",
"idx": 1,
"issingle": 1,
"modified": "2019-08-20 13:13:09.055189",
"modified_by": "Administrator",
"module": "Buying",
"name": "Buying Settings",
"owner": "Administrator",
"permissions": [
{
"amend": 0,
"cancel": 0,
"create": 1,
"delete": 0,
"email": 1,
"export": 0,
"if_owner": 0,
"import": 0,
"permlevel": 0,
"print": 1,
"read": 1,
"report": 0,
"role": "System Manager",
"set_user_permissions": 0,
"share": 1,
"submit": 0,
"create": 1,
"email": 1,
"print": 1,
"read": 1,
"role": "System Manager",
"share": 1,
"write": 1
}
],
"quick_entry": 0,
"read_only": 0,
"read_only_onload": 0,
"show_name_in_global_search": 0,
"track_changes": 0,
"track_seen": 0
}
]
}

View File

@@ -0,0 +1,10 @@
# -*- coding: utf-8 -*-
# Copyright (c) 2019, Frappe Technologies Pvt. Ltd. and Contributors
# See license.txt
from __future__ import unicode_literals
# import frappe
import unittest
class TestBuyingSettings(unittest.TestCase):
pass

View File

@@ -477,13 +477,14 @@ def make_rm_stock_entry(purchase_order, rm_items):
rm_item_code = rm_item_data["rm_item_code"]
items_dict = {
rm_item_code: {
"po_detail": rm_item_data.get("name"),
"item_name": rm_item_data["item_name"],
"description": item_wh.get(rm_item_code, {}).get('description', ""),
'qty': rm_item_data["qty"],
'from_warehouse': rm_item_data["warehouse"],
'stock_uom': rm_item_data["stock_uom"],
'main_item_code': rm_item_data["item_code"],
'allow_alternative_item': item_wh[rm_item_code].get('allow_alternative_item')
'allow_alternative_item': item_wh.get(rm_item_code, {}).get('allow_alternative_item')
}
}
stock_entry.add_to_stock_entry_detail(items_dict)

View File

@@ -16,9 +16,9 @@ frappe.listview_settings['Purchase Order'] = {
return [__("To Receive"), "orange",
"per_received,<,100|per_billed,=,100|status,!=,Closed"];
}
} else if (flt(doc.per_received, 2) == 100 && flt(doc.per_billed, 2) < 100 && doc.status !== "Closed") {
} else if (flt(doc.per_received, 2) >= 100 && flt(doc.per_billed, 2) < 100 && doc.status !== "Closed") {
return [__("To Bill"), "orange", "per_received,=,100|per_billed,<,100|status,!=,Closed"];
} else if (flt(doc.per_received, 2) == 100 && flt(doc.per_billed, 2) == 100 && doc.status !== "Closed") {
} else if (flt(doc.per_received, 2) >= 100 && flt(doc.per_billed, 2) == 100 && doc.status !== "Closed") {
return [__("Completed"), "green", "per_received,=,100|per_billed,=,100|status,!=,Closed"];
}
},

View File

@@ -1,404 +1,134 @@
{
"allow_copy": 0,
"allow_events_in_timeline": 0,
"allow_guest_to_view": 0,
"allow_import": 0,
"allow_rename": 0,
"beta": 0,
"creation": "2013-02-22 01:27:42",
"custom": 0,
"docstatus": 0,
"doctype": "DocType",
"editable_grid": 1,
"creation": "2013-02-22 01:27:42",
"doctype": "DocType",
"editable_grid": 1,
"field_order": [
"main_item_code",
"rm_item_code",
"required_qty",
"supplied_qty",
"rate",
"amount",
"column_break_6",
"bom_detail_no",
"reference_name",
"conversion_factor",
"stock_uom",
"reserve_warehouse"
],
"fields": [
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 2,
"fieldname": "main_item_code",
"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": "Item Code",
"length": 0,
"no_copy": 0,
"oldfieldname": "main_item_code",
"oldfieldtype": "Data",
"options": "Item",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"columns": 2,
"fieldname": "main_item_code",
"fieldtype": "Link",
"in_list_view": 1,
"label": "Item Code",
"oldfieldname": "main_item_code",
"oldfieldtype": "Data",
"options": "Item",
"read_only": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 2,
"fieldname": "rm_item_code",
"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": "Raw Material Item Code",
"length": 0,
"no_copy": 0,
"oldfieldname": "rm_item_code",
"oldfieldtype": "Data",
"options": "Item",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"columns": 2,
"fieldname": "rm_item_code",
"fieldtype": "Link",
"in_list_view": 1,
"label": "Raw Material Item Code",
"oldfieldname": "rm_item_code",
"oldfieldtype": "Data",
"options": "Item",
"read_only": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 2,
"fieldname": "required_qty",
"fieldtype": "Float",
"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": "Supplied Qty",
"length": 0,
"no_copy": 0,
"oldfieldname": "required_qty",
"oldfieldtype": "Currency",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"columns": 2,
"fieldname": "required_qty",
"fieldtype": "Float",
"in_list_view": 1,
"label": "Required Qty",
"oldfieldname": "required_qty",
"oldfieldtype": "Currency",
"read_only": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 2,
"fieldname": "rate",
"fieldtype": "Currency",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 1,
"in_standard_filter": 0,
"label": "Rate",
"length": 0,
"no_copy": 0,
"oldfieldname": "rate",
"oldfieldtype": "Currency",
"options": "Company:company:default_currency",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"columns": 2,
"fieldname": "rate",
"fieldtype": "Currency",
"in_list_view": 1,
"label": "Rate",
"oldfieldname": "rate",
"oldfieldtype": "Currency",
"options": "Company:company:default_currency"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "amount",
"fieldtype": "Currency",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Amount",
"length": 0,
"no_copy": 0,
"oldfieldname": "amount",
"oldfieldtype": "Currency",
"options": "Company:company:default_currency",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "amount",
"fieldtype": "Currency",
"label": "Amount",
"oldfieldname": "amount",
"oldfieldtype": "Currency",
"options": "Company:company:default_currency",
"read_only": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "column_break_6",
"fieldtype": "Column Break",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"length": 0,
"no_copy": 0,
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "column_break_6",
"fieldtype": "Column Break"
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "bom_detail_no",
"fieldtype": "Data",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "BOM Detail No",
"length": 0,
"no_copy": 0,
"oldfieldname": "bom_detail_no",
"oldfieldtype": "Data",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "bom_detail_no",
"fieldtype": "Data",
"label": "BOM Detail No",
"oldfieldname": "bom_detail_no",
"oldfieldtype": "Data",
"read_only": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "reference_name",
"fieldtype": "Data",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Reference Name",
"length": 0,
"no_copy": 0,
"oldfieldname": "reference_name",
"oldfieldtype": "Data",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "reference_name",
"fieldtype": "Data",
"label": "Reference Name",
"oldfieldname": "reference_name",
"oldfieldtype": "Data",
"read_only": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "conversion_factor",
"fieldtype": "Float",
"hidden": 1,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Conversion Factor",
"length": 0,
"no_copy": 0,
"oldfieldname": "conversion_factor",
"oldfieldtype": "Currency",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "conversion_factor",
"fieldtype": "Float",
"hidden": 1,
"label": "Conversion Factor",
"oldfieldname": "conversion_factor",
"oldfieldtype": "Currency",
"read_only": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 0,
"fieldname": "stock_uom",
"fieldtype": "Link",
"hidden": 0,
"ignore_user_permissions": 0,
"ignore_xss_filter": 0,
"in_filter": 0,
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Stock Uom",
"length": 0,
"no_copy": 0,
"oldfieldname": "stock_uom",
"oldfieldtype": "Data",
"options": "UOM",
"permlevel": 0,
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 1,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
},
"fieldname": "stock_uom",
"fieldtype": "Link",
"label": "Stock Uom",
"oldfieldname": "stock_uom",
"oldfieldtype": "Data",
"options": "UOM",
"read_only": 1
},
{
"allow_bulk_edit": 0,
"allow_in_quick_entry": 0,
"allow_on_submit": 0,
"bold": 0,
"collapsible": 0,
"columns": 2,
"fieldname": "reserve_warehouse",
"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": "Reserve Warehouse",
"length": 0,
"no_copy": 0,
"options": "Warehouse",
"permlevel": 0,
"precision": "",
"print_hide": 0,
"print_hide_if_no_value": 0,
"read_only": 0,
"remember_last_selected_value": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0,
"set_only_once": 0,
"translatable": 0,
"unique": 0
"columns": 2,
"fieldname": "reserve_warehouse",
"fieldtype": "Link",
"in_list_view": 1,
"label": "Reserve Warehouse",
"options": "Warehouse"
},
{
"fieldname": "supplied_qty",
"fieldtype": "Float",
"in_list_view": 1,
"label": "Supplied Qty",
"read_only": 1
}
],
"has_web_view": 0,
"hide_heading": 0,
"hide_toolbar": 1,
"idx": 1,
"image_view": 0,
"in_create": 0,
"is_submittable": 0,
"issingle": 0,
"istable": 1,
"max_attachments": 0,
"modified": "2019-01-07 16:51:58.016007",
"modified_by": "Administrator",
"module": "Buying",
"name": "Purchase Order Item Supplied",
"owner": "dhanalekshmi@webnotestech.com",
"permissions": [],
"quick_entry": 0,
"read_only": 0,
"read_only_onload": 0,
"show_name_in_global_search": 0,
"track_changes": 0,
"track_seen": 0,
"track_views": 0
],
"hide_toolbar": 1,
"idx": 1,
"istable": 1,
"modified": "2019-08-20 13:37:32.702068",
"modified_by": "Administrator",
"module": "Buying",
"name": "Purchase Order Item Supplied",
"owner": "dhanalekshmi@webnotestech.com",
"permissions": []
}

View File

@@ -30,7 +30,9 @@ def update_last_purchase_rate(doc, is_submit):
# for it to be considered for latest purchase rate
if flt(d.conversion_factor):
last_purchase_rate = flt(d.base_rate) / flt(d.conversion_factor)
else:
# Check if item code is present
# Conversion factor should not be mandatory for non itemized items
elif d.item_code:
frappe.throw(_("UOM Conversion factor is required in row {0}").format(d.idx))
# update last purchsae rate
@@ -84,13 +86,13 @@ def get_linked_material_requests(items):
items = json.loads(items)
mr_list = []
for item in items:
material_request = frappe.db.sql("""SELECT distinct mr.name AS mr_name,
(mr_item.qty - mr_item.ordered_qty) AS qty,
material_request = frappe.db.sql("""SELECT distinct mr.name AS mr_name,
(mr_item.qty - mr_item.ordered_qty) AS qty,
mr_item.item_code AS item_code,
mr_item.name AS mr_item
mr_item.name AS mr_item
FROM `tabMaterial Request` mr, `tabMaterial Request Item` mr_item
WHERE mr.name = mr_item.parent
AND mr_item.item_code = %(item)s
AND mr_item.item_code = %(item)s
AND mr.material_request_type = 'Purchase'
AND mr.per_ordered < 99.99
AND mr.docstatus = 1
@@ -98,6 +100,6 @@ def get_linked_material_requests(items):
ORDER BY mr_item.item_code ASC""",{"item": item}, as_dict=1)
if material_request:
mr_list.append(material_request)
return mr_list

View File

@@ -0,0 +1,6 @@
# Version 12.1.0 Release Notes
### Stock
1. [Pick List](https://erpnext.com/docs/user/manual/en/stock/pick-list)
2. [Refactored Accounts Receivable Reports](https://erpnext.com/docs/user/manual/en/accounts/accounting-reports#2-accounting-statements)

View File

@@ -8,12 +8,18 @@
"from",
"to",
"column_break_3",
"received_by",
"medium",
"caller_information",
"contact",
"contact_name",
"column_break_10",
"lead",
"lead_name",
"section_break_5",
"status",
"duration",
"recording_url",
"summary"
"recording_url"
],
"fields": [
{
@@ -60,12 +66,6 @@
"label": "Duration",
"read_only": 1
},
{
"fieldname": "summary",
"fieldtype": "Data",
"label": "Summary",
"read_only": 1
},
{
"fieldname": "recording_url",
"fieldtype": "Data",
@@ -77,10 +77,58 @@
"fieldtype": "Data",
"label": "Medium",
"read_only": 1
},
{
"fieldname": "received_by",
"fieldtype": "Link",
"label": "Received By",
"options": "Employee",
"read_only": 1
},
{
"fieldname": "caller_information",
"fieldtype": "Section Break",
"label": "Caller Information"
},
{
"fieldname": "contact",
"fieldtype": "Link",
"label": "Contact",
"options": "Contact",
"read_only": 1
},
{
"fieldname": "lead",
"fieldtype": "Link",
"label": "Lead ",
"options": "Lead",
"read_only": 1
},
{
"fetch_from": "contact.name",
"fieldname": "contact_name",
"fieldtype": "Data",
"hidden": 1,
"in_list_view": 1,
"label": "Contact Name",
"read_only": 1
},
{
"fieldname": "column_break_10",
"fieldtype": "Column Break"
},
{
"fetch_from": "lead.lead_name",
"fieldname": "lead_name",
"fieldtype": "Data",
"hidden": 1,
"in_list_view": 1,
"label": "Lead Name",
"read_only": 1
}
],
"in_create": 1,
"modified": "2019-07-01 09:09:48.516722",
"modified": "2019-08-06 05:46:53.144683",
"modified_by": "Administrator",
"module": "Communication",
"name": "Call Log",
@@ -97,10 +145,15 @@
"role": "System Manager",
"share": 1,
"write": 1
},
{
"read": 1,
"role": "Employee"
}
],
"sort_field": "modified",
"sort_order": "ASC",
"title_field": "from",
"track_changes": 1
"track_changes": 1,
"track_views": 1
}

View File

@@ -4,16 +4,92 @@
from __future__ import unicode_literals
import frappe
from frappe import _
from frappe.model.document import Document
from erpnext.crm.doctype.utils import get_employee_emails_for_popup
from erpnext.crm.doctype.utils import get_scheduled_employees_for_popup, strip_number
from frappe.contacts.doctype.contact.contact import get_contact_with_phone_number
from erpnext.crm.doctype.lead.lead import get_lead_with_phone_number
class CallLog(Document):
def before_insert(self):
number = strip_number(self.get('from'))
self.contact = get_contact_with_phone_number(number)
self.lead = get_lead_with_phone_number(number)
def after_insert(self):
employee_emails = get_employee_emails_for_popup(self.medium)
for email in employee_emails:
frappe.publish_realtime('show_call_popup', self, user=email)
self.trigger_call_popup()
def on_update(self):
doc_before_save = self.get_doc_before_save()
if doc_before_save and doc_before_save.status in ['Ringing'] and self.status in ['Missed', 'Completed']:
if not doc_before_save: return
if doc_before_save.status in ['Ringing'] and self.status in ['Missed', 'Completed']:
frappe.publish_realtime('call_{id}_disconnected'.format(id=self.id), self)
elif doc_before_save.to != self.to:
self.trigger_call_popup()
def trigger_call_popup(self):
scheduled_employees = get_scheduled_employees_for_popup(self.medium)
employee_emails = get_employees_with_number(self.to)
# check if employees with matched number are scheduled to receive popup
emails = set(scheduled_employees).intersection(employee_emails)
# # if no employee found with matching phone number then show popup to scheduled employees
# emails = emails or scheduled_employees if employee_emails
for email in emails:
frappe.publish_realtime('show_call_popup', self, user=email)
@frappe.whitelist()
def add_call_summary(call_log, summary):
doc = frappe.get_doc('Call Log', call_log)
doc.add_comment('Comment', frappe.bold(_('Call Summary')) + '<br><br>' + summary)
def get_employees_with_number(number):
number = strip_number(number)
if not number: return []
employee_emails = frappe.cache().hget('employees_with_number', number)
if employee_emails: return employee_emails
employees = frappe.get_all('Employee', filters={
'cell_number': ['like', '%{}%'.format(number)],
'user_id': ['!=', '']
}, fields=['user_id'])
employee_emails = [employee.user_id for employee in employees]
frappe.cache().hset('employees_with_number', number, employee_emails)
return employee_emails
def set_caller_information(doc, state):
'''Called from hooks on creation of Lead or Contact'''
if doc.doctype not in ['Lead', 'Contact']: return
numbers = [doc.get('phone'), doc.get('mobile_no')]
# contact for Contact and lead for Lead
fieldname = doc.doctype.lower()
# contact_name or lead_name
display_name_field = '{}_name'.format(fieldname)
# Contact now has all the nos saved in child table
if doc.doctype == 'Contact':
numbers = [d.phone for d in doc.phone_nos]
for number in numbers:
number = strip_number(number)
if not number: continue
filters = frappe._dict({
'from': ['like', '%{}'.format(number)],
fieldname: ''
})
logs = frappe.get_all('Call Log', filters=filters)
for log in logs:
frappe.db.set_value('Call Log', log.name, {
fieldname: doc.name,
display_name_field: doc.get_title()
}, update_modified=False)

View File

@@ -14,6 +14,12 @@ def get_data():
"dependencies": ["Item", "Supplier"],
"description": _("Purchase Orders given to Suppliers."),
},
{
"type": "doctype",
"name": "Purchase Invoice",
"onboard": 1,
"dependencies": ["Item", "Supplier"]
},
{
"type": "doctype",
"name": "Material Request",

View File

@@ -41,6 +41,11 @@ def get_data():
"name": "Lead Source",
"description": _("Track Leads by Lead Source.")
},
{
"type": "doctype",
"name": "Contract",
"description": _("Helps you keep tracks of Contracts based on Supplier, Customer and Employee"),
},
]
},
{

View File

@@ -134,6 +134,12 @@ def get_data():
"name": "Employee Leave Balance",
"doctype": "Leave Application"
},
{
"type": "report",
"is_query_report": True,
"name": "Leave Ledger Entry",
"doctype": "Leave Ledger Entry"
},
]
},
{
@@ -213,6 +219,16 @@ def get_data():
"name": "Employee Benefit Claim",
"dependencies": ["Employee"]
},
{
"type": "doctype",
"name": "Employee Tax Exemption Category",
"dependencies": ["Employee"]
},
{
"type": "doctype",
"name": "Employee Tax Exemption Sub Category",
"dependencies": ["Employee"]
},
]
},
{

View File

@@ -40,6 +40,11 @@ def get_data():
"type": "doctype",
"name": "Plaid Settings",
"description": _("Connect your bank accounts to ERPNext"),
},
{
"type": "doctype",
"name": "Exotel Settings",
"description": _("Connect your Exotel Account to ERPNext and track call logs"),
}
]
}

View File

@@ -94,6 +94,13 @@ def get_data():
"name": "BOM Update Tool",
"description": _("Replace BOM and update latest price in all BOMs"),
},
{
"type": "page",
"label": _("BOM Comparison Tool"),
"name": "bom-comparison-tool",
"description": _("Compare BOMs for changes in Raw Materials and Operations"),
"data_doctype": "BOM"
},
]
},
{

View File

@@ -304,12 +304,6 @@ def get_data():
"name": "Customers Without Any Sales Transactions",
"doctype": "Customer"
},
{
"type": "report",
"is_query_report": True,
"name": "Sales Partners Commission",
"doctype": "Customer"
},
{
"type": "report",
"is_query_report": True,

View File

@@ -30,6 +30,12 @@ def get_data():
"onboard": 1,
"dependencies": ["Item"],
},
{
"type": "doctype",
"name": "Pick List",
"onboard": 1,
"dependencies": ["Item"],
},
{
"type": "doctype",
"name": "Delivery Trip"
@@ -329,5 +335,5 @@ def get_data():
}
]
},
]

View File

@@ -60,7 +60,9 @@ class AccountsController(TransactionBase):
def validate(self):
self.validate_qty_is_not_zero()
if not self.get('is_return'):
self.validate_qty_is_not_zero()
if self.get("_action") and self._action != "update_after_submit":
self.set_missing_values(for_validate=True)
@@ -87,7 +89,7 @@ class AccountsController(TransactionBase):
self.validate_currency()
if self.doctype == 'Purchase Invoice':
self.validate_paid_amount()
self.calculate_paid_amount()
if self.doctype in ['Purchase Invoice', 'Sales Invoice']:
pos_check_field = "is_pos" if self.doctype=="Sales Invoice" else "is_paid"
@@ -133,22 +135,23 @@ class AccountsController(TransactionBase):
else:
df.set("print_hide", 1)
def validate_paid_amount(self):
def calculate_paid_amount(self):
if hasattr(self, "is_pos") or hasattr(self, "is_paid"):
is_paid = self.get("is_pos") or self.get("is_paid")
if cint(is_paid) == 1:
if flt(self.paid_amount) == 0 and flt(self.outstanding_amount) > 0:
if self.cash_bank_account:
self.paid_amount = flt(flt(self.outstanding_amount), self.precision("paid_amount"))
self.base_paid_amount = flt(self.paid_amount * self.conversion_rate,
self.precision("base_paid_amount"))
else:
# show message that the amount is not paid
self.paid_amount = 0
frappe.throw(
_("Note: Payment Entry will not be created since 'Cash or Bank Account' was not specified"))
else:
frappe.db.set(self, 'paid_amount', 0)
if is_paid:
if not self.cash_bank_account:
# show message that the amount is not paid
frappe.throw(_("Note: Payment Entry will not be created since 'Cash or Bank Account' was not specified"))
if cint(self.is_return) and self.grand_total > self.paid_amount:
self.paid_amount = flt(flt(self.grand_total), self.precision("paid_amount"))
elif not flt(self.paid_amount) and flt(self.outstanding_amount) > 0:
self.paid_amount = flt(flt(self.outstanding_amount), self.precision("paid_amount"))
self.base_paid_amount = flt(self.paid_amount * self.conversion_rate,
self.precision("base_paid_amount"))
def set_missing_values(self, for_validate=False):
if frappe.flags.in_test:
@@ -261,7 +264,7 @@ class AccountsController(TransactionBase):
if self.get("is_subcontracted"):
args["is_subcontracted"] = self.is_subcontracted
ret = get_item_details(args, self)
ret = get_item_details(args, self, overwrite_warehouse=False)
for fieldname, value in ret.items():
if item.meta.get_field(fieldname) and value is not None:
@@ -1190,6 +1193,11 @@ def update_child_qty_rate(parent_doctype, trans_items, parent_doctype_name, chil
.format(child_item.idx, child_item.item_code))
else:
child_item.rate = flt(d.get("rate"))
if flt(child_item.price_list_rate):
child_item.discount_percentage = flt((1 - flt(child_item.rate) / flt(child_item.price_list_rate)) * 100.0, \
child_item.precision("discount_percentage"))
child_item.flags.ignore_validate_update_after_submit = True
if new_child_flag:
child_item.idx = len(parent.items) + 1

View File

@@ -337,7 +337,7 @@ class BuyingController(StockController):
if self.doctype in ["Purchase Receipt", "Purchase Invoice"]:
rm.consumed_qty = required_qty
rm.description = bom_item.description
if item.batch_no and not rm.batch_no:
if item.batch_no and frappe.db.get_value("Item", rm.rm_item_code, "has_batch_no") and not rm.batch_no:
rm.batch_no = item.batch_no
# get raw materials rate
@@ -395,7 +395,9 @@ class BuyingController(StockController):
def set_qty_as_per_stock_uom(self):
for d in self.get("items"):
if d.meta.get_field("stock_qty"):
if not d.conversion_factor:
# Check if item code is present
# Conversion factor should not be mandatory for non itemized items
if not d.conversion_factor and d.item_code:
frappe.throw(_("Row {0}: Conversion Factor is mandatory").format(d.idx))
d.stock_qty = flt(d.qty) * flt(d.conversion_factor)
@@ -725,7 +727,7 @@ def get_items_from_bom(item_code, bom, exploded_item=1):
where
t2.parent = t1.name and t1.item = %s
and t1.docstatus = 1 and t1.is_active = 1 and t1.name = %s
and t2.item_code = t3.name and t3.is_stock_item = 1""".format(doctype),
and t2.item_code = t3.name""".format(doctype),
(item_code, bom), as_dict=1)
if not bom_items:

View File

@@ -371,7 +371,7 @@ def get_expense_account(doctype, txt, searchfield, start, page_len, filters):
return frappe.db.sql("""select tabAccount.name from `tabAccount`
where (tabAccount.report_type = "Profit and Loss"
or tabAccount.account_type in ("Expense Account", "Fixed Asset", "Temporary", "Asset Received But Not Billed"))
or tabAccount.account_type in ("Expense Account", "Fixed Asset", "Temporary", "Asset Received But Not Billed", "Capital Work in Progress"))
and tabAccount.is_group=0
and tabAccount.docstatus!=2
and tabAccount.{key} LIKE %(txt)s
@@ -440,17 +440,17 @@ def get_batch_numbers(doctype, txt, searchfield, start, page_len, filters):
@frappe.whitelist()
def item_manufacturer_query(doctype, txt, searchfield, start, page_len, filters):
search_txt = "{0}%".format(txt)
item_filters = [
['manufacturer', 'like', '%' + txt + '%'],
['item_code', '=', filters.get("item_code")]
]
item_filters = {
'manufacturer': ('like', search_txt),
'item_code': filters.get("item_code")
}
return frappe.get_all("Item Manufacturer",
fields = "manufacturer",
filters = item_filters,
item_manufacturers = frappe.get_all(
"Item Manufacturer",
fields=["manufacturer", "manufacturer_part_no"],
filters=item_filters,
limit_start=start,
limit_page_length=page_len,
as_list=1
)
return item_manufacturers

View File

@@ -18,34 +18,31 @@ def validate_return(doc):
validate_returned_items(doc)
def validate_return_against(doc):
filters = {"doctype": doc.doctype, "docstatus": 1, "company": doc.company}
if doc.meta.get_field("customer") and doc.customer:
filters["customer"] = doc.customer
elif doc.meta.get_field("supplier") and doc.supplier:
filters["supplier"] = doc.supplier
if not frappe.db.exists(filters):
if not frappe.db.exists(doc.doctype, doc.return_against):
frappe.throw(_("Invalid {0}: {1}")
.format(doc.meta.get_label("return_against"), doc.return_against))
else:
ref_doc = frappe.get_doc(doc.doctype, doc.return_against)
# validate posting date time
return_posting_datetime = "%s %s" % (doc.posting_date, doc.get("posting_time") or "00:00:00")
ref_posting_datetime = "%s %s" % (ref_doc.posting_date, ref_doc.get("posting_time") or "00:00:00")
party_type = "customer" if doc.doctype in ("Sales Invoice", "Delivery Note") else "supplier"
if get_datetime(return_posting_datetime) < get_datetime(ref_posting_datetime):
frappe.throw(_("Posting timestamp must be after {0}").format(format_datetime(ref_posting_datetime)))
if ref_doc.company == doc.company and ref_doc.get(party_type) == doc.get(party_type) and ref_doc.docstatus == 1:
# validate posting date time
return_posting_datetime = "%s %s" % (doc.posting_date, doc.get("posting_time") or "00:00:00")
ref_posting_datetime = "%s %s" % (ref_doc.posting_date, ref_doc.get("posting_time") or "00:00:00")
# validate same exchange rate
if doc.conversion_rate != ref_doc.conversion_rate:
frappe.throw(_("Exchange Rate must be same as {0} {1} ({2})")
.format(doc.doctype, doc.return_against, ref_doc.conversion_rate))
if get_datetime(return_posting_datetime) < get_datetime(ref_posting_datetime):
frappe.throw(_("Posting timestamp must be after {0}").format(format_datetime(ref_posting_datetime)))
# validate update stock
if doc.doctype == "Sales Invoice" and doc.update_stock and not ref_doc.update_stock:
frappe.throw(_("'Update Stock' can not be checked because items are not delivered via {0}")
.format(doc.return_against))
# validate same exchange rate
if doc.conversion_rate != ref_doc.conversion_rate:
frappe.throw(_("Exchange Rate must be same as {0} {1} ({2})")
.format(doc.doctype, doc.return_against, ref_doc.conversion_rate))
# validate update stock
if doc.doctype == "Sales Invoice" and doc.update_stock and not ref_doc.update_stock:
frappe.throw(_("'Update Stock' can not be checked because items are not delivered via {0}")
.format(doc.return_against))
def validate_returned_items(doc):
from erpnext.stock.doctype.serial_no.serial_no import get_serial_nos
@@ -249,6 +246,8 @@ def make_return_doc(doctype, source_name, target_doc=None):
elif doc.doctype == 'Purchase Invoice':
doc.paid_amount = -1 * source.paid_amount
doc.base_paid_amount = -1 * source.base_paid_amount
doc.payment_terms_template = ''
doc.payment_schedule = []
if doc.get("is_return") and hasattr(doc, "packed_items"):
for d in doc.get("packed_items"):

View File

@@ -45,6 +45,7 @@ class SellingController(StockController):
self.set_gross_profit()
set_default_income_account_for_item(self)
self.set_customer_address()
self.validate_for_duplicate_items()
def set_missing_values(self, for_validate=False):
@@ -381,6 +382,34 @@ class SellingController(StockController):
if self.get(address_field):
self.set(address_display_field, get_address_display(self.get(address_field)))
def validate_for_duplicate_items(self):
check_list, chk_dupl_itm = [], []
if cint(frappe.db.get_single_value("Selling Settings", "allow_multiple_items")):
return
for d in self.get('items'):
if self.doctype == "Sales Invoice":
e = [d.item_code, d.description, d.warehouse, d.sales_order or d.delivery_note, d.batch_no or '']
f = [d.item_code, d.description, d.sales_order or d.delivery_note]
elif self.doctype == "Delivery Note":
e = [d.item_code, d.description, d.warehouse, d.against_sales_order or d.against_sales_invoice, d.batch_no or '']
f = [d.item_code, d.description, d.against_sales_order or d.against_sales_invoice]
elif self.doctype in ["Sales Order", "Quotation"]:
e = [d.item_code, d.description, d.warehouse, '']
f = [d.item_code, d.description]
if frappe.db.get_value("Item", d.item_code, "is_stock_item") == 1:
if e in check_list:
frappe.throw(_("Note: Item {0} entered multiple times").format(d.item_code))
else:
check_list.append(e)
else:
if f in chk_dupl_itm:
frappe.throw(_("Note: Item {0} entered multiple times").format(d.item_code))
else:
chk_dupl_itm.append(f)
def validate_items(self):
# validate items to see if they have is_sales_item enabled
from erpnext.controllers.buying_controller import validate_item_type

View File

@@ -57,9 +57,9 @@ status_map = {
"Purchase Order": [
["Draft", None],
["To Receive and Bill", "eval:self.per_received < 100 and self.per_billed < 100 and self.docstatus == 1"],
["To Bill", "eval:self.per_received == 100 and self.per_billed < 100 and self.docstatus == 1"],
["To Bill", "eval:self.per_received >= 100 and self.per_billed < 100 and self.docstatus == 1"],
["To Receive", "eval:self.per_received < 100 and self.per_billed == 100 and self.docstatus == 1"],
["Completed", "eval:self.per_received == 100 and self.per_billed == 100 and self.docstatus == 1"],
["Completed", "eval:self.per_received >= 100 and self.per_billed == 100 and self.docstatus == 1"],
["Delivered", "eval:self.status=='Delivered'"],
["Cancelled", "eval:self.docstatus==2"],
["On Hold", "eval:self.status=='On Hold'"],

View File

@@ -81,7 +81,12 @@ class calculate_taxes_and_totals(object):
item.discount_amount = item.price_list_rate - item.rate
item.net_rate = item.rate
item.amount = flt(item.rate * item.qty, item.precision("amount"))
if not item.qty and self.doc.get("is_return"):
item.amount = flt(-1 * item.rate, item.precision("amount"))
else:
item.amount = flt(item.rate * item.qty, item.precision("amount"))
item.net_amount = item.amount
self._set_in_company_currency(item, ["price_list_rate", "rate", "net_rate", "amount", "net_amount"])

View File

@@ -39,7 +39,6 @@ def validate_filters(filters):
frappe.throw(_("'Based On' and 'Group By' can not be same"))
def get_data(filters, conditions):
data = []
inc, cond= '',''
query_details = conditions["based_on_select"] + conditions["period_wise_select"]
@@ -47,13 +46,17 @@ def get_data(filters, conditions):
posting_date = 't1.transaction_date'
if conditions.get('trans') in ['Sales Invoice', 'Purchase Invoice', 'Purchase Receipt', 'Delivery Note']:
posting_date = 't1.posting_date'
if filters.period_based_on:
posting_date = 't1.'+filters.period_based_on
if conditions["based_on_select"] in ["t1.project,", "t2.project,"]:
cond = ' and '+ conditions["based_on_select"][:-1] +' IS Not NULL'
if conditions.get('trans') in ['Sales Order', 'Purchase Order']:
cond += " and t1.status != 'Closed'"
if conditions.get('trans') == 'Quotation' and filters.get("group_by") == 'Customer':
cond += " and t1.quotation_to = 'Customer'"
year_start_date, year_end_date = frappe.db.get_value("Fiscal Year",
filters.get('fiscal_year'), ["year_start_date", "year_end_date"])
@@ -64,7 +67,7 @@ def get_data(filters, conditions):
if filters.get("group_by") == 'Item':
sel_col = 't2.item_code'
elif filters.get("group_by") == 'Customer':
sel_col = 't1.customer'
sel_col = 't1.party_name' if conditions.get('trans') == 'Quotation' else 't1.customer'
elif filters.get("group_by") == 'Supplier':
sel_col = 't1.supplier'
@@ -225,7 +228,7 @@ def based_wise_columns_query(based_on, trans):
elif based_on == "Customer":
based_on_details["based_on_cols"] = ["Customer:Link/Customer:120", "Territory:Link/Territory:120"]
based_on_details["based_on_select"] = "t1.customer_name, t1.territory, "
based_on_details["based_on_group_by"] = 't1.customer'
based_on_details["based_on_group_by"] = 't1.party_name' if trans == 'Quotation' else 't1.customer'
based_on_details["addl_tables"] = ''
elif based_on == "Customer Group":

View File

@@ -21,42 +21,45 @@ def get_list_context(context=None):
def get_transaction_list(doctype, txt=None, filters=None, limit_start=0, limit_page_length=20, order_by="modified"):
user = frappe.session.user
key = None
ignore_permissions = False
if not filters: filters = []
if doctype == 'Supplier Quotation':
filters.append((doctype, "docstatus", "<", 2))
filters.append((doctype, 'docstatus', '<', 2))
else:
filters.append((doctype, "docstatus", "=", 1))
filters.append((doctype, 'docstatus', '=', 1))
if (user != "Guest" and is_website_user()) or doctype == 'Request for Quotation':
if (user != 'Guest' and is_website_user()) or doctype == 'Request for Quotation':
parties_doctype = 'Request for Quotation Supplier' if doctype == 'Request for Quotation' else doctype
# find party for this contact
customers, suppliers = get_customers_suppliers(parties_doctype, user)
if not customers and not suppliers: return []
key, parties = get_party_details(customers, suppliers)
if doctype == 'Request for Quotation':
return rfq_transaction_list(parties_doctype, doctype, parties, limit_start, limit_page_length)
filters.append((doctype, key, "in", parties))
if key:
return post_process(doctype, get_list_for_transactions(doctype, txt,
filters=filters, fields="name",limit_start=limit_start,
limit_page_length=limit_page_length,ignore_permissions=True,
order_by="modified desc"))
if customers:
if doctype == 'Quotation':
filters.append(('quotation_to', '=', 'Customer'))
filters.append(('party_name', 'in', customers))
else:
filters.append(('customer', 'in', customers))
elif suppliers:
filters.append(('supplier', 'in', suppliers))
else:
return []
return post_process(doctype, get_list_for_transactions(doctype, txt, filters, limit_start, limit_page_length,
fields="name", order_by="modified desc"))
if doctype == 'Request for Quotation':
parties = customers or suppliers
return rfq_transaction_list(parties_doctype, doctype, parties, limit_start, limit_page_length)
# Since customers and supplier do not have direct access to internal doctypes
ignore_permissions = True
transactions = get_list_for_transactions(doctype, txt, filters, limit_start, limit_page_length,
fields='name', ignore_permissions=ignore_permissions, order_by='modified desc')
return post_process(doctype, transactions)
def get_list_for_transactions(doctype, txt, filters, limit_start, limit_page_length=20,
ignore_permissions=False,fields=None, order_by=None):
ignore_permissions=False, fields=None, order_by=None):
""" Get List of transactions like Invoices, Orders """
from frappe.www.list import get_list
meta = frappe.get_meta(doctype)
@@ -77,22 +80,12 @@ def get_list_for_transactions(doctype, txt, filters, limit_start, limit_page_len
if or_filters:
for r in frappe.get_list(doctype, fields=fields,filters=filters, or_filters=or_filters,
limit_start=limit_start, limit_page_length=limit_page_length,
limit_start=limit_start, limit_page_length=limit_page_length,
ignore_permissions=ignore_permissions, order_by=order_by):
data.append(r)
return data
def get_party_details(customers, suppliers):
if customers:
key, parties = "customer", customers
elif suppliers:
key, parties = "supplier", suppliers
else:
key, parties = "customer", []
return key, parties
def rfq_transaction_list(parties_doctype, doctype, parties, limit_start, limit_page_length):
data = frappe.db.sql("""select distinct parent as name, supplier from `tab{doctype}`
where supplier = '{supplier}' and docstatus=1 order by modified desc limit {start}, {len}""".
@@ -130,38 +123,56 @@ def get_customers_suppliers(doctype, user):
suppliers = []
meta = frappe.get_meta(doctype)
customer_field_name = get_customer_field_name(doctype)
has_customer_field = meta.has_field(customer_field_name)
has_supplier_field = meta.has_field('supplier')
if has_common(["Supplier", "Customer"], frappe.get_roles(user)):
contacts = frappe.db.sql("""
select
select
`tabContact`.email_id,
`tabDynamic Link`.link_doctype,
`tabDynamic Link`.link_name
from
from
`tabContact`, `tabDynamic Link`
where
`tabContact`.name=`tabDynamic Link`.parent and `tabContact`.email_id =%s
""", user, as_dict=1)
customers = [c.link_name for c in contacts if c.link_doctype == 'Customer'] \
if meta.get_field("customer") else None
suppliers = [c.link_name for c in contacts if c.link_doctype == 'Supplier'] \
if meta.get_field("supplier") else None
customers = [c.link_name for c in contacts if c.link_doctype == 'Customer']
suppliers = [c.link_name for c in contacts if c.link_doctype == 'Supplier']
elif frappe.has_permission(doctype, 'read', user=user):
customers = [customer.name for customer in frappe.get_list("Customer")] \
if meta.get_field("customer") else None
suppliers = [supplier.name for supplier in frappe.get_list("Customer")] \
if meta.get_field("supplier") else None
customer_list = frappe.get_list("Customer")
customers = suppliers = [customer.name for customer in customer_list]
return customers, suppliers
return customers if has_customer_field else None, \
suppliers if has_supplier_field else None
def has_website_permission(doc, ptype, user, verbose=False):
doctype = doc.doctype
customers, suppliers = get_customers_suppliers(doctype, user)
if customers:
return frappe.get_all(doctype, filters=[(doctype, "customer", "in", customers),
(doctype, "name", "=", doc.name)]) and True or False
return frappe.db.exists(doctype, get_customer_filter(doc, customers))
elif suppliers:
fieldname = 'suppliers' if doctype == 'Request for Quotation' else 'supplier'
return frappe.get_all(doctype, filters=[(doctype, fieldname, "in", suppliers),
(doctype, "name", "=", doc.name)]) and True or False
return frappe.db.exists(doctype, filters={
'name': doc.name,
fieldname: ["in", suppliers]
})
else:
return False
def get_customer_filter(doc, customers):
doctype = doc.doctype
filters = frappe._dict()
filters.name = doc.name
filters[get_customer_field_name(doctype)] = ['in', customers]
if doctype == 'Quotation':
filters.quotation_to = 'Customer'
return filters
def get_customer_field_name(doctype):
if doctype == 'Quotation':
return 'party_name'
else:
return 'customer'

View File

@@ -88,7 +88,7 @@ def get_status(start_date, end_date):
end_date = getdate(end_date)
now_date = getdate(nowdate())
return "Active" if start_date < now_date < end_date else "Inactive"
return "Active" if start_date <= now_date <= end_date else "Inactive"
def update_status_for_contracts():

View File

@@ -145,6 +145,16 @@ def _make_customer(source_name, target_doc=None, ignore_permissions=False):
@frappe.whitelist()
def make_opportunity(source_name, target_doc=None):
def set_missing_values(source, target):
address = frappe.get_all('Dynamic Link', {
'link_doctype': source.doctype,
'link_name': source.name,
'parenttype': 'Address',
}, ['parent'], limit=1)
if address:
target.customer_address = address[0].parent
target_doc = get_mapped_doc("Lead", source_name,
{"Lead": {
"doctype": "Opportunity",
@@ -157,7 +167,7 @@ def make_opportunity(source_name, target_doc=None):
"email_id": "contact_email",
"mobile_no": "contact_mobile"
}
}}, target_doc)
}}, target_doc, set_missing_values)
return target_doc
@@ -230,3 +240,15 @@ def make_lead_from_communication(communication, ignore_communication_links=False
link_communication_to_document(doc, "Lead", lead_name, ignore_communication_links)
return lead_name
def get_lead_with_phone_number(number):
if not number: return
leads = frappe.get_all('Lead', or_filters={
'phone': ['like', '%{}'.format(number)],
'mobile_no': ['like', '%{}'.format(number)]
}, limit=1)
lead = leads[0].name if leads else None
return lead

View File

@@ -31,9 +31,9 @@ frappe.ui.form.on("Opportunity", {
party_name: function(frm) {
frm.toggle_display("contact_info", frm.doc.party_name);
frm.trigger('set_contact_link');
if (frm.doc.opportunity_from == "Customer") {
frm.trigger('set_contact_link');
erpnext.utils.get_party_details(frm);
} else if (frm.doc.opportunity_from == "Lead") {
erpnext.utils.map_current_doc({
@@ -48,13 +48,6 @@ frappe.ui.form.on("Opportunity", {
frm.get_field("items").grid.set_multiple_add("item_code", "qty");
},
party_name: function(frm) {
if (frm.doc.opportunity_from == "Customer") {
frm.trigger('set_contact_link');
erpnext.utils.get_party_details(frm);
}
},
with_items: function(frm) {
frm.trigger('toggle_mandatory');
},

File diff suppressed because it is too large Load Diff

View File

@@ -18,12 +18,14 @@ frappe.listview_settings['Opportunity'] = {
listview.call_for_selected_items(method, {"status": "Closed"});
});
listview.page.fields_dict.opportunity_from.get_query = function() {
return {
"filters": {
"name": ["in", ["Customer", "Lead"]],
}
if(listview.page.fields_dict.opportunity_from) {
listview.page.fields_dict.opportunity_from.get_query = function() {
return {
"filters": {
"name": ["in", ["Customer", "Lead"]],
}
};
};
};
}
}
};

View File

@@ -45,15 +45,16 @@ class TestOpportunity(unittest.TestCase):
# create new customer and create new contact against 'new.opportunity@example.com'
customer = make_customer(opp_doc.party_name).insert(ignore_permissions=True)
frappe.get_doc({
contact = frappe.get_doc({
"doctype": "Contact",
"email_id": new_lead_email_id,
"first_name": "_Test Opportunity Customer",
"links": [{
"link_doctype": "Customer",
"link_name": customer.name
}]
}).insert(ignore_permissions=True)
})
contact.add_email(new_lead_email_id)
contact.insert(ignore_permissions=True)
opp_doc = frappe.get_doc(args).insert(ignore_permissions=True)
self.assertTrue(opp_doc.party_name)

View File

@@ -3,82 +3,59 @@ from frappe import _
import json
@frappe.whitelist()
def get_document_with_phone_number(number):
# finds contacts and leads
if not number: return
number = number.lstrip('0')
number_filter = {
'phone': ['like', '%{}'.format(number)],
'mobile_no': ['like', '%{}'.format(number)]
}
contacts = frappe.get_all('Contact', or_filters=number_filter, limit=1)
def get_last_interaction(contact=None, lead=None):
if contacts:
return frappe.get_doc('Contact', contacts[0].name)
if not contact and not lead: return
leads = frappe.get_all('Lead', or_filters=number_filter, limit=1)
if leads:
return frappe.get_doc('Lead', leads[0].name)
@frappe.whitelist()
def get_last_interaction(number, reference_doc):
reference_doc = json.loads(reference_doc) if reference_doc else get_document_with_phone_number(number)
if not reference_doc: return
reference_doc = frappe._dict(reference_doc)
last_communication = {}
last_issue = {}
if reference_doc.doctype == 'Contact':
customer_name = ''
last_communication = None
last_issue = None
if contact:
query_condition = ''
for link in reference_doc.links:
link = frappe._dict(link)
values = []
contact = frappe.get_doc('Contact', contact)
for link in contact.links:
if link.link_doctype == 'Customer':
customer_name = link.link_name
query_condition += "(`reference_doctype`='{}' AND `reference_name`='{}') OR".format(link.link_doctype, link.link_name)
last_issue = get_last_issue_from_customer(link.link_name)
query_condition += "(`reference_doctype`=%s AND `reference_name`=%s) OR"
values += [link_link_doctype, link_link_name]
if query_condition:
# remove extra appended 'OR'
query_condition = query_condition[:-2]
last_communication = frappe.db.sql("""
SELECT `name`, `content`
FROM `tabCommunication`
WHERE {}
WHERE `sent_or_received`='Received'
AND ({})
ORDER BY `modified`
LIMIT 1
""".format(query_condition)) # nosec
""".format(query_condition), values, as_dict=1) # nosec
if customer_name:
last_issue = frappe.get_all('Issue', {
'customer': customer_name
}, ['name', 'subject', 'customer'], limit=1)
elif reference_doc.doctype == 'Lead':
if lead:
last_communication = frappe.get_all('Communication', filters={
'reference_doctype': reference_doc.doctype,
'reference_name': reference_doc.name,
'reference_doctype': 'Lead',
'reference_name': lead,
'sent_or_received': 'Received'
}, fields=['name', 'content'], limit=1)
}, fields=['name', 'content'], order_by='`creation` DESC', limit=1)
last_communication = last_communication[0] if last_communication else None
return {
'last_communication': last_communication[0] if last_communication else None,
'last_issue': last_issue[0] if last_issue else None
'last_communication': last_communication,
'last_issue': last_issue
}
@frappe.whitelist()
def add_call_summary(docname, summary):
call_log = frappe.get_doc('Call Log', docname)
summary = _('Call Summary by {0}: {1}').format(
frappe.utils.get_fullname(frappe.session.user), summary)
if not call_log.summary:
call_log.summary = summary
else:
call_log.summary += '<br>' + summary
call_log.save(ignore_permissions=True)
def get_last_issue_from_customer(customer_name):
issues = frappe.get_all('Issue', {
'customer': customer_name
}, ['name', 'subject', 'customer'], order_by='`creation` DESC', limit=1)
return issues[0] if issues else None
def get_scheduled_employees_for_popup(communication_medium):
if not communication_medium: return []
def get_employee_emails_for_popup(communication_medium):
now_time = frappe.utils.nowtime()
weekday = frappe.utils.get_weekday()
@@ -98,3 +75,10 @@ def get_employee_emails_for_popup(communication_medium):
employee_emails = set([employee.user_id for employee in employees])
return employee_emails
def strip_number(number):
if not number: return
# strip 0 from the start of the number for proper number comparisions
# eg. 07888383332 should match with 7888383332
number = number.lstrip('0')
return number

View File

@@ -30,7 +30,7 @@
"in_global_search": 0,
"in_list_view": 0,
"in_standard_filter": 0,
"label": "Enrollment",
"label": "Course Enrollment",
"length": 0,
"no_copy": 0,
"options": "Course Enrollment",
@@ -298,4 +298,4 @@
"track_changes": 1,
"track_seen": 0,
"track_views": 0
}
}

View File

@@ -5,6 +5,7 @@
"engine": "InnoDB",
"field_order": [
"course",
"course_name",
"required"
],
"fields": [
@@ -16,6 +17,14 @@
"label": "Course",
"options": "Course",
"reqd": 1
},
{
"fieldname": "course_name",
"fieldtype": "Data",
"in_list_view": 1,
"label": "Course Name",
"fetch_from": "course.course_name",
"read_only":1
},
{
"default": "0",
@@ -36,4 +45,4 @@
"sort_field": "modified",
"sort_order": "DESC",
"track_changes": 1
}
}

View File

@@ -54,6 +54,7 @@ class Student(Document):
'send_welcome_email': 1,
'user_type': 'Website User'
})
student_user.flags.ignore_permissions = True
student_user.add_roles("Student")
student_user.save()
update_password_link = student_user.reset_password()

View File

@@ -705,7 +705,6 @@
"bold": 0,
"collapsible": 0,
"columns": 0,
"default": "INDIAN",
"fieldname": "nationality",
"fieldtype": "Data",
"hidden": 0,
@@ -1231,4 +1230,4 @@
"track_changes": 0,
"track_seen": 0,
"track_views": 0
}
}

View File

@@ -55,7 +55,7 @@ def preview_report_card(doc):
"courses": courses,
"assessment_groups": assessment_groups,
"course_criteria": course_criteria,
"letterhead": letterhead.content,
"letterhead": letterhead and letterhead.get('content', None),
"add_letterhead": doc.add_letterhead if doc.add_letterhead else 0
})
final_template = frappe.render_template(base_template_path, {"body": html, "title": "Report Card"})
@@ -89,4 +89,4 @@ def get_attendance_count(student, academic_year, academic_term=None):
attendance["Present"] = 0
return attendance
else:
frappe.throw(_("Provide the academic year and set the starting and ending date."))
frappe.throw(_("Provide the academic year and set the starting and ending date."))

View File

@@ -89,8 +89,6 @@ def request_and_fetch_report_id(report_type, start_date=None, end_date=None, mar
end_date=end_date,
marketplaceids=marketplaceids)
#add time delay to wait for amazon to generate report
time.sleep(20)
report_request_id = report_response.parsed["ReportRequestInfo"]["ReportRequestId"]["value"]
generated_report_id = None
#poll to get generated report

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