Completed
Push — master ( 44551c...a66a0d )
by Devin
29:25 queued 11:45
created

process-purchase.php ➔ give_purchase_form_validate_gateway()   D

Complexity

Conditions 10
Paths 24

Size

Total Lines 41
Code Lines 17

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 110
Metric Value
cc 10
eloc 17
nc 24
nop 0
dl 0
loc 41
ccs 0
cts 19
cp 0
crap 110
rs 4.8196

How to fix   Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
0 ignored issues
show
Coding Style Compatibility introduced by
For compatibility and reusability of your code, PSR1 recommends that a file should introduce either new symbols (like classes, functions, etc.) or have side-effects (like outputting something, or including other files), but not both at the same time. The first symbol is defined on line 26 and the first side effect is on line 14.

The PSR-1: Basic Coding Standard recommends that a file should either introduce new symbols, that is classes, functions, constants or similar, or have side effects. Side effects are anything that executes logic, like for example printing output, changing ini settings or writing to a file.

The idea behind this recommendation is that merely auto-loading a class should not change the state of an application. It also promotes a cleaner style of programming and makes your code less prone to errors, because the logic is not spread out all over the place.

To learn more about the PSR-1, please see the PHP-FIG site on the PSR-1.

Loading history...
2
/**
3
 * Process Purchase
4
 *
5
 * @package     Give
6
 * @subpackage  Functions
7
 * @copyright   Copyright (c) 2016, WordImpress
8
 * @license     http://opensource.org/licenses/gpl-2.0.php GNU Public License
9
 * @since       1.0
10
 */
11
12
// Exit if accessed directly
13
if ( ! defined( 'ABSPATH' ) ) {
14
	exit;
15
}
16
17
/**
18
 * Process Purchase Form
19
 *
20
 * Handles the purchase form process.
21
 *
22
 * @access      private
23
 * @since       1.0
24
 * @return      void
25
 */
26
function give_process_purchase_form() {
27
28
	do_action( 'give_pre_process_purchase' );
29
30
	// Validate the form $_POST data
31
	$valid_data = give_purchase_form_validate_fields();
32
33
	// Allow themes and plugins to hook to errors
34
	do_action( 'give_checkout_error_checks', $valid_data, $_POST );
35
36
	$is_ajax = isset( $_POST['give_ajax'] );
37
38
	// Process the login form
39
	if ( isset( $_POST['give_login_submit'] ) ) {
40
		give_process_form_login();
41
	}
42
43
	// Validate the user
44
	$user = give_get_purchase_form_user( $valid_data );
45
46
	if ( give_get_errors() || ! $user ) {
47
		if ( $is_ajax ) {
48
			do_action( 'give_ajax_checkout_errors' );
49
			give_die();
50
		} else {
51
			return false;
52
		}
53
	}
54
55
	//If AJAX send back success to proceed with form submission
56
	if ( $is_ajax ) {
57
		echo 'success';
58
		give_die();
59
	}
60
61
	//After AJAX: Setup session if not using php_sessions
62
	if ( ! Give()->session->use_php_sessions() ) {
63
		//Double-check that set_cookie is publicly accessible;
64
		// we're using a slightly modified class-wp-sessions.php
65
		$session_reflection = new ReflectionMethod( 'WP_Session', 'set_cookie' );
66
		if ( $session_reflection->isPublic() ) {
67
			// Manually set the cookie.
68
			Give()->session->init()->set_cookie();
0 ignored issues
show
Bug introduced by
The method set_cookie cannot be called on Give()->session->init() (of type array).

Methods can only be called on objects. This check looks for methods being called on variables that have been inferred to never be objects.

Loading history...
69
		}
70
	}
71
72
	// Setup user information
73
	$user_info = array(
74
		'id'         => $user['user_id'],
75
		'email'      => $user['user_email'],
76
		'first_name' => $user['user_first'],
77
		'last_name'  => $user['user_last'],
78
		'address'    => $user['address']
79
	);
80
81
	$auth_key = defined( 'AUTH_KEY' ) ? AUTH_KEY : '';
82
83
	// Setup purchase information
84
	$purchase_data = array(
85
		'price'        => ( isset( $_POST['give-amount'] ) ? (float) apply_filters( 'give_donation_total', give_sanitize_amount( give_format_amount( $_POST['give-amount'] ) ) ) : '0.00' ),
86
		'purchase_key' => strtolower( md5( $user['user_email'] . date( 'Y-m-d H:i:s' ) . $auth_key . uniqid( 'give', true ) ) ),
87
		'user_email'   => $user['user_email'],
88
		'date'         => date( 'Y-m-d H:i:s', current_time( 'timestamp' ) ),
89
		'user_info'    => stripslashes_deep( $user_info ),
90
		'post_data'    => $_POST,
91
		'gateway'      => $valid_data['gateway'],
92
		'card_info'    => $valid_data['cc_info']
93
	);
94
95
	// Add the user data for hooks
96
	$valid_data['user'] = $user;
97
98
	// Allow themes and plugins to hook before the gateway
99
	do_action( 'give_checkout_before_gateway', $_POST, $user_info, $valid_data );
100
101
	//Sanity check for price
102
	if ( ! $purchase_data['price'] ) {
103
		// Revert to manual
104
		$purchase_data['gateway'] = 'manual';
105
		$_POST['give-gateway']    = 'manual';
106
	}
107
108
	// Allow the purchase data to be modified before it is sent to the gateway
109
	$purchase_data = apply_filters( 'give_purchase_data_before_gateway', $purchase_data, $valid_data );
110
111
	// Setup the data we're storing in the purchase session
112
	$session_data = $purchase_data;
113
114
	// Make sure credit card numbers are never stored in sessions
115
	unset( $session_data['card_info']['card_number'] );
116
	unset( $session_data['post_data']['card_number'] );
117
118
	// Used for showing data to non logged-in users after purchase, and for other plugins needing purchase data.
119
	give_set_purchase_session( $session_data );
120
121
	// Send info to the gateway for payment processing
122
	give_send_to_gateway( $purchase_data['gateway'], $purchase_data );
123
	give_die();
124
125
}
126
127
add_action( 'give_purchase', 'give_process_purchase_form' );
128
add_action( 'wp_ajax_give_process_checkout', 'give_process_purchase_form' );
129
add_action( 'wp_ajax_nopriv_give_process_checkout', 'give_process_purchase_form' );
130
131
/**
132
 * Process the checkout login form
133
 *
134
 * @access      private
135
 * @since       1.0
136
 * @return      void
137
 */
138
function give_process_form_login() {
139
140
	$is_ajax = isset( $_POST['give_ajax'] );
141
142
	$user_data = give_purchase_form_validate_user_login();
143
144
	if ( give_get_errors() || $user_data['user_id'] < 1 ) {
145
		if ( $is_ajax ) {
146
			do_action( 'give_ajax_checkout_errors' );
147
			give_die();
148
		} else {
149
			wp_redirect( $_SERVER['HTTP_REFERER'] );
150
			exit;
0 ignored issues
show
Coding Style Compatibility introduced by
The function give_process_form_login() contains an exit expression.

An exit expression should only be used in rare cases. For example, if you write a short command line script.

In most cases however, using an exit expression makes the code untestable and often causes incompatibilities with other libraries. Thus, unless you are absolutely sure it is required here, we recommend to refactor your code to avoid its usage.

Loading history...
151
		}
152
	}
153
154
	give_log_user_in( $user_data['user_id'], $user_data['user_login'], $user_data['user_pass'] );
155
156
	if ( $is_ajax ) {
157
		echo 'success';
158
		give_die();
159
	} else {
160
		wp_redirect( $_SERVER['HTTP_REFERER'] );
161
	}
162
}
163
164
add_action( 'wp_ajax_give_process_checkout_login', 'give_process_form_login' );
165
add_action( 'wp_ajax_nopriv_give_process_checkout_login', 'give_process_form_login' );
166
167
/**
168
 * Purchase Form Validate Fields
169
 *
170
 * @access      private
171
 * @since       1.0
172
 * @return      bool|array
173
 */
174
function give_purchase_form_validate_fields() {
175
176
	// Check if there is $_POST
177
	if ( empty( $_POST ) ) {
178
		return false;
179
	}
180
181
	$form_id = isset( $_POST['give-form-id'] ) ? $_POST['give-form-id'] : '';
182
183
	// Start an array to collect valid data
184
	$valid_data = array(
185
		'gateway'          => give_purchase_form_validate_gateway(), // Gateway fallback (amount is validated here)
186
		'need_new_user'    => false,     // New user flag
187
		'need_user_login'  => false,     // Login user flag
188
		'logged_user_data' => array(),   // Logged user collected data
189
		'new_user_data'    => array(),   // New user collected data
190
		'login_user_data'  => array(),   // Login user collected data
191
		'guest_user_data'  => array(),   // Guest user collected data
192
		'cc_info'          => give_purchase_form_validate_cc()    // Credit card info
193
	);
194
195
	// Validate agree to terms
196
	$terms_option = get_post_meta( $form_id, '_give_terms_option', true );
197
	if ( isset( $terms_option ) && $terms_option === 'yes' ) {
198
		give_purchase_form_validate_agree_to_terms();
199
	}
200
201
	if ( is_user_logged_in() ) {
202
		// Collect logged in user data
203
		$valid_data['logged_in_user'] = give_purchase_form_validate_logged_in_user();
204
	} else if ( isset( $_POST['give-purchase-var'] ) && $_POST['give-purchase-var'] == 'needs-to-register' ) {
205
		// Set new user registration as required
206
		$valid_data['need_new_user'] = true;
207
		// Validate new user data
208
		$valid_data['new_user_data'] = give_purchase_form_validate_new_user();
209
		// Check if login validation is needed
210
	} else if ( isset( $_POST['give-purchase-var'] ) && $_POST['give-purchase-var'] == 'needs-to-login' ) {
211
		// Set user login as required
212
		$valid_data['need_user_login'] = true;
213
		// Validate users login info
214
		$valid_data['login_user_data'] = give_purchase_form_validate_user_login();
215
	} else {
216
		// Not registering or logging in, so setup guest user data
217
		$valid_data['guest_user_data'] = give_purchase_form_validate_guest_user();
218
	}
219
220
	// Return collected data
221
	return $valid_data;
222
}
223
224
/**
225
 * Purchase Form Validate Gateway
226
 *
227
 * @description: Validate the gateway and donation amount
228
 *
229
 * @access      private
230
 * @since       1.0
231
 * @return      string
232
 */
233
function give_purchase_form_validate_gateway() {
234
235
	$form_id = isset( $_REQUEST['give-form-id'] ) ? $_REQUEST['give-form-id'] : 0;
236
	$amount  = isset( $_REQUEST['give-amount'] ) ? give_format_amount( give_get_form_minimum_price( $_REQUEST['give-amount'] ) ) : 0;
237
	$gateway = give_get_default_gateway( $form_id );
238
239
	// Check if a gateway value is present
240
	if ( ! empty( $_REQUEST['give-gateway'] ) ) {
241
242
		$gateway = sanitize_text_field( $_REQUEST['give-gateway'] );
243
244
		//Is amount being donated in LIVE mode 0.00? If so, error:
245
		if ( $amount == 0 && ! give_is_test_mode() ) {
246
247
			give_set_error( 'invalid_donation_amount', __( 'Please insert a valid donation amount.', 'give' ) );
248
249
		} //Check for a minimum custom amount
250
		elseif ( ! give_verify_minimum_price() ) {
251
252
			$minimum       = give_currency_filter( give_format_amount( give_get_form_minimum_price( $form_id ) ) );
253
			$error_message = __( 'This form has a minimum donation amount of %s', 'give' );
254
255
			give_set_error( 'invalid_donation_minimum', sprintf( $error_message, $minimum ) );
256
257
		} //Is this test mode zero donation? Let it through but set to manual gateway
258
		elseif ( $amount == 0 && give_is_test_mode() ) {
259
260
			$gateway = 'manual';
261
262
		} //Check if this gateway is active
263
		elseif ( ! give_is_gateway_active( $gateway ) ) {
264
265
			give_set_error( 'invalid_gateway', __( 'The selected payment gateway is not enabled', 'give' ) );
266
267
		}
268
269
	}
270
271
	return $gateway;
272
273
}
274
275
/**
276
 * Donation Form Validate Minimum Donation Amount
277
 *
278
 * @access      private
279
 * @since       1.3.6
280
 * @return      bool
281
 */
282
function give_verify_minimum_price() {
283
284
	$amount          = give_sanitize_amount( $_REQUEST['give-amount'] );
285
	$form_id         = isset( $_REQUEST['give-form-id'] ) ? $_REQUEST['give-form-id'] : 0;
286
	$price_id        = isset( $_REQUEST['give-price-id'] ) ? $_REQUEST['give-price-id'] : 0;
287
	$variable_prices = give_has_variable_prices( $form_id );
288
289
	if ( $variable_prices && ! empty( $price_id ) ) {
290
291
		$price_level_amount = give_get_price_option_amount( $form_id, $price_id );
292
293
		if ( $price_level_amount == $amount ) {
294
			return true;
295
		}
296
	}
297
298
	$minimum = give_get_form_minimum_price( $form_id );
299
300
	if ( $minimum > $amount ) {
301
		return false;
302
	}
303
304
	return true;
305
}
306
307
/**
308
 * Purchase Form Validate Agree To Terms
309
 *
310
 * @access      private
311
 * @since       1.0
312
 * @return      void
313
 */
314
function give_purchase_form_validate_agree_to_terms() {
315
	// Validate agree to terms
316
	if ( ! isset( $_POST['give_agree_to_terms'] ) || $_POST['give_agree_to_terms'] != 1 ) {
317
		// User did not agree
318
		give_set_error( 'agree_to_terms', apply_filters( 'give_agree_to_terms_text', __( 'You must agree to the terms of use', 'give' ) ) );
319
	}
320
}
321
322
/**
323
 * Purchase Form Required Fields
324
 *
325
 * @access      private
326
 * @since       1.0
327
 *
328
 * @param       $form_id
329
 *
330
 * @return      array
331
 */
332
function give_purchase_form_required_fields( $form_id ) {
333
334
	$payment_mode = give_get_chosen_gateway( $form_id );
335
336
	$required_fields = array(
337
		'give_email' => array(
338
			'error_id'      => 'invalid_email',
339
			'error_message' => __( 'Please enter a valid email address', 'give' )
340
		),
341
		'give_first' => array(
342
			'error_id'      => 'invalid_first_name',
343
			'error_message' => __( 'Please enter your first name', 'give' )
344
		)
345
	);
346
347
	$require_address = give_require_billing_address( $payment_mode );
348
349
	if ( $require_address ) {
350
		$required_fields['card_address']    = array(
351
			'error_id'      => 'invalid_card_address',
352
			'error_message' => __( 'Please enter your primary billing address', 'give' )
353
		);
354
		$required_fields['card_zip']        = array(
355
			'error_id'      => 'invalid_zip_code',
356
			'error_message' => __( 'Please enter your zip / postal code', 'give' )
357
		);
358
		$required_fields['card_city']       = array(
359
			'error_id'      => 'invalid_city',
360
			'error_message' => __( 'Please enter your billing city', 'give' )
361
		);
362
		$required_fields['billing_country'] = array(
363
			'error_id'      => 'invalid_country',
364
			'error_message' => __( 'Please select your billing country', 'give' )
365
		);
366
		$required_fields['card_state']      = array(
367
			'error_id'      => 'invalid_state',
368
			'error_message' => __( 'Please enter billing state / province', 'give' )
369
		);
370
	}
371
372
	return apply_filters( 'give_purchase_form_required_fields', $required_fields, $form_id );
373
374
}
375
376
/**
377
 * Check if the Billing Address is required
378
 *
379
 * @since  1.0.1
380
 *
381
 * @param $payment_mode
382
 *
383
 * @return mixed|void
384
 */
385
function give_require_billing_address( $payment_mode ) {
386
387
	$return = false;
388
389
	if ( isset( $_POST['billing_country'] ) || did_action( "give_{$payment_mode}_cc_form" ) || did_action( 'give_cc_form' ) ) {
390
		$return = true;
391
	}
392
393
	// Let payment gateways and other extensions determine if address fields should be required
394
	return apply_filters( 'give_require_billing_address', $return );
395
396
}
397
398
/**
399
 * Purchase Form Validate Logged In User
400
 *
401
 * @access      private
402
 * @since       1.0
403
 * @return      array
404
 */
405
function give_purchase_form_validate_logged_in_user() {
406
	global $user_ID;
0 ignored issues
show
Compatibility Best Practice introduced by
Use of global functionality is not recommended; it makes your code harder to test, and less reusable.

Instead of relying on global state, we recommend one of these alternatives:

1. Pass all data via parameters

function myFunction($a, $b) {
    // Do something
}

2. Create a class that maintains your state

class MyClass {
    private $a;
    private $b;

    public function __construct($a, $b) {
        $this->a = $a;
        $this->b = $b;
    }

    public function myFunction() {
        // Do something
    }
}
Loading history...
407
408
	$form_id = isset( $_POST['give-form-id'] ) ? $_POST['give-form-id'] : '';
409
410
	// Start empty array to collect valid user data
411
	$valid_user_data = array(
412
		// Assume there will be errors
413
		'user_id' => - 1
414
	);
415
416
	// Verify there is a user_ID
417
	if ( $user_ID > 0 ) {
418
		// Get the logged in user data
419
		$user_data = get_userdata( $user_ID );
420
421
		// Loop through required fields and show error messages
422
		foreach ( give_purchase_form_required_fields( $form_id ) as $field_name => $value ) {
423
			if ( in_array( $value, give_purchase_form_required_fields( $form_id ) ) && empty( $_POST[ $field_name ] ) ) {
424
				give_set_error( $value['error_id'], $value['error_message'] );
425
			}
426
		}
427
428
		// Verify data
429
		if ( $user_data ) {
430
			// Collected logged in user data
431
			$valid_user_data = array(
432
				'user_id'    => $user_ID,
433
				'user_email' => isset( $_POST['give_email'] ) ? sanitize_email( $_POST['give_email'] ) : $user_data->user_email,
434
				'user_first' => isset( $_POST['give_first'] ) && ! empty( $_POST['give_first'] ) ? sanitize_text_field( $_POST['give_first'] ) : $user_data->first_name,
435
				'user_last'  => isset( $_POST['give_last'] ) && ! empty( $_POST['give_last'] ) ? sanitize_text_field( $_POST['give_last'] ) : $user_data->last_name,
436
			);
437
438
			if ( ! is_email( $valid_user_data['user_email'] ) ) {
439
				give_set_error( 'email_invalid', __( 'Invalid email', 'give' ) );
440
			}
441
442
		} else {
443
			// Set invalid user error
444
			give_set_error( 'invalid_user', __( 'The user information is invalid', 'give' ) );
445
		}
446
	}
447
448
	// Return user data
449
	return $valid_user_data;
450
}
451
452
/**
453
 * Donate Form Validate New User
454
 *
455
 * @access      private
456
 * @since       1.0
457
 * @return      array
458
 */
459
function give_purchase_form_validate_new_user() {
460
461
	$registering_new_user = false;
462
	$form_id              = isset( $_POST['give-form-id'] ) ? $_POST['give-form-id'] : '';
463
464
	// Start an empty array to collect valid user data
465
	$valid_user_data = array(
466
		// Assume there will be errors
467
		'user_id'    => - 1,
468
		// Get first name
469
		'user_first' => isset( $_POST['give_first'] ) ? sanitize_text_field( $_POST['give_first'] ) : '',
470
		// Get last name
471
		'user_last'  => isset( $_POST['give_last'] ) ? sanitize_text_field( $_POST['give_last'] ) : '',
472
	);
473
474
	// Check the new user's credentials against existing ones
475
	$user_login   = isset( $_POST['give_user_login'] ) ? trim( $_POST['give_user_login'] ) : false;
476
	$user_email   = isset( $_POST['give_email'] ) ? trim( $_POST['give_email'] ) : false;
477
	$user_pass    = isset( $_POST['give_user_pass'] ) ? trim( $_POST['give_user_pass'] ) : false;
478
	$pass_confirm = isset( $_POST['give_user_pass_confirm'] ) ? trim( $_POST['give_user_pass_confirm'] ) : false;
479
480
	// Loop through required fields and show error messages
481
	foreach ( give_purchase_form_required_fields( $form_id ) as $field_name => $value ) {
482
		if ( in_array( $value, give_purchase_form_required_fields( $form_id ) ) && empty( $_POST[ $field_name ] ) ) {
483
			give_set_error( $value['error_id'], $value['error_message'] );
484
		}
485
	}
486
487
	// Check if we have an username to register
488
	if ( $user_login && strlen( $user_login ) > 0 ) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $user_login of type string|false is loosely compared to true; this is ambiguous if the string can be empty. You might want to explicitly use !== false instead.

In PHP, under loose comparison (like ==, or !=, or switch conditions), values of different types might be equal.

For string values, the empty string '' is a special case, in particular the following results might be unexpected:

''   == false // true
''   == null  // true
'ab' == false // false
'ab' == null  // false

// It is often better to use strict comparison
'' === false // false
'' === null  // false
Loading history...
489
		$registering_new_user = true;
490
491
		// We have an user name, check if it already exists
492
		if ( username_exists( $user_login ) ) {
493
			// Username already registered
494
			give_set_error( 'username_unavailable', __( 'Username already taken', 'give' ) );
495
			// Check if it's valid
496
		} else if ( ! give_validate_username( $user_login ) ) {
497
			// Invalid username
498
			if ( is_multisite() ) {
499
				give_set_error( 'username_invalid', __( 'Invalid username. Only lowercase letters (a-z) and numbers are allowed', 'give' ) );
500
			} else {
501
				give_set_error( 'username_invalid', __( 'Invalid username', 'give' ) );
502
			}
503
		} else {
504
			// All the checks have run and it's good to go
505
			$valid_user_data['user_login'] = $user_login;
506
		}
507
	} elseif ( give_logged_in_only( $form_id ) ) {
508
		give_set_error( 'registration_required', esc_html__( 'You must register or login to complete your donation', 'give' ) );
509
	}
510
511
	// Check if we have an email to verify
512
	if ( $user_email && strlen( $user_email ) > 0 ) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $user_email of type string|false is loosely compared to true; this is ambiguous if the string can be empty. You might want to explicitly use !== false instead.

In PHP, under loose comparison (like ==, or !=, or switch conditions), values of different types might be equal.

For string values, the empty string '' is a special case, in particular the following results might be unexpected:

''   == false // true
''   == null  // true
'ab' == false // false
'ab' == null  // false

// It is often better to use strict comparison
'' === false // false
'' === null  // false
Loading history...
513
		// Validate email
514
		if ( ! is_email( $user_email ) ) {
515
			give_set_error( 'email_invalid', __( 'Sorry, that email is invalid', 'give' ) );
516
			// Check if email exists
517
		} else if ( email_exists( $user_email ) && $registering_new_user ) {
518
			give_set_error( 'email_used', __( 'Sorry, that email already active for another user', 'give' ) );
519
		} else {
520
			// All the checks have run and it's good to go
521
			$valid_user_data['user_email'] = $user_email;
522
		}
523
	} else {
524
		// No email
525
		give_set_error( 'email_empty', __( 'Enter an email', 'give' ) );
526
	}
527
528
	// Check password
529
	if ( $user_pass && $pass_confirm ) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $user_pass of type string|false is loosely compared to true; this is ambiguous if the string can be empty. You might want to explicitly use !== false instead.

In PHP, under loose comparison (like ==, or !=, or switch conditions), values of different types might be equal.

For string values, the empty string '' is a special case, in particular the following results might be unexpected:

''   == false // true
''   == null  // true
'ab' == false // false
'ab' == null  // false

// It is often better to use strict comparison
'' === false // false
'' === null  // false
Loading history...
Bug Best Practice introduced by
The expression $pass_confirm of type string|false is loosely compared to true; this is ambiguous if the string can be empty. You might want to explicitly use !== false instead.

In PHP, under loose comparison (like ==, or !=, or switch conditions), values of different types might be equal.

For string values, the empty string '' is a special case, in particular the following results might be unexpected:

''   == false // true
''   == null  // true
'ab' == false // false
'ab' == null  // false

// It is often better to use strict comparison
'' === false // false
'' === null  // false
Loading history...
530
		// Verify confirmation matches
531
		if ( $user_pass != $pass_confirm ) {
532
			// Passwords do not match
533
			give_set_error( 'password_mismatch', __( 'Passwords don\'t match', 'give' ) );
534
		} else {
535
			// All is good to go
536
			$valid_user_data['user_pass'] = $user_pass;
537
		}
538
	} else {
539
		// Password or confirmation missing
540
		if ( ! $user_pass && $registering_new_user ) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $user_pass of type string|false is loosely compared to false; this is ambiguous if the string can be empty. You might want to explicitly use === false instead.

In PHP, under loose comparison (like ==, or !=, or switch conditions), values of different types might be equal.

For string values, the empty string '' is a special case, in particular the following results might be unexpected:

''   == false // true
''   == null  // true
'ab' == false // false
'ab' == null  // false

// It is often better to use strict comparison
'' === false // false
'' === null  // false
Loading history...
541
			// The password is invalid
542
			give_set_error( 'password_empty', __( 'Enter a password', 'give' ) );
543
		} else if ( ! $pass_confirm && $registering_new_user ) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $pass_confirm of type string|false is loosely compared to false; this is ambiguous if the string can be empty. You might want to explicitly use === false instead.

In PHP, under loose comparison (like ==, or !=, or switch conditions), values of different types might be equal.

For string values, the empty string '' is a special case, in particular the following results might be unexpected:

''   == false // true
''   == null  // true
'ab' == false // false
'ab' == null  // false

// It is often better to use strict comparison
'' === false // false
'' === null  // false
Loading history...
544
			// Confirmation password is invalid
545
			give_set_error( 'confirmation_empty', __( 'Enter the password confirmation', 'give' ) );
546
		}
547
	}
548
549
	return $valid_user_data;
550
}
551
552
/**
553
 * Donation Form Validate User Login
554
 *
555
 * @access      private
556
 * @since       1.0
557
 * @return      array
558
 */
559
function give_purchase_form_validate_user_login() {
560
561
	// Start an array to collect valid user data
562
	$valid_user_data = array(
563
		// Assume there will be errors
564
		'user_id' => - 1
565
	);
566
567
	// Username
568
	if ( ! isset( $_POST['give_user_login'] ) || $_POST['give_user_login'] == '' ) {
569
		give_set_error( 'must_log_in', __( 'You must login or register to complete your donation', 'give' ) );
570
571
		return $valid_user_data;
572
	}
573
574
	// Get the user by login
575
	$user_data = get_user_by( 'login', strip_tags( $_POST['give_user_login'] ) );
576
577
	// Check if user exists
578
	if ( $user_data ) {
579
		// Get password
580
		$user_pass = isset( $_POST['give_user_pass'] ) ? $_POST['give_user_pass'] : false;
581
582
		// Check user_pass
583
		if ( $user_pass ) {
584
			// Check if password is valid
585
			if ( ! wp_check_password( $user_pass, $user_data->user_pass, $user_data->ID ) ) {
586
				// Incorrect password
587
				give_set_error(
588
					'password_incorrect',
589
					sprintf(
590
						__( 'The password you entered is incorrect. %sReset Password%s', 'give' ),
591
						'<a href="' . wp_lostpassword_url( "http://$_SERVER[HTTP_HOST]$_SERVER[REQUEST_URI]" ) . '" title="' . __( 'Lost Password', 'give' ) . '">',
592
						'</a>'
593
					)
594
				);
595
				// All is correct
596
			} else {
597
				// Repopulate the valid user data array
598
				$valid_user_data = array(
599
					'user_id'    => $user_data->ID,
600
					'user_login' => $user_data->user_login,
601
					'user_email' => $user_data->user_email,
602
					'user_first' => $user_data->first_name,
603
					'user_last'  => $user_data->last_name,
604
					'user_pass'  => $user_pass,
605
				);
606
			}
607
		} else {
608
			// Empty password
609
			give_set_error( 'password_empty', __( 'Enter a password', 'give' ) );
610
		}
611
	} else {
612
		// no username
613
		give_set_error( 'username_incorrect', __( 'The username you entered does not exist', 'give' ) );
614
	}
615
616
	return $valid_user_data;
617
}
618
619
/**
620
 * Purchase Form Validate Guest User
621
 *
622
 * @access  private
623
 * @since   1.0
624
 * @return  array
625
 */
626
function give_purchase_form_validate_guest_user() {
627
628
	$form_id = isset( $_POST['give-form-id'] ) ? $_POST['give-form-id'] : '';
629
630
	// Start an array to collect valid user data
631
	$valid_user_data = array(
632
		// Set a default id for guests
633
		'user_id' => 0,
634
	);
635
636
	// Show error message if user must be logged in
637
	if ( give_logged_in_only( $form_id ) ) {
638
		give_set_error( 'logged_in_only', __( 'You must be logged into to donate', 'give' ) );
639
	}
640
641
	// Get the guest email
642
	$guest_email = isset( $_POST['give_email'] ) ? $_POST['give_email'] : false;
643
644
	// Check email
645
	if ( $guest_email && strlen( $guest_email ) > 0 ) {
646
		// Validate email
647
		if ( ! is_email( $guest_email ) ) {
648
			// Invalid email
649
			give_set_error( 'email_invalid', __( 'Invalid email', 'give' ) );
650
		} else {
651
			// All is good to go
652
			$valid_user_data['user_email'] = $guest_email;
653
		}
654
	} else {
655
		// No email
656
		give_set_error( 'email_empty', __( 'Enter an email', 'give' ) );
657
	}
658
659
	// Loop through required fields and show error messages
660
	foreach ( give_purchase_form_required_fields( $form_id ) as $field_name => $value ) {
661
		if ( in_array( $value, give_purchase_form_required_fields( $form_id ) ) && empty( $_POST[ $field_name ] ) ) {
662
			give_set_error( $value['error_id'], $value['error_message'] );
663
		}
664
	}
665
666
	return $valid_user_data;
667
}
668
669
/**
670
 * Register And Login New User
671
 *
672
 * @param array $user_data
673
 *
674
 * @access  private
675
 * @since   1.0
676
 * @return  integer
677
 */
678
function give_register_and_login_new_user( $user_data = array() ) {
679
	// Verify the array
680
	if ( empty( $user_data ) ) {
681
		return - 1;
682
	}
683
684
	if ( give_get_errors() ) {
685
		return - 1;
686
	}
687
688
	$user_args = apply_filters( 'give_insert_user_args', array(
689
		'user_login'      => isset( $user_data['user_login'] ) ? $user_data['user_login'] : '',
690
		'user_pass'       => isset( $user_data['user_pass'] ) ? $user_data['user_pass'] : '',
691
		'user_email'      => isset( $user_data['user_email'] ) ? $user_data['user_email'] : '',
692
		'first_name'      => isset( $user_data['user_first'] ) ? $user_data['user_first'] : '',
693
		'last_name'       => isset( $user_data['user_last'] ) ? $user_data['user_last'] : '',
694
		'user_registered' => date( 'Y-m-d H:i:s' ),
695
		'role'            => get_option( 'default_role' )
696
	), $user_data );
697
698
	// Insert new user
699
	$user_id = wp_insert_user( $user_args );
700
701
	// Validate inserted user
702
	if ( is_wp_error( $user_id ) ) {
703
		return - 1;
704
	}
705
706
	// Allow themes and plugins to filter the user data
707
	$user_data = apply_filters( 'give_insert_user_data', $user_data, $user_args );
708
709
	// Allow themes and plugins to hook
710
	do_action( 'give_insert_user', $user_id, $user_data );
711
712
	// Login new user
713
	give_log_user_in( $user_id, $user_data['user_login'], $user_data['user_pass'] );
714
715
	// Return user id
716
	return $user_id;
717
}
718
719
/**
720
 * Get Purchase Form User
721
 *
722
 * @param array $valid_data
723
 *
724
 * @access  private
725
 * @since   1.0
726
 * @return  array
727
 */
728
function give_get_purchase_form_user( $valid_data = array() ) {
729
730
	// Initialize user
731
	$user    = false;
732
	$is_ajax = defined( 'DOING_AJAX' ) && DOING_AJAX;
733
734
	if ( $is_ajax ) {
735
		// Do not create or login the user during the ajax submission (check for errors only)
736
		return true;
737
	} else if ( is_user_logged_in() ) {
738
		// Set the valid user as the logged in collected data
739
		$user = $valid_data['logged_in_user'];
740
	} else if ( $valid_data['need_new_user'] === true || $valid_data['need_user_login'] === true ) {
741
		// New user registration
742
		if ( $valid_data['need_new_user'] === true ) {
743
			// Set user
744
			$user = $valid_data['new_user_data'];
745
			// Register and login new user
746
			$user['user_id'] = give_register_and_login_new_user( $user );
747
			// User login
748
		} else if ( $valid_data['need_user_login'] === true && ! $is_ajax ) {
749
750
			/*
751
			 * The login form is now processed in the give_process_purchase_login() function.
752
			 * This is still here for backwards compatibility.
753
			 * This also allows the old login process to still work if a user removes the
754
			 * checkout login submit button.
755
			 *
756
			 * This also ensures that the donor is logged in correctly if they click "Purchase"
757
			 * instead of submitting the login form, meaning the donor is logged in during the purchase process.
758
			 */
759
760
			// Set user
761
			$user = $valid_data['login_user_data'];
762
			// Login user
763
			give_log_user_in( $user['user_id'], $user['user_login'], $user['user_pass'] );
764
		}
765
	}
766
767
	// Check guest checkout
768
	if ( false === $user && false === give_logged_in_only( $_POST['give-form-id'] ) ) {
769
		// Set user
770
		$user = $valid_data['guest_user_data'];
771
	}
772
773
	// Verify we have an user
774
	if ( false === $user || empty( $user ) ) {
775
		// Return false
776
		return false;
777
	}
778
779
	// Get user first name
780
	if ( ! isset( $user['user_first'] ) || strlen( trim( $user['user_first'] ) ) < 1 ) {
781
		$user['user_first'] = isset( $_POST["give_first"] ) ? strip_tags( trim( $_POST["give_first"] ) ) : '';
782
	}
783
784
	// Get user last name
785
	if ( ! isset( $user['user_last'] ) || strlen( trim( $user['user_last'] ) ) < 1 ) {
786
		$user['user_last'] = isset( $_POST["give_last"] ) ? strip_tags( trim( $_POST["give_last"] ) ) : '';
787
	}
788
789
	// Get the user's billing address details
790
	$user['address']            = array();
791
	$user['address']['line1']   = ! empty( $_POST['card_address'] ) ? sanitize_text_field( $_POST['card_address'] ) : false;
792
	$user['address']['line2']   = ! empty( $_POST['card_address_2'] ) ? sanitize_text_field( $_POST['card_address_2'] ) : false;
793
	$user['address']['city']    = ! empty( $_POST['card_city'] ) ? sanitize_text_field( $_POST['card_city'] ) : false;
794
	$user['address']['state']   = ! empty( $_POST['card_state'] ) ? sanitize_text_field( $_POST['card_state'] ) : false;
795
	$user['address']['country'] = ! empty( $_POST['billing_country'] ) ? sanitize_text_field( $_POST['billing_country'] ) : false;
796
	$user['address']['zip']     = ! empty( $_POST['card_zip'] ) ? sanitize_text_field( $_POST['card_zip'] ) : false;
797
798
	if ( empty( $user['address']['country'] ) ) {
799
		$user['address'] = false;
800
	} // Country will always be set if address fields are present
801
802
	if ( ! empty( $user['user_id'] ) && $user['user_id'] > 0 && ! empty( $user['address'] ) ) {
803
		// Store the address in the user's meta so the donation form can be pre-populated with it on return purchases
804
		update_user_meta( $user['user_id'], '_give_user_address', $user['address'] );
805
	}
806
807
	// Return valid user
808
	return $user;
809
}
810
811
/**
812
 * Validates the credit card info
813
 *
814
 * @access  private
815
 * @since   1.0
816
 * @return  array
817
 */
818
function give_purchase_form_validate_cc() {
819
820
	$card_data = give_get_purchase_cc_info();
821
822
	// Validate the card zip
823
	if ( ! empty( $card_data['card_zip'] ) ) {
824
		if ( ! give_purchase_form_validate_cc_zip( $card_data['card_zip'], $card_data['card_country'] ) ) {
825
			give_set_error( 'invalid_cc_zip', __( 'The zip / postal code you entered for your billing address is invalid', 'give' ) );
826
		}
827
	}
828
829
	//Ensure no spaces
830
	if ( ! empty( $card_data['card_number'] ) ) {
831
		$card_data['card_number'] = str_replace( '+', '', $card_data['card_number'] ); //no "+" signs
832
		$card_data['card_number'] = str_replace( ' ', '', $card_data['card_number'] ); // No spaces
833
	}
834
835
	// This should validate card numbers at some point too
836
	return $card_data;
837
}
838
839
/**
840
 * Get Credit Card Info
841
 *
842
 * @access  private
843
 * @since   1.0
844
 * @return  array
845
 */
846
function give_get_purchase_cc_info() {
847
	$cc_info                   = array();
848
	$cc_info['card_name']      = isset( $_POST['card_name'] ) ? sanitize_text_field( $_POST['card_name'] ) : '';
849
	$cc_info['card_number']    = isset( $_POST['card_number'] ) ? sanitize_text_field( $_POST['card_number'] ) : '';
850
	$cc_info['card_cvc']       = isset( $_POST['card_cvc'] ) ? sanitize_text_field( $_POST['card_cvc'] ) : '';
851
	$cc_info['card_exp_month'] = isset( $_POST['card_exp_month'] ) ? sanitize_text_field( $_POST['card_exp_month'] ) : '';
852
	$cc_info['card_exp_year']  = isset( $_POST['card_exp_year'] ) ? sanitize_text_field( $_POST['card_exp_year'] ) : '';
853
	$cc_info['card_address']   = isset( $_POST['card_address'] ) ? sanitize_text_field( $_POST['card_address'] ) : '';
854
	$cc_info['card_address_2'] = isset( $_POST['card_address_2'] ) ? sanitize_text_field( $_POST['card_address_2'] ) : '';
855
	$cc_info['card_city']      = isset( $_POST['card_city'] ) ? sanitize_text_field( $_POST['card_city'] ) : '';
856
	$cc_info['card_state']     = isset( $_POST['card_state'] ) ? sanitize_text_field( $_POST['card_state'] ) : '';
857
	$cc_info['card_country']   = isset( $_POST['billing_country'] ) ? sanitize_text_field( $_POST['billing_country'] ) : '';
858
	$cc_info['card_zip']       = isset( $_POST['card_zip'] ) ? sanitize_text_field( $_POST['card_zip'] ) : '';
859
860
	// Return cc info
861
	return $cc_info;
862
}
863
864
/**
865
 * Validate zip code based on country code
866
 *
867
 * @since  1.0
868
 *
869
 * @param int $zip
870
 * @param string $country_code
871
 *
872
 * @return bool|mixed|void
873
 */
874
function give_purchase_form_validate_cc_zip( $zip = 0, $country_code = '' ) {
875
	$ret = false;
876
877
	if ( empty( $zip ) || empty( $country_code ) ) {
878
		return $ret;
879
	}
880
881
	$country_code = strtoupper( $country_code );
882
883
	$zip_regex = array(
884
		"AD" => "AD\d{3}",
885
		"AM" => "(37)?\d{4}",
886
		"AR" => "^([A-Z]{1}\d{4}[A-Z]{3}|[A-Z]{1}\d{4}|\d{4})$",
887
		"AS" => "96799",
888
		"AT" => "\d{4}",
889
		"AU" => "^(0[289][0-9]{2})|([1345689][0-9]{3})|(2[0-8][0-9]{2})|(290[0-9])|(291[0-4])|(7[0-4][0-9]{2})|(7[8-9][0-9]{2})$",
890
		"AX" => "22\d{3}",
891
		"AZ" => "\d{4}",
892
		"BA" => "\d{5}",
893
		"BB" => "(BB\d{5})?",
894
		"BD" => "\d{4}",
895
		"BE" => "^[1-9]{1}[0-9]{3}$",
896
		"BG" => "\d{4}",
897
		"BH" => "((1[0-2]|[2-9])\d{2})?",
898
		"BM" => "[A-Z]{2}[ ]?[A-Z0-9]{2}",
899
		"BN" => "[A-Z]{2}[ ]?\d{4}",
900
		"BR" => "\d{5}[\-]?\d{3}",
901
		"BY" => "\d{6}",
902
		"CA" => "^[ABCEGHJKLMNPRSTVXY]{1}\d{1}[A-Z]{1} *\d{1}[A-Z]{1}\d{1}$",
903
		"CC" => "6799",
904
		"CH" => "^[1-9][0-9][0-9][0-9]$",
905
		"CK" => "\d{4}",
906
		"CL" => "\d{7}",
907
		"CN" => "\d{6}",
908
		"CR" => "\d{4,5}|\d{3}-\d{4}",
909
		"CS" => "\d{5}",
910
		"CV" => "\d{4}",
911
		"CX" => "6798",
912
		"CY" => "\d{4}",
913
		"CZ" => "\d{3}[ ]?\d{2}",
914
		"DE" => "\b((?:0[1-46-9]\d{3})|(?:[1-357-9]\d{4})|(?:[4][0-24-9]\d{3})|(?:[6][013-9]\d{3}))\b",
915
		"DK" => "^([D-d][K-k])?( |-)?[1-9]{1}[0-9]{3}$",
916
		"DO" => "\d{5}",
917
		"DZ" => "\d{5}",
918
		"EC" => "([A-Z]\d{4}[A-Z]|(?:[A-Z]{2})?\d{6})?",
919
		"EE" => "\d{5}",
920
		"EG" => "\d{5}",
921
		"ES" => "^([1-9]{2}|[0-9][1-9]|[1-9][0-9])[0-9]{3}$",
922
		"ET" => "\d{4}",
923
		"FI" => "\d{5}",
924
		"FK" => "FIQQ 1ZZ",
925
		"FM" => "(9694[1-4])([ \-]\d{4})?",
926
		"FO" => "\d{3}",
927
		"FR" => "^(F-)?((2[A|B])|[0-9]{2})[0-9]{3}$",
928
		"GE" => "\d{4}",
929
		"GF" => "9[78]3\d{2}",
930
		"GL" => "39\d{2}",
931
		"GN" => "\d{3}",
932
		"GP" => "9[78][01]\d{2}",
933
		"GR" => "\d{3}[ ]?\d{2}",
934
		"GS" => "SIQQ 1ZZ",
935
		"GT" => "\d{5}",
936
		"GU" => "969[123]\d([ \-]\d{4})?",
937
		"GW" => "\d{4}",
938
		"HM" => "\d{4}",
939
		"HN" => "(?:\d{5})?",
940
		"HR" => "\d{5}",
941
		"HT" => "\d{4}",
942
		"HU" => "\d{4}",
943
		"ID" => "\d{5}",
944
		"IE" => "((D|DUBLIN)?([1-9]|6[wW]|1[0-8]|2[024]))?",
945
		"IL" => "\d{5}",
946
		"IN" => "^[1-9][0-9][0-9][0-9][0-9][0-9]$", //india
947
		"IO" => "BBND 1ZZ",
948
		"IQ" => "\d{5}",
949
		"IS" => "\d{3}",
950
		"IT" => "^(V-|I-)?[0-9]{5}$",
951
		"JO" => "\d{5}",
952
		"JP" => "\d{3}-\d{4}",
953
		"KE" => "\d{5}",
954
		"KG" => "\d{6}",
955
		"KH" => "\d{5}",
956
		"KR" => "\d{3}[\-]\d{3}",
957
		"KW" => "\d{5}",
958
		"KZ" => "\d{6}",
959
		"LA" => "\d{5}",
960
		"LB" => "(\d{4}([ ]?\d{4})?)?",
961
		"LI" => "(948[5-9])|(949[0-7])",
962
		"LK" => "\d{5}",
963
		"LR" => "\d{4}",
964
		"LS" => "\d{3}",
965
		"LT" => "\d{5}",
966
		"LU" => "\d{4}",
967
		"LV" => "\d{4}",
968
		"MA" => "\d{5}",
969
		"MC" => "980\d{2}",
970
		"MD" => "\d{4}",
971
		"ME" => "8\d{4}",
972
		"MG" => "\d{3}",
973
		"MH" => "969[67]\d([ \-]\d{4})?",
974
		"MK" => "\d{4}",
975
		"MN" => "\d{6}",
976
		"MP" => "9695[012]([ \-]\d{4})?",
977
		"MQ" => "9[78]2\d{2}",
978
		"MT" => "[A-Z]{3}[ ]?\d{2,4}",
979
		"MU" => "(\d{3}[A-Z]{2}\d{3})?",
980
		"MV" => "\d{5}",
981
		"MX" => "\d{5}",
982
		"MY" => "\d{5}",
983
		"NC" => "988\d{2}",
984
		"NE" => "\d{4}",
985
		"NF" => "2899",
986
		"NG" => "(\d{6})?",
987
		"NI" => "((\d{4}-)?\d{3}-\d{3}(-\d{1})?)?",
988
		"NL" => "^[1-9][0-9]{3}\s?([a-zA-Z]{2})?$",
989
		"NO" => "\d{4}",
990
		"NP" => "\d{5}",
991
		"NZ" => "\d{4}",
992
		"OM" => "(PC )?\d{3}",
993
		"PF" => "987\d{2}",
994
		"PG" => "\d{3}",
995
		"PH" => "\d{4}",
996
		"PK" => "\d{5}",
997
		"PL" => "\d{2}-\d{3}",
998
		"PM" => "9[78]5\d{2}",
999
		"PN" => "PCRN 1ZZ",
1000
		"PR" => "00[679]\d{2}([ \-]\d{4})?",
1001
		"PT" => "\d{4}([\-]\d{3})?",
1002
		"PW" => "96940",
1003
		"PY" => "\d{4}",
1004
		"RE" => "9[78]4\d{2}",
1005
		"RO" => "\d{6}",
1006
		"RS" => "\d{5}",
1007
		"RU" => "\d{6}",
1008
		"SA" => "\d{5}",
1009
		"SE" => "^(s-|S-){0,1}[0-9]{3}\s?[0-9]{2}$",
1010
		"SG" => "\d{6}",
1011
		"SH" => "(ASCN|STHL) 1ZZ",
1012
		"SI" => "\d{4}",
1013
		"SJ" => "\d{4}",
1014
		"SK" => "\d{3}[ ]?\d{2}",
1015
		"SM" => "4789\d",
1016
		"SN" => "\d{5}",
1017
		"SO" => "\d{5}",
1018
		"SZ" => "[HLMS]\d{3}",
1019
		"TC" => "TKCA 1ZZ",
1020
		"TH" => "\d{5}",
1021
		"TJ" => "\d{6}",
1022
		"TM" => "\d{6}",
1023
		"TN" => "\d{4}",
1024
		"TR" => "\d{5}",
1025
		"TW" => "\d{3}(\d{2})?",
1026
		"UA" => "\d{5}",
1027
		"UK" => "^(GIR|[A-Z]\d[A-Z\d]??|[A-Z]{2}\d[A-Z\d]??)[ ]??(\d[A-Z]{2})$",
1028
		"US" => "^\d{5}([\-]?\d{4})?$",
1029
		"UY" => "\d{5}",
1030
		"UZ" => "\d{6}",
1031
		"VA" => "00120",
1032
		"VE" => "\d{4}",
1033
		"VI" => "008(([0-4]\d)|(5[01]))([ \-]\d{4})?",
1034
		"WF" => "986\d{2}",
1035
		"YT" => "976\d{2}",
1036
		"YU" => "\d{5}",
1037
		"ZA" => "\d{4}",
1038
		"ZM" => "\d{5}"
1039
	);
1040
1041
	if ( ! isset ( $zip_regex[ $country_code ] ) || preg_match( "/" . $zip_regex[ $country_code ] . "/i", $zip ) ) {
1042
		$ret = true;
1043
	}
1044
1045
	return apply_filters( 'give_is_zip_valid', $ret, $zip, $country_code );
1046
}
1047
1048
1049
/**
1050
 * Check the purchase to ensure a banned email is not allowed through
1051
 *
1052
 * @since       1.0
1053
 * @return      void
1054
 */
1055
function give_check_purchase_email( $valid_data, $posted ) {
0 ignored issues
show
Unused Code introduced by
The parameter $valid_data is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
1056
	$is_banned = false;
1057
	$banned    = give_get_banned_emails();
1058
1059
	if ( empty( $banned ) ) {
1060
		return;
1061
	}
1062
1063
	if ( is_user_logged_in() ) {
1064
1065
		// The user is logged in, check that their account email is not banned
1066
		$user_data = get_userdata( get_current_user_id() );
1067
		if ( give_is_email_banned( $user_data->user_email ) ) {
1068
1069
			$is_banned = true;
1070
		}
1071
1072
		if ( give_is_email_banned( $posted['give_email'] ) ) {
1073
			$is_banned = true;
1074
		}
1075
1076
	} elseif ( isset( $posted['give-purchase-var'] ) && $posted['give-purchase-var'] == 'needs-to-login' ) {
1077
1078
		// The user is logging in, check that their email is not banned
1079
		$user_data = get_user_by( 'login', $posted['give_user_login'] );
1080
		if ( $user_data && give_is_email_banned( $user_data->user_email ) ) {
1081
			$is_banned = true;
1082
		}
1083
1084
	} else {
1085
1086
		// Guest purchase, check that the email is not banned
1087
		if ( give_is_email_banned( $posted['give_email'] ) ) {
1088
			$is_banned = true;
1089
		}
1090
1091
	}
1092
1093
	if ( $is_banned ) {
1094
		// Set an error and give the donor a general error (don't alert them that they were banned)
1095
		give_set_error( 'email_banned', __( 'An internal error has occurred, please try again or contact support.', 'give' ) );
1096
	}
1097
}
1098
1099
add_action( 'give_checkout_error_checks', 'give_check_purchase_email', 10, 2 );
1100