There seems to be quite a controversial opinion on the WordPress flush_rewrite_rules() function.

According to the Codex, it is highly discouraged to use this function on the init action hook.


In a plugin I am working on, I am using add_feed() to, well, add a feed. The Codex says that this should be run on init and requires a one-time use of flush_rewrite_rules().

See my dilemma ? I need add_feed() on init, which requires flush_rewrite_rules().

Hence, flush_rewrite_rules() on init, which is breaking all custom post type rewrite rules and permalinks, resulting in 404 pages.

So my question is: how should this be done ?

This is what I currently have on init, that is related to the issue:

add_action( 'init', 'my_foobar' );
function my_foobar() {
    // getting some settings
    add_feed( $url, $callback );

Any help would be greatly appreciated. thanks :)

1 Answer 1


You have to check the existing rewrite rules before you run a flush. If your feed name is test, they are stored under the keys 'feed/(feed|rdf|rss|rss2|atom|test)/?$' and '(feed|rdf|rss|rss2|atom|test)/?$'.

So this should do the trick:

add_action( 'init', function()
    $name       = 'test';
    $registered = FALSE;

    add_feed( $name, 'test_feed' );

    $rules = get_option( 'rewrite_rules' );
    $feeds = array_keys( $rules, 'index.php?&feed=$matches[1]' );

    foreach ( $feeds as $feed )
        if ( FALSE !== strpos( $feed, $name ) )
            $registered = TRUE;

    // Feed not yet registered, so lets flush the rules once.
    if ( ! $registered )
        flush_rewrite_rules( FALSE );
  • Accepted! Works brilliantly. I guess that $wp_rewrite global variable slipped past me. Thanks
    – Mecha
    Nov 28, 2013 at 15:14
  • @Mekku That global variable isn’t even needed. I have removed it from my answer.
    – fuxia
    Nov 28, 2013 at 15:17
  • Yes I noticed after I commented. One quick question. Is the second parameter of the array_keys function treated as a regex pattern ?
    – Mecha
    Nov 28, 2013 at 15:20
  • No, just a search string.
    – fuxia
    Nov 28, 2013 at 15:22
  • So what is the reasoning behind using $matches[1] in the search string ? The string you used uses single quotes, so the string isn't even interpolated. Thanks
    – Mecha
    Nov 28, 2013 at 15:25

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

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