Deep Tech Point
first stop in your tech adventure

Disable WordPress REST API (wp-json)

December 29, 2020 | WordPress development

Since WordPress released version 4.7.0. developers can connect the third-party apps with the backend core through a REST API endpoint. This was really great news for developers that marked a new level of WordPress platform usability. Version after version WordPress team ironed out the REST API imperfections, fixed bugs, and added missing features such as different authorization methods. Everything is great – for developers – but what about all those WordPress users that don’t need API? Well, they might need it sometime in the future and it’s there without an easy option to turn it off. The unused feature almost always introduces costs in resources and potential security concerns so let’s see how we can cut it out of our WordPress installation.

To be precise, the WordPress REST API existed even before version 4.7.0. at first in the form of a plugin. If only it stayed that way this article would be useless. However, it has been added to the WP core so tightly that it would be rather impossible to remove it completely, or at least new updates would require quite an effort.

WordPress’s official suggestion is to leave the REST API as it is. If you try to disable it, you might break some dependencies like the Admin panel functionality. But then what we can do about it? Well, a few things.

First, we will filter out links to the REST API endpoint from our HTTP headers.

remove_action('template_redirect', 'rest_output_link_header', 11);

Second, we will remove the REST API links in the HTML <head>.

remove_action('wp_head', 'rest_output_link_wp_head', 10);
remove_action('xmlrpc_rsd_apis', 'rest_output_rsd');

Finally, we will send an error code to anyone who may attempt to query the REST API endpoint directly. But since we need our Admin panel working we will do it only to the non-logged users.

add_filter( 'rest_authentication_errors', function( $result ) {
    if ( ! is_user_logged_in() ) {
        return new WP_Error(
            'rest_not_logged_in',
            __( 'You are not currently logged in.' ),
            array( 'status' => 401 )
        );
    }
    return $result;
});

Put the upper code into functions.php of your active theme and that should be it. I know, I know, it’s not exactly what I promised at the beginning of this article but it still fulfills our requirement regarding better security. It also repels crawlers, bots, and other internet pests that might try to use your REST API to leach your content.

We should not forget legacy users. If you are using an older WordPress version than 4.7.0. you don’t need the rest_authentication_errors filter but just put the following filters.

add_filter('json_enabled', '__return_false');
add_filter('json_jsonp_enabled', '__return_false');
add_filter('rest_enabled', '__return_false');
add_filter('rest_jsonp_enabled', '__return_false');

These cover version 1.x and version 2.x of the legacy API.