Make WordPress Core

Opened 7 years ago

Closed 4 months ago

#43160 closed enhancement (wontfix)

Reduce wp-admin/update-core.php load time by half

Reported by: lano1106's profile lano1106 Owned by: pbearne's profile pbearne
Milestone: Priority: normal
Severity: normal Version: 4.9.2
Component: Upgrade/Install Keywords: has-patch
Focuses: administration, performance Cc:

Description

I had this problem where loading this page was taking over a minute.
It turns out that this is caused by premium plugins that makes remote calls to validate license and/or verify the existence of update.

My whole journey is documented here:
https://wordpress.org/support/topic/displaying-wp-admin-update-core-php-takes-about-50-secs/

There is not much that can be done about that but this can be mitigated a lot when you realise that wp_update_plugins() calls set_site_transient() twice and this is where the expensive hook calls are made.

So here is my attempt to improve the situation:

$ diff wp-includes/option.php{.orig,}
1721a1722,1759
>  * Set/update the value of a site transient without calling the sometimes expensive hooks.
>  *
>  * This is particularly for the special case of wp_update_plugins() where set_site_transient() was called twice
>  * and the first time was only for setting up the last_checked update_plugins option.
>  *
>  * @since 4.9.2
>  *
>  * @see wp_update_plugins()
>  *
>  * @param string $transient  Transient name. Expected to not be SQL-escaped. Must be
>  *                           167 characters or fewer in length.
>  * @param mixed  $value      Transient value. Expected to not be SQL-escaped.
>  * @param int    $expiration Optional. Time until expiration in seconds. Default 0 (no expiration).
>  * @return bool False if value was not set and true if value was set.
>  */
> function set_site_transient_nohook( $transient, $value, $expiration = 0 ) {
> 
>     $expiration = (int) $expiration;
> 
> 	if ( wp_using_ext_object_cache() ) {
> 		$result = wp_cache_set( $transient, $value, 'site-transient', $expiration );
> 	} else {
> 		$transient_timeout = '_site_transient_timeout_' . $transient;
> 		$option = '_site_transient_' . $transient;
> 		if ( false === get_site_option( $option ) ) {
> 			if ( $expiration )
> 				add_site_option( $transient_timeout, time() + $expiration );
> 			$result = add_site_option( $option, $value );
> 		} else {
> 			if ( $expiration )
> 				update_site_option( $transient_timeout, time() + $expiration );
> 			$result = update_site_option( $option, $value );
> 		}
> 	}
> 	return $result;
> }
> 
> /**
1767,1781c1805
< 	if ( wp_using_ext_object_cache() ) {
< 		$result = wp_cache_set( $transient, $value, 'site-transient', $expiration );
< 	} else {
< 		$transient_timeout = '_site_transient_timeout_' . $transient;
< 		$option = '_site_transient_' . $transient;
< 		if ( false === get_site_option( $option ) ) {
< 			if ( $expiration )
< 				add_site_option( $transient_timeout, time() + $expiration );
< 			$result = add_site_option( $option, $value );
< 		} else {
< 			if ( $expiration )
< 				update_site_option( $transient_timeout, time() + $expiration );
< 			$result = update_site_option( $option, $value );
< 		}
< 	}
---
> 	$result = set_site_transient_nohook( $transient, $value, $expiration );
$ diff wp-includes/update.php{.orig,}
68c68
< 	set_site_transient( 'update_core', $current );
---
> 	set_site_transient_nohook( 'update_plugins', $current );

Attachments (1)

a43160.diff (3.2 KB) - added by kitchin 7 years ago.
Here it is as a patch against trunk. Not tested.

Download all attachments as: .zip

Change History (10)

@kitchin
7 years ago

Here it is as a patch against trunk. Not tested.

#1 @lano1106
7 years ago

Hi, I have new info concerning my wp-admin/update-core.php slowness issue. It is caused by the plugin Ad Inserter Pro (author contacted) who does this:

<?php
add_filter ('http_headers_useragent', 'ai_http_headers_useragent');

function ai_http_headers_useragent ($useragent) {

 $useragent = get_bloginfo ('url');

 return $useragent;

}

This appears to disrupt all the other premium plugins when they contact their servers to check the license validity. One of the things that they do remotely is to authenticate the request by checking the user-agent header field. By messing with it, it disrupts a LOT of stuff. and makes a lot of things VERY slow.

http_headers_useragent filter hook appears to be VERY VERY risky hook...

Last edited 7 years ago by lano1106 (previous) (diff)

This ticket was mentioned in Slack in #core by jeffpaul. View the logs.


7 years ago

This ticket was mentioned in PR #7078 on WordPress/wordpress-develop by @pbearne.


5 months ago
#3

  • Keywords has-patch added

This commit refactors the transient API to include a non-hook version named, set_site_transient_nohook. This update reduces redundancy in setting transients and creates a more streamlined, efficient operation in option.php. Additionally, the update method has been changed in update.php to utilize this new non-hook version.

#4 @pbearne
5 months ago

  • Owner set to pbearne
  • Status changed from new to accepted

refreshed patch

#5 @pbearne
5 months ago

  • Milestone changed from Awaiting Review to 6.7

This ticket was mentioned in Slack in #core-performance by mukeshpanchal27. View the logs.


4 months ago

#7 @adamsilverstein
4 months ago

I'm not sure we should fix this - the problem seems to be plugin related?

I am also concerned that the proposed change could break plugins that rely on the now skipped hooks. At a minimum, before making this change we should research usage of these hooks by other plugins.

This ticket was mentioned in Slack in #core-performance by mukeshpanchal27. View the logs.


4 months ago

#9 @pbearne
4 months ago

  • Milestone 6.7 deleted
  • Resolution set to wontfix
  • Status changed from accepted to closed

as per Adam's comments

Note: See TracTickets for help on using tickets.