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.

I'm making a widget that shows a set of images from recent custom posts. I want to run the following query:

SELECT p.* 
FROM wp_posts p
WHERE post_type='attachment'
AND post_mime_type LIKE 'image%'
AND post_parent IN (
  SELECT ID
  FROM wp_posts
  WHERE post_type ='my_custom_post_type'
)
ORDER BY post_date DESC
LIMIT 10;

and receive an array of attachment objects. I am unclear on the canonical WordPress method for doing something like this. Where should I start?

share|improve this question
add comment

4 Answers

up vote 2 down vote accepted

It seems like a bit of a waste to run through two loops just to use some built in API functions that weren't designed for a use case like this.

I think you're better off to use your SQL combined with the wpdb class -- faster and cleaner.

Example (with modified SQL):

<?php
function wpse52315_get_attach()
{
    global $wpdb;
    $res = $wpdb->get_results("select p1.*
        FROM {$wpdb->posts} p1, {$wpdb->posts} p2
        WHERE p1.post_parent = p2.ID 
           AND p1.post_mime_type LIKE 'image%'
           AND p2.post_type = 'your_cpt'
        ORDER BY p2.post_date
        LIMIT 10;"
    );
    return $res;
}
share|improve this answer
    
thanks for this. I thought this might be the direction to go, but WP seems to discourage direct "touching" and I didn't want to set myself up for unfortunate side effects. –  dnagirl May 16 '12 at 17:39
add comment

If all you're interested in is the number of attachments for a particular post type, you can modify Chris' function slightly to the following:

<?php
function myprefix_image_count() {
    global $wpdb;
    $res = $wpdb->get_var("select COUNT(*)
        FROM {$wpdb->posts} p1, {$wpdb->posts} p2
        WHERE p1.post_parent = p2.ID
           AND p1.post_mime_type LIKE 'image%'
           AND p2.post_type = 'your_cpt_name'
        ORDER BY p2.post_date;"
    );
    $imageCount = (int)$res;
    return $imageCount;
}
?>
share|improve this answer
add comment

Maybe something like this:

<?php
  $args = array( 'post_type' => 'portfolio', 'posts_per_page' => 10 );
  $loop = new WP_Query( array ( 'orderby' => 'title', 'order' => 'DESC' ) );  
  while ( $loop->have_posts() ) : $loop->the_post();
    the_title();
    echo '<div class="entry-content">'; the_content();
    echo '</div>';
  endwhile;
  ?>
share|improve this answer
add comment

What I recommend is one instance of WP_Query for looping through all the custom post type post and then get_posts() to retrieve the attachments for each post. Here's an untested code snippet that should do what you want:

// Setup array for storing objects
$my_attachment_objects = array();

// Arguments for custom WP_Query loop
$my_cpts_args = array(
    'post_type' => 'my_custom_post_type',
    'posts_per_page' => 10
);

// Make the new instance of the WP_Query class
$my_cpts = new WP_Query( $my_cpts_args );

// And Loop!
if( $my_cpts->have_posts() ) : while( $my_cpts->have_posts() ) : $my_cpts->the_post();

    // arguments for get_posts
    $attachment_args = array(
        'post_type' => 'attachment',
        'post_mime_type' => 'image',
        'post_status' => null, // attachments don't have statuses
        'post_parent' => $post->ID
    );
    // get the posts
    $this_posts_attachments = get_posts( $attachment_args );
    // append those posts onto the array
    $my_attachment_objects[$post->ID] = $this_posts_attachments; // make an array with the post_id as the key, just in case that's useful

endwhile; endif; wp_reset_postdata();

Hope this helps.

share|improve this answer
add comment

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.