Only expose routes with prefix /wp-json on WordPress using Apache

Try the following mod_rewrite directives instead at the top of your root .htaccess file (before the # BEGIN WordPress section):

# Reject any user requests that are not prefixed "/wp-json"
RewriteCond %{ENV:REDIRECT_STATUS} ^$
RewriteRule !wp-json($|/) - [F]

Requested URLs that are not prefixed /wp-json (or /wp-json/) are rejected with a 403 Forbidden.

The RewriteCond directive that checks against the REDIRECT_STATUS environment variable is to ensure that only requests from the client are blocked and not internally rewritten requests to index.php (the WordPress front-controller). REDIRECT_STATUS is empty on the initial request and set to “200” (as in 200 OK status) after the first successful rewrite.

<Directory />
    AllowOverride None
</Directory>
<Directory /wp-json*>
    AllowOverride All
</Directory>
<Directory /wp-json*/*>
    AllowOverride None
</Directory>

<Directory> and AllowOverride are server-only directives and will trigger a 500 Internal Server Error if used in .htaccess. However, AllowOverride enables/disables .htaccess overrides (it doesn’t block access) – which is not what you want to do here (.htaccess overrides are probably already enabled). And /wp-json is not a physical “directory” on the filesystem, so the <Directory> directive does not apply here.

Order deny,allow
Deny from all
Allow from all

Having Deny from all and Allow from all in the same context doesn’t really make sense. (You would need to disable access for the root and enable access for the specific URL-path prefix.) However, Order, Deny and Allow are Apache 2.2 directives and you are more likely to be on an Apache 2.4 server. These directives are now deprecated in favour of the Apache 2.4 Require group of directives.