Take the 2-minute tour ×
WordPress Development Stack Exchange is a question and answer site for WordPress developers and administrators. It's 100% free, no registration required.

This seems like a fairly common problem, but I'm posting this as I've yet to find a solution to my problem here on WP Answers - any help is HUGELY appreciated!

Ok - so I have a custom post type of 'events' where I capture the date of the event using a custom field and store it as a unix timestamp. Filtering posts on the front end is not a problem using the following code to show future events only:

$events = new WP_Query( 'post_type=events&posts_per_page=-1&meta_key=date_value&orderby=meta_value&meta_compare=>=&meta_value='.time().'&order=ASC' );

I've tried to filter the results in the admin in the same way using a pre_get_posts filter:

function events_pre_get_posts($query) {
  if (is_admin()) {
    if (isset($query->query_vars['post_type'])) {
      if ($query->query_vars['post_type'] == 'events') {
          $query->set('meta_key', 'date_value');
          $query->set('orderby', 'meta_value');
          $query->set('meta_compare', '>=');
          $query->set('meta_value', time());
          $query->set('order', 'ASC');
      }
    }
  }
}
add_filter('pre_get_posts' , 'events_pre_get_posts');

But in the admin this code just makes all my posts disappear!

I'm also trying to find a way to show past events in the back end and I'm really stuck there too! I not sure the best way to do this - perhaps a toggle on the 'events' posts page to view past / future events.

Help!!

share|improve this question

2 Answers 2

Second try: ;-)

pre_get_posts runs AFTER parse_query(). parse_query() transforms 'meta_key' etc. into 'meta_query'. get_posts() doesn't seem to react on 'meta_key' etc. directly. So try adding $query->parse_query() after your $query->set() calls or use filter that runs before parse_query (edited, the parse_query() filter doesn't work, either - it runs too late).

Edit: to do the switch:

function my_timeswitch() {
    $operators = array(
        '>=' => 'future',
        '<=' => 'past'
    );
    ?>
    <select name='meta_compare'>
        <?php
            foreach ($operators as $k => $v) {
                printf( "<option %s value='%s'>%s</option>\n", selected($_GET['meta_compare'], $k, false), esc_attr($k), __($v));
            }
        ?>
    </select>
    <?php
}
add_action('restrict_manage_posts', 'my_timeswitch');

This may work just on it's own. If not, you'll have to change the name to something else, then register a new public query variable via the query_vars filter and then react on it via the parse_query filter.

share|improve this answer
1  
Why not just add that to the original answer? –  t31os Feb 26 '11 at 13:07
    
Hang on - it does work! I add $query->parse_query() after all the other query stuff and it now only displays event that have yet to occur! Wicked - thanks so much @wyrfel! --- BTW, any idea if it's possible to toggle the query on the admin side between past and upcoming events?! –  Richard Sweeney Feb 26 '11 at 13:53
    
@t31os I wasn't sure how to best go about it. What's wrong with two answers if they are truely distinct answers? Basically, i decided for a second rather than editing, because it was a very distinct answer and it left the 'comment-story' on the first one intact. –  wyrfel Feb 26 '11 at 15:09
    
@Richard Sweeney: Sure you can build a switch that applies a different filter. All depends on how and when you're adding the filter. You can also do both at the same time, i think, if you depend on the new 'meta_query' query value of 3.1, as that allows several meta queries at once, if i get it right. –  wyrfel Feb 26 '11 at 15:13
    
@wyrfel I find stack exchange confusing - I'm sure there must be a better way to present different answers or edits and these comments (rather than 'answers') kinda suck! I keep hitting enter by force of pure habit! Might you have time and/or energy to point me in the right direction regarding how to go about constructing a switch statement to toggle views? I'm rather a php/WordPress noob I'm afraid to say! Cheers –  Richard Sweeney Feb 26 '11 at 15:43

Use current_time('mysql') instead of time().

time() returns a unix timestamp (that is an integer), current_time('mysql') returns a mysql timestamp.

share|improve this answer
    
Cheers @wyrfel, the value is in fact stored as a unix timestamp, so time() works ok actually. –  Richard Sweeney Feb 26 '11 at 11:40
    
@Richard Sweeney: I see, was jumping to conclusions...see second answer. –  wyrfel Feb 26 '11 at 12:15

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

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