PluginProbe ʕ •ᴥ•ʔ
Advanced Access Manager – Access Governance for WordPress / trunk
Advanced Access Manager – Access Governance for WordPress vtrunk
6.8.4 6.8.5 6.9.0 6.9.1 6.9.10 6.9.11 6.9.12 6.9.13 6.9.14 6.9.15 6.9.16 6.9.17 6.9.18 6.9.19 6.9.2 6.9.20 6.9.21 6.9.22 6.9.23 6.9.24 6.9.25 6.9.26 6.9.27 6.9.28 6.9.29 6.9.3 6.9.30 6.9.31 6.9.32 6.9.33 6.9.34 6.9.35 6.9.36 6.9.37 6.9.38 6.9.39 6.9.4 6.9.41 6.9.42 6.9.43 6.9.44 6.9.45 6.9.46 6.9.47 6.9.48 6.9.49 6.9.5 6.9.51 6.9.6 6.9.7 6.9.8 6.9.9 7.0.0 7.0.0-alpha.6 7.0.0-alpha.7 7.0.0-beta.1 7.0.0-rc1 7.0.0-rc2 7.0.0-rc3 7.0.1 7.0.10 7.0.11 7.0.2 7.0.3 7.0.4 7.0.5 7.0.6 7.0.7 7.0.8 7.0.9 7.1.0 7.1.1 trunk 3.0 4.0 4.0.1 4.1 4.2 4.3 4.4 4.4.1 4.5 4.6 4.6.1 4.6.2 4.7 4.7.1 4.7.2 4.7.5 4.7.6 4.8 4.8.1 4.9 4.9.1 4.9.2 4.9.3 4.9.4 4.9.5 4.9.5.1 4.9.5.2 5.0 5.0.1 5.0.2 5.0.3 5.0.4 5.0.5 5.0.6 5.0.7 5.0.8 5.1 5.1.1 5.10 5.11 5.2 5.2.1 5.2.5 5.2.6 5.2.7 5.3 5.3.1 5.3.2 5.3.3 5.3.4 5.3.5 5.4 5.4.1 5.4.2 5.4.3 5.4.3.1 5.4.3.2 5.5 5.5.1 5.5.2 5.6 5.6.1 5.6.1.1 5.7 5.7.1 5.7.2 5.7.3 5.8 5.8.1 5.8.2 5.8.3 5.9 5.9.1 5.9.1.1 5.9.2 5.9.2.1 5.9.3 5.9.4 5.9.5 5.9.6 5.9.6.1 5.9.6.2 5.9.6.3 5.9.7 5.9.7.1 5.9.7.2 5.9.7.3 5.9.8 5.9.8.1 5.9.9 5.9.9.1 6.0.0 6.0.1 6.0.2 6.0.3 6.0.4 6.0.5 6.1.0 6.1.1 6.2.0 6.2.1 6.2.2 6.3.0 6.3.1 6.3.2 6.3.3 6.4.0 6.4.1 6.4.2 6.4.3 6.5.0 6.5.1 6.5.2 6.5.3 6.5.4 6.6.0 6.6.1 6.6.2 6.6.3 6.6.4 6.7.0 6.7.1 6.7.2 6.7.3 6.7.4 6.7.5 6.7.6 6.7.7 6.7.8 6.7.9 6.8.0 6.8.1 6.8.2 6.8.3
advanced-access-manager / media / js / aam.js
advanced-access-manager / media / js Last commit date
aam.js 5 months ago iframe-content.js 4 years ago iframe-resizer.js 4 years ago vendor.js 1 year ago
aam.js
7584 lines
1 /**
2 * ======================================================================
3 * LICENSE: This file is subject to the terms and conditions defined in *
4 * file 'license.txt', which is part of this source code package. *
5 * ======================================================================
6 */
7
8 /**
9 *
10 */
11 (function ($) {
12
13 /**
14 * Local representation of AAM object
15 */
16 let aam;
17
18 /**
19 * Internal cache
20 */
21 const cache = {
22 roles: null
23 };
24
25 /**
26 * Reset cache value
27 *
28 * @param {string} ns
29 *
30 * @returns {void}
31 */
32 function ResetCache(ns) {
33 cache[ns] = null;
34 }
35
36 /**
37 * Get list of roles
38 *
39 * @param {callback} cb
40 *
41 * @returns {void}
42 */
43 function GetRoles(cb) {
44 if (cache.roles === null) {
45 $.ajax(`${getLocal().rest_base}aam/v2/roles`, {
46 type: 'GET',
47 headers: {
48 'X-WP-Nonce': getLocal().rest_nonce
49 },
50 dataType: 'json',
51 success: function (response) {
52 cache.roles = response; // cache the roles
53
54 cb(response);
55 }
56 });
57 } else {
58 cb(cache.roles);
59 }
60 }
61
62 /**
63 *
64 * @returns {undefined}
65 */
66 function UI() {
67
68 /**
69 * Security score tab
70 */
71 (function($) {
72 if ($('#security_gauge').length) {
73 Gauge(document.getElementById('security_gauge'), {
74 min: 0,
75 max: 100,
76 dialStartAngle: 180,
77 dialEndAngle: 0,
78 value: $('#security_gauge').data('score'),
79 label: function(value) {
80 return value;
81 },
82 color: function(value) {
83 let result = '#3c763d';
84
85 if(value < 75) {
86 result = '#a94442';
87 } else if(value <= 90) {
88 result = '#8a6d3b';
89 }
90
91 return result;
92 }
93 });
94 }
95
96 $('#security_audit_tab').bind('click', function () {
97 $('.aam-area').removeClass('text-danger');
98 getAAM().fetchContent('audit', () => {
99 $('#run_security_scan').trigger('click');
100 });
101 });
102 $('#goto_security_audit_tab').bind('click', function () {
103 $('.aam-area').removeClass('text-danger');
104 getAAM().fetchContent('audit');
105 });
106 })(jQuery);
107
108 /**
109 * Role List Interface
110 *
111 * @param {jQuery} $
112 *
113 * @returns {void}
114 */
115 (function ($) {
116
117 /**
118 *
119 * @param {type} id
120 * @returns {Boolean}
121 */
122 function isCurrent(id) {
123 var subject = getAAM().getSubject();
124
125 return (!getAAM().isUI('principal') && subject.type === 'role' && subject.id === id);
126 }
127
128 /**
129 * Load the list of roles
130 *
131 * @param {type} exclude
132 */
133 function LoadRolesDropdown(exclude, cb = null) {
134 // Display the indicator that the list of roles is loading
135 $('.aam-role-list').html(
136 '<option value="">' + getAAM().__('Loading...') + '</option>'
137 );
138
139 GetRoles((response) => {
140 $('.aam-role-list').html(
141 '<option value="">' + getAAM().__('No role') + '</option>'
142 );
143
144 for (var i in response) {
145 if (exclude !== response[i].slug) {
146 $('.aam-role-list').append(
147 '<option value="' + response[i].slug + '">' + response[i].name + '</option>'
148 );
149 }
150 }
151
152 if ($.aamEditRole) {
153 $('.aam-role-list').val($.aamEditRole[0]);
154 }
155
156 getAAM().triggerHook('post-get-role-list', {
157 list: response
158 });
159
160 if (cb) {
161 cb();
162 }
163
164 //TODO - Rewrite JavaScript to support $.aam
165 $.aamEditRole = null;
166 });
167 }
168
169 /**
170 *
171 * @param {type} container
172 * @returns {undefined}
173 */
174 function resetForm(container) {
175 $('input,select', container).each(function () {
176 if ($(this).attr('type') === 'checkbox') {
177 $(this).prop('checked', false);
178 } else {
179 $(this).val('');
180 }
181 });
182
183 $('.error-container', container).addClass('hidden');
184 }
185
186 /**
187 *
188 * @param {*} role
189 * @returns
190 */
191 function prepareRoleEndpoint(role) {
192 return getLocal().rest_base + 'aam/v2/role/' + encodeURIComponent(role);
193 }
194
195 /**
196 *
197 */
198 function initialize() {
199 if (!$('#role-list').hasClass('dataTable')) {
200 const fields = [
201 'user_count',
202 'permissions'
203 ];
204
205 getAAM().applyFilters('role-list-fields', fields);
206
207 // Prepare the RESTful API endpoint
208 let url = `${getLocal().rest_base}aam/v2/roles`;
209
210 if (url.indexOf('rest_route') === -1) {
211 url += `?fields=${fields.join(',')}`;
212 } else {
213 url += `&fields=${fields.join(',')}`;
214 }
215
216 // Initialize the role list table
217 $('#role-list').DataTable({
218 autoWidth: false,
219 ordering: true,
220 dom: 'ftrip',
221 pagingType: 'simple',
222 processing: true,
223 stateSave: true,
224 serverSide: false,
225 ajax: {
226 url,
227 type: 'GET',
228 headers: {
229 'X-WP-Nonce': getLocal().rest_nonce
230 },
231 dataType: 'json',
232 dataSrc: function (json) {
233 // Transform the received data into DT format
234 const data = [];
235
236 $.each(json, (_, role) => {
237 const actions = [];
238
239 if (role.permissions.includes('allow_manage')) {
240 actions.push('manage');
241 }
242
243 if (role.permissions.includes('allow_edit')) {
244 actions.push('edit');
245 } else {
246 actions.push('no-edit');
247 }
248
249 if (role.permissions.includes('allow_delete')) {
250 actions.push('delete');
251 } else {
252 actions.push('no-delete');
253 }
254
255 if (role.permissions.includes('allow_clone')) {
256 actions.push('clone');
257 } else {
258 actions.push('no-clone');
259 }
260
261 data.push([
262 role.slug,
263 role.user_count,
264 role.name,
265 actions.join(','),
266 0,
267 role
268 ])
269 });
270
271 return data;
272 },
273 },
274 columnDefs: [
275 { visible: false, targets: [0, 1, 4] },
276 { orderable: false, targets: [0, 1, 3, 4] }
277 ],
278 language: {
279 search: '_INPUT_',
280 searchPlaceholder: getAAM().__('Search role'),
281 info: getAAM().__('_TOTAL_ role(s)'),
282 infoFiltered: ''
283 },
284 initComplete: function () {
285 if (getAAM().isUI('main') && getLocal().caps.create_roles) {
286 var create = $('<a/>', {
287 'href': '#',
288 'class': 'btn btn-primary'
289 })
290 .html('<i class="icon-plus"></i>')
291 .bind('click', function () {
292 resetForm('#add-role-modal .modal-body');
293 $('#add-role-modal').modal('show');
294 })
295 .attr({
296 'data-toggle': "tooltip",
297 'title': getAAM().__('Create New Role')
298 });
299
300 $('.dataTables_filter', '#role-list_wrapper').append(create);
301 }
302 },
303 createdRow: function (row, data) {
304 if (isCurrent(data[0])) {
305 $('td:eq(0)', row).html(
306 '<span class="aam-highlight">' + data[2] + '</span>'
307 );
308 } else {
309 $('td:eq(0)', row).html('<span>' + data[2] + '</span>');
310 }
311
312 $(row).attr('data-id', data[0]);
313
314 //add subtitle
315 $('td:eq(0)', row).append(
316 $('<i/>', { 'class': 'aam-row-subtitle' }).html(
317 getAAM().applyFilters(
318 'role-subtitle',
319 getAAM().__('Users') + ': <b>' + parseInt(data[1]) + '</b>; Slug: <b>' + data[0] + '</b>',
320 data[5]
321 )
322 )
323 );
324
325 var actions = data[3].split(',');
326
327 var container = $('<div/>', { 'class': 'aam-row-actions' });
328
329 $.each(actions, function (i, action) {
330 switch (action) {
331 case 'manage':
332 $(container).append($('<i/>', {
333 'class': 'aam-row-action icon-cog ' + (isCurrent(data[0]) ? 'text-muted' : 'text-info')
334 }).bind('click', function () {
335 var title = $('td:eq(0) span', row).html();
336
337 getAAM().setSubject('role', data[0], title, data[4]);
338
339 $('td:eq(0) span', row).replaceWith(
340 '<span class="aam-highlight">' + title + '</span>'
341 );
342
343 $('i.icon-cog', container).attr(
344 'class', 'aam-row-action icon-spin4 animate-spin'
345 );
346
347 if (getAAM().isUI('main')) {
348 $('i.icon-cog', container).attr(
349 'class', 'aam-row-action icon-spin4 animate-spin'
350 );
351 getAAM().fetchContent('main');
352 $('i.icon-spin4', container).attr(
353 'class', 'aam-row-action icon-cog text-muted'
354 );
355 } else if (getAAM().isUI('post')) {
356 getAAM().triggerHook('load-access-form', [
357 {
358 resource_type: $('#content_resource_type').val(),
359 resource_id: $('#content_resource_id').val()
360 },
361 function() {
362 $('i.icon-spin4', container).attr(
363 'class', 'aam-row-action icon-cog text-muted'
364 );
365 }
366 ]);
367 }
368 }).attr({
369 'data-toggle': "tooltip",
370 'title': getAAM().__('Manage role')
371 }));
372 break;
373
374 case 'edit':
375 if (getAAM().isUI('main')) {
376 $(container).append($('<i/>', {
377 'class': 'aam-row-action icon-pencil text-warning'
378 }).bind('click', function () {
379 resetForm('#edit-role-modal .modal-body');
380
381 $('#edit-role-btn').data('role', data[0]);
382 $('#edit-role-name').val(data[2]);
383 $('#edit-role-slug').val(data[0]);
384 $('#edit-role-modal').modal('show');
385
386 if (data[1] > 0) {
387 $('#edit-role-slug').prop('disabled', true);
388 } else {
389 $('#edit-role-slug').prop('disabled', false);
390 }
391
392 LoadRolesDropdown(data[0], () => {
393 getAAM().triggerHook(
394 'edit-role-modal',
395 data[5]
396 );
397 });
398
399 //TODO - Rewrite JavaScript to support $.aam
400 $.aamEditRole = data;
401 }).attr({
402 'data-toggle': "tooltip",
403 'title': getAAM().__('Edit role')
404 }));
405 }
406 break;
407
408 case 'no-edit':
409 if (getAAM().isUI('main')) {
410 $(container).append($('<i/>', {
411 'class': 'aam-row-action icon-pencil text-muted'
412 }));
413 }
414 break;
415
416 case 'clone':
417 if (getAAM().isUI('main')) {
418 $(container).append($('<i/>', {
419 'class': 'aam-row-action icon-clone text-success'
420 }).bind('click', function () {
421 //TODO - Rewrite JavaScript to support $.aam
422 $.aamEditRole = data;
423 $('#clone-role').prop('checked', true);
424 $('#add-role-modal').modal('show');
425 }).attr({
426 'data-toggle': "tooltip",
427 'title': getAAM().__('Clone role')
428 }));
429 }
430 break;
431
432 case 'no-clone':
433 if (getAAM().isUI('main')) {
434 $(container).append($('<i/>', {
435 'class': 'aam-row-action icon-clone text-muted'
436 }));
437 }
438 break;
439
440 case 'delete':
441 if (getAAM().isUI('main')) {
442 $(container).append($('<i/>', {
443 'class': 'aam-row-action icon-trash-empty text-danger'
444 }).bind('click', { role: data }, function (event) {
445 $('#delete-role-btn').data('role', data[0]);
446 var message = $('#delete-role-modal .aam-confirm-message').data('message');
447 $('#delete-role-modal .aam-confirm-message').html(
448 message.replace(
449 '%s', '<strong>' + event.data.role[2] + '</strong>'
450 )
451 );
452
453 $('#delete-role-modal').modal('show');
454 }).attr({
455 'data-toggle': "tooltip",
456 'title': getAAM().__('Delete role')
457 }));
458 }
459 break;
460
461 case 'no-delete':
462 if (getAAM().isUI('main')) {
463 $(container).append($('<i/>', {
464 'class': 'aam-row-action icon-trash-empty text-muted'
465 }));
466 }
467 break;
468
469 default:
470 if (getAAM().isUI('main')) {
471 getAAM().triggerHook('role-action', {
472 container: container,
473 action: action,
474 data: data
475 });
476 }
477 break;
478 }
479 });
480 $('td:eq(1)', row).html(container);
481
482 getAAM().triggerHook('decorate-role-row', {
483 row: row,
484 data: data
485 });
486 }
487 });
488
489 $('#role-list').on('draw.dt', function () {
490 $('tr', '#role-list tbody').each(function () {
491 if (!isCurrent($(this).data('id'))) {
492 $('td:eq(0) strong', this).replaceWith(
493 '<span>' + $('td:eq(0) strong', this).text() + '</span>'
494 );
495 $('.icon-cog.text-muted', this).attr('disabled', false);
496 $('.icon-cog.text-muted', this).toggleClass('text-muted text-info');
497 }
498 });
499 });
500
501 $('#add-role-modal').on('show.bs.modal', function (e) {
502 LoadRolesDropdown();
503
504 //clear add role form first
505 $('input', '#add-role-modal').val('');
506 $('input[name="name"]', '#add-role-modal').focus();
507 });
508
509 $('#edit-role-modal').on('show.bs.modal', function () {
510 $('input[name="name"]', '#edit-role-modal').focus();
511 });
512
513 //add role button
514 $('#add-role-btn').bind('click', function () {
515 var _this = this;
516
517 ResetCache('roles');
518
519 $('input[name="name"]', '#add-role-modal').parent().removeClass(
520 'has-error'
521 );
522
523 var data = {};
524
525 $('input,select', '#add-role-modal .modal-body').each(function () {
526 if ($(this).attr('name')) {
527 if ($(this).attr('type') === 'checkbox') {
528 data[$(this).attr('name')] = $(this).is(':checked') ? true : false;
529 } else {
530 const val = $.trim($(this).val());
531
532 if (val) {
533 data[$(this).attr('name')] = val;
534 }
535 }
536 }
537 });
538
539
540 if (data.name) {
541 $.ajax(`${getLocal().rest_base}aam/v2/roles`, {
542 type: 'POST',
543 headers: {
544 'X-WP-Nonce': getLocal().rest_nonce
545 },
546 dataType: 'json',
547 data: data,
548 beforeSend: function () {
549 $('.error-container').addClass('hidden');
550 $(_this).text(getAAM().__('Saving...')).attr('disabled', true);
551 },
552 success: function (response) {
553 getAAM().setSubject(
554 'role',
555 response.slug,
556 response.name
557 );
558
559 getAAM().fetchContent('main');
560 $('#role-list').DataTable().ajax.reload();
561
562 $('#add-role-modal').modal('hide');
563 },
564 error: function (err) {
565 $('.error-container').removeClass('hidden');
566
567 // Error summary
568 $('#role-error-summary').text(
569 'Failed to create new role for the following reason(s)'
570 );
571 $('#role-error-list').empty();
572
573 $.each(err.responseJSON.errors, (_, e) => {
574 $('#role-error-list').append(`<li>${e[0]}</li>`);
575 });
576 },
577 complete: function () {
578 $(_this).text(getAAM().__('Add role')).attr('disabled', false);
579 }
580 });
581 } else {
582 $('input[name="name"]', '#add-role-modal').focus().parent().addClass(
583 'has-error'
584 );
585 }
586 });
587
588 //edit role button
589 $('#edit-role-btn').bind('click', function () {
590 var _this = this;
591
592 ResetCache('roles');
593
594 $('#edit-role-name').parent().removeClass('has-error');
595 $('#edit-role-slug').parent().removeClass('has-error');
596
597 const data = {};
598
599 $('input,select', '#edit-role-modal .modal-body').each(function () {
600 if ($(this).attr('name')) {
601 if ($(this).attr('type') === 'checkbox') {
602 data[$(this).attr('name')] = $(this).is(':checked') ? 1 : 0;
603 } else if (!$(this).prop('disabled')) {
604 const v = $.trim($(this).val());
605
606 data[$(this).attr('name')] = v;
607 }
608 }
609 });
610
611 if (data.name) {
612 $.ajax(prepareRoleEndpoint($(_this).data('role')), {
613 type: 'POST',
614 headers: {
615 'X-WP-Nonce': getLocal().rest_nonce,
616 'X-HTTP-Method-Override': 'PATCH'
617 },
618 dataType: 'json',
619 data: data,
620 beforeSend: function () {
621 $('.error-container').addClass('hidden');
622 $(_this).text(getAAM().__('Saving...')).attr('disabled', true);
623 },
624 success: function (response) {
625 // If role's slug changed, update the current subject
626 if (data.new_slug && $(_this).data('role') !== data.new_slug) {
627 getAAM().setSubject(
628 'role',
629 response.slug,
630 response.name
631 );
632 }
633
634 location.reload();
635 },
636 error: function (err) {
637 $('.error-container').removeClass('hidden');
638
639 // Error summary
640 $('#edit-role-error-summary').text(
641 'Failed to update role for the following reason(s)'
642 );
643 $('#edit-role-error-list').empty();
644
645 $.each(err.responseJSON.errors, (_, e) => {
646 $('#edit-role-error-list').append(`<li>${e[0]}</li>`);
647 });
648 },
649 complete: function () {
650 $(_this).text(getAAM().__('Update')).attr('disabled', false);
651 }
652 });
653 } else {
654 $('#edit-role-name').focus().parent().addClass('has-error');
655 }
656 });
657
658 //edit role button
659 $('#delete-role-btn').bind('click', function () {
660 var _this = this;
661
662 ResetCache('roles');
663
664 $.ajax(prepareRoleEndpoint($(_this).data('role')), {
665 type: 'POST',
666 headers: {
667 'X-WP-Nonce': getLocal().rest_nonce,
668 'X-HTTP-Method-Override': 'DELETE'
669 },
670 beforeSend: function () {
671 $(_this).text(getAAM().__('Deleting...')).attr('disabled', true);
672 },
673 success: function () {
674 var subject = getAAM().getSubject();
675
676 if (subject.type === 'role'
677 && subject.id === $(_this).data('role')
678 ) {
679 location.reload();
680 } else {
681 $('#role-list').DataTable().ajax.reload();
682 }
683 },
684 error: function (response) {
685 getAAM().notification(
686 'danger',
687 getAAM().__('I\'m having trouble deleting the role.'),
688 {
689 request: `aam/v2/role/${$(_this).data('role')}`,
690 response: response.responseJSON
691 }
692 );
693 },
694 complete: function () {
695 $('#delete-role-modal').modal('hide');
696
697 $(_this).text(
698 getAAM().__('Delete role')
699 ).attr('disabled', false);
700 }
701 });
702 });
703 }
704 }
705
706 //add setSubject hook
707 getAAM().addHook('access-level-changed', function () {
708 //clear highlight
709 $('tbody tr', '#role-list').each(function () {
710 if ($('strong', $(this)).length) {
711 var highlight = $('strong', $(this));
712 $('.icon-cog', $(this)).toggleClass('text-muted text-info');
713 $('.icon-cog', $(this)).prop('disabled', false);
714 highlight.replaceWith($('<span/>').text(highlight.text()));
715 }
716 });
717 });
718
719 //in case interface needed to be reloaded
720 getAAM().addHook('refresh', function () {
721 $('#role-list').DataTable().ajax.url(getLocal().ajaxurl).load();
722 getAAM().fetchContent('main');
723 });
724
725 getAAM().addHook('init', initialize);
726
727 })(jQuery);
728
729 /**
730 * User List Interface
731 *
732 * @param {jQuery} $
733 *
734 * @returns {void}
735 */
736 (function ($) {
737
738 /**
739 *
740 * @param {type} id
741 * @returns {Boolean}
742 */
743 function isCurrent(id) {
744 var subject = getAAM().getSubject();
745
746 return (!getAAM().isUI('principal') && subject.type === 'user' && parseInt(subject.id) === id);
747 }
748
749 /**
750 * Update user status
751 *
752 * @param {number} id
753 * @param {object} btn
754 *
755 * @returns {void}
756 */
757 function updateUserStatus(id, btn) {
758 const status = ($(btn).hasClass('icon-lock') ? 'active' : 'inactive');
759
760 $.ajax({
761 url: `${getLocal().rest_base}aam/v2/user/${id}?fields=status`,
762 type: 'POST',
763 headers: {
764 'X-WP-Nonce': getLocal().rest_nonce
765 },
766 data: {
767 status
768 },
769 beforeSend: function () {
770 $(btn).attr('class', 'aam-row-action icon-spin4 animate-spin');
771 },
772 success: function (response) {
773 if (response.status === 'inactive') {
774 $(btn).attr({
775 'class': 'aam-row-action icon-lock text-danger',
776 'title': getAAM().__('Unlock user'),
777 'data-original-title': getAAM().__('Unlock user')
778 });
779 } else {
780 $(btn).attr({
781 'class': 'aam-row-action icon-lock-open text-success',
782 'title': getAAM().__('Lock user'),
783 'data-original-title': getAAM().__('Lock user')
784 });
785 }
786 },
787 error: function (response) {
788 getAAM().notification('danger', response, {
789 request: `aam/v2/user/${id}?fields=status`,
790 payload: { status },
791 response
792 });
793 }
794 });
795 }
796
797 /**
798 *
799 * @param {*} expires
800 * @param {*} action
801 */
802 function generateJWT() {
803 if ($('#login-url-preview').length === 1) {
804 const type = $('#action-after-expiration').val();
805
806 const payload = {
807 user_id: $('#reset-user-expiration-btn').attr('data-user-id'),
808 expires_at: $('#user-expires').val(),
809 };
810
811 if (type) {
812 payload.additional_claims = {
813 trigger: {
814 type
815 }
816 }
817
818 if (type === 'change_role') {
819 payload.additional_claims.trigger.to_role = $('#expiration-change-role').val();
820 }
821 }
822
823 $.ajax(`${getLocal().rest_base}aam/v2/jwts`, {
824 type: 'POST',
825 dataType: 'json',
826 data: payload,
827 headers: {
828 'X-WP-Nonce': getLocal().rest_nonce
829 },
830 beforeSend: function () {
831 $('#login-url-preview').val(getAAM().__('Generating URL...'));
832 },
833 success: function (response) {
834 $('#login-url-preview').val(
835 $('#login-url-preview').data('url').replace('%s', response.token)
836 );
837 },
838 error: function (response) {
839 getAAM().notification('danger', response, {
840 request: 'aam/v2/jwts',
841 payload,
842 response
843 });
844 }
845 });
846 }
847 }
848
849 // Initialize the user list table
850 $('#user-list').DataTable({
851 autoWidth: false,
852 ordering: false,
853 dom: 'ftrip',
854 stateSave: true,
855 pagingType: 'simple',
856 serverSide: true,
857 processing: true,
858 ajax: function(filters, cb) {
859 const fields = [
860 'roles',
861 'display_name',
862 'permissions',
863 'user_level',
864 'expiration'
865 ];
866
867 if(getAAM().isUI('principal')) {
868 fields.push('policies');
869 }
870
871 $.ajax({
872 url: `${getLocal().rest_base}aam/v2/users`,
873 type: 'GET',
874 headers: {
875 'X-WP-Nonce': getLocal().rest_nonce
876 },
877 data: {
878 search: filters.search.value,
879 per_page: filters.length,
880 offset: filters.start,
881 fields: fields.join(','),
882 role: $('#user-list-filter').val()
883 },
884 success: function (response) {
885 const result = {
886 data: [],
887 recordsTotal: 0,
888 recordsFiltered: 0
889 };
890
891 // Transform the received data into DT format
892 const policyId = parseInt($('#aam-policy-id').val(), 10);
893
894 $.each(response.list, (_, user) => {
895 const actions = [];
896
897 if (getLocal().ui === 'principal' && policyId) {
898 if (user.policies && user.policies.includes(policyId)) {
899 actions.push('detach');
900 } else {
901 actions.push('attach');
902 }
903 } else {
904 if (user.permissions.includes('allow_manage')) {
905 actions.push('manage');
906 }
907
908 if (user.permissions.includes('allow_edit')) {
909 actions.push('edit');
910 }
911
912 if (user.permissions.includes('allow_unlock')) {
913 actions.push('unlock');
914 } else if (user.permissions.includes('allow_lock')) {
915 actions.push('lock');
916 }
917 }
918
919 result.data.push([
920 user.id,
921 user.roles.join(', '),
922 user.display_name,
923 actions.join(','),
924 user.user_level,
925 user.expiration || null
926 ]);
927 });
928
929 result.recordsTotal = response.summary.total_count;
930 result.recordsFiltered = response.summary.filtered_count;
931
932 cb(result);
933 }
934 });
935 },
936 columnDefs: [
937 { visible: false, targets: [0, 1, 4, 5] }
938 ],
939 language: {
940 search: '_INPUT_',
941 searchPlaceholder: getAAM().__('Search user'),
942 info: getAAM().__('_TOTAL_ user(s)'),
943 infoFiltered: ''
944 },
945 initComplete: function () {
946 if (getAAM().isUI('main') && getLocal().caps.create_users) {
947 var create = $('<a/>', {
948 'href': '#',
949 'class': 'btn btn-primary'
950 })
951 .html('<i class="icon-plus"></i> ')
952 .bind('click', function () {
953 window.open(getLocal().url.addUser, '_blank');
954 })
955 .attr({
956 'data-toggle': "tooltip",
957 'title': getAAM().__('Create New User')
958 });
959
960 $('.dataTables_filter', '#user-list_wrapper').append(create);
961
962 var filter = $('<select>').attr({
963 'class': 'user-filter form-control',
964 'id': 'user-list-filter'
965 })
966 .html('<option value="">' + getAAM().__('Loading...') + '</option>')
967 .bind('change', function () {
968 $('#user-list').DataTable().ajax.reload();
969 });
970
971 $('.dataTables_filter', '#user-list_wrapper').append(filter);
972
973 GetRoles((response) => {
974 $('#user-list-filter').html(
975 '<option value="">' + getAAM().__('Filter by role') + '</option>'
976 );
977
978 for (var i in response) {
979 $('#user-list-filter').append(
980 '<option value="' + response[i].slug + '">' + response[i].name + '</option>'
981 );
982 }
983 });
984 }
985 },
986 createdRow: function (row, data) {
987 if (isCurrent(data[0])) {
988 $('td:eq(0)', row).html('<strong class="aam-highlight">' + data[2] + '</strong>');
989 } else {
990 $('td:eq(0)', row).html('<span>' + data[2] + '</span>');
991 }
992
993 //add subtitle
994 var expire = (data[5] ? '; <i class="icon-clock text-danger"></i>' : '');
995 var role = (data[1] ? `${getAAM().__('Role')}: <b>${data[1]}</b>; ` : '');
996 $('td:eq(0)', row).append(
997 $('<i/>', { 'class': 'aam-row-subtitle' }).html(
998 `${role}${getAAM().__('ID')}: <b>${data[0]}</b> ${expire}`
999 )
1000 );
1001
1002 var actions = data[3].split(',');
1003 var container = $('<div/>', { 'class': 'aam-row-actions' });
1004
1005 if ($.trim(data[3])) {
1006 $.each(actions, function (i, action) {
1007 switch (action) {
1008 case 'manage':
1009 $(container).append($('<i/>', {
1010 'class': 'aam-row-action icon-cog ' + (isCurrent(data[0]) ? 'text-muted' : 'text-primary')
1011 }).bind('click', function () {
1012 if (!$(this).prop('disabled')) {
1013 $(this).prop('disabled', true);
1014 getAAM().setSubject('user', data[0], data[2], data[4]);
1015
1016 $('td:eq(0) span', row).replaceWith(
1017 '<strong class="aam-highlight">' + data[2] + '</strong>'
1018 );
1019
1020 $('i.icon-cog', container).attr(
1021 'class', 'aam-row-action icon-spin4 animate-spin'
1022 );
1023
1024 if (getAAM().isUI('main')) {
1025 getAAM().fetchContent('main');
1026
1027 $('i.icon-spin4', container).attr(
1028 'class', 'aam-row-action icon-cog text-muted'
1029 );
1030 } else if (getAAM().isUI('post')) {
1031 getAAM().triggerHook('load-access-form', [
1032 {
1033 resource_type: $('#content_resource_type').val(),
1034 resource_id: $('#content_resource_id').val()
1035 },
1036 function() {
1037 $('i.icon-spin4', container).attr(
1038 'class', 'aam-row-action icon-cog text-muted'
1039 );
1040 }
1041 ]);
1042 }
1043 }
1044 }).attr({
1045 'data-toggle': "tooltip",
1046 'title': getAAM().__('Manage user')
1047 })).prop('disabled', (isCurrent(data[0]) ? true : false));
1048 break;
1049
1050 case 'edit':
1051 if (getAAM().isUI('main')) {
1052 $(container).append($('<i/>', {
1053 'class': 'aam-row-action icon-pencil text-warning'
1054 }).bind('click', function () {
1055 // Update user's edit profile
1056 $('#edit-user-link').attr(
1057 'href',
1058 getLocal().url.editUser + '?user_id=' + data[0]
1059 );
1060
1061 $('#edit-user-expiration-btn').attr('data-user-id', data[0]);
1062 $('#reset-user-expiration-btn').attr('data-user-id', data[0]);
1063
1064 if (data[5]) {
1065 $('#reset-user-expiration-btn').removeClass('hidden');
1066 $('#user-expires').val(data[5].expires_at);
1067 $('#action-after-expiration').val(data[5].trigger.type);
1068
1069 if (data[5].trigger.type === 'change_role') {
1070 $('#expiration-change-role-holder').removeClass('hidden');
1071 getAAM().loadRoleList(data[5].trigger.to_role);
1072 } else {
1073 getAAM().loadRoleList();
1074 $('#expiration-change-role-holder').addClass('hidden');
1075 }
1076 } else {
1077 $('#reset-user-expiration-btn, #expiration-change-role-holder').addClass('hidden');
1078 $('#user-expires, #action-after-expiration, #login-url-preview, #login-url').val('');
1079 getAAM().loadRoleList();
1080 }
1081
1082 $('#edit-user-modal').modal('show');
1083
1084 }).attr({
1085 'data-toggle': "tooltip",
1086 'title': getAAM().__('Edit user')
1087 }));
1088 }
1089 break;
1090
1091 case 'lock':
1092 if (getAAM().isUI('main')) {
1093 $(container).append($('<i/>', {
1094 'class': 'aam-row-action icon-lock-open text-success'
1095 }).bind('click', function () {
1096 updateUserStatus(data[0], $(this));
1097 }).attr({
1098 'data-toggle': "tooltip",
1099 'title': getAAM().__('Lock user')
1100 }));
1101 }
1102 break;
1103
1104 case 'unlock':
1105 if (getAAM().isUI('main')) {
1106 $(container).append($('<i/>', {
1107 'class': 'aam-row-action icon-lock text-danger'
1108 }).bind('click', function () {
1109 updateUserStatus(data[0], $(this));
1110 }).attr({
1111 'data-toggle': "tooltip",
1112 'title': getAAM().__('Unlock user')
1113 }));
1114 }
1115 break;
1116
1117 default:
1118 break;
1119 }
1120 });
1121 } else {
1122 $(container).append($('<i/>', {
1123 'class': 'aam-row-action text-muted'
1124 }).text('---'));
1125 }
1126
1127 $('td:eq(1)', row).html(container);
1128 }
1129 });
1130
1131 $('#action-after-expiration').bind('change', function () {
1132 if ($(this).val() === 'change_role') {
1133 $('#expiration-change-role-holder').removeClass('hidden');
1134 } else {
1135 $('#expiration-change-role-holder').addClass('hidden');
1136 }
1137 });
1138
1139 $('#request-login-url').bind('click', function () {
1140 generateJWT();
1141 });
1142
1143 $('#user-expiration-datapicker').datetimepicker({
1144 icons: {
1145 time: "icon-clock",
1146 date: "icon-calendar",
1147 up: "icon-angle-up",
1148 down: "icon-angle-down",
1149 previous: "icon-angle-left",
1150 next: "icon-angle-right"
1151 },
1152 inline: true,
1153 minDate: new Date(),
1154 sideBySide: true
1155 });
1156
1157 $('#edit-user-modal').on('show.bs.modal', function () {
1158 try {
1159 if ($.trim($('#user-expires').val())) {
1160 $('#user-expiration-datapicker').data('DateTimePicker').defaultDate(
1161 new Date($('#user-expires').val())
1162 );
1163 } else {
1164 var tomorrow = new Date();
1165 tomorrow.setDate(tomorrow.getDate() + 1);
1166 $('#user-expiration-datapicker').data('DateTimePicker').defaultDate(
1167 tomorrow
1168 );
1169 }
1170 } catch (e) {
1171 // do nothing. Prevent from any kind of corrupted data
1172 }
1173 });
1174
1175 $('#user-expiration-datapicker').on('dp.change', function (res) {
1176 $('#user-expires').val(res.date.format());
1177 });
1178
1179 //edit role button
1180 $('#edit-user-expiration-btn').bind('click', function () {
1181 var _this = this;
1182
1183 // Get currently editing user ID
1184 const id = $(_this).attr('data-user-id');
1185
1186 // Preparing the payload
1187 const payload = {
1188 expires_at: $('#user-expires').val()
1189 };
1190
1191 // Gathering expiration attributes
1192 const expiration_trigger = $('#action-after-expiration').val() || 'logout';
1193
1194 if (expiration_trigger) {
1195 payload.trigger = {
1196 type: expiration_trigger
1197 };
1198
1199 if (expiration_trigger === 'change_role') {
1200 payload.trigger.to_role = $('#expiration-change-role').val();
1201 }
1202 }
1203
1204 $.ajax({
1205 url: `${getLocal().rest_base}aam/v2/user/${id}`,
1206 type: 'POST',
1207 headers: {
1208 'X-WP-Nonce': getLocal().rest_nonce
1209 },
1210 data: {
1211 expiration: payload
1212 },
1213 beforeSend: function () {
1214 $(_this).text(getAAM().__('Saving...')).attr('disabled', true);
1215 },
1216 success: function () {
1217 $('#user-list').DataTable().ajax.reload();
1218 },
1219 error: function (response) {
1220 getAAM().notification('danger', response, {
1221 request: `aam/v2/user/${id}`,
1222 payload: { expiration: payload },
1223 response
1224 });
1225 },
1226 complete: function () {
1227 $('#edit-user-modal').modal('hide');
1228 $(_this).text(getAAM().__('Save')).attr('disabled', false);
1229 }
1230 });
1231 });
1232
1233 // Reset user
1234 $('#reset-user-expiration-btn').bind('click', function () {
1235 var _this = this;
1236
1237 const id = $(_this).attr('data-user-id');
1238
1239 $.ajax({
1240 url: `${getLocal().rest_base}aam/v2/user/${id}`,
1241 type: 'POST',
1242 headers: {
1243 'X-WP-Nonce': getLocal().rest_nonce,
1244 'X-HTTP-Method-Override': 'DELETE'
1245 },
1246 beforeSend: function () {
1247 $(_this).text(getAAM().__('Resetting...')).attr('disabled', true);
1248 },
1249 success: function () {
1250 $('#user-list').DataTable().ajax.reload();
1251 },
1252 error: function (response) {
1253 getAAM().notification('danger', response, {
1254 request: `aam/v2/user/${id}`,
1255 response
1256 });
1257 },
1258 complete: function () {
1259 $('#edit-user-modal').modal('hide');
1260 $(_this).text(getAAM().__('Reset')).attr('disabled', false);
1261 }
1262 });
1263 });
1264
1265 //add setSubject hook
1266 getAAM().addHook('access-level-changed', function () {
1267 //clear highlight
1268 $('tbody tr', '#user-list').each(function () {
1269 if ($('strong', $(this)).length) {
1270 var highlight = $('strong', $(this));
1271 $('.icon-cog', $(this)).toggleClass('text-muted text-info');
1272 $('.icon-cog', $(this)).prop('disabled', false);
1273 highlight.replaceWith('<span>' + highlight.text() + '</span>');
1274 }
1275 });
1276 });
1277
1278 //in case interface needed to be reloaded
1279 getAAM().addHook('refresh', function () {
1280 $('#user-list').DataTable().ajax.url(getLocal().ajaxurl).load();
1281 });
1282
1283 })(jQuery);
1284
1285 /**
1286 * Visitor Interface
1287 *
1288 * @param {jQuery} $
1289 *
1290 * @returns {void}
1291 */
1292 (function ($) {
1293
1294 $('document').ready(function () {
1295 $('#manage-visitor').bind('click', function () {
1296 var _this = $(this);
1297
1298 getAAM().setSubject('visitor', null, getAAM().__('Anonymous'), 0);
1299 $('i.icon-cog', _this).attr('class', 'icon-spin4 animate-spin');
1300
1301 if (getAAM().isUI('main')) {
1302 getAAM().fetchContent('main');
1303 $('i.icon-spin4', _this).attr('class', 'icon-cog');
1304 } else if (getAAM().isUI('post')) {
1305 getAAM().triggerHook('load-access-form', [
1306 {
1307 resource_type: $('#content_resource_type').val(),
1308 resource_id: $('#content_resource_id').val()
1309 },
1310 function() {
1311 $('i.icon-spin4', _this).attr('class', 'icon-cog');
1312 }
1313 ]);
1314 }
1315 });
1316 });
1317
1318 })(jQuery);
1319
1320 /**
1321 * Default Interface
1322 *
1323 * @param {jQuery} $
1324 *
1325 * @returns {void}
1326 */
1327 (function ($) {
1328
1329 $('document').ready(function () {
1330 $('#manage-default').bind('click', function () {
1331 var _this = $(this);
1332
1333 getAAM().setSubject(
1334 'default', null, getAAM().__('All Users, Roles and Visitor'), 0
1335 );
1336
1337 $('i.icon-cog', _this).attr('class', 'icon-spin4 animate-spin');
1338 if (getAAM().isUI('main')) {
1339 getAAM().fetchContent('main');
1340 $('i.icon-spin4', _this).attr('class', 'icon-cog');
1341 } else if (getAAM().isUI('post')) {
1342 getAAM().triggerHook('load-access-form', [
1343 {
1344 resource_type: $('#content_resource_type').val(),
1345 resource_id: $('#content_resource_id').val()
1346 },
1347 function() {
1348 $('i.icon-spin4', _this).attr('class', 'icon-cog');
1349 }
1350 ]);
1351 }
1352 });
1353 });
1354
1355 })(jQuery);
1356
1357 /**
1358 * Policy Interface
1359 *
1360 * @param {jQuery} $
1361 *
1362 * @returns {void}
1363 */
1364 (function ($) {
1365
1366 /**
1367 *
1368 * @param {type} id
1369 * @param {type} effect
1370 * @param {type} btn
1371 *
1372 * @returns {undefined}
1373 */
1374 function TogglePolicy(id, effect, btn) {
1375 getAAM().queueRequest(function () {
1376 const payload = {
1377 effect
1378 };
1379
1380 // Show indicator
1381 $(btn).attr('class', 'aam-row-action icon-spin4 animate-spin');
1382
1383 const endpoint = getAAM().prepareApiEndpoint(
1384 '/policy/' + id
1385 );
1386
1387 $.ajax(endpoint, {
1388 type: 'POST',
1389 headers: {
1390 'X-WP-Nonce': getLocal().rest_nonce,
1391 'X-HTTP-Method-Override': 'PUT'
1392 },
1393 dataType: 'json',
1394 data: payload,
1395 success: function () {
1396 $('#aam-policy-overwrite').show();
1397
1398 if (effect === 'attach') {
1399 $(btn).attr(
1400 'class',
1401 'aam-row-action icon-check'
1402 );
1403 } else {
1404 $(btn).attr(
1405 'class',
1406 'aam-row-action icon-check-empty'
1407 );
1408 }
1409 },
1410 error: function (response) {
1411 getAAM().notification('danger', response, {
1412 request: '/policy/' + id,
1413 payload,
1414 response
1415 });
1416 }
1417 });
1418 });
1419 }
1420
1421 /**
1422 *
1423 * @param {*} al_type
1424 * @param {*} al_id
1425 * @param {*} policy_id
1426 * @param {*} effect
1427 * @param {*} cb
1428 */
1429 function ToggleAccessLevelPolicy(al_type, al_id, policy_id, effect, cb) {
1430 getAAM().queueRequest(function () {
1431 const payload = {
1432 effect
1433 };
1434
1435 const endpoint = getAAM().prepareApiEndpoint(
1436 '/policy/' + policy_id, true, {
1437 type: al_type,
1438 id: al_id
1439 }
1440 );
1441
1442 $.ajax(endpoint, {
1443 type: 'POST',
1444 headers: {
1445 'X-WP-Nonce': getLocal().rest_nonce,
1446 'X-HTTP-Method-Override': 'PUT'
1447 },
1448 dataType: 'json',
1449 data: payload,
1450 success: function () {
1451 cb();
1452 }
1453 });
1454 });
1455 }
1456
1457 /**
1458 * Delete policy
1459 *
1460 * @param {Int} id
1461 */
1462 function DeletePolicy(id, btn) {
1463 const endpoint = getAAM().prepareApiEndpoint(
1464 '/policy/' + id
1465 );
1466
1467 getAAM().queueRequest(function () {
1468 $.ajax(endpoint, {
1469 type: 'POST',
1470 headers: {
1471 'X-WP-Nonce': getLocal().rest_nonce,
1472 'X-HTTP-Method-Override': 'DELETE'
1473 },
1474 dataType: 'json',
1475 beforeSend: function () {
1476 $(btn).attr('data-original', $(btn).text());
1477 $(btn).text(getAAM().__('Deleting...')).attr(
1478 'disabled', true
1479 );
1480 },
1481 success: function () {
1482 $('#policy_list').DataTable().ajax.reload();
1483 },
1484 error: function (response) {
1485 getAAM().notification('danger', response);
1486 },
1487 complete: function () {
1488 $('#delete-policy-modal').modal('hide');
1489
1490 $(btn).text($(btn).attr('data-original')).attr(
1491 'disabled', false
1492 );
1493 }
1494 });
1495 });
1496 }
1497
1498 /**
1499 *
1500 * @returns {undefined}
1501 */
1502 function initialize() {
1503 var container = '#policy-content';
1504
1505 if ($(container).length) {
1506 // Reset button
1507 $('#policy_reset').bind('click', function () {
1508 const btn = this;
1509 const endpoint = getAAM().prepareApiEndpoint(
1510 '/policies'
1511 );
1512
1513 getAAM().queueRequest(function () {
1514 $.ajax(endpoint, {
1515 type: 'POST',
1516 headers: {
1517 'X-WP-Nonce': getLocal().rest_nonce,
1518 'X-HTTP-Method-Override': 'DELETE'
1519 },
1520 dataType: 'json',
1521 beforeSend: function () {
1522 $(btn).text(getAAM().__('Resetting...')).attr(
1523 'disabled', true
1524 );
1525 },
1526 success: function () {
1527 $('#policy_list').DataTable().ajax.reload();
1528 },
1529 error: function (response) {
1530 getAAM().notification('danger', response);
1531 },
1532 complete: function () {
1533 $('#aam-policy-overwrite').hide();
1534 $(btn).text(getAAM().__('Reset To Default')).attr(
1535 'disabled', false
1536 );
1537 }
1538 });
1539 });
1540 });
1541
1542 $('#delete-policy-btn').bind('click', function() {
1543 DeletePolicy($(this).attr('data-id'));
1544 });
1545
1546 $('#policy_list').DataTable({
1547 autoWidth: false,
1548 ordering: false,
1549 dom: 'ftrip',
1550 pagingType: 'simple',
1551 processing: true,
1552 stateSave: true,
1553 serverSide: false,
1554 ajax: {
1555 url: getAAM().prepareApiEndpoint('/policies?fields=excerpt,permissions'),
1556 type: 'GET',
1557 headers: {
1558 'X-WP-Nonce': getLocal().rest_nonce
1559 },
1560 dataType: 'json',
1561 dataSrc: function (json) {
1562 // Transform the received data into DT format
1563 const data = [];
1564
1565 $.each(json, (_, policy) => {
1566 data.push([
1567 policy.id,
1568 policy.title,
1569 policy.permissions,
1570 policy
1571 ])
1572 });
1573
1574 return data;
1575 },
1576 },
1577 language: {
1578 search: '_INPUT_',
1579 searchPlaceholder: getAAM().__('Search Policy'),
1580 info: getAAM().__('_TOTAL_ Policies'),
1581 infoFiltered: ''
1582 },
1583 columnDefs: [
1584 { visible: false, targets: [ 0, 3 ] }
1585 ],
1586 initComplete: function () {
1587 const create = $('<a/>', {
1588 'href': '#',
1589 'class': 'btn btn-sm btn-primary'
1590 }).html('<i class="icon-plus"></i> ' + getAAM().__('Create'))
1591 .bind('click', function () {
1592 window.open(getLocal().url.addPolicy, '_blank');
1593 });
1594
1595 $('.dataTables_filter', '#policy_list_wrapper').append(create);
1596 },
1597 createdRow: function (row, data) {
1598 const container = $('<div/>', { 'class': 'aam-row-actions' });
1599 const checked = (data[3].is_attached ? 'icon-check' : 'icon-check-empty');
1600
1601 if (data[2].includes('toggle_policy')) {
1602 $(container).append($('<i/>', {
1603 'class': 'aam-row-action ' + checked
1604 }).bind('click', function () {
1605 TogglePolicy(
1606 data[0],
1607 ($(this).hasClass('icon-check-empty') ? 'attach' : 'detach'),
1608 this
1609 );
1610 }).attr({
1611 'data-toggle': "tooltip",
1612 'title': getAAM().__('Toggle Policy')
1613 }));
1614 } else {
1615 $(container).append($('<i/>', {
1616 'class': 'aam-row-action text-muted ' + checked
1617 }));
1618 }
1619
1620 if (data[2].includes('edit_policy')) {
1621 $(container).append($('<i/>', {
1622 'class': 'aam-row-action icon-pencil text-warning'
1623 }).bind('click', function () {
1624 window.open(
1625 getLocal().url.editPost + `?post=${data[0]}&action=edit`,
1626 '_blank'
1627 );
1628 }).attr({
1629 'data-toggle': "tooltip",
1630 'title': getAAM().__('Edit Policy')
1631 }));
1632 } else {
1633 $(container).append($('<i/>', {
1634 'class': 'aam-row-action text-muted icon-pencil'
1635 }));
1636 }
1637
1638 if (data[2].includes('delete_policy')) {
1639 $(container).append($('<i/>', {
1640 'class': 'aam-row-action icon-trash-empty text-danger'
1641 }).bind('click', function () {
1642 let message = $(
1643 '.aam-confirm-message', '#delete-policy-modal'
1644 ).data('message');
1645
1646 // replace some dynamic parts
1647 message = message.replace(
1648 '%s', '<b>' + data[3].title + '</b>'
1649 );
1650 $('.aam-confirm-message', '#delete-policy-modal').html(message);
1651
1652 $('#delete-policy-btn').attr('data-id', data[0]);
1653 $('#delete-policy-modal').modal('show');
1654 }).attr({
1655 'data-toggle': "tooltip",
1656 'title': getAAM().__('Delete Policy')
1657 }));
1658 } else {
1659 $(container).append($('<i/>', {
1660 'class': 'aam-row-action text-muted icon-trash-empty'
1661 }));
1662 }
1663 $('td:eq(1)', row).html(container);
1664
1665 $('td:eq(0)', row).html(
1666 data[3].title + '<br/><small>' + data[3].excerpt + '</small>'
1667 );
1668 }
1669 });
1670 }
1671
1672 // Policy Assignee metabox
1673 if ($('#policy_principle_selector').length) {
1674 // Query params to the request
1675 const policy_id = parseInt($('#aam-policy-id').val(), 10);
1676
1677 const fields = [
1678 'permissions'
1679 ];
1680
1681 // Prepare the RESTful API endpoint
1682 let url = `${getLocal().rest_base}aam/v2/roles`;
1683
1684 if (url.indexOf('rest_route') === -1) {
1685 url += `?fields=${fields.join(',')}`;
1686 } else {
1687 url += `&fields=${fields.join(',')}`;
1688 }
1689
1690 url += `&context=policy_assignee&policy_id=${policy_id}`;
1691
1692 $('#policy_principle_role_list').DataTable({
1693 autoWidth: false,
1694 ordering: false,
1695 dom: 'ftrip',
1696 pagingType: 'simple',
1697 processing: true,
1698 stateSave: true,
1699 serverSide: false,
1700 ajax: {
1701 url,
1702 type: 'GET',
1703 headers: {
1704 'X-WP-Nonce': getLocal().rest_nonce
1705 },
1706 dataType: 'json',
1707 dataSrc: function (json) {
1708 // Transform the received data into DT format
1709 const data = [];
1710
1711 $.each(json, (_, role) => {
1712 data.push([
1713 role.slug,
1714 role.name,
1715 role.permissions,
1716 role
1717 ])
1718 });
1719
1720 return data;
1721 },
1722 },
1723 columnDefs: [
1724 { visible: false, targets: [0, 3] },
1725 ],
1726 language: {
1727 search: '_INPUT_',
1728 searchPlaceholder: getAAM().__('Search role'),
1729 info: getAAM().__('_TOTAL_ role(s)'),
1730 infoFiltered: ''
1731 },
1732 createdRow: function (row, data) {
1733 $('td:eq(0)', row).html('<span>' + data[1] + '</span>');
1734
1735 // Add subtitle
1736 $('td:eq(0)', row).append(
1737 $('<i/>', { 'class': 'aam-row-subtitle' }).html(
1738 getAAM().applyFilters(
1739 'role-subtitle',
1740 'ID: <b>' + data[0] + '</b>',
1741 data
1742 )
1743 )
1744 );
1745
1746 const checked = data[3].is_attached ? 'icon-check' : 'icon-check-empty';
1747 const container = $(
1748 '<div/>', { 'class': 'aam-row-actions' }
1749 );
1750
1751 if (data[2].includes('toggle_role_policy')) {
1752 $(container).append($('<i/>', {
1753 'class': 'aam-row-action ' + checked
1754 }).bind('click', function () {
1755 const btn = $(this);
1756 const effect = btn.hasClass('icon-check-empty') ? 'attach' : 'detach';
1757 btn.attr('class', 'aam-row-action icon-spin4 animate-spin');
1758
1759 ToggleAccessLevelPolicy(
1760 'role',
1761 data[0],
1762 policy_id,
1763 effect,
1764 () => {
1765 if (effect === 'attach') {
1766 btn.attr(
1767 'class',
1768 'aam-row-action icon-check'
1769 );
1770 } else {
1771 btn.attr(
1772 'class',
1773 'aam-row-action icon-check-empty'
1774 );
1775 }
1776 }
1777 );
1778 }));
1779 } else {
1780 $(container).append($('<i/>', {
1781 'class': 'aam-row-action text-muted ' + checked
1782 }));
1783 }
1784
1785 $('td:eq(1)', row).html(container);
1786 }
1787 });
1788
1789 $('#policy_principle_user_list').DataTable({
1790 autoWidth: false,
1791 ordering: false,
1792 dom: 'ftrip',
1793 stateSave: true,
1794 pagingType: 'simple',
1795 serverSide: true,
1796 processing: true,
1797 ajax: function(filters, cb) {
1798 const fields = [
1799 'display_name',
1800 'permissions'
1801 ];
1802
1803 $.ajax({
1804 url: `${getLocal().rest_base}aam/v2/users`,
1805 type: 'GET',
1806 headers: {
1807 'X-WP-Nonce': getLocal().rest_nonce
1808 },
1809 data: {
1810 search: filters.search.value,
1811 per_page: filters.length,
1812 offset: filters.start,
1813 fields: fields.join(','),
1814 context: 'policy_assignee',
1815 policy_id
1816 },
1817 success: function (response) {
1818 const result = {
1819 data: [],
1820 recordsTotal: 0,
1821 recordsFiltered: 0
1822 };
1823
1824 $.each(response.list, (_, user) => {
1825 result.data.push([
1826 user.id,
1827 user.display_name,
1828 user.permissions,
1829 user
1830 ]);
1831 });
1832
1833 result.recordsTotal = response.summary.total_count;
1834 result.recordsFiltered = response.summary.filtered_count;
1835
1836 cb(result);
1837 }
1838 });
1839 },
1840 columnDefs: [
1841 { visible: false, targets: [0, 3] }
1842 ],
1843 language: {
1844 search: '_INPUT_',
1845 searchPlaceholder: getAAM().__('Search user'),
1846 info: getAAM().__('_TOTAL_ user(s)'),
1847 infoFiltered: ''
1848 },
1849 createdRow: function (row, data) {
1850 $('td:eq(0)', row).append(
1851 $('<i/>', { 'class': 'aam-row-subtitle' }).html(
1852 `${getAAM().__('ID')}: <b>${data[0]}</b>`
1853 )
1854 );
1855
1856 const checked = data[3].is_attached ? 'icon-check' : 'icon-check-empty';
1857 const container = $(
1858 '<div/>', { 'class': 'aam-row-actions' }
1859 );
1860
1861 if (data[2].includes('toggle_user_policy')) {
1862 $(container).append($('<i/>', {
1863 'class': 'aam-row-action ' + checked
1864 }).bind('click', function () {
1865 const btn = $(this);
1866 const effect = btn.hasClass('icon-check-empty') ? 'attach' : 'detach';
1867
1868 btn.attr('class', 'aam-row-action icon-spin4 animate-spin');
1869
1870 ToggleAccessLevelPolicy(
1871 'user',
1872 data[0],
1873 policy_id,
1874 effect,
1875 () => {
1876 if (effect === 'attach') {
1877 btn.attr(
1878 'class',
1879 'aam-row-action icon-check'
1880 );
1881 } else {
1882 btn.attr(
1883 'class',
1884 'aam-row-action icon-check-empty'
1885 );
1886 }
1887 }
1888 );
1889 }));
1890 } else {
1891 $(container).append($('<i/>', {
1892 'class': 'aam-row-action text-muted ' + checked
1893 }));
1894 }
1895
1896 $('td:eq(1)', row).html(container);
1897 }
1898 });
1899
1900 $('#toggle_visitor_policy').bind('click', function() {
1901 const effect = $(this).data('has') === '1' ? 'detach' : 'attach';
1902 $(this).text(getAAM().__('Processing...')).prop('disabled', true);
1903
1904 ToggleAccessLevelPolicy(
1905 'visitor',
1906 null,
1907 policy_id,
1908 effect,
1909 () => {
1910 if (effect === 'attach') {
1911 $(this).text(getAAM().__('Detach Policy From Visitors')).prop('disabled', false)
1912 } else {
1913 $(this).text(getAAM().__('Attach Policy To Visitors')).prop('disabled', false)
1914 }
1915 }
1916 );
1917
1918 });
1919 }
1920
1921 }
1922
1923 getAAM().addHook('init', initialize);
1924
1925 })(jQuery);
1926
1927 /**
1928 * Admin Menu Interface
1929 *
1930 * @param {jQuery} $
1931 *
1932 * @returns {void}
1933 */
1934 (function ($) {
1935
1936 /**
1937 *
1938 * @param {Number} item
1939 * @param {Boolean} is_restricted
1940 * @param {Callback} cb
1941 *
1942 * @returns {Void}
1943 */
1944 function Save(item, is_restricted, cb) {
1945 getAAM().queueRequest(function () {
1946 const payload = {
1947 effect: is_restricted ? 'deny' : 'allow'
1948 };
1949
1950 const endpoint = getAAM().prepareApiEndpoint(
1951 '/backend-menu/' + item
1952 );
1953
1954 $.ajax(endpoint, {
1955 type: 'POST',
1956 headers: {
1957 'X-WP-Nonce': getLocal().rest_nonce,
1958 'X-HTTP-Method-Override': 'PATCH'
1959 },
1960 dataType: 'json',
1961 data: payload,
1962 success: function (response) {
1963 cb(response);
1964 },
1965 error: function (response) {
1966 getAAM().notification('danger', response, {
1967 request: '/backend-menu/' + encodeURI(item),
1968 payload,
1969 response
1970 });
1971 }
1972 });
1973 });
1974 }
1975
1976 /**
1977 *
1978 * @returns {undefined}
1979 */
1980 function initialize() {
1981 if ($('#admin_menu-content').length) {
1982 $('.aam-restrict-menu').each(function () {
1983 $(this).bind('click', function () {
1984 var _this = $(this);
1985 var status = $('i', $(this)).hasClass('icon-lock');
1986 var target = _this.data('target');
1987
1988 $('i', _this).attr('class', 'icon-spin4 animate-spin');
1989
1990 Save(_this.data('menu-id'), status, function () {
1991 getAAM().fetchContent('main');
1992 });
1993 });
1994 });
1995
1996 $('.aam-menu-item').each(function () {
1997 $(this).bind('click', function () {
1998 $('#menu-item-name').html($(this).data('name'));
1999 $('#menu-item-slug').html($(this).data('slug'));
2000 $('#menu-item-cap').html($(this).data('cap'));
2001 $('#menu-item-path').html($(this).data('path'));
2002 });
2003 });
2004
2005 $('.aam-accordion-action', '#admin-menu').each(function () {
2006 $(this).bind('click', function () {
2007 var _this = $(this);
2008
2009 const status = _this.hasClass('icon-lock-open');
2010
2011 // Show loading indicator
2012 _this.attr(
2013 'class',
2014 'aam-accordion-action icon-spin4 animate-spin'
2015 );
2016
2017 Save(
2018 _this.data('menu-id'),
2019 status,
2020 () => {
2021 $('#aam-menu-overwrite').show();
2022
2023 if (status) {
2024 _this.attr(
2025 'class',
2026 'aam-accordion-action icon-lock text-danger'
2027 );
2028 } else {
2029 _this.attr(
2030 'class',
2031 'aam-accordion-action icon-lock-open text-success'
2032 );
2033 }
2034 }
2035 );
2036 });
2037 });
2038
2039 // Reset button
2040 $('#menu-reset').bind('click', function () {
2041 const _this = $(this);
2042
2043 getAAM().queueRequest(function () {
2044 $.ajax(getAAM().prepareApiEndpoint(`/backend-menu`), {
2045 type: 'POST',
2046 headers: {
2047 'X-WP-Nonce': getLocal().rest_nonce,
2048 'X-HTTP-Method-Override': 'DELETE'
2049 },
2050 dataType: 'json',
2051 beforeSend: function () {
2052 _this.attr('data-original-label', _this.text());
2053 _this.text(getAAM().__('Resetting...'));
2054 },
2055 success: function () {
2056 getAAM().fetchContent('main');
2057 },
2058 error: function (response) {
2059 getAAM().notification('danger', response, {
2060 request: '/backend-menu',
2061 response
2062 });
2063 },
2064 complete: function () {
2065 _this.text(_this.attr('data-original-label'));
2066 }
2067 });
2068 });
2069 });
2070
2071 $(
2072 '[data-toggle="toggle"]',
2073 '#admin_menu-content'
2074 ).bootstrapToggle();
2075
2076 getAAM().triggerHook('init-backend-menu');
2077 }
2078 }
2079
2080 getAAM().addHook('init', initialize);
2081
2082 })(jQuery);
2083
2084 /**
2085 * Admin Toolbar Interface
2086 *
2087 * @param {jQuery} $
2088 *
2089 * @returns {void}
2090 */
2091 (function ($) {
2092
2093 /**
2094 *
2095 * @param {Number} item
2096 * @param {Boolean} status
2097 * @param {Callback} successCallback
2098 *
2099 * @returns {Void}
2100 */
2101 function save(item, is_hidden, cb) {
2102 getAAM().queueRequest(function () {
2103 const payload = { effect: is_hidden ? 'deny' : 'allow' };
2104 const endpoint = getAAM().prepareApiEndpoint(
2105 `/admin-toolbar/${item}`
2106 );
2107
2108 $.ajax(endpoint, {
2109 type: 'POST',
2110 headers: {
2111 'X-WP-Nonce': getLocal().rest_nonce,
2112 'X-HTTP-Method-Override': 'PATCH'
2113 },
2114 dataType: 'json',
2115 data: payload,
2116 success: function (response) {
2117 cb(response);
2118 },
2119 error: function (response) {
2120 getAAM().notification('danger', response, {
2121 request: endpoint,
2122 payload,
2123 response
2124 });
2125 }
2126 });
2127 });
2128 }
2129
2130 /**
2131 *
2132 * @returns {undefined}
2133 */
2134 function initialize() {
2135 if ($('#toolbar-content').length) {
2136 $('.aam-restrict-toolbar').each(function () {
2137 $(this).bind('click', function () {
2138 var _this = $(this);
2139 var status = $('i', $(this)).hasClass('icon-lock');
2140
2141 $('i', _this).attr('class', 'icon-spin4 animate-spin');
2142
2143 save(_this.data('toolbar'), status, function () {
2144 getAAM().fetchContent('main');
2145 });
2146 });
2147 });
2148
2149 $('.aam-toolbar-item').each(function () {
2150 $(this).bind('click', function () {
2151 $('#toolbar-item-name').html($(this).data('name'));
2152 $('#toolbar-item-id').html($(this).data('id'));
2153 $('#toolbar-item-uri').html($(this).data('uri'));
2154 });
2155 });
2156
2157 // Reset button
2158 $('#toolbar_reset').bind('click', function () {
2159 const _this = $(this);
2160
2161 getAAM().queueRequest(function () {
2162 $.ajax(getAAM().prepareApiEndpoint(`/admin-toolbar`), {
2163 type: 'POST',
2164 headers: {
2165 'X-WP-Nonce': getLocal().rest_nonce,
2166 'X-HTTP-Method-Override': 'DELETE'
2167 },
2168 dataType: 'json',
2169 beforeSend: function () {
2170 _this.attr('data-original-label', _this.text());
2171 _this.text(getAAM().__('Resetting...'));
2172 },
2173 success: function () {
2174 getAAM().fetchContent('main');
2175 },
2176 error: function (response) {
2177 getAAM().notification('danger', response, {
2178 request: 'aam/v2/admin-toolbar',
2179 response
2180 });
2181 },
2182 complete: function () {
2183 _this.text(_this.attr('data-original-label'));
2184 }
2185 });
2186 });
2187 });
2188
2189 $('.aam-accordion-action', '#toolbar_list').each(function () {
2190 $(this).bind('click', function () {
2191 var _this = $(this);
2192 const status = _this.hasClass('icon-lock-open');
2193
2194 // Show loading indicator
2195 _this.attr(
2196 'class',
2197 'aam-accordion-action icon-spin4 animate-spin'
2198 );
2199
2200 save(
2201 [_this.data('toolbar')],
2202 status,
2203 function () {
2204 $('#aam_toolbar_overwrite').show();
2205
2206 if (status) {
2207 _this.attr(
2208 'class',
2209 'aam-accordion-action icon-lock text-danger'
2210 );
2211 } else {
2212 _this.attr(
2213 'class',
2214 'aam-accordion-action icon-lock-open text-success'
2215 );
2216 }
2217 }
2218 );
2219 });
2220 });
2221
2222 $('[data-toggle="toggle"]', '#toolbar-content').bootstrapToggle();
2223
2224 getAAM().triggerHook('init-admin-toolbar');
2225 }
2226 }
2227
2228 getAAM().addHook('init', initialize);
2229
2230 })(jQuery);
2231
2232 /**
2233 * Metaboxes Interface
2234 *
2235 * @param {jQuery} $
2236 *
2237 * @returns {void}
2238 */
2239 (function ($) {
2240
2241 /**
2242 *
2243 * @param {*} slug
2244 * @param {*} screen_id
2245 * @param {*} is_hidden
2246 * @param {*} cb
2247 */
2248 function SetPermission(slug, screen_id, is_hidden, cb) {
2249 getAAM().queueRequest(function () {
2250 const data = {
2251 effect: is_hidden ? 'deny' : 'allow',
2252 screen_id
2253 };
2254
2255 $.ajax(getAAM().prepareApiEndpoint(`/metabox/${slug}`), {
2256 type: 'POST',
2257 headers: {
2258 'X-WP-Nonce': getLocal().rest_nonce,
2259 'X-HTTP-Method-Override': 'PATCH'
2260 },
2261 dataType: 'json',
2262 data,
2263 success: function (response) {
2264 cb(response);
2265 },
2266 error: function (response) {
2267 getAAM().notification('danger', response, {
2268 request: `/metabox/${slug}`,
2269 payload: data,
2270 response
2271 });
2272 }
2273 });
2274 });
2275 }
2276
2277 /**
2278 *
2279 * @param {type} endpoints
2280 * @param {type} index
2281 * @param {type} btn
2282 * @returns {undefined}
2283 */
2284 function fetchData(endpoints, index, btn) {
2285 $.ajax(endpoints[index], {
2286 type: 'GET',
2287 complete: function () {
2288 if (index < endpoints.length) {
2289 fetchData(endpoints, index + 1, btn);
2290 } else {
2291 btn.attr('class', 'icon-arrows-cw');
2292 getAAM().fetchContent('main');
2293 }
2294 }
2295 });
2296 }
2297
2298 /**
2299 *
2300 * @returns {undefined}
2301 */
2302 function initialize() {
2303 if ($('#metabox-content').length) {
2304 //init refresh list button
2305 $('#refresh-metabox-list').bind('click', function () {
2306 $('i', '#refresh-metabox-list').attr(
2307 'class', 'icon-spin4 animate-spin icon-arrows-cw'
2308 );
2309 fetchData(
2310 JSON.parse($('#aam_screen_list').text()),
2311 0,
2312 $('i', '#refresh-metabox-list')
2313 );
2314 });
2315
2316 $('#init-url-btn').bind('click', function () {
2317 var url = $('#init-url').val();
2318 url += (url.indexOf('?') === -1 ? '?' : '&') + 'init=metabox';
2319
2320 $.ajax(url, {
2321 type: 'GET',
2322 beforeSend: function () {
2323 $('#init-url-btn').text(getAAM().__('Processing...'));
2324 },
2325 complete: function () {
2326 $('#init-url-btn').text(getAAM().__('Initialize'));
2327 $('#init-url-modal').modal('hide');
2328
2329 setTimeout(() => {
2330 getAAM().fetchContent('main');
2331 }, 1000);
2332 }
2333 });
2334 });
2335
2336 $('.aam-metabox-item').each(function () {
2337 $(this).bind('click', function () {
2338 $('#metabox-title').html($(this).data('title'));
2339 $('#metabox-screen-id').html($(this).data('screen'));
2340 $('#metabox-id').html($(this).data('id'));
2341 });
2342 });
2343
2344 // Reset button
2345 $('#metabox-reset').bind('click', function () {
2346 const _this = $(this);
2347
2348 getAAM().queueRequest(function () {
2349 $.ajax(getAAM().prepareApiEndpoint(`/metaboxes`), {
2350 type: 'POST',
2351 headers: {
2352 'X-WP-Nonce': getLocal().rest_nonce,
2353 'X-HTTP-Method-Override': 'DELETE'
2354 },
2355 dataType: 'json',
2356 beforeSend: function () {
2357 _this.attr('data-original-label', _this.text());
2358 _this.text(getAAM().__('Resetting...'));
2359 },
2360 success: function () {
2361 getAAM().fetchContent('main');
2362 },
2363 error: function (response) {
2364 getAAM().notification('danger', response, {
2365 request: '/metaboxes',
2366 response
2367 });
2368 },
2369 complete: function () {
2370 _this.text(_this.attr('data-original-label'));
2371 }
2372 });
2373 });
2374 });
2375
2376 $('.aam-accordion-action', '#metabox-list').each(function () {
2377 $(this).bind('click', function () {
2378 var _this = $(this);
2379
2380 const status = _this.hasClass('icon-lock-open');
2381
2382 // Show loading indicator
2383 _this.attr(
2384 'class',
2385 'aam-accordion-action icon-spin4 animate-spin'
2386 );
2387
2388 SetPermission(
2389 $(this).data('metabox'),
2390 $(this).data('screen'),
2391 status,
2392 function () {
2393 $('#aam-metabox-overwrite').show();
2394
2395 if (status) {
2396 _this.attr(
2397 'class',
2398 'aam-accordion-action icon-lock text-danger'
2399 );
2400 } else {
2401 _this.attr(
2402 'class',
2403 'aam-accordion-action icon-lock-open text-success'
2404 );
2405 }
2406 }
2407 );
2408 });
2409 });
2410
2411 getAAM().triggerHook('init-metabox');
2412 }
2413 }
2414
2415 getAAM().addHook('init', initialize);
2416
2417 })(jQuery);
2418
2419 /**
2420 * Widgets Interface
2421 *
2422 * @param {jQuery} $
2423 *
2424 * @returns {void}
2425 */
2426 (function ($) {
2427
2428 /**
2429 *
2430 * @param {String} slug
2431 * @param {Boolean} status
2432 * @param {Callback} successCallback
2433 *
2434 * @returns {Void}
2435 */
2436 function save(slug, is_hidden, cb) {
2437 getAAM().queueRequest(function () {
2438 $.ajax(getAAM().prepareApiEndpoint(`/widget/${slug}`), {
2439 type: 'POST',
2440 headers: {
2441 'X-WP-Nonce': getLocal().rest_nonce,
2442 'X-HTTP-Method-Override': 'PATCH'
2443 },
2444 dataType: 'json',
2445 data: { effect : is_hidden ? 'deny' : 'allow' },
2446 success: function (response) {
2447 cb(response);
2448 },
2449 error: function (response) {
2450 getAAM().notification('danger', response, {
2451 request: `aam/v2/widget/${slug}`,
2452 payload: { effect : is_hidden ? 'deny' : 'allow' },
2453 response
2454 });
2455 }
2456 });
2457 });
2458 }
2459
2460 /**
2461 *
2462 * @param {type} endpoints
2463 * @param {type} index
2464 * @param {type} btn
2465 * @returns {undefined}
2466 */
2467 function fetchData(endpoints, index, btn) {
2468 $.ajax(endpoints[index], {
2469 type: 'GET',
2470 complete: function () {
2471 if (index < endpoints.length) {
2472 fetchData(endpoints, index + 1, btn);
2473 } else {
2474 btn.attr('class', 'icon-arrows-cw');
2475 getAAM().fetchContent('main');
2476 }
2477 }
2478 });
2479 }
2480
2481 /**
2482 *
2483 * @returns {undefined}
2484 */
2485 function initialize() {
2486 if ($('#widget-content').length) {
2487 //init refresh list button
2488 $('#refresh_widget_list').bind('click', function () {
2489 $('i', '#refresh_widget_list').attr(
2490 'class', 'icon-spin4 animate-spin icon-arrows-cw'
2491 );
2492 fetchData(
2493 JSON.parse($('#aam_widget_screen_list').text()),
2494 0,
2495 $('i', '#refresh_widget_list')
2496 );
2497 });
2498
2499 $('.aam-widget-item').each(function () {
2500 $(this).bind('click', function () {
2501 $('#widget_title').html($(this).data('title'));
2502 $('#widget_screen_id').html($(this).data('screen'));
2503 $('#widget_id').html($(this).data('id'));
2504 });
2505 });
2506
2507 // Reset button
2508 $('#widget_reset').bind('click', function () {
2509 const _this = $(this);
2510
2511 getAAM().queueRequest(function () {
2512 $.ajax(getAAM().prepareApiEndpoint('/widgets'), {
2513 type: 'POST',
2514 headers: {
2515 'X-WP-Nonce': getLocal().rest_nonce,
2516 'X-HTTP-Method-Override': 'DELETE'
2517 },
2518 dataType: 'json',
2519 beforeSend: function () {
2520 _this.attr('data-original-label', _this.text());
2521 _this.text(getAAM().__('Resetting...'));
2522 },
2523 success: function () {
2524 getAAM().fetchContent('main');
2525 },
2526 error: function (response) {
2527 getAAM().notification('danger', response, {
2528 request: 'aam/v2/widgets',
2529 response
2530 });
2531 },
2532 complete: function () {
2533 _this.text(_this.attr('data-original-label'));
2534 }
2535 });
2536 });
2537 });
2538
2539 $('.aam-accordion-action', '#widget-list').each(function () {
2540 $(this).bind('click', function () {
2541 var _this = $(this);
2542
2543 const status = _this.hasClass('icon-lock-open');
2544
2545 // Show loading indicator
2546 _this.attr(
2547 'class',
2548 'aam-accordion-action icon-spin4 animate-spin'
2549 );
2550
2551 save(
2552 $(this).data('widget'),
2553 status,
2554 function () {
2555 $('#aam-widget-overwrite').show();
2556
2557 if (status) {
2558 _this.attr(
2559 'class',
2560 'aam-accordion-action icon-lock text-danger'
2561 );
2562 } else {
2563 _this.attr(
2564 'class',
2565 'aam-accordion-action icon-lock-open text-success'
2566 );
2567 }
2568 }
2569 );
2570 });
2571 });
2572
2573 getAAM().triggerHook('init-widget');
2574 }
2575 }
2576
2577 getAAM().addHook('init', initialize);
2578
2579 })(jQuery);
2580
2581 /**
2582 * Capabilities Interface
2583 *
2584 * @param {jQuery} $
2585 *
2586 * @returns {void}
2587 */
2588 (function ($) {
2589
2590 /**
2591 *
2592 * @param {type} capability
2593 * @param {type} btn
2594 * @returns {undefined}
2595 */
2596 function toggle(capability, btn) {
2597 var granted = $(btn).hasClass('icon-check-empty');
2598
2599 // Show indicator
2600 $(btn).attr('class', 'aam-row-action icon-spin4 animate-spin');
2601
2602 // Prepare request payload
2603 const payload = {
2604 [granted ? 'add_capabilities' : 'deprive_capabilities'] : [
2605 capability
2606 ]
2607 };
2608
2609 // Determine endpoint
2610 let endpoint = '';
2611
2612 if (getAAM().getSubject().type === 'role') {
2613 endpoint += '/role/' + encodeURIComponent(getAAM().getSubject().id);
2614 } else if (getAAM().getSubject().type === 'user') {
2615 endpoint += '/user/' + getAAM().getSubject().id;
2616 }
2617
2618 getAAM().queueRequest(function () {
2619 $.ajax(getAAM().prepareApiEndpoint(endpoint), {
2620 type: 'POST',
2621 headers: {
2622 'X-WP-Nonce': getLocal().rest_nonce,
2623 'X-HTTP-Method-Override': 'PATCH'
2624 },
2625 dataType: 'json',
2626 data: payload,
2627 success: function () {
2628 if (granted) {
2629 $(btn).attr(
2630 'class',
2631 'aam-row-action text-success icon-check'
2632 );
2633 } else {
2634 $(btn).attr(
2635 'class',
2636 'aam-row-action text-muted icon-check-empty'
2637 );
2638 }
2639 },
2640 error: function (response) {
2641 getAAM().notification('danger', response, {
2642 request: endpoint,
2643 payload,
2644 response
2645 });
2646 }
2647 });
2648 });
2649 }
2650
2651 /**
2652 * Delete capability
2653 *
2654 * @param {String} capability
2655 * @param {Object} btn
2656 */
2657 function deleteCapability(capability, btn) {
2658 getAAM().queueRequest(function () {
2659 $.ajax(getAAM().prepareApiEndpoint(`/capability/${encodeURIComponent(capability)}`), {
2660 type: 'POST',
2661 headers: {
2662 'X-WP-Nonce': getLocal().rest_nonce,
2663 'X-HTTP-Method-Override': 'DELETE'
2664 },
2665 data: {
2666 globally: true
2667 },
2668 dataType: 'json',
2669 beforeSend: function () {
2670 $(btn).attr('data-original', $(btn).text());
2671 $(btn).text(getAAM().__('Deleting...')).attr('disabled', true);
2672 },
2673 success: function () {
2674 $('#capability-list').DataTable().ajax.reload();
2675 },
2676 error: function (response) {
2677 getAAM().notification('danger', response, {
2678 request: `/capability/${encodeURIComponent(capability)}`,
2679 payload,
2680 response
2681 });
2682 },
2683 complete: function () {
2684 $('#delete-capability-modal').modal('hide');
2685
2686 $(btn).text(getAAM().__('Delete For All Roles')).attr(
2687 'disabled', false
2688 );
2689 }
2690 });
2691 });
2692 }
2693
2694 /**
2695 *
2696 * @returns {undefined}
2697 */
2698 function initialize() {
2699 if ($('#capability-content').length) {
2700 const data = {
2701 fields: 'description,permissions,is_granted'
2702 };
2703
2704 // Initialize the capability list table
2705 const capTable = $('#capability-list').DataTable({
2706 autoWidth: false,
2707 ordering: false,
2708 pagingType: 'simple',
2709 serverSide: false,
2710 ajax: {
2711 url: getAAM().prepareApiEndpoint('/capabilities'),
2712 type: 'GET',
2713 data,
2714 headers: {
2715 'X-WP-Nonce': getLocal().rest_nonce
2716 },
2717 dataType: 'json',
2718 dataSrc: function (json) {
2719 // Transform the received data into DT format
2720 const data = [];
2721
2722 $.each(json, (_, capability) => {
2723 const actions = [];
2724
2725 let prefix = capability.permissions.includes('allow_toggle') ? '' : 'no-';
2726
2727 if (capability.is_granted) {
2728 actions.push(`${prefix}checked`);
2729 } else {
2730 actions.push(`${prefix}unchecked`);
2731 }
2732
2733 prefix = capability.permissions.includes('allow_update') ? '' : 'no-';
2734 actions.push(`${prefix}edit`);
2735
2736 prefix = capability.permissions.includes('allow_delete') ? '' : 'no-';
2737 actions.push(`${prefix}delete`);
2738
2739 data.push([
2740 capability.slug,
2741 capability.description,
2742 actions.join(','),
2743 capability.is_granted,
2744 capability
2745 ])
2746 });
2747
2748 return data;
2749 },
2750 },
2751 columnDefs: [
2752 { visible: false, targets: [0, 3, 4] }
2753 ],
2754 language: {
2755 search: '_INPUT_',
2756 searchPlaceholder: getAAM().__('Search Capability'),
2757 info: getAAM().__('_TOTAL_ capability(s)'),
2758 infoFiltered: '',
2759 infoEmpty: getAAM().__('No capabilities'),
2760 lengthMenu: '_MENU_'
2761 },
2762 createdRow: function (row, data, _, cells) {
2763 var actions = data[2].split(',');
2764
2765 var container = $('<div/>', { 'class': 'aam-row-actions' });
2766 $.each(actions, function (i, action) {
2767 switch (action) {
2768 case 'unchecked':
2769 $(container).append($('<i/>', {
2770 'class': 'aam-row-action text-muted icon-check-empty'
2771 }).bind('click', function () {
2772 capTable.cell(cells[4]).data(true);
2773 toggle(data[0], this);
2774 }));
2775 break;
2776
2777 case 'checked':
2778 $(container).append($('<i/>', {
2779 'class': 'aam-row-action text-success icon-check'
2780 }).bind('click', function () {
2781 capTable.cell(cells[4]).data(false);
2782 toggle(data[0], this);
2783 }));
2784 break;
2785
2786 case 'no-unchecked':
2787 $(container).append($('<i/>', {
2788 'class': 'aam-row-action text-muted icon-check-empty'
2789 }));
2790 break;
2791
2792 case 'no-checked':
2793 $(container).append($('<i/>', {
2794 'class': 'aam-row-action text-muted icon-check'
2795 }));
2796 break;
2797
2798 case 'edit':
2799 $(container).append($('<i/>', {
2800 'class': 'aam-row-action icon-pencil text-warning'
2801 }).bind('click', function () {
2802 $('#update-capability-slug').val(data[0]);
2803 $('#update-capability-btn').attr('data-cap', data[0]);
2804 $('#update-capability-modal').modal('show');
2805 }));
2806 break;
2807
2808 case 'no-edit':
2809 $(container).append($('<i/>', {
2810 'class': 'aam-row-action icon-pencil text-muted'
2811 }));
2812 break;
2813
2814 case 'delete':
2815 $(container).append($('<i/>', {
2816 'class': 'aam-row-action icon-trash-empty text-danger'
2817 }).bind('click', function () {
2818 let message = $(
2819 '.aam-confirm-message',
2820 '#delete-capability-modal'
2821 ).data('message');
2822
2823 // replace some dynamic parts
2824 message = message.replace(
2825 '%s', '<b>' + data[0] + '</b>'
2826 );
2827
2828 $(
2829 '.aam-confirm-message',
2830 '#delete-capability-modal'
2831 ).html(message);
2832
2833 $('#delete-capability-btn').attr('data-cap', data[0]);
2834 $('#delete-capability-modal').modal('show');
2835 }));
2836 break;
2837
2838 case 'no-delete':
2839 $(container).append($('<i/>', {
2840 'class': 'aam-row-action icon-trash-empty text-muted'
2841 }));
2842 break;
2843
2844 default:
2845 getAAM().triggerHook('decorate-capability-row', {
2846 action: action,
2847 container: container,
2848 data: data
2849 });
2850 break;
2851 }
2852 });
2853 $('td:eq(1)', row).html(container);
2854
2855 $('td:eq(0)', row).html(
2856 `<strong>${data[0]}</strong><br/>
2857 <small>${data[1] || 'No description provided'}</small>`
2858 );
2859 }
2860 });
2861
2862 $('a', '#capability-groups').each(function () {
2863 $(this).bind('click', function () {
2864 var table = $('#capability-list').DataTable();
2865
2866 if ($(this).data('assigned') === true) {
2867 table.column(3).search(true).draw();
2868 } else if ($(this).data('unassigned') === true) {
2869 table.column(3).search(false).draw();
2870 } else if ($(this).data('clear') === true) {
2871 table.columns().search('').draw();
2872 }
2873 });
2874 });
2875
2876 $('#add-capability-modal').on('show.bs.modal', function () {
2877 $('#add_capability_error').addClass('hidden');
2878 $('#ignore_capability_format_container').addClass('hidden');
2879
2880 $('#new-capability-name').val('');
2881 $('#new-capability-name').focus();
2882 });
2883
2884 $('#update-capability-modal').on('show.bs.modal', function () {
2885 $('#update_capability_error').addClass('hidden');
2886 $('#ignore_update_capability_format_container').addClass('hidden');
2887 });
2888
2889 $('#new-capability-name').bind('change', function() {
2890 const cap = $('#new-capability-name').val();
2891
2892 if (/^[a-z0-9_\-]+$/.test(cap) === false) {
2893 $('#add_capability_error').html(
2894 $('#add_capability_error').data('message').replace('%s', cap)
2895 ).removeClass('hidden');
2896 $('#ignore_capability_format_container').removeClass('hidden');
2897 } else {
2898 $('#add_capability_error').addClass('hidden');
2899 $('#ignore_capability_format_container').addClass('hidden');
2900 }
2901 });
2902
2903 $('#update-capability-slug').bind('change', function() {
2904 const cap = $('#update-capability-slug').val();
2905
2906 if (/^[a-z0-9_\-]+$/.test(cap) === false) {
2907 $('#update_capability_error').html(
2908 $('#update_capability_error').data('message').replace('%s', cap)
2909 ).removeClass('hidden');
2910 $('#ignore_update_capability_format_container').removeClass('hidden');
2911 } else {
2912 $('#update_capability_error').addClass('hidden');
2913 $('#ignore_update_capability_format_container').addClass('hidden');
2914 }
2915 });
2916
2917 $('#add-capability').bind('click', function () {
2918 $('#add-capability-modal').modal('show');
2919 });
2920
2921 $('#add-capability-btn').bind('click', function () {
2922 var _this = this;
2923
2924 const slug = $.trim($('#new-capability-name').val());
2925 const ignore = $('#ignore_capability_format').is(':checked');
2926
2927 if (slug && (/^[a-z0-9_\-]+$/.test(slug) || ignore)) {
2928 const payload = {
2929 slug,
2930 ignore_format: ignore
2931 };
2932
2933 getAAM().queueRequest(function () {
2934 $.ajax(getAAM().prepareApiEndpoint('/capabilities'), {
2935 type: 'POST',
2936 headers: {
2937 'X-WP-Nonce': getLocal().rest_nonce
2938 },
2939 dataType: 'json',
2940 data: payload,
2941 beforeSend: function () {
2942 $(_this).text(getAAM().__('Saving...')).attr('disabled', true);
2943 },
2944 success: function () {
2945 $('#add-capability-modal').modal('hide');
2946 $('#capability-list').DataTable().ajax.reload();
2947 },
2948 error: function (response) {
2949 getAAM().notification('danger', response, {
2950 request: 'aam/v2/capabilities',
2951 payload,
2952 response
2953 });
2954 },
2955 complete: function () {
2956 $(_this).text(getAAM().__('Add Capability')).attr('disabled', false);
2957 }
2958 });
2959 });
2960 } else {
2961 $('#new-capability-name').parent().addClass('has-error');
2962 }
2963 });
2964
2965 $('#update-capability-btn').bind('click', function () {
2966 const btn = this;
2967 const old_slug = $(this).attr('data-cap');
2968 const slug = $.trim($('#update-capability-slug').val());
2969 const ignore = $('#ignore_update_capability_format').is(':checked');
2970
2971 if (slug && (/^[a-z0-9_\-]+$/.test(slug) || ignore)) {
2972 // Prepare request payload
2973 const payload = {
2974 slug,
2975 ignore_format: ignore,
2976 globally: true
2977 };
2978
2979 getAAM().queueRequest(function () {
2980 $.ajax(getAAM().prepareApiEndpoint(`/capability/${encodeURIComponent(old_slug)}`), {
2981 type: 'POST',
2982 headers: {
2983 'X-WP-Nonce': getLocal().rest_nonce,
2984 'X-HTTP-Method-Override': 'PATCH'
2985 },
2986 dataType: 'json',
2987 data: payload,
2988 beforeSend: function () {
2989 $(btn).text(getAAM().__('Saving...')).attr('disabled', true);
2990 },
2991 success: function () {
2992 $('#capability-list').DataTable().ajax.reload();
2993 },
2994 error: function (response) {
2995 getAAM().notification('danger', response, {
2996 request: `aam/v2/capability/${encodeURIComponent(old_slug)}`,
2997 payload,
2998 response
2999 });
3000 },
3001 complete: function () {
3002 $('#update-capability-modal').modal('hide');
3003
3004 $(btn).text(getAAM().__('Update For All Roles')).attr(
3005 'disabled', false
3006 );
3007 }
3008 });
3009 });
3010 }
3011 });
3012
3013 $('#delete-capability-btn').bind('click', function () {
3014 deleteCapability($(this).attr('data-cap'), $(this));
3015 });
3016 }
3017 }
3018
3019 getAAM().addHook('init', initialize);
3020
3021 })(jQuery);
3022
3023 /**
3024 * Posts & Terms Interface
3025 *
3026 * @param {jQuery} $
3027 *
3028 * @returns {void}
3029 */
3030 (function ($) {
3031
3032 /**
3033 * Breadcrumb
3034 */
3035 let breadcrumb = [
3036 {
3037 label: getAAM().__('Root'),
3038 level_type: null,
3039 level_id: null
3040 },
3041 {
3042 label: getAAM().__('Post Types'),
3043 level_type: 'type_list',
3044 level_id: null
3045 }
3046 ];
3047
3048 // Internal cache
3049 let cache = {};
3050
3051 /**
3052 *
3053 * @returns
3054 */
3055 function CurrentLevel() {
3056 return breadcrumb[breadcrumb.length - 1];
3057 }
3058
3059 /**
3060 * Render the breadcrumb
3061 *
3062 * @param {Boolean} reload
3063 */
3064 function RenderBreadcrumb(reload) {
3065 // Resetting the breadcrumb
3066 $('.aam-post-breadcrumb').empty();
3067
3068 $.each(breadcrumb, function(i, level) {
3069 if (level.level_type === null) { // Root, append home icon
3070 $('.aam-post-breadcrumb').append(
3071 '<i class="icon-home"></i>'
3072 );
3073 } else {
3074 $('.aam-post-breadcrumb').append(
3075 '<i class="icon-angle-double-right"></i>'
3076 );
3077 }
3078
3079 if (i === breadcrumb.length - 1) { // last element
3080 $('.aam-post-breadcrumb').append(
3081 $('<span/>').text(level.label)
3082 );
3083 } else {
3084 $('.aam-post-breadcrumb').append(
3085 $('<a/>').attr({
3086 'href': '#',
3087 'data-type': level.level_type,
3088 'data-id': level.level_id,
3089 'data-level': i
3090 }).bind('click', function(event) {
3091 event.preventDefault();
3092
3093 breadcrumb = breadcrumb.slice(
3094 0, $(this).data('level') + 1
3095 );
3096
3097 // Take into consideration the "Root" level click
3098 if (breadcrumb.length === 1) {
3099 breadcrumb.push({
3100 label: getAAM().__('Post Types'),
3101 level_type: 'type_list',
3102 level_id: null
3103 });
3104 $('.aam-type-taxonomy-filter').val('type_list');
3105 }
3106
3107 $('#aam_content_access_form').removeClass('active');
3108
3109 RenderBreadcrumb();
3110 }).text(level.label)
3111 );
3112 }
3113 });
3114
3115 AdjustList(reload);
3116 }
3117
3118 /**
3119 *
3120 * @param {*} node
3121 */
3122 function AddToBreadcrumb(node) {
3123 // If the last breadcrumb item has the same level, replace it
3124 const last = breadcrumb[breadcrumb.length - 1];
3125
3126 if (node.level_type === last.level_type) {
3127 breadcrumb.pop();
3128 }
3129
3130 breadcrumb.push(node);
3131
3132 RenderBreadcrumb(node.reload);
3133 }
3134
3135 /**
3136 *
3137 * @param {*} level_type
3138 * @param {*} level_id
3139 * @param {*} label
3140 */
3141 function ReplaceInBreadcrumb(level_type, level_id, label) {
3142 breadcrumb.pop();
3143
3144 AddToBreadcrumb({
3145 level_type,
3146 level_id,
3147 label
3148 });
3149 }
3150
3151 /**
3152 *
3153 */
3154 function NavigateBack() {
3155 breadcrumb.pop();
3156 RenderBreadcrumb(false);
3157 }
3158
3159 /**
3160 * Save a single permission
3161 *
3162 * @param {String} permission
3163 * @param {Object} payload
3164 * @param {Callback} cb
3165 *
3166 * @returns {Void}
3167 */
3168 function UpdateContentPermission(permission, payload, cb = null) {
3169 getAAM().queueRequest(function () {
3170 const resource_type = $('#content_resource_type').val();
3171 const resource_id = $('#content_resource_id').val();
3172 const permission_scope = JSON.parse(
3173 $('#content_permission_scope').val()
3174 );
3175
3176 // If there is additional resource permission scope, add it
3177 const query = [];
3178
3179 for(key in permission_scope) {
3180 query.push(`${key}=${permission_scope[key]}`);
3181 }
3182
3183 $.ajax(getAAM().prepareApiEndpoint(
3184 `/${resource_type}/${resource_id}/${permission}?${query.join('&')}`
3185 ), {
3186 type: 'POST',
3187 headers: {
3188 'X-WP-Nonce': getLocal().rest_nonce,
3189 'X-HTTP-Method-Override': 'PATCH'
3190 },
3191 contentType: 'application/json; charset=UTF-8',
3192 dataType: 'json',
3193 data: JSON.stringify(payload),
3194 success: function (response) {
3195 if (cb) {
3196 cb(response);
3197 }
3198
3199 $('#content_resource_settings').text(JSON.stringify(
3200 response.permissions
3201 ));
3202
3203 // Update indicator
3204 if (resource_type === 'post_type') {
3205 $.each(cache.post_types.data, (_, p) => {
3206 if (p[0] === resource_id) {
3207 p[4].is_customized = true;
3208 }
3209 });
3210 } else if (resource_type === 'taxonomy') {
3211 $.each(cache.taxonomies.data, (_, p) => {
3212 if (p[0] === resource_id) {
3213 p[4].is_customized = true;
3214 }
3215 });
3216 }
3217 },
3218 error: function (response) {
3219 getAAM().notification('danger', response);
3220 }
3221 });
3222 });
3223 }
3224
3225 /**
3226 * Render the content access form
3227 *
3228 * This is the SSR to reduce complexity for the frontend implementation
3229 *
3230 * @param {Object} target
3231 * @param {Callback} callback
3232 */
3233 function RenderAccessForm(target = null, callback = null) {
3234 // Reset the form first
3235 var container = $('#aam_content_access_form');
3236
3237 // Show overlay if present
3238 $('.aam-overlay', container).show();
3239
3240 if (target === null) {
3241 let scope = {};
3242
3243 if ($('#content_permission_scope').length) {
3244 scope = JSON.parse($('#content_permission_scope').val());
3245 }
3246
3247 target = Object.assign(scope, {
3248 resource_type: $('#content_resource_type').val(),
3249 resource_id: $('#content_resource_id').val()
3250 });
3251 }
3252
3253 // Prepare payload for the SSR rendering
3254 const payload = Object.assign({
3255 action: 'aam',
3256 sub_action: 'renderContent',
3257 partial: 'content-access-form',
3258 _ajax_nonce: getLocal().nonce,
3259 }, target);
3260
3261 $.ajax(getLocal().ajaxurl, {
3262 type: 'POST',
3263 dataType: 'html',
3264 data: getAAM().prepareAjaxRequestPayload(payload),
3265 success: function (response) {
3266 $('#aam_access_form_container').html(response);
3267
3268 $('#content_list_container .dataTables_wrapper').addClass(
3269 'hidden'
3270 );
3271 container.addClass('active');
3272
3273 InitializeAccessForm();
3274
3275 if (typeof callback === 'function') {
3276 callback.call();
3277 }
3278 },
3279 error: function (response) {
3280 getAAM().notification('danger', response);
3281 }
3282 });
3283 }
3284
3285 /**
3286 *
3287 * @param {*} permission
3288 * @returns
3289 */
3290 function GetResourcePermission(permission) {
3291 const permissions = JSON.parse($('#content_resource_settings').text());
3292
3293 return permissions[permission];
3294 }
3295
3296 /**
3297 *
3298 * @param {*} resource_type
3299 * @param {*} resource_id
3300 */
3301 function InitializeAccessForm(init_toggles = true) {
3302 if (init_toggles) {
3303 $('[data-toggle="toggle"]', '#aam_access_form_container').bootstrapToggle();
3304 }
3305
3306 // Permission toggles
3307 $('input[data-toggle="toggle"]', '#permission_toggles').each(function() {
3308 $(this).bind('change', function() {
3309 UpdateContentPermission(
3310 $(this).data('permission'),
3311 { effect: $(this).prop('checked') ? 'deny' : 'allow' },
3312 () => RenderAccessForm()
3313 );
3314 });
3315 });
3316
3317 // Initialize the Content Visibility modal functionality
3318 if ($('#modal_content_visibility').length) {
3319 $('#save_list_permission').bind('click', function() {
3320 // Prepare the payload
3321 let payload = GetResourcePermission('list');
3322
3323 if (payload === undefined) {
3324 payload = {
3325 effect: 'deny',
3326 on: []
3327 }
3328 } else {
3329 payload.on = [];
3330 }
3331
3332 $(
3333 'input[data-toggle="toggle"]',
3334 '#modal_content_visibility'
3335 ).each(function() {
3336 if ($(this).prop('checked')) {
3337 payload.on.push($(this).attr('name'));
3338 }
3339 });
3340
3341 if (payload.on.length > 0) {
3342 $(this).prop('disabled', true).text(getAAM().__('Saving'));
3343
3344 UpdateContentPermission(
3345 'list',
3346 getAAM().applyFilters('aam-list-permission-payload', payload),
3347 () => {
3348 $('#modal_content_visibility').modal('hide');
3349
3350 // Reload the access form
3351 RenderAccessForm();
3352 }
3353 );
3354 }
3355 });
3356 }
3357
3358 // Initialize the Content Restriction modal functionality
3359 if ($('#modal_content_restriction').length) {
3360 // Initialize the restriction type toggles
3361 $('input[type="radio"]', '#restriction_types').each(function () {
3362 $(this).bind('click', function () {
3363 $('#restriction_type_extra > div').addClass('hidden');
3364 $('#restriction_type_extra > div[data-type="' + $(this).val() + '"').removeClass('hidden')
3365 });
3366 });
3367
3368 // Initialize the redirect type element
3369 $('#restricted_redirect_type').bind('change', function() {
3370 $('.restricted-redirect-type').addClass('hidden');
3371 $('.restricted-redirect-type[data-type="' + $(this).val() + '"]').removeClass('hidden')
3372 });
3373
3374 // Initialize the expiration picker
3375 const def = $('#aam_expire_datetime').val();
3376
3377 $('#content_expire_datepicker').datetimepicker({
3378 icons: {
3379 time: "icon-clock",
3380 date: "icon-calendar",
3381 up: "icon-angle-up",
3382 down: "icon-angle-down",
3383 previous: "icon-angle-left",
3384 next: "icon-angle-right"
3385 },
3386 inline: true,
3387 defaultDate: $.trim(def) ? new Date(def * 1000) : new Date(),
3388 sideBySide: true
3389 });
3390
3391 $('#content_expire_datepicker').on('dp.change', function (res) {
3392 $('#aam_expire_datetime').val(res.date.unix());
3393 });
3394
3395 $('#save_read_permission').bind('click', function() {
3396 const payload = {
3397 effect: 'deny'
3398 }
3399
3400 // Depending on the restriction type, collect additional
3401 // attributes
3402 const restriction_type = $(
3403 'input[name="content_restriction_type"]:checked',
3404 '#restriction_types'
3405 ).val();
3406
3407 payload.restriction_type = restriction_type;
3408
3409 if (restriction_type === 'teaser_message') {
3410 payload.message = $.trim(
3411 $('#aam_teaser_message').val()
3412 );
3413 } else if (restriction_type === 'redirect') {
3414 const redirect = {
3415 // The the redirect type
3416 type: $('#restricted_redirect_type').val()
3417 };
3418
3419 if (redirect.type === 'page_redirect') {
3420 redirect.redirect_page_id = $('#restricted_redirect_page_id').val();
3421 } else if (redirect.type === 'url_redirect') {
3422 redirect.redirect_url = $('#restricted_redirect_url').val();
3423 } else if (redirect.type === 'trigger_callback') {
3424 redirect.callback = $('#restricted_callback').val();
3425 }
3426
3427 payload.redirect = redirect;
3428 } else if (restriction_type === 'password_protected') {
3429 payload.password = $.trim(
3430 $('#restricted_password').val()
3431 );
3432 } else if (restriction_type === 'expire') {
3433 payload.expires_after = $('#aam_expire_datetime').val();
3434 }
3435
3436 $(this).prop('disabled', true).text(getAAM().__('Saving'));
3437
3438 UpdateContentPermission(
3439 'read',
3440 getAAM().applyFilters('aam-read-permission-payload', payload),
3441 () => {
3442 $('#modal_content_restriction').modal('hide');
3443
3444 // Reload the access form
3445 RenderAccessForm();
3446 }
3447 );
3448 });
3449 }
3450
3451 // Initialize the Reset to default button
3452 $('#content_reset').bind('click', function () {
3453 const resource_type = encodeURIComponent($('#content_resource_type').val());
3454 const resource_id = $('#content_resource_id').val();
3455 const permission_scope = JSON.parse(
3456 $('#content_permission_scope').val()
3457 );
3458
3459 // If there is additional resource permission scope, add it
3460 const query = [];
3461
3462 for(key in permission_scope) {
3463 query.push(`${key}=${permission_scope[key]}`);
3464 }
3465
3466 if (CurrentLevel().permissions) {
3467 CurrentLevel().permissions = undefined;
3468 }
3469
3470 $.ajax(getAAM().prepareApiEndpoint(
3471 `/${resource_type}/${resource_id}?${query.join('&')}`
3472 ), {
3473 type: 'POST',
3474 headers: {
3475 'X-WP-Nonce': getLocal().rest_nonce,
3476 'X-HTTP-Method-Override': 'DELETE'
3477 },
3478 beforeSend: function () {
3479 $('#content_reset').attr(
3480 'data-original-label', $('#content_reset').text()
3481 );
3482 $('#content_reset').text(getAAM().__('Resetting...'));
3483 },
3484 success: function () {
3485 $('#post-overwritten').addClass('hidden');
3486
3487 RenderAccessForm();
3488
3489 // Manually update the data in a table because both
3490 // Post Types & Taxonomies are static tables
3491 if (['post_type', 'taxonomy'].includes(resource_type)) {
3492 let row = null;
3493
3494 if (resource_type === 'post_type') {
3495 row = cache.post_types.data.filter(
3496 t => t[0] === resource_id
3497 ).pop();
3498 } else {
3499 row = cache.taxonomies.data.filter(
3500 t => t[0] === resource_id
3501 ).pop();
3502 }
3503
3504 row[4].is_inherited = true;
3505 row[4].is_customized = false;
3506 }
3507 },
3508 complete: function () {
3509 $('#content_reset').text(
3510 $('#content_reset').attr('data-original-label')
3511 );
3512 }
3513 });
3514 });
3515
3516 // Allow third-party plugins to initialize the Access Form
3517 getAAM().triggerHook('init-access-form', {
3518 RenderAccessForm,
3519 UpdateContentPermission,
3520 GetResourcePermission
3521 });
3522 }
3523
3524 getAAM().addHook('load-access-form', function(params) {
3525 RenderAccessForm(...params);
3526 });
3527
3528 getAAM().addHook('save-post-settings', function(params) {
3529 save(...params);
3530 });
3531
3532 /**
3533 * Get the list of post types
3534 *
3535 * It is a static list, so we are caching it
3536 *
3537 * @param {Callback} cb
3538 */
3539 function FetchPostTypeList(cb) {
3540 if (cache.post_types === undefined) {
3541 // Fetching the list of all registered post types.
3542 $.ajax(getAAM().prepareApiEndpoint(`/post_types`), {
3543 type: 'GET',
3544 headers: {
3545 'X-WP-Nonce': getLocal().rest_nonce
3546 },
3547 success: function (response) {
3548 const types = [];
3549
3550 $.each(response.list, (_, item) => {
3551 types.push([
3552 item.slug,
3553 item.icon || (item.is_hierarchical ? 'dashicons-admin-page' : 'dashicons-media-default'),
3554 item.title,
3555 ['drilldown', 'manage'],
3556 item
3557 ]);
3558 });
3559
3560 cache.post_types = {
3561 data: types,
3562 recordsTotal: response.summary.total_count,
3563 recordsFiltered: response.summary.filtered_count
3564 };
3565
3566 cb(cache.post_types);
3567 }
3568 });
3569 } else {
3570 cb(cache.post_types);
3571 }
3572 }
3573
3574 /**
3575 * Get the list of taxonomies
3576 *
3577 * This is another static list, so we are caching it as well
3578 *
3579 * @param {Callback} cb
3580 */
3581 function FetchTaxonomyList(cb) {
3582 // Fetching the list of all registered post types.
3583 if (cache.taxonomies === undefined) {
3584 $.ajax(getAAM().prepareApiEndpoint(`/taxonomies`), {
3585 type: 'GET',
3586 headers: {
3587 'X-WP-Nonce': getLocal().rest_nonce
3588 },
3589 success: function (response) {
3590 const taxonomies = [];
3591
3592 $.each(response.list, (_, item) => {
3593 taxonomies.push([
3594 item.slug,
3595 item.is_hierarchical ? 'dashicons-category' : 'dashicons-tag',
3596 item.title,
3597 ['drilldown', 'manage'],
3598 item
3599 ]);
3600 });
3601
3602 cache.taxonomies = {
3603 data: taxonomies,
3604 recordsTotal: response.summary.total_count,
3605 recordsFiltered: response.summary.filtered_count
3606 };
3607
3608 cb(cache.taxonomies);
3609 }
3610 });
3611 } else {
3612 cb(cache.taxonomies);
3613 }
3614 }
3615
3616 /**
3617 * Fetch list of posts
3618 *
3619 * @param {Object} filters
3620 * @param {Callback} cb
3621 */
3622 function FetchPostList(filters, cb) {
3623 // Fetching the list of posts
3624 $.ajax(getAAM().prepareApiEndpoint(`/posts`), {
3625 type: 'GET',
3626 headers: {
3627 'X-WP-Nonce': getLocal().rest_nonce
3628 },
3629 data: {
3630 post_type: CurrentLevel().level_id,
3631 offset: filters.start,
3632 per_page: filters.length,
3633 search: filters.search.value
3634 },
3635 success: function (response) {
3636 const result = {
3637 data: [],
3638 recordsTotal: 0,
3639 recordsFiltered: 0
3640 };
3641
3642 if (response && response.list) {
3643 $.each(response.list, (_, item) => {
3644 result.data.push([
3645 item.id,
3646 item.icon || (item.is_hierarchical ? 'dashicons-admin-page' : 'dashicons-media-default'),
3647 item.title,
3648 ['edit', 'manage'],
3649 item
3650 ]);
3651 });
3652
3653 result.recordsTotal = response.summary.total_count;
3654 result.recordsFiltered = response.summary.filtered_count;
3655 }
3656
3657 cb(result);
3658 }
3659 });
3660 }
3661
3662 /**
3663 *
3664 * @param {*} filters
3665 * @param {*} cb
3666 */
3667 function FetchTermList(filters, cb) {
3668 const payload = {
3669 taxonomy: CurrentLevel().level_id,
3670 offset: filters.start,
3671 per_page: filters.length,
3672 search: filters.search.value
3673 };
3674
3675 if (CurrentLevel().post_type) {
3676 payload.post_type = CurrentLevel().post_type;
3677 }
3678
3679 // Fetching the list of terms
3680 $.ajax(getAAM().prepareApiEndpoint(`/terms`), {
3681 type: 'GET',
3682 headers: {
3683 'X-WP-Nonce': getLocal().rest_nonce
3684 },
3685 data: payload,
3686 success: function (response) {
3687 const result = {
3688 data: [],
3689 recordsTotal: 0,
3690 recordsFiltered: 0
3691 };
3692
3693 $.each(response.list, (_, item) => {
3694 result.data.push([
3695 item.id,
3696 item.is_hierarchical ? 'dashicons-category' : 'dashicons-tag',
3697 item.title,
3698 getAAM().applyFilters(
3699 'aam-term-actions',
3700 ['edit', 'manage'],
3701 item
3702 ),
3703 item
3704 ]);
3705 });
3706
3707 result.recordsTotal = response.summary.total_count;
3708 result.recordsFiltered = response.summary.filtered_count;
3709
3710 cb(result);
3711 }
3712 });
3713 }
3714
3715 /**
3716 * Adjust the list of content items based on where are we
3717 *
3718 * @param {Boolean} reload
3719 */
3720 function AdjustList(reload = true) {
3721 const current = CurrentLevel();
3722
3723 if ([null, 'type_list'].includes(current.level_type)) {
3724 PrepareTypeListTable(reload);
3725 } else if (current.level_type === 'taxonomy_list') {
3726 PrepareTaxonomyListTable(reload);
3727 } else if (current.level_type === 'type_posts') {
3728 PreparePostListTable(reload);
3729 } else if (current.level_type === 'type_terms') {
3730 PrepareTermListTable(current, reload);
3731 } else if (current.level_type === 'taxonomy_terms') {
3732 PrepareTermListTable(current, reload)
3733 }
3734 }
3735
3736 /**
3737 *
3738 * @returns
3739 */
3740 function RenderTypeTaxonomySwitch(){
3741 const current = CurrentLevel();
3742 const options = [
3743 {
3744 value: 'type_list',
3745 label: getAAM().__('Post Types'),
3746 selected: [null, 'type_list'].includes(current.level_type)
3747 },
3748 {
3749 value: 'taxonomy_list',
3750 label: getAAM().__('Taxonomies'),
3751 selected: current.level_type === 'taxonomy_list'
3752 }
3753 ];
3754
3755 return $('<select>').attr({
3756 'class': 'form-control input-sm aam-ml-1 aam-type-taxonomy-filter aam-filtered-list'
3757 }).html(
3758 options.map(o => `'<option value="${o.value}" ${o.selected ? 'selected' : ''}>${o.label}</option>`).join('')
3759 ).bind('change', function () {
3760 $(`.aam-type-taxonomy-filter option[value="${$(this).val()}"]`).prop(
3761 'selected', true
3762 );
3763
3764 ReplaceInBreadcrumb(
3765 $(this).val(), null, $('option:selected', $(this)).text()
3766 );
3767 });
3768 }
3769
3770 /**
3771 *
3772 * @param {*} filter_id
3773 */
3774 function RenderPostTaxonomySwitch(filter_id) {
3775 FetchTaxonomyList(function(response) {
3776 const current = CurrentLevel();
3777 const options = [
3778 {
3779 value: `type_posts:${current.level_id}`,
3780 label: getAAM().__('Only %s List').replace('%s', CurrentLevel().label),
3781 selected: current.level_type === 'type'
3782 }
3783 ];
3784 $.each(response.data.filter(t => t[4].post_types.includes(current.level_id)), function(_, item) {
3785 options.push({
3786 value: `type_terms:${current.level_id}:${item[0]}`,
3787 label: item[2],
3788 selected: current.level_type === 'taxonomy' && current.level_id === item[0]
3789 });
3790 });
3791
3792 const filter_controller = $('<select>').attr({
3793 'class': 'form-control input-sm aam-ml-1 aam-post-taxonomy-filter aam-filtered-list'
3794 }).html(
3795 options.map(o => `'<option value="${o.value}" ${o.selected ? 'selected' : ''}>${o.label}</option>`).join('')
3796 ).bind('change', function () {
3797 const value = $(this).val();
3798 const [
3799 level_type, post_type, taxonomy
3800 ] = $(this).val().split(':');
3801
3802 AddToBreadcrumb({
3803 level_type,
3804 level_id: taxonomy,
3805 label: $(`.aam-post-taxonomy-filter option:selected`).text(),
3806 post_type,
3807 taxonomy
3808 });
3809
3810 $(`.aam-post-taxonomy-filter option[value="${value}"]`).prop(
3811 'selected', true
3812 );
3813 });
3814
3815 if ($('.aam-post-taxonomy-filter', filter_id).length) {
3816 $('.aam-post-taxonomy-filter', filter_id).replaceWith(filter_controller);
3817 } else {
3818 $(filter_id).append(filter_controller);
3819 }
3820 });
3821 }
3822
3823 /**
3824 *
3825 * @param {*} data
3826 */
3827 function NavigateToAccessForm(data) {
3828 if (data.btn) {
3829 $(data.btn).attr('data-class', $(data.btn).attr('class'));
3830 $(data.btn).attr(
3831 'class',
3832 'aam-row-action icon-spin4 animate-spin'
3833 );
3834 }
3835
3836 // Determine the targeting resource
3837 const target = {
3838 resource_type: data.level_type,
3839 resource_id: data.level_id
3840 };
3841
3842 if (data.post_type !== undefined) {
3843 target.post_type = data.post_type;
3844 }
3845
3846 if (data.taxonomy !== undefined) {
3847 target.taxonomy = data.taxonomy;
3848 }
3849
3850 RenderAccessForm(target, () => {
3851 // Update the breadcrumb
3852 AddToBreadcrumb({
3853 level_type: data.level_type,
3854 level_id: data.level_id,
3855 label: data.label,
3856 post_type: data.post_type,
3857 taxonomy: data.taxonomy,
3858 is_access_form: true
3859 });
3860
3861 if (data.btn){
3862 $(data.btn).attr(
3863 'class',
3864 $(data.btn).attr('data-class')
3865 ).removeAttr('data-class');
3866 }
3867 });
3868 }
3869
3870 /**
3871 *
3872 */
3873 function PrepareTypeListTable() {
3874 $('#content_list_container .dataTables_wrapper').addClass('hidden');
3875 $('#content_list_container .table').addClass('hidden');
3876
3877 if (!$('#post_type_list').hasClass('dataTable')) {
3878 $('#post_type_list').DataTable({
3879 autoWidth: false,
3880 ordering: false,
3881 pagingType: 'simple',
3882 processing: true,
3883 saveState: true,
3884 ajax: function(_, cb) {
3885 FetchPostTypeList(cb);
3886 },
3887 columnDefs: [
3888 { visible: false, targets: [0, 4] },
3889 { searchable: false, targets: [0, 1, 3, 4] }
3890 ],
3891 language: {
3892 search: '_INPUT_',
3893 searchPlaceholder: getAAM().__('Search'),
3894 info: getAAM().__('_TOTAL_ type(s)'),
3895 infoFiltered: '',
3896 lengthMenu: '_MENU_'
3897 },
3898 initComplete: function () {
3899 // Adding the root level controls
3900 $('#post_type_list_length').append(RenderTypeTaxonomySwitch());
3901 },
3902 rowCallback: function(row, data) {
3903 let overwritten = '';
3904
3905 if (data[4].is_customized) {
3906 overwritten = ' aam-access-overwritten';
3907 }
3908
3909 $('td:eq(0)', row).html(
3910 `<div class="dashicons-before ${data[1]}${overwritten}"></div>`
3911 );
3912
3913 // Decorating the post type title & make it actionable
3914 $('td:eq(1)', row).html($('<a/>', {
3915 href: '#'
3916 }).bind('click', function () {
3917 AddToBreadcrumb({
3918 level_type: 'type_posts',
3919 level_id: data[0],
3920 label: data[2]
3921 });
3922 }).html(data[2]));
3923
3924 $('td:eq(1)', row).append(`<sup>${data[0]}</sup>`);
3925
3926 const container = $('<div/>', { 'class': 'aam-row-actions' });
3927
3928 $.each(data[3], function (_, action) {
3929 switch (action) {
3930 case 'drilldown':
3931 $(container).append($('<i/>', {
3932 'class': 'aam-row-action text-success icon-level-down'
3933 }).bind('click', function () {
3934 $('td:eq(1) > a', row).trigger('click');
3935 }).attr({
3936 'data-toggle': "tooltip",
3937 'title': getAAM().__('Drill-Down')
3938 }));
3939 $('.tooltip').remove();
3940 break;
3941
3942 case 'manage':
3943 $(container).append($('<i/>', {
3944 'class': 'aam-row-action text-info icon-cog'
3945 }).bind('click', function () {
3946 NavigateToAccessForm({
3947 level_type: 'post_type',
3948 level_id: data[0],
3949 label: data[2],
3950 btn: $(this)
3951 });
3952 }).attr({
3953 'data-toggle': "tooltip",
3954 'title': getAAM().__('Manage Access')
3955 }));
3956 $('.tooltip').remove();
3957 break;
3958
3959 default:
3960 getAAM().triggerHook('post-action', {
3961 container: container,
3962 action: action,
3963 data: data
3964 });
3965 break;
3966 }
3967 });
3968 $('td:eq(2)', row).html(container);
3969 }
3970 });
3971 } else {
3972 $('#post_type_list').DataTable().ajax.reload(null, false);
3973 }
3974
3975 $('#post_type_list_wrapper .table').removeClass('hidden');
3976 $('#post_type_list_wrapper').removeClass('hidden');
3977 }
3978
3979 /**
3980 *
3981 */
3982 function PrepareTaxonomyListTable() {
3983 $('#content_list_container .dataTables_wrapper').addClass('hidden');
3984 $('#content_list_container .table').addClass('hidden');
3985
3986 if (!$('#taxonomy_list').hasClass('dataTable')) {
3987 $('#taxonomy_list').DataTable({
3988 autoWidth: false,
3989 ordering: false,
3990 pagingType: 'simple',
3991 processing: true,
3992 saveState: true,
3993 ajax: function(_, cb) {
3994 FetchTaxonomyList(cb);
3995 },
3996 columnDefs: [
3997 { visible: false, targets: [0, 4] },
3998 { searchable: false, targets: [0, 1, 3, 4] }
3999 ],
4000 language: {
4001 search: '_INPUT_',
4002 searchPlaceholder: getAAM().__('Search'),
4003 info: getAAM().__('_TOTAL_ taxonomy(s)'),
4004 infoFiltered: '',
4005 lengthMenu: '_MENU_'
4006 },
4007 initComplete: function () {
4008 // Adding the root level controls
4009 $('#taxonomy_list_length').append(RenderTypeTaxonomySwitch());
4010 },
4011 rowCallback: function(row, data) {
4012 let overwritten = '';
4013
4014 if (data[4].is_customized) {
4015 overwritten = ' aam-access-overwritten';
4016 }
4017
4018 $('td:eq(0)', row).html(
4019 `<div class="dashicons-before ${data[1]}${overwritten}"></div>`
4020 );
4021
4022 // Decorating the post type title & make it actionable
4023 $('td:eq(1)', row).html($('<a/>', {
4024 href: '#'
4025 }).bind('click', function () {
4026 AddToBreadcrumb({
4027 level_type: 'taxonomy_terms',
4028 level_id: data[0],
4029 label: data[2],
4030 taxonomy: data[0]
4031 });
4032 }).html(data[2]));
4033
4034 $('td:eq(1)', row).append(`<sup>${data[0]}</sup>`);
4035
4036 const container = $('<div/>', { 'class': 'aam-row-actions' });
4037
4038 $.each(data[3], function (_, action) {
4039 switch (action) {
4040 case 'drilldown':
4041 $(container).append($('<i/>', {
4042 'class': 'aam-row-action text-success icon-level-down'
4043 }).bind('click', function () {
4044 $('td:eq(1) > a', row).trigger('click');
4045 }).attr({
4046 'data-toggle': "tooltip",
4047 'title': getAAM().__('Drill-Down')
4048 }));
4049 $('.tooltip').remove();
4050 break;
4051
4052 case 'manage':
4053 $(container).append($('<i/>', {
4054 'class': 'aam-row-action text-info icon-cog'
4055 }).bind('click', function () {
4056 NavigateToAccessForm({
4057 level_type: 'taxonomy',
4058 level_id: data[0],
4059 label: data[2],
4060 btn: $(this)
4061 });
4062 }).attr({
4063 'data-toggle': "tooltip",
4064 'title': getAAM().__('Manage Access')
4065 }));
4066 $('.tooltip').remove();
4067 break;
4068
4069 default:
4070 getAAM().triggerHook('post-action', {
4071 container: container,
4072 action: action,
4073 data: data
4074 });
4075 break;
4076 }
4077 });
4078 $('td:eq(2)', row).html(container);
4079 }
4080 });
4081 } else {
4082 $('#taxonomy_list').DataTable().ajax.reload(null, false);
4083 }
4084
4085 $('#taxonomy_list_wrapper .table').removeClass('hidden');
4086 $('#taxonomy_list_wrapper').removeClass('hidden');
4087 }
4088
4089 /**
4090 *
4091 */
4092 function PreparePostListTable(reload = false) {
4093 $('#content_list_container .dataTables_wrapper').addClass('hidden');
4094 $('#content_list_container .table').addClass('hidden');
4095
4096 if (!$('#post_list').hasClass('dataTable')) {
4097 $('#post_list').DataTable({
4098 autoWidth: false,
4099 ordering: false,
4100 processing: true,
4101 serverSide: true,
4102 pagingType: 'simple_numbers',
4103 ajax: function(filters, cb) {
4104 FetchPostList(filters, cb);
4105 },
4106 columnDefs: [
4107 { visible: false, targets: [0, 4] },
4108 { searchable: false, targets: [0, 1, 3, 4] }
4109 ],
4110 language: {
4111 search: '_INPUT_',
4112 searchPlaceholder: getAAM().__('Search'),
4113 info: getAAM().__('_TOTAL_ post(s)'),
4114 infoFiltered: '',
4115 lengthMenu: '_MENU_'
4116 },
4117 initComplete: function () {
4118 // Adding the root level controls
4119 RenderPostTaxonomySwitch('#post_list_length');
4120 },
4121 rowCallback: function(row, data) {
4122 let overwritten = '';
4123
4124 if (data[4].is_customized) {
4125 overwritten = ' aam-access-overwritten';
4126 }
4127
4128 $('td:eq(0)', row).html(
4129 `<div class="dashicons-before ${data[1]}${overwritten}"></div>`
4130 );
4131
4132 // Decorating the post type title & make it actionable
4133 $('td:eq(1)', row).html($('<a/>', {
4134 href: '#'
4135 }).bind('click', function () {
4136 NavigateToAccessForm({
4137 level_type: 'post',
4138 level_id: data[0],
4139 label: data[2],
4140 btn: $('.icon-cog', row)
4141 });
4142 }).html(data[2]));
4143
4144 $('td:eq(1)', row).append(`<sup>ID: ${data[0]}</sup>`);
4145
4146 const container = $('<div/>', { 'class': 'aam-row-actions' });
4147
4148 $.each(data[3], function (_, action) {
4149 switch (action) {
4150 case 'manage':
4151 $(container).append($('<i/>', {
4152 'class': 'aam-row-action text-info icon-cog'
4153 }).bind('click', function () {
4154 NavigateToAccessForm({
4155 level_type: 'post',
4156 level_id: data[0],
4157 label: data[2],
4158 btn: $(this)
4159 });
4160 }).attr({
4161 'data-toggle': "tooltip",
4162 'title': getAAM().__('Manage Access')
4163 }));
4164 $('.tooltip').remove();
4165 break;
4166
4167 case 'edit':
4168 $(container).append($('<i/>', {
4169 'class': 'aam-row-action text-warning icon-pencil'
4170 }).bind('click', function () {
4171 window.open(
4172 getLocal().url.editPost + `?post=${data[0]}&action=edit`,
4173 '_blank'
4174 );
4175 }).attr({
4176 'data-toggle': "tooltip",
4177 'title': getAAM().__('Edit')
4178 }));
4179 break;
4180
4181 case 'no-edit':
4182 $(container).append($('<i/>', {
4183 'class': 'aam-row-action text-muted icon-pencil'
4184 }));
4185 break;
4186
4187 default:
4188 getAAM().triggerHook('post-action', {
4189 container: container,
4190 action: action,
4191 data: data
4192 });
4193 break;
4194 }
4195 });
4196 $('td:eq(2)', row).html(container);
4197 }
4198 });
4199 } else {
4200 // Reload list of posts
4201 $('#post_list').DataTable().ajax.reload(null, reload);
4202 // Reload the list of taxonomies
4203 RenderPostTaxonomySwitch('#post_list_length');
4204 }
4205
4206 $('#post_list_wrapper .table').removeClass('hidden');
4207 $('#post_list_wrapper').removeClass('hidden');
4208 }
4209
4210 /**
4211 *
4212 * @param {*} scope
4213 */
4214 function PrepareTermListTable(scope = null, reload = false) {
4215 $('#content_list_container .dataTables_wrapper').addClass('hidden');
4216 $('#content_list_container .table').addClass('hidden');
4217
4218 if (scope && scope.post_type) {
4219 $('#term_list').attr('data-post-type', scope.post_type);
4220 } else {
4221 $('#term_list').removeAttr('data-post-type');
4222 }
4223
4224 if (scope && scope.taxonomy) {
4225 $('#term_list').attr('data-taxonomy', scope.taxonomy);
4226 } else {
4227 $('#term_list').removeAttr('data-taxonomy');
4228 }
4229
4230 if (!$('#term_list').hasClass('dataTable')) {
4231 $('#term_list').DataTable({
4232 autoWidth: false,
4233 ordering: false,
4234 pagingType: 'simple',
4235 processing: true,
4236 serverSide: true,
4237 pagingType: 'simple_numbers',
4238 ajax: function(filters, cb) {
4239 FetchTermList(filters, cb);
4240 },
4241 columnDefs: [
4242 { visible: false, targets: [0, 4] },
4243 { searchable: false, targets: [0, 1, 3, 4] }
4244 ],
4245 language: {
4246 search: '_INPUT_',
4247 searchPlaceholder: getAAM().__('Search'),
4248 info: getAAM().__('_TOTAL_ term(s)'),
4249 infoFiltered: '',
4250 lengthMenu: '_MENU_'
4251 },
4252 rowCallback: function(row, data) {
4253 let overwritten = '';
4254
4255 if (data[4].is_customized) {
4256 overwritten = ' aam-access-overwritten';
4257 }
4258
4259 $('td:eq(0)', row).html(
4260 `<div class="dashicons-before ${data[1]}${overwritten}"></div>`
4261 );
4262
4263 // Decorating the term title & make it actionable
4264 $('td:eq(1)', row).html($('<a/>', {
4265 href: '#'
4266 }).bind('click', function () {
4267 const post_type = $('#term_list').attr('data-post-type');
4268 const taxonomy = $('#term_list').attr('data-taxonomy');
4269
4270 NavigateToAccessForm({
4271 level_type: 'term',
4272 level_id: data[0],
4273 label: data[2],
4274 btn: $('.icon-cog', row),
4275 post_type,
4276 taxonomy
4277 });
4278 }).html(data[2]));
4279
4280 $('td:eq(1)', row).append(`<sup>ID: ${data[0]}</sup>`);
4281
4282 const container = $('<div/>', { 'class': 'aam-row-actions' });
4283
4284 $.each(data[3], function (_, action) {
4285 switch (action) {
4286 case 'manage':
4287 $(container).append($('<i/>', {
4288 'class': 'aam-row-action text-info icon-cog'
4289 }).bind('click', function () {
4290 const post_type = $('#term_list').attr('data-post-type');
4291 const taxonomy = $('#term_list').attr('data-taxonomy');
4292
4293 NavigateToAccessForm({
4294 level_type: 'term',
4295 level_id: data[0],
4296 label: data[2],
4297 btn: $(this),
4298 post_type,
4299 taxonomy
4300 });
4301 }).attr({
4302 'data-toggle': "tooltip",
4303 'title': getAAM().__('Manage Access')
4304 }));
4305 $('.tooltip').remove();
4306 break;
4307
4308 case 'edit':
4309 $(container).append($('<i/>', {
4310 'class': 'aam-row-action text-warning icon-pencil'
4311 }).bind('click', function () {
4312 const url = getLocal().url.editTerm + `?taxonomy=${data[4].taxonomy}&tag_ID=${data[0]}`;
4313 window.open(url, '_blank');
4314 }).attr({
4315 'data-toggle': "tooltip",
4316 'title': getAAM().__('Edit')
4317 }));
4318 break;
4319
4320 case 'no-edit':
4321 $(container).append($('<i/>', {
4322 'class': 'aam-row-action text-muted icon-pencil'
4323 }));
4324 break;
4325
4326 default:
4327 getAAM().triggerHook('term-item-action', {
4328 container: container,
4329 action: action,
4330 data: data
4331 });
4332 break;
4333 }
4334 });
4335 $('td:eq(2)', row).html(container);
4336 }
4337 });
4338 } else {
4339 $('#term_list').DataTable().ajax.reload(null, reload);
4340 }
4341
4342 $('#term_list_wrapper .table').removeClass('hidden');
4343 $('#term_list_wrapper').removeClass('hidden');
4344 }
4345
4346 /**
4347 *
4348 */
4349 function initialize() {
4350 if ($('#post-content').length) {
4351 // Go back button
4352 $('.aam-slide-form').delegate('.post-back', 'click', function () {
4353 $('.aam-slide-form').removeClass('active');
4354 NavigateBack();
4355 });
4356
4357 RenderBreadcrumb();
4358 } else if ($('#aam_post_access_metabox').length) {
4359 InitializeAccessForm(false);
4360 }
4361
4362 const current_level = CurrentLevel();
4363
4364 if (current_level && current_level.is_access_form) {
4365 // Determine the targeting resource
4366 const target = {
4367 resource_type: current_level.level_type,
4368 resource_id: current_level.level_id
4369 };
4370
4371 if (current_level.post_type !== undefined) {
4372 target.post_type = current_level.post_type;
4373 }
4374
4375 if (current_level.taxonomy !== undefined) {
4376 target.taxonomy = current_level.taxonomy;
4377 }
4378
4379 RenderAccessForm(target);
4380 }
4381 }
4382
4383 getAAM().addHook('init', initialize);
4384 getAAM().addHook('access-level-changed', function() {
4385 cache = {};
4386 });
4387
4388 })(jQuery);
4389
4390 /**
4391 * Access Denied Redirect Interface
4392 *
4393 * @param {jQuery} $
4394 *
4395 * @returns {void}
4396 */
4397 (function ($) {
4398
4399 /**
4400 *
4401 * @param {*} payload
4402 * @param {*} successCallback
4403 */
4404 function save(payload, successCallback) {
4405 getAAM().queueRequest(function () {
4406 $.ajax(getAAM().prepareApiEndpoint('/redirect/access-denied'), {
4407 type: 'POST',
4408 headers: {
4409 'X-WP-Nonce': getLocal().rest_nonce
4410 },
4411 dataType: 'json',
4412 data: payload,
4413 success: function (response) {
4414 successCallback(response);
4415 },
4416 error: function (response) {
4417 getAAM().notification('danger', response, {
4418 request: '/redirect/access-denied',
4419 payload,
4420 response
4421 });
4422 }
4423 });
4424 });
4425 }
4426
4427 /**
4428 *
4429 * @returns {undefined}
4430 */
4431 function initialize() {
4432 var container = '#redirect-content';
4433
4434 if ($(container).length) {
4435 $('input[type="radio"]', container).each(function () {
4436 $(this).bind('click', function () {
4437 // Determine area
4438 const area = $(this).data('group');
4439
4440 // Hide group
4441 $('.' + area).hide();
4442
4443 // Show the specific one
4444 $($(this).data('action')).show();
4445
4446 // Now, if the redirect type is default, then
4447 // save the data, otherwise save only when more detail
4448 // provided
4449 const type = $(this).val();
4450
4451 // If type is default or message, also capture the HTTP
4452 // status code
4453 const http_status_code = $(`#${area}-${type}-status-code`).val();
4454
4455 if (['default', 'login_redirect'].includes(type)) {
4456 save({ area, type, http_status_code }, () => {
4457 $('#aam-redirect-overwrite').show();
4458 });
4459 }
4460 });
4461 });
4462
4463 $('input[type="text"],select,textarea', container).each(function () {
4464 $(this).bind('change', function () {
4465 const value = $.trim($(this).val());
4466
4467 let area;
4468 if ($(this).attr('id') === 'frontend-page') {
4469 area = 'frontend';
4470 } else if ($(this).attr('id') === 'backend-page') {
4471 area = 'backend';
4472 } else {
4473 area = $(this).data('group');
4474 }
4475
4476 // Determining type
4477 const type = $(`input[name="${area}.redirect.type"]:checked`).val();
4478
4479 const payload = {
4480 area,
4481 type
4482 };
4483
4484 if (type === 'page_redirect') {
4485 payload.redirect_page_id = value;
4486 } else if (type === 'url_redirect') {
4487 payload.redirect_url = value;
4488 } else if (type === 'trigger_callback') {
4489 payload.callback = value;
4490 } else if (type === 'custom_message') {
4491 if ($(this).attr('name').indexOf('message.code') !== -1) {
4492 payload.http_status_code = value;
4493 payload.message = $(`textarea[name="${area}.redirect.message"]`).val();
4494 } else {
4495 payload.message = value;
4496 payload.http_status_code = $(`#${area}-message-status-code`).val()
4497 }
4498 } else if (type === 'default') {
4499 payload.http_status_code = value;
4500 }
4501
4502 //save redirect type
4503 save(payload, () => {
4504 $('#aam-redirect-overwrite').show();
4505 });
4506 });
4507 });
4508
4509 $('#redirect-reset').bind('click', function () {
4510 const _btn = $(this);
4511
4512 $.ajax(getAAM().prepareApiEndpoint(`/redirect/access-denied`), {
4513 type: 'POST',
4514 headers: {
4515 'X-WP-Nonce': getLocal().rest_nonce,
4516 'X-HTTP-Method-Override': 'DELETE'
4517 },
4518 dataType: 'json',
4519 beforeSend: function () {
4520 var label = _btn.text();
4521 _btn.attr('data-original-label', label);
4522 _btn.text(getAAM().__('Resetting...'));
4523 },
4524 success: function () {
4525 getAAM().fetchContent('main');
4526 },
4527 error: function (response) {
4528 getAAM().notification('danger', response, {
4529 request: '/redirect/access-denied',
4530 response
4531 });
4532 },
4533 complete: function () {
4534 _btn.text(_btn.attr('data-original-label'));
4535 }
4536 });
4537 });
4538 }
4539 }
4540
4541 getAAM().addHook('init', initialize);
4542
4543 })(jQuery);
4544
4545 /**
4546 * Login Redirect Interface
4547 *
4548 * @param {jQuery} $
4549 *
4550 * @returns {void}
4551 */
4552 (function ($) {
4553
4554 /**
4555 *
4556 * @param {payload} payload
4557 * @param {function} successCallback
4558 *
4559 * @returns {void}
4560 */
4561 function save(payload, successCallback) {
4562 getAAM().queueRequest(function () {
4563 $.ajax(getAAM().prepareApiEndpoint('/redirect/login'), {
4564 type: 'POST',
4565 headers: {
4566 'X-WP-Nonce': getLocal().rest_nonce
4567 },
4568 dataType: 'json',
4569 data: payload,
4570 success: function (response) {
4571 successCallback(response);
4572 },
4573 error: function (response) {
4574 getAAM().notification('danger', response, {
4575 request: 'aam/v2/redirect/login',
4576 payload,
4577 response
4578 });
4579 }
4580 });
4581 });
4582 }
4583
4584 /**
4585 *
4586 * @returns {undefined}
4587 */
4588 function initialize() {
4589 var container = '#login_redirect-content';
4590
4591 if ($(container).length) {
4592 $('input[type="radio"]', container).each(function () {
4593 $(this).bind('click', function () {
4594 // Hide all fields
4595 $('.login-redirect-action').hide();
4596
4597 // Show the specific one
4598 $($(this).data('action')).show();
4599
4600 // Now, if the login redirect type is default, then
4601 // save the data, otherwise save only when more detail
4602 // provided
4603 const type = $(this).val();
4604
4605 if (type === 'default') {
4606 save({ type }, () => {
4607 $('#aam-login-redirect-overwrite').show();
4608 });
4609 }
4610 });
4611 });
4612
4613 $('input[type="text"],select', container).each(function () {
4614 $(this).bind('change', function () {
4615 const value = $.trim($(this).val());
4616 const type = $('input[name="login.redirect.type"]:checked').val();
4617
4618 const payload = {
4619 type
4620 };
4621
4622 if (type === 'page_redirect') {
4623 payload.redirect_page_id = value;
4624 } else if (type === 'url_redirect') {
4625 payload.redirect_url = value;
4626 } else {
4627 payload.callback = value;
4628 }
4629
4630 // Save redirect type
4631 save(payload, () => {
4632 $('#aam-login-redirect-overwrite').show();
4633 });
4634 });
4635 });
4636
4637 $('#login-redirect-reset').bind('click', function () {
4638 const _btn = $(this);
4639
4640 $.ajax(getAAM().prepareApiEndpoint(`/redirect/login`), {
4641 type: 'POST',
4642 headers: {
4643 'X-WP-Nonce': getLocal().rest_nonce,
4644 'X-HTTP-Method-Override': 'DELETE'
4645 },
4646 dataType: 'json',
4647 beforeSend: function () {
4648 var label = _btn.text();
4649 _btn.attr('data-original-label', label);
4650 _btn.text(getAAM().__('Resetting...'));
4651 },
4652 success: function () {
4653 getAAM().fetchContent('main');
4654 },
4655 error: function (response) {
4656 getAAM().notification('danger', response, {
4657 request: 'aam/v2/redirect/login',
4658 response
4659 });
4660 },
4661 complete: function () {
4662 _btn.text(_btn.attr('data-original-label'));
4663 }
4664 });
4665 });
4666 }
4667 }
4668
4669 getAAM().addHook('init', initialize);
4670
4671 })(jQuery);
4672
4673 /**
4674 * Logout Redirect Interface
4675 *
4676 * @param {jQuery} $
4677 *
4678 * @returns {void}
4679 */
4680 (function ($) {
4681
4682 /**
4683 *
4684 * @param {type} items
4685 * @param {type} status
4686 * @param {type} successCallback
4687 * @returns {undefined}
4688 */
4689 function save(payload, successCallback) {
4690 getAAM().queueRequest(function () {
4691 $.ajax(getAAM().prepareApiEndpoint('/redirect/logout'), {
4692 type: 'POST',
4693 headers: {
4694 'X-WP-Nonce': getLocal().rest_nonce
4695 },
4696 dataType: 'json',
4697 data: payload,
4698 success: function (response) {
4699 successCallback(response);
4700 },
4701 error: function (response) {
4702 getAAM().notification('danger', response, {
4703 request: 'aam/v2/redirect/logout',
4704 payload,
4705 response
4706 });
4707 }
4708 });
4709 });
4710 }
4711
4712 /**
4713 *
4714 * @returns {undefined}
4715 */
4716 function initialize() {
4717 var container = '#logout_redirect-content';
4718
4719 if ($(container).length) {
4720 $('input[type="radio"]', container).each(function () {
4721 $(this).bind('click', function () {
4722 //hide all fields
4723 $('.logout-redirect-action').hide();
4724
4725 //show the specific one
4726 $($(this).data('action')).show();
4727
4728 // Now, if the login redirect type is default, then
4729 // save the data, otherwise save only when more detail
4730 // provided
4731 const type = $(this).val();
4732
4733 if (type === 'default') {
4734 save({ type }, () => {
4735 $('#aam-logout-redirect-overwrite').show();
4736 });
4737 }
4738 });
4739 });
4740
4741 $('input[type="text"],select', container).each(function () {
4742 $(this).bind('change', function () {
4743 const value = $.trim($(this).val());
4744 const type = $('input[name="logout.redirect.type"]:checked').val();
4745
4746 const payload = {
4747 type
4748 };
4749
4750 if (type === 'page_redirect') {
4751 payload.redirect_page_id = value;
4752 } else if (type === 'url_redirect') {
4753 payload.redirect_url = value;
4754 } else {
4755 payload.callback = value;
4756 }
4757
4758 // Save redirect type
4759 save(payload, () => {
4760 $('#aam-logout-redirect-overwrite').show();
4761 });
4762 });
4763 });
4764
4765 $('#logout-redirect-reset').bind('click', function () {
4766 const _btn = $(this);
4767
4768 $.ajax(getAAM().prepareApiEndpoint(`/redirect/logout`), {
4769 type: 'POST',
4770 headers: {
4771 'X-WP-Nonce': getLocal().rest_nonce,
4772 'X-HTTP-Method-Override': 'DELETE'
4773 },
4774 dataType: 'json',
4775 beforeSend: function () {
4776 var label = _btn.text();
4777 _btn.attr('data-original-label', label);
4778 _btn.text(getAAM().__('Resetting...'));
4779 },
4780 success: function () {
4781 getAAM().fetchContent('main');
4782 },
4783 error: function (response) {
4784 getAAM().notification('danger', response, {
4785 request: 'aam/v2/redirect/logout',
4786 response
4787 });
4788 },
4789 complete: function () {
4790 _btn.text(_btn.attr('data-original-label'));
4791 }
4792 });
4793 });
4794 }
4795 }
4796
4797 getAAM().addHook('init', initialize);
4798
4799 })(jQuery);
4800
4801 /**
4802 * 404 Redirect Interface
4803 *
4804 * @param {jQuery} $
4805 *
4806 * @returns {void}
4807 */
4808 (function ($) {
4809
4810 /**
4811 *
4812 * @param {type} items
4813 * @param {type} status
4814 * @param {type} successCallback
4815 * @returns {undefined}
4816 */
4817 function save(payload, successCallback) {
4818 getAAM().queueRequest(function () {
4819 $.ajax(getAAM().prepareApiEndpoint('/redirect/not-found'), {
4820 type: 'POST',
4821 headers: {
4822 'X-WP-Nonce': getLocal().rest_nonce
4823 },
4824 dataType: 'json',
4825 data: payload,
4826 success: function (response) {
4827 successCallback(response);
4828 },
4829 error: function (response) {
4830 getAAM().notification('danger', response, {
4831 request: '/redirect/not-found',
4832 payload,
4833 response
4834 });
4835 }
4836 });
4837 });
4838 }
4839
4840 /**
4841 *
4842 * @returns {undefined}
4843 */
4844 function initialize() {
4845 var container = '#404redirect-content';
4846
4847 if ($(container).length) {
4848 $('input[type="radio"]', container).each(function () {
4849 $(this).bind('click', function () {
4850 //hide group
4851 $('.404redirect-action').hide();
4852
4853 //show the specific one
4854 $($(this).data('action')).show();
4855
4856 // Now, if the login redirect type is default, then
4857 // save the data, otherwise save only when more detail
4858 // provided
4859 const type = $(this).val();
4860
4861 if (['default', 'login_redirect'].includes(type)) {
4862 save({ type }, () => {
4863 $('#aam-404redirect-overwrite').show();
4864 });
4865 }
4866 });
4867 });
4868
4869 $('input[type="text"],select', container).each(function () {
4870 $(this).bind('change', function () {
4871 const value = $.trim($(this).val());
4872 const type = $('input[name="not_found_redirect_type"]:checked').val();
4873
4874 const payload = {
4875 type
4876 };
4877
4878 if (type === 'page_redirect') {
4879 payload.redirect_page_id = value;
4880 } else if (type === 'url_redirect') {
4881 payload.redirect_url = value;
4882 } else {
4883 payload.callback = value;
4884 }
4885
4886 // Save redirect type
4887 save(payload, () => {
4888 $('#aam-404redirect-overwrite').show();
4889 });
4890 });
4891 });
4892
4893 $('#404redirect-reset').bind('click', function () {
4894 const _btn = $(this);
4895
4896 $.ajax(getAAM().prepareApiEndpoint(`/redirect/not-found`), {
4897 type: 'POST',
4898 headers: {
4899 'X-WP-Nonce': getLocal().rest_nonce,
4900 'X-HTTP-Method-Override': 'DELETE'
4901 },
4902 dataType: 'json',
4903 beforeSend: function () {
4904 var label = _btn.text();
4905 _btn.attr('data-original-label', label);
4906 _btn.text(getAAM().__('Resetting...'));
4907 },
4908 success: function () {
4909 getAAM().fetchContent('main');
4910 },
4911 error: function (response) {
4912 getAAM().notification('danger', response, {
4913 request: '/redirect/not-found',
4914 response
4915 });
4916 },
4917 complete: function () {
4918 _btn.text(_btn.attr('data-original-label'));
4919 }
4920 });
4921 });
4922 }
4923 }
4924
4925 getAAM().addHook('init', initialize);
4926
4927 })(jQuery);
4928
4929 /**
4930 * API Routes Interface
4931 *
4932 * @param {jQuery} $
4933 *
4934 * @returns {void}
4935 */
4936 (function ($) {
4937
4938 /**
4939 *
4940 * @param {type} id
4941 * @param {type} btn
4942 * @returns {undefined}
4943 */
4944 function save(id, btn) {
4945 const is_restricted = $(btn).hasClass('icon-check-empty');
4946
4947 getAAM().queueRequest(function () {
4948 // Show indicator
4949 $(btn).attr('class', 'aam-row-action icon-spin4 animate-spin');
4950
4951 const payload = {
4952 effect: is_restricted ? 'deny' : 'allow'
4953 };
4954
4955 $.ajax(getAAM().prepareApiEndpoint(`/api-route/${id}`), {
4956 type: 'POST',
4957 dataType: 'json',
4958 data: payload,
4959 headers: {
4960 'X-WP-Nonce': getLocal().rest_nonce,
4961 },
4962 success: function () {
4963 $('#aam-route-overwrite').removeClass('hidden');
4964 updateBtn(btn, is_restricted);
4965 },
4966 error: function (response) {
4967 updateBtn(btn, !is_restricted);
4968
4969 getAAM().notification('danger', response, {
4970 request: `/api-route/${id}`,
4971 payload,
4972 response
4973 });
4974 }
4975 });
4976 });
4977 }
4978
4979 /**
4980 *
4981 * @param {type} btn
4982 * @param {type} value
4983 * @returns {undefined}
4984 */
4985 function updateBtn(btn, value) {
4986 if (value) {
4987 $(btn).attr('class', 'aam-row-action text-danger icon-check');
4988 } else {
4989 $(btn).attr('class', 'aam-row-action text-muted icon-check-empty');
4990 }
4991 }
4992
4993 /**
4994 *
4995 * @param {*} text
4996 * @returns
4997 */
4998 function escapeHtml(text) {
4999 var map = {
5000 '&': '&amp;',
5001 '<': '&lt;',
5002 '>': '&gt;',
5003 '"': '&quot;',
5004 "'": '&#039;'
5005 };
5006
5007 return text.replace(/[&<>"']/g, function(m) { return map[m]; });
5008 }
5009
5010 /**
5011 *
5012 * @returns {undefined}
5013 */
5014 function initialize() {
5015 if ($('#route-content').length) {
5016 //initialize the role list table
5017 $('#route-list').DataTable({
5018 autoWidth: false,
5019 ordering: false,
5020 pagingType: 'simple',
5021 serverSide: false,
5022 ajax: {
5023 url: getAAM().prepareApiEndpoint(`/api-routes`),
5024 type: 'GET',
5025 headers: {
5026 'X-WP-Nonce': getLocal().rest_nonce
5027 },
5028 dataType: 'json',
5029 dataSrc: function (routes) {
5030 // Transform the received data into DT format
5031 const data = [];
5032
5033 $.each(routes, (_, route) => {
5034 data.push([
5035 route.id,
5036 route.method,
5037 escapeHtml(route.endpoint),
5038 route.is_restricted ? 'checked' : 'unchecked'
5039 ]);
5040 });
5041
5042 return data;
5043 }
5044 },
5045 columnDefs: [
5046 { visible: false, targets: [0] },
5047 { className: 'text-center', targets: [0, 1] }
5048 ],
5049 language: {
5050 search: '_INPUT_',
5051 searchPlaceholder: getAAM().__('Search'),
5052 info: getAAM().__('_TOTAL_ route(s)'),
5053 infoFiltered: '',
5054 emptyTable: getAAM().__('No API endpoints found. You might have APIs disabled.'),
5055 infoEmpty: getAAM().__('Nothing to show'),
5056 lengthMenu: '_MENU_'
5057 },
5058 createdRow: function (row, data) {
5059 // decorate the method
5060 var method = $('<span/>', {
5061 'class': 'aam-api-method ' + data[1].toLowerCase()
5062 }).text(data[1]);
5063
5064 $('td:eq(0)', row).html(method);
5065
5066 var actions = data[3].split(',');
5067
5068 var container = $('<div/>', { 'class': 'aam-row-actions' });
5069 $.each(actions, function (i, action) {
5070 switch (action) {
5071 case 'unchecked':
5072 $(container).append($('<i/>', {
5073 'class': 'aam-row-action text-muted icon-check-empty'
5074 }).bind('click', function () {
5075 save(data[0], this);
5076 }));
5077 break;
5078
5079 case 'checked':
5080 $(container).append($('<i/>', {
5081 'class': 'aam-row-action text-danger icon-check'
5082 }).bind('click', function () {
5083 save(data[0], this);
5084 }));
5085 break;
5086
5087 default:
5088 break;
5089 }
5090 });
5091 $('td:eq(2)', row).html(container);
5092 }
5093 });
5094
5095 // Reset button
5096 $('#route-reset').bind('click', function () {
5097 const _btn = $(this);
5098
5099 $.ajax(getAAM().prepareApiEndpoint(`/api-routes`), {
5100 type: 'POST',
5101 headers: {
5102 'X-WP-Nonce': getLocal().rest_nonce,
5103 'X-HTTP-Method-Override': 'DELETE'
5104 },
5105 dataType: 'json',
5106 beforeSend: function () {
5107 var label = _btn.text();
5108 _btn.attr('data-original-label', label);
5109 _btn.text(getAAM().__('Resetting...'));
5110 },
5111 success: function () {
5112 getAAM().fetchContent('main');
5113 },
5114 error: function (response) {
5115 getAAM().notification('danger', response, {
5116 request: '/api-routes',
5117 response
5118 });
5119 },
5120 complete: function () {
5121 _btn.text(_btn.attr('data-original-label'));
5122 }
5123 });
5124 });
5125
5126 $('[data-toggle="toggle"]', '#route-content').bootstrapToggle();
5127
5128 getAAM().triggerHook('init-api-route');
5129 }
5130 }
5131
5132 getAAM().addHook('init', initialize);
5133
5134 })(jQuery);
5135
5136 /**
5137 * URL Interface
5138 *
5139 * @param {jQuery} $
5140 *
5141 * @returns {void}
5142 */
5143 (function ($) {
5144
5145 /**
5146 *
5147 * @param {*} rule
5148 */
5149 function ResetUrlManageForm(rule = null) {
5150 // Clearing all values and resetting the form to default
5151 $('.form-clearable', '#uri-model').val('');
5152 $('.aam-uri-access-action').hide();
5153 $('#url_save_btn').removeAttr('data-url-id');
5154 $('input[type="radio"]', '#uri-model').prop('checked', false);
5155 $('#uri-model').modal('show');
5156
5157 // If rule is provided, populating the values
5158 if (rule !== null) {
5159 $('#url_save_btn').attr('data-url-id', encodeURI(rule.id));
5160
5161 // Settings edit form attributes
5162 $('#url_rule_url').val(rule.url_schema);
5163
5164 let restriction_type = rule.effect === 'allow' ? 'allow' : 'deny';
5165 let http_status_code = null;
5166
5167 if (rule.redirect !== undefined) {
5168 restriction_type = rule.redirect.type;
5169 http_status_code = rule.redirect.http_status_code;
5170 }
5171
5172 $(`#url_access_${restriction_type}`, '#uri-model').prop(
5173 'checked', true
5174 ).trigger('click');
5175
5176 if (restriction_type === 'custom_message') {
5177 $('#url_access_custom_message_value').val(
5178 rule.redirect.message
5179 );
5180 } else if (restriction_type === 'page_redirect') {
5181 $('#url_access_page_redirect_value').val(
5182 rule.redirect.redirect_page_id
5183 );
5184 } else if (restriction_type === 'url_redirect') {
5185 $('#url_access_url_redirect_value').val(
5186 rule.redirect.redirect_url
5187 );
5188 } else if (restriction_type === 'trigger_callback') {
5189 $('#url_access_trigger_callback_value').val(
5190 rule.redirect.callback
5191 );
5192 }
5193
5194 $('#url_access_http_redirect_code').val(http_status_code);
5195 }
5196
5197 getAAM().triggerHook('aam-reset-url-manage-form', {
5198 container: $('#uri-model'),
5199 rule
5200 });
5201 }
5202 /**
5203 *
5204 */
5205 function initialize() {
5206 const container = '#url-content';
5207
5208 if ($(container).length) {
5209 $('input[name="uri.access.type"]', container).each(function () {
5210 $(this).bind('click', function () {
5211 const type = $(this).val();
5212
5213 $('.aam-uri-access-action').hide();
5214 $(`#url_access_${type}_attrs`).show();
5215
5216 if (['page_redirect', 'url_redirect'].includes(type)) {
5217 $('#url_access_http_status_code').show();
5218 }
5219 });
5220 });
5221
5222 // Reset button
5223 $('#uri-reset').bind('click', function () {
5224 const _btn = $(this);
5225
5226 $.ajax(getAAM().prepareApiEndpoint(`/urls`), {
5227 type: 'POST',
5228 headers: {
5229 'X-WP-Nonce': getLocal().rest_nonce,
5230 'X-HTTP-Method-Override': 'DELETE'
5231 },
5232 dataType: 'json',
5233 beforeSend: function () {
5234 var label = _btn.text();
5235 _btn.attr('data-original-label', label);
5236 _btn.text(getAAM().__('Resetting...'));
5237 },
5238 success: function () {
5239 getAAM().fetchContent('main');
5240 },
5241 error: function (response) {
5242 getAAM().notification('danger', response, {
5243 request: 'aam/v2/urls',
5244 response
5245 });
5246 },
5247 complete: function () {
5248 _btn.text(_btn.attr('data-original-label'));
5249 }
5250 });
5251 });
5252
5253 $('#url_save_btn').bind('click', function (event) {
5254 event.preventDefault();
5255
5256 const url_schema = $('#url_rule_url').val();
5257 const code = $('#url_access_http_redirect_code').val();
5258 const type = $('input[name="uri.access.type"]:checked').val();
5259
5260 const editing_url = $(this).attr('data-url-id');
5261
5262 if (url_schema && type) {
5263 // Preparing the payload
5264 const payload = {
5265 effect: type === 'allow' ? 'allow' : 'deny',
5266 url_schema
5267 }
5268
5269 if (type === 'custom_message') {
5270 payload.redirect = {
5271 type,
5272 message: $.trim(
5273 $('#url_access_custom_message_value').val()
5274 )
5275 }
5276 } else if (type === 'page_redirect') {
5277 payload.redirect = {
5278 type,
5279 redirect_page_id: parseInt(
5280 $('#url_access_page_redirect_value').val(), 10
5281 )
5282 }
5283 } else if (type === 'url_redirect') {
5284 payload.redirect = {
5285 type,
5286 redirect_url: $.trim(
5287 $('#url_access_url_redirect_value').val()
5288 )
5289 }
5290 } else if (type === 'trigger_callback') {
5291 payload.redirect = {
5292 type,
5293 callback: $.trim(
5294 $('#url_access_trigger_callback_value').val()
5295 )
5296 }
5297 } else if (type === 'login_redirect') {
5298 payload.redirect = {
5299 type
5300 }
5301 }
5302
5303 if (code
5304 && ['page_redirect', 'url_redirect'].includes(type)
5305 ) {
5306 payload.redirect.http_status_code = parseInt(code, 10);
5307 }
5308
5309 let endpoint = `/url`;
5310
5311 if (editing_url) {
5312 endpoint += '/' + editing_url;
5313 } else {
5314 endpoint += 's'
5315 }
5316
5317 $.ajax(getAAM().prepareApiEndpoint(endpoint), {
5318 type: 'POST',
5319 contentType: 'application/json',
5320 dataType: 'json',
5321 data: JSON.stringify(
5322 getAAM().applyFilters('aam-url-access-payload', payload)
5323 ),
5324 headers: {
5325 'X-WP-Nonce': getLocal().rest_nonce
5326 },
5327 beforeSend: function () {
5328 $('#url_save_btn').text(
5329 getAAM().__('Saving...')
5330 ).attr('disabled', true);
5331 },
5332 success: function () {
5333 $('#uri-list').DataTable().ajax.reload();
5334 $('#aam-uri-overwrite').show();
5335 },
5336 error: function (response) {
5337 getAAM().notification('danger', response, {
5338 request: endpoint,
5339 payload,
5340 response
5341 });
5342 },
5343 complete: function () {
5344 $('#uri-model').modal('hide');
5345 $('#url_save_btn')
5346 .text(getAAM().__('Save'))
5347 .attr('disabled', false);
5348 }
5349 });
5350 }
5351 });
5352
5353 $('#uri-delete-btn').bind('click', function (event) {
5354 event.preventDefault();
5355
5356 const url = $('#uri-delete-btn').attr('data-url-id');
5357
5358 $.ajax(getAAM().prepareApiEndpoint(`/url/${url}`), {
5359 type: 'POST',
5360 dataType: 'json',
5361 headers: {
5362 'X-WP-Nonce': getLocal().rest_nonce,
5363 'X-HTTP-Method-Override': 'DELETE'
5364 },
5365 beforeSend: function () {
5366 $('#uri-delete-btn').text(
5367 getAAM().__('Deleting...')
5368 ).attr('disabled', true);
5369 },
5370 success: function () {
5371 $('#uri-list').DataTable().ajax.reload();
5372 },
5373 error: function (response) {
5374 getAAM().notification('danger', response, {
5375 request: `aam/v2/url/${url}`,
5376 response
5377 });
5378 },
5379 complete: function () {
5380 $('#uri-delete-model').modal('hide');
5381 $('#uri-delete-btn').text(
5382 getAAM().__('Delete')
5383 ).attr('disabled', false);
5384 }
5385 });
5386 });
5387
5388 $('#uri-list').DataTable({
5389 autoWidth: false,
5390 ordering: false,
5391 dom: 'ftrip',
5392 pagingType: 'simple',
5393 processing: true,
5394 stateSave: true,
5395 serverSide: false,
5396 ajax: {
5397 url: getAAM().prepareApiEndpoint(`/urls`),
5398 type: 'GET',
5399 headers: {
5400 'X-WP-Nonce': getLocal().rest_nonce
5401 },
5402 dataType: 'json',
5403 dataSrc: function (json) {
5404 // Transform the received data into DT format
5405 const data = [];
5406
5407 $.each(json, (_, rule) => {
5408 const actions = ['edit'];
5409
5410 if (rule.is_customized) {
5411 actions.push('delete');
5412 } else {
5413 actions.push('no-delete');
5414 }
5415
5416 let restriction_type = null;
5417
5418 if (rule.effect === 'allow') {
5419 restriction_type = 'allow';
5420 } else if (rule.redirect) {
5421 restriction_type = rule.redirect.type;
5422 } else {
5423 restriction_type = 'deny';
5424 }
5425
5426 data.push([
5427 rule.url_schema,
5428 restriction_type,
5429 actions,
5430 rule
5431 ]);
5432 });
5433
5434 return data;
5435 },
5436 },
5437 language: {
5438 search: '_INPUT_',
5439 searchPlaceholder: getAAM().__('Search'),
5440 info: getAAM().__('_TOTAL_ URL(s)'),
5441 infoFiltered: ''
5442 },
5443 columnDefs: [
5444 { visible: false, targets: [3] }
5445 ],
5446 initComplete: function () {
5447 var create = $('<a/>', {
5448 'href': '#',
5449 'class': 'btn btn-primary'
5450 }).html('<i class="icon-plus"></i> ' + getAAM().__('Create'))
5451 .bind('click', function () {
5452 ResetUrlManageForm();
5453 });
5454
5455 $('.dataTables_filter', '#uri-list_wrapper').append(create);
5456 },
5457 createdRow: function (row, data) {
5458 const container = $(
5459 '<div/>', { 'class': 'aam-row-actions' }
5460 );
5461
5462 $.each(data[2], function (i, action) {
5463 switch (action) {
5464 case 'edit':
5465 $(container).append($('<i/>', {
5466 'class': 'aam-row-action icon-pencil text-warning'
5467 }).bind('click', function () {
5468 ResetUrlManageForm(data[3]);
5469 }).attr({
5470 'data-toggle': "tooltip",
5471 'title': getAAM().__('Edit Rule')
5472 }));
5473 break;
5474
5475 case 'no-edit':
5476 $(container).append($('<i/>', {
5477 'class': 'aam-row-action icon-pencil text-muted'
5478 }).attr({
5479 'data-toggle': "tooltip",
5480 'title': getAAM().__('Inherited')
5481 }));
5482 break;
5483
5484 case 'delete':
5485 $(container).append($('<i/>', {
5486 'class': 'aam-row-action icon-trash-empty text-danger'
5487 }).bind('click', function () {
5488 $('#uri-delete-btn').attr(
5489 'data-url-id', encodeURI(data[3].id)
5490 );
5491 $('#uri-delete-model').modal('show');
5492 }).attr({
5493 'data-toggle': "tooltip",
5494 'title': getAAM().__('Delete Rule')
5495 }));
5496 break;
5497
5498 case 'no-delete':
5499 $(container).append($('<i/>', {
5500 'class': 'aam-row-action icon-trash-empty text-muted'
5501 }).attr({
5502 'data-toggle': "tooltip",
5503 'title': getAAM().__('Inherited')
5504 }));
5505 break;
5506
5507 default:
5508 break;
5509 }
5510 });
5511
5512 // Decorate the type of access
5513 var type = $('<span/>');
5514
5515 switch(data[1]) {
5516 case 'allow':
5517 type.html(getAAM().__('Allowed'));
5518 type.attr('class', 'badge success');
5519 break;
5520
5521 case 'deny':
5522 case 'custom_message':
5523 type.html(getAAM().__('Denied'));
5524 type.attr('class', 'badge danger');
5525 break;
5526
5527 case 'login_redirect':
5528 case 'page_redirect':
5529 case 'url_redirect':
5530 type.html(getAAM().__('Redirected'));
5531 type.attr('class', 'badge redirect');
5532 break;
5533
5534 case 'trigger_callback':
5535 type.html(getAAM().__('Callback'));
5536 type.attr('class', 'badge callback');
5537 break;
5538
5539 default:
5540 getAAM().triggerHook('aam-decorate-url-rule', {
5541 badge: type,
5542 rule: data[3]
5543 });
5544 break;
5545 }
5546
5547 $('td:eq(2)', row).html(container);
5548 $('td:eq(1)', row).html(type);
5549 }
5550 });
5551 }
5552 }
5553
5554 getAAM().addHook('init', initialize);
5555 })(jQuery);
5556
5557 /**
5558 * Users & Roles (aka Identity) Interface
5559 *
5560 * @param {jQuery} $
5561 *
5562 * @returns {void}
5563 */
5564 (function ($) {
5565
5566 const current_selections = {
5567 identity_type: 'role',
5568 identity_id: null,
5569 re_init: false
5570 };
5571
5572 /**
5573 *
5574 * @param {*} permission
5575 * @param {*} is_denied
5576 */
5577 function SavePermission(permission, is_denied) {
5578 if (current_selections.re_init === false) {
5579 getAAM().queueRequest(function () {
5580 const endpoint = `/identity/${current_selections.identity_type}/${current_selections.identity_id}/${permission}`;
5581
5582 $.ajax(getAAM().prepareApiEndpoint(endpoint), {
5583 type: 'POST',
5584 contentType: 'application/json',
5585 dataType: 'json',
5586 data: JSON.stringify({
5587 effect: is_denied ? 'deny' : 'allow'
5588 }),
5589 headers: {
5590 'X-WP-Nonce': getLocal().rest_nonce
5591 },
5592 success: function (response) {
5593 $(`#aam_${current_selections.identity_type}_identity_overwrite`).removeClass('hidden');
5594 $(`#${current_selections.identity_type}_identity_list`).DataTable().ajax.reload(null, false);
5595
5596 getAAM().triggerHook('identity-permission-saved', {
5597 current_selections,
5598 permissions: response
5599 });
5600 },
5601 error: function (response) {
5602 getAAM().notification('danger', response, {
5603 request: endpoint,
5604 payload: {
5605 effect: is_denied ? 'deny' : 'allow'
5606 },
5607 response
5608 });
5609 }
5610 });
5611 });
5612 }
5613 }
5614
5615 /**
5616 *
5617 * @param {*} cb
5618 */
5619 function ResetPermissions(cb) {
5620 getAAM().queueRequest(function () {
5621 const endpoint = `/identity/${current_selections.identity_type}/${current_selections.identity_id}`;
5622
5623 $.ajax(getAAM().prepareApiEndpoint(endpoint), {
5624 type: 'POST',
5625 contentType: 'application/json',
5626 dataType: 'json',
5627 headers: {
5628 'X-WP-Nonce': getLocal().rest_nonce,
5629 'X-HTTP-Method-Override': 'DELETE'
5630 },
5631 error: function (response) {
5632 getAAM().notification('danger', response, {
5633 request: endpoint,
5634 response
5635 });
5636 },
5637 complete: function() {
5638 cb();
5639
5640 getAAM().triggerHook('identity-permission-reset', {
5641 current_selections
5642 });
5643 }
5644 });
5645 });
5646 }
5647
5648 /**
5649 *
5650 * @param {*} container
5651 * @param {*} type
5652 * @param {*} id
5653 */
5654 function InitializePermissionForm(container, type, id, cb = null) {
5655 // Initialize the permissions
5656 current_selections.re_init = true;
5657 current_selections.identity_type = type;
5658 current_selections.identity_id = id;
5659
5660 getAAM().queueRequest(function () {
5661 $.ajax(getAAM().prepareApiEndpoint(`/identity/${type}/${id}`), {
5662 type: 'GET',
5663 headers: {
5664 'X-WP-Nonce': $.aam.getLocal().rest_nonce
5665 },
5666 success: function (response) {
5667 $(`${container} input[type="checkbox"]`).prop(
5668 'checked', false
5669 ).trigger('change');
5670
5671 $.each(response.permissions, function(permission, c) {
5672 if (c.effect === 'deny') {
5673 $(`${container} input[name="${permission}"]`).prop(
5674 'checked', true
5675 ).trigger('change');
5676 }
5677 });
5678
5679 if (response.is_customized) {
5680 $('.aam-overwrite', container).removeClass('hidden');
5681 } else {
5682 $('.aam-overwrite', container).addClass('hidden');
5683 }
5684
5685 current_selections.re_init = false;
5686
5687 $(`#${type}_identity_list_wrapper`).addClass('hidden');
5688 $(container).addClass('active');
5689 },
5690 error: function (response) {
5691 $.aam.notification('danger', response);
5692 },
5693 complete: function() {
5694 if (cb) {
5695 cb();
5696 }
5697 }
5698 });
5699 });
5700 }
5701
5702 /**
5703 *
5704 */
5705 function initialize() {
5706 const container = '#identity-content';
5707
5708 if ($(container).length) {
5709 $('[data-toggle="toggle"]', '#identity-content').bootstrapToggle();
5710
5711 $('.aam-identity-go-back').bind('click', function() {
5712 const type = current_selections.identity_type;
5713
5714 $(`#${type}_identity_list_wrapper`).removeClass('hidden');
5715 $(`#aam_${type}_permissions_form`).removeClass('active');
5716
5717 getAAM().triggerHook('user-identity-go-back', {
5718 current_selections
5719 });
5720 });
5721
5722 $('.aam-identity-reset').bind('click', function() {
5723 const btn = $(this);
5724
5725 btn.text(getAAM().__('Resetting...')).prop('disabled', true);
5726
5727 ResetPermissions(function() {
5728 btn.text(getAAM().__('Reset to default')).prop('disabled', false);
5729 $('.aam-identity-overwrite').addClass('hidden');
5730 $('.aam-identity-go-back').trigger('click');
5731 });
5732 });
5733
5734 const identity_types_filter = $('<select>').attr({
5735 'class': 'form-control input-sm aam-ml-1 aam-max-width aam-identity-type'
5736 }).bind('change', function () {
5737 $('#identity_list_container > .dataTables_wrapper').addClass('hidden');
5738
5739 current_selections.identity_type = $(this).val() || 'role';
5740
5741 $(`#${current_selections.identity_type}_identity_list_wrapper`).removeClass('hidden');
5742
5743 $('.aam-identity-type').val(current_selections.identity_type);
5744 });
5745
5746 const types = getAAM().applyFilters('aam-identity-types', [
5747 { key: '', label: getAAM().__('Identity Types') },
5748 { key: 'role', label: getAAM().__('Roles') },
5749 { key: 'user', label: getAAM().__('Users') },
5750 ]);
5751
5752 $.each(types, (_, type) => {
5753 identity_types_filter.append(
5754 `<option value="${type.key}">${type.label}</option>`
5755 );
5756 });
5757
5758 $('#user_identity_list').DataTable({
5759 autoWidth: false,
5760 ordering: false,
5761 stateSave: true,
5762 pagingType: 'simple',
5763 serverSide: true,
5764 processing: true,
5765 ajax: function(filters, cb) {
5766 $.ajax({
5767 url: getAAM().prepareApiEndpoint('/identity/users'),
5768 type: 'GET',
5769 headers: {
5770 'X-WP-Nonce': getLocal().rest_nonce
5771 },
5772 data: {
5773 search: filters.search.value,
5774 per_page: filters.length,
5775 offset: filters.start
5776 },
5777 success: function (response) {
5778 const result = {
5779 data: [],
5780 recordsTotal: 0,
5781 recordsFiltered: 0
5782 };
5783
5784 $.each(response.list, (_, user) => {
5785 result.data.push([
5786 user.id,
5787 user.display_name,
5788 '',
5789 user
5790 ]);
5791 });
5792
5793 result.recordsTotal = response.summary.total_count;
5794 result.recordsFiltered = response.summary.filtered_count;
5795
5796 cb(result);
5797 }
5798 });
5799 },
5800 columnDefs: [
5801 { visible: false, targets: [0, 3] }
5802 ],
5803 language: {
5804 search: '_INPUT_',
5805 searchPlaceholder: getAAM().__('Search user'),
5806 info: getAAM().__('_TOTAL_ user(s)'),
5807 infoFiltered: '',
5808 lengthMenu: '_MENU_'
5809 },
5810 initComplete: function () {
5811 $('#user_identity_list_length').append(
5812 $(identity_types_filter).clone(true)
5813 );
5814
5815 // Determine btn color
5816 const btn_class = $('#user_identity_list').data('has-default') ? 'btn-warning' : 'btn-primary';
5817
5818 $('#user_identity_list_wrapper > .row:eq(0)').after(`
5819 <div class="row"><div class="col-sm-12"><table class="table table-bordered no-margin-bottom">
5820 <tbody>
5821 <tr class="aam-info">
5822 <td class="text-left"><b>Premium Feature.</b> Set default permissions for all users effortlessly. Each user will automatically inherit these predefined permissions, with the flexibility to customize and override them individually as needed.</td>
5823 <td class="text-center">
5824 <a href="#" class="btn btn-xs ${btn_class}" disabled id="set_default_user_permissions">Set Permissions</a>
5825 </td>
5826 </tr>
5827 </tbody>
5828 </table></div></div>
5829 `);
5830
5831 getAAM().triggerHook('user-identity-table-initialized', {
5832 current_selections,
5833 api: {
5834 InitializePermissionForm
5835 }
5836 });
5837 },
5838 createdRow: function (row, data) {
5839 var container = $('<div/>', { 'class': 'aam-row-actions' });
5840
5841 $(container).append($('<i/>', {
5842 'class': 'aam-row-action icon-cog ' + (data[3].is_customized ? 'aam-access-overwritten' : 'text-info')
5843 }).bind('click', function () {
5844 // Initialize the permissions
5845 InitializePermissionForm(
5846 '#aam_user_permissions_form',
5847 'user',
5848 data[0]
5849 );
5850 }).attr({
5851 'data-toggle': "tooltip",
5852 'title': getAAM().__('Manage User Permissions')
5853 }));
5854
5855 $('td:eq(1)', row).html(container);
5856 }
5857 });
5858
5859 $('#role_identity_list').DataTable({
5860 autoWidth: false,
5861 ordering: false,
5862 pagingType: 'simple',
5863 processing: true,
5864 stateSave: true,
5865 serverSide: false,
5866 ajax: {
5867 url: getAAM().prepareApiEndpoint('/identity/roles'),
5868 type: 'GET',
5869 headers: {
5870 'X-WP-Nonce': getLocal().rest_nonce
5871 },
5872 dataType: 'json',
5873 dataSrc: function (json) {
5874 // Transform the received data into DT format
5875 const data = [];
5876
5877 $.each(json, (_, role) => {
5878 data.push([
5879 role.id,
5880 role.name,
5881 '',
5882 role
5883 ])
5884 });
5885
5886 return data;
5887 },
5888 },
5889 columnDefs: [
5890 { visible: false, targets: [0, 3] },
5891 ],
5892 language: {
5893 search: '_INPUT_',
5894 searchPlaceholder: getAAM().__('Search role'),
5895 info: getAAM().__('_TOTAL_ role(s)'),
5896 infoFiltered: '',
5897 lengthMenu: '_MENU_'
5898 },
5899 initComplete: function () {
5900 $('#role_identity_list_length').append(
5901 $(identity_types_filter).clone(true)
5902 );
5903
5904 // Determine btn color
5905 const btn_class = $('#role_identity_list').data('has-default') ? 'btn-warning' : 'btn-primary';
5906
5907 $('#role_identity_list_wrapper > .row:eq(0)').after(`
5908 <div class="row"><div class="col-sm-12"><table class="table table-bordered no-margin-bottom">
5909 <tbody>
5910 <tr class="aam-info">
5911 <td class="text-left"><b>Premium Feature.</b> Set default permissions for all roles effortlessly. Roles will automatically inherit these predefined permissions, with the flexibility to customize and override them individually as needed.</td>
5912 <td class="text-center">
5913 <a href="#" class="btn btn-xs ${btn_class}" disabled id="set_default_role_permissions">Set Permissions</a>
5914 </td>
5915 </tr>
5916 </tbody>
5917 </table></div></div>
5918 `);
5919
5920 getAAM().triggerHook('role-identity-table-initialized', {
5921 current_selections,
5922 api: {
5923 InitializePermissionForm
5924 }
5925 });
5926 },
5927 createdRow: function (row, data) {
5928 var container = $('<div/>', { 'class': 'aam-row-actions' });
5929
5930 $(container).append($('<i/>', {
5931 'class': 'aam-row-action icon-cog ' + (data[3].is_customized ? 'aam-access-overwritten' : 'text-info')
5932 }).bind('click', function () {
5933 InitializePermissionForm(
5934 '#aam_role_permissions_form',
5935 'role',
5936 data[0]
5937 );
5938 }).attr({
5939 'data-toggle': "tooltip",
5940 'title': getAAM().__('Manage Role Permissions')
5941 }));
5942
5943 $('td:eq(1)', row).html(container);
5944 }
5945 });
5946
5947 $('#identity_list_container > .dataTables_wrapper').addClass('hidden');
5948 $('#role_identity_list_wrapper').removeClass('hidden');
5949
5950 // Initialize the permission settings
5951 $('#identity_list_container input[type="checkbox"]').each(function() {
5952 $(this).bind('change', function() {
5953 SavePermission(
5954 $(this).attr('name'),
5955 $(this).prop('checked')
5956 );
5957 });
5958 });
5959 }
5960 }
5961
5962 getAAM().addHook('init', initialize);
5963 })(jQuery);
5964
5965 /**
5966 * JWT Interface
5967 *
5968 * @param {jQuery} $
5969 *
5970 * @returns {void}
5971 */
5972 (function ($) {
5973
5974 /**
5975 * Delete token
5976 *
5977 * @param {String} id
5978 * @param {Callback} before_cb
5979 * @param {Callback} after_cb
5980 *
5981 * @returns {Void}
5982 */
5983 function DeleteToken(id, cb) {
5984 const payload = {
5985 user_id: getAAM().getSubject().id
5986 };
5987
5988 $.ajax(`${getLocal().rest_base}aam/v2/jwt/${id}`, {
5989 type: 'POST',
5990 dataType: 'json',
5991 data: payload,
5992 headers: {
5993 'X-WP-Nonce': getLocal().rest_nonce,
5994 'X-HTTP-Method-Override': 'DELETE'
5995 },
5996 success: function () {
5997 cb();
5998 },
5999 error: function (response) {
6000 getAAM().notification('danger', response, {
6001 request: `aam/v2/jwt/${id}`,
6002 payload,
6003 response
6004 });
6005 }
6006 });
6007 }
6008
6009 /**
6010 *
6011 */
6012 function initialize() {
6013 var container = '#jwt-content';
6014
6015 if ($(container).length) {
6016 $('#jwt-expiration-datapicker').datetimepicker({
6017 icons: {
6018 time: "icon-clock",
6019 date: "icon-calendar",
6020 up: "icon-angle-up",
6021 down: "icon-angle-down",
6022 previous: "icon-angle-left",
6023 next: "icon-angle-right"
6024 },
6025 minDate: new Date(),
6026 inline: true,
6027 sideBySide: true
6028 });
6029
6030 let jwtClaimsEditor;
6031
6032 const tomorrow = new Date();
6033 tomorrow.setDate(tomorrow.getDate() + 1);
6034
6035 $('#create-jwt-modal').on('show.bs.modal', function () {
6036 try {
6037 $('#jwt-expiration-datapicker').data('DateTimePicker').defaultDate(
6038 tomorrow
6039 );
6040 $('#jwt-expires').val(tomorrow.toISOString());
6041
6042 $('#aam-jwt-claims-editor').val('{}');
6043
6044 if (!$('#aam-jwt-claims-editor').next().hasClass('CodeMirror')) {
6045 jwtClaimsEditor = wp.CodeMirror.fromTextArea(
6046 document.getElementById("aam-jwt-claims-editor"),
6047 {
6048 type: 'application/json'
6049 }
6050 );
6051 }
6052 } catch (e) {
6053 // do nothing. Prevent from any kind of corrupted data
6054 }
6055 });
6056
6057 $('#jwt-expiration-datapicker').on('dp.change', function (res) {
6058 $('#jwt-expires').val(res.date.toISOString());
6059 });
6060
6061 // Prepare the URL endpoint
6062 let url = `${getLocal().rest_base}aam/v2/jwts`;
6063 url += `?user_id=${getAAM().getSubject().id}&fields=claims,signed_url`;
6064
6065 $('#jwt-list').DataTable({
6066 autoWidth: false,
6067 ordering: true,
6068 dom: 'ftrip',
6069 pagingType: 'simple',
6070 processing: true,
6071 stateSave: false,
6072 serverSide: false,
6073 ajax: {
6074 url,
6075 type: 'GET',
6076 headers: {
6077 'X-WP-Nonce': getLocal().rest_nonce
6078 },
6079 dataType: 'json',
6080 dataSrc: function (tokens) {
6081 // Transform the received data into DT format
6082 const data = [];
6083
6084 $.each(tokens, (_, token) => {
6085 let details;
6086
6087 if (token.is_valid) {
6088 details = 'Expires On: ' + (new Date(token.claims.exp * 1000)).toDateString()
6089 } else {
6090 details = 'Invalid Token: ' + token.error;
6091 }
6092
6093 data.push([
6094 token.id,
6095 token.token,
6096 token.signed_url || '',
6097 token.is_valid,
6098 details,
6099 'view,delete',
6100 token.description || ''
6101 ]);
6102 });
6103
6104 return data;
6105 }
6106 },
6107 language: {
6108 search: '_INPUT_',
6109 searchPlaceholder: getAAM().__('Search'),
6110 info: getAAM().__('_TOTAL_ token(s)'),
6111 infoFiltered: '',
6112 emptyTable: getAAM().__('No JWT tokens have been generated.'),
6113 infoEmpty: getAAM().__('Nothing to show'),
6114 lengthMenu: '_MENU_'
6115 },
6116 columnDefs: [
6117 { visible: false, targets: [0, 1, 2, 6] },
6118 { orderable: false, targets: [0, 1, 2, 3, 5] }
6119 ],
6120 initComplete: function () {
6121 var create = $('<a/>', {
6122 'href': '#',
6123 'class': 'btn btn-primary'
6124 }).html('<i class="icon-plus"></i> ' + getAAM().__('Create'))
6125 .bind('click', function () {
6126 $('#create-jwt-modal').modal('show');
6127 });
6128
6129 $('.dataTables_filter', '#jwt-list_wrapper').append(create);
6130 },
6131 createdRow: function (row, data) {
6132 // Render status
6133 if (data[3] === true) {
6134 $('td:eq(0)', row).html(
6135 '<i class="icon-ok-circled text-success"></i>'
6136 );
6137 } else {
6138 $('td:eq(0)', row).html(
6139 '<i class="icon-cancel-circled text-danger"></i>'
6140 );
6141 }
6142
6143 // Prepare Token details
6144 const details = [ data[0] ]; // JTI
6145
6146 if (data[6]) {
6147 details.push(`<small><strong>${data[6]}</strong></small>`); // Description
6148 }
6149
6150 details.push(`<small>${data[4]}</small>`); // Status
6151
6152 $('td:eq(1)', row).html(details.join('<br/>'));
6153
6154 var actions = data[5].split(',');
6155
6156 var container = $('<div/>', { 'class': 'aam-row-actions' });
6157 $.each(actions, function (i, action) {
6158 switch (action) {
6159 case 'delete':
6160 $(container).append($('<i/>', {
6161 'class': 'aam-row-action icon-trash-empty text-danger'
6162 }).bind('click', function () {
6163 if (data[3]) {
6164 $('#jwt-delete-btn').attr('data-id', data[0]);
6165 $('#delete-jwt-modal').modal('show');
6166 } else {
6167 $(this).attr(
6168 'class', 'aam-row-action icon-spin4 animate-spin'
6169 );
6170
6171 DeleteToken(data[0], () => {
6172 $('#jwt-list').DataTable().ajax.reload();
6173 })
6174 }
6175 }).attr({
6176 'data-toggle': "tooltip",
6177 'title': getAAM().__('Delete Token')
6178 }));
6179 break;
6180
6181 case 'view':
6182 $(container).append($('<i/>', {
6183 'class': 'aam-row-action icon-eye text-success'
6184 }).bind('click', function () {
6185 $('#view-jwt-token').val(data[1]);
6186
6187 if (data[2] !== '') {
6188 $('#view-jwt-url').val(data[2]);
6189 $('#jwt-passwordless-url-container').removeClass('hidden');
6190 } else {
6191 $('#jwt-passwordless-url-container').addClass('hidden');
6192 }
6193
6194 $('#view-jwt-modal').modal('show');
6195 }).attr({
6196 'data-toggle': "tooltip",
6197 'title': getAAM().__('View Token')
6198 }));
6199 break;
6200
6201 default:
6202 break;
6203 }
6204 });
6205 $('td:eq(2)', row).html(container);
6206 }
6207 });
6208
6209 $('#create-jwt-btn').bind('click', function () {
6210 // Preparing the payload
6211 const payload = {
6212 user_id: getAAM().getSubject().id,
6213 is_refreshable: $('#jwt-refreshable').is(':checked'),
6214 expires_at: $('#jwt-expires').val(),
6215 description: $('#aam-jwt-token-description').val()
6216 }
6217
6218 try {
6219 const claims = JSON.parse(jwtClaimsEditor.getValue());
6220
6221 if (Object.keys(claims).length > 0) {
6222 payload.additional_claims = JSON.stringify(claims);
6223 }
6224 } catch (e) {
6225 console.log(e);
6226 }
6227
6228 $.ajax(`${getLocal().rest_base}aam/v2/jwts?fields=token,signed_url`, {
6229 type: 'POST',
6230 dataType: 'json',
6231 data: payload,
6232 headers: {
6233 'X-WP-Nonce': getLocal().rest_nonce
6234 },
6235 beforeSend: function () {
6236 $('#create-jwt-btn').html(getAAM().__('Creating...'));
6237 },
6238 success: function (response) {
6239 $('#create-jwt-modal').modal('hide');
6240 $('#jwt-list').DataTable().ajax.reload();
6241
6242 jwtClaimsEditor.setValue('{}');
6243
6244 $('#view-jwt-token').val(response.token);
6245 $('#view-jwt-url').val(response.signed_url);
6246 $('#view-jwt-modal').modal('show');
6247 },
6248 error: function (response) {
6249 getAAM().notification('danger', response, {
6250 request: `aam/v2/jwts?fields=token,signed_url`,
6251 payload,
6252 response
6253 });
6254 },
6255 complete: function () {
6256 $('#create-jwt-btn').html(getAAM().__('Create'));
6257 }
6258 });
6259 });
6260
6261 $('#jwt-delete-btn').bind('click', function () {
6262 $('#jwt-delete-btn').html(getAAM().__('Deleting...')).prop(
6263 'disabled', true
6264 );
6265
6266 DeleteToken($('#jwt-delete-btn').attr('data-id'), () => {
6267 $('#jwt-delete-btn').html(getAAM().__('Delete')).prop(
6268 'disabled', false
6269 );
6270 $('#delete-jwt-modal').modal('hide');
6271 $('#jwt-list').DataTable().ajax.reload();
6272 });
6273 });
6274
6275 $('[data-toggle="toggle"]', container).bootstrapToggle();
6276 }
6277 }
6278
6279 getAAM().addHook('init', initialize);
6280
6281 })(jQuery);
6282
6283 /**
6284 * Security Audit Interface
6285 *
6286 * @param {jQuery} $
6287 *
6288 * @returns {void}
6289 */
6290 (function ($) {
6291
6292 /**
6293 *
6294 */
6295 const queue = [];
6296
6297 /**
6298 *
6299 */
6300 let issues_index = {};
6301
6302 /**
6303 *
6304 */
6305 function TriggerAudit(reset = false) {
6306 getAAM().queueRequest(function () {
6307 const current_step = queue[0];
6308 const step_title = $(`#check_${current_step}_status`).data('title');
6309 const indicator = $(`.aam-security-audit-step[data-step="${current_step}"]`);
6310 const payload = {
6311 step: current_step,
6312 reset
6313 };
6314
6315 if (issues_index[current_step] === undefined) {
6316 issues_index[current_step] = {};
6317 }
6318
6319 indicator.attr(
6320 'class', 'aam-security-audit-step icon-spin4 animate-spin'
6321 );
6322
6323 $.ajax(`${getLocal().rest_base}aam/v2/audit`, {
6324 type: 'POST',
6325 headers: {
6326 'X-WP-Nonce': getLocal().rest_nonce
6327 },
6328 dataType: 'json',
6329 data: payload,
6330 success: function (response) {
6331 // Append the list of identified issues to the list
6332 // if (Array.isArray(response.issues)) {
6333 // $.each(response.issues, (_, issue) => {
6334 // $(`#issue_list_${current_step} tbody`).append(
6335 // '<tr><td><strong>' + issue.type.toUpperCase() + ':</strong> ' + issue.reason + '</td></tr>'
6336 // );
6337
6338 // // Also increment the issue index
6339 // if (issues_index[current_step][issue.type] === undefined) {
6340 // issues_index[current_step][issue.type] = 0;
6341 // }
6342
6343 // issues_index[current_step][issue.type]++;
6344 // });
6345
6346 // $(`#issue_list_${current_step}`).removeClass('hidden');
6347 // }
6348
6349 if (response.is_completed) {
6350 queue.shift(); // Remove completed step
6351
6352 // Visual feedback that the step is completed
6353 const styles = ['aam-security-audit-step'];
6354 if (response.check_status === 'ok') {
6355 styles.push('icon-ok-circled', 'text-success');
6356 } else if (response.check_status === 'critical') {
6357 styles.push('icon-cancel-circled', 'text-danger');
6358 } else if (response.check_status === 'warning') {
6359 styles.push('icon-attention-circled', 'text-warning');
6360 } else if (response.check_status === 'notice') {
6361 styles.push('icon-info-circled', 'text-info');
6362 }
6363
6364 indicator.attr('class', styles.join(' '));
6365
6366 // Computing the number of issues
6367 const summary = [];
6368
6369 for(const type in issues_index[current_step]) {
6370 const c = issues_index[current_step][type];
6371 const p = c > 1;
6372
6373 summary.push(
6374 c + ' ' + getAAM().__(type + (p ? 's' : ''))
6375 );
6376 }
6377
6378 $(`#check_${current_step}_status`).html(
6379 step_title + ' - <b>DONE ' + (summary.length ? '(' + summary.join(', ') + ')' : '(OK)' ) + '</b>'
6380 );
6381
6382 if (queue.length) {
6383 TriggerAudit();
6384 } else {
6385 $('#execute_security_audit')
6386 .text(getAAM().__('Execute the Security Audit'))
6387 .attr('disabled', false);
6388
6389 const url = new URL(window.location);
6390
6391 if (url.searchParams.get('aam_page') === 'audit') {
6392 window.location.reload();
6393 } else {
6394 url.searchParams.set('aam_page', 'audit');
6395 window.location.href = url.toString();
6396 }
6397 }
6398 } else {
6399 $(`#check_${current_step}_status`).text(
6400 step_title + ' - ' + (response.progress * 100).toFixed(2) + '%'
6401 );
6402
6403 TriggerAudit();
6404 }
6405 },
6406 error: function (response) {
6407 getAAM().notification('danger', response, {
6408 request: `aam/v2/audit`,
6409 payload,
6410 response
6411 });
6412 }
6413 });
6414 });
6415 }
6416
6417 /**
6418 *
6419 */
6420 function DownloadReport(btn) {
6421 getAAM().queueRequest(function () {
6422 btn
6423 .text(getAAM().__('Generating Report...'))
6424 .prop('disabled', true);
6425
6426
6427 $.ajax(`${getLocal().rest_base}aam/v2/audit/report`, {
6428 type: 'GET',
6429 headers: {
6430 'X-WP-Nonce': getLocal().rest_nonce,
6431 'Accept': 'text/csv'
6432 },
6433 success: function (response) {
6434 getAAM().downloadFile(
6435 response, 'audit-report.csv', 'text/csv', false
6436 );
6437 },
6438 error: function (response) {
6439 getAAM().notification('danger', response, {
6440 request: `aam/v2/audit/report`,
6441 response
6442 });
6443 },
6444 complete: function() {
6445 btn
6446 .text(getAAM().__('Download Latest Report'))
6447 .prop('disabled', false);
6448 }
6449 });
6450 });
6451 }
6452
6453 /**
6454 *
6455 * @param {*} id
6456 * @param {*} list
6457 */
6458 function HydrateList(id, list) {
6459 if (Array.isArray(list)) {
6460 $(id).removeClass('hidden');
6461
6462 $.each(list, function(_, text) {
6463 $(id + ' > ul').append($('<li/>').text(text));
6464 });
6465 }
6466 }
6467
6468 /**
6469 *
6470 */
6471 function HydrateExecutiveSummary(data) {
6472 $('#executive_summary_prompt').addClass('hidden');
6473 $('#executive_summary_container').removeClass('hidden');
6474
6475 $('#executive_summary_overview').text(data.summary);
6476
6477 HydrateList('#executive_summary_critical', data.critical);
6478 HydrateList('#executive_summary_concerns', data.concerns);
6479 HydrateList('#executive_summary_recommendations', data.recommendations);
6480
6481 if (data.references && Array.isArray(data.references)) {
6482 $('#executive_summary_references').removeClass('hidden');
6483
6484 $.each(data.references, function(_, link) {
6485 $('#executive_summary_references > ul').append($('<li/>').append(
6486 $('<a/>').text(link).attr({
6487 href: link,
6488 target: '_blank'
6489 })
6490 ));
6491 });
6492 }
6493 }
6494
6495 /**
6496 *
6497 * @param {*} btn
6498 */
6499 function PrepareExecutiveSummary(btn) {
6500 $('#executive_summary_error').addClass('hidden');
6501
6502 getAAM().queueRequest(function () {
6503 btn.text(
6504 getAAM().__('Preparing Summary. It May Take Up To 20 Sec...')
6505 ).prop('disabled', true);
6506
6507 $.ajax(`${getLocal().rest_base}aam/v2/audit/summary`, {
6508 type: 'GET',
6509 headers: {
6510 'X-WP-Nonce': getLocal().rest_nonce
6511 },
6512 dataType: 'json',
6513 success: function (response) {
6514 if (response.status === 'success') {
6515 HydrateExecutiveSummary(response.results);
6516 } else {
6517 $('#executive_summary_error')
6518 .text(response.reason)
6519 .removeClass('hidden');
6520 }
6521 },
6522 error: function (response) {
6523 getAAM().notification('danger', response, {
6524 request: `aam/v2/audit/summary`,
6525 response
6526 });
6527 },
6528 complete: function() {
6529 btn
6530 .text(getAAM().__('Prepare My Executive Summary'))
6531 .prop('disabled', false);
6532 }
6533 });
6534 });
6535 }
6536
6537 /**
6538 *
6539 * @returns {undefined}
6540 */
6541 function initialize() {
6542 if ($('#audit-content').length) {
6543 $('#run_security_scan').bind('click', function () {
6544 if (!$(this).prop('disabled')) {
6545 $(this)
6546 .text(getAAM().__('Running Scan...'))
6547 .prop('disabled', true);
6548
6549 // Hide the download report container
6550 $('#download_report_container').addClass('hidden');
6551
6552 // Reset all previous results
6553 $('.aam-detected-issues tbody').empty();
6554 $('.aam-security-audit-step').attr(
6555 'class', 'icon-circle-thin text-info aam-security-audit-step'
6556 );
6557 $('.aam-check-status').each(function() {
6558 $(this).text($(this).data('title'));
6559 });
6560
6561 // Reset the issues index
6562 issues_index = {};
6563
6564 // Getting the queue of steps to execute
6565 $('.aam-security-audit-step').each(function() {
6566 queue.push($(this).data('step'));
6567 });
6568
6569 // Triggering the queue loop and perform the audit
6570 // step-by-step
6571 TriggerAudit(true);
6572 }
6573 });
6574
6575 $('.download-latest-report').bind('click', function() {
6576 DownloadReport($(this));
6577 });
6578
6579 $('#prepare_executive_summary').bind('click', function(event) {
6580 event.preventDefault();
6581
6582 if (!$(this).prop('disabled')) {
6583 PrepareExecutiveSummary($(this));
6584 }
6585 });
6586 }
6587 }
6588
6589 getAAM().addHook('init', initialize);
6590
6591 })(jQuery);
6592
6593 /**
6594 * Settings Interface
6595 *
6596 * @param {type} $
6597 *
6598 * @returns {undefined}
6599 */
6600 (function ($) {
6601
6602 /**
6603 *
6604 * @param {type} param
6605 * @param {type} value
6606 * @returns {undefined}
6607 */
6608 function Save(param, value) {
6609 getAAM().queueRequest(function () {
6610 const endpoint = `${getLocal().rest_base}aam/v2/config/${param}`;
6611 const payload = { value };
6612
6613 $.ajax(endpoint, {
6614 type: 'POST',
6615 dataType: 'json',
6616 data: payload,
6617 headers: {
6618 'X-WP-Nonce': getLocal().rest_nonce
6619 },
6620 error: function (response) {
6621 getAAM().notification('danger', response, {
6622 request: endpoint,
6623 payload,
6624 response
6625 });
6626 }
6627 });
6628 });
6629 }
6630
6631 /**
6632 *
6633 * @returns {undefined}
6634 */
6635 function initialize() {
6636 if ($('.aam-feature.settings').length) {
6637 $('[data-toggle="toggle"]', '.aam-feature.settings').bootstrapToggle();
6638
6639 $('#service-list').DataTable({
6640 autoWidth: false,
6641 ordering: false,
6642 pagingType: 'simple',
6643 data: JSON.parse($('#service-list-json').text()),
6644 columns: [
6645 { data: 'setting', visible: false },
6646 { data: 'title', visible: false },
6647 { data: 'description' },
6648 { data: 'status' }
6649 ],
6650 language: {
6651 search: '_INPUT_',
6652 searchPlaceholder: getAAM().__('Search Service'),
6653 info: getAAM().__('_TOTAL_ service(s)'),
6654 infoFiltered: '',
6655 infoEmpty: getAAM().__('Nothing to show'),
6656 lengthMenu: '_MENU_'
6657 },
6658 createdRow: function (row, data) {
6659 $('td:eq(0)', row).html(
6660 '<b>' + data.title + '</b><br/><i>' + data.description + '</i>'
6661 );
6662
6663 // Build toggler
6664 var checked = data.status ? 'checked' : '';
6665 var toggler = '<input data-toggle="toggle" name="' + data.setting + '" id="utility-' + data.setting + '" ' + checked + ' type="checkbox" data-on="' + getAAM().__('Enabled') + '" data-off="' + getAAM().__('Disabled') + '" data-size="small" />';
6666
6667 $('td:eq(1)', row).html(toggler);
6668
6669 $('[data-toggle="toggle"]', row).bootstrapToggle();
6670 $('input[type="checkbox"]', row).bind('change', function () {
6671 Save(
6672 $(this).attr('name'),
6673 $(this).prop('checked')
6674 );
6675 });
6676 }
6677 });
6678
6679 $('input[type="checkbox"]', '.aam-feature.settings').bind('change', function () {
6680 let value;
6681
6682 if ($(this).prop('checked')) {
6683 value = $(this).data('value-on') || true;
6684 } else {
6685 value = $(this).data('value-off') || false;
6686 }
6687
6688 Save($(this).attr('name'), value);
6689 });
6690
6691 $('#clear-settings').bind('click', function () {
6692 $('#clear-settings').prop('disabled', true);
6693 $('#clear-settings').text(getAAM().__('Processing...'));
6694
6695 getAAM().queueRequest(function () {
6696 $.ajax(`${getLocal().rest_base}aam/v2/core/reset`, {
6697 type: 'POST',
6698 dataType: 'json',
6699 headers: {
6700 'X-WP-Nonce': getLocal().rest_nonce,
6701 'X-HTTP-Method-Override': 'DELETE'
6702 },
6703 error: function (response) {
6704 getAAM().notification('danger', response, {
6705 request: 'aam/v2/aam',
6706 response
6707 });
6708 },
6709 complete: function () {
6710 $('#clear-settings').prop('disabled', false);
6711 $('#clear-settings').text(getAAM().__('Clear'));
6712 $('#clear-settings-modal').modal('hide');
6713
6714 location.reload();
6715 }
6716 });
6717 });
6718 });
6719 }
6720 }
6721
6722 getAAM().addHook('init', initialize);
6723
6724 // ConfigPress hook
6725 getAAM().addHook('menu-feature-click', function (feature) {
6726 if (feature === 'configpress'
6727 && !$('#aam-configpress-editor').next().hasClass('CodeMirror')) {
6728 var editor = wp.CodeMirror.fromTextArea(
6729 document.getElementById("aam-configpress-editor"), {}
6730 );
6731
6732 editor.on("blur", function () {
6733 getAAM().queueRequest(function () {
6734 const payload = {
6735 ini: editor.getValue()
6736 };
6737
6738 $.ajax(`${getLocal().rest_base}aam/v2/configpress`, {
6739 type: 'POST',
6740 dataType: 'json',
6741 data: payload,
6742 headers: {
6743 'X-WP-Nonce': getLocal().rest_nonce
6744 },
6745 error: function (response) {
6746 getAAM().notification('danger', response, {
6747 request: 'aam/v2/configpress',
6748 payload,
6749 response
6750 });
6751 }
6752 });
6753 });
6754 });
6755 }
6756 });
6757
6758 // Import/Export feature
6759 if (window.File && window.FileReader && window.FileList && window.Blob) {
6760 $('#file-api-error').remove();
6761
6762 $('#export-settings').bind('click', function() {
6763 getAAM().queueRequest(function () {
6764 $.ajax(`${getLocal().rest_base}aam/v2/core/export`, {
6765 dataType: 'json',
6766 headers: {
6767 'X-WP-Nonce': getLocal().rest_nonce
6768 },
6769 beforeSend: function () {
6770 $('#export-settings').prop('disabled', true);
6771 $('#export-settings').text(getAAM().__('Processing...'));
6772 },
6773 success: function (response) {
6774 getAAM().notification(
6775 'success',
6776 getAAM().__('Settings has been exported successfully')
6777 );
6778 getAAM().downloadFile(
6779 JSON.stringify(response),
6780 'aam-settings.json',
6781 'application/json',
6782 false
6783 )
6784 },
6785 error: function (response) {
6786 getAAM().notification('danger', response);
6787 },
6788 complete: function () {
6789 $('#export-settings').prop('disabled', false);
6790 $('#export-settings').text(getAAM().__('Download Exported Settings'));
6791 }
6792 });
6793 });
6794 });
6795
6796 // Handle the selected file
6797 $('#aam-settings').bind('change', function(e) {
6798 // Read the content for the selected file and evaluate it
6799 const reader = new FileReader();
6800
6801 reader.onload = function() {
6802 try {
6803 const content = JSON.parse(reader.result);
6804
6805 // Import AAM settings
6806 getAAM().queueRequest(function () {
6807 $.ajax(`${getLocal().rest_base}aam/v2/core/import`, {
6808 type: 'POST',
6809 dataType: 'json',
6810 contentType: 'application/json; charset=UTF-8',
6811 data: JSON.stringify({
6812 dataset: content.dataset
6813 }),
6814 headers: {
6815 'X-WP-Nonce': getLocal().rest_nonce
6816 },
6817 beforeSend: function () {
6818 $('#aam-settings').prop('disabled', true);
6819 },
6820 success: function () {
6821 getAAM().notification(
6822 'success',
6823 getAAM().__('Settings has been imported successfully')
6824 );
6825 location.reload();
6826 },
6827 error: function (response) {
6828 getAAM().notification('danger', response);
6829 },
6830 complete: function () {
6831 $('#aam-settings').prop('disabled', false);
6832 }
6833 });
6834 });
6835 } catch(ex) {
6836 getAAM().notification(
6837 'danger',
6838 getAAM().__('Invalid settings')
6839 );
6840 }
6841 }
6842
6843 reader.readAsText(e.target.files[0]);
6844 });
6845
6846 } else {
6847 $('#import-export-container').remove();
6848 }
6849 })(jQuery);
6850
6851 /**
6852 * Welcome Interface
6853 *
6854 * @param {jQuery} $
6855 *
6856 * @returns {void}
6857 */
6858 (function ($) {
6859
6860 /**
6861 *
6862 * @returns {undefined}
6863 */
6864 function initialize() {
6865 if ($('#welcome-content').length) {
6866 $('#intro_videos_block').on('show.bs.collapse', function(e) {
6867 $('.panel-body', e.target).contents().filter(function() {
6868 return this.nodeType === 8; // Node.COMMENT_NODE
6869 }).replaceWith(function() {
6870 return this.data;
6871 });
6872 });
6873 }
6874 }
6875
6876 getAAM().addHook('init', initialize);
6877
6878 })(jQuery);
6879
6880 /**
6881 * Top subject bar
6882 */
6883 (function ($) {
6884 $('#reset-subject-settings').bind('click', function() {
6885 const subject = getAAM().getSubject();
6886
6887 $('#reset-subject-msg').html(
6888 $('#reset-subject-msg')
6889 .data('message')
6890 .replace('%s', '<b>' + subject.name + '</b>')
6891 );
6892 $('#reset-subject-modal').modal('show');
6893 });
6894
6895 $('#reset-subject-btn').bind('click', function() {
6896 const _this = $(this);
6897
6898 getAAM().queueRequest(function () {
6899 $.ajax(getAAM().prepareApiEndpoint(`/settings`), {
6900 type: 'POST',
6901 dataType: 'json',
6902 headers: {
6903 'X-WP-Nonce': getLocal().rest_nonce,
6904 'X-HTTP-Method-Override': 'DELETE'
6905 },
6906 beforeSend: function () {
6907 _this.text(getAAM().__('Resetting...')).prop('disabled', true);
6908 },
6909 success: function () {
6910 getAAM().fetchContent('main');
6911 $('#reset-subject-modal').modal('hide');
6912 },
6913 error: function (response) {
6914 getAAM().notification('danger', response, {
6915 request: 'aam/v2/settings',
6916 response
6917 });
6918 },
6919 complete: function () {
6920 _this.text(getAAM().__('Reset')).prop('disabled', false);
6921 }
6922 });
6923 });
6924 });
6925 })(jQuery);
6926 }
6927
6928 /**
6929 * Main AAM class
6930 *
6931 * @returns void
6932 */
6933 function AAM() {
6934 /**
6935 * Current Subject
6936 */
6937 this.subject = {};
6938
6939 /**
6940 * Different UI hooks
6941 */
6942 this.hooks = {};
6943
6944 /**
6945 * Content filters
6946 */
6947 this.filters = {};
6948
6949 /**
6950 * Request queue
6951 */
6952 this.queue = {
6953 requests: [],
6954 processing: false
6955 };
6956
6957 /**
6958 *
6959 * @type AAM
6960 */
6961 var _this = this;
6962
6963 $(document).ajaxComplete(function () {
6964 _this.queue.processing = false;
6965
6966 if (_this.queue.requests.length > 0) {
6967 _this.queue.processing = true;
6968 _this.queue.requests.shift().call(_this);
6969 }
6970 });
6971 }
6972
6973 /**
6974 *
6975 * @param {type} request
6976 * @returns {undefined}
6977 */
6978 AAM.prototype.queueRequest = function (request) {
6979 this.queue.requests.push(request);
6980
6981 if (this.queue.processing === false) {
6982 this.queue.processing = true;
6983 this.queue.requests.shift().call(this);
6984 }
6985 };
6986
6987 /**
6988 *
6989 */
6990 AAM.prototype.loadRoleList = function (selected, target) {
6991 target = (typeof target === 'undefined' ? '#expiration-change-role' : target);
6992
6993 $(target).html(
6994 '<option value="">' + getAAM().__('Loading...') + '</option>'
6995 );
6996
6997 GetRoles((response) => {
6998 $(target).html(
6999 '<option value="">' + getAAM().__('Select Role') + '</option>'
7000 );
7001 for (var i in response) {
7002 $(target).append(
7003 '<option value="' + response[i].slug + '">' + response[i].name + '</option>'
7004 );
7005 }
7006
7007 $(target).val(selected);
7008 });
7009 }
7010
7011 /**
7012 *
7013 * @returns {undefined}
7014 */
7015 AAM.prototype.initializeMenu = function () {
7016 var _this = this;
7017
7018 //initialize the menu switch
7019 $('li', '#feature-list').each(function () {
7020 $(this).bind('click', function () {
7021 $('.aam-feature').removeClass('active');
7022 //highlight active feature
7023 $('li', '#feature-list').removeClass('active');
7024 $(this).addClass('active');
7025 //show feature content
7026 $('#' + $(this).data('feature') + '-content').addClass('active');
7027 location.hash = $(this).data('feature');
7028 //trigger hook
7029 _this.triggerHook('menu-feature-click', $(this).data('feature'));
7030 });
7031 });
7032 };
7033
7034 /**
7035 *
7036 * @param {*} view
7037 * @param {*} cb
7038 */
7039 AAM.prototype.fetchContent = function (view, cb = null) {
7040 var _this = this;
7041
7042 var payload = {
7043 action: 'aam',
7044 sub_action: 'renderContent',
7045 _ajax_nonce: getLocal().nonce,
7046 partial: view,
7047 access_level: this.getSubject().type
7048 };
7049
7050 if (payload.access_level === 'role') {
7051 payload.role_id = this.getSubject().id;
7052 } else if (payload.access_level === 'user') {
7053 payload.user_id = this.getSubject().id;
7054 }
7055
7056 $.ajax(getLocal().ajaxurl, {
7057 type: 'POST',
7058 dataType: 'html',
7059 data: payload,
7060 beforeSend: function () {
7061 if ($('#aam-initial-load').length === 0) {
7062 $('#aam-content').html(
7063 $('<div/>', { 'class': 'aam-loading' }).append($('<i/>', {
7064 'class': 'icon-spin4 animate-spin'
7065 }))
7066 );
7067 }
7068 },
7069 success: function (response) {
7070 $('#aam-content').html(response);
7071 // Init menu
7072 _this.initializeMenu();
7073
7074 // Trigger initialization hook
7075 _this.triggerHook('init');
7076
7077 // There is more than one Services available to manage
7078 if ($('#feature-list').length) {
7079 //activate one of the menu items
7080 var item = $('li:eq(0)', '#feature-list');
7081
7082 if (location.hash !== '') {
7083 var hash = location.hash.substr(1);
7084 if ($('li[data-feature="' + hash + '"]', '#feature-list').length) {
7085 item = $('li[data-feature="' + hash + '"]', '#feature-list');
7086 }
7087 }
7088
7089 item.trigger('click');
7090 } else {
7091 $('.aam-feature:eq(0)').addClass('active');
7092 }
7093
7094 $('.aam-sidebar .metabox-holder').hide();
7095 $('.aam-sidebar .shared-metabox').show();
7096 $('.aam-sidebar .' + view + '-metabox').show();
7097
7098 if (view !== 'main') { //hide subject and user/role manager
7099 $('#aam-subject-banner').hide();
7100 } else {
7101 $('#aam-subject-banner').show();
7102 }
7103
7104 if (cb) {
7105 cb();
7106 }
7107 }
7108 });
7109 };
7110
7111 /**
7112 *
7113 * @param {type} view
7114 * @param {type} success
7115 * @param {type} failure
7116 * @returns {undefined}
7117 */
7118 AAM.prototype.fetchPartial = function (view, success) {
7119 var _this = this;
7120
7121 //referred object ID like post, page or any custom post type
7122 var object = window.location.search.match(/&id\=([^&]*)/);
7123 var type = window.location.search.match(/&type\=([^&]*)/);
7124
7125 const payload = {
7126 action: 'aam',
7127 sub_action: 'renderContent',
7128 _ajax_nonce: getLocal().nonce,
7129 partial: view,
7130 access_level: this.getSubject().type,
7131 id: object ? object[1] : null,
7132 type: type ? type[1] : null
7133 }
7134
7135 if (payload.access_level === 'role') {
7136 payload.role_id = this.getSubject().id;
7137 } else if (payload.access_level === 'user') {
7138 payload.user_id = this.getSubject().id;
7139 }
7140
7141 $.ajax(getLocal().ajaxurl, {
7142 type: 'POST',
7143 dataType: 'html',
7144 data: payload,
7145 success: function (response) {
7146 success.call(_this, response);
7147 },
7148 error: function(response) {
7149 getAAM().notification('danger', response);
7150 }
7151 });
7152 };
7153
7154 /**
7155 * Add UI hook
7156 *
7157 * @param {String} name
7158 * @param {Function} callback
7159 *
7160 * @returns {void}
7161 */
7162 AAM.prototype.addHook = function (name, callback) {
7163 if (typeof this.hooks[name] === 'undefined') {
7164 this.hooks[name] = new Array();
7165 }
7166
7167 this.hooks[name].push(callback);
7168 };
7169
7170 /**
7171 * Trigger UI hook
7172 *
7173 * @param {String} name
7174 * @param {Object} params
7175 *
7176 * @returns {void}
7177 */
7178 AAM.prototype.triggerHook = function (name, params) {
7179 if (typeof this.hooks[name] !== 'undefined') {
7180 for (var i in this.hooks[name]) {
7181 this.hooks[name][i].call(this, params);
7182 }
7183 }
7184 };
7185
7186 /**
7187 * Add UI filter
7188 *
7189 * @param {String} name
7190 * @param {Function} callback
7191 *
7192 * @returns {void}
7193 */
7194 AAM.prototype.addFilter = function (name, callback) {
7195 if (typeof this.filters[name] === 'undefined') {
7196 this.filters[name] = new Array();
7197 }
7198
7199 this.filters[name].push(callback);
7200 };
7201
7202 /**
7203 * Apply UI filters
7204 *
7205 * @param {String} name
7206 * @param {String} result
7207 * @param {Object} params
7208 *
7209 * @returns {void}
7210 */
7211 AAM.prototype.applyFilters = function (name, result, params) {
7212 if (typeof this.filters[name] !== 'undefined') {
7213 for (var i in this.filters[name]) {
7214 result = this.filters[name][i].call(this, result, params);
7215 }
7216 }
7217
7218 return result;
7219 };
7220
7221 /**
7222 * Initialize the AAM
7223 *
7224 * @returns {undefined}
7225 */
7226 AAM.prototype.initialize = function () {
7227 // Read default subject and set it for AAM object
7228 if ($('#aam-subject-type').length > 0) {
7229 this.setSubject(
7230 $('#aam-subject-type').val(),
7231 $('#aam-subject-id').val(),
7232 $('#aam-subject-name').val()
7233 );
7234 } else if (getLocal().subject.type) {
7235 this.setSubject(
7236 getLocal().subject.type,
7237 getLocal().subject.id,
7238 getLocal().subject.name
7239 );
7240 } else {
7241 $('#aam-subject-banner').addClass('hidden');
7242 }
7243
7244 //load the UI javascript support
7245 UI();
7246
7247 // Initialize help context
7248 $('.aam-help-menu').each(function () {
7249 var target = $(this).data('target');
7250
7251 if (target) {
7252 $(this).bind('click', function () {
7253 if ($(this).hasClass('active')) {
7254 $('.aam-help-context', target).removeClass('active');
7255 $('.aam-postbox-inside', target).show();
7256 $(this).removeClass('active');
7257 } else {
7258 $('.aam-postbox-inside', target).hide();
7259 $('.aam-help-context', target).addClass('active');
7260 $(this).addClass('active');
7261 }
7262 });
7263 }
7264 });
7265
7266 // Help tooltip
7267 $('body').delegate('[data-toggle="tooltip"]', 'hover', function (event) {
7268 event.preventDefault();
7269
7270 $(this).tooltip({
7271 'placement': $(this).data('placement') || 'top',
7272 'container': 'body'
7273 });
7274
7275 $(this).tooltip('show');
7276 });
7277
7278 $('.aam-area').each(function () {
7279 $(this).bind('click', function () {
7280 $('.aam-area').removeClass('text-danger');
7281 $(this).addClass('text-danger');
7282 getAAM().fetchContent($(this).data('type'));
7283 });
7284 });
7285
7286 const query = new URLSearchParams(location.search);
7287
7288 if (query.has('aam_page')) {
7289 $('.aam-area').removeClass('text-danger');
7290 $('.aam-area[data-type="' + query.get('aam_page') + '"]').addClass(
7291 'text-danger'
7292 );
7293
7294 getAAM().fetchContent(query.get('aam_page'));
7295 } else {
7296 getAAM().fetchContent('main'); // Fetch default AAM content
7297 }
7298
7299 // preventDefault for all links with # href
7300 $('#aam-container').delegate('a[href="#"]', 'click', function (event) {
7301 event.preventDefault();
7302 });
7303
7304 // Initialize clipboard
7305 var clipboard = new ClipboardJS('.aam-copy-clipboard');
7306
7307 clipboard.on('success', function (e) {
7308 getAAM().notification(
7309 'success',
7310 getAAM().__('Data has been saved to clipboard')
7311 );
7312 });
7313
7314 clipboard.on('error', function (e) {
7315 getAAM().notification(
7316 'danger',
7317 getAAM().__('Failed to save data to clipboard')
7318 );
7319 });
7320 };
7321
7322 /**
7323 *
7324 * @param {type} label
7325 * @returns {unresolved}
7326 */
7327 AAM.prototype.__ = function (label) {
7328 return (getLocal().translation[label] ? getLocal().translation[label] : label);
7329 };
7330
7331 /**
7332 *
7333 * @param {type} type
7334 * @param {type} id
7335 * @param {type} name
7336 * @returns {undefined}
7337 */
7338 AAM.prototype.setSubject = function (type, id, name) {
7339 this.subject = {
7340 type: type,
7341 id: id,
7342 name: name
7343 };
7344
7345 // Reset all roles
7346 if ($('#role-list').is('.dataTable')) {
7347 $('#role-list').DataTable().rows().eq(0).each(function(i) {
7348 $(
7349 'td:eq(0) span',
7350 $('#role-list').DataTable().row(i).node()
7351 ).removeClass('aam-highlight');
7352
7353 $(
7354 '.icon-cog',
7355 $('#role-list').DataTable().row(i).node()
7356 ).attr('class', 'aam-row-action icon-cog text-info');
7357 });
7358 }
7359
7360 if (getAAM().isUI('main')) {
7361 // First set the type of the subject
7362 $('.aam-current-subject').text(
7363 type.charAt(0).toUpperCase() + type.slice(1) + ': '
7364 );
7365
7366 // Second set the name of the subject
7367 $('.aam-current-subject').append($('<strong/>').text(name));
7368 }
7369
7370 this.triggerHook('access-level-changed');
7371 };
7372
7373 /**
7374 *
7375 * @returns {aam_L1.AAM.subject}
7376 */
7377 AAM.prototype.getSubject = function () {
7378 return this.subject;
7379 };
7380
7381 /**
7382 * Show notification
7383 *
7384 * @param {String} status
7385 * @param {Object} response
7386 * @param {Object} metadata
7387 *
7388 * @returns {Void}
7389 */
7390 AAM.prototype.notification = function (status, response, metadata = null) {
7391 let notification_header;
7392 let notification_message;
7393
7394 // Determine the visible message
7395 if (typeof response === 'string') {
7396 notification_message = response;
7397 } else if (response && response.responseJSON && response.responseJSON.message) {
7398 notification_message = response.responseJSON.message;
7399 }
7400
7401 switch (status) {
7402 case 'success':
7403 notification_header = 'Success';
7404 notification_message = getAAM().__(
7405 notification_message || 'Operation completed successfully'
7406 );
7407 break;
7408
7409 case 'danger':
7410 notification_header = 'No go';
7411 notification_message = notification_message || 'An unexpected application issue has arisen. Please feel free to report this issue to us, and we will promptly provide you with a solution.'
7412 break;
7413
7414 default:
7415 break;
7416 }
7417
7418 if (status === 'success') {
7419 $.toast({
7420 text: notification_message,
7421 heading: notification_header,
7422 icon: 'success',
7423 showHideTransition: 'fade',
7424 allowToastClose: true,
7425 hideAfter: 6000,
7426 stack: 5,
7427 position: 'top-right',
7428 textAlign: 'left',
7429 loader: true,
7430 loaderBg: '#5cb85c'
7431 });
7432 } else {
7433 $.toast({
7434 text: notification_message,
7435 heading: notification_header,
7436 icon: 'error',
7437 showHideTransition: 'fade',
7438 allowToastClose: true,
7439 hideAfter: false,
7440 stack: 5,
7441 position: 'top-right',
7442 textAlign: 'left',
7443 loader: true,
7444 loaderBg: '#a94442'
7445 });
7446 }
7447 };
7448
7449 /**
7450 *
7451 * @param {type} type
7452 * @returns {Boolean}
7453 */
7454 AAM.prototype.isUI = function (type) {
7455 return (getLocal().ui === type);
7456 };
7457
7458 /**
7459 *
7460 */
7461 AAM.prototype.downloadFile = function(content, filename, mime, decode = true) {
7462 let binaryString;
7463
7464 if (decode) {
7465 binaryString = window.atob(content);
7466 } else {
7467 binaryString = content;
7468 }
7469
7470 const bytes = new Uint8Array(binaryString.length);
7471 const base64 = bytes.map((_, i) => binaryString.charCodeAt(i));
7472
7473 var blob = new Blob([base64], { type: mime || 'application/octet-stream' });
7474
7475 if (typeof window.navigator.msSaveBlob !== 'undefined') {
7476 // IE workaround for "HTML7007: One or more blob URLs were
7477 // revoked by closing the blob for which they were created.
7478 // These URLs will no longer resolve as the data backing
7479 // the URL has been freed."
7480 window.navigator.msSaveBlob(blob, filename);
7481 }
7482 else {
7483 var blobURL = window.URL.createObjectURL(blob);
7484 var tempLink = document.createElement('a');
7485 tempLink.style.display = 'none';
7486 tempLink.href = blobURL;
7487 tempLink.setAttribute('download', filename);
7488
7489 // Safari thinks _blank anchor are pop ups. We only want to set _blank
7490 // target if the browser does not support the HTML5 download attribute.
7491 // This allows you to download files in desktop safari if pop up blocking
7492 // is enabled.
7493 if (typeof tempLink.download === 'undefined') {
7494 tempLink.setAttribute('target', '_blank');
7495 }
7496
7497 document.body.appendChild(tempLink);
7498 tempLink.click();
7499 document.body.removeChild(tempLink);
7500 window.URL.revokeObjectURL(blobURL);
7501 }
7502 }
7503
7504 /**
7505 *
7506 * @returns {aamLocal}
7507 */
7508 var getLocal = function () {
7509 return aamLocal;
7510 }
7511
7512 AAM.prototype.getLocal = getLocal;
7513
7514 /**
7515 *
7516 * @param {String} url
7517 * @param {Boolean} include_access_level
7518 * @param {Object} override
7519 *
7520 * @returns {String}
7521 */
7522 AAM.prototype.prepareApiEndpoint = function (
7523 url, include_access_level = true, override = null
7524 ) {
7525 let response = `${getLocal().rest_base}aam/v2${url}`;
7526
7527 if (include_access_level) {
7528 const al = override || getAAM().getSubject();
7529 const type = al.type;
7530 const params = [`access_level=${type}`];
7531
7532 if (type === 'role') {
7533 params.push(`role_id=${al.id}`);
7534 } else if (type === 'user') {
7535 params.push(`user_id=${al.id}`);
7536 }
7537
7538 if (response.includes('?')) {
7539 response += '&' + params.join('&');
7540 } else {
7541 response += '?' + params.join('&');
7542 }
7543 }
7544
7545 return response;
7546 }
7547
7548 /**
7549 *
7550 * @param {*} mergeWith
7551 * @returns
7552 */
7553 AAM.prototype.prepareAjaxRequestPayload = function(mergeWith = {}) {
7554 // Prepare the payload
7555 const data = {
7556 access_level: getAAM().getSubject().type
7557 };
7558
7559 if (data.access_level === 'role') {
7560 data.role_id = getAAM().getSubject().id;
7561 } else if (data.access_level === 'user') {
7562 data.user_id = getAAM().getSubject().id;
7563 }
7564
7565 return Object.assign({}, mergeWith, data);
7566 }
7567
7568 /**
7569 *
7570 * @returns {aamL#14.AAM|AAM}
7571 */
7572 function getAAM() {
7573 return aam;
7574 }
7575
7576 /**
7577 * Initialize UI
7578 */
7579 $(document).ready(function () {
7580 $.aam = aam = window['aam'] = new AAM();
7581 getAAM().initialize();
7582 });
7583
7584 })(jQuery);