Make WordPress Core

Opened 11 months ago

Last modified 6 weeks ago

#63518 assigned defect (bug)

get_blog_details( get_all: false ) not working as expected

Reported by: apermo's profile apermo Owned by: johnjamesjacoby's profile johnjamesjacoby
Milestone: 7.1 Priority: normal
Severity: normal Version:
Component: Networks and Sites Keywords: has-patch changes-requested reporter-feedback has-unit-tests
Focuses: multisite Cc:

Description

I recently played around with get_blog_details() and found that the second parameter is not as expected.

<?php
get_blog_details( 1, true ); // will return the long results.
get_blog_details( 1, false ); // will also return the long results.

get_blog_details( 2, false ); // will return the short results.
get_blog_details( 2, true ); // will return the long results.
get_blog_details( 2, false ); // will still return the short results.

So if you call it with $get_all = false first, it works as expected and it seems to cache the short result separately and you can call them in any order and how often you want.
If you call $get_all = true first, it will ignore the second parameter and will always return the long results.

It seems to me like the caching in the function is not working properly.

Attachments (1)

63518.patch (1.3 KB) - added by immeet94 11 months ago.

Download all attachments as: .zip

Change History (12)

@immeet94
11 months ago

#1 @immeet94
11 months ago

  • Keywords has-patch needs-testing added

Hey @apermo
Thanks for created ticket and i created patch for that, please review and test it.let me know for query.
Thanks

#2 @apermo
11 months ago

Hey @immeet94 thank you for the patch.
I tried to apply your patch and test it, but I could not find where to apply your patch, checked with 6.8.1 and trunk.

Could you verify your patch?

Greetings from WCEU2025

#3 @ravigadhiyawp
11 months ago

Reproduction Report

Description

This report validates whether the issue can be reproduced.

Environment

  • WordPress: 6.8.1
  • PHP: 8.2.23
  • Server: nginx/1.26.1
  • Database: mysqli (Server: 8.0.35 / Client: mysqlnd 8.2.23)
  • Browser: Chrome 137.0.0.0
  • OS: Windows 10/11
  • Theme: Twenty Twenty-Five 1.2
  • MU Plugins: None activated
  • Plugins:
    • Test Reports 1.2.0

Actual Results

  1. ❌ Error condition not occurs (not reproduced).

Additional Notes

  • To reproduce the issue, I printed the result returned by get_blog_details() as suggested by @apermo . It appears to be working as expected upon inspection. I couldn’t find any issue.

Supplemental Artifacts

Screenshot: https://prnt.sc/ipp9hsBdXHWT

#4 @SirLouen
11 months ago

  • Keywords changes-requested added; needs-testing removed

#5 @SirLouen
11 months ago

  • Keywords reporter-feedback added

#6 @debarghyabanerjee
10 months ago

I tried reproducing the issue reported, but I couldn't reproduce it as well.

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


8 weeks ago
#7

  • Keywords has-unit-tests added

When get_blog_details() is called with $get_all=true first, the full result is cached. A subsequent call with $get_all=false incorrectly returns the full cached result instead of a short one.

The "try the other cache" block now discards the full cache hit when short is requested, allowing WP_Site::get_instance() to build a clean short result without an extra DB query.

Trac ticket: https://core.trac.wordpress.org/ticket/63518#ticket

## Use of AI Tools

AI used to dig deeper into the issue, to write documentation and to help writing unit test.
Everything generated was reviewed afterwards.

#8 @apermo
8 weeks ago

@debarghyabanerjee @ravigadhiyawp did you try to reproduce on a Multisite? I just tried again, and I still can reproduce the issue.

How to reproduce:

  1. Set up a WordPress multisite environment
  2. Run the following code on any multisite site (e.g. in a mu-plugin or via WP-CLI eval):
<?php
$site_id = get_current_blog_id();

// Call with $get_all = true first, then false.

$full  = get_blog_details( $site_id, true );
$short = get_blog_details( $site_id, false );

echo "Full fields:\n";
print_r( array_keys( get_object_vars( $full ) ) );

echo "Short fields:\n";
print_r( array_keys( get_object_vars( $short ) ) );

Expected:
The short result should only contain the base site fields (blog_id, domain, path, site_id, registered, last_updated, public, archived, mature, spam, deleted, lang_id).

Actual:
The short result incorrectly includes blogname, siteurl, post_count, and home — the same fields as the full result.

Root cause:
In ms-blogs.php, the "Try the other cache" block (around line 212) returns the full cached result directly when $get_all = false:

} else {
   return $details; // Returns full result even though short was requested
}

Fix: Replace that return with unset( $details ) so the code falls through to WP_Site::get_instance() (which uses its own sites cache — no extra DB query) and builds a clean short result.

PHPUnit reproduction: The patch includes two multisite tests covering both sequences from the ticket description. Run with:

npm run test:php -- --configuration=tests/phpunit/multisite.xml --filter="test_get_blog_details_(get_all_true_then_false|false_true_false)"

Without the fix, test_get_blog_details_get_all_true_then_false_returns_short fails. With the fix, all 21 getBlogDetails tests pass.

To see the test, check the pull request I just opened.

@apermo commented on PR #11016:


8 weeks ago
#9

Failing test: Tests_Error_Protection_wpRecoveryModeKeyService::test_validate_recovery_mode_key_returns_wp_error_if_bad

Issue: Expects 'invalid_recovery_key_format' but gets 'token_not_found'
Likely unrelated to get_blog_details() or the changes from the PR. AI research is suggesting a cache-related race condition in that test.

This ticket was mentioned in Slack in #core-multisite by apermo. View the logs.


6 weeks ago

#11 @johnjamesjacoby
6 weeks ago

  • Milestone changed from Awaiting Review to 7.1
  • Owner set to johnjamesjacoby
  • Status changed from new to assigned
Note: See TracTickets for help on using tickets.