Opened 12 years ago
Last modified 3 weeks ago
#31199 accepted defect (bug)
Potential reference to unset variable in get_bulk_actions (WP_Posts_List_Table)
| Reported by: | sgrant | Owned by: | chriscct7 |
|---|---|---|---|
| Priority: | normal | Milestone: | Future Release |
| Component: | Administration | Version: | |
| Severity: | normal | Keywords: | has-patch reporter-feedback close has-unit-tests |
| Cc: | Focuses: |
Description
get_post_type_object can return null in some cases, which causes a notice when current_user_can is called later in the function.
Attached a patch to check if delete_posts is set, and to only add actions if it is. Thanks!
Attachments (3)
Change History (10)
#1
@
12 years ago
- Keywords has-patch added
Hi sgrant
Could you please provide a the way you have triggered this bug, so that I can reproduce it ?
And I think you made a mistake in your patch : $post_type_obj->delete_posts will never exist, its $post_type_obj->cap->delete_posts that has to be checked.
#3
@
8 years ago
- Keywords reporter-feedback removed
- Milestone Awaiting Review → 5.1
- Owner set to
- Status new → accepted
Updated patch with additional checks for edit_posts cap as well as empty post_type_obj variable.
#6
@
12 months ago
- Keywords close added
Hi @sgrant,
As we haven't seen any progress on this regarding steps to recreate the problem, I'm applying the close tag.
Feel free to respond and remove it if you'd prefer to keep the discussion going. For example, you might try installing the Test Reports plugin and submitting a bug report. This will help us pinpoint any external factors contributing to the issue, allowing the community and me to offer more effective assistance. 😃
This ticket was mentioned in PR #13565 on WordPress/wordpress-develop by whopiyush.
3 weeks ago
#7
- Keywords has-unit-tests added
WP_Posts_List_Table::get_bulk_actions() passes the result of get_post_type_object() straight into current_user_can() without checking it. get_post_type_object() returns null for an unregistered post type, so both capability checks in the method read ->cap off null. On PHP 8 that is a warning, and before PHP 8 it was a notice about an undefined property, which is what the reporter described.
The ticket has sat with a close keyword for years because nobody could supply reproduction steps. Here they are, and they are reproducible on trunk.
A screen can hold a post type that is not registered. wp_ajax_fetch_list() builds a list table from a screen id taken out of the request:
$wp_list_table = _get_list_table( $list_class, array( 'screen' => $_GET['list_args']['screen']['id'] ) );
convert_to_screen() does not verify that the post type exists. The edit branch of WP_Screen::get() only appends the post type to the id, so any screen id of the form edit-<unknown> produces a WP_Posts_List_Table whose screen->post_type is unregistered. get_bulk_actions() is then reached through bulk_actions(), and the warning is raised.
The reproduction is now a unit test rather than a manual recipe. On unmodified trunk it fails with:
Tests_Admin_wpPostsListTable::test_get_bulk_actions_with_unregistered_post_type Attempt to read property "cap" on null src/wp-admin/includes/class-wp-posts-list-table.php:436
The change returns early when no post type object is available. With no post type there are no valid bulk actions to offer, so an empty array is the correct result, and it matches the direction the ticket owner already suggested in 31199-2.patch ("additional checks for edit_posts cap as well as empty post_type_obj variable").
Scope notes:
- Only
get_bulk_actions()is touched. The file has other unguarded uses ofget_post_type_object()inajax_user_can(),no_items(),extra_tablenav()andinline_edit(). Those are deliberately left alone, since each is a separate question about which screen states the list table is expected to support, and folding them in would make this hard to review. Happy to follow up on them separately if that is wanted. - The existing behaviour for a registered post type is unchanged, and that is pinned by a second test rather than left implied. It asserts the
editandtrashactions are still returned forpage, and it passes both before and after the change. - The early return keeps the
edit_postsanddelete_postscapability checks exactly as they are, so a user who cannot edit or delete still gets the same actions they do today.
Use of AI Tools
AI assistance: Yes
Tool(s): Claude
Model(s): Sonnet
Used for: test cases, code review
![(please configure the [header_logo] section in trac.ini)](/chrome/site/your_project_logo.png)
Add isset check before referencing