as3cf = $as3cf; $this->plugin_file_path = $plugin_file_path; add_action( 'admin_notices', array( $this, 'admin_notices' ) ); add_action( 'network_admin_notices', array( $this, 'admin_notices' ) ); add_action( 'admin_enqueue_scripts', array( $this, 'enqueue_notice_scripts' ) ); add_action( 'wp_ajax_as3cf-dismiss-notice', array( $this, 'ajax_dismiss_notice' ) ); } /** * As this class is a singelton it should not be clone-able */ protected function __clone() { // Singleton } /** * Create a notice * * @param string $message * @param array $args * * @return string notice ID */ public function add_notice( $message, $args = array() ) { $defaults = array( 'type' => 'info', 'dismissible' => true, 'inline' => false, 'flash' => true, 'only_show_to_user' => true, // The user who has initiated an action resulting in notice. Otherwise show to all users. 'only_show_in_settings' => false, 'custom_id' => '', 'auto_p' => true, // Automatically wrap the message in a

'class' => '', // Extra classes for the notice ); $notice = array_intersect_key( array_merge( $defaults, $args ), $defaults ); $notice['message'] = $message; $notice['triggered_by'] = get_current_user_id(); $notice['created_at'] = time(); if ( $notice['custom_id'] ) { $notice['id'] = $notice['custom_id']; } else { $notice['id'] = apply_filters( 'as3cf_notice_id_prefix', 'as3cf-notice-' ) . sha1( $notice['message'] ); } $this->save_notice( $notice ); return $notice['id']; } /** * Save a notice * * @param array $notice */ protected function save_notice( $notice ) { $user_id = get_current_user_id(); if ( $notice['only_show_to_user'] ) { $notices = get_user_meta( $user_id, 'as3cf_notices', true ); } else { $notices = get_site_transient( 'as3cf_notices' ); } if ( ! is_array( $notices ) ) { $notices = array(); } if ( ! array_key_exists( $notice['id'], $notices ) ) { $notices[ $notice['id'] ] = $notice; if ( $notice['only_show_to_user'] ) { update_user_meta( $user_id, 'as3cf_notices', $notices ); } else { set_site_transient( 'as3cf_notices', $notices ); } } } /** * Remove a notice * * @param array $notice */ public function remove_notice( $notice ) { $user_id = get_current_user_id(); if ( $notice['only_show_to_user'] ) { $notices = get_user_meta( $user_id, 'as3cf_notices', true ); } else { $notices = get_site_transient( 'as3cf_notices' ); } if ( ! is_array( $notices ) ) { $notices = array(); } if ( array_key_exists( $notice['id'], $notices ) ) { unset( $notices[ $notice['id'] ] ); if ( $notice['only_show_to_user'] ) { $this->update_user_meta( $user_id, 'as3cf_notices', $notices ); } else { $this->set_site_transient( 'as3cf_notices', $notices ); } } } /** * Remove a notice by it's ID * * @param string $notice_id */ public function remove_notice_by_id( $notice_id ) { $notice = $this->find_notice_by_id( $notice_id ); if ( $notice ) { $this->remove_notice( $notice ); } } /** * Dismiss a notice * * @param string $notice_id */ protected function dismiss_notice( $notice_id ) { $user_id = get_current_user_id(); $notice = $this->find_notice_by_id( $notice_id ); if ( $notice ) { if ( $notice['only_show_to_user'] ) { $notices = get_user_meta( $user_id, 'as3cf_notices' ); unset( $notices[ $notice['id'] ] ); $this->update_user_meta( $user_id, 'as3cf_notices', $notices ); } else { $dismissed_notices = $this->get_dismissed_notices( $user_id ); if ( ! in_array( $notice['id'], $dismissed_notices ) ) { $dismissed_notices[] = $notice['id']; update_user_meta( $user_id, 'as3cf_dismissed_notices', $dismissed_notices ); } } } } /** * Check if a notice has been dismissed for the current user * * @param null|int $user_id * * @return array */ public function get_dismissed_notices( $user_id = null ) { if ( is_null( $user_id ) ) { $user_id = get_current_user_id(); } $dismissed_notices = get_user_meta( $user_id, 'as3cf_dismissed_notices', true ); if ( ! is_array( $dismissed_notices ) ) { $dismissed_notices = array(); } return $dismissed_notices; } /** * Un-dismiss a notice for a user * * @param string $notice_id * @param null|int $user_id * @param null|array $dismissed_notices */ public function undismiss_notice_for_user( $notice_id, $user_id = null, $dismissed_notices = null ) { if ( is_null( $user_id ) ) { $user_id = get_current_user_id(); } if ( is_null( $dismissed_notices ) ) { $dismissed_notices = $this->get_dismissed_notices( $user_id ); } $key = array_search( $notice_id, $dismissed_notices ); unset( $dismissed_notices[ $key ] ); $this->update_user_meta( $user_id, 'as3cf_dismissed_notices', $dismissed_notices ); } /** * Un-dismiss a notice for all users that have dismissed it * * @param string $notice_id */ public function undismiss_notice_for_all( $notice_id ) { $args = array( 'meta_key' => 'as3cf_dismissed_notices', 'meta_value' => $notice_id, 'meta_compare' => 'LIKE', ); $users = get_users( $args ); foreach( $users as $user ) { $this->undismiss_notice_for_user( $notice_id, $user->ID ); } } /** * Find a notice by it's ID * * @param string $notice_id * * @return array|null */ public function find_notice_by_id( $notice_id ) { $user_id = get_current_user_id(); $user_notices = get_user_meta( $user_id, 'as3cf_notices', true ); if ( ! is_array( $user_notices ) ) { $user_notices = array(); } $global_notices = get_site_transient( 'as3cf_notices' ); if ( ! is_array( $global_notices ) ) { $global_notices = array(); } $notices = array_merge( $user_notices, $global_notices ); if ( array_key_exists( $notice_id, $notices ) ) { return $notices[ $notice_id ]; } return null; } /** * Show the notices */ public function admin_notices() { $user_id = get_current_user_id(); $dismissed_notices = get_user_meta( $user_id, 'as3cf_dismissed_notices', true ); if ( ! is_array( $dismissed_notices ) ) { $dismissed_notices = array(); } $user_notices = get_user_meta( $user_id, 'as3cf_notices', true ); if ( is_array( $user_notices ) && ! empty( $user_notices ) ) { foreach ( $user_notices as $notice ) { $this->maybe_show_notice( $notice, $dismissed_notices ); } } $global_notices = get_site_transient( 'as3cf_notices' ); if ( is_array( $global_notices ) && ! empty( $global_notices ) ) { foreach ( $global_notices as $notice ) { $this->maybe_show_notice( $notice, $dismissed_notices ); } } } /** * If it should be shown, display an individual notice * * @param array $notice */ protected function maybe_show_notice( $notice, $dismissed_notices ) { $screen = get_current_screen(); if ( $notice['only_show_in_settings'] && false === strpos( $screen->id, $this->as3cf->hook_suffix ) ) { return; } if ( ! $notice['only_show_to_user'] && in_array( $notice['id'], $dismissed_notices ) ) { return; } if ( 'info' === $notice['type'] ) { $notice['type'] = 'notice-info'; } $this->as3cf->render_view( 'notice', $notice ); if ( $notice['flash'] ) { $this->remove_notice( $notice ); } } /** * Enqueue notice scripts in the admin */ public function enqueue_notice_scripts() { $version = defined( 'SCRIPT_DEBUG' ) && SCRIPT_DEBUG ? time() : $GLOBALS['aws_meta']['amazon-s3-and-cloudfront']['version']; $suffix = ( defined( 'SCRIPT_DEBUG' ) && SCRIPT_DEBUG ) ? '' : '.min'; // Enqueue notice.js globally as notices can be dismissed on any admin page $src = plugins_url( 'assets/js/notice' . $suffix . '.js', $this->plugin_file_path ); wp_enqueue_script( 'as3cf-notice', $src, array( 'jquery' ), $version, true ); wp_localize_script( 'as3cf-notice', 'as3cf_notice', array( 'strings' => array( 'dismiss_notice_error' => __( 'Error dismissing notice.', 'amazon-s3-and-cloudfront' ), ), 'nonces' => array( 'dismiss_notice' => wp_create_nonce( 'as3cf-dismiss-notice' ), ), ) ); } /** * Handler for AJAX request to dismiss a notice */ public function ajax_dismiss_notice() { $this->as3cf->verify_ajax_request(); if ( ! isset( $_POST['notice_id'] ) || ! ( $notice_id = sanitize_text_field( $_POST['notice_id'] ) ) ) { $out = array( 'error' => __( 'Invalid notice ID.', 'amazon-s3-and-cloudfront' ) ); $this->as3cf->end_ajax( $out ); } $this->dismiss_notice( $notice_id ); $out = array( 'success' => '1', ); $this->as3cf->end_ajax( $out ); } /** * Helper to update/delete user meta * * @param int $user_id * @param string $key * @param array $value */ protected function update_user_meta( $user_id, $key, $value ) { if ( empty( $value ) ) { delete_user_meta( $user_id, $key); } else { update_user_meta( $user_id, $key, $value ); } } /** * Helper to update/delete site transient * * @param string $key * @param array $value */ protected function set_site_transient( $key, $value ) { if ( empty( $value ) ) { delete_site_transient( $key ); } else { set_site_transient( $key, $value ); } } }