Including category-base in a post permalink results in 404

I have static front-page and separate page /news/ as the Posts page. I would like to have the single-post URLs like this:

www.example.com/news/categoryname/subcategory/postname/

and for the category archives:

Read More
www.example.com/news/categoryname/

What I’ve tried already:

  • If I add news as my category base and /news/%category%/%postname%/ as the custom permalink structure, I get the desired URLs but also 404 error for single posts (both with news/ in URL and without it). All other pages (e.g. category archives, pages etc.) are accessible.

  • If I leave category-base empty and permalinks as /news/%category%/%postname%/, there are no 404 errors, but category URLs additionally contain the default category slug, like so: www.example.com/news/category/categoryname/

  • If I use plugins to remove the default category base or just set category base to . it’s removed together with the news part

  • If I set permalinks as /%category%/%postname%/ and add only the category base news, there are also no 404 errors, but links to posts don’t start with news: www.example.com/categoryname/subcategory/postname/

There are some similar unanswered questions: Posts not showing with custom categorybase and subcategories and wordpress permalinks tweeks

Related posts

Leave a Reply

4 comments

  1. You only need to add “/.” after category base:

    Category base: news/. (/. is required as it prevents 404s for post).

    This worked perfectly for me 🙂

    EDIT: This field will strip trailing or leading slashes unless you include the “.”

  2. I returned to this problem recently and I’ve found the solution finally! It may or may not work for you – there are two possible cases:

    1. If some posts on your site are placed under parent categories and some – in subcategories (child categories), or the categories have different nesting levels (some parent categories have only subcategories while others – sub-subcategories), then there is no solution. It’s impossible to distinguish news/category/post-name/ from news/category/subcategory/ with regex in rewrite rules.

    2. If you have fixed nesting level for all categories and post only in the last-level subcategories, then you are in luck! There is quite simple solution:

    The reason of those 404 pages with news both in category base and custom permalink structure is that the category base internal rewrite rule takes the precedence over the permalink structure rules. So news/category/subcategory/postname/ is interpreted as index.php?category_name=category/subcategory/postname and, obviously, WordPress can’t find such category, returning 404 page.

    What you need to do is to add new rewrite rule on top of the rules list. Place this code in your functions.php or wherever you think it’s appropriate:

    add_action( 'init', 'wpa58471_category_base' );
    function wpa58471_category_base() {
        // Remember to flush the rules once manually after you added this code!
        add_rewrite_rule(
            // The regex to match the incoming URL
            'news/([^/]+)/([^/]+)/([^/]+)(/[0-9]+)?/?$',
            // The resulting internal URL
            'index.php?category_name=$matches[1]/$matches[2]&name=$matches[3]&paged=$matches[4]',
            // Add the rule to the top of the rewrite list
            'top' );
    }
    

    and then update permalink structure from your WordPress General Options page. The code above is for two-level nesting, if you have more or less nested category structure, then edit the regex and resulting URL accordingly.

    P.S. thanks to contributors of these useful answers: help with add_rewrite_rule and tool to analyze rewrite rules.

  3. Custom permalink structure: /media/%category%/%postname%/
    Category base: .

    Worked for me, WordPress 3.4.1, without any related plugins.

    Update: Well, later I’ve noticed that wp_list_categories outputs links without “media” in the URL. But posts are accessible with the desired URL structure, and categories archives is in the right place.
    Now I’m looking into changing wp_list_categories behavior.

  4. I’d better post a comment, but I cannot for now. Your code works perfectly, but if you do not want to break the per category RSS feeds it should look like this:

    add_action( 'init', 'wpa58471_category_base' );
    function wpa58471_category_base() {
    // Remember to flush the rules once manually after you added this code!
        add_rewrite_rule(
        // The regex to match the incoming URL
        'news/([^/]+)/([^/]+)/([^/][^f][^e][^e][^d]+)(/[0-9]+)?/?$', //here my changes to exclude 'feed'
        // The resulting internal URL
        'index.php?category_name=$matches[1]/$matches[2]&name=$matches[3]&paged=$matches[4]',
        // Add the rule to the top of the rewrite list
        'top' );
    }
    

    Anyways, thanks for a great code sample. 🙂