Test Failed
Pull Request — master (#2054)
by Devin
05:04
created

functions.php ➔ give_get_price_id()   C

Complexity

Conditions 8
Paths 28

Size

Total Lines 30
Code Lines 13

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 72

Importance

Changes 0
Metric Value
cc 8
eloc 13
nc 28
nop 2
dl 0
loc 30
rs 5.3846
c 0
b 0
f 0
ccs 0
cts 0
cp 0
crap 72
1
<?php
2
/**
3
 * Payment Functions
4
 *
5
 * @package     Give
6
 * @subpackage  Payments
7
 * @copyright   Copyright (c) 2016, WordImpress
8
 * @license     https://opensource.org/licenses/gpl-license GNU Public License
9
 * @since       1.0
10
 */
11
12
// Exit if accessed directly.
13
if ( ! defined( 'ABSPATH' ) ) {
14
	exit;
15
}
16
17
/**
18
 * Get Payments
19
 *
20
 * Retrieve payments from the database.
21
 *
22
 * Since 1.0, this function takes an array of arguments, instead of individual
23
 * parameters. All of the original parameters remain, but can be passed in any
24
 * order via the array.
25
 *
26
 * @since 1.0
27
 *
28
 * @param array $args {
29
 *                        Optional. Array of arguments passed to payments query.
30
 *
31
 * @type int $offset The number of payments to offset before retrieval.
32
 *                            Default is 0.
33
 * @type int $number The number of payments to query for. Use -1 to request all
34
 *                            payments. Default is 20.
35
 * @type string $mode Default is 'live'.
36
 * @type string $order Designates ascending or descending order of payments.
37
 *                            Accepts 'ASC', 'DESC'. Default is 'DESC'.
38 42
 * @type string $orderby Sort retrieved payments by parameter. Default is 'ID'.
39 42
 * @type string $status The status of the payments. Default is 'any'.
40 42
 * @type string $user User. Default is null.
41
 * @type string $meta_key Custom field key. Default is null.
42 42
 * }
43 42
 *
44
 * @return array $payments Payments retrieved from the database
45 42
 */
46
function give_get_payments( $args = array() ) {
47
48
	// Fallback to post objects to ensure backwards compatibility.
49
	if ( ! isset( $args['output'] ) ) {
50
		$args['output'] = 'posts';
51
	}
52
53
	$args     = apply_filters( 'give_get_payments_args', $args );
54
	$payments = new Give_Payments_Query( $args );
55
56
	return $payments->get_payments();
57
}
58
59
/**
60 42
 * Retrieve payment by a given field
61
 *
62
 * @since  1.0
63
 *
64 42
 * @param  string $field The field to retrieve the payment with.
65
 * @param  mixed $value The value for $field.
66 42
 *
67 42
 * @return mixed
68 42
 */
69
function give_get_payment_by( $field = '', $value = '' ) {
70 42
71
	if ( empty( $field ) || empty( $value ) ) {
72
		return false;
73
	}
74 42
75
	switch ( strtolower( $field ) ) {
76
77
		case 'id':
78
			$payment = new Give_Payment( $value );
79
			$id      = $payment->ID;
80
81
			if ( empty( $id ) ) {
82
				return false;
83
			}
84
85
			break;
86
87 View Code Duplication
		case 'key':
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
88
			$payment = give_get_payments( array(
89
				'meta_key'       => '_give_payment_purchase_key',
0 ignored issues
show
introduced by
Detected usage of meta_key, possible slow query.
Loading history...
90
				'meta_value'     => $value,
0 ignored issues
show
introduced by
Detected usage of meta_value, possible slow query.
Loading history...
91
				'posts_per_page' => 1,
92
				'fields'         => 'ids',
93
			) );
94
95
			if ( $payment ) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $payment of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using ! empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
96
				$payment = new Give_Payment( $payment[0] );
97
			}
98
99
			break;
100
101 View Code Duplication
		case 'payment_number':
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
102
			$payment = give_get_payments( array(
103
				'meta_key'       => '_give_payment_number',
0 ignored issues
show
introduced by
Detected usage of meta_key, possible slow query.
Loading history...
104
				'meta_value'     => $value,
0 ignored issues
show
introduced by
Detected usage of meta_value, possible slow query.
Loading history...
105
				'posts_per_page' => 1,
106 42
				'fields'         => 'ids',
107
			) );
108 42
109 42
			if ( $payment ) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $payment of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using ! empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
110
				$payment = new Give_Payment( $payment[0] );
111
			}
112
113
			break;
114
115
		default:
116
			return false;
117
	}// End switch().
118
119
	if ( $payment ) {
120
		return $payment;
121
	}
122
123
	return false;
124
}
125
126 52
/**
127
 * Insert Payment
128
 *
129
 * @since  1.0
130 52
 *
131 52
 * @param  array $payment_data Arguments passed.
132 52
 *
133 52
 * @return int|bool Payment ID if payment is inserted, false otherwise.
134 52
 */
135 52
function give_insert_payment( $payment_data = array() ) {
136
137
	if ( empty( $payment_data ) ) {
138 52
		return false;
139 52
	}
140 52
141 52
	$payment    = new Give_Payment();
142 52
	$gateway    = ! empty( $payment_data['gateway'] ) ? $payment_data['gateway'] : '';
143 52
	$gateway    = empty( $gateway ) && isset( $_POST['give-gateway'] ) ? $_POST['give-gateway'] : $gateway;
0 ignored issues
show
introduced by
Detected access of super global var $_POST, probably need manual inspection.
Loading history...
introduced by
Detected usage of a non-sanitized input variable: $_POST
Loading history...
144 52
	$form_id    = isset( $payment_data['give_form_id'] ) ? $payment_data['give_form_id'] : 0;
145 52
	$price_id   = give_get_payment_meta_price_id( $payment_data );
146 52
	$form_title = isset( $payment_data['give_form_title'] ) ? $payment_data['give_form_title'] : get_the_title( $form_id );
147 52
148 52
	// Set properties.
149 52
	$payment->total          = $payment_data['price'];
150 52
	$payment->status         = ! empty( $payment_data['status'] ) ? $payment_data['status'] : 'pending';
151 52
	$payment->currency       = ! empty( $payment_data['currency'] ) ? $payment_data['currency'] : give_get_currency();
152 52
	$payment->user_info      = $payment_data['user_info'];
153 52
	$payment->gateway        = $gateway;
154 52
	$payment->form_title     = $form_title;
155
	$payment->form_id        = $form_id;
156
	$payment->price_id       = $price_id;
157
	$payment->donor_id       = ( ! empty( $payment_data['donor_id'] ) ? $payment_data['donor_id'] : '' );
158 52
	$payment->user_id        = $payment_data['user_info']['id'];
159 52
	$payment->email          = $payment_data['user_email'];
160 52
	$payment->first_name     = $payment_data['user_info']['first_name'];
161 52
	$payment->last_name      = $payment_data['user_info']['last_name'];
162
	$payment->email          = $payment_data['user_info']['email'];
163 52
	$payment->ip             = give_get_ip();
164
	$payment->key            = $payment_data['purchase_key'];
165
	$payment->mode           = ( ! empty( $payment_data['mode'] ) ? (string) $payment_data['mode'] : ( give_is_test_mode() ? 'test' : 'live' ) );
166 52
	$payment->parent_payment = ! empty( $payment_data['parent'] ) ? absint( $payment_data['parent'] ) : '';
167
168
	// Add the donation.
169
	$args = array(
170
		'price'    => $payment->total,
171 52
		'price_id' => $payment->price_id,
172 20
	);
173 20
174 20
	$payment->add_donation( $payment->form_id, $args );
175 20
0 ignored issues
show
Coding Style introduced by
Functions must not contain multiple empty lines in a row; found 2 empty lines
Loading history...
176
177
	// Set date if present.
178 52
	if ( isset( $payment_data['post_date'] ) ) {
179
		$payment->date = $payment_data['post_date'];
180
	}
181 52
182
	// Handle sequential payments.
183
	if ( give_get_option( 'enable_sequential' ) ) {
184 52
		$number          = give_get_next_payment_number();
185
		$payment->number = give_format_payment_number( $number );
186
		update_option( 'give_last_payment_number', $number );
187 52
	}
188 52
189
	// Save payment.
190
	$payment->save();
191
192
	/**
193
	 * Fires while inserting payments.
194
	 *
195
	 * @since 1.0
196
	 *
197
	 * @param int $payment_id The payment ID.
198
	 * @param array $payment_data Arguments passed.
199
	 */
200
	do_action( 'give_insert_payment', $payment->ID, $payment_data );
201
202
	// Return payment ID upon success.
203
	if ( ! empty( $payment->ID ) ) {
204
		return $payment->ID;
205
	}
206
207
	// Return false if no payment was inserted.
208 35
	return false;
209 35
210 35
}
211
212 35
/**
213
 * Create payment.
214
 *
215
 * @param $payment_data
216
 *
217
 * @return bool|int
218
 */
219
function give_create_payment( $payment_data ) {
220
221
	$form_id  = intval( $payment_data['post_data']['give-form-id'] );
222
	$price_id = isset( $payment_data['post_data']['give-price-id'] ) ? $payment_data['post_data']['give-price-id'] : '';
223
224
	// Collect payment data.
225
	$insert_payment_data = array(
226
		'price'           => $payment_data['price'],
227
		'give_form_title' => $payment_data['post_data']['give-form-title'],
228
		'give_form_id'    => $form_id,
229 31
		'give_price_id'   => $price_id,
230
		'date'            => $payment_data['date'],
231 31
		'user_email'      => $payment_data['user_email'],
232 31
		'purchase_key'    => $payment_data['purchase_key'],
233 31
		'currency'        => give_get_currency(),
234 31
		'user_info'       => $payment_data['user_info'],
235 31
		'status'          => 'pending',
236
		'gateway'         => 'paypal',
237
	);
238 31
239 31
	/**
240
	 * Filter the payment params.
241 31
	 *
242
	 * @since 1.8
243 31
	 *
244 16
	 * @param array $insert_payment_data
245 16
	 */
246
	$insert_payment_data = apply_filters( 'give_create_payment', $insert_payment_data );
247 31
248
	// Record the pending payment.
249
	return give_insert_payment( $insert_payment_data );
250 14
}
251
252 14
/**
253
 * Updates a payment status.
254 14
 *
255
 * @since  1.0
256
 *
257
 * @param  int $payment_id Payment ID.
258
 * @param  string $new_status New Payment Status. Default is 'publish'.
259
 *
260
 * @return bool
261 14
 */
262
function give_update_payment_status( $payment_id, $new_status = 'publish' ) {
263 31
264
	$updated = false;
265 31
	$payment = new Give_Payment( $payment_id );
266
267
	if ( $payment && $payment->ID > 0 ) {
268 1
269
		$payment->status = $new_status;
270 1
		$updated         = $payment->save();
271
272
	}
273 31
274
	return $updated;
275
}
276 31
277 31
278 31
/**
279
 * Deletes a Donation
280
 *
281 31
 * @since  1.0
282
 * @global      $give_logs
283 31
 *
284 31
 * @param  int $payment_id Payment ID (default: 0).
285 31
 * @param  bool $update_donor If we should update the donor stats (default:true).
286
 *
287 31
 * @return void
288 31
 */
289
function give_delete_donation( $payment_id = 0, $update_donor = true ) {
290
	global $give_logs;
291
292
	$payment  = new Give_Payment( $payment_id );
293
	$amount   = give_get_payment_amount( $payment_id );
294
	$status   = $payment->post_status;
295
	$donor_id = give_get_payment_donor_id( $payment_id );
296
	$donor    = new Give_Donor( $donor_id );
0 ignored issues
show
Documentation introduced by
$donor_id is of type integer, but the function expects a boolean.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
297
298
	// Only undo donations that aren't these statuses.
299
	$dont_undo_statuses = apply_filters( 'give_undo_donation_statuses', array(
300
		'pending',
301
		'cancelled',
302 20
	) );
303
304
	if ( ! in_array( $status, $dont_undo_statuses ) ) {
305
		give_undo_donation( $payment_id );
306
	}
307 20
308
	if ( $status == 'publish' ) {
0 ignored issues
show
introduced by
Found "== '". Use Yoda Condition checks, you must
Loading history...
309 20
310 20
		// Only decrease earnings if they haven't already been decreased (or were never increased for this payment).
311
		give_decrease_total_earnings( $amount );
312 18
313 18
		// @todo: Refresh only range related stat cache
314
		give_delete_donation_stats();
315 20
316 20
		if ( $donor->id && $update_donor ) {
317
318 18
			// Decrement the stats for the donor.
319 18
			$donor->decrease_donation_count();
320
			$donor->decrease_value( $amount );
321 20
322
		}
323
	}
324
325
	/**
326
	 * Fires before deleting payment.
327
	 *
328
	 * @since 1.0
329
	 *
330
	 * @param int $payment_id Payment ID.
331
	 */
332
	do_action( 'give_payment_delete', $payment_id );
333
334
	if ( $donor->id && $update_donor ) {
335
336
		// Remove the payment ID from the donor.
337 6
		$donor->remove_payment( $payment_id );
338
339
	}
340 6
341 6
	// Remove the payment.
342 6
	wp_delete_post( $payment_id, true );
343 6
344 6
	// Remove related sale log entries.
345 6
	$give_logs->delete_logs( null, 'sale', array(
346
		array(
347 6
			'key'   => '_give_log_payment_id',
348
			'value' => $payment_id,
349 6
		),
350 6
	) );
351 6
352
	/**
353
	 * Fires after payment deleted.
354 6
	 *
355
	 * @since 1.0
356
	 *
357
	 * @param int $payment_id Payment ID.
358
	 */
359
	do_action( 'give_payment_deleted', $payment_id );
360
}
361
362
/**
363
 * Undo Donation
364
 *
365
 * Undoes a donation, including the decrease of donations and earning stats.
366
 * Used for when refunding or deleting a donation.
367
 *
368
 * @since  1.0
369
 *
370
 * @param  int $payment_id Payment ID.
371
 *
372
 * @return void
373 6
 */
374
function give_undo_donation( $payment_id ) {
375
376
	$payment = new Give_Payment( $payment_id );
377
378
	$maybe_decrease_earnings = apply_filters( 'give_decrease_earnings_on_undo', true, $payment, $payment->form_id );
379
	if ( true === $maybe_decrease_earnings ) {
380
		// Decrease earnings.
381
		give_decrease_earnings( $payment->form_id, $payment->total );
382
	}
383
384
	$maybe_decrease_donations = apply_filters( 'give_decrease_donations_on_undo', true, $payment, $payment->form_id );
385
	if ( true === $maybe_decrease_donations ) {
386
		// Decrease donation count.
387
		give_decrease_donation_count( $payment->form_id );
388
	}
389
390
}
391
392
393
/**
394
 * Count Payments
395
 *
396
 * Returns the total number of payments recorded.
397
 *
398
 * @since  1.0
399
 *
400
 * @param  array $args Arguments passed.
401
 *
402
 * @return object $stats Contains the number of payments per payment status.
403
 */
404
function give_count_payments( $args = array() ) {
405
406
	global $wpdb;
407
408
	$defaults = array(
409
		'user'       => null,
410
		's'          => null,
411
		'start-date' => null,
412
		'end-date'   => null,
413
		'form_id'    => null,
414
	);
415
416
	$args = wp_parse_args( $args, $defaults );
417
418
	$select = 'SELECT p.post_status,count( * ) AS num_posts';
419
	$join   = '';
420 6
	$where  = "WHERE p.post_type = 'give_payment' AND p.post_status IN ('" . implode( "','", give_get_payment_status_keys() ) . "')";
421
422
	// Count payments for a specific user.
423
	if ( ! empty( $args['user'] ) ) {
424
425
		if ( is_email( $args['user'] ) ) {
426 6
			$field = 'email';
427
		} elseif ( is_numeric( $args['user'] ) ) {
428
			$field = 'id';
429
		} else {
430
			$field = '';
431
		}
432
433
		$join = "LEFT JOIN $wpdb->postmeta m ON (p.ID = m.post_id)";
434
435
		if ( ! empty( $field ) ) {
436
			$where .= "
437
				AND m.meta_key = '_give_payment_user_{$field}'
438
				AND m.meta_value = '{$args['user']}'";
439
		}
440
	} elseif ( ! empty( $args['donor'] ) ) {
441
442
		$join  = "LEFT JOIN $wpdb->postmeta m ON (p.ID = m.post_id)";
443
		$where .= "
444
			AND m.meta_key = '_give_payment_customer_id'
445
			AND m.meta_value = '{$args['donor']}'";
446
447
		// Count payments for a search.
448 6
	} elseif ( ! empty( $args['s'] ) ) {
449
450
		if ( is_email( $args['s'] ) || strlen( $args['s'] ) == 32 ) {
451
452
			if ( is_email( $args['s'] ) ) {
453
				$field = '_give_payment_user_email';
454
			} else {
455
				$field = '_give_payment_purchase_key';
456
			}
457
458
			$join  = "LEFT JOIN $wpdb->postmeta m ON (p.ID = m.post_id)";
459
			$where .= $wpdb->prepare( '
460
                AND m.meta_key = %s
461
                AND m.meta_value = %s', $field, $args['s'] );
462
463
		} elseif ( '#' == substr( $args['s'], 0, 1 ) ) {
464
465
			$search = str_replace( '#:', '', $args['s'] );
466 6
			$search = str_replace( '#', '', $search );
467 6
468
			$select = 'SELECT p.post_status,count( * ) AS num_posts ';
469
			$join   = '';
470 6
			$where  = $wpdb->prepare( 'WHERE p.post_type=%s  AND p.ID = %d ', 'give_payment', $search );
471 6
472 6
		} elseif ( is_numeric( $args['s'] ) ) {
473
474 6
			$join  = "LEFT JOIN $wpdb->postmeta m ON (p.ID = m.post_id)";
475
			$where .= $wpdb->prepare( "
476 6
				AND m.meta_key = '_give_payment_user_id'
477
				AND m.meta_value = %d", $args['s'] );
478 6
479 6
		} else {
480
			$search = $wpdb->esc_like( $args['s'] );
481
			$search = '%' . $search . '%';
482
483 6
			$where .= $wpdb->prepare( 'AND ((p.post_title LIKE %s) OR (p.post_content LIKE %s))', $search, $search );
484
		}// End if().
485 6
	}// End if().
486 6
487 6
	if ( ! empty( $args['form_id'] ) && is_numeric( $args['form_id'] ) ) {
488 6
489 6
		$join  = "LEFT JOIN $wpdb->postmeta m ON (p.ID = m.post_id)";
490
		$where .= $wpdb->prepare( '
491 6
                AND m.meta_key = %s
492 6
                AND m.meta_value = %s', '_give_payment_form_id', $args['form_id'] );
493 6
	}
494
495 6
	// Limit payments count by date.
496
	if ( ! empty( $args['start-date'] ) && false !== strpos( $args['start-date'], '/' ) ) {
497 6
498
		$date_parts = explode( '/', $args['start-date'] );
499
		$month      = ! empty( $date_parts[0] ) && is_numeric( $date_parts[0] ) ? $date_parts[0] : 0;
500
		$day        = ! empty( $date_parts[1] ) && is_numeric( $date_parts[1] ) ? $date_parts[1] : 0;
501 6
		$year       = ! empty( $date_parts[2] ) && is_numeric( $date_parts[2] ) ? $date_parts[2] : 0;
502 6
503
		$is_date = checkdate( $month, $day, $year );
504 6 View Code Duplication
		if ( false !== $is_date ) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
505 6
506
			$date  = new DateTime( $args['start-date'] );
507 6
			$where .= $wpdb->prepare( " AND p.post_date >= '%s'", $date->format( 'Y-m-d' ) );
508
509
		}
510
511
		// Fixes an issue with the payments list table counts when no end date is specified (with stats class).
512
		if ( empty( $args['end-date'] ) ) {
513
			$args['end-date'] = $args['start-date'];
514
		}
515
	}
516
517
	if ( ! empty( $args['end-date'] ) && false !== strpos( $args['end-date'], '/' ) ) {
518
519
		$date_parts = explode( '/', $args['end-date'] );
520
521
		$month = ! empty( $date_parts[0] ) ? $date_parts[0] : 0;
522
		$day   = ! empty( $date_parts[1] ) ? $date_parts[1] : 0;
523
		$year  = ! empty( $date_parts[2] ) ? $date_parts[2] : 0;
524
525
		$is_date = checkdate( $month, $day, $year );
526 View Code Duplication
		if ( false !== $is_date ) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
527
528
			$date  = new DateTime( $args['end-date'] );
529
			$where .= $wpdb->prepare( " AND p.post_date <= '%s'", $date->format( 'Y-m-d' ) );
530
531
		}
532
	}
533
534
	$where = apply_filters( 'give_count_payments_where', $where );
535
	$join  = apply_filters( 'give_count_payments_join', $join );
536
537
	$query = "$select
538
		FROM $wpdb->posts p
539
		$join
540
		$where
541
		GROUP BY p.post_status
542
	";
543
544
	$cache_key = md5( $query );
545
546
	$count = wp_cache_get( $cache_key, 'counts' );
547
	if ( false !== $count ) {
548
		return $count;
549
	}
550
551
	$count = $wpdb->get_results( $query, ARRAY_A );
0 ignored issues
show
introduced by
Usage of a direct database call is discouraged.
Loading history...
552
553
	$stats    = array();
554
	$statuses = get_post_stati();
555
	if ( isset( $statuses['private'] ) && empty( $args['s'] ) ) {
556
		unset( $statuses['private'] );
557
	}
558
559
	foreach ( $statuses as $state ) {
560
		$stats[ $state ] = 0;
561
	}
562
563
	foreach ( (array) $count as $row ) {
564
565
		if ( 'private' == $row['post_status'] && empty( $args['s'] ) ) {
566
			continue;
567
		}
568
569
		$stats[ $row['post_status'] ] = $row['num_posts'];
570
	}
571
572
	$stats = (object) $stats;
573
	wp_cache_set( $cache_key, $stats, 'counts' );
574
575
	return $stats;
576
}
577
578
579 52
/**
580 52
 * Check For Existing Payment
581 52
 *
582 52
 * @since  1.0
583 52
 *
584 52
 * @param  int $payment_id Payment ID
585 52
 *
586 52
 * @return bool $exists True if payment exists, false otherwise.
587 52
 */
588
function give_check_for_existing_payment( $payment_id ) {
589 52
	$exists  = false;
590
	$payment = new Give_Payment( $payment_id );
591
592
	if ( $payment_id === $payment->ID && 'publish' === $payment->status ) {
593
		$exists = true;
594
	}
595
596
	return $exists;
597
}
598
599
/**
600
 * Get Payment Status
601 52
 *
602 52
 * @since 1.0
603
 *
604 52
 * @param WP_Post|Give_Payment|int $payment Payment object or payment ID.
605
 * @param bool $return_label Whether to return the translated status label
606
 *                                           instead of status value. Default false.
607
 *
608
 * @return bool|mixed True if payment status exists, false otherwise.
609
 */
610
function give_get_payment_status( $payment, $return_label = false ) {
611
612
	if ( is_numeric( $payment ) ) {
613
614
		$payment = new Give_Payment( $payment );
615
616
		if ( ! $payment->ID > 0 ) {
617
			return false;
618
		}
0 ignored issues
show
introduced by
Blank line found after control structure
Loading history...
619
620
	}
621
622
	if ( ! is_object( $payment ) || ! isset( $payment->post_status ) ) {
623
		return false;
624
	}
625
626
	$statuses = give_get_payment_statuses();
627
628
	if ( ! is_array( $statuses ) || empty( $statuses ) ) {
629
		return false;
630
	}
631
632
	// Get payment object if not already given.
633
	$payment = $payment instanceof Give_Payment ? $payment : new Give_Payment( $payment->ID );
634
635
	if ( array_key_exists( $payment->status, $statuses ) ) {
636
		if ( true === $return_label ) {
637
			// Return translated status label.
638
			return $statuses[ $payment->status ];
639
		} else {
640
			// Account that our 'publish' status is labeled 'Complete'
641
			$post_status = 'publish' == $payment->status ? 'Complete' : $payment->post_status;
642
643
			// Make sure we're matching cases, since they matter
644
			return array_search( strtolower( $post_status ), array_map( 'strtolower', $statuses ) );
645
		}
646
	}
647
648
	return false;
649
}
650
651
/**
652
 * Retrieves all available statuses for payments.
653
 *
654
 * @since  1.0
655
 *
656
 * @return array $payment_status All the available payment statuses.
657
 */
658
function give_get_payment_statuses() {
659
	$payment_statuses = array(
660
		'pending'     => __( 'Pending', 'give' ),
661
		'publish'     => __( 'Complete', 'give' ),
662
		'refunded'    => __( 'Refunded', 'give' ),
663
		'failed'      => __( 'Failed', 'give' ),
664
		'cancelled'   => __( 'Cancelled', 'give' ),
665
		'abandoned'   => __( 'Abandoned', 'give' ),
666
		'preapproval' => __( 'Pre-Approved', 'give' ),
667
		'processing'  => __( 'Processing', 'give' ),
668
		'revoked'     => __( 'Revoked', 'give' ),
669
	);
670
671
	return apply_filters( 'give_payment_statuses', $payment_statuses );
672
}
673
674
/**
675
 * Get Payment Status Keys
676
 *
677
 * Retrieves keys for all available statuses for payments
678
 *
679
 * @since  1.0
680
 *
681
 * @return array $payment_status All the available payment statuses.
682
 */
683
function give_get_payment_status_keys() {
684
	$statuses = array_keys( give_get_payment_statuses() );
685
	asort( $statuses );
686
687
	return array_values( $statuses );
688
}
689
690
/**
691
 * Get Earnings By Date
692
 *
693
 * @since  1.0
694
 *
695
 * @param  int $day Day number. Default is null.
696
 * @param  int $month_num Month number. Default is null.
697
 * @param  int $year Year number. Default is null.
698
 * @param  int $hour Hour number. Default is null.
699
 *
700
 * @return int $earnings  Earnings
701
 */
702
function give_get_earnings_by_date( $day = null, $month_num, $year = null, $hour = null ) {
703
704
	// This is getting deprecated soon. Use Give_Payment_Stats with the get_earnings() method instead.
705
	global $wpdb;
706
707
	$args = array(
708
		'post_type'              => 'give_payment',
709
		'nopaging'               => true,
0 ignored issues
show
introduced by
Disabling pagination is prohibited in VIP context, do not set nopaging to true ever.
Loading history...
710
		'year'                   => $year,
711
		'monthnum'               => $month_num,
712
		'post_status'            => array( 'publish' ),
713
		'fields'                 => 'ids',
714
		'update_post_term_cache' => false,
715
	);
716
	if ( ! empty( $day ) ) {
717
		$args['day'] = $day;
718
	}
719
720
	if ( ! empty( $hour ) ) {
721
		$args['hour'] = $hour;
722
	}
723
724
	$args = apply_filters( 'give_get_earnings_by_date_args', $args );
725
	$key  = Give_Cache::get_key( 'give_stats', $args );
726
727 View Code Duplication
	if ( ! empty( $_GET['_wpnonce'] ) && wp_verify_nonce( $_GET['_wpnonce'], 'give-refresh-reports' ) ) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
728
		$earnings = false;
729
	} else {
730
		$earnings = Give_Cache::get( $key );
731
	}
732
733
	if ( false === $earnings ) {
734
		$donations = get_posts( $args );
735
		$earnings  = 0;
736
		if ( $donations ) {
737
			$donations = implode( ',', $donations );
738
739
			$earnings = $wpdb->get_var( "SELECT SUM(meta_value) FROM $wpdb->postmeta WHERE meta_key = '_give_payment_total' AND post_id IN ({$donations})" );
0 ignored issues
show
introduced by
Usage of a direct database call is discouraged.
Loading history...
introduced by
Usage of a direct database call without caching is prohibited. Use wp_cache_get / wp_cache_set.
Loading history...
740
741
		}
742
		// Cache the results for one hour.
743
		Give_Cache::set( $key, $earnings, HOUR_IN_SECONDS );
744
	}
745
746
	return round( $earnings, 2 );
747
}
748
749
/**
750
 * Get Donations (sales) By Date
751
 *
752
 * @since  1.0
753
 *
754
 * @param  int $day Day number. Default is null.
755
 * @param  int $month_num Month number. Default is null.
756
 * @param  int $year Year number. Default is null.
757
 * @param  int $hour Hour number. Default is null.
758
 *
759
 * @return int $count     Sales
760
 */
761
function give_get_sales_by_date( $day = null, $month_num = null, $year = null, $hour = null ) {
762
763
	// This is getting deprecated soon. Use Give_Payment_Stats with the get_sales() method instead.
764
	$args = array(
765
		'post_type'              => 'give_payment',
766
		'nopaging'               => true,
0 ignored issues
show
introduced by
Disabling pagination is prohibited in VIP context, do not set nopaging to true ever.
Loading history...
767
		'year'                   => $year,
768
		'fields'                 => 'ids',
769
		'post_status'            => array( 'publish' ),
770 5
		'update_post_meta_cache' => false,
771
		'update_post_term_cache' => false,
772 5
	);
773
774
	$show_free = apply_filters( 'give_sales_by_date_show_free', true, $args );
775
776
	if ( false === $show_free ) {
777
		$args['meta_query'] = array(
0 ignored issues
show
introduced by
Detected usage of meta_query, possible slow query.
Loading history...
778
			array(
779
				'key'     => '_give_payment_total',
780
				'value'   => 0,
781
				'compare' => '>',
782
				'type'    => 'NUMERIC',
783 42
			),
784
		);
785
	}
786 42
787
	if ( ! empty( $month_num ) ) {
788 42
		$args['monthnum'] = $month_num;
789
	}
790 42
791
	if ( ! empty( $day ) ) {
792 42
		$args['day'] = $day;
793
	}
794 42
795
	if ( ! empty( $hour ) ) {
796 42
		$args['hour'] = $hour;
797 42
	}
798 42
799 42
	$args = apply_filters( 'give_get_sales_by_date_args', $args );
800
801 42
	$key = Give_Cache::get_key( 'give_stats', $args );
802
803 View Code Duplication
	if ( ! empty( $_GET['_wpnonce'] ) && wp_verify_nonce( $_GET['_wpnonce'], 'give-refresh-reports' ) ) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
804 42
		$count = false;
805 42
	} else {
806
		$count = Give_Cache::get( $key );
807
	}
808
809
	if ( false === $count ) {
810
		$donations = new WP_Query( $args );
811
		$count     = (int) $donations->post_count;
812
		// Cache the results for one hour.
813 42
		Give_Cache::set( $key, $count, HOUR_IN_SECONDS );
814 42
	}
815 42
816
	return $count;
817 42
}
818
819
/**
820
 * Checks whether a payment has been marked as complete.
821
 *
822 42
 * @since  1.0
823
 *
824
 * @param  int $payment_id Payment ID to check against.
825 42
 *
826
 * @return bool $ret True if complete, false otherwise.
827
 */
828 42
function give_is_payment_complete( $payment_id ) {
829 42
	$payment = new Give_Payment( $payment_id );
830 42
831
	$ret = false;
832 42
833
	if ( $payment->ID > 0 ) {
834
835
		if ( (int) $payment_id === (int) $payment->ID && 'publish' == $payment->status ) {
836 42
			$ret = true;
837
		}
838
	}
839
840
	return apply_filters( 'give_is_payment_complete', $ret, $payment_id, $payment->post_status );
841
}
842
843
/**
844
 * Get Total Donations.
845
 *
846
 * @since  1.0
847
 *
848
 * @return int $count Total number of donations.
849 42
 */
850 42
function give_get_total_donations() {
851 42
852
	$payments = give_count_payments();
853 42
854
	return $payments->publish;
855
}
856
857
/**
858
 * Get Total Earnings
859
 *
860
 * @since  1.0
861
 *
862
 * @param bool $recalculate Recalculate earnings forcefully.
863
 *
864
 * @return float $total Total earnings.
865
 */
866 19
function give_get_total_earnings( $recalculate = false ) {
867 19
868 19
	$total = get_option( 'give_earnings_total', 0 );
869
870
	// Calculate total earnings.
871 19
	if ( ! $total || $recalculate ) {
872
		global $wpdb;
873 19
874
		$total = (float) 0;
875
876
		$args = apply_filters( 'give_get_total_earnings_args', array(
877
			'offset' => 0,
878
			'number' => - 1,
879
			'status' => array( 'publish' ),
880
			'fields' => 'ids',
881
		) );
882
883
		$payments = give_get_payments( $args );
884
		if ( $payments ) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $payments of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using ! empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
885
886
			/**
887
			 * If performing a donation, we need to skip the very last payment in the database,
888 42
			 * since it calls give_increase_total_earnings() on completion,
889
			 * which results in duplicated earnings for the very first donation.
890 42
			 */
891
			if ( did_action( 'give_update_payment_status' ) ) {
892
				array_pop( $payments );
893
			}
894
895
			if ( ! empty( $payments ) ) {
896
				$payments = implode( ',', $payments );
897
				$total    += $wpdb->get_var( "SELECT SUM(meta_value) FROM $wpdb->postmeta WHERE meta_key = '_give_payment_total' AND post_id IN({$payments})" );
0 ignored issues
show
introduced by
Usage of a direct database call is discouraged.
Loading history...
introduced by
Usage of a direct database call without caching is prohibited. Use wp_cache_get / wp_cache_set.
Loading history...
898
			}
899
		}
900
901
		update_option( 'give_earnings_total', $total, 'no' );
902
	}
903
904 18
	if ( $total < 0 ) {
905
		$total = 0; // Don't ever show negative earnings.
906 18
	}
907
908
	return apply_filters( 'give_total_earnings', round( $total, give_currency_decimal_filter() ) );
909
}
910
911
/**
912
 * Increase the Total Earnings
913
 *
914
 * @since  1.0
915
 *
916
 * @param  int $amount The amount you would like to increase the total earnings by.
917
 *                       Default is 0.
918
 *
919
 * @return float $total  Total earnings.
920
 */
921
function give_increase_total_earnings( $amount = 0 ) {
922
	$total = give_get_total_earnings();
923
	$total += $amount;
924
	update_option( 'give_earnings_total', $total );
925
926
	return $total;
927
}
928
929
/**
930
 * Decrease the Total Earnings
931
 *
932
 * @since 1.0
933
 *
934
 * @param int $amount The amount you would like to decrease the total earnings by.
935
 *
936
 * @return float $total Total earnings.
937
 */
938
function give_decrease_total_earnings( $amount = 0 ) {
939
	$total = give_get_total_earnings();
940
	$total -= $amount;
941
	if ( $total < 0 ) {
942
		$total = 0;
943
	}
944
	update_option( 'give_earnings_total', $total );
945
946
	return $total;
947
}
948
949
/**
950 42
 * Get Payment Meta for a specific Payment
951
 *
952 42
 * @since 1.0
953
 *
954
 * @param int $payment_id Payment ID.
955
 * @param string $meta_key The meta key to pull.
956
 * @param bool $single Pull single meta entry or as an object.
957
 *
958
 * @return mixed $meta Payment Meta.
959
 */
960
function give_get_payment_meta( $payment_id = 0, $meta_key = '_give_payment_meta', $single = true ) {
961
	$payment = new Give_Payment( $payment_id );
962
963
	return $payment->get_meta( $meta_key, $single );
964
}
965
966
/**
967
 * Update the meta for a payment
968
 *
969
 * @param  int $payment_id Payment ID.
970
 * @param  string $meta_key Meta key to update.
971
 * @param  string $meta_value Value to update to.
972
 * @param  string $prev_value Previous value.
973
 *
974
 * @return mixed Meta ID if successful, false if unsuccessful.
975
 */
976
function give_update_payment_meta( $payment_id = 0, $meta_key = '', $meta_value = '', $prev_value = '' ) {
977
	$payment = new Give_Payment( $payment_id );
978
979
	return $payment->update_meta( $meta_key, $meta_value, $prev_value );
980
}
981
982
/**
983
 * Get the user_info Key from Payment Meta
984
 *
985
 * @since 1.0
986
 *
987
 * @param int $payment_id Payment ID.
988
 *
989
 * @return array $user_info User Info Meta Values.
990
 */
991
function give_get_payment_meta_user_info( $payment_id ) {
992
	$payment = new Give_Payment( $payment_id );
993
994
	return $payment->user_info;
995
}
996 31
997
/**
998 31
 * Get the donations Key from Payment Meta
999
 *
1000
 * Retrieves the form_id from a (Previously titled give_get_payment_meta_donations)
1001
 *
1002
 * @since 1.0
1003
 *
1004
 * @param int $payment_id Payment ID.
1005
 *
1006
 * @return int $form_id Form ID.
1007
 */
1008
function give_get_payment_form_id( $payment_id ) {
1009
	$payment = new Give_Payment( $payment_id );
1010
1011
	return $payment->form_id;
1012
}
1013
1014
/**
1015
 * Get the user email associated with a payment
1016
 *
1017
 * @since 1.0
1018
 *
1019
 * @param int $payment_id Payment ID.
1020
 *
1021
 * @return string $email User email.
1022
 */
1023
function give_get_payment_user_email( $payment_id ) {
1024
	$payment = new Give_Payment( $payment_id );
1025
1026
	return $payment->email;
1027
}
1028
1029
/**
1030
 * Is the payment provided associated with a user account
1031
 *
1032
 * @since  1.3
1033
 *
1034
 * @param  int $payment_id The payment ID.
1035
 *
1036
 * @return bool $is_guest_payment If the payment is associated with a user (false) or not (true)
1037
 */
1038
function give_is_guest_payment( $payment_id ) {
1039
	$payment_user_id  = give_get_payment_user_id( $payment_id );
1040
	$is_guest_payment = ! empty( $payment_user_id ) && $payment_user_id > 0 ? false : true;
1041
1042
	return (bool) apply_filters( 'give_is_guest_payment', $is_guest_payment, $payment_id );
1043
}
1044
1045
/**
1046
 * Get the user ID associated with a payment
1047
 *
1048
 * @since 1.3
1049
 *
1050
 * @param int $payment_id Payment ID.
1051
 *
1052
 * @return int $user_id User ID.
1053
 */
1054
function give_get_payment_user_id( $payment_id ) {
1055
	$payment = new Give_Payment( $payment_id );
1056
1057
	return $payment->user_id;
1058
}
1059
1060
/**
1061
 * Get the donor ID associated with a payment.
1062
 *
1063
 * @since 1.0
1064
 *
1065
 * @param int $payment_id Payment ID.
1066
 *
1067
 * @return int $payment->customer_id Donor ID.
1068
 */
1069
function give_get_payment_donor_id( $payment_id ) {
1070
	$payment = new Give_Payment( $payment_id );
1071
1072
	return $payment->customer_id;
1073
}
1074
1075
/**
1076
 * Get the IP address used to make a donation
1077
 *
1078
 * @since 1.0
1079
 *
1080
 * @param int $payment_id Payment ID.
1081
 *
1082
 * @return string $ip User IP.
1083
 */
1084
function give_get_payment_user_ip( $payment_id ) {
1085
	$payment = new Give_Payment( $payment_id );
1086 52
1087
	return $payment->ip;
1088 52
}
1089
1090
/**
1091
 * Get the date a payment was completed
1092
 *
1093
 * @since 1.0
1094
 *
1095
 * @param int $payment_id Payment ID.
1096
 *
1097
 * @return string $date The date the payment was completed.
1098
 */
1099
function give_get_payment_completed_date( $payment_id = 0 ) {
1100
	$payment = new Give_Payment( $payment_id );
1101
1102
	return $payment->completed_date;
1103
}
1104
1105
/**
1106
 * Get the gateway associated with a payment
1107
 *
1108
 * @since 1.0
1109
 *
1110
 * @param int $payment_id Payment ID.
1111
 *
1112
 * @return string $gateway Gateway.
1113
 */
1114
function give_get_payment_gateway( $payment_id ) {
1115
	$payment = new Give_Payment( $payment_id );
1116
1117
	return $payment->gateway;
1118
}
1119 20
1120
/**
1121
 * Get the currency code a payment was made in
1122
 *
1123 20
 * @since 1.0
1124
 *
1125
 * @param int $payment_id Payment ID.
1126
 *
1127 20
 * @return string $currency The currency code.
1128 20
 */
1129 20
function give_get_payment_currency_code( $payment_id = 0 ) {
1130
	$payment = new Give_Payment( $payment_id );
1131 20
1132
	return $payment->currency;
1133 20
}
1134
1135
/**
1136
 * Get the currency name a payment was made in
1137
 *
1138
 * @since 1.0
1139
 *
1140
 * @param int $payment_id Payment ID.
1141
 *
1142
 * @return string $currency The currency name.
1143
 */
1144
function give_get_payment_currency( $payment_id = 0 ) {
1145
	$currency = give_get_payment_currency_code( $payment_id );
1146 20
1147
	return apply_filters( 'give_payment_currency', give_get_currency_name( $currency ), $payment_id );
1148
}
1149
1150 20
/**
1151 20
 * Get the key for a donation
1152 20
 *
1153
 * @since 1.0
1154 20
 *
1155
 * @param int $payment_id Payment ID.
1156 2
 *
1157
 * @return string $key Donation key.
1158
 */
1159
function give_get_payment_key( $payment_id = 0 ) {
1160
	$payment = new Give_Payment( $payment_id );
1161
1162
	return $payment->key;
1163 2
}
1164
1165
/**
1166 20
 * Get the payment order number
1167 20
 *
1168 20
 * This will return the payment ID if sequential order numbers are not enabled or the order number does not exist
1169 20
 *
1170 20
 * @since 1.0
1171
 *
1172 20
 * @param int $payment_id Payment ID.
1173 20
 *
1174
 * @return string $number Payment order number.
1175 20
 */
1176
function give_get_payment_number( $payment_id = 0 ) {
1177
	$payment = new Give_Payment( $payment_id );
1178
1179
	return $payment->number;
1180
}
1181 20
1182
/**
1183
 * Formats the payment number with the prefix and postfix
1184
 *
1185
 * @since  1.3
1186
 *
1187 20
 * @param  int $number The payment number to format.
1188 20
 *
1189
 * @return string      The formatted payment number.
1190
 */
1191
function give_format_payment_number( $number ) {
1192
1193 20
	if ( ! give_get_option( 'enable_sequential' ) ) {
1194
		return $number;
1195 20
	}
1196 2
1197 2
	if ( ! is_numeric( $number ) ) {
1198
		return $number;
1199 20
	}
1200
1201
	$prefix  = give_get_option( 'sequential_prefix' );
1202
	$number  = absint( $number );
1203
	$postfix = give_get_option( 'sequential_postfix' );
1204
1205
	$formatted_number = $prefix . $number . $postfix;
1206
1207
	return apply_filters( 'give_format_payment_number', $formatted_number, $prefix, $number, $postfix );
1208
}
1209
1210
/**
1211
 * Gets the next available order number
1212
 *
1213
 * This is used when inserting a new payment
1214
 *
1215
 * @since 1.0
1216
 * @return string $number The next available payment number.
1217
 */
1218
function give_get_next_payment_number() {
1219
1220
	if ( ! give_get_option( 'enable_sequential' ) ) {
1221
		return false;
1222
	}
1223
1224
	$number           = get_option( 'give_last_payment_number' );
1225
	$start            = give_get_option( 'sequential_start', 1 );
1226
	$increment_number = true;
1227
1228
	if ( false !== $number ) {
1229
1230
		if ( empty( $number ) ) {
1231
1232
			$number           = $start;
1233
			$increment_number = false;
1234
1235
		}
1236
	} else {
1237
1238
		// This case handles the first addition of the new option, as well as if it get's deleted for any reason.
1239
		$payments     = new Give_Payments_Query( array(
1240
			'number'  => 1,
1241
			'order'   => 'DESC',
1242
			'orderby' => 'ID',
1243
			'output'  => 'posts',
1244
			'fields'  => 'ids',
1245
		) );
1246
		$last_payment = $payments->get_payments();
1247
1248
		if ( ! empty( $last_payment ) ) {
1249
1250
			$number = give_get_payment_number( $last_payment[0] );
1251
1252
		}
1253
1254
		if ( ! empty( $number ) && $number !== (int) $last_payment[0] ) {
1255
1256
			$number = give_remove_payment_prefix_postfix( $number );
1257
1258
		} else {
1259
1260
			$number           = $start;
1261
			$increment_number = false;
1262
		}
1263 52
	}// End if().
1264
1265 52
	$increment_number = apply_filters( 'give_increment_payment_number', $increment_number, $number );
1266
1267
	if ( $increment_number ) {
1268
		$number ++;
1269
	}
1270
1271
	return apply_filters( 'give_get_next_payment_number', $number );
1272
}
1273
1274
/**
1275
 * Given a given a number, remove the pre/postfix
1276
 *
1277
 * @since  1.3
1278
 *
1279
 * @param  string $number The formatted Current Number to increment.
1280
 *
1281
 * @return string The new Payment number without prefix and postfix.
1282
 */
1283
function give_remove_payment_prefix_postfix( $number ) {
1284
1285
	$prefix  = give_get_option( 'sequential_prefix' );
1286
	$postfix = give_get_option( 'sequential_postfix' );
1287
1288
	// Remove prefix.
1289
	$number = preg_replace( '/' . $prefix . '/', '', $number, 1 );
1290
1291
	// Remove the postfix.
1292
	$length      = strlen( $number );
1293
	$postfix_pos = strrpos( $number, $postfix );
1294
	if ( false !== $postfix_pos ) {
1295
		$number = substr_replace( $number, '', $postfix_pos, $length );
1296
	}
1297
1298
	// Ensure it's a whole number.
1299
	$number = intval( $number );
1300
1301
	return apply_filters( 'give_remove_payment_prefix_postfix', $number, $prefix, $postfix );
1302
1303
}
1304
1305
1306
/**
1307
 * Get Payment Amount
1308
 *
1309
 * Get the fully formatted payment amount. The payment amount is retrieved using give_get_payment_amount() and is then
1310
 * sent through give_currency_filter() and  give_format_amount() to format the amount correctly.
1311
 *
1312
 * @since       1.0
1313
 *
1314
 * @param int $payment_id Payment ID.
1315
 *
1316
 * @return string $amount Fully formatted payment amount.
1317
 */
1318
function give_payment_amount( $payment_id = 0 ) {
1319
	$amount = give_get_payment_amount( $payment_id );
1320
1321
	return give_currency_filter( give_format_amount( $amount, array( 'sanitize' => false ) ), give_get_payment_currency_code( $payment_id ) );
1322
}
1323
1324
/**
1325
 * Get the amount associated with a payment
1326
 *
1327
 * @access public
1328
 * @since  1.0
1329
 *
1330
 * @param int $payment_id Payment ID.
1331
 *
1332
 * @return mixed
1333
 */
1334
function give_get_payment_amount( $payment_id ) {
1335
1336
	$payment = new Give_Payment( $payment_id );
1337
1338
	return apply_filters( 'give_payment_amount', floatval( $payment->total ), $payment_id );
1339
}
1340
1341
/**
1342
 * Payment Subtotal
1343
 *
1344
 * Retrieves subtotal for payment and then returns a full formatted amount. This
1345
 * function essentially calls give_get_payment_subtotal()
1346
 *
1347 18
 * @since 1.5
1348
 *
1349
 * @param int $payment_id Payment ID.
1350
 *
1351 18
 * @see   give_get_payment_subtotal()
1352
 *
1353 18
 * @return array Fully formatted payment subtotal.
1354
 */
1355
function give_payment_subtotal( $payment_id = 0 ) {
1356
	$subtotal = give_get_payment_subtotal( $payment_id );
1357
1358
	return give_currency_filter( give_format_amount( $subtotal, array( 'sanitize' => false ) ), give_get_payment_currency_code( $payment_id ) );
1359
}
1360
1361
/**
1362
 * Get Payment Subtotal
1363
 *
1364
 * Retrieves subtotal for payment and then returns a non formatted amount.
1365
 *
1366
 * @since 1.5
1367
 *
1368
 * @param int $payment_id Payment ID.
1369
 *
1370
 * @return float $subtotal Subtotal for payment (non formatted).
1371
 */
1372
function give_get_payment_subtotal( $payment_id = 0 ) {
1373
	$payment = new Give_Payment( $payment_id );
1374
1375
	return $payment->subtotal;
1376
}
1377
1378
/**
1379
 * Retrieves the donation ID
1380
 *
1381
 * @since  1.0
1382
 *
1383
 * @param int $payment_id Payment ID.
1384
 *
1385
 * @return string The donation ID.
1386
 */
1387
function give_get_payment_transaction_id( $payment_id = 0 ) {
1388
	$payment = new Give_Payment( $payment_id );
1389
1390
	return $payment->transaction_id;
1391
}
1392
1393
/**
1394
 * Sets a Transaction ID in post meta for the given Payment ID.
1395
 *
1396
 * @since  1.0
1397
 *
1398
 * @param int $payment_id Payment ID.
1399
 * @param string $transaction_id The transaction ID from the gateway.
1400
 *
1401
 * @return bool|mixed
1402
 */
1403
function give_set_payment_transaction_id( $payment_id = 0, $transaction_id = '' ) {
1404
1405
	if ( empty( $payment_id ) || empty( $transaction_id ) ) {
1406
		return false;
1407
	}
1408
1409
	$transaction_id = apply_filters( 'give_set_payment_transaction_id', $transaction_id, $payment_id );
1410
1411
	return give_update_payment_meta( $payment_id, '_give_payment_transaction_id', $transaction_id );
1412
}
1413
1414
/**
1415
 * Retrieve the donation ID based on the key
1416
 *
1417
 * @since 1.0
1418
 * @global object $wpdb Used to query the database using the WordPress Database API.
1419
 *
1420
 * @param string $key the key to search for.
1421
 *
1422
 * @return int $purchase Donation ID.
1423
 */
1424 View Code Duplication
function give_get_purchase_id_by_key( $key ) {
0 ignored issues
show
Duplication introduced by
This function seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
1425
	global $wpdb;
1426
1427
	$purchase = $wpdb->get_var( $wpdb->prepare( "SELECT post_id FROM $wpdb->postmeta WHERE meta_key = '_give_payment_purchase_key' AND meta_value = %s LIMIT 1", $key ) );
0 ignored issues
show
introduced by
Usage of a direct database call is discouraged.
Loading history...
introduced by
Usage of a direct database call without caching is prohibited. Use wp_cache_get / wp_cache_set.
Loading history...
1428
1429
	if ( $purchase != null ) {
1430
		return $purchase;
1431
	}
1432
1433
	return 0;
1434
}
1435
1436
1437
/**
1438
 * Retrieve the donation ID based on the transaction ID
1439
 *
1440
 * @since 1.3
1441
 * @global object $wpdb Used to query the database using the WordPress Database API.
1442 52
 *
1443
 * @param string $key The transaction ID to search for.
1444
 *
1445
 * @return int $purchase Donation ID.
1446 52
 */
1447 View Code Duplication
function give_get_purchase_id_by_transaction_id( $key ) {
0 ignored issues
show
Duplication introduced by
This function seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
1448 52
	global $wpdb;
1449 52
1450 52
	$purchase = $wpdb->get_var( $wpdb->prepare( "SELECT post_id FROM $wpdb->postmeta WHERE meta_key = '_give_payment_transaction_id' AND meta_value = %s LIMIT 1", $key ) );
0 ignored issues
show
introduced by
Usage of a direct database call is discouraged.
Loading history...
introduced by
Usage of a direct database call without caching is prohibited. Use wp_cache_get / wp_cache_set.
Loading history...
1451 52
1452 52
	if ( $purchase != null ) {
1453 52
		return $purchase;
1454 52
	}
1455 52
1456 52
	return 0;
1457 52
}
1458 52
1459 52
/**
1460
 * Retrieve all notes attached to a donation
1461
 *
1462 52
 * @since 1.0
1463
 *
1464 52
 * @param int $payment_id The donation ID to retrieve notes for.
1465
 * @param string $search Search for notes that contain a search term.
1466 52
 *
1467
 * @return array $notes Donation Notes
1468
 */
1469
function give_get_payment_notes( $payment_id = 0, $search = '' ) {
1470
1471
	if ( empty( $payment_id ) && empty( $search ) ) {
1472
		return false;
1473
	}
1474
1475
	remove_action( 'pre_get_comments', 'give_hide_payment_notes', 10 );
1476
	remove_filter( 'comments_clauses', 'give_hide_payment_notes_pre_41', 10 );
1477
1478
	$notes = get_comments( array(
1479
		'post_id' => $payment_id,
1480
		'order'   => 'ASC',
1481
		'search'  => $search,
1482
	) );
1483
1484
	add_action( 'pre_get_comments', 'give_hide_payment_notes', 10 );
1485
	add_filter( 'comments_clauses', 'give_hide_payment_notes_pre_41', 10, 2 );
1486
1487
	return $notes;
1488
}
1489
1490
1491
/**
1492
 * Add a note to a payment
1493
 *
1494
 * @since 1.0
1495
 *
1496
 * @param int $payment_id The payment ID to store a note for.
1497
 * @param string $note The note to store.
1498
 *
1499
 * @return int The new note ID
1500
 */
1501
function give_insert_payment_note( $payment_id = 0, $note = '' ) {
1502
	if ( empty( $payment_id ) ) {
1503
		return false;
1504
	}
1505
1506
	/**
1507
	 * Fires before inserting payment note.
1508
	 *
1509
	 * @since 1.0
1510
	 *
1511
	 * @param int $payment_id Payment ID.
1512
	 * @param string $note The note.
1513
	 */
1514
	do_action( 'give_pre_insert_payment_note', $payment_id, $note );
1515
1516
	$note_id = wp_insert_comment( wp_filter_comment( array(
1517
		'comment_post_ID'      => $payment_id,
1518
		'comment_content'      => $note,
1519
		'user_id'              => is_admin() ? get_current_user_id() : 0,
1520
		'comment_date'         => current_time( 'mysql' ),
1521
		'comment_date_gmt'     => current_time( 'mysql', 1 ),
1522
		'comment_approved'     => 1,
1523
		'comment_parent'       => 0,
1524
		'comment_author'       => '',
1525
		'comment_author_IP'    => '',
1526
		'comment_author_url'   => '',
1527
		'comment_author_email' => '',
1528
		'comment_type'         => 'give_payment_note',
1529
1530
	) ) );
1531
1532
	/**
1533
	 * Fires after payment note inserted.
1534
	 *
1535
	 * @since 1.0
1536
	 *
1537
	 * @param int $note_id Note ID.
1538
	 * @param int $payment_id Payment ID.
1539
	 * @param string $note The note.
1540
	 */
1541
	do_action( 'give_insert_payment_note', $note_id, $payment_id, $note );
1542
1543
	return $note_id;
1544
}
1545
1546
/**
1547
 * Deletes a payment note
1548
 *
1549
 * @since 1.0
1550
 *
1551
 * @param int $comment_id The comment ID to delete.
1552
 * @param int $payment_id The payment ID the note is connected to.
1553
 *
1554
 * @return bool True on success, false otherwise.
1555
 */
1556
function give_delete_payment_note( $comment_id = 0, $payment_id = 0 ) {
1557
	if ( empty( $comment_id ) ) {
1558
		return false;
1559
	}
1560
1561
	/**
1562
	 * Fires before deleting donation note.
1563
	 *
1564
	 * @since 1.0
1565
	 *
1566
	 * @param int $comment_id Note ID.
1567
	 * @param int $payment_id Payment ID.
1568
	 */
1569
	do_action( 'give_pre_delete_payment_note', $comment_id, $payment_id );
1570
1571
	$ret = wp_delete_comment( $comment_id, true );
1572
1573
	/**
1574
	 * Fires after donation note deleted.
1575
	 *
1576
	 * @since 1.0
1577
	 *
1578
	 * @param int $comment_id Note ID.
1579
	 * @param int $payment_id Payment ID.
1580
	 */
1581
	do_action( 'give_post_delete_payment_note', $comment_id, $payment_id );
1582
1583
	return $ret;
1584
}
1585
1586
/**
1587
 * Gets the payment note HTML
1588
 *
1589
 * @since 1.0
1590
 *
1591
 * @param object|int $note The comment object or ID.
1592
 * @param int $payment_id The payment ID the note is connected to.
1593
 *
1594
 * @return string
1595
 */
1596
function give_get_payment_note_html( $note, $payment_id = 0 ) {
1597
1598
	if ( is_numeric( $note ) ) {
1599
		$note = get_comment( $note );
1600
	}
1601
1602
	if ( ! empty( $note->user_id ) ) {
1603
		$user = get_userdata( $note->user_id );
1604
		$user = $user->display_name;
1605
	} else {
1606
		$user = esc_html__( 'System', 'give' );
1607
	}
1608
1609
	$date_format = give_date_format() . ', ' . get_option( 'time_format' );
1610
1611
	$delete_note_url = wp_nonce_url( add_query_arg( array(
1612
		'give-action' => 'delete_payment_note',
1613
		'note_id'     => $note->comment_ID,
1614
		'payment_id'  => $payment_id,
1615
	) ), 'give_delete_payment_note_' . $note->comment_ID );
1616
1617
	$note_html = '<div class="give-payment-note" id="give-payment-note-' . $note->comment_ID . '">';
1618
	$note_html .= '<p>';
1619
	$note_html .= '<strong>' . $user . '</strong>&nbsp;&ndash;&nbsp;<span style="color:#aaa;font-style:italic;">' . date_i18n( $date_format, strtotime( $note->comment_date ) ) . '</span><br/>';
1620
	$note_html .= $note->comment_content;
1621
	$note_html .= '&nbsp;&ndash;&nbsp;<a href="' . esc_url( $delete_note_url ) . '" class="give-delete-payment-note" data-note-id="' . absint( $note->comment_ID ) . '" data-payment-id="' . absint( $payment_id ) . '" aria-label="' . esc_attr__( 'Delete this donation note.', 'give' ) . '">' . esc_html__( 'Delete', 'give' ) . '</a>';
1622
	$note_html .= '</p>';
1623
	$note_html .= '</div>';
1624
1625
	return $note_html;
1626
1627
}
1628
1629
/**
1630
 * Exclude notes (comments) on give_payment post type from showing in Recent
1631
 * Comments widgets
1632
 *
1633
 * @since 1.0
1634
 *
1635
 * @param object $query WordPress Comment Query Object.
1636
 *
1637
 * @return void
1638
 */
1639
function give_hide_payment_notes( $query ) {
1640
	if ( version_compare( floatval( get_bloginfo( 'version' ) ), '4.1', '>=' ) ) {
1641
		$types = isset( $query->query_vars['type__not_in'] ) ? $query->query_vars['type__not_in'] : array();
1642
		if ( ! is_array( $types ) ) {
1643
			$types = array( $types );
1644
		}
1645
		$types[]                           = 'give_payment_note';
1646
		$query->query_vars['type__not_in'] = $types;
1647
	}
1648
}
1649
1650
add_action( 'pre_get_comments', 'give_hide_payment_notes', 10 );
1651
1652
/**
1653
 * Exclude notes (comments) on give_payment post type from showing in Recent Comments widgets
1654
 *
1655
 * @since 1.0
1656
 *
1657
 * @param array $clauses Comment clauses for comment query.
1658
 * @param object $wp_comment_query WordPress Comment Query Object.
1659
 *
1660
 * @return array $clauses Updated comment clauses.
1661
 */
1662
function give_hide_payment_notes_pre_41( $clauses, $wp_comment_query ) {
0 ignored issues
show
Unused Code introduced by
The parameter $wp_comment_query 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...
1663
	if ( version_compare( floatval( get_bloginfo( 'version' ) ), '4.1', '<' ) ) {
1664
		$clauses['where'] .= ' AND comment_type != "give_payment_note"';
1665
	}
1666
1667
	return $clauses;
1668
}
1669
1670
add_filter( 'comments_clauses', 'give_hide_payment_notes_pre_41', 10, 2 );
1671
1672
1673
/**
1674
 * Exclude notes (comments) on give_payment post type from showing in comment feeds
1675
 *
1676
 * @since 1.0
1677
 *
1678
 * @param string $where
1679
 * @param object $wp_comment_query WordPress Comment Query Object.
1680
 *
1681
 * @return string $where
1682
 */
1683
function give_hide_payment_notes_from_feeds( $where, $wp_comment_query ) {
0 ignored issues
show
Unused Code introduced by
The parameter $wp_comment_query 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...
1684
	global $wpdb;
1685
1686
	$where .= $wpdb->prepare( ' AND comment_type != %s', 'give_payment_note' );
1687
1688
	return $where;
1689
}
1690
1691
add_filter( 'comment_feed_where', 'give_hide_payment_notes_from_feeds', 10, 2 );
1692
1693
1694
/**
1695
 * Remove Give Comments from the wp_count_comments function
1696
 *
1697
 * @access public
1698
 * @since  1.0
1699
 *
1700
 * @param array $stats (empty from core filter).
1701
 * @param int $post_id Post ID.
1702
 *
1703
 * @return array Array of comment counts.
1704
 */
1705
function give_remove_payment_notes_in_comment_counts( $stats, $post_id ) {
1706
	global $wpdb, $pagenow;
1707
1708 42
	if ( 'index.php' != $pagenow ) {
1709 42
		return $stats;
1710 42
	}
1711
1712 42
	$post_id = (int) $post_id;
1713
1714
	if ( apply_filters( 'give_count_payment_notes_in_comments', false ) ) {
1715
		return $stats;
1716 42
	}
1717
1718 34
	$stats = wp_cache_get( "comments-{$post_id}", 'counts' );
1719 34
1720 34
	if ( false !== $stats ) {
1721 34
		return $stats;
1722
	}
1723 34
1724
	$where = 'WHERE comment_type != "give_payment_note"';
1725
1726
	if ( $post_id > 0 ) {
1727
		$where .= $wpdb->prepare( ' AND comment_post_ID = %d', $post_id );
1728
	}
1729 34
1730
	$count = $wpdb->get_results( "SELECT comment_approved, COUNT( * ) AS num_comments FROM {$wpdb->comments} {$where} GROUP BY comment_approved", ARRAY_A );
0 ignored issues
show
introduced by
Usage of a direct database call is discouraged.
Loading history...
1731
1732 34
	$total    = 0;
1733
	$approved = array(
1734 34
		'0'            => 'moderated',
0 ignored issues
show
introduced by
Detected usage of 0, possible slow query.
Loading history...
1735
		'1'            => 'approved',
1736 42
		'spam'         => 'spam',
1737
		'trash'        => 'trash',
1738
		'post-trashed' => 'post-trashed',
1739
	);
1740
	foreach ( (array) $count as $row ) {
1741
		// Don't count post-trashed toward totals.
1742
		if ( 'post-trashed' != $row['comment_approved'] && 'trash' != $row['comment_approved'] ) {
1743
			$total += $row['num_comments'];
1744
		}
1745
		if ( isset( $approved[ $row['comment_approved'] ] ) ) {
1746
			$stats[ $approved[ $row['comment_approved'] ] ] = $row['num_comments'];
1747
		}
1748
	}
1749
1750
	$stats['total_comments'] = $total;
1751
	foreach ( $approved as $key ) {
1752 52
		if ( empty( $stats[ $key ] ) ) {
1753
			$stats[ $key ] = 0;
1754 52
		}
1755
	}
1756 32
1757
	$stats = (object) $stats;
1758 32
	wp_cache_set( "comments-{$post_id}", $stats, 'counts' );
1759
1760 32
	return $stats;
1761
}
1762
1763 32
add_filter( 'wp_count_comments', 'give_remove_payment_notes_in_comment_counts', 10, 2 );
1764
1765 32
1766
/**
1767 32
 * Filter where older than one week
1768
 *
1769 32
 * @access public
1770
 * @since  1.0
1771 32
 *
1772
 * @param string $where Where clause.
1773 52
 *
1774
 * @return string $where Modified where clause.
1775
 */
1776
function give_filter_where_older_than_week( $where = '' ) {
1777
	// Payments older than one week.
1778
	$start = date( 'Y-m-d', strtotime( '-7 days' ) );
1779
	$where .= " AND post_date <= '{$start}'";
1780
1781
	return $where;
1782
}
1783
1784
1785
/**
1786
 * Get Payment Form ID.
1787
 *
1788
 * Retrieves the form title and appends the level name if present.
1789
 *
1790
 * @since 1.5
1791
 *
1792
 * @param array $payment_meta Payment meta data.
1793
 * @param bool $only_level If set to true will only return the level name if multi-level enabled.
1794
 * @param string $separator The separator between the .
1795
 *
1796
 * @return string $form_title Returns the full title if $only_level is false, otherwise returns the levels title.
1797
 */
1798
function give_get_payment_form_title( $payment_meta, $only_level = false, $separator = '' ) {
1799
1800
	$form_id    = isset( $payment_meta['form_id'] ) ? $payment_meta['form_id'] : 0;
1801
	$price_id   = isset( $payment_meta['price_id'] ) ? $payment_meta['price_id'] : null;
1802
	$form_title = isset( $payment_meta['form_title'] ) ? $payment_meta['form_title'] : '';
1803
1804
	if ( $only_level == true ) {
0 ignored issues
show
Coding Style Best Practice introduced by
It seems like you are loosely comparing two booleans. Considering using the strict comparison === instead.

When comparing two booleans, it is generally considered safer to use the strict comparison operator.

Loading history...
introduced by
Found "== true". Use Yoda Condition checks, you must
Loading history...
1805
		$form_title = '';
1806
	}
1807
1808
	// If multi-level, append to the form title.
1809
	if ( give_has_variable_prices( $form_id ) ) {
1810
1811
		// Only add separator if there is a form title.
1812
		if ( ! empty( $form_title ) ) {
1813
			$form_title .= ' ' . $separator . ' ';
1814
		}
1815
1816
		$form_title .= '<span class="donation-level-text-wrap">';
1817
1818
		if ( $price_id == 'custom' ) {
0 ignored issues
show
introduced by
Found "== '". Use Yoda Condition checks, you must
Loading history...
1819
			$custom_amount_text = give_get_meta( $form_id, '_give_custom_amount_text', true );
1820
			$form_title         .= ! empty( $custom_amount_text ) ? $custom_amount_text : __( 'Custom Amount', 'give' );
1821
		} else {
1822
			$form_title .= give_get_price_option_name( $form_id, $price_id );
1823
		}
1824
1825
		$form_title .= '</span>';
1826
1827
	}
1828
1829
	return apply_filters( 'give_get_payment_form_title', $form_title, $payment_meta );
1830
1831
}
1832
1833
/**
1834
 * Get Price ID
1835
 *
1836
 * Retrieves the Price ID when provided a proper form ID and price (donation) total
1837
 *
1838
 * @param int $form_id Form ID.
1839
 * @param string $price Price ID.
1840
 *
1841
 * @return string $price_id
1842
 */
1843
function give_get_price_id( $form_id, $price ) {
1844
	$price_id = null;
1845
1846
	if ( give_has_variable_prices( $form_id ) ) {
1847
1848
		$levels = give_get_meta( $form_id, '_give_donation_levels', true );
1849
1850
		foreach ( $levels as $level ) {
1851
1852
			$level_amount = give_maybe_sanitize_amount( $level['_give_amount'] );
1853
1854
			// Check that this indeed the recurring price.
1855
			if ( $level_amount == $price ) {
1856
1857
				$price_id = $level['_give_id']['level_id'];
1858
				break;
1859
1860
			}
1861
		}
1862
1863
		if( is_null( $price_id ) && give_is_custom_price_mode( $form_id ) ) {
0 ignored issues
show
introduced by
Space after opening control structure is required
Loading history...
introduced by
No space before opening parenthesis is prohibited
Loading history...
1864
			$price_id = 'custom';
1865
		}
1866
	}
1867
1868
	// Price ID must be numeric or string.
1869
	$price_id = ! is_numeric( $price_id ) && ! is_string( $price_id ) ? 0 : $price_id;
1870
1871
	return $price_id;
1872
}
1873
1874
/**
1875
 * Get/Print give form dropdown html
1876
 *
1877
 * This function is wrapper to public method forms_dropdown of Give_HTML_Elements class to get/print form dropdown html.
1878
 * Give_HTML_Elements is defined in includes/class-give-html-elements.php.
1879
 *
1880
 * @since 1.6
1881
 *
1882
 * @param array $args Arguments for form dropdown.
1883
 * @param bool $echo This parameter decides if print form dropdown html output or not.
1884
 *
1885
 * @return string
1886
 */
1887
function give_get_form_dropdown( $args = array(), $echo = false ) {
1888
	$form_dropdown_html = Give()->html->forms_dropdown( $args );
1889
1890
	if ( ! $echo ) {
1891
		return $form_dropdown_html;
1892
	}
1893
1894
	echo $form_dropdown_html;
0 ignored issues
show
introduced by
Expected next thing to be a escaping function, not '$form_dropdown_html'
Loading history...
1895
}
1896
1897
/**
1898
 * Get/Print give form variable price dropdown html
1899
 *
1900
 * @since 1.6
1901
 *
1902
 * @param array $args Arguments for form dropdown.
1903
 * @param bool $echo This parameter decide if print form dropdown html output or not.
1904
 *
1905
 * @return string|bool
1906
 */
1907
function give_get_form_variable_price_dropdown( $args = array(), $echo = false ) {
1908
1909
	// Check for give form id.
1910
	if ( empty( $args['id'] ) ) {
1911
		return false;
1912
	}
1913
1914
	$form = new Give_Donate_Form( $args['id'] );
1915
1916
	// Check if form has variable prices or not.
1917
	if ( ! $form->ID || ! $form->has_variable_prices() ) {
1918
		return false;
1919
	}
1920
1921
	$variable_prices        = $form->get_prices();
1922
	$variable_price_options = array();
1923
1924
	// Check if multi donation form support custom donation or not.
1925
	if ( $form->is_custom_price_mode() ) {
1926
		$variable_price_options['custom'] = _x( 'Custom', 'custom donation dropdown item', 'give' );
1927
	}
1928
1929
	// Get variable price and ID from variable price array.
1930
	foreach ( $variable_prices as $variable_price ) {
1931
		$variable_price_options[ $variable_price['_give_id']['level_id'] ] = ! empty( $variable_price['_give_text'] ) ? $variable_price['_give_text'] : give_currency_filter( give_format_amount( $variable_price['_give_amount'], array( 'sanitize' => false ) ) );
1932
	}
1933
1934
	// Update options.
1935
	$args = array_merge( $args, array(
1936
		'options' => $variable_price_options,
1937
	) );
1938
1939
	// Generate select html.
1940
	$form_dropdown_html = Give()->html->select( $args );
1941
1942
	if ( ! $echo ) {
1943
		return $form_dropdown_html;
1944
	}
1945
1946
	echo $form_dropdown_html;
0 ignored issues
show
introduced by
Expected next thing to be a escaping function, not '$form_dropdown_html'
Loading history...
1947
}
1948
1949
/**
1950
 * Get the price_id from the payment meta.
1951
 *
1952
 * Some gateways use `give_price_id` and others were using just `price_id`;
1953
 * This checks for the difference and falls back to retrieving it from the form as a last resort.
1954
 *
1955
 * @since 1.8.6
1956
 *
1957
 * @param $payment_meta
1958
 *
1959
 * @return string
1960
 */
1961
function give_get_payment_meta_price_id( $payment_meta ) {
1962
1963
	if ( isset( $payment_meta['give_price_id'] ) ) {
1964
		$price_id = $payment_meta['give_price_id'];
1965
	} elseif ( isset( $payment_meta['price_id'] ) ) {
1966
		$price_id = $payment_meta['price_id'];
1967
	} else {
1968
		$price_id = give_get_price_id( $payment_meta['give_form_id'], $payment_meta['price'] );
1969
	}
1970
1971
	return apply_filters( 'give_get_payment_meta_price_id', $price_id );
1972
1973
}
1974