' . esc_html__( 'Updates', 'mainwp' ) . '', 'read', 'UpdatesManage', array( static::get_class_name(), 'render', ) ); $updates_count = MainWP_Common_Handler::instance()->sites_available_updates_count(); $label_color_plugins = ''; $label_color_themes = ''; $label_color_wp = ''; $label_color_translations = ''; $label_color_total = ''; if ( isset( $updates_count['plugins'] ) && 0 < $updates_count['plugins'] ) { $label_color_plugins = ' blue '; } if ( isset( $updates_count['wp'] ) && 0 < $updates_count['wp'] ) { $label_color_wp = ' blue '; } if ( isset( $updates_count['themes'] ) && 0 < $updates_count['themes'] ) { $label_color_themes = ' blue '; } if ( isset( $updates_count['translations'] ) && 0 < $updates_count['translations'] ) { $label_color_translations = ' blue '; } if ( isset( $updates_count['total'] ) && 0 < $updates_count['total'] ) { $label_color_total = ' blue '; } MainWP_Menu::add_left_menu( array( 'title' => esc_html__( 'Updates', 'mainwp' ) . ' ' . intval( $updates_count['total'] ) . '', 'parent_key' => 'managesites', 'slug' => 'UpdatesManage', 'href' => 'admin.php?page=UpdatesManage', 'icon' => '', 'desc' => 'Manage updates on your child sites', 'leftsub_order' => 4, ), 1 ); $init_sub_subleftmenu = array( array( 'title' => esc_html__( 'Plugins', 'mainwp' ) . ' ' . intval( $updates_count['plugins'] ) . '', 'parent_key' => 'UpdatesManage', 'href' => 'admin.php?page=UpdatesManage&tab=plugins-updates', 'slug' => 'UpdatesManage', 'right' => '', ), array( 'title' => esc_html__( 'Themes', 'mainwp' ) . ' ' . intval( $updates_count['themes'] ) . '', 'parent_key' => 'UpdatesManage', 'href' => 'admin.php?page=UpdatesManage&tab=themes-updates', 'slug' => 'UpdatesManage', 'right' => '', ), array( 'title' => esc_html__( 'WordPress', 'mainwp' ) . ' ' . intval( $updates_count['wp'] ) . '', 'parent_key' => 'UpdatesManage', 'href' => 'admin.php?page=UpdatesManage&tab=wordpress-updates', 'slug' => 'UpdatesManage&tab=wordpress-updates', 'right' => '', 'active_params' => array( 'tab' => 'updates-ignore' ), ), array( 'title' => esc_html__( 'Updates Ignore', 'mainwp' ), 'parent_key' => 'UpdatesManage', 'slug' => 'UpdatesManage&tab=updates-ignore', 'href' => '', // fix warning. 'menu_hidden' => true, ), ); $show_language_updates = get_option( 'mainwp_show_language_updates', 1 ); if ( $show_language_updates ) { $init_sub_subleftmenu[] = array( 'title' => esc_html__( 'Translation', 'mainwp' ) . ' ' . intval( $updates_count['translations'] ) . '', 'parent_key' => 'UpdatesManage', 'href' => 'admin.php?page=UpdatesManage&tab=translations-updates', 'slug' => 'UpdatesManage&tab=translations-updates', 'right' => '', ); } $init_sub_subleftmenu = apply_filters( 'mainwp_sub_leftmenu_updates', $init_sub_subleftmenu ); MainWP_Menu::init_subpages_left_menu( $subPages, $init_sub_subleftmenu, 'UpdatesManage', 'UpdatesManage' ); foreach ( $init_sub_subleftmenu as $item ) { if ( MainWP_Menu::is_disable_menu_item( 3, $item['slug'] ) ) { continue; } MainWP_Menu::add_left_menu( $item, 2 ); } } /** * Method on_load_page() * * Run on page load. */ public static function on_load_page() { add_filter( 'mainwp_header_actions_right', array( static::get_class_name(), 'screen_options' ), 10, 2 ); } /** * Method screen_options() * * Create Page Settings button. * * @param mixed $input Page Settings button HTML. * * @return mixed Page Settings button. */ public static function screen_options( $input ) { return $input . ' '; } /** * Sets the MainWP Update page page title and pass it off to method MainWP_UI::render_top_header(). * * @uses \MainWP\Dashboard\MainWP_UI::render_top_header() */ public static function render_header() { $params = array( 'title' => esc_html__( 'Available Updates', 'mainwp' ), ); MainWP_UI::render_top_header( $params ); } /** * Closes the page container. */ public static function render_footer() { echo ''; } /** * Generates individual site overview page link. * * @param object $website The site object. * @param bool $echo_out Either echo or not. * * @return string Dashboard link. */ public static function render_site_link_dashboard( $website, $echo_out = true ) { $lnk = '' . stripslashes( $website->name ) . ''; if ( $echo_out ) { echo $lnk; // phpcs:ignore WordPress.Security.EscapeOutput } else { return $lnk; } } /** * Checks if the current user has permission to uignore updates. * * @return bool Whether user can ignore updates or not. */ public static function user_can_ignore_updates() { if ( null === static::$user_can_ignore_updates ) { static::$user_can_ignore_updates = \mainwp_current_user_can( 'dashboard', 'ignore_unignore_updates' ); } return static::$user_can_ignore_updates; } /** * Checks if the current user has permission to update translations. * * @return bool Whether user can update translations or not. */ public static function user_can_update_trans() { if ( null === static::$user_can_update_trans ) { static::$user_can_update_trans = \mainwp_current_user_can( 'dashboard', 'update_translations' ); } return static::$user_can_update_trans; } /** * Checks if the current user has permission to update WordPress core files. * * @return bool Whether user can update WordPress or not. */ public static function user_can_update_wp() { if ( null === static::$user_can_update_wp ) { static::$user_can_update_wp = \mainwp_current_user_can( 'dashboard', 'update_wordpress' ); } return static::$user_can_update_wp; } /** * Checks if the current user has permission to update themes. * * @return bool Whether user can update themes or not. */ public static function user_can_update_themes() { if ( null === static::$user_can_update_themes ) { static::$user_can_update_themes = \mainwp_current_user_can( 'dashboard', 'update_themes' ); } return static::$user_can_update_themes; } /** * Checks if the current user has permission to update plugins. * * @return bool Whether user can update plugins or not. */ public static function user_can_update_plugins() { if ( null === static::$user_can_update_plugins ) { static::$user_can_update_plugins = \mainwp_current_user_can( 'dashboard', 'update_plugins' ); } return static::$user_can_update_plugins; } /** * Renders updates page. * * @param string $abandoned_tab Render abandoned plugins|themes tab, abandoned_plugins|abandoned_themes. * * @uses \MainWP\Dashboard\MainWP_DB_Common::get_user_extension() * @uses \MainWP\Dashboard\MainWP_DB_Common::get_groups_for_current_user() * @uses \MainWP\Dashboard\MainWP_DB::get_websites_by_group_id() * @uses \MainWP\Dashboard\MainWP_DB::get_website_option() * @uses \MainWP\Dashboard\MainWP_DB::fetch_object() * @uses \MainWP\Dashboard\MainWP_DB::data_seek() * @uses \MainWP\Dashboard\MainWP_Utility::array_sort() */ public static function render( $abandoned_tab = '' ) { // phpcs:ignore Generic.Metrics.CyclomaticComplexity -- NOSONAR - current complexity is the only way to achieve desired results, pull request solutions appreciated. static::handle_limit_sites(); $websites = static::get_sites_for_current_user(); $userExtension = MainWP_DB_Common::instance()->get_user_extension(); $site_view = (int) $userExtension->site_view; $site_offset_for_groups = array(); $all_groups = array(); $sites_in_groups = array(); $all_groups_sites = array(); if ( MAINWP_VIEW_PER_GROUP === $site_view ) { $groups = MainWP_DB_Common::instance()->get_groups_for_current_user(); foreach ( $groups as $group ) { $all_groups[ $group->id ] = $group->name; } foreach ( $all_groups as $group_id => $group_name ) { $all_groups_sites[ $group_id ] = array(); $group_sites = MainWP_DB::instance()->get_websites_by_group_id( $group_id ); foreach ( $group_sites as $site ) { if ( ! isset( $sites_in_groups[ $site->id ] ) ) { $sites_in_groups[ $site->id ] = 1; } $all_groups_sites[ $group_id ][] = $site->id; } unset( $group_sites ); } $sites_not_in_groups = array(); $pos = 0; MainWP_DB::data_seek( $websites, 0 ); while ( $websites && ( $website = MainWP_DB::fetch_object( $websites ) ) ) { $site_offset_for_groups[ $website->id ] = $pos; ++$pos; if ( ! isset( $sites_in_groups[ $website->id ] ) ) { $sites_not_in_groups[] = $website->id; } } if ( ! empty( $sites_not_in_groups ) ) { $all_groups_sites[0] = $sites_not_in_groups; $all_groups[0] = esc_html__( 'Others', 'mainwp' ); } } $decodedDismissedPlugins = ! empty( $userExtension->dismissed_plugins ) ? json_decode( $userExtension->dismissed_plugins, true ) : array(); $decodedDismissedThemes = ! empty( $userExtension->dismissed_themes ) ? json_decode( $userExtension->dismissed_themes, true ) : array(); $decodedDismissedCores = ! empty( $userExtension->ignored_wp_upgrades ) ? json_decode( $userExtension->ignored_wp_upgrades, true ) : array(); $total_wp_upgrades = 0; $total_plugin_upgrades = 0; $total_translation_upgrades = 0; $total_theme_upgrades = 0; $total_sync_errors = 0; $total_plugins_outdate = 0; $total_themes_outdate = 0; $allTranslations = array(); $translationsInfo = array(); $allPlugins = array(); $pluginsInfo = array(); $allThemes = array(); $themesInfo = array(); $allPluginsOutdate = array(); $allThemesOutdate = array(); MainWP_DB::data_seek( $websites, 0 ); while ( $websites && ( $website = MainWP_DB::fetch_object( $websites ) ) ) { $wp_upgrades = ! empty( $website->wp_upgrades ) ? json_decode( $website->wp_upgrades, true ) : array(); $ignored_core_upgrades = ! empty( $website->ignored_wp_upgrades ) ? json_decode( $website->ignored_wp_upgrades, true ) : array(); if ( $website->is_ignoreCoreUpdates || MainWP_Common_Functions::instance()->is_ignored_updates( $wp_upgrades, $ignored_core_upgrades, 'core' ) || MainWP_Common_Functions::instance()->is_ignored_updates( $wp_upgrades, $decodedDismissedCores, 'core' ) ) { $wp_upgrades = array(); } if ( is_array( $wp_upgrades ) && ! empty( $wp_upgrades ) ) { ++$total_wp_upgrades; } $translation_upgrades = json_decode( $website->translation_upgrades, true ); $plugin_upgrades = json_decode( $website->plugin_upgrades, true ); if ( $website->is_ignorePluginUpdates ) { $plugin_upgrades = array(); } $theme_upgrades = json_decode( $website->theme_upgrades, true ); if ( $website->is_ignoreThemeUpdates ) { $theme_upgrades = array(); } $decodedPremiumUpgrades = MainWP_DB::instance()->get_website_option( $website, 'premium_upgrades' ); $decodedPremiumUpgrades = ! empty( $decodedPremiumUpgrades ) ? json_decode( $decodedPremiumUpgrades, true ) : array(); if ( is_array( $decodedPremiumUpgrades ) ) { foreach ( $decodedPremiumUpgrades as $crrSlug => $premiumUpgrade ) { $premiumUpgrade['premium'] = true; if ( 'plugin' === $premiumUpgrade['type'] ) { if ( ! is_array( $plugin_upgrades ) ) { $plugin_upgrades = array(); } if ( ! $website->is_ignorePluginUpdates ) { $premiumUpgrade = array_filter( $premiumUpgrade ); if ( ! isset( $plugin_upgrades[ $crrSlug ] ) ) { continue; // to fix missing update name. } $plugin_upgrades[ $crrSlug ] = array_merge( $plugin_upgrades[ $crrSlug ], $premiumUpgrade ); } } elseif ( 'theme' === $premiumUpgrade['type'] ) { if ( ! is_array( $theme_upgrades ) ) { $theme_upgrades = array(); } if ( ! $website->is_ignoreThemeUpdates ) { $theme_upgrades[ $crrSlug ] = $premiumUpgrade; } } } } if ( is_array( $translation_upgrades ) ) { $total_translation_upgrades += count( $translation_upgrades ); } if ( is_array( $plugin_upgrades ) && ! $website->is_ignorePluginUpdates ) { $_ignored_plugins = json_decode( $website->ignored_plugins, true ); if ( is_array( $_ignored_plugins ) ) { $plugin_upgrades = MainWP_Common_Functions::instance()->get_not_ignored_updates_themesplugins( $plugin_upgrades, $_ignored_plugins ); } $_ignored_plugins = json_decode( $userExtension->ignored_plugins, true ); if ( is_array( $_ignored_plugins ) ) { $plugin_upgrades = MainWP_Common_Functions::instance()->get_not_ignored_updates_themesplugins( $plugin_upgrades, $_ignored_plugins ); } $total_plugin_upgrades += count( $plugin_upgrades ); } if ( is_array( $theme_upgrades ) ) { $_ignored_themes = json_decode( $website->ignored_themes, true ); if ( is_array( $_ignored_themes ) ) { $theme_upgrades = MainWP_Common_Functions::instance()->get_not_ignored_updates_themesplugins( $theme_upgrades, $_ignored_themes ); } $_ignored_themes = json_decode( $userExtension->ignored_themes, true ); if ( is_array( $_ignored_themes ) ) { $theme_upgrades = MainWP_Common_Functions::instance()->get_not_ignored_updates_themesplugins( $theme_upgrades, $_ignored_themes ); } $total_theme_upgrades += count( $theme_upgrades ); } $themesIgnoredAbandoned_perSites = array(); $ignoredAbandoned_themes = MainWP_DB::instance()->get_website_option( $website, 'themes_outdate_dismissed' ); $ignoredAbandoned_themes = ! empty( $ignoredAbandoned_themes ) ? json_decode( $ignoredAbandoned_themes, true ) : array(); if ( is_array( $ignoredAbandoned_themes ) ) { $ignoredAbandoned_themes = array_filter( $ignoredAbandoned_themes ); $themesIgnoredAbandoned_perSites = array_merge( $themesIgnoredAbandoned_perSites, $ignoredAbandoned_themes ); } $ignoredAbandoned_plugins = MainWP_DB::instance()->get_website_option( $website, 'plugins_outdate_dismissed' ); $ignoredAbandoned_plugins = ! empty( $ignoredAbandoned_plugins ) ? json_decode( $ignoredAbandoned_plugins, true ) : array(); $plugins_outdate = MainWP_DB::instance()->get_website_option( $website, 'plugins_outdate_info' ); $plugins_outdate = ! empty( $plugins_outdate ) ? json_decode( $plugins_outdate, true ) : array(); $themes_outdate = MainWP_DB::instance()->get_website_option( $website, 'themes_outdate_info' ); $themes_outdate = ! empty( $themes_outdate ) ? json_decode( $themes_outdate, true ) : array(); if ( is_array( $plugins_outdate ) ) { if ( is_array( $ignoredAbandoned_plugins ) ) { $plugins_outdate = array_diff_key( $plugins_outdate, $ignoredAbandoned_plugins ); } if ( is_array( $decodedDismissedPlugins ) ) { $plugins_outdate = array_diff_key( $plugins_outdate, $decodedDismissedPlugins ); } $total_plugins_outdate += count( $plugins_outdate ); } if ( is_array( $themes_outdate ) ) { if ( is_array( $themesIgnoredAbandoned_perSites ) ) { $themes_outdate = array_diff_key( $themes_outdate, $themesIgnoredAbandoned_perSites ); } if ( is_array( $decodedDismissedThemes ) ) { $themes_outdate = array_diff_key( $themes_outdate, $decodedDismissedThemes ); } $total_themes_outdate += count( $themes_outdate ); } // to fix displaying per sites/tags. if ( is_array( $plugins_outdate ) ) { foreach ( $plugins_outdate as $slug => $plugin_outdate ) { $slug = esc_html( $slug ); if ( ! isset( $allPluginsOutdate[ $slug ] ) ) { $allPluginsOutdate[ $slug ] = array( 'name' => esc_html( $plugin_outdate['Name'] ), 'cnt' => 1, 'uri' => esc_html( $plugin_outdate['PluginURI'] ), ); } else { ++$allPluginsOutdate[ $slug ]['cnt']; } } } if ( is_array( $themes_outdate ) ) { foreach ( $themes_outdate as $slug => $theme_outdate ) { $slug = esc_html( $slug ); if ( ! isset( $allThemesOutdate[ $slug ] ) ) { $allThemesOutdate[ $slug ] = array( 'name' => esc_html( $theme_outdate['Name'] ), 'cnt' => 1, ); } else { ++$allThemesOutdate[ $slug ]['cnt']; } } } if ( MAINWP_VIEW_PER_PLUGIN_THEME === $site_view ) { if ( is_array( $translation_upgrades ) ) { foreach ( $translation_upgrades as $translation_upgrade ) { $slug = esc_html( $translation_upgrade['slug'] ); if ( ! isset( $allTranslations[ $slug ] ) ) { $allTranslations[ $slug ] = array( 'name' => isset( $translation_upgrade['name'] ) ? esc_html( $translation_upgrade['name'] ) : $slug, 'cnt' => 1, ); } else { ++$allTranslations[ $slug ]['cnt']; } $translationsInfo[ $slug ] = array( 'name' => isset( $translation_upgrade['name'] ) ? esc_html( $translation_upgrade['name'] ) : $slug, 'slug' => $slug, 'version' => esc_html( $translation_upgrade['version'] ), ); } } if ( is_array( $plugin_upgrades ) ) { foreach ( $plugin_upgrades as $slug => $plugin_upgrade ) { if ( ! isset( $allPlugins[ $slug ] ) ) { $allPlugins[ $slug ] = array( 'name' => esc_html( $plugin_upgrade['Name'] ), 'cnt' => 1, ); } else { ++$allPlugins[ $slug ]['cnt']; } $pluginsInfo[ $slug ] = array( 'name' => esc_html( $plugin_upgrade['Name'] ), 'slug' => isset( $plugin_upgrade['update']['slug'] ) ? esc_html( $plugin_upgrade['update']['slug'] ) : '', 'premium' => ( isset( $plugin_upgrade['premium'] ) ? esc_html( $plugin_upgrade['premium'] ) : 0 ), 'PluginURI' => esc_html( $plugin_upgrade['PluginURI'] ), 'version' => esc_html( $plugin_upgrade['Version'] ), ); } } if ( is_array( $theme_upgrades ) ) { foreach ( $theme_upgrades as $slug => $theme_upgrade ) { if ( ! isset( $allThemes[ $slug ] ) ) { $allThemes[ $slug ] = array( 'name' => esc_html( $theme_upgrade['Name'] ), 'cnt' => 1, ); } else { ++$allThemes[ $slug ]['cnt']; } $up_th_name = isset( $theme_upgrade['Name'] ) ? esc_html( $theme_upgrade['Name'] ) : ''; if ( empty( $up_th_name ) ) { $up_th_name = isset( $theme_upgrade['name'] ) ? esc_html( $theme_upgrade['name'] ) : 'N/A'; } $themesInfo[ $slug ] = array( 'name' => $up_th_name, 'premium' => ( isset( $theme_upgrade['premium'] ) ? esc_html( $theme_upgrade['premium'] ) : 0 ), ); } } } if ( '' !== $website->sync_errors ) { ++$total_sync_errors; } } /** * Filter: mainwp_updates_translation_sort_by * * Filters the default sorting option for Translation updates. * * @since 4.1 */ $allTranslationsSortBy = apply_filters( 'mainwp_updates_translation_sort_by', 'name' ); /** * Filter: mainwp_updates_plugins_sort_by * * Filters the default sorting option for Plugin updates. * * @since 4.1 */ $allPluginsSortBy = apply_filters( 'mainwp_updates_plugins_sort_by', 'name' ); /** * Filter: mainwp_updates_themes_sort_by * * Filters the default sorting option for Theme updates. * * @since 4.1 */ $allThemesSortBy = apply_filters( 'mainwp_updates_themes_sort_by', 'name' ); /** * Filter: mainwp_updates_abandoned_plugins_sort_by * * Filters the default sorting option for Abandoned plugins. * * @since 4.1 */ $allPluginsOutdateSortBy = apply_filters( 'mainwp_updates_abandoned_plugins_sort_by', 'name' ); /** * Filter: mainwp_updates_abandoned_themes_sort_by * * Filters the default sorting option for Abandoned themes. * * @since 4.1 */ $allThemesOutdateSortBy = apply_filters( 'mainwp_updates_abandoned_themes_sort_by', 'name' ); MainWP_Utility::array_sort( $allTranslations, $allTranslationsSortBy ); MainWP_Utility::array_sort( $allPlugins, $allPluginsSortBy ); MainWP_Utility::array_sort( $allThemes, $allThemesSortBy ); MainWP_Utility::array_sort( $allPluginsOutdate, $allPluginsOutdateSortBy ); MainWP_Utility::array_sort( $allThemesOutdate, $allThemesOutdateSortBy ); $mainwp_show_language_updates = get_option( 'mainwp_show_language_updates', 1 ); /** * Limits number of updates to process. * * Limits the number of updates that will be processed in a single run on Update Everything action. * * @since 4.0 */ $limit_updates_all = apply_filters( 'mainwp_limit_updates_all', 0 ); // phpcs:disable WordPress.Security.NonceVerification,WordPress.Security.ValidatedSanitizedInput.InputNotSanitized if ( 0 < $limit_updates_all && isset( $_GET['continue_update'] ) && '' !== $_GET['continue_update'] ) { static::$continue_update = sanitize_text_field( wp_unslash( $_GET['continue_update'] ) ); if ( ( 'plugins_upgrade_all' === static::$continue_update || 'themes_upgrade_all' === static::$continue_update || 'translations_upgrade_all' === static::$continue_update ) && isset( $_GET['slug'] ) && '' !== $_GET['slug'] ) { static::$continue_update_slug = wp_unslash( $_GET['slug'] ); } } $current_tab = ''; if ( isset( $_GET['tab'] ) ) { $current_tab = sanitize_text_field( wp_unslash( $_GET['tab'] ) ); if ( ! in_array( $current_tab, array( 'wordpress-updates', 'updates-ignore', 'plugins-updates', 'themes-updates', 'translations-updates', true ) ) ) { $current_tab = 'plugins-updates'; } } elseif ( 'abandoned_plugins' === $abandoned_tab ) { $current_tab = 'abandoned-plugins'; } elseif ( 'abandoned_themes' === $abandoned_tab ) { $current_tab = 'abandoned-themes'; } if ( empty( $current_tab ) ) { $current_tab = 'plugins-updates'; } // phpcs:enable static::render_header( 'UpdatesManage' ); static::render_header_tabs( $mainwp_show_language_updates, $current_tab, $total_wp_upgrades, $total_plugin_upgrades, $total_theme_upgrades, $total_translation_upgrades, $total_plugins_outdate, $total_themes_outdate, $site_view ); ?>