.js` + `.asset.php`. * * @since 1.0.0 */ const SCREENS = array( // Parent plugin's Settings page. The bundle injects our import // panel into the Tools tab. The hook suffix follows the // parent's menu structure — Settings lives under the Redirects // top-level menu since 4.0. 'redirects_page_404-to-301-settings' => 'redirects-importer', ); /** * Singleton instance. * * @since 1.0.0 * @var self|null */ private static $instance = null; /** * Retrieve the shared instance. * * @since 1.0.0 * * @return self */ public static function instance(): self { if ( null === self::$instance ) { self::$instance = new self(); } return self::$instance; } /** * Register the WordPress hooks owned by this class. * * @since 1.0.0 * * @return void */ public function register(): void { // Priority 20 keeps us strictly after the parent's enqueue, so // `addFilter` callbacks land before the parent's React tree // renders for the first time. add_action( 'admin_enqueue_scripts', array( $this, 'enqueue' ), 20 ); } /** * Enqueue the matching bundle for the current admin screen. * * @since 1.0.0 * * @param string $hook Current admin screen hook. * * @return void */ public function enqueue( string $hook ): void { if ( ! isset( self::SCREENS[ $hook ] ) ) { return; } $entry = self::SCREENS[ $hook ]; $asset_file = D404_REDIRECTS_IMPORTER_DIR . 'build/' . $entry . '.asset.php'; // Build output is generated by `npm run build`; bail quietly on // fresh checkouts that haven't been built yet so the admin // doesn't fatal. if ( ! file_exists( $asset_file ) ) { return; } $asset = require $asset_file; $handle = 'd404-' . $entry; wp_enqueue_script( $handle, D404_REDIRECTS_IMPORTER_URL . 'build/' . $entry . '.js', $asset['dependencies'] ?? array(), $asset['version'] ?? D404_REDIRECTS_IMPORTER_VERSION, true ); // `wp-scripts` extracts imported SCSS into `.css`. // Enqueue it only when the file exists so a JS-only build // (or a future refactor that drops the styles) doesn't 404. $css_file = D404_REDIRECTS_IMPORTER_DIR . 'build/' . $entry . '.css'; if ( file_exists( $css_file ) ) { wp_enqueue_style( $handle, D404_REDIRECTS_IMPORTER_URL . 'build/' . $entry . '.css', array(), $asset['version'] ?? D404_REDIRECTS_IMPORTER_VERSION ); } wp_set_script_translations( $handle, '404-to-301-redirects-importer' ); } }