Thanks @christian for keeping your way of precise and detailed explanations as always.
Unfortunately, Option B solution doesn’t work (I didn’t test Option A). I’ve spent a few hours with AI trying to figure out what the issue is and what could be a fix. And it looks like I am ready to provide AI’s report on the subject.
Cornerstone Forms + Native WP Query looper: search field cannot work, and the recommended pre_get_posts workaround fails due to the form’s AJAX re-render
Following up on my ticket about search fields on CPT archives (post types events , documents , built with ACF; archives use Layouts with a Native WP Query looper and a Cornerstone Form for filtering).
Environment: WordPress [7.0.1], Pro [6.8.12], cornerstone-forms.js ver 1.0.10.
Summary of the problem:
- A search text input named
s breaks the CPT archive: WordPress flips to a global search context, losing the post type and the assigned archive layout.
- A search input named
search does not work either — and I can now demonstrate exactly why.
Diagnosis (verified with query-var and SQL logging):
- The Native WP Query looper does consume the main query, and the
pre_get_posts mapping works correctly on a normal page load. Opening the full results URL directly in a new tab — e.g. /events/?search=test&event-level=&cs-form-id=events-filter&event-season=2026&paged=1 — returns correctly filtered and searched results.
- However, when the user actually submits the form ,
cornerstone-forms.js intercepts the submission: it updates the URL via history state and re-renders the looper through an AJAX request instead of a page load. In that AJAX context, standard pre_get_posts snippets (including the hook you provided) never apply, because is_admin() is true for admin-ajax and is_main_query() / is_post_type_archive() / is_home() don’t match. Result: filters work, search is silently ignored — in 100% of real user interactions.
- Reproduction of the contrast: submit the form → search ignored; press browser reload on the identical resulting URL → search works.
Working workaround (PHP snippet update):
add_action( 'pre_get_posts', function ( $query ) {
if ( is_admin() && ! wp_doing_ajax() ) {
return;
}
if ( empty( $_REQUEST['search'] ) ) {
return;
}
$post_types = array_filter( (array) $query->get( 'post_type' ) );
if (
( $query->is_main_query() && $query->is_home() ) || array_intersect( $post_types, array( 'post', 'events', 'documents' ) )
) {
$query->set( 's', sanitize_text_field( wp_unslash( $_REQUEST['search'] ) ) );
}
}, 9999 );
Requests:
- Please treat this as a product gap: Cornerstone Forms currently offers no supported way to connect a search text input to the
s parameter of a Native WP Query looper — naming the field s breaks the archive, naming it anything else means the keyword is never applied, and the AJAX re-render defeats the standard WordPress with the hook you recommend.
- Ideally, add a field option like “map to WP search (
s )” that restricts the search to the looper’s post type without triggering the global search context — handled consistently in both full page loads and the form’s AJAX re-render.
- At minimum, please correct the guidance you provide, since a main-query-only
pre_get_posts snippet cannot work with the form’s AJAX submission path.
P.S. With this snippet version, use of ‘search’ for the Search Field Name inside a blog posts archive is also possible for consistancy. This way all URL parameres will look the same no matter if it’s ACF CPT or native WP blog posts. I hope that will help to improve CF Forms in the following updates.