This is driving me nuts and I'm sure it's simple but nothing I search for comes up with a simple structure (everything is very complex).

I have a custom post type "product_listing" and a custom taxonomy of "product_cat" (which is hierarchical and should be have like categories).

I simply want my URLs to look like this:

mysite.com/products/category1/product-name1 
mysite.com/products/category2/product-name2

But for the life of me, no matter what I do, I'm getting the dreaded 404 issue. Pages work okay, and Posts work okay, but my custom posts don't work correctly. They're showing up as:

mysite.com/products/product-name1
mysite.com/products/product-name2

Which actually works! It's just that I want to see my custom taxonomy in there, PLUS, I want to be able to access the taxonomy.php template I have setup by going to:

mysite.com/products/category1/
mysite.com/products/category2/

None of my slugs are the same, nor do I want them to be. Here is the post type and taxonomy part of my functions.php file:

///// CUSTOM POST TYPES /////


// register the new post type
    register_post_type( 'product_listing',
        array( 'labels' => array(
            'name' => __( 'Products' ),
            'singular_name' => __( 'Product' ),
            'add_new' => __( 'Add New' ),
            'add_new_item' => __( 'Create New Product' ),
            'edit' => __( 'Edit' ),
            'edit_item' => __( 'Edit Product' ),
            'new_item' => __( 'New Product' ),
            'view' => __( 'View Products' ),
            'view_item' => __( 'View Product' ),
            'search_items' => __( 'Search Products' ),
            'not_found' => __( 'No products found' ),
            'not_found_in_trash' => __( 'No products found in trash' ),
            'parent' => __( 'Parent Product' ),
            ),
            'description' => __( 'This is where you can create new products on your site.' ),
            'public' => true,
            'show_ui' => true,
            'capability_type' => 'post',
            'publicly_queryable' => true,
            'exclude_from_search' => false,
            'menu_position' => 2,
            'menu_icon' => get_stylesheet_directory_uri() . '/images/tag_orange.png',
            'hierarchical' => true,
          '_builtin' => false, // It's a custom post type, not built in!
            'rewrite' => array( 'slug' => 'products', 'with_front' => true ),
            'query_var' => true,
            'supports' => array( 'title', 'editor', 'author', 'thumbnail', 'excerpt', 'trackbacks', 'custom-fields', 'comments', 'revisions' ),
            )
);



//hook into the init action and call create_book_taxonomies when it fires
add_action( 'init', 'create_product_taxonomies', 0 );
//add_action('admin_init', 'flush_rewrite_rules');

//create two taxonomies, genres and writers for the post type "book"
function create_product_taxonomies() 
{
  // Add new taxonomy, make it hierarchical (like categories)
  $labels = array(
    'name' => _x( 'Categories', 'taxonomy general name' ),
    'singular_name' => _x( 'Category', 'taxonomy singular name' ),
    'search_items' =>  __( 'Search Categories' ),
    'all_items' => __( 'All Categories' ),
    'parent_item' => __( 'Parent Categories' ),
    'parent_item_colon' => __( 'Parent Categories:' ),
    'edit_item' => __( 'Edit Category' ), 
    'update_item' => __( 'Update Category' ),
    'add_new_item' => __( 'Add New Category' ),
    'new_item_name' => __( 'New Category Name' ),
    'menu_name' => __( 'Category' ),
  );    

  register_taxonomy('product_cat',array('product_listing'), array(
    'hierarchical' => true,
    'labels' => $labels,
    'show_ui' => true,
    'query_var' => true,
    //'rewrite' => true,
    'rewrite' => array( 'slug' => '%category%', 'with_front' => true ),
  ));

  // Add new taxonomy, NOT hierarchical (like tags)
  $labels = array(
    'name' => _x( 'Scents', 'taxonomy general name' ),
    'singular_name' => _x( 'Scent', 'taxonomy singular name' ),
    'search_items' =>  __( 'Search Scents' ),
    'popular_items' => __( 'Popular Scents' ),
    'all_items' => __( 'All Scents' ),
    'parent_item' => null,
    'parent_item_colon' => null,
    'edit_item' => __( 'Edit Scent' ), 
    'update_item' => __( 'Update Scent' ),
    'add_new_item' => __( 'Add New Scent' ),
    'new_item_name' => __( 'New Scent Name' ),
    'separate_items_with_commas' => __( 'Separate scents with commas' ),
    'add_or_remove_items' => __( 'Add or remove scents' ),
    'choose_from_most_used' => __( 'Choose from the most used scents' ),
    'menu_name' => __( 'Scents' ),
  ); 

  register_taxonomy('scent','product_listing',array(
    'hierarchical' => false,
    'labels' => $labels,
    'show_ui' => true,
    'query_var' => true,
    //'rewrite' => array( 'slug' => 'scents' ),
  ));
}

I also have another custom taxonomy of "scents" that I'd ideally like to have some kind of friendly url but I'm more open on this. I'd like to maybe access a list of all scents by going to mysite.com/products/scents but they don't have to be category specific.

Can anybody help me? I've been going crosseyed for hours. Thanks!

link|improve this question

feedback

4 Answers

up vote 13 down vote accepted

Change slug in your post type arguments to products/%product_cat%, and slug in your taxonomy arguments to just products, then flush your rewrite rules. WordPress should now handle /products/my-product-cat/post-name/!

Now finally, we need to help WordPress a little with generating permalinks (out of the box, it won't recognise the permastruct tag %product_cat%):

function filter_post_type_link($link, $post)
{
    if ($post->post_type != 'product_listing')
        return $link;

    if ($cats = get_the_terms($post->ID, 'product_cat'))
        $link = str_replace('%product_cat%', array_pop($cats)->slug, $link);
    return $link;
}
add_filter('post_type_link', 'filter_post_type_link', 10, 2);

One thing to note, this will just grab the first product category for the post ordered by name. If you're assigning multiple categories to a single product, I can easily change how it determines which one to use in the permalink.

Lemme know how you get on with this, and we can tackle the other issues!

link|improve this answer
Oh WOW I'm in awe! This WORKED! Finally! I didn't ever think anything would!!! thank you SOOOOOO much!!! ............ Now, how would I generate a link (something like the_permalink) to grab the taxonomy url on its own? /products/my-product-cat/ – RodeoRamsey Dec 14 '10 at 3:21
I think I got that worked out^^^ ............ but now I'm stuck on Pagination. Seems to break when using any pagination (custom function or builtin) as /products/my-product-cat/ looks okay but /products/my-product-cat/page/2/ returns a 404 and drops the taxonomy.php file in favor of the index.php file. I've tried everything I could find and still nothing. – RodeoRamsey Dec 14 '10 at 6:45
1  
Would you consider changing the single product rewrites to product/cat-name/product-name? (note the singularity) The trouble is the rewrite rule for the taxonomy pagination isn't triggered, because it's getting caught by an earlier rule for single products! – TheDeadMedic Dec 14 '10 at 10:52
I'm open to it. But to wrap my head around it, would that mean products would have a different URL path if you're viewing a single product page vs. a 'category' page? So single would be product/cat-name/prod-name but cats would be products/cat-name/ ? Wouldn't that sort of defeat the purpose of "human friendly" urls? I have a hard time helping my clients learn the wp dashboard let alone that difference... If I'm misunderstanding pls let me know! I might also be happy with NO front directory, such as product-cat/product-nam and just product-cat/. Could that work? – RodeoRamsey Dec 14 '10 at 14:44
2  
You got it - though I'd say it is "human friendly", as there is a clear distinction between archives (products/) and singular items (product/). And no, I'd keep the 'front directory' - it helps keep a clear distinction from posts and pages, plus otherwise you might end up with performance issues (i.e. verbose rewrite rules). – TheDeadMedic Dec 14 '10 at 15:31
show 4 more comments
feedback

I'm not sure wp supports that structure out of the box - but you can very easily create your own rewrite rules to do so.

Check out a previous answer here Author url rewrite.

You can change the line

$newrules['author/([^/]+)/songs/?$'] = 'index.php?post_type=songs&author=$matches[1]';

to something like

$newrules['products/([^/]+)/([^/]+)/?$'] = 'index.php?post_type=product_listing&product_cat=$matches[1]&name=$matches[2]';

the product_cat part here may be superfluous - I am not sure if it is needed.

You can add any rules you like and they will have priority over the inbuilt ones.

link|improve this answer
Well isn't that interesting. Oh boy, I think custom rewrite rules are beyond me. I tried the above code (and the rest of it from the other post) and nothing changed. I flushed everything and then tried again and still no change, so I commented out all the rewrite rules set in the custom post types and taxonomies and flushed and STILL nothing. – RodeoRamsey Dec 14 '10 at 1:09
feedback

Yeah it was driving me crazy before setting the permalink for custom post type. I found a plugin to handle the custom post type. It's very easy to use. http://wordpress.org/extend/plugins/custom-post-permalinks/ WP should add this as a core feature! Leo

link|improve this answer
I had seen this one before and refrained from using it because it said "for non-hierarchical" taxonomies. I had one that was set to hierarchical so I didn't think it would work, but so far, it seems to have done the trick! Plus, it seems to be working to accomplish the /products/cat-name/prod-name/ structure I was trying to achieve (see comment to other answer). @TheDeadMedic, is this a viable option? Or should I stick with the rewrites in the functions.php file? – RodeoRamsey Dec 14 '10 at 17:57
feedback

Thanks @TheDeadMechanic, your answer helped me out, but only partially. I wanted to do the same thing @RodeoRamsey asked for, but with nested categories (ie: mysite.com/products/category1/child-category-1/grandchild-category-1/product-name) and your solution didn't work for that.

I finally came up with an extended solution to my question that works, so if anyone else needs nested categories/subcategories you can see a detailed solution on my own question. Hope it helps others, and thanks for the initial steps.

link|improve this answer
feedback

Your Answer

 
or
required, but never shown

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