count_open(); /* translators: %d: number of open incidents */ $badge = $open > 0 ? ' ' . (int) $open . '' : ''; // One shared callable for the top-level page and its mirror submenu — // two distinct instances would register two render callbacks on the // same page hook and paint the dashboard twice. $dashboard = array( new DashboardPage(), 'render' ); add_menu_page( __( 'Aftercare', 'aftercare' ), __( 'Aftercare', 'aftercare' ) . $badge, self::CAP, 'aftercare', $dashboard, 'dashicons-chart-line', 58 ); add_submenu_page( 'aftercare', __( 'Dashboard', 'aftercare' ), __( 'Dashboard', 'aftercare' ), self::CAP, 'aftercare', $dashboard ); add_submenu_page( 'aftercare', __( 'Change Ledger', 'aftercare' ), __( 'Ledger', 'aftercare' ), self::CAP, 'aftercare-ledger', array( new LedgerPage(), 'render' ) ); add_submenu_page( 'aftercare', __( 'Incidents', 'aftercare' ), __( 'Incidents', 'aftercare' ) . $badge, self::CAP, 'aftercare-incidents', array( new IncidentsPage(), 'render' ) ); add_submenu_page( 'aftercare', __( 'PHP Errors', 'aftercare' ), __( 'PHP Errors', 'aftercare' ), self::CAP, 'aftercare-errors', array( new ErrorsPage(), 'render' ) ); if ( class_exists( ReportBuilder::class ) ) { add_submenu_page( 'aftercare', __( 'Client Reports', 'aftercare' ), __( 'Reports', 'aftercare' ), self::CAP, 'aftercare-reports', array( new ReportsPage(), 'render' ) ); } add_submenu_page( 'aftercare', __( 'Aftercare Settings', 'aftercare' ), __( 'Settings', 'aftercare' ), self::CAP, 'aftercare-settings', array( new SettingsPage(), 'render' ) ); } public function enqueue_assets( string $hook ): void { if ( ! str_contains( $hook, 'aftercare' ) ) { return; } wp_enqueue_style( 'aftercare-admin', AFTERCARE_URL . 'assets/css/admin.css', array(), AFTERCARE_VERSION ); wp_enqueue_script( 'aftercare-admin', AFTERCARE_URL . 'assets/js/admin.js', array(), AFTERCARE_VERSION, true ); } /** * Debug/QA helper: run the daily pipeline immediately. */ public function handle_run_now(): void { if ( ! current_user_can( self::CAP ) ) { wp_die( esc_html__( 'You do not have permission to do that.', 'aftercare' ) ); } check_admin_referer( 'aftercare_run_now' ); ( new \Aftercare\Core\Cron() )->run_daily(); wp_safe_redirect( add_query_arg( 'aftercare_ran', '1', admin_url( 'admin.php?page=aftercare' ) ) ); exit; } /** * Shared page chrome. */ public static function header( string $title ): void { echo '

' . esc_html( $title ) . '

'; } public static function footer(): void { echo '
'; } }