diff --git a/includes/Admin/Admin_Page.php b/includes/Admin/Admin_Page.php index 5dd4881e8..7517e0a9e 100644 --- a/includes/Admin/Admin_Page.php +++ b/includes/Admin/Admin_Page.php @@ -56,7 +56,9 @@ public function __construct( Admin_AJAX $admin_ajax ) { */ public function add_hooks() { add_action( 'admin_menu', array( $this, 'add_and_initialize_page' ) ); + add_action( 'network_admin_menu', array( $this, 'add_and_initialize_network_page' ) ); add_filter( 'plugin_action_links', array( $this, 'filter_plugin_action_links' ), 10, 4 ); + add_filter( 'network_admin_plugin_action_links', array( $this, 'filter_network_admin_plugin_action_links' ), 10, 4 ); add_action( 'admin_enqueue_scripts', array( $this, 'add_jump_to_line_code_editor' ) ); $this->admin_ajax->add_hooks(); @@ -87,6 +89,35 @@ public function add_and_initialize_page() { add_action( 'load-' . $this->get_hook_suffix(), array( $this, 'initialize_page' ) ); } + /** + * Adds the admin page under the network "Settings" menu. + * + * The "Tools" menu does not exist in the Network Admin, so the screen is + * added under "Settings" (settings.php) instead. + * + * @since 2.1.0 + */ + public function add_network_page() { + $this->hook_suffix = add_submenu_page( + 'settings.php', + __( 'Plugin Check', 'plugin-check' ), + __( 'Plugin Check', 'plugin-check' ), + 'manage_network_plugins', + 'plugin-check', + array( $this, 'render_page' ) + ); + } + + /** + * Adds and initializes the admin page under the network "Settings" menu. + * + * @since 2.1.0 + */ + public function add_and_initialize_network_page() { + $this->add_network_page(); + add_action( 'load-' . $this->get_hook_suffix(), array( $this, 'initialize_page' ) ); + } + /** * Initializes page hooks. * @@ -336,6 +367,39 @@ static function ( Check $check ) { * @return array The modified list of actions. */ public function filter_plugin_action_links( $actions, $plugin_file, $plugin_data, $context ) { + return $this->add_check_action_link( $actions, $plugin_file, $context, admin_url( 'tools.php?page=plugin-check' ) ); + } + + /** + * Adds "check this plugin" link in the Network Admin plugins list table. + * + * In the Network Admin the page lives under "Settings" (settings.php), so + * the link URL differs from the regular WP Admin. + * + * @since 2.1.0 + * + * @param array $actions List of actions. + * @param string $plugin_file Plugin main file. + * @param array $plugin_data An array of plugin data. + * @param string $context The plugin context. + * @return array The modified list of actions. + */ + public function filter_network_admin_plugin_action_links( $actions, $plugin_file, $plugin_data, $context ) { + return $this->add_check_action_link( $actions, $plugin_file, $context, network_admin_url( 'settings.php?page=plugin-check' ) ); + } + + /** + * Adds the "check this plugin" action link using the given page URL. + * + * @since 2.1.0 + * + * @param array $actions List of actions. + * @param string $plugin_file Plugin main file. + * @param string $context The plugin context. + * @param string $page_url The Plugin Check page URL to link to. + * @return array The modified list of actions. + */ + private function add_check_action_link( $actions, $plugin_file, $context, $page_url ) { if ( in_array( $context, array( 'mustuse', 'dropins' ), true ) ) { return $actions; @@ -345,7 +409,7 @@ public function filter_plugin_action_links( $actions, $plugin_file, $plugin_data if ( $plugin_check_base_name === $plugin_file ) { $actions[] = sprintf( '%2$s', - esc_url( admin_url( 'tools.php?page=plugin-check' ) ), + esc_url( $page_url ), esc_html__( 'Check a plugin', 'plugin-check' ) ); return $actions; @@ -354,7 +418,7 @@ public function filter_plugin_action_links( $actions, $plugin_file, $plugin_data if ( current_user_can( 'activate_plugins' ) ) { $actions[] = sprintf( '%2$s', - esc_url( admin_url( "tools.php?page=plugin-check&plugin={$plugin_file}" ) ), + esc_url( $page_url . "&plugin={$plugin_file}" ), esc_html__( 'Check this plugin', 'plugin-check' ) ); } diff --git a/tests/phpunit/tests/Admin/Admin_Page_Tests.php b/tests/phpunit/tests/Admin/Admin_Page_Tests.php index 68feffcfd..496861a5b 100644 --- a/tests/phpunit/tests/Admin/Admin_Page_Tests.php +++ b/tests/phpunit/tests/Admin/Admin_Page_Tests.php @@ -25,7 +25,39 @@ public function set_up() { public function test_add_hooks() { $this->admin_page->add_hooks(); $this->assertEquals( 10, has_action( 'admin_menu', array( $this->admin_page, 'add_and_initialize_page' ) ) ); + $this->assertEquals( 10, has_action( 'network_admin_menu', array( $this->admin_page, 'add_and_initialize_network_page' ) ) ); $this->assertEquals( 10, has_filter( 'plugin_action_links', array( $this->admin_page, 'filter_plugin_action_links' ) ) ); + $this->assertEquals( 10, has_filter( 'network_admin_plugin_action_links', array( $this->admin_page, 'filter_network_admin_plugin_action_links' ) ) ); + } + + public function test_add_and_initialize_network_page() { + + if ( ! is_multisite() ) { + $this->markTestSkipped( 'The Network Admin is only available on multisite.' ); + } + + global $_parent_pages; + + $current_screen = get_current_screen(); + + $admin_user = self::factory()->user->create( array( 'role' => 'administrator' ) ); + grant_super_admin( $admin_user ); + wp_set_current_user( $admin_user ); + + set_current_screen( 'dashboard-network' ); + + $this->admin_page->add_and_initialize_network_page(); + $page_hook = $this->admin_page->get_hook_suffix(); + $parent_pages = $_parent_pages; + + set_current_screen( $current_screen ); + + $this->assertNotEmpty( $page_hook ); + + // In the Network Admin the page lives under "Settings" (settings.php). + $this->assertArrayHasKey( 'plugin-check', $parent_pages ); + $this->assertEquals( 'settings.php', $parent_pages['plugin-check'] ); + $this->assertNotFalse( has_action( "load-{$page_hook}", array( $this->admin_page, 'initialize_page' ) ) ); } public function test_add_and_initialize_page() { @@ -156,6 +188,33 @@ public function test_filter_plugin_action_links() { ); } + public function test_filter_network_admin_plugin_action_links() { + + $base_file = 'akismet/akismet.php'; + + $action_links = $this->admin_page->filter_network_admin_plugin_action_links( array(), $base_file, array(), 'all' ); + $this->assertEmpty( $action_links ); + + /** Administrator check */ + $admin_user = self::factory()->user->create( array( 'role' => 'administrator' ) ); + + if ( is_multisite() ) { + grant_super_admin( $admin_user ); + } + wp_set_current_user( $admin_user ); + $action_links = $this->admin_page->filter_network_admin_plugin_action_links( array(), $base_file, array(), 'all' ); + + // In the Network Admin the link points to settings.php instead of tools.php. + $this->assertEquals( + sprintf( + '%2$s', + esc_url( network_admin_url( "settings.php?page=plugin-check&plugin={$base_file}" ) ), + esc_html__( 'Check this plugin', 'plugin-check' ) + ), + $action_links[0] + ); + } + public function test_filter_plugin_action_links_for_plugin_checker_check_link() { $base_file = 'plugin-check/plugin.php';