: str_replace(): Passing null to parameter #2 ($replace) of type array|string is deprecated in
if ( wp.updates.searchTerm === data.s && 'typechange' !== eventtype ) {
wp.updates.searchTerm = data.s;
if ( window.history && window.history.replaceState ) {
window.history.replaceState( null, '', searchLocation );
if ( ! $searchTab.length ) {
$searchTab = $( '<li class="plugin-install-search" />' )
'text': __( 'Search Results' )
$( '.wp-filter .filter-links .current' )
.removeClass( 'current' )
.parents( '.filter-links' )
$pluginFilter.prev( 'p' ).remove();
$( '.plugins-popular-tags-wrapper' ).remove();
if ( 'undefined' !== typeof wp.updates.searchRequest ) {
wp.updates.searchRequest.abort();
$( 'body' ).addClass( 'loading-content' );
wp.updates.searchRequest = wp.ajax.post( 'search-install-plugins', data ).done( function( response ) {
$( 'body' ).removeClass( 'loading-content' );
$pluginFilter.append( response.items );
delete wp.updates.searchRequest;
if ( 0 === response.count ) {
wp.a11y.speak( __( 'You do not appear to have any plugins available at this time.' ) );
/* translators: %s: Number of plugins. */
__( 'Number of plugins found: %d' ),
if ( $pluginSearch.length ) {
$pluginSearch.attr( 'aria-describedby', 'live-search-desc' );
* Handles changes to the plugin search box on the Installed Plugins screen,
* searching the plugin list dynamically.
$pluginSearch.on( 'keyup input', _.debounce( function( event ) {
_ajax_nonce: wp.updates.ajaxNonce,
s: encodeURIComponent( event.target.value ),
if ( 'keyup' === event.type && 27 === event.which ) {
if ( wp.updates.searchTerm === data.s ) {
wp.updates.searchTerm = data.s;
queryArgs = _.object( _.compact( _.map( location.search.slice( 1 ).split( '&' ), function( item ) {
if ( item ) return item.split( '=' );
data.plugin_status = queryArgs.plugin_status || 'all';
if ( window.history && window.history.replaceState ) {
window.history.replaceState( null, '', location.href.split( '?' )[ 0 ] + '?s=' + data.s + '&plugin_status=' + data.plugin_status );
if ( 'undefined' !== typeof wp.updates.searchRequest ) {
wp.updates.searchRequest.abort();
$( 'body' ).addClass( 'loading-content' );
$( '.subsubsub .current' ).removeClass( 'current' );
wp.updates.searchRequest = wp.ajax.post( 'search-plugins', data ).done( function( response ) {
// Can we just ditch this whole subtitle business?
var $subTitle = $( '<span />' ).addClass( 'subtitle' ).html(
/* translators: %s: Search query. */
__( 'Search results for: %s' ),
'<strong>' + _.escape( decodeURIComponent( data.s ) ) + '</strong>'
$oldSubTitle = $( '.wrap .subtitle' );
$( '.subsubsub .' + data.plugin_status + ' a' ).addClass( 'current' );
} else if ( $oldSubTitle.length ) {
$oldSubTitle.replaceWith( $subTitle );
$( '.wp-header-end' ).before( $subTitle );
$( 'body' ).removeClass( 'loading-content' );
$bulkActionForm.append( response.items );
delete wp.updates.searchRequest;
if ( 0 === response.count ) {
wp.a11y.speak( __( 'No plugins found. Try a different search.' ) );
/* translators: %s: Number of plugins. */
__( 'Number of plugins found: %d' ),
* Trigger a search event when the search form gets submitted.
$document.on( 'submit', '.search-plugins', function( event ) {
$( 'input.wp-filter-search' ).trigger( 'input' );
* Trigger a search event when the "Try Again" button is clicked.
$document.on( 'click', '.try-again', function( event ) {
$pluginInstallSearch.trigger( 'input' );
* Trigger a search event when the search type gets changed.
$( '#typeselector' ).on( 'change', function() {
var $search = $( 'input[name="s"]' );
if ( $search.val().length ) {
$search.trigger( 'input', 'typechange' );
* Click handler for updating a plugin from the details modal on `plugin-install.php`.
* @param {Event} event Event interface.
$( '#plugin_update_from_iframe' ).on( 'click', function( event ) {
var target = window.parent === window ? null : window.parent,
$.support.postMessage = !! window.postMessage;
if ( false === $.support.postMessage || null === target || -1 !== window.parent.location.pathname.indexOf( 'update-core.php' ) ) {
plugin: $( this ).data( 'plugin' ),
slug: $( this ).data( 'slug' )
target.postMessage( JSON.stringify( update ), window.location.origin );
* Handles postMessage events.
* @since 4.6.0 Switched `update-plugin` action to use the queue.
* @param {Event} event Event interface.
$( window ).on( 'message', function( event ) {
var originalEvent = event.originalEvent,
expectedOrigin = document.location.protocol + '//' + document.location.host,
if ( originalEvent.origin !== expectedOrigin ) {
message = JSON.parse( originalEvent.data );
'undefined' !== typeof message.status &&
'undefined' !== typeof message.slug &&
'undefined' !== typeof message.text &&
'undefined' !== typeof message.ariaLabel
var $card = $( '.plugin-card-' + message.slug ),
$message = $card.find( '[data-slug="' + message.slug + '"]' );
if ( 'undefined' !== typeof message.removeClasses ) {
$message.removeClass( message.removeClasses );
if ( 'undefined' !== typeof message.addClasses ) {
$message.addClass( message.addClasses );
if ( '' === message.ariaLabel ) {
$message.removeAttr( 'aria-label' );
$message.attr( 'aria-label', message.ariaLabel );
if ( 'dependencies-check-success' === message.status ) {
.attr( 'data-name', message.pluginName )
.attr( 'data-slug', message.slug )
.attr( 'data-plugin', message.plugin )
.attr( 'href', message.href );
$message.text( message.text );
if ( 'undefined' === typeof message.action ) {
switch ( message.action ) {
// Called from `wp-admin/includes/class-wp-upgrader-skins.php`.
case 'decrementUpdateCount':
/** @property {string} message.upgradeType */
wp.updates.decrementCount( message.upgradeType );
if ( 'undefined' === typeof message.data || 'undefined' === typeof message.data.slug ) {
message.data = wp.updates._addCallbacks( message.data, message.action );
wp.updates.queue.push( message );
wp.updates.queueChecker();
* Adds a callback to display a warning before leaving the page.
$( window ).on( 'beforeunload', wp.updates.beforeunload );
* Prevents the page form scrolling when activating auto-updates with the Spacebar key.
$document.on( 'keydown', '.column-auto-updates .toggle-auto-update, .theme-overlay .toggle-auto-update', function( event ) {
if ( 32 === event.which ) {
* Click and keyup handler for enabling and disabling plugin and theme auto-updates.
* These controls can be either links or buttons. When JavaScript is enabled,
* we want them to behave like buttons. An ARIA role `button` is added via
* the JavaScript that targets elements with the CSS class `aria-button-if-js`.
$document.on( 'click keyup', '.column-auto-updates .toggle-auto-update, .theme-overlay .toggle-auto-update', function( event ) {
var data, asset, type, $parent,
action = $toggler.attr( 'data-wp-action' ),
$label = $toggler.find( '.label' );
if ( 'keyup' === event.type && 32 !== event.which ) {
if ( 'themes' !== pagenow ) {
$parent = $toggler.closest( '.column-auto-updates' );
$parent = $toggler.closest( '.theme-autoupdate' );
// Prevent multiple simultaneous requests.
if ( $toggler.attr( 'data-doing-ajax' ) === 'yes' ) {
$toggler.attr( 'data-doing-ajax', 'yes' );
asset = $toggler.closest( 'tr' ).attr( 'data-plugin' );
asset = $toggler.closest( 'tr' ).attr( 'data-slug' );
asset = $toggler.attr( 'data-slug' );
// Clear any previous errors.
$parent.find( '.notice.notice-error' ).addClass( 'hidden' );
if ( 'enable' === action ) {
$label.text( __( 'Enabling...' ) );
$label.text( __( 'Disabling...' ) );
$toggler.find( '.dashicons-update' ).removeClass( 'hidden' );
action: 'toggle-auto-updates',
_ajax_nonce: settings.ajax_nonce,
$.post( window.ajaxurl, data )
.done( function( response ) {
var $enabled, $disabled, enabledNumber, disabledNumber, errorMessage,
href = $toggler.attr( 'href' );
if ( ! response.success ) {
// if WP returns 0 for response (which can happen in a few cases),
// output the general error message since we won't have response.data.error.
if ( response.data && response.data.error ) {
errorMessage = response.data.error;
errorMessage = __( 'The request could not be completed.' );
$parent.find( '.notice.notice-error' ).removeClass( 'hidden' ).find( 'p' ).text( errorMessage );
wp.a11y.speak( errorMessage, 'assertive' );
// Update the counts in the enabled/disabled views if on a screen
if ( 'themes' !== pagenow ) {
$enabled = $( '.auto-update-enabled span' );
$disabled = $( '.auto-update-disabled span' );
enabledNumber = parseInt( $enabled.text().replace( /[^\d]+/g, '' ), 10 ) || 0;
disabledNumber = parseInt( $disabled.text().replace( /[^\d]+/g, '' ), 10 ) || 0;
enabledNumber = Math.max( 0, enabledNumber );
disabledNumber = Math.max( 0, disabledNumber );
$enabled.text( '(' + enabledNumber + ')' );
$disabled.text( '(' + disabledNumber + ')' );
if ( 'enable' === action ) {
// The toggler control can be either a link or a button.
if ( $toggler[ 0 ].hasAttribute( 'href' ) ) {
href = href.replace( 'action=enable-auto-update', 'action=disable-auto-update' );
$toggler.attr( 'href', href );
$toggler.attr( 'data-wp-action', 'disable' );
$label.text( __( 'Disable auto-updates' ) );
$parent.find( '.auto-update-time' ).removeClass( 'hidden' );
wp.a11y.speak( __( 'Auto-updates enabled' ) );
// The toggler control can be either a link or a button.
if ( $toggler[ 0 ].hasAttribute( 'href' ) ) {
href = href.replace( 'action=disable-auto-update', 'action=enable-auto-update' );
$toggler.attr( 'href', href );
$toggler.attr( 'data-wp-action', 'enable' );
$label.text( __( 'Enable auto-updates' ) );
$parent.find( '.auto-update-time' ).addClass( 'hidden' );
wp.a11y.speak( __( 'Auto-updates disabled' ) );
$document.trigger( 'wp-auto-update-setting-changed', { state: action, type: type, asset: asset } );
$parent.find( '.notice.notice-error' )
.text( __( 'The request could not be completed.' ) );
wp.a11y.speak( __( 'The request could not be completed.' ), 'assertive' );
$toggler.removeAttr( 'data-doing-ajax' ).find( '.dashicons-update' ).addClass( 'hidden' );
})( jQuery, window.wp, window._wpUpdatesSettings );