@@ -461,6 +461,147 @@ public function testSrOnlyFormatDoesNotEnqueueOnOtherAdminPages() {
461461 }
462462
463463
464+ /**
465+ * Test that edac_filter_admin_post_id overrides the post ID localized into edac_script_vars.
466+ *
467+ * @return void
468+ */
469+ public function testAdminPostIdFilterOverridesLocalizedPostId () {
470+ global $ post , $ pagenow , $ wp_scripts ;
471+
472+ $ original_post = $ this ->factory ()->post ->create_and_get ();
473+ $ alternate_post = $ this ->factory ()->post ->create_and_get ();
474+ $ post = $ original_post ;
475+ $ pagenow = 'post.php ' ;
476+
477+ $ filter_callback = static function () use ( $ alternate_post ) {
478+ return $ alternate_post ->ID ;
479+ };
480+ add_filter ( 'edac_filter_admin_post_id ' , $ filter_callback );
481+
482+ $ this ->enqueue_admin ::maybe_enqueue_admin_and_editor_app_scripts ();
483+
484+ remove_filter ( 'edac_filter_admin_post_id ' , $ filter_callback );
485+
486+ $ localized_data = $ wp_scripts ->get_data ( 'edac ' , 'data ' );
487+ $ this ->assertStringContainsString ( (string ) $ alternate_post ->ID , $ localized_data );
488+ }
489+
490+ /**
491+ * When the filter flags a latest-posts homepage (show_on_front=posts), the scan URL
492+ * uses get_home_url() rather than an invalid preview link.
493+ *
494+ * @return void
495+ */
496+ public function testScanUrlUsesHomeUrlWhenLatestPostsHomeFilterReturnsTrue () {
497+ global $ post , $ pagenow , $ wp_scripts ;
498+
499+ $ post = $ this ->factory ()->post ->create_and_get ( [ 'post_type ' => 'page ' ] );
500+ $ pagenow = 'post.php ' ;
501+
502+ update_option ( 'show_on_front ' , 'posts ' );
503+ update_option ( 'page_for_posts ' , 0 );
504+
505+ $ filter_callback = static function () {
506+ return true ;
507+ };
508+ add_filter ( 'edac_filter_post_is_latest_posts_home ' , $ filter_callback );
509+
510+ $ this ->enqueue_admin ::maybe_enqueue_admin_and_editor_app_scripts ();
511+
512+ remove_filter ( 'edac_filter_post_is_latest_posts_home ' , $ filter_callback );
513+ delete_option ( 'show_on_front ' );
514+ delete_option ( 'page_for_posts ' );
515+
516+ $ localized_data = $ wp_scripts ->get_data ( 'edac-editor-app ' , 'data ' );
517+ $ this ->assertStringContainsString ( 'edac_pageScanner ' , $ localized_data );
518+ $ this ->assertStringNotContainsString ( 'preview=true ' , $ localized_data );
519+ // The scan URL should be based on the home URL, not a preview link.
520+ // In WP 6.9 forward slashes are no longer escaped in json_encode output; handle both forms.
521+ // See: https://github.com/WordPress/wordpress-develop/pull/9557.
522+ $ expected_home = esc_url_raw ( trailingslashit ( get_home_url () ) );
523+ if ( version_compare ( get_bloginfo ( 'version ' ), '6.9 ' , '< ' ) ) {
524+ $ expected_home = str_replace ( '/ ' , '\\/ ' , $ expected_home );
525+ }
526+ $ this ->assertStringContainsString ( $ expected_home , $ localized_data );
527+ }
528+
529+ /**
530+ * Fallback case: show_on_front=page with no static front page configured also
531+ * counts as a latest-posts homepage, so the scan URL still uses get_home_url().
532+ *
533+ * @return void
534+ */
535+ public function testScanUrlUsesHomeUrlWhenShowOnFrontIsPageWithNoFrontPageConfigured () {
536+ global $ post , $ pagenow , $ wp_scripts ;
537+
538+ $ post = $ this ->factory ()->post ->create_and_get ( [ 'post_type ' => 'page ' ] );
539+ $ pagenow = 'post.php ' ;
540+
541+ update_option ( 'show_on_front ' , 'page ' );
542+ delete_option ( 'page_on_front ' ); // No static front page configured — WP falls back to latest posts.
543+
544+ $ filter_callback = static function () {
545+ return true ;
546+ };
547+ add_filter ( 'edac_filter_post_is_latest_posts_home ' , $ filter_callback );
548+
549+ $ this ->enqueue_admin ::maybe_enqueue_admin_and_editor_app_scripts ();
550+
551+ remove_filter ( 'edac_filter_post_is_latest_posts_home ' , $ filter_callback );
552+ delete_option ( 'show_on_front ' );
553+
554+ $ localized_data = $ wp_scripts ->get_data ( 'edac-editor-app ' , 'data ' );
555+ $ this ->assertStringContainsString ( 'edac_pageScanner ' , $ localized_data );
556+ $ this ->assertStringNotContainsString ( 'preview=true ' , $ localized_data );
557+ // The scan URL should be based on the home URL, not a preview link.
558+ // In WP 6.9 forward slashes are no longer escaped in json_encode output; handle both forms.
559+ // See: https://github.com/WordPress/wordpress-develop/pull/9557.
560+ $ expected_home = esc_url_raw ( trailingslashit ( get_home_url () ) );
561+ if ( version_compare ( get_bloginfo ( 'version ' ), '6.9 ' , '< ' ) ) {
562+ $ expected_home = str_replace ( '/ ' , '\\/ ' , $ expected_home );
563+ }
564+ $ this ->assertStringContainsString ( $ expected_home , $ localized_data );
565+ }
566+
567+ /**
568+ * The 'active' flag must reflect the filtered post ID's type: when the filter returns a
569+ * non-scannable post type, $active is false so the scanner doesn't run.
570+ *
571+ * @return void
572+ */
573+ public function testActiveReflectsFilteredPostIdPostType () {
574+ global $ post , $ pagenow , $ wp_scripts ;
575+
576+ // Global $post is a 'post' type (scannable under current option).
577+ $ scannable_post = $ this ->factory ()->post ->create_and_get ( [ 'post_type ' => 'post ' ] );
578+ // The filter will return a 'page' ID; make 'page' non-scannable for this test.
579+ $ non_scannable_post = $ this ->factory ()->post ->create_and_get ( [ 'post_type ' => 'page ' ] );
580+ $ post = $ scannable_post ;
581+ $ pagenow = 'post.php ' ;
582+
583+ // Restrict scannable types to 'post' only so 'page' becomes non-scannable.
584+ update_option ( 'edac_post_types ' , [ 'post ' ] );
585+
586+ $ filter_callback = static function () use ( $ non_scannable_post ) {
587+ return $ non_scannable_post ->ID ;
588+ };
589+ add_filter ( 'edac_filter_admin_post_id ' , $ filter_callback );
590+
591+ $ this ->enqueue_admin ::maybe_enqueue_admin_and_editor_app_scripts ();
592+
593+ remove_filter ( 'edac_filter_admin_post_id ' , $ filter_callback );
594+ // Restore original scannable post types.
595+ update_option ( 'edac_post_types ' , [ 'post ' , 'page ' ] );
596+
597+ $ localized_data = $ wp_scripts ->get_data ( 'edac-editor-app ' , 'data ' );
598+ $ this ->assertNotEmpty ( $ localized_data );
599+ // $active must be false because the filtered post type ('page') is not scannable.
600+ // wp_localize_script serializes PHP false as "" (empty string) in older WP versions
601+ // and may serialize it as JSON false in newer ones — accept both forms.
602+ $ this ->assertMatchesRegularExpression ( '/"active"\s*:\s*(false|"")/ ' , $ localized_data );
603+ }
604+
464605 /**
465606 * Helper to set a mock current screen with block editor context.
466607 *
0 commit comments