get attachments for all posts of particular post type

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?

Solutions Collecting From Web of "get attachments for all posts of particular post type"

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;
}

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.

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;
  ?>

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;
}
?>