blob: 964a175ac9fdab9ac810df639b3ba1590ec33ca8 [file] [log] [blame]
Anand Doshi885e0742015-03-03 14:55:30 +05301// Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors
Nabin Haitce245122015-02-22 20:14:49 +05302// License: GNU General Public License v3. See license.txt
3
Rushabh Mehtaf56d73c2013-10-10 16:35:09 +05304// get tax rate
Rushabh Mehta2a21bc92015-02-25 15:08:42 +05305frappe.provide("erpnext.taxes");
Rushabh Mehta2a21bc92015-02-25 15:08:42 +05306
Deepesh Garg9e791ef2023-07-17 21:44:43 +05307erpnext.accounts.taxes = {
8 setup_tax_validations: function(doctype) {
9 let me = this;
10 frappe.ui.form.on(doctype, {
11 setup: function(frm) {
12 // set conditional display for rate column in taxes
13 $(frm.wrapper).on('grid-row-render', function(e, grid_row) {
barredterrad2387512024-03-19 12:03:36 +010014 if(['Sales Taxes and Charges', 'Purchase Taxes and Charges'].includes(grid_row.doc.doctype)) {
Deepesh Garg9e791ef2023-07-17 21:44:43 +053015 me.set_conditional_mandatory_rate_or_amount(grid_row);
16 }
17 });
18 },
19 onload: function(frm) {
20 if(frm.get_field("taxes")) {
21 frm.set_query("account_head", "taxes", function(doc) {
22 if(frm.cscript.tax_table == "Sales Taxes and Charges") {
23 var account_type = ["Tax", "Chargeable", "Expense Account"];
24 } else {
25 var account_type = ["Tax", "Chargeable", "Income Account", "Expenses Included In Valuation"];
26 }
27
28 return {
29 query: "erpnext.controllers.queries.tax_account_query",
30 filters: {
31 "account_type": account_type,
32 "company": doc.company,
Deepesh Garg9e791ef2023-07-17 21:44:43 +053033 }
34 }
35 });
36 frm.set_query("cost_center", "taxes", function(doc) {
37 return {
38 filters: {
39 "company": doc.company,
40 "is_group": 0
41 }
42 };
43 });
44 }
45 },
46 validate: function(frm) {
47 // neither is absolutely mandatory
48 if(frm.get_docfield("taxes")) {
49 frm.get_docfield("taxes", "rate").reqd = 0;
50 frm.get_docfield("taxes", "tax_amount").reqd = 0;
51 }
52
53 },
54 taxes_on_form_rendered: function(frm) {
55 me.set_conditional_mandatory_rate_or_amount(frm.open_grid_row());
56 },
57 });
58 },
59
60 set_conditional_mandatory_rate_or_amount: function(grid_row) {
61 if(grid_row) {
62 if(grid_row.doc.charge_type==="Actual") {
63 grid_row.toggle_editable("tax_amount", true);
64 grid_row.toggle_reqd("tax_amount", true);
65 grid_row.toggle_editable("rate", false);
66 grid_row.toggle_reqd("rate", false);
67 } else {
68 grid_row.toggle_editable("rate", true);
69 grid_row.toggle_reqd("rate", true);
70 grid_row.toggle_editable("tax_amount", false);
71 grid_row.toggle_reqd("tax_amount", false);
72 }
73 }
74 },
75
76 validate_taxes_and_charges: function(cdt, cdn) {
77 let d = locals[cdt][cdn];
78 let msg = "";
79
80 if (d.account_head && !d.description) {
81 // set description from account head
82 d.description = d.account_head.split(' - ').slice(0, -1).join(' - ');
83 }
84
85 if (!d.charge_type && (d.row_id || d.rate || d.tax_amount)) {
86 msg = __("Please select Charge Type first");
87 d.row_id = "";
88 d.rate = d.tax_amount = 0.0;
89 } else if ((d.charge_type == 'Actual' || d.charge_type == 'On Net Total' || d.charge_type == 'On Paid Amount') && d.row_id) {
90 msg = __("Can refer row only if the charge type is 'On Previous Row Amount' or 'Previous Row Total'");
91 d.row_id = "";
92 } else if ((d.charge_type == 'On Previous Row Amount' || d.charge_type == 'On Previous Row Total') && d.row_id) {
93 if (d.idx == 1) {
94 msg = __("Cannot select charge type as 'On Previous Row Amount' or 'On Previous Row Total' for first row");
95 d.charge_type = '';
96 } else if (!d.row_id) {
97 msg = __("Please specify a valid Row ID for row {0} in table {1}", [d.idx, __(d.doctype)]);
98 d.row_id = "";
99 } else if (d.row_id && d.row_id >= d.idx) {
100 msg = __("Cannot refer row number greater than or equal to current row number for this Charge type");
101 d.row_id = "";
102 }
103 }
104 if (msg) {
105 frappe.validated = false;
106 refresh_field("taxes");
107 frappe.throw(msg);
108 }
109
110 },
111
112 setup_tax_filters: function(doctype) {
113 let me = this;
114 frappe.ui.form.on(doctype, {
115 account_head: function(frm, cdt, cdn) {
116 let d = locals[cdt][cdn];
117
Rishik Sahu5ebf7c82023-10-12 14:03:49 +0530118 if (d.docstatus == 1) {
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530119 // Should not trigger any changes on change post submit
120 return;
121 }
122
123 if(!d.charge_type && d.account_head){
124 frappe.msgprint(__("Please select Charge Type first"));
125 frappe.model.set_value(cdt, cdn, "account_head", "");
126 } else if (d.account_head) {
127 frappe.call({
128 type:"GET",
129 method: "erpnext.controllers.accounts_controller.get_tax_rate",
130 args: {"account_head":d.account_head},
131 callback: function(r) {
132 if (d.charge_type!=="Actual") {
133 frappe.model.set_value(cdt, cdn, "rate", r.message.tax_rate || 0);
134 }
135 frappe.model.set_value(cdt, cdn, "description", r.message.account_name);
136 }
137 })
138 }
139 },
140 row_id: function(frm, cdt, cdn) {
141 me.validate_taxes_and_charges(cdt, cdn);
142 },
143 rate: function(frm, cdt, cdn) {
144 me.validate_taxes_and_charges(cdt, cdn);
145 },
146 tax_amount: function(frm, cdt, cdn) {
147 me.validate_taxes_and_charges(cdt, cdn);
148 },
149 charge_type: function(frm, cdt, cdn) {
150 me.validate_taxes_and_charges(cdt, cdn);
151 let open_form = frm.open_grid_row();
152 if(open_form) {
153 me.set_conditional_mandatory_rate_or_amount(open_form);
154 } else {
155 // apply in current row
156 me.set_conditional_mandatory_rate_or_amount(frm.get_field('taxes').grid.get_row(cdn));
157 }
158 },
159 included_in_print_rate: function(frm, cdt, cdn) {
160 let tax = frappe.get_doc(cdt, cdn);
161 try {
162 me.validate_taxes_and_charges(cdt, cdn);
Dany Robert50d56db2024-01-29 09:32:44 +0530163 me.validate_inclusive_tax(tax, frm);
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530164 } catch(e) {
165 tax.included_in_print_rate = 0;
166 refresh_field("included_in_print_rate", tax.name, tax.parentfield);
167 throw e;
168 }
Rushabh Mehta2cb7a9f2016-06-15 16:45:03 +0530169 }
170 });
171 },
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530172
Dany Robert50d56db2024-01-29 09:32:44 +0530173 validate_inclusive_tax: function(tax, frm) {
174 this.frm = this.frm || frm;
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530175 let actual_type_error = function() {
176 var msg = __("Actual type tax cannot be included in Item rate in row {0}", [tax.idx])
177 frappe.throw(msg);
178 };
179
180 let on_previous_row_error = function(row_range) {
181 var msg = __("For row {0} in {1}. To include {2} in Item rate, rows {3} must also be included",
182 [tax.idx, __(tax.doctype), tax.charge_type, row_range])
183 frappe.throw(msg);
184 };
185
186 if(cint(tax.included_in_print_rate)) {
187 if(tax.charge_type == "Actual") {
188 // inclusive tax cannot be of type Actual
189 actual_type_error();
Dany Robert50d56db2024-01-29 09:32:44 +0530190 } else if (tax.charge_type == "On Previous Row Amount" && this.frm &&
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530191 !cint(this.frm.doc["taxes"][tax.row_id - 1].included_in_print_rate)
192 ) {
193 // referred row should also be an inclusive tax
194 on_previous_row_error(tax.row_id);
Dany Robert50d56db2024-01-29 09:32:44 +0530195 } else if (tax.charge_type == "On Previous Row Total" && this.frm) {
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530196 var taxes_not_included = $.map(this.frm.doc["taxes"].slice(0, tax.row_id),
197 function(t) { return cint(t.included_in_print_rate) ? null : t; });
198 if(taxes_not_included.length > 0) {
199 // all rows above this tax should be inclusive
200 on_previous_row_error(tax.row_id == 1 ? "1" : "1 - " + tax.row_id);
Rushabh Mehtac712cdb2015-05-03 22:20:44 +0530201 }
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530202 } else if(tax.category == "Valuation") {
203 frappe.throw(__("Valuation type charges can not marked as Inclusive"));
Rohit Waghchaure70be24d2016-08-08 22:54:38 +0530204 }
205 }
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530206 }
Rohit Waghchaure70be24d2016-08-08 22:54:38 +0530207}
208
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530209erpnext.accounts.payment_triggers = {
210 setup: function(doctype) {
Deepesh Garg40772542023-07-22 23:07:18 +0530211 frappe.ui.form.on(doctype, {
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530212 allocate_advances_automatically(frm) {
213 frm.trigger('fetch_advances');
214 },
Deepesh Garge6261072022-10-17 16:48:13 +0530215
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530216 only_include_allocated_payments(frm) {
217 frm.trigger('fetch_advances');
218 },
Deepesh Garge6261072022-10-17 16:48:13 +0530219
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530220 fetch_advances(frm) {
221 if(frm.doc.allocate_advances_automatically) {
222 frappe.call({
223 doc: frm.doc,
224 method: "set_advances",
225 callback: function(r, rt) {
226 refresh_field("advances");
227 }
228 })
pateljannat5b02d322020-11-05 18:04:14 +0530229 }
Rushabh Mehtaf56d73c2013-10-10 16:35:09 +0530230 }
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530231 });
232 },
Rushabh Mehtaf56d73c2013-10-10 16:35:09 +0530233}
Nabin Haitce245122015-02-22 20:14:49 +0530234
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530235erpnext.accounts.pos = {
236 setup: function(doctype) {
237 frappe.ui.form.on(doctype, {
238 mode_of_payment: function(frm, cdt, cdn) {
239 var d = locals[cdt][cdn];
240 get_payment_mode_account(frm, d.mode_of_payment, function(account){
241 frappe.model.set_value(cdt, cdn, 'account', account)
242 })
Nabin Hait613d0812015-02-23 11:58:15 +0530243 }
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530244 });
245 },
246
247 get_payment_mode_account: function(frm, mode_of_payment, callback) {
248 if(!frm.doc.company) {
249 frappe.throw({message:__("Please select a Company first."), title: __("Mandatory")});
Nabin Hait613d0812015-02-23 11:58:15 +0530250 }
Nabin Haitce245122015-02-22 20:14:49 +0530251
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530252 if(!mode_of_payment) {
253 return;
Rushabh Mehta2cb7a9f2016-06-15 16:45:03 +0530254 }
Rushabh Mehta2a21bc92015-02-25 15:08:42 +0530255
Deepesh Garg9e791ef2023-07-17 21:44:43 +0530256 return frappe.call({
257 method: "erpnext.accounts.doctype.sales_invoice.sales_invoice.get_bank_cash_account",
258 args: {
259 "mode_of_payment": mode_of_payment,
260 "company": frm.doc.company
261 },
262 callback: function(r, rt) {
263 if(r.message) {
264 callback(r.message.account)
265 }
266 }
267 });
Nabin Hait613d0812015-02-23 11:58:15 +0530268 }
Rushabh Mehta2a21bc92015-02-25 15:08:42 +0530269}