Some additional info, after further research with Query Monitor. The issue appears to come down to this query:
SELECT t.*, tt.*
FROM cpdm_terms AS t
INNER JOIN cpdm_term_taxonomy AS tt
ON t.term_id = tt.term_id
WHERE tt.taxonomy IN ('category')
AND t.term_id IN ( 185,186,187,188,189,190,191,192,193,194,195,196,197,198,199,200,201,806,9008 )
Of those category IDs, only 185-193 are actually children of 9008, the rest are other categories (none of which are related to 9008 in any way). This is, however, the correct quantity of child categories. In reality, 177-193 and 801 are the children of 9008. So, somehow, it’s choosing to pull the wrong categories in…
“a post is showing up on the category archive page”
“However, if I view the category via API (/wp-json/wp/v2/rulings?categories=9008), everything looks fine ”
You mentioned plugins, but not themes. Have you switched to default theme, as at first glance I would guess a theme / archive template issue
Just tried it in vanilla Twenty Twenty-One, same basic issue:
SELECT SQL_CALC_FOUND_ROWS cpdm_posts.ID
FROM cpdm_posts
LEFT JOIN cpdm_term_relationships
ON (cpdm_posts.ID = cpdm_term_relationships.object_id)
WHERE 1=1
AND ( cpdm_term_relationships.term_taxonomy_id IN (185,186,187,188,189,190,191,192,193,194,195,196,197,198,199,200,201,806,9008) )
AND cpdm_posts.post_type = 'post'
AND (cpdm_posts.post_status = 'publish'
OR cpdm_posts.post_status = 'private')
GROUP BY cpdm_posts.ID
ORDER BY cpdm_posts.post_date DESC
LIMIT 0, 10
Okay, so, if I change to a custom taxonomy instead of the built in “categories”, it shows fine, and the only ID that shows in the SQL query is the parent ID. So there’s some issue with the “category” taxonomy…