[wp-trac] [WordPress Trac] #60154: Add filter hook to either get_post_stati or WP_List_Util::filter
WordPress Trac
noreply at wordpress.org
Wed Dec 27 03:18:36 UTC 2023
#60154: Add filter hook to either get_post_stati or WP_List_Util::filter
-------------------------+-----------------------------
Reporter: Malaiac | Owner: (none)
Type: enhancement | Status: new
Priority: normal | Milestone: Awaiting Review
Component: Query | Version: trunk
Severity: normal | Keywords:
Focuses: |
-------------------------+-----------------------------
In the WP_Query class, around line 2649 at this time
there is a condition if a post_type is selected
{{{#!php
<?php
if ( ! empty( $queried_post_types ) ) {
....
$public_statuses = get_post_stati( array( 'public' => true ) );
$status_clauses = array();
foreach ( $public_statuses as $public_status ) {
$status_clauses[] = "{$wpdb->posts}.post_status =
'$public_status'";
}
...
}}}
This code does not allow to filter statuses depending on other query vars,
since neither get_post_stati or wp_filter_object_list (used by
get_post_stati) have any hookable filter.
User scenario : I need to filter shop_order posts by a custom taxonomy.
I need to be able to select shop_order without any assigned term from this
taxonomy, but only if they're "live" ( processing, completed, etc. but not
refunded, failed or cancelled), as I don't care if a cancelled Order has
no assigned term from this taxonomy.
So if
{{{
$WP_Query->query_vars['post_type'] == 'shop_order'
&& $_GET['taxonomy'] == -1
}}}
( -1 being the value I put in the admin select field to select orders
without relationship to the taxonomy )
I want to be able to filter $public_statuses = get_post_stati( array(
'public' => true ) ); to remove 'dead' statuses from the list
current where clause =
AND wp_posts.post_type = 'shop_order' AND ((wp_posts.post_status = 'wc-
pending' OR wp_posts.post_status = 'wc-processing' OR wp_posts.post_status
= 'wc-on-hold' OR wp_posts.post_status = 'wc-completed' OR
wp_posts.post_status = 'wc-cancelled' OR wp_posts.post_status = 'wc-
refunded' OR wp_posts.post_status = 'wc-failed' OR wp_posts.post_status =
'wc-partially-paid'))
expected where clause =
AND wp_posts.post_type = 'shop_order' AND ((wp_posts.post_status = 'wc-
pending' OR wp_posts.post_status = 'wc-processing' OR wp_posts.post_status
= 'wc-on-hold' OR wp_posts.post_status = 'wc-completed' OR
wp_posts.post_status = 'wc-partially-paid'))
My own hook hooks on 'posts_where' and add the filter
{{{#!php
<?php
$where .= $wpdb->prepare(
" AND ID IN (
SELECT object_id
FROM ". $wpdb->term_relationships
. "
WHERE term_taxonomy_id = %d
)
", $term_taxonomy_id
);
}}}
and since I'm filtering the $where string of the SQL query, I _could_
remove the 'dead' statuses by str_replace on the where clause, but that's
really ugly
I propose this code
{{{#!php
<?php
function get_post_stati( $args = array(), $output = 'names', $operator =
'and' ) {
global $wp_post_statuses;
$field = ( 'names' === $output ) ? 'name' : false;
return wp_filter_object_list( $wp_post_statuses, $args, $output,
$operator );
}
}}}
to be replaced by this code :
{{{#!php
<?php
function get_post_stati( $args = array(), $output = 'names', $operator =
'and' ) {
global $wp_post_statuses;
$field = ( 'names' === $output ) ? 'name' : false;
$statuses = wp_filter_object_list( $wp_post_statuses, $args,
$operator, $field );
return apply_filters( 'get_post_stati', $statuses, $args,
$operator, $field);
}
}}}
as I would then be able to
{{{#!php
<?php
add_filter('get_post_stati', 'custom_get_post_stati', 10, 4);
function custom_get_post_stati( $statuses, $args, $operator, $field ) {
if( is_admin() && isset( $_GET['taxonomy'] && $_GET['taxonomy'] ==
-1 ) {
// remove the 'dead' statuses
}
return $statuses;
}
}}}
--
Ticket URL: <https://core.trac.wordpress.org/ticket/60154>
WordPress Trac <https://core.trac.wordpress.org/>
WordPress publishing platform
More information about the wp-trac
mailing list