我提出的解决方案已经由@cybmeta(+1)发布,但我还是添加了它,因为它以一般方式处理;-)
以同样的方式WP_Query
参数:
\'post__in\' => [1,2,3],
\'orderby\' => \'post__in\'
使用自定义的顺序:
ORDERBY FIELD( wp_posts.ID, 1, 2, 3 )
我们可以使用以下方法定义自己的元排序:
\'meta__in\' => [ \'apple\', \'orange\', \'banana\' ],
\'orderby\' => \'meta__in\'
要获取以下SQL部件:
ORDERBY FIELD( wp_postmeta.meta_value, \'apple\', \'orange\', \'banana\' )
首先,我们定义自己版本的
wp_parse_id_list()
助手函数。
/**
* Note that this function is based on the core wp_parse_id_list() function.
* Clean up an array, comma- or space-separated list of string keys.
*
* @uses sanitize_key()
* @param array|string $list List of keys.
* @return array Sanitized array of keys.
*/
function wpse_parse_meta_list( $list )
{
if ( ! is_array( $list ) )
$list = preg_split(\'/[\\s,]+/\', $list);
return array_unique( array_map( \'sanitize_key\', $list ) );
}
然后我们构建以下演示插件,以添加对
\'meta__in\'
订购,英寸
WP_Query
:
<?php
/**
* Plugin Name: Support for order by meta__in in WP_Query
*/
add_filter( \'posts_orderby\', function ( $orderby, \\WP_Query $q )
{
if( $meta__in = $q->get( \'meta__in\' ) )
{
if( is_array( $meta__in ) && ! empty( $meta__in ) )
{
global $wpdb;
// Transform the meta__in array into a comma separated strings of keys
// Example [ \'apple\', \'banana\' ] --> "apple", "banana"
$list = \'"\' . join( \'","\', wpse_parse_meta_list( $meta__in ) ) . \'"\';
// Override the orderby part with custom ordering:
$orderby = " FIELD( {$wpdb->postmeta}.meta_value, {$list} ) ";
}
}
return $orderby;
}, 10, 2 );
/**
* Note that this function is based on the core wp_parse_id_list() function.
* Clean up an array, comma- or space-separated list of string keys.
*
* @uses sanitize_key()
* @param array|string $list List of keys.
* @return array Sanitized array of keys.
*/
function wpse_parse_meta_list( $list )
{
if ( ! is_array( $list ) )
$list = preg_split(\'/[\\s,]+/\', $list);
return array_unique( array_map( \'sanitize_key\', $list ) );
}
我们在插件中添加了helper函数。
注意:我们只使用\'meta__in\'
用于订购而非额外订购的参数WHERE
限制,就像我们对\'post__in\'
参数但这可能是一个有趣的扩展;-)
还要注意的是get_posts()
, 那只是一个WP_Query
wrapper默认设置了以下参数:
\'suppress_filters\' => true
即不接受
posts_*
默认情况下过滤。
所以如果你不能使用WP_Query
或get_posts()
使用suppress_filters => false
, 那么您需要一种替代方法,例如@PieterGoosen建议的方法。