I can select posts via my custom taxonomy as explained in the codex. But I am not sure, how I have to set up the tax_query if I want to get only posts which have no relation in the custom taxonomy at all. Any suggestion?
2 Answers
I have found an answer by myself, for those landing here by google:
$taxq = array(
array(
'taxonomy' => 'story_lng',
'field' => 'id',
'operator' => 'NOT EXISTS',
)
);
That results in
AND (NOT EXISTS( SELECT
1
FROM
wp_term_relationships
INNER JOIN
wp_term_taxonomy ON wp_term_taxonomy.term_taxonomy_id = wp_term_relationships.term_taxonomy_id
WHERE
wp_term_taxonomy.taxonomy = 'story_lng'
AND wp_term_relationships.object_id = wp_posts.ID))
AND wp_posts.post_type = 'story'
AND (wp_posts.post_status = 'publish'
OR wp_posts.post_author = 1
AND wp_posts.post_status = 'private')
wich is basically the same as Pieter Goosen suggested, but merged in one query (and fewer lines of code).
-
Good answer. Just for interest sake, I wonder which method will be faster, I'm quite interested to test this when I have time. Just remember to acept your own answer ;-). Enjoy Commented Jan 11, 2016 at 12:49
-
Yes, it would be worth a test. In most cases a query with a subquery is faster than two queries I think.– PaflowCommented Jan 11, 2016 at 12:55
-
1Had time to test this, and your method is definitely faster. Enjoy ;-) Commented Jan 18, 2016 at 16:34
The only way is to get all the terms and exclude posts which belongs to those terms
$taxonomy = 'my_tax';
$terms = get_terms(
$taxonomy,
['fields' => 'ids'] // Get only IDS
);
// Setup your query args
$args = [
'tax_query' => [
[
'taxonomy' => $taxonomy,
'terms' => $terms,
'operator' => 'NOT IN' // Skip posts belonging to the passed terms
]
],
// any other args
];
$q = new WP_Query( $args );
You would want to make sure that you actually have terms and not an empty array or a WP_Error
object as this might lead to unexpected output
-
Thank you a lot for your help, but I found a better solution by myself as you can see below / above.– PaflowCommented Jan 11, 2016 at 12:38