• I have two custom taxonomies, one for “client,” which is literally the client’s name, so “John Smith,” and another for “clothing,” which is like “pants, shirts, shoes.”

    The “client” tax is used to attach content to a client, and is used for images and other cpt. The “clothing” tax is only attached to images and used to sort images based on their category.

    I’m trying to show a list of categories that is custom to each client, meaning, if a single client only has 2 images attached to clothing – > shirt, when this client is logged in looking at their account page on the front-end of the site, I only want that client to see a single tax term from clothing for “shirts.”

    By default, wp_list_categories() would return all categories site-wide, including every client and every image of every client. That is not what I want.

    This code returns what I want, but it’s not unique to the client:

    
    wp_list_categories( array(
                            'orderby'      => 'title',
                            'order'        => 'ASC',
                            'show_count'   => true,
                            'title_li'     => '',
                            'taxonomy'     => 'clothing',
    ));
    

    I’m trying to add an additinal tax query to the above to make the output unique to a specific client, from the client tax.

    This returns the same as the above:

    
    wp_list_categories( array(
                            'orderby'      => 'title',
                            'order'        => 'ASC',
                            'show_count'   => true,
                            'title_li'     => '',
                            'taxonomy'     => 'clothing',
                            'tax_query'    => array(
                               array(
                                  'taxonomy'  => 'client',
                                  'field'     => 'slug',
                                  'terms'     => $currentUser,
                               ),
                            ),
    ));

    Note: $currentUser outputs the correct logged in test user in all these examples

    Last, I tried this but it still returns all of the “clothing” tax items.

    
    wp_list_categories( array(
                               'orderby'      => 'title',
                               'order'        => 'ASC',
                               'show_count'   => true,
                               'title_li'     => '',
                               'taxonomy'     => 'clothing',
                               'tax_query'    => array(
                                  'relation'  => 'AND',
                                  array(
                                     'taxonomy'  => 'clothing',
                                     'field'     => 'slug',
                                     'terms'     => array(),
                                  ),
                                  array(
                                     'taxonomy'  => 'client',
                                     'field'     => 'slug',
                                     'terms'     => $currentUser,
                                  ),
                               ),
                            ) );
    

    So my relation => ‘AND’ is not filtering properly. For the clothing tax query, I want it to return all terms that are attached, for the client tax query, I want to then limit the clothing terms returned to only belonging to that client.

    What am I missing with this, provided it’s even possible?

Viewing 8 replies - 1 through 8 (of 8 total)
  • You are adding parameters to a function that doesn’t look at them.
    wp_list_categories is only for getting a list of terms for a taxonomy, not for terms that apply to certain objects. https://developer.www.ads-software.com/reference/functions/wp_list_categories/
    The tax_query field makes no sense on a taxonomy list function.
    Taxonomies are for querying posts(post types), so if you go to the taxonomy link of the user’s name(run that query), you would see the posts and each post would have the other taxonomy’s terms that were set. You don’t get the whole list of terms, but just the ones on each post.

    There is an old plugin called Query Multiple Taxonomies. It is no longer supported, but you can make links to show posts by using the slugs of the two taxonomies. Or if there are two terms in the same taxonomy, use a + between the terms.

    https://developer.www.ads-software.com/reference/functions/get_the_terms/
    get_the_terms() gives you all the terms for one post. That’s not really what you want either, but it’s useful for themes to show on the single post page.

    Thread Starter traveler

    (@visualeight)

    Hello Joy,
    Thanks for your response. So, perhaps I’m reading the documentation incorrectly, but going to the wp_list_categories link above in your response, the first list item under args reads like this function can accept other parameters like get_categories, get_terms, or WP_Term_Query.

    So in the documentation, when a function says additional arguments can be added like other linked functions, am I interpreting that wrong? I see it on a lot of function pages in the docs..

    Since images are a post type, can’t they be queried in the same manner with multiple tax_query’s?

    If you actually clicked on those other functions to read their parameters, you would see the full list, and see that retrieving taxonomy terms is not the same as retrieving the post objects that the terms point to.

    Images are stored in the post table, and if you have added taxonomies to images, then you can find the images by using the taxonomies. But the wp_list_categories function is about retrieving all the terms defined, not the posts the terms are assigned to.
    A tax_query is for the posts table, not the taxonomy tables.

    Moderator bcworkz

    (@bcworkz)

    Hi traveler – Your goal is to list only clothing terms which are presently assigned to images that are assigned a particular client. I assume the terms are assigned to image attachment posts. The only way to do that is to query for all image attachment posts with the particular client term assigned. Loop through the found attachments to collect all assigned clothing terms. Take measures to ensure there are no redundant terms while building the list. You can then use the resulting list of terms for direct output, or compile an array of unique term IDs for use with the “include” arg for something like wp_dropdown_categories() (which can display other taxonomy terms instead of category terms)

    Thread Starter traveler

    (@visualeight)

    Hey bcworkz, thanks for your reply. To clarify, the images being queried are saved to an ACF image gallery field on the client’s page. Is that what you mean by “I assume the terms are assigned to image attachment posts”?

    So I abandoned the approach I had outlined above and instead went back to query all images attached to that client’s page through the ACF gallery. The query is returning the correct images. So then I did a var_dump($imgQuery) to see what all was returned. I should note, this is the first time I’ve viewed a query like this so most of it made sense but it seemed like a lot of things were repeated throughout. But, the point is, the correct images were returned and looking at the query behind it the image IDs were correct and post_parent also returned the correct post/client parent.

    In theory what you said above makes sense, but looking at the returned data I do not see any mention of the custom tax that is attached to the media attachments. My thoughts were to take the returned image IDs and use that to pull the assigned taxonomy, but I did not see a WP function that would take an image ID and return it’s assigned taxonomy. But, I do not see a WP function that does that unless I’ve read through the documentation and not fully understood it.

    Can you please point me in the direction of what I need to pull the assigned tax for the images? Ideally, once the assigned custom tax for each image is procured, I’d like to push them into different arrays (if assigned “shoes” taxonomy, it’s pushed to shoeArray().

    Here is a sample of the returned image loop that is returning the correct images:

    
    public 'posts' => 
        array (size=6)
          0 => 
            object(WP_Post)[2262]
              public 'ID' => int 241
              public 'post_author' => string '2' (length=1)
              public 'post_date' => string '2020-10-08 01:27:48' (length=19)
              public 'post_date_gmt' => string '2020-10-08 01:27:48' (length=19)
              public 'post_content' => string '' (length=0)
              public 'post_title' => string 'johnny-firstperson_sunglasses' (length=29)
              public 'post_excerpt' => string '' (length=0)
              public 'post_status' => string 'inherit' (length=7)
              public 'comment_status' => string 'closed' (length=6)
              public 'ping_status' => string 'closed' (length=6)
              public 'post_password' => string '' (length=0)
              public 'post_name' => string 'johnny-firstperson_sunglasses' (length=29)
              public 'to_ping' => string '' (length=0)
              public 'pinged' => string '' (length=0)
              public 'post_modified' => string '2020-10-08 01:29:48' (length=19)
              public 'post_modified_gmt' => string '2020-10-08 01:29:48' (length=19)
              public 'post_content_filtered' => string '' (length=0)
              public 'post_parent' => int 216
              public 'guid' => string 'https://closetleesaevans.local/wp-content/uploads/2020/10/johnny-firstperson_sunglasses.jpg' (length=90)
              public 'menu_order' => int 0
              public 'post_type' => string 'attachment' (length=10)
              public 'post_mime_type' => string 'image/jpeg' (length=10)
              public 'comment_count' => string '0' (length=1)
              public 'filter' => string 'raw' (length=3)
          1 => 
            object(WP_Post)[2235]
              public 'ID' => int 242
              public 'post_author' => string '2' (length=1)
              public 'post_date' => string '2020-10-08 01:27:48' (length=19)
              public 'post_date_gmt' => string '2020-10-08 01:27:48' (length=19)
              public 'post_content' => string '' (length=0)
              public 'post_title' => string 'johnny-firstperson_top_hat' (length=26)
              public 'post_excerpt' => string '' (length=0)
              public 'post_status' => string 'inherit' (length=7)
              public 'comment_status' => string 'closed' (length=6)
              public 'ping_status' => string 'closed' (length=6)
              public 'post_password' => string '' (length=0)
              public 'post_name' => string 'johnny-firstperson_top_hat' (length=26)
              public 'to_ping' => string '' (length=0)
              public 'pinged' => string '' (length=0)
              public 'post_modified' => string '2020-10-08 01:29:35' (length=19)
              public 'post_modified_gmt' => string '2020-10-08 01:29:35' (length=19)
              public 'post_content_filtered' => string '' (length=0)
              public 'post_parent' => int 216
              public 'guid' => string 'https://closetleesaevans.local/wp-content/uploads/2020/10/johnny-firstperson_top_hat.jpg' (length=87)
              public 'menu_order' => int 0
              public 'post_type' => string 'attachment' (length=10)
              public 'post_mime_type' => string 'image/jpeg' (length=10)
              public 'comment_count' => string '0' (length=1)
              public 'filter' => string 'raw' (length=3)
          2 => 
            object(WP_Post)[2265]
              public 'ID' => int 239
              public 'post_author' => string '2' (length=1)
              public 'post_date' => string '2020-10-08 01:27:47' (length=19)
              public 'post_date_gmt' => string '2020-10-08 01:27:47' (length=19)
              public 'post_content' => string '' (length=0)
              public 'post_title' => string 'johnny-firstperson_shirt-1' (length=26)
              public 'post_excerpt' => string '' (length=0)
              public 'post_status' => string 'inherit' (length=7)
              public 'comment_status' => string 'closed' (length=6)
              public 'ping_status' => string 'closed' (length=6)
              public 'post_password' => string '' (length=0)
              public 'post_name' => string 'johnny-firstperson_shirt-1' (length=26)
              public 'to_ping' => string '' (length=0)
              public 'pinged' => string '' (length=0)
              public 'post_modified' => string '2020-10-08 01:29:06' (length=19)
              public 'post_modified_gmt' => string '2020-10-08 01:29:06' (length=19)
              public 'post_content_filtered' => string '' (length=0)
              public 'post_parent' => int 216
              public 'guid' => string 'https://closetleesaevans.local/wp-content/uploads/2020/10/johnny-firstperson_shirt-1.jpg' (length=87)
              public 'menu_order' => int 0
              public 'post_type' => string 'attachment' (length=10)
              public 'post_mime_type' => string 'image/jpeg' (length=10)
              public 'comment_count' => string '0' (length=1)
              public 'filter' => string 'raw' (length=3)
          3 => 
            object(WP_Post)[2266]
              public 'ID' => int 240
              public 'post_author' => string '2' (length=1)
              public 'post_date' => string '2020-10-08 01:27:47' (length=19)
              public 'post_date_gmt' => string '2020-10-08 01:27:47' (length=19)
              public 'post_content' => string '' (length=0)
              public 'post_title' => string 'johnny-firstperson_shoes-1' (length=26)
              public 'post_excerpt' => string '' (length=0)
              public 'post_status' => string 'inherit' (length=7)
              public 'comment_status' => string 'closed' (length=6)
              public 'ping_status' => string 'closed' (length=6)
              public 'post_password' => string '' (length=0)
              public 'post_name' => string 'johnny-firstperson_shoes-1' (length=26)
              public 'to_ping' => string '' (length=0)
              public 'pinged' => string '' (length=0)
              public 'post_modified' => string '2020-10-08 01:29:12' (length=19)
              public 'post_modified_gmt' => string '2020-10-08 01:29:12' (length=19)
              public 'post_content_filtered' => string '' (length=0)
              public 'post_parent' => int 216
              public 'guid' => string 'https://closetleesaevans.local/wp-content/uploads/2020/10/johnny-firstperson_shoes-1.jpg' (length=87)
              public 'menu_order' => int 0
              public 'post_type' => string 'attachment' (length=10)
              public 'post_mime_type' => string 'image/jpeg' (length=10)
              public 'comment_count' => string '0' (length=1)
              public 'filter' => string 'raw' (length=3)
          4 => 
            object(WP_Post)[2267]
              public 'ID' => int 237
              public 'post_author' => string '2' (length=1)
              public 'post_date' => string '2020-10-08 01:27:46' (length=19)
              public 'post_date_gmt' => string '2020-10-08 01:27:46' (length=19)
              public 'post_content' => string '' (length=0)
              public 'post_title' => string 'johnny-firstperson_jacket-1' (length=27)
              public 'post_excerpt' => string '' (length=0)
              public 'post_status' => string 'inherit' (length=7)
              public 'comment_status' => string 'closed' (length=6)
              public 'ping_status' => string 'closed' (length=6)
              public 'post_password' => string '' (length=0)
              public 'post_name' => string 'johnny-firstperson_jacket-1' (length=27)
              public 'to_ping' => string '' (length=0)
              public 'pinged' => string '' (length=0)
              public 'post_modified' => string '2020-10-08 01:28:06' (length=19)
              public 'post_modified_gmt' => string '2020-10-08 01:28:06' (length=19)
              public 'post_content_filtered' => string '' (length=0)
              public 'post_parent' => int 216
              public 'guid' => string 'https://closetleesaevans.local/wp-content/uploads/2020/10/johnny-firstperson_jacket-1.jpg' (length=88)
              public 'menu_order' => int 0
              public 'post_type' => string 'attachment' (length=10)
              public 'post_mime_type' => string 'image/jpeg' (length=10)
              public 'comment_count' => string '0' (length=1)
              public 'filter' => string 'raw' (length=3)
          5 => 
            object(WP_Post)[2316]
              public 'ID' => int 238
              public 'post_author' => string '2' (length=1)
              public 'post_date' => string '2020-10-08 01:27:46' (length=19)
              public 'post_date_gmt' => string '2020-10-08 01:27:46' (length=19)
              public 'post_content' => string '' (length=0)
              public 'post_title' => string 'johnny-firstperson_pants-1' (length=26)
              public 'post_excerpt' => string '' (length=0)
              public 'post_status' => string 'inherit' (length=7)
              public 'comment_status' => string 'closed' (length=6)
              public 'ping_status' => string 'closed' (length=6)
              public 'post_password' => string '' (length=0)
              public 'post_name' => string 'johnny-firstperson_pants-1' (length=26)
              public 'to_ping' => string '' (length=0)
              public 'pinged' => string '' (length=0)
              public 'post_modified' => string '2020-10-08 01:28:57' (length=19)
              public 'post_modified_gmt' => string '2020-10-08 01:28:57' (length=19)
              public 'post_content_filtered' => string '' (length=0)
              public 'post_parent' => int 216
              public 'guid' => string 'https://closetleesaevans.local/wp-content/uploads/2020/10/johnny-firstperson_pants-1.jpg' (length=87)
              public 'menu_order' => int 0
              public 'post_type' => string 'attachment' (length=10)
              public 'post_mime_type' => string 'image/jpeg' (length=10)
              public 'comment_count' => string '0' (length=1)
              public 'filter' => string 'raw' (length=3)
    

    Since an attachment is a post type, you can use
    https://developer.www.ads-software.com/reference/functions/get_the_terms/
    passing the attachment ID or object.

    Thread Starter traveler

    (@visualeight)

    Hello Joy, thank you for clearing that up for me!

    Thread Starter traveler

    (@visualeight)

    I wanted to follow up on this, been busy on a different project, but in case anyone is following this thread for a similar reason I wanted to post my progress.

    The ultimate goal is to have a dynamically created menu based off of a custom taxonomy for “clothing” that corresponds to a logged-in user and images attached to that logged-in user with the clothing taxonomy. So if a single user has 3 pairs of shoes (as images) attached to their profile, then this menu should show a link for “shoes” and take that user to a list/archive view of their images with that “shoes” tax.

    My image query pulled in all of the images attached to a user/client’s page:

    <?php  
                            $imgArgs = array(
                               'post_type'       => 'attachment',
                               'post_mime_type'  => 'image',
                               'post_status'     => 'inherit',
                               'post_per_page'   => -1,
                               'tax_query'    => array(
                                  array(
                                     'taxonomy'     => 'client',
                                     'field'        => 'slug',
                                     'terms'        => $currentUser,
                                     'order'           => 'ASC',
                                     'orderby'         => 'menu_order',
                                  ),
                               ),
                            );
                            $imgQuery = new WP_Query($imgArgs);
                            if ($imgQuery->have_posts()) :
                               $returnedTaxes = array();
                               while ($imgQuery->have_posts()) : $imgQuery->the_post();
                                  
                               // CHECKS IF IMAGE HAS CLOTHING TAX ASSIGNED
                               // PREVENTS ERROR ON UNCATEGORIZED IMAGE
                                  if (get_the_terms( get_the_ID(), 'clothing' )):
    
                                     foreach ( get_the_terms( get_the_ID(), 'clothing' ) as $tax ): 
                                        $taxName = $tax->name;  
                                        $returnedTaxes[] = $taxName;
                                     endforeach;
    
                                  else:
                                     $returnedTaxes[] = 'uncategorized';
    
                                  endif;
                               endwhile;
    else :
                                  echo '<p>There are no closet items yet.</p>';
                            endif;
                            wp_reset_postdata(); ?>
    

    This worked fine to pull in the images based on the $currentUser variable which pulls in the current logged-in user. Then for the images pulled in by the query, I first check if they have the “clothing” tax assigned to them, if a single image did not have a clothing tax assignment, it threw an error. For the images with assigned clothing tax’s, I pushed those into an array. For any potential image that is not assigned to the clothing tax, I pushed that to the same array using “uncategorized” as a temporary tax and to not throw an error.

    Then I used a foreach loop to go through this array and separate them into key/value pairs which only returns the tax name of items assigned that tax that are attached to that client page. This was intentional, so if a client does not have any image assigned to the clothing tax, they will not see an option to visit an empty list feed for that tax item.

    
    // BUILD LIST OF CLOTHING TAX TERMS
                               foreach(array_count_values($returnedTaxes) as $key => $total):
                                  // $termLink = get_term_link($key, 'clothing');
    
                                  // echo print_r($termLink);
                                  echo $key . ' ' . $total . '<br>';
                               
    
                               endforeach;
    

    The above foreach loop is correctly returning the number of images assigned to the clothing tax and this particular user.

    Now what remains is to add an active link to the tax terms that are rendered based on the image query, so that a client can open their “closet page” and see their clothing taxonomy of images, and essentially sort through his/her closet on their phone.

    To do this, since there is not a default archive view for tax terms, my plan was to create a layout for the clothing tax, “taxonomy-clothing.php”, and use this to query images for a signed-in user that are attached to their client page and have the clothing tax. So if you have 300 sleeveless shirts, then in this menu you’d see a link for “sleeveless” and clicking it would take you to a tax list of “clothing-sleeveless” images. I would need a way to populate the specific tax term in the query dynamically based on the link clicked.

    My question would be, do you recommend the above approach I’ve taken or would you advise I go about it differently. Two, to create the taxonomy links to view all “sleeveless” or all “boots”, does the plan above make sense for this? Any recommendation on dynamically populating the tax query term like “sleeveless” or “boots”?

Viewing 8 replies - 1 through 8 (of 8 total)
  • The topic ‘wp_list_categories() by multiple custom taxonomy queries’ is closed to new replies.