web-dev-qa-db-ja.com

'parse_query'フィルタを使用して、複数の基準に基づいて投稿を表示します

「A」または「B」の基準を満たす投稿を表示するように、WordPress管理者の投稿ページをフィルタリングしようとしています。私は文書を精査しましたが、これを実行するための良い方法を見つけることができません。

詳細:作成者が自分の投稿しか編集できないように、ユーザーロールのスコープを設定しました。ただし、作成者が投稿を編集できるように他の作成者を選択できるように、カスタムフィールドを追加しました。この機能は、 'parse_query'フィルタでどちらか一方を使用しても完全に機能しますが、両方のクエリを有効にしようとすると、すべての条件に一致する投稿を表示したいと思います(なし)。

参考までに、これが私のコードです(これはfunctions.phpにあります)。

add_filter('parse_query', 'show_appropriate_posts');
function show_appropriate_posts($query) {
    if ( strpos($_SERVER[ 'REQUEST_URI' ], '/wp-admin/edit.php') !== false ) {
        if ( !current_user_can('manage_options') ) {
            global $current_user;

            //Only list posts by this user (A).
            $query->set('author', $current_user->id);

            //List posts this user is "tagged" in (B).
            $query->set('meta_key', 'add_editing_permission_for');
            $query->set('meta_value', $current_user->id);
            $query->set('meta_compare', 'LIKE');

            //@TODO: Need to show posts that meet (A) -or- (B).
        }
    }
}

繰り返しになりますが、(A)と(B)の両方が単独で実行されたときに機能しています。

1
GreatBlakes

meta_queryに関する私のコメントを無視してください。 $query->set()でうまく機能しないだけでなく、クエリの重要な "A OR B"要件を制御することはできません。

代わりに、以下のようにpre_get_postsアクションフックとposts_where filterフックの両方を組み合わせることで、必要なものが可能になると思います。

add_action('pre_get_posts', 'my_show_appropriate_posts');
function my_show_appropriate_posts($query){

    if(strpos($_SERVER[ 'REQUEST_URI' ], '/wp-admin/edit.php') !== false) :

        if(!current_user_can('manage_options')) :

            /** Unset so that we can control exactly where this part of the query is included */
            $query->set('author', null);

            /** Ensure that the relevant tables required for a meta query are included */
            $query->set('meta_query', array(
                array(
                    'key'       => 'add_editing_permission_for',
                    'value'     => 'dummy', // This cannot be empty because of a bug in WordPress
                    'compare'   => '='
                )
            ));

            /** Call the filter to amend the '$where' portion of the query */
            add_filter('posts_where', 'my_custom_posts_where');

        endif;

    endif;

}

function my_custom_posts_where( $where = '' ){

    global $wpdb;

    /** Add our required conditions to the '$where' portion of the query */
    $where.= sprintf(
        ' AND ( %1$s.post_author = %2$s OR ( %3$s.meta_key = "add_editing_permission_for" AND %3$s.meta_value = %2$s ) )',
        $wpdb->posts,
        get_current_user_id(),
        $wpdb->postmeta
    );

    /** Remove the filter to call this function, as we don't want it any more */
    remove_filter('posts_where', 'my_custom_posts_where');

    return $where;

}

おすすめ読書

5
David Gard