PluginProbe ʕ •ᴥ•ʔ
Hustle – Email Marketing, Lead Generation, Optins, Popups / 7.8.9
Hustle – Email Marketing, Lead Generation, Optins, Popups v7.8.9
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 / providers / aweber / hustle-aweber.php
wordpress-popup / inc / providers / aweber Last commit date
images 7 years ago lib 3 years ago aweber.php 3 years ago hustle-addon-aweber-exception.php 3 years ago hustle-addon-aweber-form-settings-exception.php 3 years ago hustle-aweber-form-hooks.php 3 years ago hustle-aweber-form-settings.php 3 years ago hustle-aweber.php 3 years ago
hustle-aweber.php
709 lines
1 <?php // phpcs:ignore WordPress.Files.FileName.InvalidClassFileName
2 /**
3 * Hustle_Aweber class
4 *
5 * @package Hustle
6 */
7
8 if ( ! class_exists( 'Hustle_Aweber' ) ) :
9
10 /**
11 * Class Hustle_Aweber
12 */
13 class Hustle_Aweber extends Hustle_Provider_Abstract {
14
15 const SLUG = 'aweber';
16
17 const APP_ID = 'b0cd0152';
18
19 const AUTH_CODE = 'aut_code';
20 const CONSUMER_KEY = 'consumer_key';
21 const CONSUMER_SECRET = 'consumer_secret';
22 const ACCESS_TOKEN = 'access_token';
23 const ACCESS_SECRET = 'access_secret';
24 const ACCESS_OAUTH2_TOKEN = 'access_oauth2_token';
25 const REFRESH_TIME = 'expires_in';
26 const ACCESS_OAUTH2_REFRESH = 'access_oauth2_refresh';
27
28 /**
29 * Api
30 *
31 * @var AWeberAPI
32 */
33 protected static $api;
34 /**
35 * Errors
36 *
37 * @var array
38 */
39 protected static $errors;
40
41 /**
42 * Aweber Provider Instance
43 *
44 * @since 3.0.5
45 *
46 * @var self|null
47 */
48 protected static $instance = null;
49
50 /**
51 * Slug
52 *
53 * @since 3.0.5
54 * @var string
55 */
56 protected $slug = 'aweber';
57
58 /**
59 * Version
60 *
61 * @since 3.0.5
62 * @var string
63 */
64 protected $version = '1.0';
65
66 /**
67 * Class
68 *
69 * @since 3.0.5
70 * @var string
71 */
72 protected $class = __CLASS__;
73
74 /**
75 * Title
76 *
77 * @since 3.0.5
78 * @var string
79 */
80 protected $title = 'Aweber';
81
82 /**
83 * Class name of form settings
84 *
85 * @var string
86 */
87 protected $form_settings = 'Hustle_Aweber_Form_Settings';
88
89 /**
90 * Class name of form hooks
91 *
92 * @since 4.0
93 * @var string
94 */
95 protected $form_hooks = 'Hustle_Aweber_Form_Hooks';
96
97 /**
98 * Provider constructor.
99 */
100 public function __construct() {
101 $this->icon_2x = plugin_dir_url( __FILE__ ) . 'images/icon.png';
102 $this->logo_2x = plugin_dir_url( __FILE__ ) . 'images/logo.png';
103 }
104
105 /**
106 * Get Instance
107 *
108 * @return self|null
109 */
110 public static function get_instance() {
111 if ( is_null( self::$instance ) ) {
112 self::$instance = new self();
113 }
114
115 return self::$instance;
116 }
117
118 /**
119 * Get API
120 *
121 * @return null|object
122 */
123 public static function api() {
124 if ( ! is_null( self::$api ) ) {
125
126 return self::$api;
127 }
128
129 return null;
130 }
131
132 /**
133 * Get API Instance
134 *
135 * @since 1.0
136 * @since 4.0.1 $multi_global_id parameter added
137 *
138 * @param string|null $multi_global_id Multi global ID.
139 * @param array|null $api_credentials Api creds.
140 *
141 * @return Hustle_Addon_Aweber_Wp_Api
142 * @throws Hustle_Addon_Aweber_Wp_Api_Exception Missing global ID.
143 */
144 public function get_api( $multi_global_id = null, $api_credentials = array() ) {
145
146 if ( is_null( self::$api ) ) {
147
148 if ( ! empty( $api_credentials ) ) {
149 $api = new Hustle_Addon_Aweber_Wp_Api( $api_credentials );
150 } elseif ( empty( $api_credentials ) && ! empty( $multi_global_id ) ) {
151
152 if ( ! $multi_global_id ) {
153 throw new Hustle_Addon_Aweber_Wp_Api_Exception( __( 'Missing global ID instance.', 'hustle' ) );
154 }
155 $api_credentials = $this->get_credentials_keys( $multi_global_id );
156 $api = new Hustle_Addon_Aweber_Wp_Api( $api_credentials );
157 } else {
158 $api = new Hustle_Addon_Aweber_Wp_Api();
159 }
160
161 self::$api = $api;
162 }
163
164 return self::$api;
165 }
166
167 /**
168 * Retrieve the stored credentials key.
169 * Checks the global-multi settings first. If empty, checks
170 * the old wp_options keys where it was stored before 4.0.1.
171 *
172 * @since 4.0.1
173 *
174 * @param string|null $multi_global_id Multi global ID.
175 * @return array
176 */
177 private function get_credentials_keys( $multi_global_id ) {
178
179 $get_keys_from_options = false;
180
181 $keys_names = self::get_option_keys();
182 $api_credentials = array_fill_keys( $keys_names, '' );
183 $setting_values = $this->get_settings_values();
184 $instance_settings = $setting_values[ $multi_global_id ];
185
186 if ( isset( $instance_settings[ self::ACCESS_OAUTH2_TOKEN ] ) ) {
187 foreach ( $api_credentials as $api_credentials_key => $value ) {
188
189 // Some of our pre-defined keys aren't used for oAuth2.
190 if ( ! isset( $instance_settings[ $api_credentials_key ] ) ) {
191 continue;
192 }
193 $api_credentials[ $api_credentials_key ] = $instance_settings[ $api_credentials_key ];
194 }
195 } else {
196 foreach ( $api_credentials as $api_credentials_key => $value ) {
197
198 /**
199 * If there's any key missing in the saved multi settings,
200 * try retrieving them from the wp_options instead.
201 */
202 if ( empty( $instance_settings[ $api_credentials_key ] ) ) {
203 $get_keys_from_options = true;
204 break;
205 }
206
207 $api_credentials[ $api_credentials_key ] = $instance_settings[ $api_credentials_key ];
208 }
209
210 /**
211 * Any of the keys is missing in the saved multi settings.
212 * Try retrieving them from wp_options.
213 * This is were they were stored before 4.0.1.
214 */
215 if ( $get_keys_from_options ) {
216
217 foreach ( $api_credentials as $api_credentials_key => $value ) {
218
219 $saved_key = $this->get_provider_option( $api_credentials_key, '' );
220 if ( empty( $saved_key ) ) {
221 break;
222 }
223
224 $api_credentials[ $api_credentials_key ] = $saved_key;
225 }
226 }
227 }
228
229 return $api_credentials;
230 }
231
232 /**
233 * Get the account ID
234 *
235 * @since 4.0.1
236 *
237 * @param string $global_multi_id Global multi ID.
238 * @return string|false
239 */
240 public function get_account_id( $global_multi_id ) {
241
242 $account_id = $this->get_setting( 'account_id', false, $global_multi_id );
243
244 if ( ! $account_id ) {
245 try {
246 $account_id = $this->get_validated_account_id( $global_multi_id );
247 $saved_settings = $this->get_settings_values();
248 $settings_to_save = $saved_settings[ $global_multi_id ];
249 $settings_to_save['account_id'] = $account_id;
250
251 $this->save_multi_settings_values( $global_multi_id, $settings_to_save );
252
253 } catch ( Exception $e ) {
254 Hustle_Provider_Utils::maybe_log( __METHOD__, $e->getMessage() );
255 }
256 }
257
258 return $account_id;
259 }
260
261 /**
262 * Get validated account_id
263 *
264 * @param string $global_multi_id Global multi ID.
265 * @param array $api_key Api key.
266 * @return integer
267 * @throws Hustle_Addon_Aweber_Exception Failed to get AWeber account information.
268 */
269 public function get_validated_account_id( $global_multi_id = null, $api_key = array() ) {
270
271 $api = $this->get_api( $global_multi_id, $api_key );
272
273 $accounts = $api->get_accounts();
274 if ( ! isset( $accounts->entries ) ) {
275 throw new Hustle_Addon_Aweber_Exception( __( 'Failed to get AWeber account information', 'hustle' ) );
276 }
277
278 $entries = $accounts->entries;
279 if ( ! isset( $entries[0] ) ) {
280 throw new Hustle_Addon_Aweber_Exception( __( 'Failed to get AWeber account information', 'hustle' ) );
281 }
282
283 $first_entry = $entries[0];
284 $account_id = $first_entry->id;
285
286 /**
287 * Filter validated account_id
288 *
289 * @since 1.3
290 *
291 * @param integer $account_id
292 * @param object $accounts
293 * @param Hustle_Addon_Aweber_Wp_Api $api
294 */
295 $account_id = apply_filters( 'hustle_addon_aweber_validated_account_id', $account_id, $accounts, $api );
296
297 return $account_id;
298 }
299
300 /**
301 * Validate Access Token
302 *
303 * @param string $verifier_code Verification code.
304 */
305 public function get_validated_access_token( $verifier_code ) {
306 // reinit api.
307 self::$api = null;
308
309 // get access_token.
310 $api = $this->get_api();
311 $access_tokens = $api->process_callback_request( $verifier_code );
312
313 // reinit api with new access token open success for future usage.
314 self::$api = null;
315 return $access_tokens;
316 }
317
318 /**
319 * Get the wizard callbacks for the global settings.
320 *
321 * @since 4.0
322 *
323 * @return array
324 */
325 public function settings_wizards() {
326 return array(
327 array(
328 'callback' => array( $this, 'configure_api_key' ),
329 'is_completed' => array( $this, 'is_connected' ),
330 ),
331 );
332 }
333
334
335 /**
336 * Configure the API key settings. Global settings.
337 *
338 * @since 4.0
339 *
340 * @param array $submitted_data Submitted data.
341 * @return array
342 */
343 public function configure_api_key( $submitted_data ) {
344 $has_errors = false;
345 $default_data = array(
346 'api_key' => '',
347 'name' => '',
348 );
349 $current_data = $this->get_current_data( $default_data, $submitted_data );
350 $is_submit = isset( $submitted_data['api_key'] );
351 $global_multi_id = $this->get_global_multi_id( $submitted_data );
352 $api_key_validated = true;
353 if ( $is_submit ) {
354
355 $validated_credentials = $this->get_validated_credentials( $submitted_data['api_key'] );
356
357 if ( empty( $validated_credentials ) || ! is_array( $validated_credentials ) ) {
358 $api_key_validated = false;
359 $error_message = $this->provider_connection_falied();
360 $has_errors = true;
361 }
362
363 if ( ! $has_errors ) {
364
365 // If not active, activate it.
366 if (
367 $this->is_active() ||
368 Hustle_Providers::get_instance()->activate_addon( $this->slug )
369 ) {
370
371 $keys_names = self::get_option_keys();
372
373 $settings_to_save = array(
374 'api_key' => $current_data['api_key'],
375 'name' => $current_data['name'],
376 );
377
378 foreach ( $keys_names as $name ) {
379
380 // Some of our pre-defined keys aren't used for oAuth2.
381 if ( ! isset( $validated_credentials[ $name ] ) ) {
382 continue;
383 }
384
385 // Add the key to the $settings_to_save.
386 $settings_to_save[ $name ] = $validated_credentials[ $name ];
387
388 // Store it in the wp_options to remain compatible with 4.0.0 in case of a rollback, even though these won't be used.
389 $this->update_provider_option( $name, $validated_credentials[ $name ] );
390 }
391
392 $this->save_multi_settings_values( $global_multi_id, $settings_to_save );
393
394 } else {
395 $error_message = __( "Provider couldn't be activated.", 'hustle' );
396 $has_errors = true;
397
398 }
399 }
400
401 if ( ! $has_errors ) {
402
403 return array(
404 'html' => Hustle_Provider_Utils::get_integration_modal_title_markup( __( 'Aweber Added', 'hustle' ), __( 'You can now go to your pop-ups, slide-ins and embeds and assign them to this integration', 'hustle' ) ),
405 'buttons' => array(
406 'close' => array(
407 'markup' => Hustle_Provider_Utils::get_provider_button_markup( __( 'Close', 'hustle' ), 'sui-button-ghost', 'close' ),
408 ),
409 ),
410 'redirect' => false,
411 'has_errors' => false,
412 'notification' => array(
413 'type' => 'success',
414 'text' => '<strong>' . $this->get_title() . '</strong> ' . esc_html__( 'Successfully connected', 'hustle' ),
415 ),
416 );
417
418 }
419 }
420
421 $options = array(
422 array(
423 'type' => 'wrapper',
424 'class' => $api_key_validated ? '' : 'sui-form-field-error',
425 'elements' => array(
426 'label' => array(
427 'type' => 'label',
428 'for' => 'api_key',
429 'value' => __( 'Authorization code', 'hustle' ),
430 ),
431 'api_key' => array(
432 'type' => 'text',
433 'name' => 'api_key',
434 'value' => $current_data['api_key'],
435 'placeholder' => __( 'Enter Code', 'hustle' ),
436 'id' => 'api_key',
437 'icon' => 'key',
438 ),
439 'error' => array(
440 'type' => 'error',
441 'class' => $api_key_validated ? 'sui-hidden' : '',
442 'value' => __( 'Please enter a valid Aweber authorization code', 'hustle' ),
443 ),
444 ),
445 ),
446 array(
447 'type' => 'wrapper',
448 'style' => 'margin-bottom: 0;',
449 'elements' => array(
450 'label' => array(
451 'type' => 'label',
452 'for' => 'instance-name-input',
453 'value' => __( 'Identifier', 'hustle' ),
454 ),
455 'name' => array(
456 'type' => 'text',
457 'name' => 'name',
458 'value' => $current_data['name'],
459 'placeholder' => __( 'E.g. Business Account', 'hustle' ),
460 'id' => 'instance-name-input',
461 ),
462 'message' => array(
463 'type' => 'description',
464 'value' => __( 'Helps to distinguish your integrations if you have connected to the multiple accounts of this integration.', 'hustle' ),
465 ),
466 ),
467 ),
468 );
469
470 $api = $this->get_api();
471
472 $auth_url = $api->get_authorization_uri( 0, true, Hustle_Data::INTEGRATIONS_PAGE );
473
474 $step_html = Hustle_Provider_Utils::get_integration_modal_title_markup(
475 __( 'Configure Aweber', 'hustle' ),
476 sprintf(
477 /* translators: 1. open 'a' tag 2. closing 'a' tag */
478 __( 'Please %1$sclick here%2$s to connect to Aweber service to get your authorization code.', 'hustle' ),
479 '<a href="' . esc_url( $auth_url ) . '" target="_blank">',
480 '</a>'
481 )
482 );
483 if ( $has_errors ) {
484
485 $error_notice = array(
486 'type' => 'notice',
487 'icon' => 'info',
488 'class' => 'sui-notice-error',
489 'value' => esc_html( $error_message ),
490 );
491 array_unshift( $options, $error_notice );
492 }
493 $step_html .= Hustle_Provider_Utils::get_html_for_options( $options );
494
495 $is_edit = $this->settings_are_completed( $global_multi_id );
496 if ( $is_edit ) {
497 $buttons = array(
498 'disconnect' => array(
499 'markup' => Hustle_Provider_Utils::get_provider_button_markup(
500 __( 'Disconnect', 'hustle' ),
501 'sui-button-ghost',
502 'disconnect',
503 true
504 ),
505 ),
506 'save' => array(
507 'markup' => Hustle_Provider_Utils::get_provider_button_markup(
508 __( 'Save', 'hustle' ),
509 '',
510 'connect',
511 true
512 ),
513 ),
514 );
515 } else {
516 $buttons = array(
517 'connect' => array(
518 'markup' => Hustle_Provider_Utils::get_provider_button_markup(
519 __( 'Connect', 'hustle' ),
520 'sui-button-right',
521 'connect',
522 true
523 ),
524 ),
525 );
526
527 }
528
529 $response = array(
530 'html' => $step_html,
531 'buttons' => $buttons,
532 'has_errors' => $has_errors,
533 );
534
535 return $response;
536 }
537
538 /**
539 * Validate the migrated API key.
540 *
541 * @since 4.1.1
542 *
543 * @param array $data Data.
544 * @return array
545 */
546 public function configure_migrated_api_key( $data ) {
547 $has_errors = false;
548 $default_data = array(
549 'api_key' => '',
550 'name' => '',
551 );
552
553 $current_data = $this->get_current_data( $default_data, $data );
554 $global_multi_id = $this->get_global_multi_id( $data );
555 $validated_credentials = $this->get_validated_credentials( $data['api_key'] );
556
557 if ( empty( $validated_credentials ) || ! is_array( $validated_credentials ) ) {
558 $has_errors = true;
559 }
560
561 if ( ! $has_errors ) {
562
563 // If not active, activate it.
564 if (
565 $this->is_active() ||
566 Hustle_Providers::get_instance()->activate_addon( $this->slug )
567 ) {
568
569 $keys_names = self::get_option_keys();
570
571 $settings_to_save = array(
572 'api_key' => $current_data['api_key'],
573 'name' => $current_data['name'],
574 );
575
576 foreach ( $keys_names as $name ) {
577
578 // Some of our pre-defined keys aren't used for oAuth2.
579 if ( ! isset( $validated_credentials[ $name ] ) ) {
580 continue;
581 }
582
583 // Add the key to the $settings_to_save.
584 $settings_to_save[ $name ] = $validated_credentials[ $name ];
585
586 // Store it in the wp_options to remain compatible with 4.0.0 in case of a rollback, even though these won't be used.
587 $this->update_provider_option( $name, $validated_credentials[ $name ] );
588 }
589
590 $this->save_multi_settings_values( $global_multi_id, $settings_to_save );
591
592 } else {
593 $has_errors = true;
594 }
595 }
596
597 return $has_errors;
598 }
599
600 /**
601 * Validate the provided API key.
602 *
603 * @since 4.0
604 *
605 * @param string $api_key Api key.
606 * @return bool
607 */
608 private function get_validated_credentials( $api_key ) {
609 if ( empty( trim( $api_key ) ) ) {
610 return false;
611 }
612
613 // Check if API key is valid.
614 try {
615
616 $tokens = $this->get_validated_access_token( $api_key );
617 if ( ! $tokens ) {
618 return false;
619 } else {
620 $api_key = array(
621 self::ACCESS_OAUTH2_REFRESH => $tokens['refresh_token'],
622 self::ACCESS_OAUTH2_TOKEN => $tokens['access_token'],
623 self::REFRESH_TIME => time() + $tokens['expires_in'],
624 );
625 }
626 } catch ( Exception $e ) {
627 Hustle_Provider_Utils::maybe_log( $e->getMessage() );
628 return false;
629 }
630
631 // Check API Key by validating it on get_info request.
632 try {
633 $account_id = $this->get_validated_account_id( null, $api_key );
634 if ( ! $account_id ) {
635 Hustle_Provider_Utils::maybe_log( __METHOD__, __( 'Invalid Aweber authorization code.', 'hustle' ) );
636 return false;
637 }
638 } catch ( Exception $e ) {
639 Hustle_Provider_Utils::maybe_log( __METHOD__, $e->getMessage() );
640 return false;
641 }
642
643 return $api_key;
644 }
645
646 /**
647 * Remove wp_options rows
648 */
649 public function remove_wp_options() {
650 $keys_names = self::get_option_keys();
651
652 foreach ( $keys_names as $name ) {
653 $this->delete_provider_option( $name );
654 }
655 }
656
657 /**
658 * Get additional params' keys
659 *
660 * @return array
661 */
662 private static function get_option_keys() {
663 return array(
664 self::CONSUMER_KEY,
665 self::CONSUMER_SECRET,
666 self::ACCESS_TOKEN,
667 self::ACCESS_SECRET,
668 self::AUTH_CODE,
669 self::ACCESS_OAUTH2_REFRESH,
670 self::ACCESS_OAUTH2_TOKEN,
671 self::REFRESH_TIME,
672 );
673 }
674
675 /**
676 * Get 3.0 provider mappings
677 *
678 * @return array
679 */
680 public function get_30_provider_mappings() {
681 return array(
682 'api_key' => 'api_key',
683 );
684 }
685
686 /**
687 * Refreshes the token for the registered multi-ids.
688 *
689 * @since 4.3.3
690 */
691 public static function refresh_token() {
692 $aweber_instance = self::get_instance();
693
694 // Aweber is supposed to be connected if we're executing this, but check just in case.
695 if ( ! $aweber_instance->is_connected() ) {
696 return;
697 }
698
699 $multi_ids = wp_list_pluck( $aweber_instance->get_global_multi_ids(), 'id' );
700
701 foreach ( $multi_ids as $multi_id ) {
702 $api_instance = $aweber_instance->get_api( $multi_id );
703 $api_instance->validate_auth_token_lifespan( $multi_id );
704 }
705 }
706 }
707
708 endif;
709