PluginProbe
MainWP Dashboard: Self-hosted WordPress Management for Agencies / 6.2.2
MainWP Dashboard: Self-hosted WordPress Management for Agencies v6.2.2
6.2.2 6.2.1 6.2 6.1.8 6.1.7 6.1.6 6.1.5 6.1.4 6.1.3 6.1.2 6.1.1 6.1 6.0.12 6.0.11 4.6.0.1 5.0 5.0.1 5.0.2 5.0.3 5.0.3.1 5.0.3.2 5.1 5.1.1 5.2 5.2.1 All 155 releases
mainwp / assets / js / mainwp-clients.js

mainwp-clients.js in MainWP Dashboard: Self-hosted WordPress Management for Agencies 6.2.2, at assets/js/mainwp-clients.js

930 lines 35.8 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 /**
2 * MainWP Clients.page
3 */
4 /* eslint-disable complexity */
5 let import_client_current = 0;
6 let import_client_total = 0;
7 let import_client_count_success = 0;
8 let import_client_count_fails = 0;
9 let import_client_stop_by_user = false;
10 jQuery(function () {
11
12 // Toggle bulk actions based on checkbox selection
13 jQuery(document).on('change', '#mainwp-manage-sites-body-table .check-column INPUT:checkbox', function () {
14 mainwp_clients_toggle_bulk_actions();
15 });
16
17 // Toggle bulk actions for client fields
18 jQuery(document).on('change', '#mainwp-clients-custom-fields-table .check-column INPUT:checkbox', function () {
19 mainwp_client_fields_toggle_bulk_actions();
20 });
21
22 // Select all client fields
23 jQuery(document).on('change', '#mainwp-client-fields-select-all', function () {
24 jQuery('.mainwp-client-field-checkbox').prop('checked', jQuery(this).prop('checked'));
25 mainwp_client_fields_toggle_bulk_actions();
26 });
27
28 // Handle bulk actions for client fields
29 jQuery(document).on('click', '#mainwp-do-client-fields-bulk-actions', function () {
30 const action = jQuery('#mainwp-client-fields-bulk-actions-menu').dropdown('get value');
31 if (action === 'delete') {
32 mainwp_client_fields_bulk_delete();
33 }
34 return false;
35 });
36
37 // Delete single client.
38 jQuery(document).on('click', '.client_deleteitem', function () {
39 let confirmation = confirm('Are you sure you want to proceed?');
40 if (confirmation) {
41 let parent = jQuery(this).closest('div.menu');
42 let rowElement = jQuery(this).parents('tr');
43 let clientid = parent.attr('clientid');
44 let data = mainwp_secure_data({
45 action: 'mainwp_clients_delete_client',
46 clientid: clientid,
47 });
48 jQuery.post(ajaxurl, data, function (response) {
49 if (response.success) {
50 rowElement.html('<td colspan="8"><i class="green check icon"></i> ' + response.result + '</td>');
51 }
52 }, 'json');
53 }
54
55 return false;
56 });
57
58 jQuery(document).on('click', '.client-suspend-unsuspend-sites', function () {
59 const $button = jQuery(this);
60
61 const new_status = $button.attr('suspend-status') === '0' ? 1 : 0;
62 const clientid = $button.closest('.mainwp-widget-footer').attr('client-id');
63
64 const data = mainwp_secure_data({
65 action: 'mainwp_clients_suspend_client',
66 clientid: clientid,
67 suspend_status: new_status
68 });
69
70 $button.prop('disabled', true);
71
72 jQuery.post(ajaxurl, data, function (response) {
73 $button.prop('disabled', false);
74
75 if (response === 'success') {
76 $button.text(new_status === 0 ? MainWP.I18n.t('Suspend Sites') : MainWP.I18n.t('Unsuspend Sites'));
77 $button.attr('suspend-status', new_status);
78 }
79 });
80 });
81
82 jQuery('#mainwp_edit_clients_icon_select').dropdown({
83 onChange: function (val) {
84 const $field = jQuery('[id="client_fields[default_field][selected_icon]"]');
85 $field.val(val);
86 $field.trigger('change');
87 }
88 });
89
90
91 jQuery('.mainwp-edit-clients-select-contact-icon').dropdown({
92 onChange: function (val) {
93 const $parent = jQuery(this).closest('.mainwp_edit_clients_contact_icon_wrapper');
94 const inname = $parent.attr('input-name');
95
96 if (inname !== undefined) {
97 const selector = `[id="client_fields[${inname}][selected_icon][]"]`;
98 const $field = $parent.find(selector);
99
100 $field.val(val);
101 $field.trigger('change');
102 }
103 }
104 });
105
106
107 jQuery(document).on('click', '.mainwp-client-add-contact', function () {
108 let templ = jQuery(this).attr('add-contact-temp');
109 jQuery('.after-add-contact-field').after(templ);
110 let justAdded = jQuery('.after-add-contact-field').next().next().next().next().next().next();
111 jQuery(justAdded).find('.mainwp-edit-clients-select-contact-icon').dropdown({
112 onChange: function (val) {
113 let parent = jQuery(this).closest('.mainwp_edit_clients_contact_icon_wrapper');
114 let inname = parent.attr('input-name');
115 if (undefined !== inname) {
116 const selector = `[id="client_fields[${inname}][selected_icon][]"]`;
117 const $field = $parent.find(selector);
118 $field.val(val);
119 $field.trigger('change');
120 }
121 }
122 });
123 });
124
125 jQuery(document).on('click', '.mainwp-client-remove-contact', function () {
126
127 if (jQuery(this).attr('contact-id') > 0) {
128 jQuery('.after-add-contact-field').before('<input type="hidden" value="' + jQuery(this).attr('contact-id') + '" name="client_fields[delele_contacts][]">'); // to delete contact when submit the client.
129 }
130
131 let parent = jQuery(this).closest('.remove-contact-field-parent');
132 let limit = 0;
133 while (!parent.prev().hasClass('top-contact-fields')) {
134 limit++;
135 parent.prev().remove(); // prev contact field.
136 if (limit > 50) break;
137 }
138 if (parent.prev().hasClass('top-contact-fields')) {
139 parent.prev().remove();
140 }
141 if (parent.next().hasClass('bottom-contact-fields')) {
142 parent.next().remove();
143 }
144 parent.remove();
145 });
146
147 // Handel Modal import client
148 import_client_total = jQuery('#mainwp_manageclients_total_import').val();
149 if (jQuery('#mainwp_manageclients_do_import').val() == 1) {
150 mainwp_manageclient_import_client();
151 }
152
153 jQuery(document).on('click', '#mainwp_manageclients_btn_import', function () {
154 if (import_client_stop_by_user) {
155 import_client_stop_by_user = false;
156 jQuery('#mainwp_manageclients_import_logging .log').append(MainWP.I18n.t('Continue import.') + "\n");
157 jQuery('#mainwp_manageclients_btn_import').val(MainWP.I18n.t('Pause'));
158 mainwp_manageclient_import_client();
159 } else {
160 import_client_stop_by_user = true;
161 jQuery('#mainwp_manageclients_import_logging .log').append(MainWP.I18n.t('Paused import by user.') + "\n");
162 jQuery('#mainwp_manageclients_btn_import').val(MainWP.I18n.t('Continue'));
163 }
164 });
165
166 });
167
168
169 let bulkManageClientsMaxThreads = mainwpParams['maximumInstallUpdateRequests'] == undefined ? 3 : mainwpParams['maximumInstallUpdateRequests'];
170 let bulkManageClientsCurrentThreads = 0;
171 let bulkManageClientsTotal = 0;
172 let bulkManageClientsFinished = 0;
173 let bulkManageClientsTaskRunning = false;
174
175 // Trigger Manage Bulk Actions
176 jQuery(document).on('click', '#mainwp-do-clients-bulk-actions', function () {
177 let action = jQuery("#mainwp-clients-bulk-actions-menu").dropdown("get value");
178 if (action) {
179 mainwp_manageclients_doaction(action);
180 }
181 return false;
182 });
183
184
185 let mainwp_manageclients_doaction = function (action) {
186 if (action && !bulkManageClientsTaskRunning) {
187 let confirmMsg = '';
188 if (action === 'delete') {
189 confirmMsg = MainWP.I18n.t("You are about to remove the selected clients from your MainWP Dashboard?");
190 }
191 mainwp_confirm(confirmMsg, function () { mainwp_manageclients_doaction_process(action); });
192 }
193 return false;
194 }
195
196
197
198 let mainwp_manageclients_doaction_process = function (action) {
199
200 manageclients_bulk_init();
201
202 bulkManageClientsTotal = jQuery('#mainwp-manage-sites-body-table .check-column INPUT:checkbox:checked[status="queue"]').length;
203 bulkManageClientsTaskRunning = true;
204
205 if (action == 'delete') {
206 mainwp_manageclients_bulk_remove_next();
207 return false;
208 }
209 }
210
211
212
213 let mainwp_manageclients_bulk_remove_next = function () {
214 while ((checkedBox = jQuery('#mainwp-manage-sites-body-table .check-column INPUT:checkbox:checked[status="queue"]:first')) && (checkedBox.length > 0) && (bulkManageClientsCurrentThreads < bulkManageClientsMaxThreads)) { // NOSONAR -- modified out side the function.
215 mainwp_manageclients_bulk_remove_specific(checkedBox);
216 }
217 if ((bulkManageClientsTotal > 0) && (bulkManageClientsFinished == bulkManageClientsTotal)) { // NOSONAR -- modified out side the function.
218 setHtml('#mainwp-message-zone-client', MainWP.I18n.t("Process completed. Reloading page..."));
219 setTimeout(function () {
220 mainwp_forceReload();
221 }, 3000);
222 }
223 }
224
225 let mainwp_manageclients_bulk_remove_specific = function (pCheckedBox) {
226
227 pCheckedBox.attr('status', 'running');
228 let rowObj = pCheckedBox.closest('tr');
229 bulkManageClientsCurrentThreads++;
230
231 let id = rowObj.attr('clientid');
232
233 rowObj.html('<td colspan="999"><i class="notched circle loading icon"></i> ' + 'Removing ...' + '</td>');
234
235 let data = mainwp_secure_data({
236 action: 'mainwp_clients_delete_client',
237 clientid: id
238 });
239 jQuery.post(ajaxurl, data, function (response) {
240 bulkManageClientsCurrentThreads--;
241 bulkManageClientsFinished++;
242 rowObj.html('<td colspan="999"></td>');
243 let result = '';
244 let error = '';
245 if (response.error != undefined) {
246 error = response.error;
247 } else if (response.success == 'SUCCESS') {
248 result = MainWP.I18n.t('The client has been removed.');
249 }
250
251 if (error == '') {
252 rowObj.html('<td colspan="999"><i class="green check icon"></i> ' + result + '</td>');
253 } else {
254 rowObj.html('<td colspan="999"><i class="red times icon"></i> ' + error + '</td>');
255 }
256
257 setTimeout(function () {
258 jQuery('tr[clientid=' + id + ']').fadeOut(1000);
259 }, 3000);
260
261 mainwp_manageclients_bulk_remove_next();
262 }, 'json');
263 };
264
265 let manageclients_bulk_init = function () {
266 mainwp_set_message_zone('#mainwp-message-zone-client');
267 if (!bulkManageClientsTaskRunning) {
268 bulkManageClientsMaxThreads = mainwpParams['maximumInstallUpdateRequests'] == undefined ? 3 : mainwpParams['maximumInstallUpdateRequests'];
269 bulkManageClientsCurrentThreads = 0;
270 bulkManageClientsTotal = 0;
271 bulkManageClientsFinished = 0;
272 jQuery('#mainwp-manage-sites-body-table .check-column INPUT:checkbox').each(function () {
273 jQuery(this).attr('status', 'queue')
274 });
275 }
276 };
277
278 let mainwp_clients_toggle_bulk_actions = function () {
279 const checkedCount = jQuery('#mainwp-manage-sites-body-table .check-column INPUT:checkbox:checked').length;
280 const bulkActionsMenu = jQuery('#mainwp-clients-bulk-actions-menu');
281 const applyButton = jQuery('#mainwp-do-clients-bulk-actions');
282
283 if (checkedCount > 0) {
284 bulkActionsMenu.removeClass('disabled');
285 applyButton.prop('disabled', false);
286 } else {
287 bulkActionsMenu.addClass('disabled');
288 applyButton.prop('disabled', true);
289 }
290 };
291
292 let mainwp_client_fields_toggle_bulk_actions = function () {
293 const checkedCount = jQuery('#mainwp-clients-custom-fields-table .check-column INPUT:checkbox:checked').length;
294 const bulkActionsMenu = jQuery('#mainwp-client-fields-bulk-actions-menu');
295 const applyButton = jQuery('#mainwp-do-client-fields-bulk-actions');
296
297 if (checkedCount > 0) {
298 bulkActionsMenu.removeClass('disabled');
299 applyButton.prop('disabled', false);
300 } else {
301 bulkActionsMenu.addClass('disabled');
302 applyButton.prop('disabled', true);
303 }
304 };
305
306 let mainwp_client_fields_bulk_delete = function () {
307 const selectedFields = [];
308 jQuery('.mainwp-client-field-checkbox:checked').each(function () {
309 selectedFields.push(jQuery(this).val());
310 });
311
312 if (selectedFields.length === 0) {
313 return false;
314 }
315
316 const confirmMessage = selectedFields.length === 1
317 ? MainWP.I18n.t('Are you sure you want to delete this field?')
318 : MainWP.I18n.t('Are you sure you want to delete these %s fields?').replace('%s', selectedFields.length);
319
320 if (!confirm(confirmMessage)) {
321 return false;
322 }
323
324 mainwp_set_message_zone('#mainwp-message-zone-client');
325
326 jQuery.post(ajaxurl, mainwp_secure_data({
327 action: 'mainwp_clients_bulk_delete_fields',
328 field_ids: selectedFields,
329 }), function (response) {
330 if (response?.success) {
331 selectedFields.forEach(function (fieldId) {
332 jQuery('.mainwp-field[field-id="' + fieldId + '"]').fadeOut(300, function () {
333 jQuery(this).remove();
334 if (jQuery('#mainwp-clients-custom-fields-table tbody tr').length === 0) {
335 location.reload();
336 }
337 });
338 });
339 mainwp_set_message_zone('#mainwp-message-zone-client', MainWP.I18n.t('Selected fields have been deleted successfully.'), 'green');
340 jQuery('#mainwp-client-fields-select-all').prop('checked', false);
341 mainwp_client_fields_toggle_bulk_actions();
342 } else {
343 const errorMessage = response?.data?.message || MainWP.I18n.t('Fields could not be deleted.');
344 mainwp_set_message_zone('#mainwp-message-zone-client', errorMessage, 'red');
345 }
346 }, 'json');
347
348 return true;
349 };
350
351 // Handle tab QSW add client
352 const mainwp_add_client_onvisible_callback = function (obj_item) {
353 const tab = jQuery(obj_item).attr("data-tab");
354 if (tab === 'multiple-client') {
355 jQuery('#bulk_add_createclient').hide();
356 jQuery('#mainwp_qsw_add_client_continue_button').show();
357 } else if (tab === 'single-client') {
358 jQuery('#mainwp_qsw_add_client_continue_button').show();
359 jQuery('#bulk_add_multi_create_client').hide();
360 }
361 }
362
363 // Handle remove row client
364 const mainwp_qsw_add_client_delete_row = function (index) {
365 const row = jQuery("#mainwp-qsw-add-client-row-" + index);
366 row.remove();
367 return false;
368 }
369 // Handle show more input òn client multi client.
370 const mainwp_qsw_add_client_more_row = function (index) {
371 jQuery(".mainwp-qsw-add-client-column-more-" + index).fadeToggle("slow");
372 jQuery("#icon-visible-" + index).toggle();
373 jQuery("#icon-hidden-" + index).toggle();
374 return false;
375 }
376
377 // Track keyup events on Client Name and Client Email inputs.
378 jQuery(document).on('keyup change', '.mainwp-qsw-add-client-client-name, .mainwp-qsw-add-client-client-email, input[name^="client_fields"][name$="[client.contact.name][]"], input[name^="client_fields"][name$="[contact.email][]"]', function () {
379 const current_row = jQuery(this).closest('.mainwp-qsw-add-client-rows');
380 const client_name = current_row.find('.mainwp-qsw-add-client-client-name').val().trim();
381 const client_email = current_row.find('.mainwp-qsw-add-client-client-email').val().trim();
382
383 // If at least one of the two inputs Client Name or Client Email has data
384 if (client_name !== '' || client_email !== '') {
385 jQuery('#bulk_add_multi_create_client').show(); // Display Add Multi Client button.
386 jQuery('#mainwp_qsw_add_client_continue_button').hide(); // Hide Continue button.
387 } else {
388 // If all fields are empty, hide the Add Multi Client button.
389 let all_empty = true;
390 jQuery('.mainwp-qsw-add-client-client-name, .mainwp-qsw-add-client-client-email, input[name^="client_fields"][name$="[client.contact.name][]"], input[name^="client_fields"][name$="[contact.email][]"]').each(function () {
391 if (jQuery(this).val().trim() !== '') {
392 all_empty = false;
393 }
394 });
395
396 if (all_empty) {
397 jQuery('#bulk_add_multi_create_client').hide(); // Hide Add Multi Client button.
398 jQuery('#mainwp_qsw_add_client_continue_button').show(); // Display Continue button.
399 }
400 }
401 });
402
403 // Handle event click button Add Multi Client
404 jQuery(document).on('click', '#bulk_add_multi_create_client', function (e) {
405 let all_rows_valid = true;
406 let errors = []; // Array declaration containing error messages.
407 let form_data = []; // Initialize array containing form data
408 // eslint-disable-next-line complexity
409 jQuery('.mainwp-qsw-add-client-rows').each(function () { //phpcs:ignore -- NOSONAR -- complex
410 let website_id = null;
411 const row_index = jQuery(this).attr('id').replace('mainwp-qsw-add-client-row-', '');
412
413 if (jQuery('#mainwp-qsw-add-client-website-id-' + row_index).length > 0) {
414 website_id = jQuery('#mainwp-qsw-add-client-website-id-' + row_index)?.val().trim();
415 }
416 const site_url = jQuery('#mainwp-qsw-add-client-site-url-' + row_index).val().trim();
417 const client_name = jQuery('#mainwp-qsw-add-client-client-name-' + row_index).val().trim();
418 const client_email = jQuery('#mainwp-qsw-add-client-client-email-' + row_index).val().trim();
419 const contact_name = jQuery('input[name="client_fields[' + row_index + '][new_contacts_field][client.contact.name][]"]').val().trim();
420 const contact_email = jQuery('input[name="client_fields[' + row_index + '][new_contacts_field][contact.email][]"]').val().trim();
421 const contact_role = jQuery('input[name="client_fields[' + row_index + '][new_contacts_field][contact.role][]"]').val().trim();
422
423
424 // Check if the line has Client Name or Client Email, but is missing data.
425 if (client_name !== '' || client_email !== '') {
426 if (site_url === '' || client_name === '' || client_email === '') {
427 all_rows_valid = false;
428 errors.push(`The data in row ${(Number.parseInt(row_index) + 1)} is incomplete!`);
429 }
430
431 if (contact_name !== '' || contact_email !== '') {
432 if (contact_name === '' || contact_email === '') {
433 all_rows_valid = false;
434 errors.push(`The data in row ${(Number.parseInt(row_index) + 1)} is incomplete!`);
435 }
436 }
437
438 if ((!mainwp_validate_email(client_email) && client_email !== '') || (contact_email !== '' && !mainwp_validate_email(contact_email))) {
439 all_rows_valid = false;
440 errors.push(`Field email in row ${(Number.parseInt(row_index) + 1)} is invalid!`);
441 }
442
443 // If All rows valid then add data to form_data
444 if (all_rows_valid) {
445 form_data.push({
446 website_id: website_id,
447 website_url: site_url,
448 client_name: client_name,
449 client_email: client_email,
450 contacts_field: {
451 contact_name: contact_name,
452 contact_email: contact_email,
453 contact_role: contact_role
454 }
455 });
456 }
457 }
458 });
459
460 // If there is a column with missing data, prevent submission and display a message.
461 if (all_rows_valid) {
462 let msg = MainWP.I18n.t('Creating the client. Please wait...');
463 jQuery('#mainwp-message-zone').html('').hide(); // Hide message error
464 mainwp_set_message_zone('#mainwp-message-zone-client', '<i class="notched circle loading icon"></i> ' + msg); // show message creating.
465 jQuery('#bulk_add_multi_create_client').attr('disabled', 'disabled'); // disable button
466
467 const data = mainwp_secure_data({
468 action: "mainwp_clients_add_multi_client",
469 data: form_data,
470 });
471 jQuery.post(ajaxurl, data, function (response) {
472 if (response?.success) {
473 mainwp_forceReload('admin.php?page=mainwp-setup&step=monitoring&message=1');
474 } else if (response?.error) {
475 mainwp_set_message_zone('#mainwp-message-zone', response.error, 'red');
476 } else {
477 mainwp_set_message_zone('#mainwp-message-zone', MainWP.I18n.t('Undefined error. Please try again.'), 'red');
478 }
479 jQuery('#bulk_add_multi_create_client').attr('disabled', false); // enable button
480 });
481 return true;
482 }
483
484 e.preventDefault(); //Prevent form submission or further processing.
485 mainwp_set_message_zone('#mainwp-message-zone', errors.join('<br />'), 'red');
486 return false;
487
488 });
489
490 jQuery(document).on('click', '#bulk_add_createclient', function () {
491 let currPage = jQuery(this).attr('current-page');
492 mainwp_createclient(currPage);
493 });
494
495 let mainwp_createclient = function (currPage) {
496 if (jQuery('input[name="client_fields[default_field][client.name]"]').val() == '') {
497 feedback('mainwp-message-zone-client', MainWP.I18n.t('Client name field is required! Please enter a Client name.'), 'yellow');
498 return;
499 }
500
501 let valid_contact = true;
502 jQuery('input[name="client_fields[new_contacts_field][client.contact.name][]"]').each(function () {
503 if (jQuery(this).val() == '') {
504 valid_contact = false;
505 }
506 });
507 jQuery('input[name="client_fields[new_contacts_field][contact.email][]"]').each(function () {
508 if (jQuery(this).val() == '') {
509 valid_contact = false;
510 }
511 });
512
513
514 jQuery('input[name="client_fields[contacts_field][client.contact.name][]"]').each(function () {
515 if (jQuery(this).val() == '') {
516 valid_contact = false;
517 }
518 });
519 jQuery('input[name="client_fields[contacts_field][client.contact.email][]"]').each(function () {
520 if (jQuery(this).val() == '') {
521 valid_contact = false;
522 }
523 });
524
525
526 if (!valid_contact) {
527 feedback('mainwp-message-zone-client', MainWP.I18n.t('Contact Name and Contact Email are required. Please enter a Contact Name and Contact Email.'), 'yellow');
528 return;
529 }
530
531 let selected_sites = [];
532 jQuery("input[name='selected_sites[]']:checked").each(function () {
533 selected_sites.push(jQuery(this).val());
534 });
535
536 if (jQuery('input[name="select_by"]').val() == 'site') {
537 selected_sites = [];
538 jQuery("input[name='selected_sites[]']:checked").each(function () {
539 selected_sites.push(jQuery(this).val());
540 });
541 }
542
543 let is_first_client = false;
544 if (jQuery("input[name=selected_first_site]").length > 0) {
545 selected_sites.push(jQuery("input[name=selected_first_site]").val());
546 is_first_client = true;
547 }
548
549 mainwp_set_message_zone('#mainwp-message-zone-client');
550 let msg = MainWP.I18n.t('Creating the client. Please wait...');
551 if (jQuery('input[name="client_fields[client_id]"]').val() != 0) {
552 msg = MainWP.I18n.t('Updating the client. Please wait...');
553 }
554 mainwp_set_message_zone('#mainwp-message-zone-client', '<i class="notched circle loading icon"></i> ' + msg);
555 jQuery('#bulk_add_createclient').attr('disabled', 'disabled');
556
557 //Add Client via ajax!!
558 let formdata = new FormData(jQuery('#createclient_form')[0]);
559 formdata.append("action", 'mainwp_clients_add_client');
560 formdata.append("select_by", jQuery('input[name="select_by"]').val());
561 formdata.append("selected_sites[]", selected_sites);
562 formdata.append("is_first_client", is_first_client);
563 formdata.append("security", security_nonces['mainwp_clients_add_client']);
564
565 jQuery.ajax({
566 type: 'POST',
567 url: ajaxurl,
568 data: formdata,
569 success: function (response) {
570 mainwp_set_message_zone('#mainwp-message-zone-client');
571 jQuery('#bulk_add_createclient').prop("disabled", false);
572 if (response?.success) {
573 if ('add-new' == currPage) {
574 mainwp_forceReload("admin.php?page=ManageClients");
575 } else if ('qsw-add' == currPage) {
576 mainwp_set_message_zone('#mainwp-message-zone', '<a href="admin.php?page=mainwp-setup&step=monitoring" class="ui mini basic green right floated button">Continue</a><div class="ui header">Congratulations! You have added your first client.</div> After finishing the Quick Setup Wizard, you can add more clients from the Add New Client page. Proceeding to the next step in 3 seconds...', 'green');
577 setTimeout(function () {
578 mainwp_forceReload('admin.php?page=mainwp-setup&step=monitoring&message=1');
579 }, 3000);
580 } else {
581 mainwp_forceReload();
582 }
583 } else if (response?.error) {
584 feedback('mainwp-message-zone-client', response.error, 'red');
585 } else {
586 feedback('mainwp-message-zone-client', MainWP.I18n.t('Undefined error. Please try again.'), 'red');
587 }
588 },
589 error: function () {
590 },
591 contentType: false,
592 cache: false,
593 processData: false,
594 enctype: 'multipart/form-data',
595 dataType: 'json'
596 });
597
598 };
599
600 // Trigger new client fields modal
601 jQuery(document).on('click', '#mainwp-clients-new-custom-field-button', function () {
602 let parent = jQuery(this).parents('#mainwp-clients-custom-field-modal');
603 jQuery(parent).find('input[name="field-name"]').val('');
604 jQuery(parent).find('input[name="field-description"]').val('');
605 jQuery(parent).find('input[name="field-id"]').val(0);
606 jQuery(parent).find('#mainwp-clients-save-new-custom-field').addClass('disabled').prop('disabled', true);
607 jQuery('#mainwp-clients-custom-field-modal').modal({
608 closable: false,
609 }).modal('show');
610 });
611
612 // Edit client custom fields.
613 jQuery(document).on('click', '#mainwp-clients-edit-custom-field', function () {
614 let parent = jQuery(this).closest('.mainwp-field');
615 let field_name = parent.find('.field-name').html();
616 let field_desc = parent.find('.field-description').html();
617 let field_id = parent.attr('field-id');
618
619 field_name = field_name.replace(/\[|\]/gi, ""); // NOSONAR.
620
621 jQuery('#mainwp-clients-custom-field-modal input[name="field-name"]').val(field_name);
622 jQuery('#mainwp-clients-custom-field-modal input[name="field-description"]').val(field_desc);
623 jQuery('#mainwp-clients-custom-field-modal input[name="field-id"]').val(field_id);
624
625 let saveButton = jQuery('#mainwp-clients-custom-field-modal').find('#mainwp-clients-save-new-custom-field');
626 if (field_name.trim() !== '' && field_desc.trim() !== '') {
627 saveButton.removeClass('disabled').prop('disabled', false);
628 } else {
629 saveButton.addClass('disabled').prop('disabled', true);
630 }
631
632 jQuery('#mainwp-clients-custom-field-modal').modal({
633 closable: false,
634 }).modal('show');
635 return false;
636 });
637
638 // Save/Update custom fields
639 jQuery(document).on('click', '#mainwp-clients-save-new-custom-field', function () {
640 mainwp_clients_update_custom_field(this);
641 return false;
642 });
643
644 // Validate required fields for custom field modal
645 jQuery(document).on('input', '#mainwp-clients-custom-field-modal input[name="field-name"], #mainwp-clients-custom-field-modal input[name="field-description"]', function () {
646 let parent = jQuery('#mainwp-clients-custom-field-modal');
647 let fieldName = parent.find('input[name="field-name"]').val().trim();
648 let fieldDesc = parent.find('input[name="field-description"]').val().trim();
649 let saveButton = parent.find('#mainwp-clients-save-new-custom-field');
650
651 if (fieldName !== '' && fieldDesc !== '') {
652 saveButton.removeClass('disabled').prop('disabled', false);
653 } else {
654 saveButton.addClass('disabled').prop('disabled', true);
655 }
656 });
657
658 let mainwp_clients_update_custom_field = function (me) {
659 let parent = jQuery(me).parents('#mainwp-clients-custom-field-modal');
660 let errors = [];
661 let client_id = jQuery(me).attr('client-id');
662
663 if (parent.find('input[name="field-name"]').val().trim() == '') {
664 errors.push('Field name is required.');
665 }
666
667 if (parent.find('input[name="field-description"]').val().trim() == '') {
668 errors.push('Field description is required.');
669 }
670
671 if (errors.length > 0) {
672 parent.find('.ui.message').html(errors.join('<br />')).show();
673 return false;
674 }
675
676 let fields = mainwp_secure_data({
677 field_name: parent.find('input[name="field-name"]').val(),
678 field_desc: parent.find('input[name="field-description"]').val(),
679 field_id: parent.find('input[name="field-id"]').val(),
680 client_id: client_id,
681 action: 'mainwp_clients_save_field',
682 });
683
684 parent.find('.ui.message').html('<i class="notched circle loading icon"></i> Saving field. Please wait...').show().removeClass('yellow');
685
686 jQuery.post(ajaxurl, fields, function (response) {
687 if (response) {
688 if (response.success) {
689 mainwp_forceReload();
690 } else if (response.error) {
691 parent.find('.ui.message').html(response.error).show().removeClass('yellow').addClass('red');
692 } else {
693 parent.find('.ui.message').html('Undefined error occurred. Please try again.').show().removeClass('yellow').addClass('red');
694 }
695 } else {
696 parent.find('.ui.message').html('Undefined error occurred. Please try again.').show().removeClass('yellow').addClass('red');
697 }
698 }, 'json');
699 }
700
701 // Delete Custom field
702 jQuery(document).on('click', '#mainwp-clients-delete-general-field', function () {
703 if (confirm(MainWP.I18n.t('Are you sure you want to delete this field?'))) {
704
705 let parent = jQuery(this).closest('.mainwp-field');
706 jQuery.post(ajaxurl, mainwp_secure_data({
707 action: 'mainwp_clients_delete_general_field',
708 field_id: parent.attr('field-id'),
709 }), function (data) {
710 mainwp_set_message_zone('#mainwp-message-zone-client');
711 if (data?.success) {
712 parent.html('<td colspan="3"><i class="green check icon"></i> ' + MainWP.I18n.t('Field has been deleted successfully.') + '</td>').fadeOut(3000);
713 } else {
714 mainwp_set_message_zone('#mainwp-message-zone-client', MainWP.I18n.t('Field can not be deleted.'), 'red');
715 }
716 }, 'json');
717 }
718 return false;
719 });
720
721 // Delete Custom field
722 jQuery(document).on('click', '#mainwp-clients-delete-individual-field', function () {
723 if (confirm(MainWP.I18n.t('Are you sure you want to delete this field?'))) {
724
725 let parent = jQuery(this).closest('.mainwp-field');
726
727 jQuery.post(ajaxurl, mainwp_secure_data({
728 action: 'mainwp_clients_delete_field',
729 field_id: parent.attr('field-id'),
730 client_id: jQuery(this).attr('client-id'),
731 }), function (data) {
732 if (data?.success) {
733 parent.html('<td colspan="3"><i class="green check icon"></i> ' + MainWP.I18n.t('Field has been deleted successfully.') + '</td>').fadeOut(3000);
734 } else {
735 mainwp_set_message_zone('#mainwp-message-zone-client', MainWP.I18n.t('Field can not be deleted.'), 'red');
736 }
737 }, 'json');
738 }
739 return false;
740 });
741
742
743 jQuery(document).on('click', '.mainwp-edit-client-note', function () {
744 let id = jQuery(this).attr('id').substring(13);
745 let note = jQuery('#mainwp-notes-' + id + '-note').html();
746 jQuery('#mainwp-notes-html').html(note == '' ? MainWP.I18n.t('No saved notes. Click the Edit button to edit site notes.') : note);
747 jQuery('#mainwp-notes-note').val(note);
748 jQuery('#mainwp-notes-itemid').val(id);
749 jQuery('#mainwp-which-note').val('client'); // to fix conflict.
750 mainwp_notes_show(true);
751 return false;
752 });
753
754
755 let mainwp_notes_client_save = function () {
756 let normalid = jQuery('#mainwp-notes-itemid').val();
757 let newnote = jQuery('#mainwp-notes-note').val();
758 newnote = newnote.replaceAll(/(?:\r\n|\r|\n)/g, '<br>');
759 let data = mainwp_secure_data({
760 action: 'mainwp_clients_notes_save',
761 clientid: normalid,
762 note: newnote
763 });
764
765 jQuery('#mainwp-notes-status').html('<i class="notched circle loading icon"></i> ' + MainWP.I18n.t('Saving note. Please wait...')).show();
766
767 jQuery.post(ajaxurl, data, function (response) {
768 if (response.error != undefined) {
769 jQuery('#mainwp-notes-status').html(response.error).addClass('red');
770 } else if (response.result == 'SUCCESS') {
771 jQuery('#mainwp-notes-status').html(MainWP.I18n.t('Note saved successfully.')).addClass('green');
772 if (jQuery('#mainwp-notes-' + normalid + '-note').length > 0) {
773 jQuery('#mainwp-notes-' + normalid + '-note').html(response?.esc_note_content??'');
774 jQuery('#mainwp-notes-html').html(response?.esc_note_content??'');
775 }
776 } else {
777 jQuery('#mainwp-notes-status').html(MainWP.I18n.t('Undefined error occurred while saving your note!')).addClass('red');
778 }
779 }, 'json');
780
781 setTimeout(function () {
782 jQuery('#mainwp-notes-status').fadeOut(300);
783 }, 3000);
784
785 jQuery('#mainwp-notes-html').show();
786 jQuery('#mainwp-notes-editor').hide();
787 jQuery('#mainwp-notes-save').hide();
788 jQuery('#mainwp-notes-edit').show();
789
790 };
791
792 // Handle import client for csv.
793 // eslint-disable-next-line complexity
794 const mainwp_manageclient_import_client = function () { // NOSONAR
795 if (import_client_stop_by_user)
796 return;
797
798 jQuery('#mainwp-importing-clients').hide();
799 import_client_current++;
800 if (import_client_current > import_client_total) {
801 jQuery('#mainwp-import-clients-status-message').hide();
802 jQuery('#mainwp_manageclients_btn_import').attr('disabled', 'true'); //Disable
803 if (import_client_count_success < import_client_total) {
804 jQuery('#mainwp_manageclients_btn_save_csv').prop("disabled", false); //Enable
805 }
806
807 if (import_client_count_fails == 0) {
808 jQuery('#mainwp_manageclients_import_logging .log').html('<div style="text-align:center;margin:50px 0;"><h2 class="ui icon header"><i class="green check icon"></i><div class="content">Congratulations!<div class="sub header">' + import_client_count_success + ' clients imported successfully.</div></div></h2></div>');
809 jQuery('#mainwp_manageclients_btn_import').hide();
810 setTimeout(function () {
811 location.reload();
812 }, 2000);
813 } else {
814 jQuery('#mainwp_manageclients_import_logging .log').append('<div class="ui yellow message">Process completed with errors. ' + import_client_count_fails + ' client(s) failed to import. Please review logs to resolve problems and try again.</div>');
815 jQuery('#mainwp_manageclients_btn_import').hide();
816 jQuery('#mainwp-import-clients-modal-try-again').show();
817 jQuery('#mainwp-import-clients-modal-continue').show();
818 }
819
820 jQuery('#mainwp_manageclients_import_logging').scrollTop(jQuery('#mainwp_manageclients_import_logging .log').height());
821 return;
822 }
823
824 let import_client_data = jQuery('#mainwp_manageclients_import_csv_line_' + import_client_current).attr('encoded-data');
825 let import_client_line_orig = jQuery('#mainwp_manageclients_import_csv_line_' + import_client_current).attr('original');
826 let decoded_client_val = JSON.parse(import_client_data);
827
828 let import_city = decoded_client_val['client.city'];
829 let import_address_1 = decoded_client_val['client.contact.address.1'];
830 let import_address_2 = decoded_client_val['client.contact.address.2'];
831 let import_country = decoded_client_val['client.country'];
832 let import_email = decoded_client_val['client.email'];
833 let import_name = decoded_client_val['client.name'];
834 let import_state = decoded_client_val['client.state'];
835 let import_suspended = decoded_client_val['client.suspended'];
836 let import_zip = decoded_client_val['client.zip'];
837 let import_url = decoded_client_val['client.url'];
838
839 if (import_city === undefined)
840 import_city = '';
841 if (import_address_1 === undefined)
842 import_address_1 = '';
843 if (import_address_2 === undefined)
844 import_address_2 = '';
845 if (import_country === undefined)
846 import_country = '';
847 if (import_email === undefined)
848 import_email = '';
849 if (import_name === undefined) {
850 import_name = '';
851 }
852 if (import_state === undefined) {
853 import_state = '';
854 }
855 if (import_suspended === undefined) {
856 import_suspended = '';
857 }
858 if (import_zip === undefined) {
859 import_zip = '';
860 }
861 if (import_url === undefined) {
862 import_url = [];
863 }
864
865 jQuery('#mainwp_manageclients_import_logging .log').append('<strong>[' + import_client_current + '] << ' + import_client_line_orig + '</strong><br/>');
866
867 let errors = [];
868
869 if (import_name == '') {
870 errors.push(MainWP.I18n.t('Please enter the client name.'));
871 }
872
873 if (import_email == '') {
874 errors.push(MainWP.I18n.t('Please enter email of the client.'));
875 }
876
877 if (errors.length > 0) {
878 jQuery('#mainwp_manageclients_import_logging .log').append('[' + import_client_current + '] >> Error - ' + errors.join(" ") + '<br/>');
879 jQuery('#mainwp_manageclients_import_fail_logging').append('<span>' + import_client_line_orig + '</span>');
880 import_client_count_fails++;
881 mainwp_manageclient_import_client();
882 return;
883 }
884
885 // Checking client exist yet
886 let data_check_client = mainwp_secure_data({
887 action: 'mainwp_clients_check_client',
888 email: import_email,
889 });
890 jQuery.post(ajaxurl, data_check_client, function (response) {
891 if (response.success) {
892 // Create new client.
893 let data = mainwp_secure_data({
894 action: 'mainwp_clients_import_client',
895 name: import_name,
896 email: import_email,
897 urls: import_url,
898 city: import_city,
899 address_1: import_address_1,
900 address_2: import_address_2,
901 country: import_country,
902 state: import_state,
903 suspended: import_suspended,
904 zip: import_zip,
905 });
906 jQuery.post(ajaxurl, data, function (res_client) {
907 let add_result = 'Create a new [' + import_name + '] >> ';
908 if (res_client.success) {
909 import_client_count_success++;
910 } else {
911 jQuery('#mainwp_manageclients_import_fail_logging').append('<span>' + import_client_line_orig + '</span>');
912 import_client_count_fails++;
913 }
914 jQuery('#mainwp_manageclients_import_logging .log').append(add_result + res_client.data.message + "<br/>");
915 mainwp_manageclient_import_client();
916 });
917 } else {
918 let check_result = response?.data?.error;
919 errors.push(check_result);
920 }
921
922 if (errors.length > 0) {
923 jQuery('#mainwp_manageclients_import_fail_logging').append('<span>' + import_client_line_orig + '</span>');
924 jQuery('#mainwp_manageclients_import_logging .log').append(errors.join("\n") + '<br/>');
925 import_client_count_fails++;
926 mainwp_manageclient_import_client();
927 }
928 jQuery('#mainwp_manageclients_import_logging').scrollTop(jQuery('#mainwp_manageclients_import_logging .log').height());
929 }, 'json');
930 }