Completed
Push — master ( ff1020...000c95 )
by Rodrigo
23:32 queued 11s
created

WC_Admin_Notices::wc_admin_feature_plugin_notice()   A

Complexity

Conditions 3
Paths 2

Size

Total Lines 8

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 12

Importance

Changes 0
Metric Value
cc 3
nc 2
nop 0
dl 0
loc 8
ccs 0
cts 5
cp 0
crap 12
rs 10
c 0
b 0
f 0
1
<?php
2
/**
3
 * Display notices in admin
4
 *
5
 * @package WooCommerce\Admin
6
 * @version 3.4.0
7
 */
8
9
defined( 'ABSPATH' ) || exit;
10
11
/**
12
 * WC_Admin_Notices Class.
13
 */
14
class WC_Admin_Notices {
15
16
	/**
17
	 * Stores notices.
18
	 *
19
	 * @var array
20
	 */
21
	private static $notices = array();
22
23
	/**
24
	 * Array of notices - name => callback.
25
	 *
26
	 * @var array
27
	 */
28
	private static $core_notices = array(
29
		'install'                   => 'install_notice',
30
		'update'                    => 'update_notice',
31
		'template_files'            => 'template_file_check_notice',
32
		'legacy_shipping'           => 'legacy_shipping_notice',
33
		'no_shipping_methods'       => 'no_shipping_methods_notice',
34
		'regenerating_thumbnails'   => 'regenerating_thumbnails_notice',
35
		'regenerating_lookup_table' => 'regenerating_lookup_table_notice',
36
		'no_secure_connection'      => 'secure_connection_notice',
37
		'wc_admin'                  => 'wc_admin_feature_plugin_notice',
38
	);
39
40
	/**
41
	 * Constructor.
42
	 */
43
	public static function init() {
44
		self::$notices = get_option( 'woocommerce_admin_notices', array() );
45
46
		add_action( 'switch_theme', array( __CLASS__, 'reset_admin_notices' ) );
47
		add_action( 'woocommerce_installed', array( __CLASS__, 'reset_admin_notices' ) );
48
		add_action( 'wp_loaded', array( __CLASS__, 'hide_notices' ) );
49
		add_action( 'shutdown', array( __CLASS__, 'store_notices' ) );
50
51
		if ( current_user_can( 'manage_woocommerce' ) ) {
52
			add_action( 'admin_print_styles', array( __CLASS__, 'add_notices' ) );
53
		}
54
	}
55
56
	/**
57
	 * Store notices to DB
58
	 */
59
	public static function store_notices() {
60
		update_option( 'woocommerce_admin_notices', self::get_notices() );
61
	}
62
63
	/**
64
	 * Get notices
65
	 *
66
	 * @return array
67
	 */
68 2
	public static function get_notices() {
69 2
		return self::$notices;
70
	}
71
72
	/**
73
	 * Remove all notices.
74
	 */
75 2
	public static function remove_all_notices() {
76 2
		self::$notices = array();
77
	}
78
79
	/**
80
	 * Reset notices for themes when switched or a new version of WC is installed.
81
	 */
82 2
	public static function reset_admin_notices() {
83 2
		if ( ! self::is_ssl() ) {
84 2
			self::add_notice( 'no_secure_connection' );
85
		}
86 2
		self::add_wc_admin_feature_plugin_notice();
87 2
		self::add_notice( 'template_files' );
88
	}
89
90
	/**
91
	 * Show a notice.
92
	 *
93
	 * @param string $name Notice name.
94
	 */
95 2
	public static function add_notice( $name ) {
96 2
		self::$notices = array_unique( array_merge( self::get_notices(), array( $name ) ) );
97
	}
98
99
	/**
100
	 * Remove a notice from being displayed.
101
	 *
102
	 * @param string $name Notice name.
103
	 */
104
	public static function remove_notice( $name ) {
105
		self::$notices = array_diff( self::get_notices(), array( $name ) );
106
		delete_option( 'woocommerce_admin_notice_' . $name );
107
	}
108
109
	/**
110
	 * See if a notice is being shown.
111
	 *
112
	 * @param string $name Notice name.
113
	 *
114
	 * @return boolean
115
	 */
116
	public static function has_notice( $name ) {
117
		return in_array( $name, self::get_notices(), true );
118
	}
119
120
	/**
121
	 * Hide a notice if the GET variable is set.
122
	 */
123
	public static function hide_notices() {
124
		if ( isset( $_GET['wc-hide-notice'] ) && isset( $_GET['_wc_notice_nonce'] ) ) { // WPCS: input var ok, CSRF ok.
125
			if ( ! wp_verify_nonce( sanitize_key( wp_unslash( $_GET['_wc_notice_nonce'] ) ), 'woocommerce_hide_notices_nonce' ) ) { // WPCS: input var ok, CSRF ok.
0 ignored issues
show
introduced by
Detected usage of a non-sanitized input variable: $_GET
Loading history...
126
				wp_die( esc_html__( 'Action failed. Please refresh the page and retry.', 'woocommerce' ) );
127
			}
128
129
			if ( ! current_user_can( 'manage_woocommerce' ) ) {
130
				wp_die( esc_html__( 'You don&#8217;t have permission to do this.', 'woocommerce' ) );
131
			}
132
133
			$hide_notice = sanitize_text_field( wp_unslash( $_GET['wc-hide-notice'] ) ); // WPCS: input var ok, CSRF ok.
0 ignored issues
show
introduced by
Detected usage of a non-sanitized input variable: $_GET
Loading history...
134
135
			self::remove_notice( $hide_notice );
136
137
			update_user_meta( get_current_user_id(), 'dismissed_' . $hide_notice . '_notice', true );
0 ignored issues
show
introduced by
update_user_meta() usage is highly discouraged, check VIP documentation on "Working with wp_users"
Loading history...
138
139
			do_action( 'woocommerce_hide_' . $hide_notice . '_notice' );
140
		}
141
	}
142
143
	/**
144
	 * Add notices + styles if needed.
145
	 */
146
	public static function add_notices() {
147
		$notices = self::get_notices();
148
149
		if ( empty( $notices ) ) {
150
			return;
151
		}
152
153
		$screen          = get_current_screen();
154
		$screen_id       = $screen ? $screen->id : '';
155
		$show_on_screens = array(
156
			'dashboard',
157
			'plugins',
158
		);
159
160
		// Notices should only show on WooCommerce screens, the main dashboard, and on the plugins screen.
161
		if ( ! in_array( $screen_id, wc_get_screen_ids(), true ) && ! in_array( $screen_id, $show_on_screens, true ) ) {
162
			return;
163
		}
164
165
		wp_enqueue_style( 'woocommerce-activation', plugins_url( '/assets/css/activation.css', WC_PLUGIN_FILE ), array(), WC_VERSION );
166
167
		// Add RTL support.
168
		wp_style_add_data( 'woocommerce-activation', 'rtl', 'replace' );
169
170
		foreach ( $notices as $notice ) {
171
			if ( ! empty( self::$core_notices[ $notice ] ) && apply_filters( 'woocommerce_show_admin_notice', true, $notice ) ) {
172
				add_action( 'admin_notices', array( __CLASS__, self::$core_notices[ $notice ] ) );
173
			} else {
174
				add_action( 'admin_notices', array( __CLASS__, 'output_custom_notices' ) );
175
			}
176
		}
177
	}
178
179
	/**
180
	 * Add a custom notice.
181
	 *
182
	 * @param string $name        Notice name.
183
	 * @param string $notice_html Notice HTML.
184
	 */
185
	public static function add_custom_notice( $name, $notice_html ) {
186
		self::add_notice( $name );
187
		update_option( 'woocommerce_admin_notice_' . $name, wp_kses_post( $notice_html ) );
188
	}
189
190
	/**
191
	 * Output any stored custom notices.
192
	 */
193
	public static function output_custom_notices() {
194
		$notices = self::get_notices();
195
196
		if ( ! empty( $notices ) ) {
197
			foreach ( $notices as $notice ) {
198
				if ( empty( self::$core_notices[ $notice ] ) ) {
199
					$notice_html = get_option( 'woocommerce_admin_notice_' . $notice );
200
201
					if ( $notice_html ) {
202
						include dirname( __FILE__ ) . '/views/html-notice-custom.php';
203
					}
204
				}
205
			}
206
		}
207
	}
208
209
	/**
210
	 * If we need to update, include a message with the update button.
211
	 */
212
	public static function update_notice() {
213
		if ( WC_Install::needs_db_update() ) {
214
			$next_scheduled_date = WC()->queue()->get_next( 'woocommerce_run_update_callback', null, 'woocommerce-db-updates' );
215
216
			if ( $next_scheduled_date || ! empty( $_GET['do_update_woocommerce'] ) ) { // WPCS: input var ok, CSRF ok.
217
				include dirname( __FILE__ ) . '/views/html-notice-updating.php';
218
			} else {
219
				include dirname( __FILE__ ) . '/views/html-notice-update.php';
220
			}
221
		} else {
222
			WC_Install::update_db_version();
223
			include dirname( __FILE__ ) . '/views/html-notice-updated.php';
224
		}
225
	}
226
227
	/**
228
	 * If we have just installed, show a message with the install pages button.
229
	 */
230
	public static function install_notice() {
231
		include dirname( __FILE__ ) . '/views/html-notice-install.php';
232
	}
233
234
	/**
235
	 * Show a notice highlighting bad template files.
236
	 */
237
	public static function template_file_check_notice() {
238
		$core_templates = WC_Admin_Status::scan_template_files( WC()->plugin_path() . '/templates' );
239
		$outdated       = false;
240
241
		foreach ( $core_templates as $file ) {
242
243
			$theme_file = false;
244 View Code Duplication
			if ( file_exists( get_stylesheet_directory() . '/' . $file ) ) {
245
				$theme_file = get_stylesheet_directory() . '/' . $file;
246
			} elseif ( file_exists( get_stylesheet_directory() . '/' . WC()->template_path() . $file ) ) {
247
				$theme_file = get_stylesheet_directory() . '/' . WC()->template_path() . $file;
248
			} elseif ( file_exists( get_template_directory() . '/' . $file ) ) {
249
				$theme_file = get_template_directory() . '/' . $file;
250
			} elseif ( file_exists( get_template_directory() . '/' . WC()->template_path() . $file ) ) {
251
				$theme_file = get_template_directory() . '/' . WC()->template_path() . $file;
252
			}
253
254
			if ( false !== $theme_file ) {
255
				$core_version  = WC_Admin_Status::get_file_version( WC()->plugin_path() . '/templates/' . $file );
256
				$theme_version = WC_Admin_Status::get_file_version( $theme_file );
257
258
				if ( $core_version && $theme_version && version_compare( $theme_version, $core_version, '<' ) ) {
259
					$outdated = true;
260
					break;
261
				}
262
			}
263
		}
264
265
		if ( $outdated ) {
266
			include dirname( __FILE__ ) . '/views/html-notice-template-check.php';
267
		} else {
268
			self::remove_notice( 'template_files' );
269
		}
270
	}
271
272
	/**
273
	 * Show a notice asking users to convert to shipping zones.
274
	 *
275
	 * @todo remove in 4.0.0
276
	 */
277
	public static function legacy_shipping_notice() {
278
		$maybe_load_legacy_methods = array( 'flat_rate', 'free_shipping', 'international_delivery', 'local_delivery', 'local_pickup' );
279
		$enabled                   = false;
280
281
		foreach ( $maybe_load_legacy_methods as $method ) {
282
			$options = get_option( 'woocommerce_' . $method . '_settings' );
283
			if ( $options && isset( $options['enabled'] ) && 'yes' === $options['enabled'] ) {
284
				$enabled = true;
285
			}
286
		}
287
288
		if ( $enabled ) {
289
			include dirname( __FILE__ ) . '/views/html-notice-legacy-shipping.php';
290
		} else {
291
			self::remove_notice( 'template_files' );
292
		}
293
	}
294
295
	/**
296
	 * No shipping methods.
297
	 */
298
	public static function no_shipping_methods_notice() {
299
		if ( wc_shipping_enabled() && ( empty( $_GET['page'] ) || empty( $_GET['tab'] ) || 'wc-settings' !== $_GET['page'] || 'shipping' !== $_GET['tab'] ) ) { // WPCS: input var ok, CSRF ok.
300
			$product_count = wp_count_posts( 'product' );
301
			$method_count  = wc_get_shipping_method_count();
302
303
			if ( $product_count->publish > 0 && 0 === $method_count ) {
304
				include dirname( __FILE__ ) . '/views/html-notice-no-shipping-methods.php';
305
			}
306
307
			if ( $method_count > 0 ) {
308
				self::remove_notice( 'no_shipping_methods' );
309
			}
310
		}
311
	}
312
313
	/**
314
	 * Notice shown when regenerating thumbnails background process is running.
315
	 */
316
	public static function regenerating_thumbnails_notice() {
317
		include dirname( __FILE__ ) . '/views/html-notice-regenerating-thumbnails.php';
318
	}
319
320
	/**
321
	 * Notice about secure connection.
322
	 */
323
	public static function secure_connection_notice() {
324
		if ( self::is_ssl() || get_user_meta( get_current_user_id(), 'dismissed_no_secure_connection_notice', true ) ) {
0 ignored issues
show
introduced by
get_user_meta() usage is highly discouraged, check VIP documentation on "Working with wp_users"
Loading history...
325
			return;
326
		}
327
328
		include dirname( __FILE__ ) . '/views/html-notice-secure-connection.php';
329
	}
330
331
	/**
332
	 * Notice shown when regenerating thumbnails background process is running.
333
	 *
334
	 * @since 3.6.0
335
	 */
336
	public static function regenerating_lookup_table_notice() {
337
		// See if this is still relevent.
338
		if ( ! wc_update_product_lookup_tables_is_running() ) {
339
			self::remove_notice( 'regenerating_lookup_table' );
340
			return;
341
		}
342
343
		include dirname( __FILE__ ) . '/views/html-notice-regenerating-lookup-table.php';
344
	}
345
346
347
	/**
348
	 * If on WordPress 5.0 or greater, inform users of WooCommerce Admin feature plugin.
349
	 *
350
	 * @since 3.6.4
351
	 * @todo  Remove this notice and associated code once the feature plugin has been merged into core.
352
	 */
353 2
	public static function add_wc_admin_feature_plugin_notice() {
354 2
		$wordpress_version            = get_bloginfo( 'version' );
355
356 2
		if ( version_compare( $wordpress_version, '5.0', '>=' ) ) {
357 2
			self::add_notice( 'wc_admin' );
358
		}
359
	}
360
361
	/**
362
	 * Notice to try WooCommerce Admin
363
	 *
364
	 * @since 3.6.4
365
	 * @todo  Remove this notice and associated code once the feature plugin has been merged into core.
366
	 */
367
	public static function wc_admin_feature_plugin_notice() {
368
		if ( get_user_meta( get_current_user_id(), 'dismissed_wc_admin_notice', true ) || self::is_plugin_active( 'woocommerce-admin/woocommerce-admin.php' ) ) {
0 ignored issues
show
introduced by
get_user_meta() usage is highly discouraged, check VIP documentation on "Working with wp_users"
Loading history...
369
			self::remove_notice( 'wc_admin' );
370
			return;
371
		}
372
373
		include dirname( __FILE__ ) . '/views/html-notice-wc-admin.php';
374
	}
375
376
	/**
377
	 * Determine if the store is running SSL.
378
	 *
379
	 * @return bool Flag SSL enabled.
380
	 * @since  3.5.1
381
	 */
382 2
	protected static function is_ssl() {
383 2
		$shop_page = wc_get_page_permalink( 'shop' );
384
385 2
		return ( is_ssl() && 'https' === substr( $shop_page, 0, 5 ) );
386
	}
387
388
	/**
389
	 * Wrapper for is_plugin_active.
390
	 *
391
	 * @param string $plugin Plugin to check.
392
	 * @return boolean
393
	 */
394
	protected static function is_plugin_active( $plugin ) {
395
		if ( ! function_exists( 'is_plugin_active' ) ) {
396
			include_once ABSPATH . 'wp-admin/includes/plugin.php';
397
		}
398
		return is_plugin_active( $plugin );
399
	}
400
401
	/**
402
	 * Simplify Commerce is no longer in core.
403
	 *
404
	 * @deprecated 3.6.0 No longer shown.
405
	 */
406
	public static function simplify_commerce_notice() {
407
		wc_deprecated_function( 'WC_Admin_Notices::simplify_commerce_notice', '3.6.0' );
408
	}
409
410
	/**
411
	 * Show the Theme Check notice.
412
	 *
413
	 * @deprecated 3.3.0 No longer shown.
414
	 */
415
	public static function theme_check_notice() {
416
		wc_deprecated_function( 'WC_Admin_Notices::theme_check_notice', '3.3.0' );
417
	}
418
}
419
420
WC_Admin_Notices::init();
421