PluginProbe
Formidable Forms – WordPress Form Builder for Contact Forms, Calculators, Quizzes & More / 6.12.1
Formidable Forms – WordPress Form Builder for Contact Forms, Calculators, Quizzes & More v6.12.1
6.35 6.34 6.33.1 6.33 6.32.1 6.32 6.31 6.25 6.25.1 6.26 6.26.1 6.27 6.28 6.29 6.3 6.3.1 6.3.2 6.30 6.4 6.4.1 6.4.2 6.5 6.5.1 6.5.2 6.5.3 All 141 releases
← All changes | classes/controllers/FrmAddonsController.php +352 -206 6.36.12.1 View file →
@@ -5,9 +5,9 @@
5 5
6 6 class FrmAddonsController {
7 7
8 8 /**
9 - * @var string $plugin
9 + * @var string
10 10 */
11 11 protected static $plugin;
12 12
13 13 /**
@@ -18,12 +18,15 @@
18 18 return;
19 19 }
20 20
21 21 $label = __( 'Add-Ons', 'formidable' );
22 - $label = '<span style="color:#fe5a1d">' . $label . '</span>';
22 + $label = '<span style="color:#1da867">' . $label . '</span>';
23 23
24 24 add_submenu_page( 'formidable', 'Formidable | ' . __( 'Add-Ons', 'formidable' ), $label, 'frm_view_forms', 'formidable-addons', 'FrmAddonsController::list_addons' );
25 25
26 + // remove default created subpage, make the page with highest priority as default.
27 + remove_submenu_page( 'formidable', 'formidable' );
28 +
26 29 if ( ! FrmAppHelper::pro_is_installed() ) {
27 30 add_submenu_page(
28 31 'formidable',
29 32 'Formidable | ' . __( 'Upgrade', 'formidable' ),
@@ -49,15 +52,15 @@
49 52 $addons = self::get_api_addons();
50 53 $errors = array();
51 54
52 55 if ( isset( $addons['error'] ) ) {
53 - $api = new FrmFormApi();
54 - $errors = $api->get_error_from_response( $addons );
56 + $api = new FrmFormApi();
57 + $errors = $api->get_error_from_response( $addons );
55 58 $license_type = isset( $addons['error']['type'] ) ? $addons['error']['type'] : '';
56 59 unset( $addons['error'] );
57 60 }
58 61
59 - $pro = array(
62 + $pro = array(
60 63 'pro' => array(
61 64 'title' => 'Formidable Forms Pro',
62 65 'slug' => 'formidable-pro',
63 66 'released' => '2011-02-05',
@@ -69,9 +72,9 @@
69 72 self::prepare_addons( $addons );
70 73
71 74 $pricing = FrmAppHelper::admin_upgrade_link( 'addons' );
72 75
73 - include( FrmAppHelper::plugin_path() . '/classes/views/addons/list.php' );
76 + include FrmAppHelper::plugin_path() . '/classes/views/addons/list.php';
74 77 }
75 78
76 79 /**
77 80 * @return void
@@ -85,9 +88,9 @@
85 88 }
86 89
87 90 ksort( $plugins );
88 91
89 - include( FrmAppHelper::plugin_path() . '/classes/views/addons/settings.php' );
92 + include FrmAppHelper::plugin_path() . '/classes/views/addons/settings.php';
90 93 }
91 94
92 95 /**
93 96 * @return array
@@ -109,8 +112,21 @@
109 112 return $addons;
110 113 }
111 114
112 115 /**
116 + * Retrieves the count of available addons.
117 + *
118 + * @since 6.9
119 + *
120 + * @return int Count of addons.
121 + */
122 + public static function get_addons_count() {
123 + $addons = self::get_api_addons();
124 +
125 + return count( $addons );
126 + }
127 +
128 + /**
113 129 * If the API is unable to connect, show something on the addons page
114 130 *
115 131 * @since 3.04.03
116 132 * @return array
@@ -272,8 +288,10 @@
272 288 }
273 289
274 290 /**
275 291 * @since 4.0.01
292 + *
293 + * @return bool
276 294 */
277 295 public static function is_license_expired() {
278 296 $version_info = self::get_primary_license_info();
279 297 if ( ! isset( $version_info['error'] ) ) {
@@ -279,30 +297,29 @@
279 297 if ( ! isset( $version_info['error'] ) ) {
280 298 return false;
281 299 }
282 300
283 - return $version_info['error'];
284 - }
301 + $expires = isset( $version_info['error']['expires'] ) ? $version_info['error']['expires'] : 0;
302 + if ( empty( $expires ) || $expires > time() ) {
303 + return false;
304 + }
285 305
286 - /**
287 - * @since 4.08
288 - *
289 - * @return boolean|int false or the number of days until expiration.
290 - */
291 - public static function is_license_expiring() {
292 - if ( is_callable( 'FrmProAddonsController::is_license_expiring' ) ) {
293 - return FrmProAddonsController::is_license_expiring();
306 + $rate_limited = ! empty( $version_info['response_code'] ) && 429 === (int) $version_info['response_code'];
307 + if ( $rate_limited ) {
308 + // Do not return false positives for rate limited responses.
309 + return false;
294 310 }
295 311
296 - return false;
312 + return $version_info['error'];
297 313 }
298 314
299 315 /**
300 316 * @since 4.08
317 + * @since 6.7 This is public.
301 318 *
302 319 * @return array|false
303 320 */
304 - protected static function get_primary_license_info() {
321 + public static function get_primary_license_info() {
305 322 $installed_addons = apply_filters( 'frm_installed_addons', array() );
306 323 if ( empty( $installed_addons ) || ! isset( $installed_addons['formidable_pro'] ) ) {
307 324 return false;
308 325 }
@@ -334,9 +351,9 @@
334 351 $version_info = self::fill_update_addon_info( $installed_addons );
335 352 $transient->last_checked = time();
336 353 $wp_plugins = self::get_plugins();
337 354
338 - foreach ( $version_info as $id => $plugin ) {
355 + foreach ( $version_info as $plugin ) {
339 356 $plugin = (object) $plugin;
340 357
341 358 if ( ! isset( $plugin->new_version ) || ! isset( $plugin->package ) ) {
342 359 continue;
@@ -351,20 +368,21 @@
351 368 // don't show an update if the plugin isn't installed
352 369 continue;
353 370 }
354 371
355 - $wp_plugin = isset( $wp_plugins[ $folder ] ) ? $wp_plugins[ $folder ] : array();
356 - $wp_version = isset( $wp_plugin['Version'] ) ? $wp_plugin['Version'] : '1.0';
372 + $wp_plugin = isset( $wp_plugins[ $folder ] ) ? $wp_plugins[ $folder ] : array();
373 + $wp_version = isset( $wp_plugin['Version'] ) ? $wp_plugin['Version'] : '1.0';
374 + $plugin->slug = explode( '/', $folder )[0];
357 375
358 376 if ( version_compare( $wp_version, $plugin->new_version, '<' ) ) {
359 - $slug = explode( '/', $folder );
360 - $plugin->slug = $slug[0];
361 377 $transient->response[ $folder ] = $plugin;
378 + } else {
379 + $transient->no_update[ $folder ] = $plugin;
362 380 }
363 381
364 382 $transient->checked[ $folder ] = $wp_version;
365 383
366 - }
384 + }//end foreach
367 385
368 386 return $transient;
369 387 }
370 388
@@ -387,9 +405,9 @@
387 405 * Check if a plugin is installed before showing an update for it
388 406 *
389 407 * @since 3.05
390 408 *
391 - * @param string $plugin - the folder/filename.php for a plugin
409 + * @param string $plugin The folder/filename.php for a plugin.
392 410 *
393 411 * @return bool - True if installed
394 412 */
395 413 protected static function is_installed( $plugin ) {
@@ -444,9 +462,9 @@
444 462 'code' => $addon_info['error']['code'],
445 463 );
446 464 }
447 465 }
448 - }
466 + }//end foreach
449 467
450 468 return $version_info;
451 469 }
452 470
@@ -453,9 +471,9 @@
453 471 /**
454 472 * Get the action link for an addon that isn't active.
455 473 *
456 474 * @since 3.06.03
457 - * @param string $plugin The plugin slug
475 + * @param string $plugin The plugin slug.
458 476 * @return array
459 477 */
460 478 public static function install_link( $plugin ) {
461 479 $link = array();
@@ -466,14 +484,14 @@
466 484 $link = array(
467 485 'url' => $addon['plugin'],
468 486 'class' => 'frm-activate-addon',
469 487 );
470 - } elseif ( isset( $addon['url'] ) && ! empty( $addon['url'] ) ) {
488 + } elseif ( ! empty( $addon['url'] ) ) {
471 489 $link = array(
472 490 'url' => $addon['url'],
473 491 'class' => 'frm-install-addon',
474 492 );
475 - } elseif ( isset( $addon['categories'] ) && ! empty( $addon['categories'] ) ) {
493 + } elseif ( ! empty( $addon['categories'] ) ) {
476 494 $link = array(
477 495 'categories' => $addon['categories'],
478 496 );
479 497 }
@@ -485,9 +503,9 @@
485 503 $link = array(
486 504 'url' => 'formidable-' . $plugin . '/formidable-' . $plugin . '.php',
487 505 'class' => 'frm-activate-addon',
488 506 );
489 - }
507 + }//end if
490 508
491 509 return $link;
492 510 }
493 511
@@ -492,12 +510,12 @@
492 510 }
493 511
494 512 /**
495 513 * @since 4.09
496 - * @param string $plugin The plugin slug
514 + * @param string $plugin The plugin slug.
497 515 * @return array|false
498 516 */
499 - protected static function get_addon( $plugin ) {
517 + public static function get_addon( $plugin ) {
500 518 $addons = self::get_api_addons();
501 519 self::prepare_addons( $addons );
502 520 foreach ( $addons as $addon ) {
503 521 $slug = explode( '/', $addon['plugin'] );
@@ -523,10 +541,10 @@
523 541
524 542 /**
525 543 * @since 3.04.03
526 544 *
527 - * @param array $addons
528 - * @param object $license The FrmAddon object
545 + * @param array $addons
546 + * @param object $license The FrmAddon object.
529 547 *
530 548 * @return array
531 549 */
532 550 public static function get_addon_for_license( $addons, $license ) {
@@ -533,9 +551,9 @@
533 551 $download_id = $license->download_id;
534 552 $plugin = array();
535 553 if ( empty( $download_id ) && ! empty( $addons ) ) {
536 554 foreach ( $addons as $addon ) {
537 - if ( strtolower( $license->plugin_name ) == strtolower( $addon['title'] ) ) {
555 + if ( strtolower( $license->plugin_name ) === strtolower( $addon['title'] ) ) {
538 556 return $addon;
539 557 }
540 558 }
541 559 } elseif ( isset( $addons[ $download_id ] ) ) {
@@ -603,9 +621,9 @@
603 621 self::prepare_addon_link( $addon['link'] );
604 622
605 623 self::set_addon_status( $addon );
606 624 $addons[ $id ] = $addon;
607 - }
625 + }//end foreach
608 626 }
609 627
610 628 /**
611 629 * @return bool
@@ -617,9 +635,9 @@
617 635 return is_plugin_active( $file_name );
618 636 }
619 637
620 638 /**
621 - * @return string|false either 'visual-views' or 'views', false if one is not found.
639 + * @return false|string either 'visual-views' or 'views', false if one is not found.
622 640 */
623 641 private static function get_active_views_version() {
624 642 if ( ! is_callable( 'FrmViewsAppHelper::plugin_version' ) ) {
625 643 return false;
@@ -685,9 +703,9 @@
685 703 'content' => 'button',
686 704 );
687 705
688 706 $features = array(
689 - 'Display Entries' => array(
707 + 'Display Entries' => array(
690 708 array(
691 709 'label' => 'Display form data with virtually limitless views',
692 710 'link' => array(
693 711 'content' => 'views',
@@ -737,9 +755,9 @@
737 755 'label' => 'Export your entries to a CSV',
738 756 'lite' => true,
739 757 ),
740 758 ),
741 - 'Form Building' => array(
759 + 'Form Building' => array(
742 760 array(
743 761 'label' => 'Save a calculated value into a field',
744 762 'link' => array(
745 763 'content' => 'calculations',
@@ -823,9 +841,9 @@
823 841 'label' => 'Use input placeholder text in your fields that clear when typing starts.',
824 842 'lite' => true,
825 843 ),
826 844 ),
827 - 'Form Actions' => array(
845 + 'Form Actions' => array(
828 846 array(
829 847 'label' => 'Conditionally send your email notifications based on values in your form',
830 848 'link' => array(
831 849 'content' => 'conditional-emails',
@@ -848,9 +866,9 @@
848 866 ),
849 867 'lite' => true,
850 868 ),
851 869 ),
852 - 'Form Appearance' => array(
870 + 'Form Appearance' => array(
853 871 array(
854 872 'label' => 'Create Multiple styles for different forms',
855 873 'link' => array(
856 874 'content' => 'multiple-styles',
@@ -880,57 +898,68 @@
880 898 ),
881 899 ),
882 900 );
883 901
884 - include( FrmAppHelper::plugin_path() . '/classes/views/addons/upgrade_to_pro.php' );
902 + include FrmAppHelper::plugin_path() . '/classes/views/addons/upgrade_to_pro.php';
885 903 }
886 904
887 905 /**
888 - * Install Pro after connection with Formidable.
906 + * @since 5.5.2
889 907 *
890 - * @since 4.02.05
908 + * @param string $plugin
909 + * @param string $redirect
910 + * @param bool $network_wide
911 + * @param bool $silent
912 + * @return WP_Error|null Null on success, WP_Error on invalid file.
913 + */
914 + protected static function activate_plugin( $plugin, $redirect = '', $network_wide = false, $silent = false ) {
915 + if ( ! function_exists( 'activate_plugin' ) ) {
916 + require_once ABSPATH . 'wp-admin/includes/plugin.php';
917 + }
918 + return activate_plugin( $plugin, $redirect, $network_wide, $silent );
919 + }
920 +
921 + /**
922 + * Deactivate a specified plugin.
891 923 *
924 + * @since 6.8
925 + *
926 + * @param string $plugin
927 + * @param bool $silent
892 928 * @return void
893 929 */
894 - public static function connect_pro() {
895 - FrmAppHelper::permission_check( 'install_plugins' );
896 - check_ajax_referer( 'frm_ajax', 'nonce' );
897 -
898 - $url = self::get_current_plugin();
899 - if ( FrmAppHelper::pro_is_installed() || empty( $url ) ) {
900 - wp_die();
930 + protected static function deactivate_plugin( $plugin, $silent = false ) {
931 + if ( ! function_exists( 'deactivate_plugins' ) ) {
932 + require_once ABSPATH . 'wp-admin/includes/plugin.php';
901 933 }
902 -
903 - $response = array();
904 -
905 - // It's already installed and active.
906 - $active = self::activate_plugin( 'formidable-pro/formidable-pro.php', false, false, true );
907 - if ( is_wp_error( $active ) ) {
908 - // The plugin was installed, but not active. Download it now.
909 - self::ajax_install_addon();
910 - } else {
911 - $response['active'] = true;
912 - $response['success'] = true;
913 - }
914 -
915 - echo json_encode( $response );
916 - wp_die();
934 + deactivate_plugins( $plugin, $silent );
917 935 }
918 936
919 937 /**
920 - * @since 5.5.2
938 + * Uninstall a specified plugin.
921 939 *
940 + * @since 6.8
941 + *
922 942 * @param string $plugin
923 - * @param string $redirect
924 - * @param bool $network_wide
925 - * @param bool $silent
926 - * @return null|WP_Error Null on success, WP_Error on invalid file.
943 + * @return true|WP_Error True on success, WP_Error on invalid file.
927 944 */
928 - protected static function activate_plugin( $plugin, $redirect = '', $network_wide = false, $silent = false ) {
929 - if ( ! function_exists( 'activate_plugin' ) ) {
945 + protected static function uninstall_plugin( $plugin ) {
946 + if ( ! current_user_can( 'delete_plugins' ) ) {
947 + return new WP_Error( 'uninstall_failed', __( 'Current user cannot delete plugins.', 'formidable' ) );
948 + }
949 +
950 + if ( ! function_exists( 'delete_plugins' ) ) {
930 951 require_once ABSPATH . 'wp-admin/includes/plugin.php';
931 952 }
932 - return activate_plugin( $plugin, $redirect, $network_wide, $silent );
953 +
954 + self::deactivate_plugin( $plugin, true );
955 + $result = delete_plugins( array( $plugin ) );
956 +
957 + if ( is_wp_error( $result ) ) {
958 + return $result;
959 + }
960 +
961 + return true;
933 962 }
934 963
935 964 /**
936 965 * @since 5.0.10
@@ -937,9 +966,9 @@
937 966 *
938 967 * @return string
939 968 */
940 969 protected static function get_current_plugin() {
941 - if ( ! isset( self::$plugin ) ) {
970 + if ( empty( self::$plugin ) ) {
942 971 self::$plugin = FrmAppHelper::get_param( 'plugin', '', 'post', 'esc_url_raw' );
943 972 }
944 973 return self::$plugin;
945 974 }
@@ -945,8 +974,10 @@
945 974 }
946 975
947 976 /**
948 977 * @since 4.08
978 + *
979 + * @return array|void
949 980 */
950 981 protected static function download_and_activate() {
951 982 if ( is_admin() ) {
952 983 FrmAppHelper::set_current_screen_and_hook_suffix();
@@ -957,9 +988,9 @@
957 988 $installed = self::install_addon();
958 989 if ( is_array( $installed ) && isset( $installed['message'] ) ) {
959 990 return $installed;
960 991 }
961 - self::maybe_activate_addon( $installed );
992 + self::handle_addon_action( $installed, 'activate' );
962 993 }
963 994
964 995 /**
965 996 * @since 3.04.02
@@ -967,9 +998,9 @@
967 998 * @return void
968 999 */
969 1000 protected static function maybe_show_cred_form() {
970 1001 if ( ! function_exists( 'request_filesystem_credentials' ) ) {
971 - include_once( ABSPATH . 'wp-admin/includes/file.php' );
1002 + include_once ABSPATH . 'wp-admin/includes/file.php';
972 1003 }
973 1004
974 1005 // Start output bufferring to catch the filesystem form if credentials are needed.
975 1006 ob_start();
@@ -1011,12 +1042,9 @@
1011 1042 *
1012 1043 * @return bool
1013 1044 */
1014 1045 public static function url_is_allowed( $download_url ) {
1015 - return (
1016 - FrmAppHelper::validate_url_is_in_s3_bucket( $download_url, 'zip' ) ||
1017 - ( strpos( $download_url, 'https://downloads.wordpress.org/plugin' ) === 0 && substr_compare( $download_url, '.zip', -4 ) === 0 )
1018 - );
1046 + return FrmAppHelper::validate_url_is_in_s3_bucket( $download_url, 'zip' ) || in_array( $download_url, self::allowed_external_urls(), true );
1019 1047 }
1020 1048
1021 1049 /**
1022 1050 * We do not need any extra credentials if we have gotten this far,
@@ -1053,33 +1081,139 @@
1053 1081 return $plugin;
1054 1082 }
1055 1083
1056 1084 /**
1057 - * @since 3.06.03
1085 + * Handle the AJAX request to activate an add-on.
1058 1086 *
1087 + * @since 6.8
1088 + *
1059 1089 * @return void
1060 1090 */
1061 1091 public static function ajax_activate_addon() {
1092 + self::process_addon_action(
1093 + function ( $plugin ) {
1094 + return self::handle_addon_action( $plugin, 'activate' );
1095 + },
1096 + array( 'FrmAddonsController', 'get_addon_activation_response' )
1097 + );
1098 + }
1062 1099
1100 + /**
1101 + * @since 3.04.02
1102 + *
1103 + * @param string $installed The plugin folder name with file name.
1104 + */
1105 + protected static function maybe_activate_addon( $installed ) {
1106 + self::ajax_activate_addon();
1107 + }
1108 +
1109 + /**
1110 + * Handle the AJAX request to deactivate an add-on.
1111 + *
1112 + * @since 6.8
1113 + *
1114 + * @return void
1115 + */
1116 + public static function ajax_deactivate_addon() {
1117 + self::process_addon_action(
1118 + function ( $plugin ) {
1119 + return self::handle_addon_action( $plugin, 'deactivate' );
1120 + }
1121 + );
1122 + }
1123 +
1124 + /**
1125 + * Handle the AJAX request to uninstall an add-on.
1126 + *
1127 + * @since 6.8
1128 + *
1129 + * @return void
1130 + */
1131 + public static function ajax_uninstall_addon() {
1132 + self::process_addon_action(
1133 + function ( $plugin ) {
1134 + return self::handle_addon_action( $plugin, 'uninstall' );
1135 + }
1136 + );
1137 + }
1138 +
1139 + /**
1140 + * Process a specific action (activate, deactivate, uninstall) on an add-on.
1141 + *
1142 + * @since 6.8
1143 + *
1144 + * @param callable $action_callback The specific add-on action to be executed.
1145 + * @param callable|null $response_callback Optional. The response handling callback. Default null.
1146 + * @return void
1147 + */
1148 + private static function process_addon_action( $action_callback, $response_callback = null ) {
1063 1149 self::install_addon_permissions();
1064 -
1065 1150 FrmAppHelper::set_current_screen_and_hook_suffix();
1066 1151
1067 1152 $plugin = FrmAppHelper::get_param( 'plugin', '', 'post', 'sanitize_text_field' );
1068 - self::maybe_activate_addon( $plugin );
1153 + call_user_func( $action_callback, $plugin );
1069 1154
1070 - echo json_encode( self::get_addon_activation_response() );
1071 - wp_die();
1155 + if ( is_callable( $response_callback ) ) {
1156 + wp_send_json_success( call_user_func( $response_callback ) );
1157 + return;
1158 + }
1159 +
1160 + wp_send_json_success();
1072 1161 }
1073 1162
1074 1163 /**
1164 + * Attempt to perform a specific action (activate, deactivate, uninstall) on an add-on.
1165 + *
1166 + * @since 6.8
1167 + *
1168 + * @param string $installed The plugin folder name with file name.
1169 + * @param string $action The action type ('activate', 'deactivate', 'uninstall').
1170 + * @return array|void
1171 + */
1172 + protected static function handle_addon_action( $installed, $action ) {
1173 + if ( ! $installed || ! $action ) {
1174 + return;
1175 + }
1176 +
1177 + $result = null;
1178 + switch ( $action ) {
1179 + case 'activate':
1180 + $result = self::activate_plugin( $installed );
1181 + break;
1182 + case 'deactivate':
1183 + self::deactivate_plugin( $installed );
1184 + break;
1185 + case 'uninstall':
1186 + $result = self::uninstall_plugin( $installed );
1187 + break;
1188 + }
1189 +
1190 + if ( is_wp_error( $result ) ) {
1191 + // Ignore the invalid header message that shows with nested plugins.
1192 + if ( $result->get_error_code() !== 'no_plugin_header' ) {
1193 + if ( wp_doing_ajax() ) {
1194 + wp_send_json_error( array( 'error' => $result->get_error_message() ) );
1195 + }
1196 + return array(
1197 + 'message' => $result->get_error_message(),
1198 + 'success' => false,
1199 + );
1200 + }
1201 + }
1202 +
1203 + return $result;
1204 + }
1205 +
1206 + /**
1075 1207 * @return array
1076 1208 */
1077 1209 private static function get_addon_activation_response() {
1078 1210 $activating_page = self::get_activating_page();
1079 1211
1212 + $message = $activating_page ? __( 'Your plugin has been activated. Would you like to save and reload the page now?', 'formidable' ) : __( 'Your plugin has been activated.', 'formidable' );
1213 +
1080 1214 $response = array(
1081 - 'message' => __( 'Your plugin has been activated. Would you like to save and reload the page now?', 'formidable' ),
1215 + 'message' => $message,
1082 1216 'saveAndReload' => $activating_page,
1083 1217 );
1084 1218
1085 1219 return $response;
@@ -1104,34 +1238,8 @@
1104 1238 return '';
1105 1239 }
1106 1240
1107 1241 /**
1108 - * @since 3.04.02
1109 - *
1110 - * @param string $installed The plugin folder name with file name
1111 - */
1112 - protected static function maybe_activate_addon( $installed ) {
1113 - if ( ! $installed ) {
1114 - return;
1115 - }
1116 -
1117 - $activate = self::activate_plugin( $installed );
1118 - if ( is_wp_error( $activate ) ) {
1119 - // Ignore the invalid header message that shows with nested plugins.
1120 - if ( $activate->get_error_code() !== 'no_plugin_header' ) {
1121 - if ( wp_doing_ajax() ) {
1122 - echo json_encode( array( 'error' => $activate->get_error_message() ) );
1123 - wp_die();
1124 - }
1125 - return array(
1126 - 'message' => $activate->get_error_message(),
1127 - 'success' => false,
1128 - );
1129 - }
1130 - }
1131 - }
1132 -
1133 - /**
1134 1242 * Run security checks before installing
1135 1243 *
1136 1244 * @since 3.04.02
1137 1245 *
@@ -1154,15 +1262,18 @@
1154 1262 public static function connect_link() {
1155 1263 $auth = get_option( 'frm_connect_token' );
1156 1264 if ( empty( $auth ) ) {
1157 1265 $auth = hash( 'sha512', wp_rand() );
1158 - update_option( 'frm_connect_token', $auth );
1266 + update_option( 'frm_connect_token', $auth, 'no' );
1159 1267 }
1160 - $link = FrmAppHelper::admin_upgrade_link( 'connect', 'api-connect' );
1268 + $page = FrmAppHelper::simple_get( 'page', 'sanitize_title', 'formidable-settings' );
1269 + $link = 'https://formidableforms.com/api-connect/';
1161 1270 $args = array(
1162 1271 'v' => 2,
1163 1272 'siteurl' => FrmAppHelper::site_url(),
1164 1273 'url' => get_rest_url(),
1274 + 'inst' => (int) FrmAppHelper::pro_is_included(),
1275 + 'return' => $page,
1165 1276 'token' => $auth,
1166 1277 'l' => self::get_pro_license(),
1167 1278 );
1168 1279
@@ -1180,9 +1291,12 @@
1180 1291 // Verify params present (auth & download link).
1181 1292 $post_auth = FrmAppHelper::get_param( 'token', '', 'request', 'sanitize_text_field' );
1182 1293 $post_url = FrmAppHelper::get_param( 'file_url', '', 'request', 'sanitize_text_field' );
1183 1294
1184 - if ( empty( $post_auth ) || empty( $post_url ) ) {
1295 + // The download link is not required if already installed.
1296 + $is_installed = FrmAppHelper::pro_is_included();
1297 + $file_missing = ! $is_installed && empty( $post_url );
1298 + if ( ! $post_auth || $file_missing ) {
1185 1299 return false;
1186 1300 }
1187 1301
1188 1302 // Verify auth.
@@ -1197,8 +1311,10 @@
1197 1311 /**
1198 1312 * Install and/or activate the add-on file.
1199 1313 *
1200 1314 * @since 4.08
1315 + *
1316 + * @return array
1201 1317 */
1202 1318 public static function install_addon_api() {
1203 1319 self::$plugin = FrmAppHelper::get_param( 'file_url', '', 'request', 'esc_url_raw' );
1204 1320
@@ -1209,11 +1325,11 @@
1209 1325
1210 1326 // It's already installed and active.
1211 1327 $active = self::activate_plugin( 'formidable-pro/formidable-pro.php', false, false, true );
1212 1328 if ( is_wp_error( $active ) ) {
1213 - // Download plugin now.
1214 - $response = self::download_and_activate();
1215 - if ( is_array( $response ) && isset( $response['success'] ) ) {
1329 + $response = self::maybe_download_and_activate();
1330 + if ( is_array( $response ) ) {
1331 + // The download failed.
1216 1332 return $response;
1217 1333 }
1218 1334 }
1219 1335
@@ -1240,22 +1356,58 @@
1240 1356 );
1241 1357 }
1242 1358
1243 1359 /**
1360 + * @since 6.8.3
1361 + *
1362 + * @return array|true
1363 + */
1364 + private static function maybe_download_and_activate() {
1365 + if ( ! self::$plugin ) {
1366 + return array(
1367 + 'success' => false,
1368 + 'message' => __( 'The plugin download was not found.', 'formidable' ),
1369 + );
1370 + }
1371 +
1372 + // Download plugin now.
1373 + $response = self::download_and_activate();
1374 + if ( is_array( $response ) && isset( $response['success'] ) ) {
1375 + // The download failed.
1376 + return $response;
1377 + }
1378 +
1379 + return true;
1380 + }
1381 +
1382 + /**
1244 1383 * Render a conditional action button for a specified plugin
1245 1384 *
1246 - * @param string $plugin
1385 + * @since 4.09
1386 + *
1387 + * @param string $plugin
1247 1388 * @param array|string $upgrade_link_args
1248 - * @since 4.09
1389 + * @return void
1249 1390 */
1250 1391 public static function conditional_action_button( $plugin, $upgrade_link_args ) {
1251 1392 if ( is_callable( 'FrmProAddonsController::conditional_action_button' ) ) {
1252 - return FrmProAddonsController::conditional_action_button( $plugin, $upgrade_link_args );
1393 + FrmProAddonsController::conditional_action_button( $plugin, $upgrade_link_args );
1394 + return;
1253 1395 }
1254 1396
1255 1397 $addon = self::get_addon( $plugin );
1256 1398 $upgrade_link = FrmAppHelper::admin_upgrade_link( $upgrade_link_args );
1257 - self::addon_upgrade_link( $addon, $upgrade_link );
1399 +
1400 + if ( ! is_array( $upgrade_link_args ) ) {
1401 + // A string $upgrade_link_args is used for the utm-medium value when calling
1402 + // FrmAppHelper::admin_upgrade_link above.
1403 + // For self::addon_upgrade_link, we'll pass just an empty array with the link key (set below).
1404 + $upgrade_link_args = array();
1405 + }
1406 +
1407 + $upgrade_link_args['link'] = $upgrade_link;
1408 +
1409 + self::addon_upgrade_link( $addon, $upgrade_link_args );
1258 1410 }
1259 1411
1260 1412 /**
1261 1413 * Render a conditional action button for an add on
@@ -1261,16 +1413,22 @@
1261 1413 * Render a conditional action button for an add on
1262 1414 *
1263 1415 * @since 4.09.01
1264 1416 *
1265 - * @param array $addon
1266 - * @param string|false $license_type
1267 - * @param string $plan_required
1268 - * @param string $upgrade_link
1417 + * @param array $atts {
1418 + * Button attributes.
1419 + *
1420 + * @type array $addon
1421 + * @type false|string $license_type
1422 + * @type string $plan_required
1423 + * @type string $upgrade_link
1424 + * }
1425 + * @return void
1269 1426 */
1270 1427 public static function show_conditional_action_button( $atts ) {
1271 1428 if ( is_callable( 'FrmProAddonsController::show_conditional_action_button' ) ) {
1272 - return FrmProAddonsController::show_conditional_action_button( $atts );
1429 + FrmProAddonsController::show_conditional_action_button( $atts );
1430 + return;
1273 1431 }
1274 1432
1275 1433 self::addon_upgrade_link( $atts['addon'], $atts['upgrade_link'] );
1276 1434 }
@@ -1277,13 +1435,17 @@
1277 1435
1278 1436 /**
1279 1437 * @since 4.09.01
1280 1438 *
1281 - * @param array|false $addon
1439 + * @param array|false $addon
1440 + * @param array|string $upgrade_link
1282 1441 *
1283 1442 * @return void
1284 1443 */
1285 1444 protected static function addon_upgrade_link( $addon, $upgrade_link ) {
1445 + $atts = is_array( $upgrade_link ) ? $upgrade_link : array();
1446 + $upgrade_link = is_array( $upgrade_link ) ? $upgrade_link['link'] : $upgrade_link;
1447 +
1286 1448 if ( $addon ) {
1287 1449 $upgrade_link .= '&utm_content=' . $addon['slug'];
1288 1450 }
1289 1451
@@ -1290,10 +1452,15 @@
1290 1452 if ( $addon && isset( $addon['categories'] ) && in_array( 'Solution', $addon['categories'], true ) ) {
1291 1453 // Solutions will go to a separate page.
1292 1454 $upgrade_link = FrmAppHelper::admin_upgrade_link( 'addons', $addon['link'] );
1293 1455 }
1456 +
1457 + $class = ! empty( $atts['class'] ) ? $atts['class'] : '';
1458 + if ( strpos( $class, 'frm-button' ) === false ) {
1459 + $class .= ' frm-button-secondary frm-button-sm';
1460 + }
1294 1461 ?>
1295 - <a class="install-now button frm-button-secondary frm-button-sm" href="<?php echo esc_url( $upgrade_link ); ?>" target="_blank" rel="noopener" aria-label="<?php esc_attr_e( 'Upgrade Now', 'formidable' ); ?>">
1462 + <a class="install-now button <?php echo esc_attr( $class ); ?>" href="<?php echo esc_url( $upgrade_link ); ?>" target="_blank" rel="noopener" aria-label="<?php esc_attr_e( 'Upgrade Now', 'formidable' ); ?>">
1296 1463 <?php esc_html_e( 'Upgrade Now', 'formidable' ); ?>
1297 1464 </a>
1298 1465 <?php
1299 1466 }
@@ -1316,107 +1483,86 @@
1316 1483 wp_die();
1317 1484 }
1318 1485
1319 1486 /**
1320 - * @since 4.06.02
1487 + * Allowed URLs used for internal source of plugins installation.
1321 1488 *
1322 - * @deprecated 4.09.01
1489 + * @since 6.3.1
1323 1490 *
1324 - * @return void
1491 + * @return array
1325 1492 */
1326 - public static function ajax_multiple_addons() {
1327 - FrmDeprecated::ajax_multiple_addons();
1328 - }
1493 + private static function allowed_external_urls() {
1494 + $allowed_url_list = array(
1495 + 'https://downloads.wordpress.org/plugin/formidable-gravity-forms-importer.zip',
1496 + 'https://downloads.wordpress.org/plugin/formidable-import-pirate-forms.zip',
1497 + 'https://downloads.wordpress.org/plugin/wp-mail-smtp.zip',
1498 + );
1329 1499
1330 - /**
1331 - * @since 3.04.03
1332 - * @deprecated 3.06
1333 - * @codeCoverageIgnore
1334 - * @return array
1335 - */
1336 - public static function error_for_license( $license ) {
1337 - return FrmDeprecated::error_for_license( $license );
1338 - }
1500 + /**
1501 + * List of URLs used in plugin formidable internal installation.
1502 + *
1503 + * @since 6.3.1
1504 + *
1505 + * @param array $allowed_url_list List of URLs.
1506 + */
1507 + $allowed_url_list = apply_filters( 'frm_allowed_external_urls', $allowed_url_list );
1339 1508
1340 - /**
1341 - * @since 3.04.03
1342 - * @deprecated 3.06
1343 - * @codeCoverageIgnore
1344 - */
1345 - public static function get_pro_updater() {
1346 - return FrmDeprecated::get_pro_updater();
1509 + if ( ! is_array( $allowed_url_list ) ) {
1510 + _doing_it_wrong( __METHOD__, 'Only an array of URLs could be used within this filter.', '6.3.1' );
1511 +
1512 + return array();
1513 + }
1514 +
1515 + return $allowed_url_list;
1347 1516 }
1348 1517
1349 1518 /**
1350 - * @since 3.04.03
1351 - * @deprecated 3.06
1352 - * @codeCoverageIgnore
1519 + * Gets required plan for an addon.
1353 1520 *
1354 - * @return array
1521 + * @since 6.4.2
1522 + *
1523 + * @return string Empty string if no plan is required for active license.
1355 1524 */
1356 - public static function get_addon_info( $license = '' ) {
1357 - return FrmDeprecated::get_addon_info( $license );
1358 - }
1525 + public static function get_addon_required_plan( $addon_id ) {
1526 + $api = new FrmFormApi();
1527 + $addons = $api->get_api_info();
1359 1528
1360 - /**
1361 - * @since 3.04.03
1362 - * @deprecated 3.06
1363 - * @codeCoverageIgnore
1364 - *
1365 - * @return string
1366 - */
1367 - public static function get_cache_key( $license ) {
1368 - return FrmDeprecated::get_cache_key( $license );
1529 + if ( is_array( $addons ) && array_key_exists( $addon_id, $addons ) ) {
1530 + $dates = $addons[ $addon_id ];
1531 + $requires = FrmFormsHelper::get_plan_required( $dates );
1532 + }
1533 +
1534 + if ( ! isset( $requires ) || ! is_string( $requires ) ) {
1535 + $requires = '';
1536 + }
1537 +
1538 + return $requires;
1369 1539 }
1370 1540
1371 1541 /**
1372 - * @since 3.04.03
1542 + * @since 4.02.05
1543 + * @deprecated 6.8.3
1373 1544 *
1374 - * @deprecated 3.06
1375 - *
1376 1545 * @codeCoverageIgnore
1377 1546 *
1378 1547 * @return void
1379 1548 */
1380 - public static function reset_cached_addons( $license = '' ) {
1381 - FrmDeprecated::reset_cached_addons( $license );
1549 + public static function connect_pro() {
1550 + _deprecated_function( __METHOD__, '6.8.3' );
1382 1551 }
1383 1552
1384 1553 /**
1385 - * @since 2.03.08
1386 - * @deprecated 3.04.03
1387 - * @codeCoverageIgnore
1554 + * @since 4.08
1555 + * @deprecated 6.11.1
1388 1556 *
1389 - * @param boolean $return
1390 - * @param string $package
1391 - *
1392 - * @return boolean
1557 + * @return bool|int false or the number of days until expiration.
1393 1558 */
1394 - public static function add_shorten_edd_filename_filter( $return, $package ) {
1395 - return FrmDeprecated::add_shorten_edd_filename_filter( $return, $package );
1396 - }
1559 + public static function is_license_expiring() {
1560 + _deprecated_function( __METHOD__, '6.11.1', 'FrmProAddonsController::is_license_expiring' );
1397 1561
1398 - /**
1399 - * @since 2.03.08
1400 - * @deprecated 3.04.03
1401 - * @codeCoverageIgnore
1402 - *
1403 - * @param string $filename
1404 - * @param string $ext
1405 - *
1406 - * @return string
1407 - */
1408 - public static function shorten_edd_filename( $filename, $ext ) {
1409 - return FrmDeprecated::shorten_edd_filename( $filename, $ext );
1410 - }
1562 + if ( is_callable( 'FrmProAddonsController::is_license_expiring' ) ) {
1563 + return FrmProAddonsController::is_license_expiring();
1564 + }
1411 1565
1412 - /**
1413 - * @deprecated 3.04.03
1414 - *
1415 - * @codeCoverageIgnore
1416 - *
1417 - * @return void
1418 - */
1419 - public static function get_licenses() {
1420 - FrmDeprecated::get_licenses();
1566 + return false;
1421 1567 }
1422 1568 }