Changeset 60788
- Timestamp:
- 09/21/2025 05:25:49 AM (3 weeks ago)
- Location:
- trunk
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/wp-includes/post.php
r60724 r60788 3401 3401 } 3402 3402 3403 $query = "SELECT post_status, COUNT( * ) AS num_posts FROM {$wpdb->posts} WHERE post_type = %s"; 3404 3405 if ( 'readable' === $perm && is_user_logged_in() ) { 3406 $post_type_object = get_post_type_object( $type ); 3407 if ( ! current_user_can( $post_type_object->cap->read_private_posts ) ) { 3408 $query .= $wpdb->prepare( 3409 " AND (post_status != 'private' OR ( post_author = %d AND post_status = 'private' ))", 3410 get_current_user_id() 3411 ); 3412 } 3413 } 3414 3415 $query .= ' GROUP BY post_status'; 3416 3417 $results = (array) $wpdb->get_results( $wpdb->prepare( $query, $type ), ARRAY_A ); 3403 if ( 3404 'readable' === $perm && 3405 is_user_logged_in() && 3406 ! current_user_can( get_post_type_object( $type )->cap->read_private_posts ) 3407 ) { 3408 // Optimized query uses subqueries which can leverage DB indexes for better performance. See #61097. 3409 $query = $wpdb->prepare( 3410 " 3411 SELECT post_status, COUNT(*) AS num_posts 3412 FROM ( 3413 SELECT post_status 3414 FROM {$wpdb->posts} 3415 WHERE post_type = %s AND post_status != 'private' 3416 UNION ALL 3417 SELECT post_status 3418 FROM {$wpdb->posts} 3419 WHERE post_type = %s AND post_status = 'private' AND post_author = %d 3420 ) AS filtered_posts 3421 ", 3422 $type, 3423 $type, 3424 get_current_user_id() 3425 ); 3426 } else { 3427 $query = $wpdb->prepare( 3428 " 3429 SELECT post_status, COUNT(*) AS num_posts 3430 FROM {$wpdb->posts} 3431 WHERE post_type = %s 3432 ", 3433 $type 3434 ); 3435 } 3436 3437 $query .= ' GROUP BY post_status'; 3438 $results = (array) $wpdb->get_results( $query, ARRAY_A ); 3418 3439 $counts = array_fill_keys( get_post_stati(), 0 ); 3419 3440 -
trunk/tests/phpunit/tests/post.php
r60251 r60788 7 7 */ 8 8 class Tests_Post extends WP_UnitTestCase { 9 protected static $editor_id;10 9 protected static $grammarian_id; 11 10 11 protected static $user_ids = array( 12 'administrator' => null, 13 'editor' => null, 14 'author' => null, 15 'contributor' => null, 16 ); 17 12 18 private $post_ids = array(); 13 19 14 20 public static function wpSetUpBeforeClass( WP_UnitTest_Factory $factory ) { 15 self::$editor_id = $factory->user->create( array( 'role' => 'editor' ) ); 21 22 self::$user_ids = array( 23 'administrator' => $factory->user->create( 24 array( 25 'role' => 'administrator', 26 ) 27 ), 28 'editor' => $factory->user->create( 29 array( 30 'role' => 'editor', 31 ) 32 ), 33 'author' => $factory->user->create( 34 array( 35 'role' => 'author', 36 ) 37 ), 38 'contributor' => $factory->user->create( 39 array( 40 'role' => 'contributor', 41 ) 42 ), 43 ); 16 44 17 45 add_role( … … 143 171 /** 144 172 * @ticket 24803 173 * @covers ::wp_count_posts 145 174 */ 146 175 public function test_wp_count_posts() { … … 162 191 } 163 192 193 /** 194 * Ensure `wp_count_posts()` in 'readable' context excludes private posts 195 * authored by other users when the current user lacks the capability to 196 * read private posts. 197 * 198 * @ticket 61097 199 * @covers ::wp_count_posts 200 */ 201 public function test_wp_count_posts_readable_excludes_unreadable_private_posts() { 202 $post_type = rand_str( 20 ); 203 register_post_type( $post_type ); 204 205 $admin_user_id = self::$user_ids['administrator']; 206 207 self::factory()->post->create_many( 208 5, 209 array( 210 'post_type' => $post_type, 211 'post_status' => 'publish', 212 'post_author' => $admin_user_id, 213 ) 214 ); 215 216 self::factory()->post->create_many( 217 3, 218 array( 219 'post_type' => $post_type, 220 'post_status' => 'private', 221 'post_author' => $admin_user_id, 222 ) 223 ); 224 225 $current_user_id = self::$user_ids['author']; 226 wp_set_current_user( $current_user_id ); 227 228 $count = wp_count_posts( $post_type, 'readable' ); 229 $this->assertEquals( 5, $count->publish ); 230 _unregister_post_type( $post_type ); 231 } 232 233 /** 234 * @covers ::wp_count_posts 235 */ 164 236 public function test_wp_count_posts_filtered() { 165 237 $post_type = rand_str( 20 ); … … 187 259 } 188 260 261 /** 262 * @covers ::wp_count_posts 263 */ 189 264 public function test_wp_count_posts_insert_invalidation() { 190 265 $post_ids = self::factory()->post->create_many( 3 ); … … 207 282 } 208 283 284 /** 285 * @covers ::wp_count_posts 286 */ 209 287 public function test_wp_count_posts_trash_invalidation() { 210 288 $post_ids = self::factory()->post->create_many( 3 ); … … 227 305 /** 228 306 * @ticket 49685 307 * @covers ::wp_count_posts 229 308 */ 230 309 public function test_wp_count_posts_status_changes_visible() { … … 253 332 wp_set_object_terms( $post, 'foo', $tax ); 254 333 255 wp_set_current_user( self::$ editor_id);334 wp_set_current_user( self::$user_ids['editor'] ); 256 335 257 336 $wp_tag_cloud = wp_tag_cloud( … … 306 385 ); 307 386 308 wp_set_current_user( self::$ editor_id);387 wp_set_current_user( self::$user_ids['editor'] ); 309 388 310 389 edit_post( $data );
Note: See TracChangeset for help on using the changeset viewer.