0

I am looking to implement a custom post query that includes the following parameters:

  • WordPress custom loop to select the oldest post from a custom post type and display it on the page. There are multiple pages that will use this logic.
  • Use PHP/WordPress logic to retrieve the second oldest post fourteen days later. This post would replace the oldest post on the page.
  • After another fourteen days has passed, use the same logic to the retrieve the third oldest post. This logic should continue every fourteen days.
  • The same logic with a slight variation should be used to populate an HTML dropdown menu. This menu will display all of the posts except for the one that is currently being displayed on the page as title, content, custom fields, etc.
  • Advanced Custom Fields is installed and can be used in a meta_query if necessary.

Detailed Explanation

The client's website use pages with a custom template to display posts retrieved from the "sendouts" custom post type. These pages are referred to as "retailers" internally. Retailers will be added to the site at various times throughout the year. Each retailer is a business that will be providing send outs to their customers. The "sendout" posts will be a general pool that will be available to all of the retailers. New "sendout" posts will be added to WordPress every fourteen days by the client. When a new retailer page is created, the first post it will display will be the oldest. This post will display on the page. After fourteen days, the second oldest "sendout" post will be displayed on the page and the oldest will be moved into a HTML dropdown menu. This will continue every fourteen days for each retailer page.

The displaying of "sendout" posts will be unique to each page unless two pages were created on the same day. The page created date or use of Advanced Custom Fields could be used to provide the necessary parameters to achieve this functionality.

Base Code

$postDate = post_date_gmt('Y-m-d H:i:s');

$args = array(
    'post_type' => 'sendouts',
    'cat' => '101',
    'order' => 'ASC',
    'orderby' => 'date',
    'date_query' => array(
        'after' => 'post_date_gmt',
        'before' => array(
            // Possibly use: $postDate->add(new DateInterval('P14D')),
        ),
        'inclusive' => true,
     ),
     'posts_per_page' => -1,
);
query_posts($args);

Loop for HTML dropdown

<?php query_posts($args); ?>
    <?php if (have_posts()) : ?>
        <div class="sendout__nav-trigger">
            <button class="btn btn--nav-trigger">
                <span>Past Sendouts</span>
            </button>
        </div>
        <ul class="sendout__list">
        <?php if ( $query->have_posts() ) : while ( $query->have_posts() ) : $query->the_post(); ?>
            <li>
                <a href="<?php the_permalink(); ?>" rel="<?php the_ID(); ?>" class="sendout-link"><?php the_title(); ?></a>
            </li>
        <?php endwhile; endif; wp_reset_query(); ?>
        </ul>
    <?php else : ?>
        <p>
            <strong>Sorry, there are no retailer send outs to display.</strong>
        </p>
    <?php endif; ?>

My PHP knowledge is novice and my WordPress knowledge is midlevel, so I may be approaching this the wrong way.

  • This sounds complicated, what are you actually trying to build that this technical solution is meant to solve? What was the clients original requirement or problem? I see your code references sendouts, but you make no mention of it anywhere else in your question :( Providing context can help people devise solutions/answers, and make your question easier to understand. Phrasing things in generic terms, or as a specific solution you aren't sure of can hurt your Q. Also, avoid query_posts like the plague, never use that function. – Tom J Nowell Feb 1 at 0:32
  • The functionality is similar to a time-released/drip content, subscription-style system. In this case retailers providing send outs to farmers using a WP custom post type (sendouts) and advanced custom fields on a two week schedule. Would a custom plugin be better suited? What are the cons of query_posts? Cheers. – Mike Hermary Feb 1 at 1:36
  • Re: query_posts, there are no reasonable uses of the function, and it introduces a lot of problems. Do a search on the site for query_posts vs the better ways to do things like the pre_get_posts filter, or WP_Query. query_posts is a function you should not learn or use, it encourages bad habits, causes problems, reduces performances/site speed, and there are better alternatives. Consider its presence in WP legacy backwards compat – Tom J Nowell Feb 1 at 11:01
  • Also, are these posts sent out to everybody? Are farmers going to see the same sendouts all of which get released 14 days later? Or does each user have their own timetable of 14 days etc? There's still some ambiguity here, I'm unfamiliar with what sendouts are or how they work. Scheduled publishing dates could do the job, but that would publish for all people at the same time, which might be what you want, or don't want, I don't know :/ – Tom J Nowell Feb 1 at 11:04
  • Where is the $query variable for your HTML dropdown created? – Tom J Nowell Feb 1 at 11:05
0
+50

I've quickly tested the below code with a small subset of sendouts ( 3 ) and changing the publishing date of my page that uses this template it works fine

<?php
/**
* Template Name: show sendouts template
*
*/
get_header();
global $wpdb, $post;
$curDate=strtotime(date('Y-m-d H:i:s'));

$postDate=strtotime($post->post_date);

$pageAge=($curDate-$postDate) / (60 * 60 * 24); // age of the page in days

$steps= 14; // days used as interval between the steps
$totSteps= intval($pageAge / $steps); // how many steps passed from the page publishing date

$Q = "SELECT ID, post_title FROM ".$wpdb->prefix."posts where post_type = 'sendout' and post_status = 'publish' ORDER BY post_date ASC LIMIT ".($totSteps + 1);

$sendouts=$wpdb->get_results($Q);
$dropDownoptions=[];

$dropDownoptions[]='<option value="" selected>Pick a sendout</option>';
for($k = 0 ; $k < count( $sendouts) ; $k ++){
  if($totSteps == $k ){
    // use the post which corresponds to the current step as main post
    $mainPost =get_post($sendouts[$k]->ID);
  }
  else{
    // use the others to populate the dropdown
    $dropDownoptions[]= '<option value = "'.get_the_permalink($sendouts[$k]->ID).'">'.$sendouts[$k]->post_title.'</option>';
  }
}
// MAIN CONTENT
echo '<h1>'.$mainPost->post_title.'</h1>';
echo '<p>'.$mainPost->post_content.'</p>';
?>
<!-- DROPDOWN-->
<select id="sendout_select"><?php foreach($dropDownoptions as $option){echo $option;}?></select>
  <script>
    jQuery(function(){
      // bind change event to select
      jQuery('#sendout_select').on('change', function () {
          var url = jQuery(this).val(); // get selected value
          if (url) { // require a URL
              window.location = url; // redirect
          }
          return false;
      });
    });
</script>
<?
get_footer();
| improve this answer | |

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.