Failed Conditions
Push — develop ( 12386e...3e9729 )
by Remco
06:20
created

src/Gateways/Gateway.php (11 issues)

1
<?php
2
/**
3
 * Gateway
4
 *
5
 * @author    Pronamic <[email protected]>
6
 * @copyright 2005-2021 Pronamic
7
 * @license   GPL-3.0-or-later
8
 * @package   Pronamic\WordPress\Pay\Extensions\MemberPress
9
 */
10
11
namespace Pronamic\WordPress\Pay\Extensions\MemberPress\Gateways;
12
13
use MeprBaseRealGateway;
14
use MeprEmailFactory;
15
use MeprOptions;
16
use MeprProduct;
17
use MeprSubscription;
18
use MeprTransaction;
19
use MeprTransactionsHelper;
20
use MeprUser;
21
use MeprUtils;
22
use MeprView;
23
use Pronamic\WordPress\Pay\Core\PaymentMethods;
24
use Pronamic\WordPress\Pay\Core\Util as Core_Util;
25
use Pronamic\WordPress\Pay\Payments\Payment;
26
use Pronamic\WordPress\Pay\Plugin;
27
use Pronamic\WordPress\Pay\Extensions\MemberPress\Pronamic;
28
use Pronamic\WordPress\Pay\Subscriptions\SubscriptionStatus;
29
use ReflectionClass;
30
31
/**
32
 * WordPress pay MemberPress gateway
33
 *
34
 * @author  Remco Tolsma
35
 * @version 2.2.3
36
 * @since   1.0.0
37
 */
38
class Gateway extends MeprBaseRealGateway {
39
	/**
40
	 * Payment method.
41
	 *
42
	 * @var string
43
	 */
44
	protected $payment_method;
45
46
	/**
47
	 * MemberPress transaction.
48
	 *
49
	 * @var MeprTransaction
50
	 */
51
	public $mp_txn;
52
53
	/**
54
	 * Pronamic payment.
55
	 *
56
	 * @var Payment
57
	 */
58
	public $pronamic_payment;
59
60
	/**
61
	 * Constructs and initialize iDEAL gateway.
62
	 */
63
	public function __construct() {
64
		// Set the name of this gateway.
65
		// @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L12-13.
66
		$this->name = __( 'Pronamic', 'pronamic_ideal' );
67
68
		if ( ! empty( $this->payment_method ) ) {
69
			$this->name = sprintf(
70
				/* translators: %s: payment method name */
71
				__( 'Pronamic - %s', 'pronamic_ideal' ),
72
				PaymentMethods::get_name( $this->payment_method )
73
			);
74
		}
75
76
		// Set the default settings.
77
		// @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L72-73.
78
		$this->set_defaults();
79
80
		// Set the capabilities of this gateway.
81
		// @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L36-37.
82
		$this->capabilities = array();
83
84
		// Setup the notification actions for this gateway.
85
		$this->notifiers = array();
86
87
		// Support single-page checkout.
88
		$this->has_spc_form = true;
0 ignored issues
show
Bug Best Practice introduced by
The property has_spc_form does not exist. Although not strictly required by PHP, it is generally a best practice to declare properties explicitly.
Loading history...
89
90
		// Key.
91
		$key = 'pronamic_pay';
92
93
		if ( null !== $this->payment_method ) {
94
			$key = sprintf( 'pronamic_pay_%s', $this->payment_method );
95
		}
96
97
		$this->key = $key;
0 ignored issues
show
Bug Best Practice introduced by
The property key does not exist. Although not strictly required by PHP, it is generally a best practice to declare properties explicitly.
Loading history...
98
	}
99
100
	/**
101
	 * Load the specified settings.
102
	 *
103
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L69-70
104
	 *
105
	 * @param array $settings MemberPress gateway settings array.
106
	 */
107
	public function load( $settings ) {
108
		$this->settings = (object) $settings;
109
110
		$this->set_defaults();
111
	}
112
113
	/**
114
	 * Custom helper function to send transaction notices.
115
	 *
116
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/lib/MeprUtils.php#L1333-L1351
117
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/models/MeprTransaction.php
118
	 *
119
	 * @param MeprTransaction $transaction MemberPress transaction object.
120
	 * @param string          $method      PHP function name to call.
121
	 *
122
	 * @return mixed
123
	 */
124
	public function send_transaction_notices( $transaction, $method ) {
125
		$class = 'MeprUtils';
126
127
		if ( ! Core_Util::class_method_exists( $class, $method ) ) {
128
			$class = $this;
129
		}
130
131
		// `send_product_welcome_notices` is called from `send_signup_notices` in newer versions.
132
		if ( 'send_product_welcome_notices' === $method ) {
133
			if ( 'MeprUtils' === $class ) {
134
				return null;
135
			}
136
137
			if ( ! \method_exists( $class, 'send_product_welcome_notices' ) ) {
138
				return null;
139
			}
140
		}
141
142
		return call_user_func( array( $class, $method ), $transaction );
143
	}
144
145
	/**
146
	 * Get icon function (this is not a MemberPress function).
147
	 *
148
	 * @since 1.0.2
149
	 * @return string
150
	 */
151
	protected function get_icon() {
152
		return '';
153
	}
154
155
	/**
156
	 * Get class alias name.
157
	 *
158
	 * @return string
159
	 */
160
	public function get_alias() {
161
		return 'MeprPronamicGateway';
162
	}
163
164
	/**
165
	 * Set the default settings.
166
	 *
167
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L72-73
168
	 */
169
	protected function set_defaults() {
170
		if ( ! isset( $this->settings ) ) {
171
			$this->settings = array();
172
		}
173
174
		$this->settings = (object) array_merge(
175
			array(
176
				'gateway'   => $this->get_alias(),
177
				'id'        => $this->generate_id(),
178
				'label'     => '',
179
				'use_label' => true,
180
				'icon'      => $this->get_icon(),
181
				'use_icon'  => true,
182
				'desc'      => '',
183
				'use_desc'  => true,
184
				'config_id' => '',
185
				'email'     => '',
186
				'sandbox'   => false,
187
				'debug'     => false,
188
			),
189
			(array) $this->settings
190
		);
191
192
		$this->id        = $this->settings->id;
193
		$this->label     = $this->settings->label;
194
		$this->use_label = $this->settings->use_label;
195
		$this->icon      = $this->settings->icon;
196
		$this->use_icon  = $this->settings->use_icon;
197
		$this->desc      = $this->settings->desc;
198
		$this->use_desc  = $this->settings->use_desc;
199
	}
200
201
	/**
202
	 * Process payment.
203
	 *
204
	 * @param MeprTransaction $txn MemberPress transaction object.
205
	 *
206
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L119-122
207
	 */
208
	public function process_payment( $txn ) {
209
210
	}
211
212
	/**
213
	 * Record subscription payment.
214
	 *
215
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L140-145
216
	 */
217
	public function record_subscription_payment() {
218
		$transaction = $this->mp_txn;
219
220
		$transaction->status     = MeprTransaction::$complete_str;
221
		$transaction->expires_at = MeprUtils::ts_to_mysql_date( $this->pronamic_payment->get_end_date()->getTimestamp(), 'Y-m-d 23:59:59' );
0 ignored issues
show
Bug Best Practice introduced by
The property expires_at does not exist. Although not strictly required by PHP, it is generally a best practice to declare properties explicitly.
Loading history...
222
		$transaction->store();
223
224
		$subscription = $transaction->subscription();
225
226
		if ( $subscription ) {
227
			$should_activate = ! \in_array(
228
				$subscription->status,
229
				array(
230
					MeprSubscription::$active_str,
231
					MeprSubscription::$cancelled_str,
232
				),
233
				true
234
			);
235
236
			if ( $should_activate ) {
237
				$subscription->status = MeprSubscription::$active_str;
238
				$subscription->store();
239
			}
240
241
			$subscription->expire_confirmation_txn();
242
243
			$subscription->limit_payment_cycles();
244
		}
245
246
		$this->send_transaction_notices( $transaction, 'send_transaction_receipt_notices' );
247
248
		return $transaction;
249
	}
250
251
	/**
252
	 * Record payment failure.
253
	 *
254
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L147-148
255
	 */
256
	public function record_payment_failure() {
257
		$transaction = $this->mp_txn;
258
259
		// @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/models/MeprTransaction.php#L50.
260
		$transaction->status = MeprTransaction::$failed_str;
261
		$transaction->store();
262
263
		// Expire associated subscription transactions for non-recurring payments.
264
		if ( ! ( isset( $this->pronamic_payment ) && $this->pronamic_payment->get_recurring() ) ) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $this->pronamic_payment->get_recurring() of type boolean|null is loosely compared to false; this is ambiguous if the boolean can be false. You might want to explicitly use !== null instead.

If an expression can have both false, and null as possible values. It is generally a good practice to always use strict comparison to clearly distinguish between those two values.

$a = canBeFalseAndNull();

// Instead of
if ( ! $a) { }

// Better use one of the explicit versions:
if ($a !== null) { }
if ($a !== false) { }
if ($a !== null && $a !== false) { }
Loading history...
265
			$subscription = $transaction->subscription();
266
267
			if ( $subscription ) {
268
				$subscription->expire_txns();
269
				$subscription->store();
270
			}
271
		}
272
273
		$this->send_transaction_notices( $transaction, 'send_failed_txn_notices' );
274
275
		return $transaction;
276
	}
277
278
	/**
279
	 * Record payment.
280
	 *
281
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L124-129
282
	 */
283
	public function record_payment() {
284
		$transaction = $this->mp_txn;
285
286
		$transaction->status = MeprTransaction::$complete_str;
287
288
		// This will only work before maybe_cancel_old_sub is run.
289
		$upgrade   = $transaction->is_upgrade();
290
		$downgrade = $transaction->is_downgrade();
291
292
		$event_transaction = $transaction->maybe_cancel_old_sub();
0 ignored issues
show
Are you sure the assignment to $event_transaction is correct as $transaction->maybe_cancel_old_sub() targeting MeprTransaction::maybe_cancel_old_sub() seems to always return null.

This check looks for function or method calls that always return null and whose return value is assigned to a variable.

class A
{
    function getObject()
    {
        return null;
    }

}

$a = new A();
$object = $a->getObject();

The method getObject() can return nothing but null, so it makes no sense to assign that value to a variable.

The reason is most likely that a function or method is imcomplete or has been reduced for debug purposes.

Loading history...
293
294
		$subscription = $transaction->subscription();
295
296
		if ( $subscription ) {
297
			$event_subscription = $subscription->maybe_cancel_old_sub();
0 ignored issues
show
Are you sure the assignment to $event_subscription is correct as $subscription->maybe_cancel_old_sub() targeting MeprSubscription::maybe_cancel_old_sub() seems to always return null.

This check looks for function or method calls that always return null and whose return value is assigned to a variable.

class A
{
    function getObject()
    {
        return null;
    }

}

$a = new A();
$object = $a->getObject();

The method getObject() can return nothing but null, so it makes no sense to assign that value to a variable.

The reason is most likely that a function or method is imcomplete or has been reduced for debug purposes.

Loading history...
298
299
			$subscription->status     = MeprSubscription::$active_str;
300
			$subscription->created_at = $transaction->created_at;
301
			$subscription->store();
302
303
			if ( false === $event_transaction && false !== $event_subscription ) {
304
				$event_transaction = $event_subscription;
305
			}
306
		}
307
308
		$transaction->store();
309
310
		/*
311
		 * For some reasons the `send_product_welcome_notices` function accepts 1 or 3 arguments. We are not sure
312
		 * if this is a difference in the 'Business' and 'Developer' edition or between version `1.2.4` and `1.2.7`.
313
		 *
314
		 * @link https://github.com/wp-premium/memberpress-developer/blob/1.2.4/app/lib/MeprBaseGateway.php#L596-L612
315
		 * @link https://github.com/wp-premium/memberpress-business/blob/1.2.7/app/lib/MeprBaseGateway.php#L609-L619
316
		 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/models/MeprTransaction.php#L51
317
		 */
318
		$reflection = new ReflectionClass( 'MeprBaseRealGateway' );
319
320
		if ( $reflection->hasMethod( 'send_product_welcome_notices' ) && 3 === $reflection->getMethod( 'send_product_welcome_notices' )->getNumberOfParameters() ) {
321
			$uemail = MeprEmailFactory::fetch(
322
				'MeprUserProductWelcomeEmail',
323
				'MeprBaseProductEmail',
324
				array(
325
					array(
326
						'product_id' => $transaction->product_id,
327
					),
328
				)
329
			);
330
331
			/**
332
			 * The `send_product_welcome_notices` method is only available in earlier version of MemberPress.
333
			 *
334
			 * @scrutinizer ignore-call
335
			 */
336
			$this->send_product_welcome_notices(
337
				$uemail,
338
				MeprTransactionsHelper::get_email_params( $transaction ),
339
				$transaction->user()
340
			);
341
		} else {
342
			$this->send_transaction_notices( $transaction, 'send_product_welcome_notices' );
343
		}
344
345
		// Send upgrade/downgrade notices.
346
		$product = $transaction->product();
347
348
		if ( 'lifetime' === $product->period_type ) {
349
			if ( $upgrade ) {
350
				$this->upgraded_sub( $transaction, $event_transaction );
351
				$this->send_transaction_notices( $transaction, 'send_upgraded_txn_notices' );
352
			} elseif ( $downgrade ) {
353
				$this->downgraded_sub( $transaction, $event_transaction );
354
				$this->send_transaction_notices( $transaction, 'send_downgraded_txn_notices' );
355
			} else {
356
				$this->new_sub( $transaction );
357
			}
358
		}
359
360
		$this->send_transaction_notices( $transaction, 'send_signup_notices' );
361
		$this->send_transaction_notices( $transaction, 'send_transaction_receipt_notices' );
362
363
		return $transaction;
364
	}
365
366
	/**
367
	 * Process refund.
368
	 *
369
	 * @param MeprTransaction $txn MemberPress transaction object.
370
	 *
371
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L131-133
372
	 */
373
	public function process_refund( MeprTransaction $txn ) {
374
375
	}
376
377
	/**
378
	 * Record refund.
379
	 *
380
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L135-138
381
	 */
382
	public function record_refund() {
383
384
	}
385
386
	/**
387
	 * Process trial payment.
388
	 *
389
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L150-157
390
	 *
391
	 * @param MeprTransaction $transaction MemberPress transaction object.
392
	 */
393
	public function process_trial_payment( $transaction ) {
394
395
	}
396
397
	/**
398
	 * Record trial payment.
399
	 *
400
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L159-161
401
	 *
402
	 * @param MeprTransaction $transaction MemberPress transaction object.
403
	 */
404
	public function record_trial_payment( $transaction ) {
405
406
	}
407
408
	/**
409
	 * Process create subscription.
410
	 *
411
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L163-167
412
	 *
413
	 * @param MeprTransaction $txn MemberPress transaction object.
414
	 */
415
	public function process_create_subscription( $txn ) {
416
417
	}
418
419
	/**
420
	 * Record create subscription.
421
	 *
422
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L169-174
423
	 */
424
	public function record_create_subscription() {
425
426
	}
427
428
	/**
429
	 * Process update subscription.
430
	 *
431
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L176
432
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/lib/MeprBaseGateway.php#L194
433
	 *
434
	 * @param int $sub_id Subscription ID.
435
	 */
436
	public function process_update_subscription( $sub_id ) {
437
438
	}
439
440
	/**
441
	 * Record update subscription.
442
	 *
443
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L178-182
444
	 */
445
	public function record_update_subscription() {
446
447
	}
448
449
	/**
450
	 * Process suspend subscription.
451
	 *
452
	 * @param int $sub_id Subscription id.
453
	 *
454
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L184-186
455
	 */
456
	public function process_suspend_subscription( $sub_id ) {
457
		if ( ! MeprSubscription::exists( $sub_id ) ) {
458
			return;
459
		}
460
461
		$sub = new MeprSubscription( $sub_id );
462
463
		if ( MeprSubscription::$suspended_str === $sub->status ) {
464
			// Subscription is already suspended.
465
			return;
466
		}
467
468
		$subscription = get_pronamic_subscription_by_meta( '_pronamic_subscription_source_id', $sub->id );
469
470
		if ( ! $subscription ) {
471
			return;
472
		}
473
474
		$sub->status = MeprSubscription::$suspended_str;
475
476
		$sub->store();
477
478
		// Send suspended subscription notices.
479
		MeprUtils::send_suspended_sub_notices( $sub );
480
481
		$note = sprintf(
482
			/* translators: %s: extension name */
483
			__( '%s subscription on hold.', 'pronamic_ideal' ),
484
			__( 'MemberPress', 'pronamic_ideal' )
485
		);
486
487
		$subscription->add_note( $note );
488
489
		// The status of canceled or completed subscriptions will not be changed automatically.
490
		if ( ! in_array( $subscription->get_status(), array( SubscriptionStatus::CANCELLED, SubscriptionStatus::COMPLETED ), true ) ) {
491
			$subscription->set_status( SubscriptionStatus::ON_HOLD );
492
493
			$subscription->save();
494
		}
495
	}
496
497
	/**
498
	 * Record suspend subscription.
499
	 *
500
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L188-191
501
	 */
502
	public function record_suspend_subscription() {
503
504
	}
505
506
	/**
507
	 * Process resume subscription.
508
	 *
509
	 * @param int $sub_id Subscription id.
510
	 *
511
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L193-195
512
	 */
513
	public function process_resume_subscription( $sub_id ) {
514
		if ( ! MeprSubscription::exists( $sub_id ) ) {
515
			return;
516
		}
517
518
		$sub = new MeprSubscription( $sub_id );
519
520
		if ( MeprSubscription::$active_str === $sub->status ) {
521
			// Subscription is already active.
522
			return;
523
		}
524
525
		$subscription = get_pronamic_subscription_by_meta( '_pronamic_subscription_source_id', $sub->id );
526
527
		if ( ! $subscription ) {
528
			return;
529
		}
530
531
		$sub->status = MeprSubscription::$active_str;
532
533
		$sub->store();
534
535
		// Check if prior txn is expired yet or not, if so create a temporary txn so the user can access the content immediately.
536
		$prior_txn = $sub->latest_txn();
537
538
		if ( false === $prior_txn || ! ( $prior_txn instanceof MeprTransaction ) || strtotime( $prior_txn->expires_at ) < time() ) {
539
			$txn                  = new MeprTransaction();
540
			$txn->subscription_id = $sub->id;
541
			$txn->trans_num       = $sub->subscr_id . '-' . uniqid();
542
			$txn->status          = MeprTransaction::$confirmed_str;
543
			$txn->txn_type        = MeprTransaction::$subscription_confirmation_str;
544
			$txn->response        = (string) $sub;
545
			$txn->expires_at      = MeprUtils::ts_to_mysql_date( time() + MeprUtils::days( 1 ), 'Y-m-d 23:59:59' );
546
547
			$txn->set_subtotal( 0.00 ); // Just a confirmation txn.
548
549
			$txn->store();
550
		}
551
552
		// Send resumed subscription notices.
553
		MeprUtils::send_resumed_sub_notices( $sub );
554
555
		// Add note.
556
		$note = sprintf(
557
			/* translators: %s: extension name */
558
			__( '%s subscription reactivated.', 'pronamic_ideal' ),
559
			__( 'MemberPress', 'pronamic_ideal' )
560
		);
561
562
		$subscription->add_note( $note );
563
564
		// The status of canceled or completed subscriptions will not be changed automatically.
565
		if ( ! in_array( $subscription->get_status(), array( SubscriptionStatus::CANCELLED, SubscriptionStatus::COMPLETED ), true ) ) {
566
			$subscription->set_status( SubscriptionStatus::ACTIVE );
567
568
			$subscription->save();
569
		}
570
	}
571
572
	/**
573
	 * Record resume subscription.
574
	 *
575
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L197-201
576
	 */
577
	public function record_resume_subscription() {
578
579
	}
580
581
	/**
582
	 * Process cancel subscription.
583
	 *
584
	 * @param int $sub_id Subscription id.
585
	 *
586
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L202-206
587
	 */
588
	public function process_cancel_subscription( $sub_id ) {
589
		if ( ! MeprSubscription::exists( $sub_id ) ) {
590
			return;
591
		}
592
593
		$sub = new MeprSubscription( $sub_id );
594
595
		if ( MeprSubscription::$cancelled_str === $sub->status ) {
596
			// Subscription is already cancelled.
597
			return;
598
		}
599
600
		$subscription = get_pronamic_subscription_by_meta( '_pronamic_subscription_source_id', $sub->id );
601
602
		if ( ! $subscription ) {
603
			return;
604
		}
605
606
		// Add note.
607
		$note = sprintf(
608
			/* translators: %s: extension name */
609
			__( '%s subscription cancelled.', 'pronamic_ideal' ),
610
			__( 'MemberPress', 'pronamic_ideal' )
611
		);
612
613
		$subscription->add_note( $note );
614
615
		// The status of canceled or completed subscriptions will not be changed automatically.
616
		if ( ! in_array( $subscription->get_status(), array( SubscriptionStatus::CANCELLED, SubscriptionStatus::COMPLETED ), true ) ) {
617
			$subscription->set_status( SubscriptionStatus::CANCELLED );
618
619
			$subscription->next_payment_date          = null;
620
			$subscription->next_payment_delivery_date = null;
621
622
			// Delete next payment post meta.
623
			$subscription->set_meta( 'next_payment', null );
624
			$subscription->set_meta( 'next_payment_delivery_date', null );
625
626
			$subscription->save();
627
		}
628
629
		// Cancel MemberPress subscription.
630
		$sub->status = MeprSubscription::$cancelled_str;
631
632
		$sub->store();
633
634
		// Expire the grace period (confirmation) if no completed payments have come through.
635
		if ( (int) $sub->txn_count <= 0 ) {
636
			$sub->expire_txns();
637
		}
638
639
		$sub->limit_reached_actions();
640
641
		// Send cancelled subscription notices.
642
		MeprUtils::send_cancelled_sub_notices( $sub );
643
	}
644
645
	/**
646
	 * Record cancel subscription.
647
	 *
648
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L208-212
649
	 */
650
	public function record_cancel_subscription() {
651
652
	}
653
654
	/**
655
	 * Process signup form.
656
	 *
657
	 * Gets called when the signup form is posted used for running any payment
658
	 * method specific actions when processing the customer signup form.
659
	 *
660
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L214-217
661
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/controllers/MeprCheckoutCtrl.php#L262
662
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/lib/MeprBaseGateway.php#L232-L235
663
	 *
664
	 * @param MeprTransaction $txn MemberPress transaction object.
665
	 */
666
	public function process_signup_form( $txn ) {
667
668
	}
669
670
	/**
671
	 * Payment redirect.
672
	 *
673
	 * @param MeprTransaction $txn MemberPress transaction object.
674
	 *
675
	 * @throws \Exception Throws exception on gateway payment start error.
676
	 * @since 1.0.2
677
	 */
678
	public function payment_redirect( $txn ) {
679
		// Gateway.
680
		$config_id = $this->get_config_id();
681
682
		$gateway = Plugin::get_gateway( $config_id );
0 ignored issues
show
Are you sure the assignment to $gateway is correct as Pronamic\WordPress\Pay\P...get_gateway($config_id) targeting Pronamic\WordPress\Pay\Plugin::get_gateway() seems to always return null.

This check looks for function or method calls that always return null and whose return value is assigned to a variable.

class A
{
    function getObject()
    {
        return null;
    }

}

$a = new A();
$object = $a->getObject();

The method getObject() can return nothing but null, so it makes no sense to assign that value to a variable.

The reason is most likely that a function or method is imcomplete or has been reduced for debug purposes.

Loading history...
683
684
		if ( null === $gateway ) {
685
			return;
686
		}
687
688
		// Create Pronamic payment.
689
		$txn = new MeprTransaction( $txn->id );
690
691
		$payment = Pronamic::get_payment( $txn );
692
693
		$payment->config_id = $config_id;
694
		$payment->method    = $this->payment_method;
695
696
		$error = null;
697
698
		try {
699
			$payment = Plugin::start_payment( $payment );
700
		} catch ( \Exception $e ) {
701
			$error = $e;
702
		}
703
704
		/*
705
		 * Update trial transaction.
706
		 *
707
		 * Notes:
708
		 * - MemberPress also uses trial amount for prorated upgrade/downgrade
709
		 * - Not updated BEFORE payment start, as transaction total amount is used for subscription amount.
710
		 * - Reload transaction to make sure actual status is being used (i.e. on free downgrade).
711
		 */
712
		$txn = new MeprTransaction( $txn->id );
713
714
		$subscription = $txn->subscription();
715
716
		if ( $subscription && $subscription->in_trial() ) {
717
			$txn->expires_at = MeprUtils::ts_to_mysql_date( $payment->get_end_date()->getTimestamp(), 'Y-m-d 23:59:59' );
718
719
			$txn->set_subtotal( $subscription->trial_amount );
720
			$txn->store();
721
		}
722
723
		if ( $error instanceof \Exception ) {
724
			// Rethrow error, caught by MemberPress.
725
			throw $error;
726
		}
727
728
		// Redirect.
729
		$gateway->redirect( $payment );
730
	}
731
732
	/**
733
	 * Display payment page.
734
	 *
735
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L219-223
736
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/controllers/MeprCheckoutCtrl.php#L290
737
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/gateways/MeprPayPalGateway.php#L775-L850
738
	 *
739
	 * @param MeprTransaction $txn MemberPress transaction object.
740
	 *
741
	 * @throws \Exception Throws exception on gateway payment start error.
742
	 */
743
	public function display_payment_page( $txn ) {
744
		// Gateway.
745
		$config_id = $this->get_config_id();
746
747
		$gateway = Plugin::get_gateway( $config_id );
0 ignored issues
show
Are you sure the assignment to $gateway is correct as Pronamic\WordPress\Pay\P...get_gateway($config_id) targeting Pronamic\WordPress\Pay\Plugin::get_gateway() seems to always return null.

This check looks for function or method calls that always return null and whose return value is assigned to a variable.

class A
{
    function getObject()
    {
        return null;
    }

}

$a = new A();
$object = $a->getObject();

The method getObject() can return nothing but null, so it makes no sense to assign that value to a variable.

The reason is most likely that a function or method is imcomplete or has been reduced for debug purposes.

Loading history...
748
749
		if ( null === $gateway ) {
750
			return;
751
		}
752
753
		// Redirect payment on empty input HTML.
754
		$gateway->set_payment_method( $this->payment_method );
755
756
		$html = $gateway->get_input_html();
757
758
		if ( empty( $html ) ) {
759
			$this->payment_redirect( $txn );
760
		}
761
	}
762
763
	/**
764
	 * Process payment form.
765
	 *
766
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L239-289
767
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/controllers/MeprCheckoutCtrl.php#L336
768
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/gateways/MeprPayPalGateway.php#L1011
769
	 *
770
	 * @param MeprTransaction $txn MemberPress transaction object.
771
	 *
772
	 * @return void
773
	 * @throws \Exception Throws exception on gateway payment start error.
774
	 */
775
	public function process_payment_form( $txn ) {
776
		// Gateway.
777
		$config_id = $this->get_config_id();
778
779
		$gateway = Plugin::get_gateway( $config_id );
0 ignored issues
show
Are you sure the assignment to $gateway is correct as Pronamic\WordPress\Pay\P...get_gateway($config_id) targeting Pronamic\WordPress\Pay\Plugin::get_gateway() seems to always return null.

This check looks for function or method calls that always return null and whose return value is assigned to a variable.

class A
{
    function getObject()
    {
        return null;
    }

}

$a = new A();
$object = $a->getObject();

The method getObject() can return nothing but null, so it makes no sense to assign that value to a variable.

The reason is most likely that a function or method is imcomplete or has been reduced for debug purposes.

Loading history...
780
781
		if ( null === $gateway ) {
782
			return;
783
		}
784
785
		// Redirect.
786
		$this->payment_redirect( $txn );
787
	}
788
789
	/**
790
	 * Enqueue payment form scripts.
791
	 *
792
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L219-223
793
	 */
794
	public function enqueue_payment_form_scripts() {
795
796
	}
797
798
	/**
799
	 * Display payment form.
800
	 *
801
	 * This spits out html for the payment form on the registration / payment
802
	 * page for the user to fill out for payment.
803
	 *
804
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L230-233
805
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/lib/MeprBaseGateway.php#L248-L251
806
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/controllers/MeprCheckoutCtrl.php#L318
807
	 *
808
	 * @param float    $amount     Transaction amount to create a payment form for.
809
	 * @param MeprUser $user       MemberPress user object.
810
	 * @param int      $product_id Product ID.
811
	 * @param int      $txn_id     Transaction ID.
812
	 */
813
	public function display_payment_form( $amount, $user, $product_id, $txn_id ) {
814
		// Gateway.
815
		$config_id = $this->get_config_id();
816
817
		$gateway = Plugin::get_gateway( $config_id );
0 ignored issues
show
Are you sure the assignment to $gateway is correct as Pronamic\WordPress\Pay\P...get_gateway($config_id) targeting Pronamic\WordPress\Pay\Plugin::get_gateway() seems to always return null.

This check looks for function or method calls that always return null and whose return value is assigned to a variable.

class A
{
    function getObject()
    {
        return null;
    }

}

$a = new A();
$object = $a->getObject();

The method getObject() can return nothing but null, so it makes no sense to assign that value to a variable.

The reason is most likely that a function or method is imcomplete or has been reduced for debug purposes.

Loading history...
818
819
		if ( null === $gateway ) {
820
821
			$admin_message = null;
822
823
			if ( \current_user_can( 'manage_options' ) ) {
824
				$admin_message = __( 'For admins only: check payment method settings in MemberPress.', 'pronamic_ideal' );
825
			}
826
827
			printf(
828
				'<div class="mp_wrapper mp_payment_form_wrapper"><ul><li>%s</li>%s</ul></div>',
829
				\esc_html( Plugin::get_default_error_message() ),
830
				null === $admin_message ? '' : sprintf( '<li><em>%s</em></li>', \esc_html( $admin_message ) )
831
			);
832
833
			return;
834
		}
835
836
		// Invoice.
837
		$product = new MeprProduct( $product_id );
838
839
		$coupon = false;
840
841
		$txn = new MeprTransaction( $txn_id );
842
843
		// Artificially set the price of the $prd in case a coupon was used.
844
		if ( $product->price !== $amount ) {
845
			$coupon         = true;
846
			$product->price = $amount;
847
		}
848
849
		$invoice = MeprTransactionsHelper::get_invoice( $txn );
850
851
		// phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
852
		echo $invoice;
853
854
		?>
855
		<div class="mp_wrapper mp_payment_form_wrapper">
856
			<form action="" method="post" id="payment-form" class="mepr-form" novalidate>
857
				<input type="hidden" name="mepr_process_payment_form" value="Y"/>
858
				<input type="hidden" name="mepr_transaction_id" value="<?php echo esc_attr( $txn_id ); ?>"/>
859
				<input type="hidden" name="pronamic_pay_memberpress_pay" value="1"/>
860
861
				<div class="mepr_spacer">&nbsp;</div>
862
863
				<?php
864
865
				$gateway->set_payment_method( $this->payment_method );
866
867
				// phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped
868
				echo $gateway->get_input_html();
869
870
				?>
871
872
				<div class="mepr_spacer">&nbsp;</div>
873
874
				<input type="submit" class="mepr-submit" value="<?php esc_attr_e( 'Pay', 'pronamic_ideal' ); ?>"/>
875
				<img src="<?php echo esc_attr( admin_url( 'images/loading.gif' ) ); ?>" style="display: none;" class="mepr-loading-gif"/>
876
				<?php MeprView::render( '/shared/has_errors', get_defined_vars() ); ?>
877
878
				<noscript>
879
					<p class="mepr_nojs">
880
						<?php esc_html_e( 'JavaScript is disabled in your browser. You will not be able to complete your purchase until you either enable JavaScript in your browser, or switch to a browser that supports it.', 'pronamic_ideal' ); ?>
881
					</p>
882
				</noscript>
883
			</form>
884
		</div>
885
		<?php
886
	}
887
888
	/**
889
	 * Single-page checkout payment fields.
890
	 *
891
	 * @return string
892
	 */
893
	public function spc_payment_fields() {
894
		// Gateway.
895
		$config_id = $this->get_config_id();
896
897
		$gateway = Plugin::get_gateway( $config_id );
0 ignored issues
show
Are you sure the assignment to $gateway is correct as Pronamic\WordPress\Pay\P...get_gateway($config_id) targeting Pronamic\WordPress\Pay\Plugin::get_gateway() seems to always return null.

This check looks for function or method calls that always return null and whose return value is assigned to a variable.

class A
{
    function getObject()
    {
        return null;
    }

}

$a = new A();
$object = $a->getObject();

The method getObject() can return nothing but null, so it makes no sense to assign that value to a variable.

The reason is most likely that a function or method is imcomplete or has been reduced for debug purposes.

Loading history...
898
899
		if ( null === $gateway ) {
900
			return '';
901
		}
902
903
		// Input HTML.
904
		$gateway->set_payment_method( $this->payment_method );
905
906
		$html = $gateway->get_input_html();
907
908
		if ( empty( $html ) ) {
909
			return '';
910
		}
911
912
		return $html;
913
	}
914
915
	/**
916
	 * Validate payment form.
917
	 *
918
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L235-236
919
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/controllers/MeprCheckoutCtrl.php#L330
920
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/lib/MeprBaseGateway.php#L253-L254
921
	 *
922
	 * @param array $errors Array with errors.
923
	 * @return array
924
	 */
925
	public function validate_payment_form( $errors ) {
926
		return $errors;
927
	}
928
929
	/**
930
	 * Display options form.
931
	 *
932
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L291-292
933
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/gateways/MeprAuthorizeGateway.php#L1027-1037
934
	 */
935
	public function display_options_form() {
936
		$mepr_options = MeprOptions::fetch();
937
938
		?>
939
		<table>
940
			<tr>
941
				<?php
942
943
				$name = sprintf(
944
					'%s[%s][%s]',
945
					$mepr_options->integrations_str,
946
					$this->id,
947
					'config_id'
948
				);
949
950
				?>
951
				<td>
952
					<?php esc_html_e( 'Configuration', 'pronamic_ideal' ); ?>
953
				</td>
954
				<td>
955
					<select name="<?php echo esc_attr( $name ); ?>">
956
						<?php
957
958
						foreach ( Plugin::get_config_select_options( $this->payment_method ) as $value => $label ) {
959
							printf(
960
								'<option value="%s" %s>%s</option>',
961
								esc_attr( $value ),
962
								selected( $value, $this->settings->config_id, false ),
963
								esc_html( $label )
964
							);
965
						}
966
967
						?>
968
					</select>
969
				</td>
970
			</tr>
971
		</table>
972
		<?php
973
	}
974
975
	/**
976
	 * Validate options form.
977
	 *
978
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L294-295
979
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/gateways/MeprPayPalGateway.php#L909-L924
980
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/models/MeprOptions.php#L416-L423
981
	 *
982
	 * @param array $errors Array with errors.
983
	 * @return array
984
	 */
985
	public function validate_options_form( $errors ) {
986
		return $errors;
987
	}
988
989
	/**
990
	 * Enqueue user account scripts.
991
	 *
992
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L297-302
993
	 */
994
	public function enqueue_user_account_scripts() {
995
996
	}
997
998
	/**
999
	 * Display update account form.
1000
	 *
1001
	 * @param int    $sub_id  Subscription ID.
1002
	 * @param array  $errors  Array with errors.
1003
	 * @param string $message Update message.
1004
	 *
1005
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L365-366
1006
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/lib/MeprBaseStaticGateway.php#L160-L161
1007
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/gateways/MeprStripeGateway.php#L1108-L1168
1008
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/controllers/MeprAccountCtrl.php#L388
1009
	 */
1010
	public function display_update_account_form( $sub_id, $errors = array(), $message = '' ) {
1011
1012
	}
1013
1014
	/**
1015
	 * Validate update account form.
1016
	 *
1017
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L368-369
1018
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/gateways/MeprStripeGateway.php#L1170-L1173
1019
	 *
1020
	 * @param  array $errors Array with errors.
1021
	 * @return array
1022
	 */
1023
	public function validate_update_account_form( $errors = array() ) {
1024
		return $errors;
1025
	}
1026
1027
	/**
1028
	 * Process update account form.
1029
	 *
1030
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L371-372
1031
	 * @link https://github.com/wp-premium/memberpress-basic/blob/1.3.18/app/gateways/MeprStripeGateway.php#L1175-L1181
1032
	 *
1033
	 * @param int $sub_id Subscription ID.
1034
	 */
1035
	public function process_update_account_form( $sub_id ) {
1036
1037
	}
1038
1039
	/**
1040
	 * Is test mode.
1041
	 *
1042
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L374-375
1043
	 *
1044
	 * @return boolean
1045
	 */
1046
	public function is_test_mode() {
1047
		return false;
1048
	}
1049
1050
	/**
1051
	 * Force SSL.
1052
	 *
1053
	 * @link https://gitlab.com/pronamic/memberpress/blob/1.2.4/app/lib/MeprBaseGateway.php#L377-378
1054
	 *
1055
	 * @return boolean
1056
	 */
1057
	public function force_ssl() {
1058
		return false;
1059
	}
1060
1061
	/**
1062
	 * Get config ID.
1063
	 *
1064
	 * @return string|int|null
1065
	 */
1066
	protected function get_config_id() {
1067
		// Get config ID setting.
1068
		$config_id = $this->settings->config_id;
1069
1070
		// Check empty config ID.
1071
		if ( empty( $config_id ) ) {
1072
			$config_id = \get_option( 'pronamic_pay_config_id' );
1073
		}
1074
1075
		// Check empty config ID.
1076
		if ( empty( $config_id ) ) {
1077
			$config_id = null;
1078
		}
1079
1080
		return $config_id;
1081
	}
1082
}
1083