PluginProbe
Authorizer / 2.7.0
Authorizer v2.7.0
3.15.3 3.15.2 3.15.1 3.15.0 3.14.3 3.14.4 3.14.2 3.14.1 2.8.1 2.8.2 2.8.3 2.8.4 2.8.5 2.8.6 2.8.7 2.8.8 2.9.0 2.9.1 2.9.10 2.9.11 2.9.12 2.9.13 2.9.2 2.9.3 2.9.6 All 126 releases
authorizer / js / authorizer.js

authorizer.js in Authorizer 2.7.0, at js/authorizer.js

1,324 lines 56.2 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 var animation_speed = 300;
2 var shake_speed = 600;
3
4
5
6 // Switch between option tabs.
7 function choose_tab( list_name, delay ) {
8 var $ = jQuery;
9
10 // default delay is 0
11 delay = typeof delay !== 'undefined' ? delay : 0;
12
13 // default to the access list tab
14 list_name = typeof list_name !== 'undefined' ? list_name : 'access_lists';
15
16 // Hide all tab content, then show selected tab content
17 $( 'div.section_info, div.section_info + table' ).hide();
18 $( '#section_info_' + list_name + ', #section_info_' + list_name + ' + table' ).show();
19
20 // Set active tab
21 $( '.nav-tab-wrapper a' ).removeClass( 'nav-tab-active' );
22 $( 'a.nav-tab-' + list_name ).addClass( 'nav-tab-active' );
23
24 // Hide site options if they are overridden by a multisite setting.
25 setTimeout( hide_multisite_overridden_options, delay );
26
27 // Hide Save Changes button if we're on the access lists page (changing
28 // access lists saves automatically via AJAX).
29 $( 'body:not(.network-admin) #submit' ).toggle( list_name !== 'access_lists' );
30
31 // Save user's active tab to sessionStorage (so we can restore it on reload).
32 // Note: session storage persists until the browser tab is closed.
33 sessionStorage.setItem( 'tab', list_name );
34 }
35
36 // Switch between pages in the Approved User list.
37 function refresh_approved_user_list( currentPage, searchTerm ) {
38 var $ = jQuery;
39 var $list = $( '#list_auth_settings_access_users_approved' );
40 var $spinner = $( '<span class="spinner is-active"></span>' ).css({
41 'position': 'relative',
42 'top': '45%',
43 'left': '-240px',
44 });
45 var $overlay = $( '<div id="list_auth_settings_access_users_approved_overlay"></div>' ).css({
46 'background-color': '#f1f1f1',
47 'z-index': 1,
48 'opacity': 0.8,
49 'position': 'absolute',
50 'top': $list.position().top,
51 'left': $list.position().left,
52 'width': $list.width(),
53 'height': $list.height(),
54 });
55 $overlay.append( $spinner );
56
57 // Show overlay and wait cursor.
58 $list.after( $overlay );
59 $( 'html' ).addClass( 'busy' );
60
61 $.post( ajaxurl, {
62 'action': 'refresh_approved_user_list',
63 'nonce_save_auth_settings': $( '#nonce_save_auth_settings' ).val(),
64 'is_network_admin': auth_L10n.is_network_admin,
65 'paged': currentPage,
66 'search': searchTerm,
67 }, function( response ) {
68 if ( response.success ) {
69 // Update user list and total user and page count.
70 $( '#list_auth_settings_access_users_approved' ).html( response.html );
71 $( '.displaying-num' ).html( response.total_users_html );
72 $( '.total-pages' ).html( response.total_pages_html );
73
74 // Adjust our current page if the query changed the total page count.
75 if ( currentPage > response.total_pages ) {
76 currentPage = response.total_pages;
77 }
78
79 // Update pager elements.
80 refresh_approved_user_pager( currentPage );
81
82 // Update querystring with new paged param value (but don't reload the page).
83 if ( history.pushState ) {
84 var url = window.location.href;
85 url = updateQueryStringParameter( url, 'paged', currentPage );
86 url = updateQueryStringParameter( url, 'search', searchTerm );
87 window.history.pushState( { path: url }, '', url );
88 }
89 }
90 // Remove overlay and wait cursor.
91 $overlay.remove();
92 $( 'html' ).removeClass( 'busy' );
93 }).fail( function() {
94 // Remove overlay and wait cursor.
95 $overlay.remove();
96 $( 'html' ).removeClass( 'busy' );
97 });
98 }
99
100 // Update the pager elements when changing pages.
101 function refresh_approved_user_pager( currentPage ) {
102 var $ = jQuery;
103 var totalPages = parseInt( $( '.total-pages' ).first().text().replace( /[^0-9]/g, '' ) ) || 1;
104
105 // If total number of pages changed (because a search filter reduced it), make
106 // sure current page is not larger than it.
107 if ( currentPage > totalPages ) {
108 currentPage = totalPages;
109 }
110 if ( currentPage < 1 ) {
111 currentPage = 1;
112 }
113 if ( totalPages < 1 ) {
114 totalPages = 1;
115 }
116
117 // Update current page text input.
118 $( '#current-page-selector' ).val( currentPage );
119
120 // Update current page span.
121 $( '#table-paging .current-page-text' ).text( currentPage );
122
123 // Update first page button.
124 var $first = $( '.first-page' );
125 if ( $first.is( 'a' ) && currentPage <= 1 ) {
126 $first.replaceWith( '<span class="first-page tablenav-pages-navspan" aria-hidden="true">&laquo;</span>' );
127 } else if ( $first.is( 'span' ) && currentPage > 1 ) {
128 $first.replaceWith( '<a class="first-page" href="' + updateQueryStringParameter( window.location.href, 'paged', '1' ) + '"><span class="screen-reader-text">' + auth_L10n.first_page + '</span><span aria-hidden="true">&laquo;</span></a>' );
129 }
130
131 // Update prev page button.
132 var $prev = $( '.prev-page' );
133 if ( $prev.is( 'a' ) && currentPage <= 1 ) {
134 $prev.replaceWith( '<span class="prev-page tablenav-pages-navspan" aria-hidden="true">&lsaquo;</span>' );
135 } else if ( currentPage > 1 ) {
136 $prev.replaceWith( '<a class="prev-page" href="' + updateQueryStringParameter( window.location.href, 'paged', currentPage - 1 ) + '"><span class="screen-reader-text">' + auth_L10n.prev_page + '</span><span aria-hidden="true">&lsaquo;</span></a>' );
137 }
138
139 // Update next button.
140 var $next = $( '.next-page' );
141 if ( $next.is( 'a' ) && currentPage >= totalPages ) {
142 $next.replaceWith( '<span class="next-page tablenav-pages-navspan" aria-hidden="true">&rsaquo;</span>' );
143 } else if ( currentPage < totalPages ) {
144 $next.replaceWith( '<a class="next-page" href="' + updateQueryStringParameter( window.location.href, 'paged', currentPage + 1 ) + '"><span class="screen-reader-text">' + auth_L10n.next_page + '</span><span aria-hidden="true">&rsaquo;</span></a>' );
145 }
146
147 // Update last button.
148 var $last = $( '.last-page' );
149 if ( $last.is( 'a' ) && currentPage >= totalPages ) {
150 $last.replaceWith( '<span class="last-page tablenav-pages-navspan" aria-hidden="true">&raquo;</span>' );
151 } else if ( $last.is( 'span' ) && currentPage < totalPages ) {
152 $last.replaceWith( '<a class="last-page" href="' + updateQueryStringParameter( window.location.href, 'paged', totalPages ) + '"><span class="screen-reader-text">' + auth_L10n.next_page + '</span><span aria-hidden="true">&raquo;</span></a>' );
153 }
154 }
155
156 // Update user's usermeta field.
157 function auth_update_usermeta( caller ) {
158 var $ = jQuery,
159 $caller = $( caller ),
160 $usermeta = $caller.parent().children( '.auth-usermeta' ),
161 email = $caller.siblings( '.auth-email' ).val(),
162 usermeta = $usermeta.val(),
163 nonce_save_auth_settings = $( '#nonce_save_auth_settings' ).val();
164
165 // Remove reference to caller if it's the usermeta field itself (not a button triggering the save).
166 if ( $caller.hasClass( 'auth-usermeta' ) ) {
167 $caller = $();
168 }
169
170 // Disable inputs, show spinner.
171 $caller.attr( 'disabled', 'disabled' );
172 $usermeta.attr( 'disabled', 'disabled' );
173 var $row = $usermeta.closest( 'li' );
174 var $spinner = $( '<span class="spinner is-active"></span>' ).css({
175 'position': 'absolute',
176 'top': $row.position().top,
177 'left': $row.position().left + $row.width(),
178 });
179 $usermeta.after( $spinner );
180 $( 'html' ).addClass( 'busy' );
181
182 // Call ajax save function.
183 $.post( ajaxurl, {
184 'action': 'update_auth_usermeta',
185 'email': email,
186 'usermeta': usermeta,
187 'nonce_save_auth_settings': nonce_save_auth_settings,
188 }, function ( response ) {
189 var succeeded = response === 'success';
190 var spinner_text = succeeded ? auth_L10n.saved + '.' : '<span style="color: red;">' + auth_L10n.failed + '.</span>';
191 var spinner_wait = succeeded ? 500 : 2000;
192
193 // Enable inputs, remove spinner.
194 $caller.removeAttr( 'disabled' );
195 $usermeta.removeAttr( 'disabled' );
196 $caller.css( 'display', 'none' );
197 $( 'form .spinner:not(:has(.spinner-text))' ).animate( { width: '60px' }, 'fast' ).append( '<span class="spinner-text">' + spinner_text + '</span>' ).delay( spinner_wait ).hide( animation_speed, function() {
198 $( this ).remove();
199 });
200 $( 'html' ).removeClass( 'busy' );
201
202 }).fail( function ( response ) {
203 var succeeded = false;
204 var spinner_text = succeeded ? auth_L10n.saved + '.' : '<span style="color: red;">' + auth_L10n.failed + '.</span>';
205 var spinner_wait = succeeded ? 500 : 2000;
206
207 // Enable inputs, remove spinner.
208 $caller.removeAttr( 'disabled' );
209 $usermeta.removeAttr( 'disabled' );
210 $caller.css( 'display', 'none' );
211 $( 'form .spinner:not(:has(.spinner-text))' ).animate( { width: '60px' }, 'fast' ).append( '<span class="spinner-text">' + spinner_text + '</span>' ).delay( spinner_wait ).hide( animation_speed, function() {
212 $( this ).remove();
213 });
214 $( 'html' ).removeClass( 'busy' );
215
216 });
217
218 }
219
220 // Update user's role (multisite options page).
221 function auth_multisite_change_role( caller ) {
222 var is_multisite = true;
223 auth_change_role( caller, is_multisite );
224 }
225
226 // Update user's role.
227 function auth_change_role( caller, is_multisite ) {
228 var $ = jQuery;
229
230 // Set default for multisite flag (run different save routine if multisite)
231 is_multisite = typeof is_multisite !== 'undefined' ? is_multisite : false;
232
233 var email = $( caller ).parent().find( '.auth-email' );
234 var role = $( caller ).parent().find( '.auth-role' );
235 var date_added = $( caller ).parent().find( '.auth-date-added' );
236
237 var user = {
238 'email': email.val(),
239 'role': role.val(),
240 'date_added': date_added.val(),
241 'edit_action': 'change_role',
242 'multisite_user': is_multisite,
243 };
244
245 // Update the options in the database with this change.
246 update_auth_user( caller, 'access_users_approved', user );
247
248 return true;
249 }
250
251 // Add user to list (multisite options page).
252 function auth_multisite_add_user( caller, list, create_local_account ) {
253 var is_multisite = true;
254
255 // Default to the approved list.
256 list = typeof list !== 'undefined' ? list : 'approved';
257
258 // Default to not creating a local account.
259 create_local_account = typeof create_local_account !== 'undefined' ? create_local_account : false;
260
261 // There currently is no multisite blocked list, so do nothing.
262 if ( list === 'blocked' ) {
263 return;
264 }
265
266 auth_add_user( caller, list, create_local_account, is_multisite );
267 }
268 // Add user to list (list = blocked or approved).
269 function auth_add_user( caller, list, create_local_account, is_multisite ) {
270 var $ = jQuery;
271
272 // Skip email address validation if adding from pending list (not user-editable).
273 var skip_validation = $( caller ).parent().parent().attr( 'id' ) === 'list_auth_settings_access_users_pending';
274
275 // Skip email address validation if we're banning an existing user (since they're already in a list).
276 skip_validation = skip_validation || $( caller ).attr( 'id' ).indexOf( 'block_user' ) > -1;
277
278 // Set default for multisite flag (run different save routine if multisite)
279 is_multisite = typeof is_multisite !== 'undefined' ? is_multisite : false;
280
281 // Default to the approved list.
282 list = typeof list !== 'undefined' ? list : 'approved';
283
284 // Default to not creating a local account.
285 create_local_account = typeof create_local_account !== 'undefined' ? create_local_account : false;
286
287 var email = $( caller ).parent().find( '.auth-email' );
288 var role = $( caller ).parent().find( '.auth-role' );
289 var date_added = $( caller ).parent().find( '.auth-date-added' );
290
291 // Helper variable for disabling buttons while processing. This will be
292 // set differently if our clicked button is nested in a div (below).
293 var buttons = caller;
294
295 // Button (caller) might be nested in a div, so we need to walk up one more level
296 if ( email.length === 0 || role.length === 0 ) {
297 email = $( caller ).parent().parent().find( '.auth-email' );
298 role = $( caller ).parent().parent().find( '.auth-role' );
299 date_added = $( caller ).parent().parent().find( '.auth-date-added' );
300 buttons = $( caller ).parent().children();
301 }
302
303 // Support a single email address, or multiple (separated by newlines, commas, semicolons, or spaces).
304 var emails = $.trim( email.val() ).replace( /mailto:/g, '' ).split( /[\s,;]+/ );
305
306 // Remove any invalid email addresses.
307 if ( ! skip_validation ) {
308 // Check if the email(s) being added is well-formed.
309 emails = emails.filter( function ( email ) {
310 return valid_email( email );
311 });
312 // Remove any duplicates in the list of emails to add.
313 emails = remove_duplicates_from_array_of_strings( emails );
314 }
315
316 // Shake and quit if no valid email addresses exist.
317 if ( emails.length < 1 ) {
318 $( '#new_' + list + '_user_email' ).parent().effect( 'shake', shake_speed );
319 return false;
320 }
321
322 $( buttons ).attr( 'disabled', 'disabled' );
323
324 var users = [];
325 for ( var i = 0; i < emails.length; i++ ) {
326 var user = {
327 'email': emails[i],
328 'role': role.val(),
329 'date_added': date_added.val(),
330 'edit_action': 'add',
331 'local_user': create_local_account,
332 'multisite_user': is_multisite,
333 };
334 users.push( user );
335
336 // Get next highest user ID.
337 var next_id = 1 + Math.max.apply(
338 null,
339 $( '#list_auth_settings_access_users_' + list + ' li .auth-email' ).map( function ( el, index ) {
340 return parseInt( this.id.replace( 'auth_multisite_settings_access_users_' + list + '_', '' ).replace( 'auth_settings_access_users_' + list + '_', '' ) );
341 })
342 );
343
344 // Add the new item.
345 var auth_js_prefix = is_multisite ? 'auth_multisite_' : 'auth_';
346 var local_icon = create_local_account ? '&nbsp;<a title="' + auth_L10n.local_wordpress_user + '" class="auth-local-user"><span class="glyphicon glyphicon-user"></span></a>' : '';
347 var ban_button = list === 'approved' && ! is_multisite ? '<a class="button" id="block_user_' + next_id + '" onclick="' + auth_js_prefix + 'add_user( this, \'blocked\', false ); ' + auth_js_prefix + 'ignore_user( this, \'approved\' );" title="' + auth_L10n.block_ban_user + '"><span class="glyphicon glyphicon-ban-circle"></span></a>' : '';
348 $( ' \
349 <li id="new_user_' + next_id + '" class="new-user" style="display: none;"> \
350 <input type="text" id="auth_settings_access_users_' + list + '_' + next_id + '" name="auth_settings[access_users_' + list + '][' + next_id + '][email]" value="' + user.email + '" readonly="true" class="auth-email" /> \
351 <select name="auth_settings[access_users_' + list + '][' + next_id + '][role]" class="auth-role" onchange="' + auth_js_prefix + 'change_role( this );"> \
352 </select> \
353 <input type="text" name="auth_settings[access_users_' + list + '][' + next_id + '][date_added]" value="' + getShortDate() + '" readonly="true" class="auth-date-added" /> \
354 ' + ban_button + ' \
355 <a class="button" id="ignore_user_' + next_id + '" onclick="' + auth_js_prefix + 'ignore_user( this, \'' + list + '\' );" title="' + auth_L10n.remove_user + '"><span class="glyphicon glyphicon-remove"></span></a> \
356 ' + local_icon + ' \
357 <span class="spinner is-active"></span> \
358 </li> \
359 ' ).appendTo( '#list_auth_settings_access_users_' + list + '' ).slideDown( 250 );
360
361 // Populate the role dropdown in the new element. Because clone() doesn't
362 // save selected state on select elements, set that too.
363 $( 'option', role ).clone().appendTo( '#new_user_' + next_id + ' .auth-role' );
364 $( '#new_user_' + next_id + ' .auth-role' ).val( role.val() );
365 }
366
367 // Remove the 'empty list' item if it exists.
368 $( '#list_auth_settings_access_users_' + list + ' li.auth-empty' ).remove();
369
370 // Update the options in the database with this change.
371 update_auth_user( buttons, 'access_users_' + list, users );
372
373 // Reset the new user textboxes
374 if ( email.hasClass( 'new' ) ) {
375 email.val( '' ).keydown();
376 }
377
378 // Re-enable the action buttons now that we're done saving.
379 $( buttons ).removeAttr( 'disabled' );
380 return true;
381 }
382
383 // Remove user from list (multisite options page).
384 function auth_multisite_ignore_user( caller, list_name ) {
385 var is_multisite = true;
386
387 // Set default list if not provided.
388 list_name = typeof list_name !== 'undefined' ? list_name : '';
389
390 auth_ignore_user( caller, list_name, is_multisite );
391 }
392 // Remove user from list.
393 function auth_ignore_user( caller, list_name, is_multisite ) {
394 var $ = jQuery;
395
396 // Set default for multisite flag (run different save routine if multisite)
397 is_multisite = typeof is_multisite !== 'undefined' ? is_multisite : false;
398
399 // Set default list if not provided.
400 list_name = typeof list_name !== 'undefined' ? list_name : 'approved';
401
402 var email = $( caller ).parent().find( '.auth-email' );
403
404 var user = {
405 'email': email.val(),
406 'role': '',
407 'date_added': '',
408 'edit_action': 'remove',
409 'multisite_user': is_multisite,
410 };
411
412 // Show an 'empty list' message if we're deleting the last item
413 var list = $( caller ).closest( 'ul' );
414 if ( $( 'li', list ).length <= 1 ) {
415 $( list ).append( '<li class="auth-empty"><em>' + auth_L10n.no_users_in + ' ' + list_name + '</em></li>' );
416 }
417
418 $( caller ).parent().slideUp( 250, function() {
419 // Remove the list item.
420 $( this ).remove();
421
422 // Update the options in the database with this change.
423 update_auth_user( caller, 'access_users_' + list_name, user );
424 });
425 }
426
427
428 // Make changes to one of the user lists (pending, approved, blocked) via ajax.
429 function update_auth_user( caller, setting, users_to_edit ) {
430 var $ = jQuery,
431 access_users_pending = [],
432 access_users_approved = [],
433 access_users_blocked = [],
434 nonce_save_auth_settings = $( '#nonce_save_auth_settings' ).val();
435
436 // Defaults:
437 // setting = 'access_users_pending' or 'access_users_approved' or 'access_users_blocked',
438 // users_to_edit = [
439 // {
440 // email: 'johndoe@example.com',
441 // role: 'subscriber',
442 // date_added: 'Jun 2014',
443 // edit_action: 'add' or 'remove' or 'change_role',
444 // local_user: true or false,
445 // multisite_user: true or false,
446 // }, {
447 // ...
448 // }
449 // ]
450 setting = typeof setting !== 'undefined' ? setting : 'none';
451
452 // If we are only editing a single user, make that user the only item in the array.
453 users_to_edit = typeof users_to_edit !== 'undefined' ? users_to_edit : [];
454 if ( ! Array.isArray( users_to_edit ) ) {
455 users_to_edit = [ users_to_edit ];
456 }
457
458 // Enable wait cursor.
459 $( 'html' ).addClass( 'busy' );
460
461 // Disable button (prevent duplicate clicks).
462 $( caller ).attr( 'disabled', 'disabled' );
463
464 // Enable spinner by element that triggered this event (caller).
465 var $row = $( caller ).closest( 'li' );
466 if ( $row.length > 0 ) {
467 var $spinner = $( '<span class="spinner is-active"></span>' ).css({
468 'position': 'absolute',
469 'top': $row.position().top,
470 'left': $row.position().left + $row.width(),
471 });
472 $row.append( $spinner );
473 }
474
475 // Grab the value of the setting we are saving.
476 if ( setting === 'access_users_pending' ) {
477 access_users_pending = users_to_edit;
478 } else if ( setting === 'access_users_approved' ) {
479 access_users_approved = users_to_edit;
480 } else if ( setting === 'access_users_blocked' ) {
481 access_users_blocked = users_to_edit;
482 }
483
484 $.post( ajaxurl, {
485 'action': 'update_auth_user',
486 'setting': setting,
487 'access_users_pending': access_users_pending,
488 'access_users_approved': access_users_approved,
489 'access_users_blocked': access_users_blocked,
490 'nonce_save_auth_settings': nonce_save_auth_settings,
491 }, function( response ) {
492 // Server responded, but if success isn't true it failed to save.
493 var succeeded = response.success;
494 var spinner_text = succeeded ? auth_L10n.saved + '.' : '<span style="color: red;">' + auth_L10n.failed + '.</span>';
495 var spinner_wait = succeeded ? 500 : 2000;
496
497 // Remove any new user entries that were rejected by the server.
498 if ( response.invalid_emails.length > 0 ) {
499 for ( var i = 0; i < response.invalid_emails.length; i++ ) {
500 var duplicate_email = response.invalid_emails[i];
501 $( 'li.new-user .auth-email[value="' + duplicate_email + '"]' )
502 .siblings( '.spinner' ).addClass( 'duplicate' ).append( '<span class="spinner-text" style="color: red;">' + auth_L10n.duplicate + '.</span>' )
503 .parent().fadeOut( spinner_wait, function () { $( this ).remove(); });
504 }
505 }
506
507 // Show message ('Saved', 'Failed', or 'Saved, removing duplicates').
508 $( 'form .spinner:not(:has(.spinner-text)):not(.duplicate)' ).append( '<span class="spinner-text">' + spinner_text + '</span>' ).delay( spinner_wait ).hide( animation_speed, function() {
509 $( this ).remove();
510 });
511 $( caller ).removeAttr( 'disabled' );
512
513 // Disable wait cursor.
514 $( 'html' ).removeClass( 'busy' );
515 }).fail( function() {
516 // Fail fires if the server doesn't respond or responds with 500 codes
517 var succeeded = false;
518 var spinner_text = succeeded ? auth_L10n.saved + '.' : '<span style="color: red;">' + auth_L10n.failed + '.</span>';
519 var spinner_wait = succeeded ? 500 : 2000;
520 $( 'form .spinner:not(:has(.spinner-text))' ).append( '<span class="spinner-text">' + spinner_text + '</span>' ).delay( spinner_wait ).hide( animation_speed, function() {
521 $( this ).remove();
522 });
523 $( caller ).removeAttr( 'disabled' );
524
525 // Disable wait cursor.
526 $( 'html' ).removeClass( 'busy' );
527 });
528 }
529
530
531 // Multisite functions
532 function save_auth_multisite_settings( caller ) {
533 var $ = jQuery;
534
535 // Enable wait cursor.
536 $( 'html' ).addClass( 'busy' );
537
538 // Disable button (prevent duplicate clicks).
539 $( caller ).attr( 'disabled', 'disabled' );
540
541 // Enable spinner by element that triggered this event (caller).
542 var $spinner = $( '<span class="spinner is-active"></span>' ).css({
543 'position': 'absolute',
544 'top': $( caller ).position().top,
545 'left': $( caller ).position().left + $( caller ).width() + 20,
546 });
547 $( caller ).after( $spinner );
548
549 // Get form elements to save
550
551 var nonce_save_auth_settings = $( '#nonce_save_auth_settings' ).val();
552
553 var multisite_override = $( '#auth_settings_multisite_override' ).is( ':checked' ) ? '1' : '';
554
555 var access_who_can_login = $( 'form input[name="auth_settings[access_who_can_login]"]:checked' ).val();
556
557 var access_who_can_view = $( 'form input[name="auth_settings[access_who_can_view]"]:checked' ).val();
558
559 var access_users_approved = {};
560 $( '#list_auth_settings_access_users_approved li' ).each( function( index ) {
561 var user = {};
562 user.email = $( '.auth-email', this ).val();
563 user.role = $( '.auth-role', this ).val();
564 user.date_added = $( '.auth-date-added', this ).val();
565 user.local_user = $( '.auth-local-user', this ).length !== 0;
566 access_users_approved[index] = user;
567 });
568
569 var access_default_role = $( '#auth_settings_access_default_role' ).val();
570
571 var google = $( '#auth_settings_google' ).is( ':checked' ) ? '1' : '';
572 var google_clientid = $( '#auth_settings_google_clientid' ).val();
573 var google_clientsecret = $( '#auth_settings_google_clientsecret' ).val();
574 var google_hosteddomain = $( '#auth_settings_google_hosteddomain' ).val();
575
576 var cas = $( '#auth_settings_cas' ).is( ':checked' ) ? '1' : '';
577 var cas_custom_label = $( '#auth_settings_cas_custom_label' ).val();
578 var cas_host = $( '#auth_settings_cas_host' ).val();
579 var cas_port = $( '#auth_settings_cas_port' ).val();
580 var cas_path = $( '#auth_settings_cas_path' ).val();
581 var cas_version = $( '#auth_settings_cas_version' ).val();
582 var cas_attr_email = $( '#auth_settings_cas_attr_email' ).val();
583 var cas_attr_first_name = $( '#auth_settings_cas_attr_first_name' ).val();
584 var cas_attr_last_name = $( '#auth_settings_cas_attr_last_name' ).val();
585 var cas_attr_update_on_login = $( '#auth_settings_cas_attr_update_on_login' ).is( ':checked' ) ? '1' : '';
586 var cas_auto_login = $( '#auth_settings_cas_auto_login' ).is( ':checked' ) ? '1' : '';
587
588 var ldap = $( '#auth_settings_ldap' ).is( ':checked' ) ? '1' : '';
589 var ldap_host = $( '#auth_settings_ldap_host' ).val();
590 var ldap_port = $( '#auth_settings_ldap_port' ).val();
591 var ldap_search_base = $( '#auth_settings_ldap_search_base' ).val();
592 var ldap_uid = $( '#auth_settings_ldap_uid' ).val();
593 var ldap_attr_email = $( '#auth_settings_ldap_attr_email' ).val();
594 var ldap_user = $( '#auth_settings_ldap_user' ).val();
595 var ldap_password = $( '#auth_settings_ldap_password' ).val();
596 var ldap_tls = $( '#auth_settings_ldap_tls' ).is( ':checked' ) ? '1' : '';
597 var ldap_lostpassword_url = $( '#auth_settings_ldap_lostpassword_url' ).val();
598 var ldap_attr_first_name = $( '#auth_settings_ldap_attr_first_name' ).val();
599 var ldap_attr_last_name = $( '#auth_settings_ldap_attr_last_name' ).val();
600 var ldap_attr_update_on_login = $( '#auth_settings_ldap_attr_update_on_login' ).is( ':checked' ) ? '1' : '';
601
602 var advanced_lockouts = {
603 'attempts_1': $( '#auth_settings_advanced_lockouts_attempts_1' ).val(),
604 'duration_1': $( '#auth_settings_advanced_lockouts_duration_1' ).val(),
605 'attempts_2': $( '#auth_settings_advanced_lockouts_attempts_2' ).val(),
606 'duration_2': $( '#auth_settings_advanced_lockouts_duration_2' ).val(),
607 'reset_duration': $( '#auth_settings_advanced_lockouts_reset_duration' ).val()
608 };
609 var advanced_hide_wp_login = $( '#auth_settings_advanced_hide_wp_login' ).is( ':checked' ) ? '1' : '';
610 var advanced_widget_enabled = $( '#auth_settings_advanced_widget_enabled' ).is( ':checked' ) ? '1' : '';
611 var advanced_users_per_page = $( '#auth_settings_advanced_users_per_page' ).val();
612 var advanced_users_sort_by = $( '#auth_settings_advanced_users_sort_by' ).val();
613 var advanced_users_sort_order = $( '#auth_settings_advanced_users_sort_order' ).val();
614
615 $.post( ajaxurl, {
616 action: 'save_auth_multisite_settings',
617 'nonce_save_auth_settings': nonce_save_auth_settings,
618 'multisite_override': multisite_override,
619 'access_who_can_login': access_who_can_login,
620 'access_who_can_view': access_who_can_view,
621 'access_users_approved': access_users_approved,
622 'access_default_role': access_default_role,
623 'google': google,
624 'google_clientid': google_clientid,
625 'google_clientsecret': google_clientsecret,
626 'google_hosteddomain': google_hosteddomain,
627 'cas': cas,
628 'cas_custom_label': cas_custom_label,
629 'cas_host': cas_host,
630 'cas_port': cas_port,
631 'cas_path': cas_path,
632 'cas_version': cas_version,
633 'cas_attr_email': cas_attr_email,
634 'cas_attr_first_name': cas_attr_first_name,
635 'cas_attr_last_name': cas_attr_last_name,
636 'cas_attr_update_on_login': cas_attr_update_on_login,
637 'cas_auto_login': cas_auto_login,
638 'ldap': ldap,
639 'ldap_host': ldap_host,
640 'ldap_port': ldap_port,
641 'ldap_search_base': ldap_search_base,
642 'ldap_uid': ldap_uid,
643 'ldap_attr_email': ldap_attr_email,
644 'ldap_user': ldap_user,
645 'ldap_password': ldap_password,
646 'ldap_tls': ldap_tls,
647 'ldap_lostpassword_url': ldap_lostpassword_url,
648 'ldap_attr_first_name': ldap_attr_first_name,
649 'ldap_attr_last_name': ldap_attr_last_name,
650 'ldap_attr_update_on_login': ldap_attr_update_on_login,
651 'advanced_lockouts': advanced_lockouts,
652 'advanced_hide_wp_login': advanced_hide_wp_login,
653 'advanced_users_per_page': advanced_users_per_page,
654 'advanced_users_sort_by': advanced_users_sort_by,
655 'advanced_users_sort_order': advanced_users_sort_order,
656 'advanced_widget_enabled': advanced_widget_enabled,
657 }, function( response ) {
658 var succeeded = response === 'success';
659 var spinner_text = succeeded ? auth_L10n.saved + '.' : '<span style="color: red;">' + auth_L10n.failed + '.</span>';
660 var spinner_wait = succeeded ? 500 : 2000;
661 $( 'form .spinner:not(:has(.spinner-text))' ).append( '<span class="spinner-text">' + spinner_text + '</span>' ).delay( spinner_wait ).hide( animation_speed, function() {
662 $( this ).remove();
663 });
664 $( caller ).removeAttr( 'disabled' );
665
666 // Disable wait cursor.
667 $( 'html' ).removeClass( 'busy' );
668 }).fail( function() {
669 // Fail fires if the server doesn't respond
670 var succeeded = false;
671 var spinner_text = succeeded ? auth_L10n.saved + '.' : '<span style="color: red;">' + auth_L10n.failed + '.</span>';
672 var spinner_wait = succeeded ? 500 : 2000;
673 $( 'form .spinner:not(:has(.spinner-text))' ).append( '<span class="spinner-text">' + spinner_text + '</span>' ).delay( spinner_wait ).hide( animation_speed, function() {
674 $( this ).remove();
675 });
676 $( caller ).removeAttr( 'disabled' );
677
678 // Disable wait cursor.
679 $( 'html' ).removeClass( 'busy' );
680 });
681 }
682
683 // Hide or show (with overlay) the multisite settings based on the "multisite override" setting.
684 function hide_multisite_settings_if_disabled() {
685 var $ = jQuery;
686
687 if ( $( '#auth_settings_multisite_override' ).length === 0 )
688 return;
689
690 var settings = $( '#auth_multisite_settings' );
691 var overlay = $( '#auth_multisite_settings_disabled_overlay' );
692
693 if ( $( '#auth_settings_multisite_override' ).is( ':checked' ) ) {
694 overlay.hide( animation_speed );
695 } else {
696 overlay.css({
697 'background-color': '#f1f1f1',
698 'z-index': 1,
699 'opacity': 0.8,
700 'position': 'absolute',
701 'top': settings.position().top,
702 'left': settings.position().left - 20,
703 'width': '100%',
704 'height': settings.height(),
705 'padding-left': 20,
706 });
707 overlay.show();
708 }
709 }
710
711 // Hide (with overlay) site options if overridden by a multisite option.
712 function hide_multisite_overridden_options() {
713 var $ = jQuery;
714
715 $( '.auth_multisite_override_overlay' ).each( function() {
716 // Option to hide is stored in the overlay's id with 'overlay-hide-' prefix.
717 var option_container_to_hide = $( this ).closest( 'tr' );
718 if ( option_container_to_hide.length > 0 ) {
719 $( this ).css({
720 'background-color': '#f1f1f1',
721 'z-index': 1,
722 'opacity': 0.8,
723 'position': 'absolute',
724 'top': option_container_to_hide.position().top,
725 'left': option_container_to_hide.position().left,
726 'width': '100%',
727 'height': option_container_to_hide.height(),
728 });
729 $( this ).show();
730 }
731 });
732 }
733
734
735
736 // Helper function to remove duplicate entries from an array of strings.
737 function remove_duplicates_from_array_of_strings( a ) {
738 var seen = {};
739 return a.filter( function ( item ) {
740 return seen.hasOwnProperty( item ) ? false : ( seen[item] = true );
741 });
742 }
743
744 // Helper function to hide/show wordpress option
745 function animate_option( action, option ) {
746 var $ = jQuery;
747 if ( action === 'show' ) {
748 $( 'div.animated_wrapper', option ).slideDown( animation_speed );
749 $( 'th', option ).animate({ padding: '20px 10px 20px 0' }, { duration: animation_speed });
750 $( 'td', option ).animate({ padding: '15px 10px' }, { duration: animation_speed });
751 } else if ( action === 'hide' ) {
752 $( 'div.animated_wrapper', option ).slideUp( animation_speed );
753 $( 'td, th', option ).animate({ padding: '0px' }, { duration: animation_speed });
754 } else if ( action === 'hide_immediately' ) {
755 $( 'div.animated_wrapper', option ).hide();
756 $( 'td, th', option ).css({ padding: '0px' });
757 }
758 }
759
760 // Helper function to grab a querystring param value by name
761 function getParameterByName( needle, haystack ) {
762 needle = needle.replace( /[\[]/, "\\\[").replace(/[\]]/, "\\\]" );
763 var regex = new RegExp( "[\\?&]" + needle + "=([^&#]*)" );
764 var results = regex.exec( haystack );
765 if( results === null )
766 return '';
767 else
768 return decodeURIComponent( results[1].replace( /\+/g, " " ) );
769 }
770
771 // Helper function to generate a random string
772 function getRandomId() {
773 var text = "";
774 var possible = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
775 for ( var i=0; i < 5; i++ )
776 text += possible.charAt( Math.floor( Math.random() * possible.length ) );
777 return text;
778 }
779
780 // Helper function to return a short date (e.g., Jul 2013) for today's date
781 function getShortDate( date ) {
782 date = typeof date !== 'undefined' ? date : new Date();
783 var month = '';
784 switch ( date.getMonth() ) {
785 case 0: month = 'Jan'; break;
786 case 1: month = 'Feb'; break;
787 case 2: month = 'Mar'; break;
788 case 3: month = 'Apr'; break;
789 case 4: month = 'May'; break;
790 case 5: month = 'Jun'; break;
791 case 6: month = 'Jul'; break;
792 case 7: month = 'Aug'; break;
793 case 8: month = 'Sep'; break;
794 case 9: month = 'Oct'; break;
795 case 10: month = 'Nov'; break;
796 case 11: month = 'Dec'; break;
797 }
798 return month + ' ' + date.getFullYear();
799 }
800
801 // Helper function to grab a querystring value
802 function querystring( key ) {
803 var re = new RegExp( '(?:\\?|&)'+key+'=(.*?)(?=&|$)', 'gi' );
804 var r = [], m;
805 while ( ( m = re.exec( document.location.search ) ) !== null )
806 r.push( m[1] );
807 return r;
808 }
809
810 // Helper function to check if an email address is valid.
811 function valid_email( email ) {
812 var re = /^(([^<>()[\]\\.,;:\s@\"]+(\.[^<>()[\]\\.,;:\s@\"]+)*)|(\".+\"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/;
813 return email.length > 0 && re.test( email );
814 }
815
816 // Helper function to set or update a querystring value.
817 function updateQueryStringParameter( uri, key, value ) {
818 // Remove the hash before operating on the URI.
819 var i = uri.indexOf( '#' );
820 var hash = i === -1 ? '' : uri.substr( i );
821 uri = i === -1 ? uri : uri.substr( 0, i );
822
823 var re = new RegExp( "([?&])" + key + "=.*?(&|$)", "i" );
824 var separator = uri.indexOf( '?' ) !== -1 ? "&" : "?";
825
826 if ( ! value ) {
827 // Remove key-value pair if empty.
828 uri = uri.replace( new RegExp( "([?&]?)" + key + "=[^&]*", "i" ), '' );
829 if ( uri.slice( -1 ) === '?' ) {
830 uri = uri.slice( 0, -1 );
831 }
832 // Replace first occurrence of & by ? if no ? is present.
833 if ( uri.indexOf( '?' ) === -1 ) {
834 uri = uri.replace( /&/, '?' );
835 }
836 } else if ( uri.match( re ) ) {
837 uri = uri.replace( re, '$1' + key + "=" + value + '$2' );
838 } else {
839 uri = uri + separator + key + "=" + value;
840 }
841 return uri + hash;
842 }
843
844
845 jQuery( document ).ready( function( $ ) {
846 // Grab references to form elements that we will show/hide on page load
847 var auth_settings_access_role_receive_pending_emails = $( '#auth_settings_access_role_receive_pending_emails' ).closest( 'tr' );
848 var auth_settings_access_pending_redirect_to_message = $( '#wp-auth_settings_access_pending_redirect_to_message-wrap' ).closest( 'tr' );
849 var auth_settings_access_blocked_redirect_to_message = $( '#wp-auth_settings_access_blocked_redirect_to_message-wrap' ).closest( 'tr' );
850 var auth_settings_access_should_email_approved_users = $( '#auth_settings_access_should_email_approved_users' ).closest( 'tr' );
851 var auth_settings_access_email_approved_users_subject = $( '#auth_settings_access_email_approved_users_subject' ).closest( 'tr' );
852 var auth_settings_access_email_approved_users_body = $( '#wp-auth_settings_access_email_approved_users_body-wrap' ).closest( 'tr' );
853 var auth_settings_access_public_pages = $( '#auth_settings_access_public_pages' ).closest( 'tr' );
854 var auth_settings_access_redirect_to_login = $( '#radio_auth_settings_access_redirect_to_login' ).closest( 'tr' );
855 var auth_settings_access_public_warning = $( '#radio_auth_settings_access_public_warning' ).closest( 'tr' );
856 var auth_settings_access_redirect_to_message = $( '#wp-auth_settings_access_redirect_to_message-wrap' ).closest( 'tr' );
857 var auth_settings_external_settings_table = $( '#auth_settings_google' ).closest( 'table' );
858 var auth_settings_external_google = $( '#auth_settings_google' ).closest( 'tr' );
859 var auth_settings_external_google_clientid = $( '#auth_settings_google_clientid' ).closest( 'tr' );
860 var auth_settings_external_google_clientsecret = $( '#auth_settings_google_clientsecret' ).closest( 'tr' );
861 var auth_settings_external_google_hosteddomain = $( '#auth_settings_google_hosteddomain' ).closest( 'tr' );
862 var auth_settings_external_cas = $( '#auth_settings_cas' ).closest( 'tr' );
863 var auth_settings_external_cas_custom_label = $( '#auth_settings_cas_custom_label' ).closest( 'tr' );
864 var auth_settings_external_cas_host = $( '#auth_settings_cas_host' ).closest( 'tr' );
865 var auth_settings_external_cas_port = $( '#auth_settings_cas_port' ).closest( 'tr' );
866 var auth_settings_external_cas_path = $( '#auth_settings_cas_path' ).closest( 'tr' );
867 var auth_settings_external_cas_version = $( '#auth_settings_cas_version' ).closest( 'tr' );
868 var auth_settings_external_cas_attr_email = $( '#auth_settings_cas_attr_email' ).closest( 'tr' );
869 var auth_settings_external_cas_attr_first_name = $( '#auth_settings_cas_attr_first_name' ).closest( 'tr' );
870 var auth_settings_external_cas_attr_last_name = $( '#auth_settings_cas_attr_last_name' ).closest( 'tr' );
871 var auth_settings_external_cas_attr_update_on_login = $( '#auth_settings_cas_attr_update_on_login' ).closest( 'tr' );
872 var auth_settings_external_cas_auto_login = $( '#auth_settings_cas_auto_login' ).closest( 'tr' );
873 var auth_settings_external_ldap = $( '#auth_settings_ldap' ).closest( 'tr' );
874 var auth_settings_external_ldap_host = $( '#auth_settings_ldap_host' ).closest( 'tr' );
875 var auth_settings_external_ldap_port = $( '#auth_settings_ldap_port' ).closest( 'tr' );
876 var auth_settings_external_ldap_search_base = $( '#auth_settings_ldap_search_base' ).closest( 'tr' );
877 var auth_settings_external_ldap_uid = $( '#auth_settings_ldap_uid' ).closest( 'tr' );
878 var auth_settings_external_ldap_attr_email = $( '#auth_settings_ldap_attr_email' ).closest( 'tr' );
879 var auth_settings_external_ldap_user = $( '#auth_settings_ldap_user' ).closest( 'tr' );
880 var auth_settings_external_ldap_password = $( '#auth_settings_ldap_password' ).closest( 'tr' );
881 var auth_settings_external_ldap_tls = $( '#auth_settings_ldap_tls' ).closest( 'tr' );
882 var auth_settings_external_ldap_lostpassword_url = $( '#auth_settings_ldap_lostpassword_url' ).closest( 'tr' );
883 var auth_settings_external_ldap_attr_first_name = $( '#auth_settings_ldap_attr_first_name' ).closest( 'tr' );
884 var auth_settings_external_ldap_attr_last_name = $( '#auth_settings_ldap_attr_last_name' ).closest( 'tr' );
885 var auth_settings_external_ldap_attr_update_on_login = $( '#auth_settings_ldap_attr_update_on_login' ).closest( 'tr' );
886
887 // Wrap the th and td in the rows above so we can animate their heights (can't animate tr heights with jquery)
888 $( 'th, td', auth_settings_access_role_receive_pending_emails ).wrapInner( '<div class="animated_wrapper" />' );
889 $( 'th, td', auth_settings_access_pending_redirect_to_message ).wrapInner( '<div class="animated_wrapper" />' );
890 $( 'th, td', auth_settings_access_blocked_redirect_to_message ).wrapInner( '<div class="animated_wrapper" />' );
891 $( 'th, td', auth_settings_access_should_email_approved_users ).wrapInner( '<div class="animated_wrapper" />' );
892 $( 'th, td', auth_settings_access_email_approved_users_subject ).wrapInner( '<div class="animated_wrapper" />' );
893 $( 'th, td', auth_settings_access_email_approved_users_body ).wrapInner( '<div class="animated_wrapper" />' );
894 $( 'th, td', auth_settings_access_public_pages ).wrapInner( '<div class="animated_wrapper" />' );
895 $( 'th, td', auth_settings_access_redirect_to_login ).wrapInner( '<div class="animated_wrapper" />' );
896 $( 'th, td', auth_settings_access_public_warning ).wrapInner( '<div class="animated_wrapper" />' );
897 $( 'th, td', auth_settings_access_redirect_to_message ).wrapInner( '<div class="animated_wrapper" />' );
898 $( 'th, td', auth_settings_external_google_clientid ).wrapInner( '<div class="animated_wrapper" />' );
899 $( 'th, td', auth_settings_external_google_clientsecret ).wrapInner( '<div class="animated_wrapper" />' );
900 $( 'th, td', auth_settings_external_google_hosteddomain ).wrapInner( '<div class="animated_wrapper" />' );
901 $( 'th, td', auth_settings_external_cas_custom_label ).wrapInner( '<div class="animated_wrapper" />' );
902 $( 'th, td', auth_settings_external_cas_host ).wrapInner( '<div class="animated_wrapper" />' );
903 $( 'th, td', auth_settings_external_cas_port ).wrapInner( '<div class="animated_wrapper" />' );
904 $( 'th, td', auth_settings_external_cas_path ).wrapInner( '<div class="animated_wrapper" />' );
905 $( 'th, td', auth_settings_external_cas_version ).wrapInner( '<div class="animated_wrapper" />' );
906 $( 'th, td', auth_settings_external_cas_attr_email ).wrapInner( '<div class="animated_wrapper" />' );
907 $( 'th, td', auth_settings_external_cas_attr_first_name ).wrapInner( '<div class="animated_wrapper" />' );
908 $( 'th, td', auth_settings_external_cas_attr_last_name ).wrapInner( '<div class="animated_wrapper" />' );
909 $( 'th, td', auth_settings_external_cas_attr_update_on_login ).wrapInner( '<div class="animated_wrapper" />' );
910 $( 'th, td', auth_settings_external_cas_auto_login ).wrapInner( '<div class="animated_wrapper" />' );
911 $( 'th, td', auth_settings_external_ldap_host ).wrapInner( '<div class="animated_wrapper" />' );
912 $( 'th, td', auth_settings_external_ldap_port ).wrapInner( '<div class="animated_wrapper" />' );
913 $( 'th, td', auth_settings_external_ldap_search_base ).wrapInner( '<div class="animated_wrapper" />' );
914 $( 'th, td', auth_settings_external_ldap_uid ).wrapInner( '<div class="animated_wrapper" />' );
915 $( 'th, td', auth_settings_external_ldap_attr_email ).wrapInner( '<div class="animated_wrapper" />' );
916 $( 'th, td', auth_settings_external_ldap_user ).wrapInner( '<div class="animated_wrapper" />' );
917 $( 'th, td', auth_settings_external_ldap_password ).wrapInner( '<div class="animated_wrapper" />' );
918 $( 'th, td', auth_settings_external_ldap_tls ).wrapInner( '<div class="animated_wrapper" />' );
919 $( 'th, td', auth_settings_external_ldap_lostpassword_url ).wrapInner( '<div class="animated_wrapper" />' );
920 $( 'th, td', auth_settings_external_ldap_attr_first_name ).wrapInner( '<div class="animated_wrapper" />' );
921 $( 'th, td', auth_settings_external_ldap_attr_last_name ).wrapInner( '<div class="animated_wrapper" />' );
922 $( 'th, td', auth_settings_external_ldap_attr_update_on_login ).wrapInner( '<div class="animated_wrapper" />' );
923
924 // If we're viewing the dashboard widget, reset a couple of the relevant
925 // option variables (since they aren't nested in table rows).
926 if ( $( '#auth_dashboard_widget' ).length ) {
927 // Remove the helper link, since there are no tabs on the dashboard widget
928 $( '#dashboard_link_approved_users' ).contents().unwrap();
929 }
930
931 // Hide settings unless "Only approved users" is checked
932 if ( ! $( '#radio_auth_settings_access_who_can_login_approved_users' ).is( ':checked' ) ) {
933 animate_option( 'hide_immediately', auth_settings_access_role_receive_pending_emails );
934 animate_option( 'hide_immediately', auth_settings_access_pending_redirect_to_message );
935 animate_option( 'hide_immediately', auth_settings_access_blocked_redirect_to_message );
936 animate_option( 'hide_immediately', auth_settings_access_should_email_approved_users );
937 }
938
939 // Hide Welcome email body/subject options if "Send welcome email" is off.
940 if ( ! $( '#auth_settings_access_should_email_approved_users' ).is( ':checked' ) ) {
941 animate_option( 'hide_immediately', auth_settings_access_email_approved_users_subject );
942 animate_option( 'hide_immediately', auth_settings_access_email_approved_users_body );
943 }
944
945 // On load: Show/hide public access options if everyone can see site
946 if ( ! $( '#radio_auth_settings_access_who_can_view_logged_in_users' ).is( ':checked' ) ) {
947 animate_option( 'hide_immediately', auth_settings_access_public_pages );
948 animate_option( 'hide_immediately', auth_settings_access_redirect_to_login );
949 animate_option( 'hide_immediately', auth_settings_access_public_warning );
950 animate_option( 'hide_immediately', auth_settings_access_redirect_to_message );
951 }
952
953 // Hide Google options if unchecked
954 if ( ! $( '#auth_settings_google' ).is( ':checked' ) ) {
955 animate_option( 'hide_immediately', auth_settings_external_google_clientid );
956 animate_option( 'hide_immediately', auth_settings_external_google_clientsecret );
957 animate_option( 'hide_immediately', auth_settings_external_google_hosteddomain );
958 }
959
960 // Hide CAS options if unchecked
961 if ( ! $( '#auth_settings_cas' ).is( ':checked' ) ) {
962 animate_option( 'hide_immediately', auth_settings_external_cas_custom_label );
963 animate_option( 'hide_immediately', auth_settings_external_cas_host );
964 animate_option( 'hide_immediately', auth_settings_external_cas_port );
965 animate_option( 'hide_immediately', auth_settings_external_cas_path );
966 animate_option( 'hide_immediately', auth_settings_external_cas_version );
967 animate_option( 'hide_immediately', auth_settings_external_cas_attr_email );
968 animate_option( 'hide_immediately', auth_settings_external_cas_attr_first_name );
969 animate_option( 'hide_immediately', auth_settings_external_cas_attr_last_name );
970 animate_option( 'hide_immediately', auth_settings_external_cas_attr_update_on_login );
971 animate_option( 'hide_immediately', auth_settings_external_cas_auto_login );
972 }
973
974 // Hide LDAP options if unchecked
975 if ( ! $( '#auth_settings_ldap' ).is( ':checked' ) ) {
976 animate_option( 'hide_immediately', auth_settings_external_ldap_host );
977 animate_option( 'hide_immediately', auth_settings_external_ldap_port );
978 animate_option( 'hide_immediately', auth_settings_external_ldap_search_base );
979 animate_option( 'hide_immediately', auth_settings_external_ldap_uid );
980 animate_option( 'hide_immediately', auth_settings_external_ldap_attr_email );
981 animate_option( 'hide_immediately', auth_settings_external_ldap_user );
982 animate_option( 'hide_immediately', auth_settings_external_ldap_password );
983 animate_option( 'hide_immediately', auth_settings_external_ldap_tls );
984 animate_option( 'hide_immediately', auth_settings_external_ldap_lostpassword_url );
985 animate_option( 'hide_immediately', auth_settings_external_ldap_attr_first_name );
986 animate_option( 'hide_immediately', auth_settings_external_ldap_attr_last_name );
987 animate_option( 'hide_immediately', auth_settings_external_ldap_attr_update_on_login );
988 }
989
990 // Event handler: Hide "Handle unauthorized visitors" option if access is granted to "Everyone"
991 $( 'input[name="auth_settings[access_who_can_login]"]' ).change( function() {
992 // Hide settings unless "Only approved users" is checked
993 var action = $( '#radio_auth_settings_access_who_can_login_approved_users' ).is( ':checked' ) ? 'show' : 'hide';
994 animate_option( action, auth_settings_access_role_receive_pending_emails );
995 animate_option( action, auth_settings_access_pending_redirect_to_message );
996 animate_option( action, auth_settings_access_blocked_redirect_to_message );
997 animate_option( action, auth_settings_access_should_email_approved_users );
998 action = action === 'show' && $( '#auth_settings_access_should_email_approved_users' ).is( ':checked' ) ? 'show' : 'hide_immediately';
999 animate_option( action, auth_settings_access_email_approved_users_subject );
1000 animate_option( action, auth_settings_access_email_approved_users_body );
1001 });
1002
1003 // Event handler: Hide Welcome email body/subject options if "Send welcome email" is off.
1004 $( 'input[name="auth_settings[access_should_email_approved_users]"]' ).change( function() {
1005 var action = $( this ).is( ':checked' ) ? 'show' : 'hide';
1006 animate_option( action, auth_settings_access_email_approved_users_subject );
1007 animate_option( action, auth_settings_access_email_approved_users_body );
1008 });
1009
1010 // Event handler: Hide "Handle unauthorized visitors" option if access is granted to "Everyone"
1011 $( 'input[name="auth_settings[access_who_can_view]"]' ).change( function() {
1012 var action = $( '#radio_auth_settings_access_who_can_view_everyone' ).is( ':checked' ) ? 'hide' : 'show';
1013 animate_option( action, auth_settings_access_redirect_to_login );
1014 animate_option( action, auth_settings_access_redirect_to_message );
1015 animate_option( action, auth_settings_access_public_pages );
1016 animate_option( action, auth_settings_access_public_warning );
1017 });
1018
1019 // Event handler: Show/hide Google options based on checkbox
1020 $( 'input[name="auth_settings[google]"]' ).change( function() {
1021 var action = $( this ).is( ':checked' ) ? 'show' : 'hide';
1022 animate_option( action, auth_settings_external_google_clientid );
1023 animate_option( action, auth_settings_external_google_clientsecret );
1024 animate_option( action, auth_settings_external_google_hosteddomain );
1025 });
1026
1027 // Event handler: Show/hide CAS options based on checkbox
1028 $( 'input[name="auth_settings[cas]"]' ).change( function() {
1029 var action = $( this ).is( ':checked' ) ? 'show' : 'hide';
1030 animate_option( action, auth_settings_external_cas_custom_label );
1031 animate_option( action, auth_settings_external_cas_host );
1032 animate_option( action, auth_settings_external_cas_port );
1033 animate_option( action, auth_settings_external_cas_path );
1034 animate_option( action, auth_settings_external_cas_version );
1035 animate_option( action, auth_settings_external_cas_attr_email );
1036 animate_option( action, auth_settings_external_cas_attr_first_name );
1037 animate_option( action, auth_settings_external_cas_attr_last_name );
1038 animate_option( action, auth_settings_external_cas_attr_update_on_login );
1039 animate_option( action, auth_settings_external_cas_auto_login );
1040 });
1041
1042 // Event handler: Show/hide LDAP options based on checkbox
1043 $( 'input[name="auth_settings[ldap]"]' ).change( function() {
1044 var action = $( this ).is( ':checked' ) ? 'show' : 'hide';
1045 animate_option( action, auth_settings_external_ldap_host );
1046 animate_option( action, auth_settings_external_ldap_port );
1047 animate_option( action, auth_settings_external_ldap_search_base );
1048 animate_option( action, auth_settings_external_ldap_uid );
1049 animate_option( action, auth_settings_external_ldap_attr_email );
1050 animate_option( action, auth_settings_external_ldap_user );
1051 animate_option( action, auth_settings_external_ldap_password );
1052 animate_option( action, auth_settings_external_ldap_tls );
1053 animate_option( action, auth_settings_external_ldap_lostpassword_url );
1054 animate_option( action, auth_settings_external_ldap_attr_first_name );
1055 animate_option( action, auth_settings_external_ldap_attr_last_name );
1056 animate_option( action, auth_settings_external_ldap_attr_update_on_login );
1057 });
1058
1059 // Show save button if usermeta field is modified.
1060 $( 'form input.auth-usermeta' ).on( 'keyup', function ( event ) {
1061 // Don't do anything if tab or arrow keys were pressed.
1062 if ( event.which === 9 || event.which === 37 || event.which === 38 || event.which === 39 || event.which === 40 ) {
1063 return;
1064 }
1065 $( this ).siblings( '.button' ).css( 'display', 'inline-block' );
1066 });
1067
1068 // List management function: pressing enter in the new approved or new
1069 // blocked user (email or role field) adds the user to the list.
1070 $( '#new_approved_user_email, #new_approved_user_role, #new_blocked_user_email' ).on( 'keyup', function( e ) {
1071 // For textareas, make ctrl-enter add the user; for inputs, make enter add the user.
1072 if ( $( this ).is( 'textarea' ) ) {
1073 if ( e.which == 13 && ( e.ctrlKey || e.altKey ) ) { // Enter key (without Ctrl modifier)
1074 $( this ).parent().find( 'a' ).trigger( 'click' );
1075 }
1076 } else if ( e.which == 13 ) { // Enter key on input[type="text"]
1077 $( this ).parent().find( 'a' ).trigger( 'click' );
1078 e.preventDefault();
1079 }
1080 });
1081
1082 // Don't submit form (i.e., save options) when hitting enter in any user list field.
1083 $( 'input.auth-email, select.auth-role, input.auth-date-added, input.auth-usermeta' ).on( 'keydown', function( e ) {
1084 if ( e.which == 13 ) { // Enter key
1085 e.preventDefault();
1086 return false;
1087 }
1088 });
1089
1090 // Enable the user-friendly multiselect form element on the options page.
1091 $( '#auth_settings_access_public_pages' ).multiSelect({
1092 selectableOptgroup: true,
1093 selectableHeader: '<div class="custom-header">' + auth_L10n.private_pages + '</div>',
1094 selectionHeader: '<div class="custom-header">' + auth_L10n.public_pages + '</div>',
1095 });
1096
1097 // Switch to the first tab (or the tab indicated in sessionStorage, or the querystring).
1098 var tab = '';
1099 if ( querystring( 'tab' ).length > 0 ) {
1100 tab = querystring( 'tab' )[0];
1101 } else if ( sessionStorage.getItem( 'tab' ) ) {
1102 tab = sessionStorage.getItem( 'tab' );
1103 }
1104 if ( $.inArray( tab, [ 'access_lists', 'access_login', 'access_public', 'external', 'advanced' ] ) < 0 ) {
1105 tab = 'access_lists';
1106 }
1107 choose_tab( tab, animation_speed );
1108
1109 // Hide/show multisite settings based on override checkbox.
1110 $( 'input[name="auth_settings[multisite_override]"]' ).change( function() {
1111 hide_multisite_settings_if_disabled();
1112 });
1113 hide_multisite_settings_if_disabled();
1114
1115 // Wire up pager events on Approved User list (first/last/next/previous
1116 // buttons, go to page text input, and search.
1117 $( '#current-page-selector, #user-search-input' ).on( 'keydown', function ( e ) {
1118 if ( e.which == 13 ) { // Enter key
1119 var searchTerm = $( '#user-search-input' ).val();
1120 var currentPage = parseInt( $( this ).val() ) || 1;
1121 var totalPages = parseInt( $( '.total-pages' ).first().text().replace( /[^0-9]/g, '' ) ) || 1;
1122
1123 // Make sure current page is between 1 and max pages.
1124 if ( currentPage < 1 ) {
1125 currentPage = 1;
1126 } else if ( currentPage > totalPages ) {
1127 currentPage = totalPages;
1128 }
1129
1130 // Update user list with users on next page.
1131 refresh_approved_user_list( currentPage, searchTerm );
1132
1133 // Prevent default behavior.
1134 e.preventDefault();
1135 return false;
1136 }
1137 });
1138 $( '.tablenav' ).on( 'click', '.pagination-links a, #search-submit', function ( e ) {
1139 var searchTerm = $( '#user-search-input' ).val();
1140 var currentPage = parseInt( getParameterByName( 'paged', $( this ).attr( 'href' ) ) ) || 1;
1141 var totalPages = parseInt( $( '.total-pages' ).first().text().replace( /[^0-9]/g, '' ) ) || 1;
1142 if ( currentPage > totalPages ) {
1143 currentPage = totalPages;
1144 }
1145
1146 // Update user list with users on next page.
1147 refresh_approved_user_list( currentPage, searchTerm );
1148
1149 // Remove focus from clicked element.
1150 $( this ).blur();
1151
1152 // Prevent default behavior.
1153 e.preventDefault();
1154 return false;
1155 });
1156
1157 // Enable growable textarea for new user field.
1158 $( 'textarea#new_approved_user_email' ).autogrow();
1159
1160 });
1161
1162
1163 /**
1164 * Portions below from Bootstrap
1165 * http://getbootstrap.com/getting-started/#download
1166 */
1167
1168
1169 /*!
1170 * Bootstrap v3.1.1 (http://getbootstrap.com)
1171 * Copyright 2011-2014 Twitter, Inc.
1172 * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
1173 */
1174
1175 if ( typeof jQuery === 'undefined' ) { throw new Error( 'Bootstrap\'s JavaScript requires jQuery' ) }
1176
1177 /* ========================================================================
1178 * Bootstrap: dropdown.js v3.1.1
1179 * http://getbootstrap.com/javascript/#dropdowns
1180 * ========================================================================
1181 * Copyright 2011-2014 Twitter, Inc.
1182 * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
1183 * ======================================================================== */
1184
1185
1186 +function ($) {
1187 'use strict';
1188
1189 // DROPDOWN CLASS DEFINITION
1190 // =========================
1191
1192 var backdrop = '.dropdown-backdrop'
1193 var toggle = '[data-toggle=dropdown]'
1194 var Dropdown = function ( element ) {
1195 $( element ).on( 'click.bs.dropdown', this.toggle)
1196 }
1197
1198 Dropdown.prototype.toggle = function ( e ) {
1199 var $this = $( this )
1200
1201 if ($this.is( '.disabled, :disabled' )) return
1202
1203 var $parent = getParent($this)
1204 var isActive = $parent.hasClass( 'open' )
1205
1206 clearMenus()
1207
1208 if (!isActive) {
1209 if ( 'ontouchstart' in document.documentElement && !$parent.closest( '.navbar-nav' ).length) {
1210 // if mobile we use a backdrop because click events don't delegate
1211 $( '<div class="dropdown-backdrop"/>' ).insertAfter($( this )).on( 'click', clearMenus)
1212 }
1213
1214 var relatedTarget = { relatedTarget: this }
1215 $parent.trigger( e = $.Event( 'show.bs.dropdown', relatedTarget ) )
1216
1217 if (e.isDefaultPrevented()) return
1218
1219 $parent
1220 .toggleClass( 'open' )
1221 .trigger( 'shown.bs.dropdown', relatedTarget)
1222
1223 $this.focus()
1224 }
1225
1226 return false
1227 }
1228
1229 Dropdown.prototype.keydown = function (e) {
1230 if (!/(38|40|27)/.test(e.keyCode)) return
1231
1232 var $this = $( this )
1233
1234 e.preventDefault()
1235 e.stopPropagation()
1236
1237 if ($this.is( '.disabled, :disabled' )) return
1238
1239 var $parent = getParent($this)
1240 var isActive = $parent.hasClass( 'open' )
1241
1242 if (!isActive || (isActive && e.keyCode == 27)) {
1243 if (e.which == 27) $parent.find(toggle).focus()
1244 return $this.click()
1245 }
1246
1247 var desc = ' li:not(.divider):visible a'
1248 var $items = $parent.find( '[role=menu]' + desc + ', [role=listbox]' + desc)
1249
1250 if (!$items.length) return
1251
1252 var index = $items.index($items.filter( ':focus' ))
1253
1254 if (e.keyCode == 38 && index > 0) index-- // up
1255 if (e.keyCode == 40 && index < $items.length - 1) index++ // down
1256 if (!~index) index = 0
1257
1258 $items.eq(index).focus()
1259 }
1260
1261 function clearMenus(e) {
1262 $(backdrop).remove()
1263 $(toggle).each(function () {
1264 var $parent = getParent($( this ))
1265 var relatedTarget = { relatedTarget: this }
1266 if (!$parent.hasClass( 'open' )) return
1267 $parent.trigger(e = $.Event( 'hide.bs.dropdown', relatedTarget))
1268 if (e.isDefaultPrevented()) return
1269 $parent.removeClass( 'open' ).trigger( 'hidden.bs.dropdown', relatedTarget)
1270 })
1271 }
1272
1273 function getParent($this) {
1274 var selector = $this.attr( 'data-target' )
1275
1276 if (!selector) {
1277 selector = $this.attr( 'href' )
1278 selector = selector && /#[A-Za-z]/.test(selector) && selector.replace(/.*(?=#[^\s]*$)/, '' ) //strip for ie7
1279 }
1280
1281 var $parent = selector && $(selector)
1282
1283 return $parent && $parent.length ? $parent : $this.parent()
1284 }
1285
1286
1287 // DROPDOWN PLUGIN DEFINITION
1288 // ==========================
1289
1290 var old = $.fn.dropdown
1291
1292 $.fn.dropdown = function (option) {
1293 return this.each(function () {
1294 var $this = $( this )
1295 var data = $this.data( 'bs.dropdown' )
1296
1297 if (!data) $this.data( 'bs.dropdown', (data = new Dropdown( this )))
1298 if (typeof option == 'string' ) data[option].call($this)
1299 })
1300 }
1301
1302 $.fn.dropdown.Constructor = Dropdown
1303
1304
1305 // DROPDOWN NO CONFLICT
1306 // ====================
1307
1308 $.fn.dropdown.noConflict = function () {
1309 $.fn.dropdown = old
1310 return this
1311 }
1312
1313
1314 // APPLY TO STANDARD DROPDOWN ELEMENTS
1315 // ===================================
1316
1317 $(document)
1318 .on( 'click.bs.dropdown.data-api', clearMenus)
1319 .on( 'click.bs.dropdown.data-api', '.dropdown form', function (e) { e.stopPropagation() })
1320 .on( 'click.bs.dropdown.data-api', toggle, Dropdown.prototype.toggle)
1321 .on( 'keydown.bs.dropdown.data-api', toggle + ', [role=menu], [role=listbox]', Dropdown.prototype.keydown)
1322
1323 }(jQuery);
1324