2

I am trying to select posts that have category id 4 but exclude posts that also have category id 2

Here's what i'm trying

$query = new WP_Query(array(
  "cat__in"         => array(4),
  "cat__not_in"     => array(2),
  "post_type"       => "post",
  "post_status"     => "publish",
  "orderby"         => "date",
  "order"           => "DESC",
  "posts_per_page"  => $limit,
  "offset"          => 0
));

However, it's not making the proper selection. What am I doing wrong?

  • 1
    cat__in and cat__not_in is not valid parameters. Go and check the valid category parameters in WP_Query. You can just simply pass 'cat'=>4 to your arguments to just get posts from category 4. Or as Brad suggested, use pre_get_posts and pass the same parameters to that – Pieter Goosen Jul 14 '14 at 10:09
2

Use pre_get_posts to exclude the categories you don't want to display in the loop.

function exclude_posts_from_specific_category( $query ) {
    if ( $query->is_home() && $query->is_main_query() ) {
        $query->set( 'cat', '-2' );
    }
}
add_action( 'pre_get_posts', 'exclude_posts_from_specific_category' );

Or create a new WP_Query and use the Category Parameters.

<?php

$args = array( 

'category__not_in' => 2 ,

'category__in' => 4 

);

$the_query = new WP_Query( $args );


if ( $the_query->have_posts() ) {
        echo '<ul>';
        while ( $the_query->have_posts() ) {
        $the_query->the_post();
        echo '<li>' . get_the_title() . '</li>';
    }
        echo '</ul>';
} else {

}

wp_reset_postdata();

If you only want to display posts from one category, you would use the category archive. See Template Hierarchy.

  • Ah, that was my problem. I was using cat__in and cat__not_in. I needed to use the full word category in each parameter. I'm going to tinker with your other method, too. – user633183 Jul 14 '14 at 18:05
  • I've edited my answer to compile a complete(?) list of methods to do this. – user633183 Jul 14 '14 at 18:34
  • That's great @naomik. Did you also test your code as well? – Brad Dalton Jul 14 '14 at 21:22
  • do you mean unit tests? I just ran a quick smoke test to see that each method in my post works. – user633183 Jul 14 '14 at 23:38
  • Lets leave the commenting here as its dragging out a bit but i simply suggest you test all code snippets in your theme. – Brad Dalton Jul 15 '14 at 8:23
1

As it turns out, this can be done in 4 separate ways

Using cat with a negative number

$query = new WP_Query(array(
  "cat" => "4, -2",
  // ...
));

Using category__in and category__not_in

I was mistakenly using cat__in and cat__not_in which are not valid WP_Query parameters

$query = new WP_Query(array(
  "category__in"     => array(4),
  "category__not_in" => array(2),
  // ...
));

Using tax_query

$query = new WP_Query(array(
  "tax_query" => array(
    "relation" => "AND",
    array(
      "taxonomy" => "category",
      "field"    => "term_id",
      "terms"    => array(4)
    ),
   array(
      "taxonomy" => "category",
      "field"    => "term_id",
      "terms"    => array(2),
      "operator" => "NOT IN"
    ),
  ),
  // ...
));

Using the pre_get_posts filter (as provided by Brad Dalton)

function exclude_posts_from_specific_category($query) {
  if ($query->is_home() && $query->is_main_query()) {
    $query->set("cat", "-2");
  }
}
add_action("pre_get_posts", "exclude_posts_from_specific_category");
-2

Suppose you have posts with cat id 4.

query_posts('cat=4');
  while (have_posts()) : the_post();
      the_content();
  endwhile;
  • Please add an explanation to your answer: why would that solve the problem? – fuxia Jul 14 '14 at 9:23
  • You should never use query_posts, never – Pieter Goosen Jul 14 '14 at 10:04
  • reason for never using query_posts ? – jojo Jul 14 '14 at 10:27
  • This post should shed some light on that – Pieter Goosen Jul 14 '14 at 10:49

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.