PluginProbe ʕ •ᴥ•ʔ
Hustle – Email Marketing, Lead Generation, Optins, Popups / 7.8.14.1
Hustle – Email Marketing, Lead Generation, Optins, Popups v7.8.14.1
7.8.14 7.8.14.1 7.8.13 7.8.13.1 trunk 3.0 3.1 3.1.1 3.1.2 3.1.3 3.1.4 4.3.2 4.4.4 4.4.5 4.4.5.1 4.4.5.4 4.6 4.6.1.1 4.6.1.4 4.7.0.2 4.7.0.3 4.7.0.7 4.7.0.9 4.7.1.0 4.7.1.1 4.8.0.0 5.0.0 5.0.1 5.0.1.1 5.0.1.2 5.1 5.1.1 5.1.2 5.1.3 5.1.3.1 5.1.3.2 5.1.4 5.1.5 6.0 6.0.1 6.0.2 6.0.3 6.0.4.2 6.0.5 6.0.6.1 6.0.7 6.0.8.1 6.0.9 7.0.0.1 7.0.2 7.0.3 7.0.4 7.1.0 7.1.1 7.2.0 7.2.1 7.3.0 7.3.1 7.3.3 7.3.5 7.3.6 7.3.7 7.4.0 7.4.1 7.4.11 7.4.13 7.4.13.1 7.4.2 7.4.3 7.4.4 7.4.5 7.4.5.1 7.4.5.2 7.4.6 7.4.7 7.5.0 7.6.0 7.6.1 7.6.3 7.6.4 7.6.6 7.7.0 7.7.1 7.8.0 7.8.1 7.8.10 7.8.10.1 7.8.10.2 7.8.11 7.8.12 7.8.12.1 7.8.2 7.8.3 7.8.4 7.8.5 7.8.6 7.8.7 7.8.8 7.8.9 7.8.9.1 7.8.9.2 7.8.9.3
wordpress-popup / inc / opt-in-utils.php
wordpress-popup / inc Last commit date
display-conditions 5 months ago front 2 days ago helpers 1 month ago metas 3 months ago multisite 5 months ago palettes 3 years ago provider 1 month ago providers 2 days ago templates 3 years ago update 5 months ago class-hustle-admin-page-abstract.php 1 month ago class-hustle-auth-token.php 5 months ago class-hustle-condition-factory.php 6 years ago class-hustle-cross-sell.php 10 months ago class-hustle-dashboard-admin.php 1 month ago class-hustle-data.php 1 month ago class-hustle-db.php 2 years ago class-hustle-installer.php 4 years ago class-hustle-meta.php 3 years ago class-hustle-module-admin.php 1 month ago class-hustle-module-collection.php 5 months ago class-hustle-module-fields.php 3 months ago class-hustle-module-page-abstract.php 1 month ago class-hustle-module-validator.php 3 months ago class-hustle-notifications.php 2 days ago class-hustle-settings-admin.php 1 month ago class-hustle-wp-dashboard-page.php 5 months ago class-opt-in.php 2 days ago hustle-background-conversion-log.php 3 months ago hustle-deletion.php 3 months ago hustle-embedded-admin.php 3 years ago hustle-entries-admin.php 5 months ago hustle-entry-model.php 1 month ago hustle-general-data-protection.php 5 months ago hustle-init.php 1 month ago hustle-mail.php 5 months ago hustle-migration.php 5 months ago hustle-model.php 2 days ago hustle-module-model.php 1 month ago hustle-module-widget-legacy.php 5 months ago hustle-module-widget.php 5 months ago hustle-modules-common-admin-ajax.php 1 month ago hustle-popup-admin.php 3 years ago hustle-providers-admin.php 1 month ago hustle-providers.php 5 months ago hustle-settings-admin-ajax.php 1 month ago hustle-settings-page.php 3 years ago hustle-slidein-admin.php 3 years ago hustle-sshare-admin.php 2 days ago hustle-sshare-model.php 2 days ago hustle-tracking-model.php 3 months ago interface-hustle-auth-provider.php 5 months ago opt-in-geo.php 5 months ago opt-in-utils.php 2 days ago opt-in-wpmudev-api.php 5 months ago
opt-in-utils.php
1426 lines
1 <?php // phpcs:ignore WordPress.Files.FileName.InvalidClassFileName
2 /**
3 * Conditions utils
4 *
5 * @package Hustle
6 */
7
8 /**
9 * Class Opt_In_Utils
10 */
11 class Opt_In_Utils {
12
13 /**
14 * CPT
15 *
16 * @var array
17 */
18 private static $post_types;
19
20 /**
21 * Array of administrator roles
22 *
23 * @var array
24 */
25 private static $admin_roles;
26
27 /**
28 * Is static cache enabled
29 *
30 * @var boolean
31 */
32 private static $static_cache;
33
34 /**
35 * Plugin name according White Label option
36 * White Label -> WPMU DEV Plugin Labels
37 *
38 * @var string
39 */
40 private static $plugin_name;
41
42 /**
43 * Returns the referrer.
44 *
45 * @return string
46 */
47 public static function get_referrer() {
48 $referrer = '';
49
50 $po_method = filter_input( INPUT_POST, '_po_method_', FILTER_SANITIZE_SPECIAL_CHARS );
51 $is_ajax = ( defined( 'DOING_AJAX' ) && DOING_AJAX ) ||
52 'raw' === $po_method;
53
54 $http_referer = filter_input( INPUT_SERVER, 'HTTP_REFERER', FILTER_SANITIZE_SPECIAL_CHARS );
55 if ( isset( $_REQUEST['thereferrer'] ) ) { // phpcs:ignore WordPress.Security.NonceVerification.Recommended
56 $referrer = $_REQUEST['thereferrer'];// phpcs:ignore
57 } elseif ( ! $is_ajax && $http_referer ) {
58 // When doing Ajax request we NEVER use the HTTP_REFERER!
59 $referrer = $http_referer;
60 }
61
62 return esc_attr( $referrer );
63 }
64
65 /**
66 * Tests if the current referrer is one of the referers of the list.
67 * Current referrer has to be specified in the URL param "thereferer".
68 *
69 * @param array $source_list List of referers to check.
70 * @return bool
71 */
72 public static function test_referrer( $source_list ) {
73 $response = false;
74 if ( is_string( $source_list ) ) {
75 $source_list = preg_split( '/\r\n|\r|\n/', $source_list );
76 }
77 if ( ! is_array( $source_list ) ) {
78 return true;
79 }
80
81 $referrer = self::get_referrer();
82
83 if ( ! empty( $referrer ) ) {
84 foreach ( $source_list as $item ) {
85 $item = trim( $item );
86 $res = stripos( $referrer, $item ) || fnmatch( $item, $referrer );
87 if ( false !== $res ) {
88 $response = true;
89 break;
90 }
91 }
92 }
93
94 return $response;
95 }
96
97 /**
98 * Get the real page id or false
99 *
100 * @global object $wp_query WP_Query.
101 * @global WP_Post $post Post.
102 * @return int|boolean
103 */
104 public static function get_real_page_id() {
105 global $wp_query, $post;
106
107 $is_wc_shop = class_exists( 'woocommerce' ) && is_shop();
108 $is_posts_page = $wp_query->is_posts_page;
109
110 if ( ! $is_wc_shop && ! $is_posts_page && ( ! isset( $post ) || ! ( $post instanceof WP_Post ) || 'page' !== $post->post_type || ! is_page() ) ) {
111 return false;
112 }
113
114 if ( $is_wc_shop ) {
115 $page_id = wc_get_page_id( 'shop' );
116 } elseif ( $is_posts_page ) {
117 $page_id = get_option( 'page_for_posts' );
118 } else {
119 $page_id = $post->ID;
120 }
121
122 return $page_id;
123 }
124
125 /**
126 * Returns current actual url, the one seen on browser
127 *
128 * @param bool $with_protocol Whether to retrieve the URL with the protocol.
129 * @return string
130 */
131 public static function get_current_actual_url( $with_protocol = false ) {
132
133 if ( ! isset( $_SERVER['HTTP_HOST'] ) || ! isset( $_SERVER['REQUEST_URI'] ) ) {
134 return '';
135 }
136
137 $host = filter_var( wp_unslash( $_SERVER['HTTP_HOST'] ), FILTER_SANITIZE_URL );
138 $uri = filter_var( wp_unslash( $_SERVER['REQUEST_URI'] ), FILTER_SANITIZE_URL );
139
140 $url = $host . $uri;
141
142 if ( ! $with_protocol ) {
143 return $url;
144 }
145
146 return 'http' . ( isset( $_SERVER['HTTPS'] ) ? 's' : '' ) . '://' . $url;
147 }
148
149 /**
150 * Returns current url
151 * should only be called after plugins_loaded hook is fired
152 *
153 * @return string
154 */
155 public static function get_current_url() {
156 if ( ! did_action( 'plugins_loaded' ) ) {
157 new Exception( 'This method should only be called after plugins_loaded hook is fired' ); }
158
159 global $wp;
160 return add_query_arg( $wp->query_string, '', home_url( $wp->request ) );
161 }
162
163 /**
164 * Checks if user is allowed to perform the ajax actions
165 *
166 * @since 4.0
167 * @param array $capability Hustle capability.
168 * @param int $module_id Optional. Module id.
169 */
170 public static function is_user_allowed_ajax( $capability, $module_id = null ) {
171 if ( is_null( $module_id ) ) {
172 $allowed = current_user_can( $capability );
173 } else {
174 $allowed = self::is_user_allowed( $capability, $module_id );
175 }
176
177 if ( ! $allowed ) {
178 wp_send_json_error( esc_html__( 'Invalid request, you are not allowed to make this request', 'hustle' ) );
179 }
180 }
181
182 /**
183 * Check is it admin role or not
184 *
185 * @param string|array $role Role.
186 * @return bool
187 */
188 public static function is_admin_role( $role ) {
189 $admin_roles = array_keys( self::get_admin_roles() );
190
191 if ( ! is_array( $role ) ) {
192 return in_array( $role, $admin_roles, true );
193 }
194
195 return (bool) array_intersect( $role, $admin_roles );
196 }
197
198 /**
199 * Get admin role array
200 *
201 * @since 4.1.0
202 * @return array
203 */
204 public static function get_admin_roles() {
205
206 if ( is_null( self::$admin_roles ) ) {
207 $admins = array();
208 $all_roles = wp_roles();
209
210 if ( $all_roles->is_role( 'administrator' ) ) {
211 $admins['administrator'] = ucfirst( translate_user_role( 'administrator', 'hustle' ) );
212
213 } else {
214 foreach ( $all_roles->roles as $name => $data ) {
215 if ( ! empty( $data['capabilities']['manage_options'] ) && true === $data['capabilities']['manage_options'] ) {
216 $admins[ $name ] = $data['name'];
217 }
218 }
219 }
220
221 self::$admin_roles = apply_filters( 'hustle_get_admin_roles', $admins );
222 }
223
224 return self::$admin_roles;
225 }
226
227 /**
228 * Checks if user has the capability
229 *
230 * @since 4.0
231 * @param array $capability Hustle capability.
232 * @param int $module_id Optional. Module id.
233 * @return bool
234 */
235 public static function is_user_allowed( $capability, $module_id = null ) {
236
237 // Super admins can do everything.
238 if ( current_user_can( 'setup_network' ) ) {
239 return true;
240 }
241
242 $user = wp_get_current_user();
243 $current_user_caps = (array) $user->allcaps;
244 $current_user_roles = (array) $user->roles;
245
246 if ( self::is_admin_role( $current_user_roles ) ) {
247 // If editing a module and the user is godish, allow.
248 return true;
249
250 } elseif ( 'hustle_edit_module' === $capability && ! empty( $current_user_caps['hustle_create'] ) ) {
251 // If the user can create, it also can edit. Allow.
252 return true;
253
254 } elseif ( is_null( $module_id ) ) {
255 // If we're not editing a module, check for the requested capability.
256 return ! empty( $current_user_caps[ $capability ] );
257
258 } else {
259
260 // If editing a module and the user isn't godish...
261 $module = Hustle_Module_Model::new_instance( $module_id );
262
263 // If the module isn't valid, abort.
264 if ( is_wp_error( $module ) ) {
265 return false;
266 }
267
268 // Check for the specific allowed roles.
269 $allowed_roles = $module->get_edit_roles();
270 return (bool) array_intersect( $allowed_roles, $current_user_roles );
271 }
272
273 return false;
274 }
275
276 /**
277 * Get's the status of the membership.
278 *
279 * @since 4.3.3
280 *
281 * @return string
282 */
283 public static function get_membership_status() {
284 // Dashboard is active.
285 if ( class_exists( 'WPMUDEV_Dashboard' ) ) {
286 // Get membership type.
287 if ( method_exists( 'WPMUDEV_Dashboard_Api', 'get_membership_status' ) ) {
288 $status = WPMUDEV_Dashboard::$api->get_membership_status();
289 } else {
290 $status = WPMUDEV_Dashboard::$api->get_membership_type();
291 // Check if API key is available.
292 if ( 'free' === $status && WPMUDEV_Dashboard::$api->has_key() ) {
293 $status = 'expired';
294 }
295 }
296 } else {
297 $status = 'free';
298 }
299 return $status;
300 }
301
302 /**
303 * Checks whether Hustle is included in the membership.
304 *
305 * @since 4.3.3
306 *
307 * @return boolean
308 */
309 public static function is_hustle_included_in_membership() {
310 if ( class_exists( 'WPMUDEV_Dashboard' ) ) {
311 if ( class_exists( 'WPMUDEV_Dashboard' ) && method_exists( \WPMUDEV_Dashboard::$upgrader, 'user_can_install' ) ) {
312 return \WPMUDEV_Dashboard::$upgrader->user_can_install( 1107020, true );
313 }
314 }
315
316 return false;
317 }
318
319 /**
320 * Return URL link for wp.org, wpmudev, support, live chat, docs, installing plugin.
321 *
322 * @since 4.3.4
323 *
324 * @param string $link_for The section to retrieve the link for.
325 * @param string|bool $campaign Utm campaign tag to be used in link.
326 *
327 * @return string
328 */
329 public static function get_link( $link_for, $campaign = false ) {
330 $domain = 'https://wpmudev.com';
331 $wp_org = 'https://wordpress.org';
332 $utm_tags = ! $campaign ? '' : "?utm_source=hustle&utm_medium=plugin&utm_campaign={$campaign}";
333
334 switch ( $link_for ) {
335 case 'chat':
336 $link = "{$domain}/live-support/{$utm_tags}";
337 break;
338 case 'plugin':
339 $link = "{$domain}/project/hustle/{$utm_tags}";
340 break;
341 case 'support':
342 if ( 'full' === self::get_membership_status() ) {
343 $link = "{$domain}/hub/support/{$utm_tags}#get-support";
344 } else {
345 $link = "{$wp_org}/support/plugin/wordpress-popup";
346 }
347 break;
348 case 'docs':
349 $link = "{$domain}/docs/wpmu-dev-plugins/hustle/{$utm_tags}";
350 break;
351 case 'install_plugin':
352 if ( self::is_hustle_included_in_membership() ) {
353 // Return the pro plugin URL.
354 $url = WPMUDEV_Dashboard::$ui->page_urls->plugins_url;
355 $link = $url . '#pid=1107020';
356 } else {
357 // Return the free URL.
358 $link = wp_nonce_url( self_admin_url( 'update.php?action=install-plugin&plugin=wordpress-popup' ), 'install-plugin_wordpress-popup' );
359 }
360 break;
361 case 'roadmap':
362 $link = "{$domain}/roadmap/{$utm_tags}";
363 break;
364 case 'wpmudev':
365 $link = "{$domain}/{$utm_tags}";
366 break;
367 case 'blog':
368 $link = "{$domain}/blog/{$utm_tags}";
369 break;
370 default:
371 $link = '';
372 break;
373 }
374
375 return $link;
376 }
377
378 /**
379 * Checks if the ajax
380 *
381 * @since 1.0
382 * @param string $action ajax call action name.
383 */
384 public static function validate_ajax_call( $action ) {
385 if ( ! check_ajax_referer( $action, false, false ) ) {
386 wp_send_json_error( esc_html__( 'Invalid request, you are not allowed to make this request', 'hustle' ) ); }
387 }
388
389 /**
390 * Verify if current version is FREE
391 **/
392 public static function is_free() {
393 $is_free = ! file_exists( Opt_In::$plugin_path . 'lib/wpmudev-dashboard/wpmudev-dash-notification.php' );
394
395 return $is_free;
396 }
397
398 /**
399 * Get the user roles options.
400 *
401 * @since 4.0
402 *
403 * @return array
404 */
405 public static function get_user_roles() {
406
407 global $wp_roles;
408 $roles = $wp_roles->get_names();
409
410 return apply_filters( 'hustle_get_module_permissions_roles', $roles );
411 }
412
413 // ====================================
414 // INTEGRATIONS
415 // ====================================
416
417 /**
418 * Used for sanitizing form submissions.
419 * This method will do a simple sanitation of $post_data. It applies sanitize_text_field() to the keys and values of the first level array.
420 * The keys from second level arrays are converted to numbers, and their values are sanitized with sanitize_text_field() as well.
421 * This method doesn’t do an exhaustive sanitation, so you should handled special cases if your integration requires something different.
422 * The names passed on $required_fields are searched into $post_data array keys. If the key is not set, an array with the key “errors” is returned.
423 *
424 * @since 3.0.5
425 * @param array $post_data The data to be sanitized and validated.
426 * @param array $required_fields Fields that must exist on $post_data so the validation doesn't fail.
427 * @return array
428 */
429 public static function validate_and_sanitize_fields( $post_data, $required_fields = array() ) {
430 // for serialized data or form.
431 if ( ! is_array( $post_data ) && is_string( $post_data ) ) {
432 $post_string = $post_data;
433 $post_data = array();
434 wp_parse_str( $post_string, $post_data );
435 }
436
437 $errors = array();
438 foreach ( $required_fields as $key => $required_field ) {
439 if ( ! isset( $post_data[ $required_field ] ) || ( empty( trim( $post_data[ $required_field ] ) ) && '0' !== $post_data[ $required_field ] ) ) {
440 /* translators: required field name */
441 $errors[ $required_field ] = sprintf( __( 'Field %s is required.', 'hustle' ), $required_field );
442 continue;
443 }
444 }
445
446 if ( ! empty( $errors ) ) {
447 return array( 'errors' => $errors );
448 }
449
450 $sanitized_data = array();
451 foreach ( $post_data as $key => $post_datum ) {
452 /**
453 * Sanitize here every request so we dont need to sanitize it again on other methods,
454 * unless special treatment is required.
455 */
456 $sanitized_data[ sanitize_text_field( $key ) ] = self::sanitize_text_input_deep( $post_datum );
457 }
458
459 return $sanitized_data;
460 }
461
462 /**
463 * Sanitizes the values of a multi-dimensional array.
464 * The keys of the sub-arrays are converted to numerical arrays.
465 * Sub-arrays are expected to have numerical indexes.
466 *
467 * @since 3.0.5
468 * @param array|string $value Value.
469 * @return string
470 */
471 public static function sanitize_text_input_deep( $value ) {
472 if ( is_array( $value ) ) {
473 array_walk_recursive(
474 $value,
475 function ( &$val ) {
476 $val = sanitize_textarea_field( $val );
477 }
478 );
479 } else {
480 $value = sanitize_textarea_field( $value );
481 }
482
483 return $value;
484 }
485
486 /**
487 * Adds an entry to debug log
488 *
489 * By default it will check `WP_DEBUG` and HUSTLE_DEBUG to decide whether to add the log,
490 * then will check `filters`.
491 *
492 * @since 3.0.5
493 * @since 4.0 also checks HUSTLE_DEBUG
494 */
495 public static function maybe_log() {
496
497 $wp_debug_enabled = ( defined( 'WP_DEBUG' ) && WP_DEBUG );
498
499 $enabled = ( defined( 'HUSTLE_DEBUG' ) && HUSTLE_DEBUG );
500
501 $stored_settings = Hustle_Settings_Admin::get_general_settings();
502 $debug_setting_enabled = '1' === $stored_settings['debug_enabled'];
503
504 $enabled = ( $wp_debug_enabled && ( $debug_setting_enabled || $enabled ) );
505
506 /**
507 * Filter to enable or disable log for Hustle
508 *
509 * By default it will check `WP_DEBUG`
510 *
511 * @since 3.0.5
512 *
513 * @param bool $enabled current enabled status
514 */
515 $enabled = apply_filters( 'hustle_enable_log', $enabled );
516
517 if ( $enabled ) {
518 $args = func_get_args();
519 $message = wp_json_encode( $args );
520 if ( false !== $message ) {
521 error_log( '[Hustle] ' . $message );// phpcs:ignore WordPress.PHP.DevelopmentFunctions.error_log_error_log
522 }
523 }
524 }
525
526 // ====================================
527 // MISC?
528 // ====================================
529
530 /**
531 * Returns list of optin providers based on their declared classes that implement Opt_In_Provider_Interface
532 *
533 * @return array
534 */
535 public static function get_post_types() {
536 if ( empty( self::$post_types ) ) {
537 /**
538 * Add all custom post types
539 */
540 $post_types = array();
541 $cpts = get_post_types(
542 array(
543 'public' => true,
544 '_builtin' => false,
545 ),
546 'objects'
547 );
548 foreach ( $cpts as $cpt ) {
549
550 // skip ms_invoice.
551 if ( 'ms_invoice' === $cpt->name ) {
552 continue;
553 }
554
555 $cpt_array['name'] = $cpt->name;
556 $cpt_array['label'] = $cpt->label;
557 $cpt_array['data'] = array();
558
559 $post_types[ $cpt->name ] = $cpt_array;
560 }
561 self::$post_types = $post_types;
562 }
563 return self::$post_types;
564 }
565
566
567 /**
568 * Get usable object for select2
569 *
570 * @param string $post_type post type.
571 * @param array $include_ids Include IDs.
572 * @return array
573 */
574 public static function get_select2_data( $post_type, $include_ids = null ) {
575 $data = array();
576
577 if ( array() === $include_ids ) {
578 return $data;
579 }
580
581 $args = array(
582 'numberposts' => -1,
583 'post_type' => $post_type,
584 'post_status' => 'publish',
585 'order' => 'ASC',
586 );
587
588 if ( ! empty( $include_ids ) ) {
589 $args['post__in'] = $include_ids;
590 }
591
592 $posts = get_posts( $args );
593 foreach ( $posts as $post ) {
594 $data[] = (object) array(
595 'id' => $post->ID,
596 'text' => $post->post_title,
597 );
598 }
599
600 return $data;
601 }
602
603 /**
604 * Return reCAPTCHA languages
605 *
606 * @since 4.0
607 * @return array
608 */
609 public static function get_captcha_languages() {
610 return apply_filters(
611 'hustle_captcha_languages',
612 array(
613 'ar' => esc_html__( 'Arabic', 'hustle' ),
614 'af' => esc_html__( 'Afrikaans', 'hustle' ),
615 'am' => esc_html__( 'Amharic', 'hustle' ),
616 'hy' => esc_html__( 'Armenian', 'hustle' ),
617 'az' => esc_html__( 'Azerbaijani', 'hustle' ),
618 'eu' => esc_html__( 'Basque', 'hustle' ),
619 'bn' => esc_html__( 'Bengali', 'hustle' ),
620 'bg' => esc_html__( 'Bulgarian', 'hustle' ),
621 'ca' => esc_html__( 'Catalan', 'hustle' ),
622 'zh-HK' => esc_html__( 'Chinese (Hong Kong)', 'hustle' ),
623 'zh-CN' => esc_html__( 'Chinese (Simplified)', 'hustle' ),
624 'zh-TW' => esc_html__( 'Chinese (Traditional)', 'hustle' ),
625 'hr' => esc_html__( 'Croatian', 'hustle' ),
626 'cs' => esc_html__( 'Czech', 'hustle' ),
627 'da' => esc_html__( 'Danish', 'hustle' ),
628 'nl' => esc_html__( 'Dutch', 'hustle' ),
629 'en-GB' => esc_html__( 'English (UK)', 'hustle' ),
630 'en' => esc_html__( 'English (US)', 'hustle' ),
631 'et' => esc_html__( 'Estonian', 'hustle' ),
632 'fil' => esc_html__( 'Filipino', 'hustle' ),
633 'fi' => esc_html__( 'Finnish', 'hustle' ),
634 'fr' => esc_html__( 'French', 'hustle' ),
635 'fr-CA' => esc_html__( 'French (Canadian)', 'hustle' ),
636 'gl' => esc_html__( 'Galician', 'hustle' ),
637 'ka' => esc_html__( 'Georgian', 'hustle' ),
638 'de' => esc_html__( 'German', 'hustle' ),
639 'de-AT' => esc_html__( 'German (Austria)', 'hustle' ),
640 'de-CH' => esc_html__( 'German (Switzerland)', 'hustle' ),
641 'el' => esc_html__( 'Greek', 'hustle' ),
642 'gu' => esc_html__( 'Gujarati', 'hustle' ),
643 'iw' => esc_html__( 'Hebrew', 'hustle' ),
644 'hi' => esc_html__( 'Hindi', 'hustle' ),
645 'hu' => esc_html__( 'Hungarain', 'hustle' ),
646 'is' => esc_html__( 'Icelandic', 'hustle' ),
647 'id' => esc_html__( 'Indonesian', 'hustle' ),
648 'it' => esc_html__( 'Italian', 'hustle' ),
649 'ja' => esc_html__( 'Japanese', 'hustle' ),
650 'kn' => esc_html__( 'Kannada', 'hustle' ),
651 'ko' => esc_html__( 'Korean', 'hustle' ),
652 'lo' => esc_html__( 'Laothian', 'hustle' ),
653 'lv' => esc_html__( 'Latvian', 'hustle' ),
654 'lt' => esc_html__( 'Lithuanian', 'hustle' ),
655 'ms' => esc_html__( 'Malay', 'hustle' ),
656 'ml' => esc_html__( 'Malayalam', 'hustle' ),
657 'mr' => esc_html__( 'Marathi', 'hustle' ),
658 'mn' => esc_html__( 'Mongolian', 'hustle' ),
659 'no' => esc_html__( 'Norwegian', 'hustle' ),
660 'fa' => esc_html__( 'Persian', 'hustle' ),
661 'pl' => esc_html__( 'Polish', 'hustle' ),
662 'pt' => esc_html__( 'Portuguese', 'hustle' ),
663 'pt-BR' => esc_html__( 'Portuguese (Brazil)', 'hustle' ),
664 'pt-PT' => esc_html__( 'Portuguese (Portugal)', 'hustle' ),
665 'ro' => esc_html__( 'Romanian', 'hustle' ),
666 'ru' => esc_html__( 'Russian', 'hustle' ),
667 'sr' => esc_html__( 'Serbian', 'hustle' ),
668 'si' => esc_html__( 'Sinhalese', 'hustle' ),
669 'sk' => esc_html__( 'Slovak', 'hustle' ),
670 'sl' => esc_html__( 'Slovenian', 'hustle' ),
671 'es' => esc_html__( 'Spanish', 'hustle' ),
672 'es-419' => esc_html__( 'Spanish (Latin America)', 'hustle' ),
673 'sw' => esc_html__( 'Swahili', 'hustle' ),
674 'sv' => esc_html__( 'Swedish', 'hustle' ),
675 'ta' => esc_html__( 'Tamil', 'hustle' ),
676 'te' => esc_html__( 'Telugu', 'hustle' ),
677 'th' => esc_html__( 'Thai', 'hustle' ),
678 'tr' => esc_html__( 'Turkish', 'hustle' ),
679 'uk' => esc_html__( 'Ukrainian', 'hustle' ),
680 'ur' => esc_html__( 'Urdu', 'hustle' ),
681 'vi' => esc_html__( 'Vietnamese', 'hustle' ),
682 'zu' => esc_html__( 'Zulu', 'hustle' ),
683 )
684 );
685 }
686
687 /**
688 * Gets post property
689 *
690 * @since 4.0.4
691 * @param string $property Requested post property.
692 * @param string $default_value Fallback value.
693 * @return string
694 */
695 public static function get_post_data( $property, $default_value = '' ) {
696 global $post;
697
698 if ( ! $post ) {
699 // fallback on wp_ajax, `global $post` not available.
700 $wp_referer = wp_get_referer();
701 if ( $wp_referer ) {
702 $post_id = ! function_exists( 'wpcom_vip_url_to_postid' ) ? url_to_postid( $wp_referer ) : wpcom_vip_url_to_postid( $wp_referer );
703 if ( $post_id ) {
704 $post_object = get_post( $post_id );
705 // make sure it's wp_post.
706 if ( $post_object instanceof WP_Post ) {
707 // set global $post as $post_object retrieved from `get_post` for next usage.
708 $post = $post_object;// phpcs:ignore WordPress.WP.GlobalVariablesOverride.Prohibited
709 }
710 }
711 }
712 }
713
714 $post_data = (array) $post;
715 if ( isset( $post_data[ $property ] ) ) {
716 return $post_data[ $property ];
717 }
718
719 return $default_value;
720 }
721
722 // ====================================
723 // MODULES HELPERS
724 // ====================================
725
726 /**
727 * Get current post id
728 *
729 * @since 4.0
730 *
731 * @return int|string
732 */
733 public static function get_post_id() {
734 return get_post() ? get_the_ID() : '0';
735 }
736
737 /**
738 * Gets the a current user's property.
739 *
740 * @since 4.0.4
741 * @param string $property The user's property to be retrieved.
742 * @return string
743 */
744 public static function get_user_data( $property ) {
745 $current_user = wp_get_current_user();
746
747 if ( $current_user && $current_user->exists() ) {
748 return $current_user->get( $property );
749 }
750 return '';
751 }
752
753 /**
754 * Replace a key in an array without changing its order.
755 *
756 * @since 4.0
757 *
758 * @param string $old_key Old key.
759 * @param string $new_key New key.
760 * @param array $source_array Array.
761 * @return array
762 */
763 public static function replace_array_key( $old_key, $new_key, $source_array ) {
764
765 // Replace the name without changing the array's order.
766 $keys_array = array_keys( $source_array );
767 $index = array_search( $old_key, $keys_array, true );
768
769 if ( false === $index ) {
770 return $source_array;
771 }
772
773 $keys_array[ $index ] = $new_key;
774
775 $new_array = array_combine( $keys_array, array_values( $source_array ) );
776
777 return $new_array;
778 }
779
780 /**
781 * Get the display name of a module type.
782 *
783 * @since 4.0
784 *
785 * @param string $module_type Module type.
786 * @param boolean $plural Plural.
787 * @param boolean $capitalized Capitalized.
788 * @return string
789 */
790 public static function get_module_type_display_name( $module_type, $plural = false, $capitalized = false ) {
791
792 $display_name = '';
793
794 if ( Hustle_Module_Model::POPUP_MODULE === $module_type ) {
795 if ( ! $plural ) {
796 $display_name = __( 'pop-up', 'hustle' );
797 } else {
798 $display_name = __( 'pop-ups', 'hustle' );
799 }
800 } elseif ( Hustle_Module_Model::SLIDEIN_MODULE === $module_type ) {
801 if ( ! $plural ) {
802 $display_name = __( 'slide-in', 'hustle' );
803 } else {
804 $display_name = __( 'slide-ins', 'hustle' );
805 }
806 } elseif ( Hustle_Module_Model::EMBEDDED_MODULE === $module_type ) {
807 if ( ! $plural ) {
808 $display_name = __( 'embed', 'hustle' );
809 } else {
810 $display_name = __( 'embeds', 'hustle' );
811 }
812 } elseif ( Hustle_Module_Model::SOCIAL_SHARING_MODULE === $module_type ) {
813 if ( ! $plural ) {
814 $display_name = __( 'social sharing', 'hustle' );
815 } else {
816 $display_name = __( 'social shares', 'hustle' );
817 }
818 }
819
820 if ( $capitalized ) {
821 $display_name = ucwords( $display_name );
822 }
823
824 return esc_html( $display_name );
825 }
826
827 /**
828 * Get page templates
829 *
830 * @since 4.0.3
831 */
832 public static function hustle_get_page_templates() {
833 $templates = get_page_templates();
834 $page_templates = array();
835 foreach ( $templates as $template_name => $template_filename ) {
836 $page_templates[ $template_filename ] = $template_name;
837 }
838 return $page_templates;
839 }
840
841 /**
842 * Add special scripts for IE if it's detected
843 *
844 * @global bool $is_IE
845 * @global bool $is_edge
846 */
847 public static function maybe_add_scripts_for_ie() {
848 global $is_IE, $is_edge;
849
850 if ( $is_IE || $is_edge ) {
851 wp_enqueue_script(
852 'optin_admin_fitie',
853 Opt_In::$plugin_url . 'assets/js/vendor/fitie/fitie.js',
854 array(),
855 Opt_In::VERSION,
856 true
857 );
858 }
859 }
860
861 /**
862 * Check if WooCommerce is active or not
863 *
864 * @return bool
865 */
866 public static function is_woocommerce_active() {
867 return is_plugin_active( 'woocommerce/woocommerce.php' );
868 }
869
870 /**
871 * Check if Forminator is installed or not.
872 *
873 * @return bool
874 */
875 public static function is_forminator_installed() {
876 return file_exists( WP_PLUGIN_DIR . '/forminator/forminator.php' );
877 }
878
879 /**
880 * Gets the first key of an array.
881 *
882 * @since 4.0.0
883 *
884 * @param array $source_array Array.
885 * @return mixed
886 */
887 public static function array_key_first( array $source_array ) {
888 return $source_array ? array_keys( $source_array )[0] : null;
889 }
890
891 /**
892 * Get the global placeholders for display.
893 * The array's key has the placeholder value, that's what's inserted between
894 * brackets and then replaced by self::replace_global_placeholders().
895 * The array's value has the display name for the placeholder.
896 *
897 * @since 4.0.3
898 * @see Opt_In_Utils::replace_global_placeholders()
899 * @return array
900 */
901 public static function get_global_placeholders() {
902
903 $placeholders = array(
904 'site_url' => __( 'Site URL', 'hustle' ),
905 'site_name' => __( 'Site name', 'hustle' ),
906 'post_url' => __( 'Post/page URL', 'hustle' ),
907 'post_title' => __( 'Post/page title', 'hustle' ),
908 );
909
910 /**
911 * Filter the available global placeholders.
912 * These are used in some text fields, to be replaced by
913 * self::replace_global_placeholders().
914 *
915 * @since 4.0.3
916 * @see Opt_In_Utils::replace_global_placeholders()
917 * @return array
918 */
919 return apply_filters( 'hustle_get_global_placeholders', $placeholders );
920 }
921
922 /**
923 * Replace the global placeholders from a string.
924 * These are added to some text fields by the admin.
925 * The available ones are returned by self::get_global_placeholders().
926 *
927 * @since 4.0.3
928 * @see Opt_In_Utils::replace_global_placeholders()
929 * @param string $source_text String with placeholders to be replaced.
930 * @return string
931 */
932 public static function replace_global_placeholders( $source_text ) {
933
934 preg_match_all( '/\{[^}]*\}/', $source_text, $matches );
935
936 if ( ! empty( $matches[0] ) && is_array( $matches[0] ) ) {
937
938 $defined_placeholders = array(
939 '{site_url}' => site_url(),
940 '{site_name}' => get_bloginfo( 'name' ),
941 '{post_url}' => get_permalink(),
942 '{post_title}' => esc_html( get_the_title() ),
943 );
944
945 /**
946 * Filter the placeholders and their values.
947 * The keys of the array belong to the placeholder to be replaced.
948 * The values of the array belong to the value to use as replacement.
949 * Eg: [ '{post_url}' => get_permalink() ]
950 *
951 * @since 4.0.3
952 * @return array
953 */
954 $defined_placeholders = apply_filters( 'hustle_global_placeholders_to_replace', $defined_placeholders );
955
956 foreach ( $matches[0] as $placeholder ) {
957
958 if ( key_exists( $placeholder, $defined_placeholders ) ) {
959 $replacement = $defined_placeholders[ $placeholder ];
960
961 if ( $replacement !== $placeholder ) {
962 // Replace if we found something.
963 $source_text = str_replace( $placeholder, $replacement, $source_text );
964 }
965 }
966 }
967 }
968
969 return $source_text;
970 }
971
972 // Static stuff below.
973
974 /**
975 * Returns array of browsers
976 *
977 * @since 4.1
978 * @return array|mixed|null|void
979 */
980 public static function get_browsers() {
981
982 $browsers = array(
983 'chrome' => __( 'Chrome', 'hustle' ),
984 'firefox' => __( 'Firefox', 'hustle' ),
985 'safari' => __( 'Safari', 'hustle' ),
986 'edge' => __( 'Edge', 'hustle' ),
987 'MSIE' => __( 'Internet Explorer', 'hustle' ),
988 'opera' => __( 'Opera', 'hustle' ),
989 );
990
991 /**
992 * Filter the list of browsers
993 * Must return an associative array where the key is the browser's slug
994 * and the value is its display name.
995 *
996 * @since 4.1
997 */
998 return apply_filters( 'hustle_get_browsers_list', $browsers );
999 }
1000
1001 /**
1002 * Returns array of countries
1003 *
1004 * @return array|mixed|null|void
1005 */
1006 public static function get_countries() {
1007
1008 $countries = array(
1009 'AU' => __( 'Australia', 'hustle' ),
1010 'AF' => __( 'Afghanistan', 'hustle' ),
1011 'AL' => __( 'Albania', 'hustle' ),
1012 'DZ' => __( 'Algeria', 'hustle' ),
1013 'AS' => __( 'American Samoa', 'hustle' ),
1014 'AD' => __( 'Andorra', 'hustle' ),
1015 'AO' => __( 'Angola', 'hustle' ),
1016 'AI' => __( 'Anguilla', 'hustle' ),
1017 'AQ' => __( 'Antarctica', 'hustle' ),
1018 'AG' => __( 'Antigua and Barbuda', 'hustle' ),
1019 'AR' => __( 'Argentina', 'hustle' ),
1020 'AM' => __( 'Armenia', 'hustle' ),
1021 'AW' => __( 'Aruba', 'hustle' ),
1022 'AT' => __( 'Austria', 'hustle' ),
1023 'AZ' => __( 'Azerbaijan', 'hustle' ),
1024 'BS' => __( 'Bahamas', 'hustle' ),
1025 'BH' => __( 'Bahrain', 'hustle' ),
1026 'BD' => __( 'Bangladesh', 'hustle' ),
1027 'BB' => __( 'Barbados', 'hustle' ),
1028 'BY' => __( 'Belarus', 'hustle' ),
1029 'BE' => __( 'Belgium', 'hustle' ),
1030 'BZ' => __( 'Belize', 'hustle' ),
1031 'BJ' => __( 'Benin', 'hustle' ),
1032 'BM' => __( 'Bermuda', 'hustle' ),
1033 'BT' => __( 'Bhutan', 'hustle' ),
1034 'BO' => __( 'Bolivia', 'hustle' ),
1035 'BA' => __( 'Bosnia and Herzegovina', 'hustle' ),
1036 'BW' => __( 'Botswana', 'hustle' ),
1037 'BV' => __( 'Bouvet Island', 'hustle' ),
1038 'BR' => __( 'Brazil', 'hustle' ),
1039 'IO' => __( 'British Indian Ocean Territory', 'hustle' ),
1040 'BN' => __( 'Brunei', 'hustle' ),
1041 'BG' => __( 'Bulgaria', 'hustle' ),
1042 'BF' => __( 'Burkina Faso', 'hustle' ),
1043 'BI' => __( 'Burundi', 'hustle' ),
1044 'KH' => __( 'Cambodia', 'hustle' ),
1045 'CM' => __( 'Cameroon', 'hustle' ),
1046 'CA' => __( 'Canada', 'hustle' ),
1047 'CV' => __( 'Cape Verde', 'hustle' ),
1048 'KY' => __( 'Cayman Islands', 'hustle' ),
1049 'CF' => __( 'Central African Republic', 'hustle' ),
1050 'TD' => __( 'Chad', 'hustle' ),
1051 'CL' => __( 'Chile', 'hustle' ),
1052 'CN' => __( 'China, People\'s Republic of', 'hustle' ),
1053 'CX' => __( 'Christmas Island', 'hustle' ),
1054 'CC' => __( 'Cocos Islands', 'hustle' ),
1055 'CO' => __( 'Colombia', 'hustle' ),
1056 'KM' => __( 'Comoros', 'hustle' ),
1057 'CD' => __( 'Congo, Democratic Republic of the', 'hustle' ),
1058 'CG' => __( 'Congo, Republic of the', 'hustle' ),
1059 'CK' => __( 'Cook Islands', 'hustle' ),
1060 'CR' => __( 'Costa Rica', 'hustle' ),
1061 'CI' => __( 'Côte d\'Ivoire', 'hustle' ),
1062 'HR' => __( 'Croatia', 'hustle' ),
1063 'CU' => __( 'Cuba', 'hustle' ),
1064 'CW' => __( 'Curaçao', 'hustle' ),
1065 'CY' => __( 'Cyprus', 'hustle' ),
1066 'CZ' => __( 'Czech Republic', 'hustle' ),
1067 'DK' => __( 'Denmark', 'hustle' ),
1068 'DJ' => __( 'Djibouti', 'hustle' ),
1069 'DM' => __( 'Dominica', 'hustle' ),
1070 'DO' => __( 'Dominican Republic', 'hustle' ),
1071 'TL' => __( 'East Timor', 'hustle' ),
1072 'EC' => __( 'Ecuador', 'hustle' ),
1073 'EG' => __( 'Egypt', 'hustle' ),
1074 'SV' => __( 'El Salvador', 'hustle' ),
1075 'GQ' => __( 'Equatorial Guinea', 'hustle' ),
1076 'ER' => __( 'Eritrea', 'hustle' ),
1077 'EE' => __( 'Estonia', 'hustle' ),
1078 'ET' => __( 'Ethiopia', 'hustle' ),
1079 'FK' => __( 'Falkland Islands', 'hustle' ),
1080 'FO' => __( 'Faroe Islands', 'hustle' ),
1081 'FJ' => __( 'Fiji', 'hustle' ),
1082 'FI' => __( 'Finland', 'hustle' ),
1083 'FR' => __( 'France', 'hustle' ),
1084 'FX' => __( 'France, Metropolitan', 'hustle' ),
1085 'GF' => __( 'French Guiana', 'hustle' ),
1086 'PF' => __( 'French Polynesia', 'hustle' ),
1087 'TF' => __( 'French South Territories', 'hustle' ),
1088 'GA' => __( 'Gabon', 'hustle' ),
1089 'GM' => __( 'Gambia', 'hustle' ),
1090 'GE' => __( 'Georgia', 'hustle' ),
1091 'DE' => __( 'Germany', 'hustle' ),
1092 'GH' => __( 'Ghana', 'hustle' ),
1093 'GI' => __( 'Gibraltar', 'hustle' ),
1094 'GR' => __( 'Greece', 'hustle' ),
1095 'GL' => __( 'Greenland', 'hustle' ),
1096 'GD' => __( 'Grenada', 'hustle' ),
1097 'GP' => __( 'Guadeloupe', 'hustle' ),
1098 'GU' => __( 'Guam', 'hustle' ),
1099 'GT' => __( 'Guatemala', 'hustle' ),
1100 'GN' => __( 'Guinea', 'hustle' ),
1101 'GW' => __( 'Guinea-Bissau', 'hustle' ),
1102 'GY' => __( 'Guyana', 'hustle' ),
1103 'HT' => __( 'Haiti', 'hustle' ),
1104 'HM' => __( 'Heard Island And Mcdonald Island', 'hustle' ),
1105 'HN' => __( 'Honduras', 'hustle' ),
1106 'HK' => __( 'Hong Kong', 'hustle' ),
1107 'HU' => __( 'Hungary', 'hustle' ),
1108 'IS' => __( 'Iceland', 'hustle' ),
1109 'IN' => __( 'India', 'hustle' ),
1110 'ID' => __( 'Indonesia', 'hustle' ),
1111 'IR' => __( 'Iran', 'hustle' ),
1112 'IQ' => __( 'Iraq', 'hustle' ),
1113 'IE' => __( 'Ireland', 'hustle' ),
1114 'IL' => __( 'Israel', 'hustle' ),
1115 'IT' => __( 'Italy', 'hustle' ),
1116 'JM' => __( 'Jamaica', 'hustle' ),
1117 'JP' => __( 'Japan', 'hustle' ),
1118 'JT' => __( 'Johnston Island', 'hustle' ),
1119 'JO' => __( 'Jordan', 'hustle' ),
1120 'KZ' => __( 'Kazakhstan', 'hustle' ),
1121 'KE' => __( 'Kenya', 'hustle' ),
1122 'XK' => __( 'Kosovo', 'hustle' ),
1123 'KI' => __( 'Kiribati', 'hustle' ),
1124 'KP' => __( 'Korea, Democratic People\'s Republic of', 'hustle' ),
1125 'KR' => __( 'Korea, Republic of', 'hustle' ),
1126 'KW' => __( 'Kuwait', 'hustle' ),
1127 'KG' => __( 'Kyrgyzstan', 'hustle' ),
1128 'LA' => __( 'Lao People\'s Democratic Republic', 'hustle' ),
1129 'LV' => __( 'Latvia', 'hustle' ),
1130 'LB' => __( 'Lebanon', 'hustle' ),
1131 'LS' => __( 'Lesotho', 'hustle' ),
1132 'LR' => __( 'Liberia', 'hustle' ),
1133 'LY' => __( 'Libya', 'hustle' ),
1134 'LI' => __( 'Liechtenstein', 'hustle' ),
1135 'LT' => __( 'Lithuania', 'hustle' ),
1136 'LU' => __( 'Luxembourg', 'hustle' ),
1137 'MO' => __( 'Macau', 'hustle' ),
1138 'MK' => __( 'Macedonia', 'hustle' ),
1139 'MG' => __( 'Madagascar', 'hustle' ),
1140 'MW' => __( 'Malawi', 'hustle' ),
1141 'MY' => __( 'Malaysia', 'hustle' ),
1142 'MV' => __( 'Maldives', 'hustle' ),
1143 'ML' => __( 'Mali', 'hustle' ),
1144 'MT' => __( 'Malta', 'hustle' ),
1145 'MH' => __( 'Marshall Islands', 'hustle' ),
1146 'MQ' => __( 'Martinique', 'hustle' ),
1147 'MR' => __( 'Mauritania', 'hustle' ),
1148 'MU' => __( 'Mauritius', 'hustle' ),
1149 'YT' => __( 'Mayotte', 'hustle' ),
1150 'MX' => __( 'Mexico', 'hustle' ),
1151 'FM' => __( 'Micronesia', 'hustle' ),
1152 'MD' => __( 'Moldova', 'hustle' ),
1153 'MC' => __( 'Monaco', 'hustle' ),
1154 'MN' => __( 'Mongolia', 'hustle' ),
1155 'ME' => __( 'Montenegro', 'hustle' ),
1156 'MS' => __( 'Montserrat', 'hustle' ),
1157 'MA' => __( 'Morocco', 'hustle' ),
1158 'MZ' => __( 'Mozambique', 'hustle' ),
1159 'MM' => __( 'Myanmar', 'hustle' ),
1160 'NA' => __( 'Namibia', 'hustle' ),
1161 'NR' => __( 'Nauru', 'hustle' ),
1162 'NP' => __( 'Nepal', 'hustle' ),
1163 'NL' => __( 'Netherlands', 'hustle' ),
1164 'AN' => __( 'Netherlands Antilles', 'hustle' ),
1165 'NC' => __( 'New Caledonia', 'hustle' ),
1166 'NZ' => __( 'New Zealand', 'hustle' ),
1167 'NI' => __( 'Nicaragua', 'hustle' ),
1168 'NE' => __( 'Niger', 'hustle' ),
1169 'NG' => __( 'Nigeria', 'hustle' ),
1170 'NU' => __( 'Niue', 'hustle' ),
1171 'NF' => __( 'Norfolk Island', 'hustle' ),
1172 'MNP' => __( 'Northern Mariana Islands', 'hustle' ),
1173 'MP' => __( 'Mariana Islands, Northern', 'hustle' ),
1174 'NO' => __( 'Norway', 'hustle' ),
1175 'OM' => __( 'Oman', 'hustle' ),
1176 'PK' => __( 'Pakistan', 'hustle' ),
1177 'PW' => __( 'Palau', 'hustle' ),
1178 'PS' => __( 'Palestine, State of', 'hustle' ),
1179 'PA' => __( 'Panama', 'hustle' ),
1180 'PG' => __( 'Papua New Guinea', 'hustle' ),
1181 'PY' => __( 'Paraguay', 'hustle' ),
1182 'PE' => __( 'Peru', 'hustle' ),
1183 'PH' => __( 'Philippines', 'hustle' ),
1184 'PN' => __( 'Pitcairn Islands', 'hustle' ),
1185 'PL' => __( 'Poland', 'hustle' ),
1186 'PT' => __( 'Portugal', 'hustle' ),
1187 'PR' => __( 'Puerto Rico', 'hustle' ),
1188 'QA' => __( 'Qatar', 'hustle' ),
1189 'RE' => __( 'Réunion', 'hustle' ),
1190 'RO' => __( 'Romania', 'hustle' ),
1191 'RU' => __( 'Russia', 'hustle' ),
1192 'RW' => __( 'Rwanda', 'hustle' ),
1193 'SH' => __( 'Saint Helena', 'hustle' ),
1194 'KN' => __( 'Saint Kitts and Nevis', 'hustle' ),
1195 'LC' => __( 'Saint Lucia', 'hustle' ),
1196 'PM' => __( 'Saint Pierre and Miquelon', 'hustle' ),
1197 'VC' => __( 'Saint Vincent and the Grenadines', 'hustle' ),
1198 'WS' => __( 'Samoa', 'hustle' ),
1199 'SM' => __( 'San Marino', 'hustle' ),
1200 'ST' => __( 'Sao Tome and Principe', 'hustle' ),
1201 'SA' => __( 'Saudi Arabia', 'hustle' ),
1202 'SN' => __( 'Senegal', 'hustle' ),
1203 'CS' => __( 'Serbia', 'hustle' ),
1204 'SC' => __( 'Seychelles', 'hustle' ),
1205 'SL' => __( 'Sierra Leone', 'hustle' ),
1206 'SG' => __( 'Singapore', 'hustle' ),
1207 'MF' => __( 'Sint Maarten', 'hustle' ),
1208 'SK' => __( 'Slovakia', 'hustle' ),
1209 'SI' => __( 'Slovenia', 'hustle' ),
1210 'SB' => __( 'Solomon Islands', 'hustle' ),
1211 'SO' => __( 'Somalia', 'hustle' ),
1212 'ZA' => __( 'South Africa', 'hustle' ),
1213 'GS' => __( 'South Georgia and the South Sandwich Islands', 'hustle' ),
1214 'ES' => __( 'Spain', 'hustle' ),
1215 'LK' => __( 'Sri Lanka', 'hustle' ),
1216 'XX' => __( 'Stateless Persons', 'hustle' ),
1217 'SD' => __( 'Sudan', 'hustle' ),
1218 'SS' => __( 'South Sudan', 'hustle' ),
1219 'SR' => __( 'Suriname', 'hustle' ),
1220 'SJ' => __( 'Svalbard and Jan Mayen', 'hustle' ),
1221 'SZ' => __( 'Swaziland', 'hustle' ),
1222 'SE' => __( 'Sweden', 'hustle' ),
1223 'CH' => __( 'Switzerland', 'hustle' ),
1224 'SY' => __( 'Syria', 'hustle' ),
1225 'TW' => __( 'Taiwan, Republic of China', 'hustle' ),
1226 'TJ' => __( 'Tajikistan', 'hustle' ),
1227 'TZ' => __( 'Tanzania', 'hustle' ),
1228 'TH' => __( 'Thailand', 'hustle' ),
1229 'TG' => __( 'Togo', 'hustle' ),
1230 'TK' => __( 'Tokelau', 'hustle' ),
1231 'TO' => __( 'Tonga', 'hustle' ),
1232 'TT' => __( 'Trinidad and Tobago', 'hustle' ),
1233 'TN' => __( 'Tunisia', 'hustle' ),
1234 'TR' => __( 'Turkey', 'hustle' ),
1235 'TM' => __( 'Turkmenistan', 'hustle' ),
1236 'TC' => __( 'Turks and Caicos Islands', 'hustle' ),
1237 'TV' => __( 'Tuvalu', 'hustle' ),
1238 'UG' => __( 'Uganda', 'hustle' ),
1239 'UA' => __( 'Ukraine', 'hustle' ),
1240 'AE' => __( 'United Arab Emirates', 'hustle' ),
1241 'GB' => __( 'United Kingdom', 'hustle' ),
1242 'US' => __( 'United States of America (USA)', 'hustle' ),
1243 'UM' => __( 'US Minor Outlying Islands', 'hustle' ),
1244 'UY' => __( 'Uruguay', 'hustle' ),
1245 'UZ' => __( 'Uzbekistan', 'hustle' ),
1246 'VU' => __( 'Vanuatu', 'hustle' ),
1247 'VA' => __( 'Vatican City', 'hustle' ),
1248 'VE' => __( 'Venezuela', 'hustle' ),
1249 'VN' => __( 'Vietnam', 'hustle' ),
1250 'VG' => __( 'Virgin Islands, British', 'hustle' ),
1251 'VI' => __( 'Virgin Islands, U.S.', 'hustle' ),
1252 'WF' => __( 'Wallis And Futuna', 'hustle' ),
1253 'EH' => __( 'Western Sahara', 'hustle' ),
1254 'YE' => __( 'Yemen', 'hustle' ),
1255 'ZM' => __( 'Zambia', 'hustle' ),
1256 'ZW' => __( 'Zimbabwe', 'hustle' ),
1257 );
1258
1259 // Deprecated.
1260 $countries = apply_filters_deprecated( 'opt_in-country-list', array( $countries ), '4.6.0', 'opt_in_country_list' );
1261 /**
1262 * Returns a list with countries
1263 * Must be an associative array where the key is the country code
1264 * and its value is its display name.
1265 */
1266 return apply_filters( 'opt_in_country_list', $countries );
1267 }
1268
1269 /**
1270 * Get HTML for notice about using cookies
1271 */
1272 public static function get_cookie_saving_notice() {
1273 ?>
1274 <div class="sui-notice">
1275 <div class="sui-notice-content">
1276 <div class="sui-notice-message">
1277
1278 <span class="sui-notice-icon sui-icon-info sui-md" aria-hidden="true"></span>
1279 <p style="margin-top: 0;"><?php esc_html_e( 'Note: When enabled, this will set a tracking cookie in your visitor’s web browser.', 'hustle' ); ?></p>
1280
1281 </div>
1282 </div>
1283 </div>
1284 <?php
1285 }
1286
1287 /**
1288 * Check if static cache is enabled
1289 *
1290 * @return boolean
1291 */
1292 public static function is_static_cache_enabled() {
1293 if ( ! is_null( self::$static_cache ) ) {
1294 return self::$static_cache;
1295 }
1296
1297 if ( defined( 'HUSTLE_STATIC_CACHE_ENABLED' ) ) {
1298 self::$static_cache = HUSTLE_STATIC_CACHE_ENABLED;
1299 } elseif ( apply_filters( 'wp_hummingbird_is_active_module_page_cache', false ) ) {
1300 self::$static_cache = true;
1301 } else {
1302 self::$static_cache = self::is_hub_cache();
1303 }
1304
1305 return self::$static_cache;
1306 }
1307
1308 /**
1309 * Is Static Server Cache enabled on HUB or not
1310 *
1311 * @return boolean
1312 */
1313 private static function is_hub_cache() {
1314 $key_option = 'hustle_hub_cache_enabled';
1315 $cache = get_site_transient( $key_option );
1316
1317 if ( false === $cache ) {
1318 $cache = self::is_hub_cache_enabled();
1319 set_site_transient( $key_option, (int) $cache, DAY_IN_SECONDS );
1320 }
1321
1322 return (bool) $cache;
1323 }
1324
1325 /**
1326 * Check if Static Server Cache is enabled on HUB
1327 *
1328 * @return boolean
1329 */
1330 private static function is_hub_cache_enabled() {
1331 return (bool) self::get_hosting_feature( 'static_cache' );
1332 }
1333
1334 /**
1335 * Get list of hosting features and their status
1336 *
1337 * @param string $name The name of the hosting feature to check.
1338 * @return mixed The status of the hosting feature, or an empty string if not found.
1339 */
1340 private static function get_hosting_feature( $name ) {
1341 if ( function_exists( 'wpmudev_hosting_features' ) ) {
1342 $states = wpmudev_hosting_features();
1343 return isset( $states[ $name ] ) ? $states[ $name ] : '';
1344 }
1345
1346 return '';
1347 }
1348
1349 /**
1350 * Get branded plugin name
1351 *
1352 * @return string
1353 */
1354 public static function get_plugin_name() {
1355 if ( is_null( self::$plugin_name ) ) {
1356 $branding_plugin_name = self::get_branding_plugin_name();
1357 if ( $branding_plugin_name ) {
1358 $plugin_name = $branding_plugin_name;
1359 } elseif ( self::is_free() ) {
1360 $plugin_name = __( 'Hustle', 'hustle' );
1361 } else {
1362 $plugin_name = __( 'Hustle Pro', 'hustle' );
1363 }
1364
1365 self::$plugin_name = $plugin_name;
1366 }
1367
1368 return self::$plugin_name;
1369 }
1370
1371 /**
1372 * Get branding plugin name
1373 *
1374 * @return null|string
1375 */
1376 private static function get_branding_plugin_name() {
1377 if ( ! class_exists( 'WPMUDEV_Dashboard' )
1378 || empty( WPMUDEV_Dashboard::$whitelabel )
1379 || ! method_exists( WPMUDEV_Dashboard::$whitelabel, 'get_settings' ) ) {
1380 return;
1381 }
1382 $settings = WPMUDEV_Dashboard::$whitelabel->get_settings();
1383 if ( empty( $settings['enabled'] ) || true !== $settings['enabled']
1384 || empty( $settings['labels_config'][1107020]['name'] ) ) {
1385 return;
1386 }
1387
1388 return $settings['labels_config'][1107020]['name'];
1389 }
1390
1391 /**
1392 * Build notification response
1393 *
1394 * @param string $type The type of notification (success, error, etc.).
1395 * @param string $message The notification message.
1396 * @return array The notification response.
1397 */
1398 public static function build_notification( $type, $message ) {
1399 return array(
1400 'action' => 'notification',
1401 'status' => $type,
1402 'message' => $message,
1403 );
1404 }
1405
1406 /**
1407 * Get HUB API key
1408 *
1409 * @return string
1410 */
1411 public static function get_hub_api_key() {
1412 if ( ! class_exists( 'WPMUDEV_Dashboard' ) ) {
1413 return '';
1414 }
1415
1416 if (
1417 WPMUDEV_Dashboard::$api &&
1418 WPMUDEV_Dashboard::$api->has_key()
1419 ) {
1420 return WPMUDEV_Dashboard::$api->get_key();
1421 }
1422
1423 return '';
1424 }
1425 }
1426