Filtering for the COT admin list table. (#33789)
* Column sorting for the COT admin list table. * Add filter for easier extensibility. * Implement date based filtering within the admin order list table. * Implement customer-based filtering within admin order list table. * Allow filtering down to no results, better management of http_referer state. * Changelog. * Bring up-to-date, fix some conflict resolution mis-steps. * Address coding standards. * Remove unused import.
This commit is contained in:
parent
a498cc8280
commit
bc31065b8e
|
@ -0,0 +1,4 @@
|
|||
Significance: patch
|
||||
Type: add
|
||||
|
||||
Add support for filtering the Custom Order Table admin list UI.
|
|
@ -19,6 +19,13 @@ class ListTable extends WP_List_Table {
|
|||
*/
|
||||
private $order_query_args = array();
|
||||
|
||||
/**
|
||||
* Tracks if a filter (ie, date or customer filter) has been applied.
|
||||
*
|
||||
* @var bool
|
||||
*/
|
||||
private $has_filter = false;
|
||||
|
||||
/**
|
||||
* Sets up the admin list table for orders (specifically, for orders managed by the OrdersTableDataStore).
|
||||
*
|
||||
|
@ -41,7 +48,6 @@ class ListTable extends WP_List_Table {
|
|||
*/
|
||||
public function setup(): void {
|
||||
add_action( 'admin_notices', array( $this, 'bulk_action_notices' ) );
|
||||
|
||||
add_filter( 'manage_woocommerce_page_wc-orders_columns', array( $this, 'get_columns' ) );
|
||||
add_filter( 'set_screen_option_edit_orders_per_page', array( $this, 'set_items_per_page' ), 10, 3 );
|
||||
add_filter( 'default_hidden_columns', array( $this, 'default_hidden_columns' ), 10, 2 );
|
||||
|
@ -73,7 +79,7 @@ class ListTable extends WP_List_Table {
|
|||
* @return mixed
|
||||
*/
|
||||
public function set_items_per_page( $default, string $option, int $value ) {
|
||||
return 'edit_orders_per_page' === $option ? absint( $value ) : $default;
|
||||
return $option === 'edit_orders_per_page' ? absint( $value ) : $default;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -93,7 +99,7 @@ class ListTable extends WP_List_Table {
|
|||
<hr class='wp-header-end'>
|
||||
";
|
||||
|
||||
if ( $this->has_items() ) {
|
||||
if ( $this->has_items() || $this->has_filter ) {
|
||||
$this->views();
|
||||
|
||||
echo '<form id="wc-orders-filter" method="get" action="' . esc_url( get_admin_url( null, 'admin.php' ) ) . '">';
|
||||
|
@ -172,6 +178,8 @@ class ListTable extends WP_List_Table {
|
|||
);
|
||||
|
||||
$this->set_order_args();
|
||||
$this->set_date_args();
|
||||
$this->set_customer_args();
|
||||
|
||||
/**
|
||||
* Provides an opportunity to modify the query arguments used in the (Custom Order Table-powered) order list
|
||||
|
@ -208,6 +216,43 @@ class ListTable extends WP_List_Table {
|
|||
$this->order_query_args['order'] = in_array( $direction, array( 'ASC', 'DESC' ), true ) ? $direction : 'ASC';
|
||||
}
|
||||
|
||||
/**
|
||||
* Implements date (month-based) filtering.
|
||||
*/
|
||||
private function set_date_args() {
|
||||
$year_month = sanitize_text_field( wp_unslash( $_GET['m'] ?? '' ) );
|
||||
|
||||
if ( empty( $year_month ) || ! preg_match( '/^[0-9]{6}$/', $year_month ) ) {
|
||||
return;
|
||||
}
|
||||
|
||||
$year = (int) substr( $year_month, 0, 4 );
|
||||
$month = (int) substr( $year_month, 4, 2 );
|
||||
|
||||
if ( $month < 0 || $month > 12 ) {
|
||||
return;
|
||||
}
|
||||
|
||||
$last_day_of_month = date_create( "$year-$month" )->format( 'Y-m-t' );
|
||||
$this->order_query_args['date_created'] = "$year-$month-01..." . $last_day_of_month;
|
||||
$this->has_filter = true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Implements filtering of orders by customer.
|
||||
*/
|
||||
private function set_customer_args() {
|
||||
// phpcs:ignore WordPress.Security.ValidatedSanitizedInput.InputNotSanitized
|
||||
$customer = (int) wp_unslash( $_GET['_customer_user'] ?? '' );
|
||||
|
||||
if ( $customer < 1 ) {
|
||||
return;
|
||||
}
|
||||
|
||||
$this->order_query_args['customer'] = $customer;
|
||||
$this->has_filter = true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the list of views for this table (all orders, completed orders, etc, each with a count of the number of
|
||||
* corresponding orders).
|
||||
|
@ -229,7 +274,7 @@ class ListTable extends WP_List_Table {
|
|||
}
|
||||
|
||||
$all_count = array_sum( $view_counts );
|
||||
$view_links['all'] = $this->get_view_link( 'all', __( 'All', 'woocommerce' ), $all_count, 'all' === $current );
|
||||
$view_links['all'] = $this->get_view_link( 'all', __( 'All', 'woocommerce' ), $all_count, $current === 'all' );
|
||||
|
||||
foreach ( $view_counts as $slug => $count ) {
|
||||
$view_links[ $slug ] = $this->get_view_link( $slug, $statuses[ $slug ], $count, $slug === $current );
|
||||
|
@ -238,7 +283,6 @@ class ListTable extends WP_List_Table {
|
|||
return $view_links;
|
||||
}
|
||||
|
||||
// phpcs:disable Generic.Commenting.Todo.CommentFound
|
||||
/**
|
||||
* Count orders by status.
|
||||
*
|
||||
|
@ -287,7 +331,7 @@ class ListTable extends WP_List_Table {
|
|||
protected function extra_tablenav( $which ) {
|
||||
echo '<div class="alignleft actions">';
|
||||
|
||||
if ( 'top' === $which ) {
|
||||
if ( $which === 'top' ) {
|
||||
$this->months_filter();
|
||||
$this->customers_filter();
|
||||
|
||||
|
@ -557,7 +601,7 @@ class ListTable extends WP_List_Table {
|
|||
|
||||
$latest_note = current( $latest_notes );
|
||||
|
||||
if ( isset( $latest_note->content ) && 1 === $approved_comments_count ) {
|
||||
if ( isset( $latest_note->content ) && $approved_comments_count === 1 ) {
|
||||
$tooltip = wc_sanitize_tooltip( $latest_note->content );
|
||||
} elseif ( isset( $latest_note->content ) ) {
|
||||
/* translators: %d: notes count */
|
||||
|
@ -704,8 +748,6 @@ class ListTable extends WP_List_Table {
|
|||
echo '<input type="hidden" name="page" value="wc-orders" >';
|
||||
|
||||
$state_params = array(
|
||||
'_customer_user',
|
||||
'm',
|
||||
'paged',
|
||||
'status',
|
||||
);
|
||||
|
@ -715,7 +757,7 @@ class ListTable extends WP_List_Table {
|
|||
continue;
|
||||
}
|
||||
|
||||
echo '<input type="hidden" name="status" value="' . esc_attr( sanitize_text_field( wp_unslash( $_GET[ $param ] ) ) ) . '" >';
|
||||
echo '<input type="hidden" name="' . esc_attr( $param ) . '" value="' . esc_attr( sanitize_text_field( wp_unslash( $_GET[ $param ] ) ) ) . '" >';
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -63,8 +63,6 @@ class PageController {
|
|||
}
|
||||
|
||||
/**
|
||||
=======
|
||||
>>>>>>> trunk
|
||||
* Sets up the page controller, including registering the menu item.
|
||||
*
|
||||
* @return void
|
||||
|
@ -168,6 +166,23 @@ class PageController {
|
|||
if ( $this->orders_table->current_action() ) {
|
||||
$this->orders_table->handle_bulk_actions();
|
||||
}
|
||||
|
||||
$this->strip_http_referer();
|
||||
}
|
||||
|
||||
/**
|
||||
* Perform a redirect to remove the `_wp_http_referer` and `_wpnonce` strings if present in the URL (see also
|
||||
* wp-admin/edit.php where a similar process takes place), otherwise the size of this field builds to an
|
||||
* unmanageable length over time.
|
||||
*/
|
||||
private function strip_http_referer(): void {
|
||||
$current_url = esc_url_raw( wp_unslash( $_SERVER['REQUEST_URI'] ?? '' ) );
|
||||
$stripped_url = remove_query_arg( array( '_wp_http_referer', '_wpnonce' ), $current_url );
|
||||
|
||||
if ( $stripped_url !== $current_url ) {
|
||||
wp_safe_redirect( $stripped_url );
|
||||
exit;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -196,5 +211,4 @@ class PageController {
|
|||
$this->order->save();
|
||||
$theorder = $this->order;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue