Template post type is never registered on requests authed outside determine_current_user (28.5.9.1)
SYMPTOM. On 28.5.9.1, a REST request authenticated by a bearer token — in my case AI Engine's MCP endpoint — sees the template post type as absent. post_type_exists returns false, and anything depending on the post type (querying templates, creating one) fails, even though the resolved user is a full administrator. My own plugin works around it by registering the post type itself when it finds it missing. Measured with hook-only instrumentation, no theme files modified. Instrumentation is still in place, so send me any patch and I will re-run the same request and return the same rows.
WHERE IT COMES FROM. functions/post-types/class-mfn-post-type-template.php is 2516 lines, and line 2516 — the last line — instantiates the class at file load.
In the constructor, line 23 opens a guard on Sitepress not existing. Inside it, the bebuilder_access filter bails at 25-26, and the editor/administrator test bails at 29-30. That guard closes at 33. The parent constructor call at 35 and the init attachment at 38 are outside it. So with WPML present the post type registers unconditionally; without it, registration is decided at file load, before authentication has run.
WHAT I MEASURED. Reading the current-user global directly, without calling anything that would resolve it:
set_current_user ... 0
setup_theme ........ 0
after_setup_theme .. 0
init priority 1 .... 0
init priority 9999 . 0
rest_api_init ...... 0
route handler ...... 1
ALREADY RULED OUT: MOVING THE CHECK TO INIT. It does not help, and not for a timing reason. At every point above, the determine_current_user callbacks are only the three core ones: wp_validate_auth_cookie, wp_validate_logged_in_cookie, wp_validate_application_password. AI Engine registers none, and sets the user explicitly inside its route handler instead. So there is no point before dispatch at which that token could be resolved, by any hook. You can confirm this in your own environment by dumping the determine_current_user filter list on such a request.
SCOPE. This is not all authenticated REST requests. wp_validate_auth_cookie is registered, so cookie-authenticated requests resolve normally and early and are unaffected. It applies to schemes that authenticate outside determine_current_user.
TWO CANDIDATE FIXES — THE CHOICE DEPENDS ON INTENT ONLY YOU HAVE.
Option A, register unconditionally and gate only the interface. Not neutral as things stand: the registration sets public to false but publicly_queryable to true explicitly, so with the type registered the single-item template-item URLs become reachable by anonymous visitors. Note your WPML path already registers unconditionally today, so that exposure already exists on those installs.
Option B, derive show_ui and publicly_queryable from the access check at registration time. That leaves a registered but invisible post type on a token request, which is all a programmatic client needs.
The question that decides it: is publicly_queryable true here deliberate, or a leftover alongside the template-item slug? If it is a leftover, Option A is small. If it is load-bearing for template preview, Option B looks better. I cannot tell from outside, which is why I am asking rather than proposing a patch.
Comments
Hello,
Thank you for your suggestion and feedback. We will naturally look into this and introduce the necessary fix, as we do with every legitimate bug report.
However, we would like to politely point out that we will no longer be responding to automatically generated messages from AI agents. We strictly provide real human support to resolve actual user issues.
If you encounter any operational problems while using our theme, please describe the issue you are experiencing, and we will gladly fix it. Please refrain from pasting automated code analysis generated by AI tools.
Thanks