J'utilise le code suivant pour faire un tax_query et cela ne semble plus fonctionner ..
À un moment donné, cela fonctionnait et pour la vie de moi, il ne le ferait plus.
<?php
global $pf_override;
class PF_override {
public $site_terms = array();
function __construct() {
// add filters
add_filter( 'init', array( &$this, 'populates_site_terms' ) );
add_filter( 'pre_get_posts', array( &$this, 'filter_query' ) );
}
function populates_site_terms() {
// my actual function does some processing and
// checks caches and combines IDs from multiple
// different sources here and then sets site_terms
$this->site_terms = array( 1, 2, 3 );
}
function filter_query( $query ) {
// not the main query?
if ( !$query->is_main_query() ) {
return $query;
}
// have terms to filter by?
if ( !empty( $this->site_terms ) ) {
// construct tax_query
$tax_query = array(
'taxonomy' => 'site_category',
'field' => 'id',
'terms' => $this->site_terms,
'operator' => 'IN'
);
// this needs to be an array of arrays
$taxquery = array(
$tax_query
);
// set this..
$query->set( 'tax_query', $taxquery );
}
// return new query object
return $query;
}
}
// not the admin? init class
if ( !is_admin() ) {
$pf_override = new PF_override();
}
?>
La taxonomie est ajoutée comme suit:
function PF_register_post_type() {
$labels = array(
'name' => _x( 'Site Category', 'taxonomy general name' ),
'singular_name' => _x( 'Site Category', 'taxonomy singular name' ),
'search_items' => __( 'Search Site Categories' ),
'all_items' => __( 'All Site Categories' ),
'parent_item' => __( 'Parent Site Category' ),
'parent_item_colon' => __( 'Parent Site Category:' ),
'edit_item' => __( 'Edit Site Category' ),
'update_item' => __( 'Update Site Category' ),
'add_new_item' => __( 'Add New Site Category' ),
'new_item_name' => __( 'New Site Category Name' ),
'menu_name' => __( 'Site Category' ),
);
$args = array(
'hierarchical' => true,
'labels' => $labels,
'show_ui' => true,
'show_admin_column' => true,
'query_var' => true,
'rewrite' => array( 'slug' => 'sitecat' ),
);
register_taxonomy( 'site_category', array( 'post', 'page', 'attachment', 'revision', 'nav_menu_item' ), $args );
}
add_action( 'init', 'PF_register_post_types', 1 );
Dans mon footer.php j'ajoute ce code:
$GLOBALS['wp_query']->request
Je reçois ce résultat en allant sur mydomain.com/testing:
SELECT wp_posts.* FROM wp_posts WHERE 1=1 AND wp_posts.post_name = 'testing' AND wp_posts.post_type = 'post' ORDER BY wp_posts.post_date DESC
La variable $ pf_override indique que $ pf_override-> site_terms doit être défini comme un tableau de
array( [0] => 1, [1] => 2, [2] => 3 )
Eh bien, il semble qu'après avoir fouillé dans le code, tax_query soit bloqué sur des pages à publication unique/page, ce qui explique pourquoi je me lance dans cette affaire.
Si vous estimez qu'il est avantageux d'exécuter tax_query dans toutes les circonstances, exprimez votre opinion sur trac.
Voir le billet ici: http://core.trac.wordpress.org/ticket/24819
J'ai réussi à contourner ce problème en dupliquant le code principal pour des publications uniques et en ajoutant des clauses join et where. Le nouveau code est le suivant:
<?php
global $pf_override;
class PF_override {
public $site_terms = array();
public $sql_join = '';
public $sql_where = '';
function __construct() {
// add filters
add_filter( 'init', array( &$this, 'populates_site_terms' ) );
add_filter( 'pre_get_posts', array( &$this, 'filter_query' ) );
add_filter( 'posts_join', array( &$this, 'filter_join' ) );
add_filter( 'posts_where', array( &$this, 'filter_where' ) );
}
function populates_site_terms() {
// my actual function does some processing and
// checks caches and combines IDs from multiple
// different sources here and then sets site_terms
$this->site_terms = array( 1, 2, 3 );
}
function filter_query( $query ) {
// not the main query?
if ( !$query->is_main_query() ) {
return $query;
}
// have terms to filter by?
if ( !empty( $this->site_terms ) ) {
// construct tax_query
$tax_query = array(
'taxonomy' => 'site_category',
'field' => 'id',
'terms' => $this->site_terms,
'operator' => 'IN'
);
// this needs to be an array of arrays
$taxquery = array(
$tax_query
);
// set this..
$query->set( 'tax_query', $taxquery );
if ( $query->is_singular ) {
global $wpdb;
$q = &$query->query_vars;
$q['suppress_filters'] = false;
$query->parse_tax_query( $q );
$clauses = $query->tax_query->get_sql( $wpdb->posts, 'ID' );
$this->sql_join .= $clauses['join'];
$this->sql_where .= $clauses['where'];
}
}
return $query;
}
function filter_join( $join ) {
if ( !empty( $this->sql_join ) ) {
$join .= $this->sql_join;
}
return $join;
}
function filter_where( $where ) {
if ( !empty( $this->sql_where ) ) {
$where .= $this->sql_where;
}
return $where;
}
}
// not the admin? init class
if ( !is_admin() ) {
$pf_override = new PF_override();
}
?>
Je veux donner une solution simple.
add_action('pre_get_posts', 'filter_query');
function filter_query( $query ) {
// **PLEASE NOTE**
// $this->site_terms refers specifically to logic in the question
if ( $query->is_main_query() && $query->is_singular && ! empty( $this->site_terms ) ) {
$site = get_queried_object();
$terms = wp_get_object_terms($site->ID, 'site_category', array('fields' => 'ids') );
if ( empty($terms) || empty( array_intersect($terms, $this->site_terms) ) ) {
$query->set( 'page_id', -1 ); // 404
}
}
}
Comme avantage supplémentaire, il est possible de rediriger les visiteurs vers la page souhaitée au lieu de forcer une erreur 404 en modifiant $query->set( 'page_id', -1 );
avec l'id d'une page spécialement créée.
J'espère que ça aide.