Completed
Branch BUG-10351-incompatible-addons (9de45c)
by
unknown
67:57 queued 56:07
created
core/EE_Payment_Processor.core.php 1 patch
Indentation   +734 added lines, -734 removed lines patch added patch discarded remove patch
@@ -1,5 +1,5 @@  discard block
 block discarded – undo
1 1
 <?php if ( ! defined('EVENT_ESPRESSO_VERSION')) {
2
-    exit('No direct script access allowed');
2
+	exit('No direct script access allowed');
3 3
 }
4 4
 EE_Registry::instance()->load_class('Processor_Base');
5 5
 
@@ -16,737 +16,737 @@  discard block
 block discarded – undo
16 16
 class EE_Payment_Processor extends EE_Processor_Base
17 17
 {
18 18
 
19
-    /**
20
-     * @var EE_Payment_Processor $_instance
21
-     * @access    private
22
-     */
23
-    private static $_instance;
24
-
25
-
26
-
27
-    /**
28
-     * @singleton method used to instantiate class object
29
-     * @access    public
30
-     * @return EE_Payment_Processor instance
31
-     */
32
-    public static function instance()
33
-    {
34
-        // check if class object is instantiated
35
-        if ( ! self::$_instance instanceof EE_Payment_Processor) {
36
-            self::$_instance = new self();
37
-        }
38
-        return self::$_instance;
39
-    }
40
-
41
-
42
-
43
-    /**
44
-     *private constructor to prevent direct creation
45
-     *
46
-     * @Constructor
47
-     * @access private
48
-     */
49
-    private function __construct()
50
-    {
51
-        do_action('AHEE__EE_Payment_Processor__construct');
52
-        add_action('http_api_curl', array($this, '_curl_requests_to_paypal_use_tls'), 10, 3);
53
-    }
54
-
55
-
56
-
57
-    /**
58
-     * Using the selected gateway, processes the payment for that transaction, and updates the transaction
59
-     * appropriately. Saves the payment that is generated
60
-     *
61
-     * @param EE_Payment_Method    $payment_method
62
-     * @param EE_Transaction       $transaction
63
-     * @param float                $amount       if only part of the transaction is to be paid for, how much.
64
-     *                                           Leave null if payment is for the full amount owing
65
-     * @param EE_Billing_Info_Form $billing_form (or probably null, if it's an offline or offsite payment method).
66
-     *                                           Receive_form_submission() should have
67
-     *                                           already been called on the billing form
68
-     *                                           (ie, its inputs should have their normalized values set).
69
-     * @param string               $return_url   string used mostly by offsite gateways to specify
70
-     *                                           where to go AFTER the offsite gateway
71
-     * @param string               $method       like 'CART', indicates who the client who called this was
72
-     * @param bool                 $by_admin     TRUE if payment is being attempted from the admin
73
-     * @param boolean              $update_txn   whether or not to call
74
-     *                                           EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment()
75
-     * @param string               $cancel_url   URL to return to if off-site payments are cancelled
76
-     * @return \EE_Payment
77
-     * @throws \EE_Error
78
-     */
79
-    public function process_payment(
80
-        EE_Payment_Method $payment_method,
81
-        EE_Transaction $transaction,
82
-        $amount = null,
83
-        $billing_form = null,
84
-        $return_url = null,
85
-        $method = 'CART',
86
-        $by_admin = false,
87
-        $update_txn = true,
88
-        $cancel_url = ''
89
-    ) {
90
-        if ((float)$amount < 0) {
91
-            throw new EE_Error(
92
-                sprintf(
93
-                    __(
94
-                        'Attempting to make a payment for a negative amount of %1$d for transaction %2$d. That should be a refund',
95
-                        'event_espresso'
96
-                    ),
97
-                    $amount,
98
-                    $transaction->ID()
99
-                )
100
-            );
101
-        }
102
-        // verify payment method
103
-        $payment_method = EEM_Payment_Method::instance()->ensure_is_obj($payment_method, true);
104
-        // verify transaction
105
-        EEM_Transaction::instance()->ensure_is_obj($transaction);
106
-        $transaction->set_payment_method_ID($payment_method->ID());
107
-        // verify payment method type
108
-        if ($payment_method->type_obj() instanceof EE_PMT_Base) {
109
-            $payment = $payment_method->type_obj()->process_payment(
110
-                $transaction,
111
-                min($amount, $transaction->remaining()),//make sure we don't overcharge
112
-                $billing_form,
113
-                $return_url,
114
-                add_query_arg(array('ee_cancel_payment' => true), $cancel_url),
115
-                $method,
116
-                $by_admin
117
-            );
118
-            // check if payment method uses an off-site gateway
119
-            if ($payment_method->type_obj()->payment_occurs() !== EE_PMT_Base::offsite) {
120
-                // don't process payments for off-site gateways yet because no payment has occurred yet
121
-                $this->update_txn_based_on_payment($transaction, $payment, $update_txn);
122
-            }
123
-            return $payment;
124
-        } else {
125
-            EE_Error::add_error(
126
-                sprintf(
127
-                    __('A valid payment method could not be determined due to a technical issue.%sPlease try again or contact %s for assistance.', 'event_espresso'),
128
-                    '<br/>',
129
-                    EE_Registry::instance()->CFG->organization->get_pretty('email')
130
-                ), __FILE__, __FUNCTION__, __LINE__
131
-            );
132
-            return null;
133
-        }
134
-    }
135
-
136
-
137
-
138
-    /**
139
-     * @param EE_Transaction|int $transaction
140
-     * @param EE_Payment_Method  $payment_method
141
-     * @throws EE_Error
142
-     * @return string
143
-     */
144
-    public function get_ipn_url_for_payment_method($transaction, $payment_method)
145
-    {
146
-        /** @type \EE_Transaction $transaction */
147
-        $transaction = EEM_Transaction::instance()->ensure_is_obj($transaction);
148
-        $primary_reg = $transaction->primary_registration();
149
-        if ( ! $primary_reg instanceof EE_Registration) {
150
-            throw new EE_Error(
151
-                sprintf(
152
-                    __(
153
-                        "Cannot get IPN URL for transaction with ID %d because it has no primary registration",
154
-                        "event_espresso"
155
-                    ),
156
-                    $transaction->ID()
157
-                )
158
-            );
159
-        }
160
-        $payment_method = EEM_Payment_Method::instance()->ensure_is_obj($payment_method, true);
161
-        $url = add_query_arg(
162
-            array(
163
-                'e_reg_url_link'    => $primary_reg->reg_url_link(),
164
-                'ee_payment_method' => $payment_method->slug(),
165
-            ),
166
-            EE_Registry::instance()->CFG->core->txn_page_url()
167
-        );
168
-        return $url;
169
-    }
170
-
171
-
172
-
173
-    /**
174
-     * Process the IPN. Firstly, we'll hope we put the standard args into the IPN URL so
175
-     * we can easily find what registration the IPN is for and what payment method.
176
-     * However, if not, we'll give all payment methods a chance to claim it and process it.
177
-     * If a payment is found for the IPN info, it is saved.
178
-     *
179
-     * @param array              $_req_data            eg $_REQUEST
180
-     * @param EE_Transaction|int $transaction          optional (or a transactions id)
181
-     * @param EE_Payment_Method  $payment_method       (or a slug or id of one)
182
-     * @param boolean            $update_txn           whether or not to call
183
-     *                                                 EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment()
184
-     * @param bool               $separate_IPN_request whether the IPN uses a separate request ( true like PayPal )
185
-     *                                                 or is processed manually ( false like Mijireh )
186
-     * @throws EE_Error
187
-     * @throws Exception
188
-     * @return EE_Payment
189
-     */
190
-    public function process_ipn(
191
-        $_req_data,
192
-        $transaction = null,
193
-        $payment_method = null,
194
-        $update_txn = true,
195
-        $separate_IPN_request = true
196
-    ) {
197
-        EE_Registry::instance()->load_model('Change_Log');
198
-        $_req_data = $this->_remove_unusable_characters_from_array((array)$_req_data);
199
-        EE_Processor_Base::set_IPN($separate_IPN_request);
200
-        $obj_for_log = null;
201
-        if ($transaction instanceof EE_Transaction) {
202
-            $obj_for_log = $transaction;
203
-            if ($payment_method instanceof EE_Payment_Method) {
204
-                $obj_for_log = EEM_Payment::instance()->get_one(
205
-                    array(
206
-                        array('TXN_ID' => $transaction->ID(), 'PMD_ID' => $payment_method->ID()),
207
-                        'order_by' => array('PAY_timestamp' => 'desc'),
208
-                    )
209
-                );
210
-            }
211
-        } else if ($payment_method instanceof EE_Payment) {
212
-            $obj_for_log = $payment_method;
213
-        }
214
-        $log = EEM_Change_Log::instance()->log(
215
-            EEM_Change_Log::type_gateway,
216
-            array('IPN data received' => $_req_data),
217
-            $obj_for_log
218
-        );
219
-        try {
220
-            /**
221
-             * @var EE_Payment $payment
222
-             */
223
-            $payment = null;
224
-            if ($transaction && $payment_method) {
225
-                /** @type EE_Transaction $transaction */
226
-                $transaction = EEM_Transaction::instance()->ensure_is_obj($transaction);
227
-                /** @type EE_Payment_Method $payment_method */
228
-                $payment_method = EEM_Payment_Method::instance()->ensure_is_obj($payment_method);
229
-                if ($payment_method->type_obj() instanceof EE_PMT_Base) {
230
-                    try {
231
-                        $payment = $payment_method->type_obj()->handle_ipn($_req_data, $transaction);
232
-                        $log->set_object($payment);
233
-                    } catch (EventEspresso\core\exceptions\IpnException $e) {
234
-                        EEM_Change_Log::instance()->log(
235
-                            EEM_Change_Log::type_gateway,
236
-                            array(
237
-                                'message'     => 'IPN Exception: ' . $e->getMessage(),
238
-                                'current_url' => EEH_URL::current_url(),
239
-                                'payment'     => $e->getPaymentProperties(),
240
-                                'IPN_data'    => $e->getIpnData(),
241
-                            ),
242
-                            $obj_for_log
243
-                        );
244
-                        return $e->getPayment();
245
-                    }
246
-                } else {
247
-                    // not a payment
248
-                    EE_Error::add_error(
249
-                        sprintf(
250
-                            __('A valid payment method could not be determined due to a technical issue.%sPlease refresh your browser and try again or contact %s for assistance.', 'event_espresso'),
251
-                            '<br/>',
252
-                            EE_Registry::instance()->CFG->organization->get_pretty('email')
253
-                        ),
254
-                        __FILE__, __FUNCTION__, __LINE__
255
-                    );
256
-                }
257
-            } else {
258
-                //that's actually pretty ok. The IPN just wasn't able
259
-                //to identify which transaction or payment method this was for
260
-                // give all active payment methods a chance to claim it
261
-                $active_payment_methods = EEM_Payment_Method::instance()->get_all_active();
262
-                foreach ($active_payment_methods as $active_payment_method) {
263
-                    try {
264
-                        $payment = $active_payment_method->type_obj()->handle_unclaimed_ipn($_req_data);
265
-                        $payment_method = $active_payment_method;
266
-                        EEM_Change_Log::instance()->log(
267
-                            EEM_Change_Log::type_gateway, array('IPN data' => $_req_data), $payment
268
-                        );
269
-                        break;
270
-                    } catch (EventEspresso\core\exceptions\IpnException $e) {
271
-                        EEM_Change_Log::instance()->log(
272
-                            EEM_Change_Log::type_gateway,
273
-                            array(
274
-                                'message'     => 'IPN Exception: ' . $e->getMessage(),
275
-                                'current_url' => EEH_URL::current_url(),
276
-                                'payment'     => $e->getPaymentProperties(),
277
-                                'IPN_data'    => $e->getIpnData(),
278
-                            ),
279
-                            $obj_for_log
280
-                        );
281
-                        return $e->getPayment();
282
-                    } catch (EE_Error $e) {
283
-                        //that's fine- it apparently couldn't handle the IPN
284
-                    }
285
-                }
286
-            }
287
-            // 			EEM_Payment_Log::instance()->log("got to 7",$transaction,$payment_method);
288
-            if ($payment instanceof EE_Payment) {
289
-                $payment->save();
290
-                //  update the TXN
291
-                $this->update_txn_based_on_payment($transaction, $payment, $update_txn, $separate_IPN_request);
292
-            } else {
293
-                //we couldn't find the payment for this IPN... let's try and log at least SOMETHING
294
-                if ($payment_method) {
295
-                    EEM_Change_Log::instance()->log(EEM_Change_Log::type_gateway, array('IPN data' => $_req_data), $payment_method);
296
-                } elseif ($transaction) {
297
-                    EEM_Change_Log::instance()->log(EEM_Change_Log::type_gateway, array('IPN data' => $_req_data), $transaction);
298
-                }
299
-            }
300
-            return $payment;
301
-        } catch (EE_Error $e) {
302
-            do_action(
303
-                'AHEE__log', __FILE__, __FUNCTION__, sprintf(
304
-                    __('Error occurred while receiving IPN. Transaction: %1$s, req data: %2$s. The error was "%3$s"', 'event_espresso'),
305
-                    print_r($transaction, true),
306
-                    print_r($_req_data, true),
307
-                    $e->getMessage()
308
-                )
309
-            );
310
-            throw $e;
311
-        }
312
-    }
313
-
314
-
315
-
316
-    /**
317
-     * Removes any non-printable illegal characters from the input,
318
-     * which might cause a raucous when trying to insert into the database
319
-     *
320
-     * @param  array $request_data
321
-     * @return array
322
-     */
323
-    protected function _remove_unusable_characters_from_array(array $request_data)
324
-    {
325
-        $return_data = array();
326
-        foreach ($request_data as $key => $value) {
327
-            $return_data[$this->_remove_unusable_characters($key)] = $this->_remove_unusable_characters($value);
328
-        }
329
-        return $return_data;
330
-    }
331
-
332
-
333
-
334
-    /**
335
-     * Removes any non-printable illegal characters from the input,
336
-     * which might cause a raucous when trying to insert into the database
337
-     *
338
-     * @param string $request_data
339
-     * @return string
340
-     */
341
-    protected function _remove_unusable_characters($request_data)
342
-    {
343
-        return preg_replace('/[^[:print:]]/', '', $request_data);
344
-    }
345
-
346
-
347
-
348
-    /**
349
-     * Should be called just before displaying the payment attempt results to the user,
350
-     * when the payment attempt has finished. Some payment methods may have special
351
-     * logic to perform here. For example, if process_payment() happens on a special request
352
-     * and then the user is redirected to a page that displays the payment's status, this
353
-     * should be called while loading the page that displays the payment's status. If the user is
354
-     * sent to an offsite payment provider, this should be called upon returning from that offsite payment
355
-     * provider.
356
-     *
357
-     * @param EE_Transaction|int $transaction
358
-     * @param bool               $update_txn whether or not to call
359
-     *                                       EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment()
360
-     * @throws \EE_Error
361
-     * @return EE_Payment
362
-     * @deprecated 4.6.24 method is no longer used. Instead it is up to client code, like SPCO,
363
-     *                                       to call handle_ipn() for offsite gateways that don't receive separate IPNs
364
-     */
365
-    public function finalize_payment_for($transaction, $update_txn = true)
366
-    {
367
-        /** @var $transaction EE_Transaction */
368
-        $transaction = EEM_Transaction::instance()->ensure_is_obj($transaction);
369
-        $last_payment_method = $transaction->payment_method();
370
-        if ($last_payment_method instanceof EE_Payment_Method) {
371
-            $payment = $last_payment_method->type_obj()->finalize_payment_for($transaction);
372
-            $this->update_txn_based_on_payment($transaction, $payment, $update_txn);
373
-            return $payment;
374
-        } else {
375
-            return null;
376
-        }
377
-    }
378
-
379
-
380
-
381
-    /**
382
-     * Processes a direct refund request, saves the payment, and updates the transaction appropriately.
383
-     *
384
-     * @param EE_Payment_Method $payment_method
385
-     * @param EE_Payment        $payment_to_refund
386
-     * @param array             $refund_info
387
-     * @return EE_Payment
388
-     * @throws \EE_Error
389
-     */
390
-    public function process_refund(
391
-        EE_Payment_Method $payment_method,
392
-        EE_Payment $payment_to_refund,
393
-        $refund_info = array()
394
-    ) {
395
-        if ($payment_method instanceof EE_Payment_Method && $payment_method->type_obj()->supports_sending_refunds()) {
396
-            $payment_method->type_obj()->process_refund($payment_to_refund, $refund_info);
397
-            $this->update_txn_based_on_payment($payment_to_refund->transaction(), $payment_to_refund);
398
-        }
399
-        return $payment_to_refund;
400
-    }
401
-
402
-
403
-
404
-    /**
405
-     * This should be called each time there may have been an update to a
406
-     * payment on a transaction (ie, we asked for a payment to process a
407
-     * payment for a transaction, or we told a payment method about an IPN, or
408
-     * we told a payment method to
409
-     * "finalize_payment_for" (a transaction), or we told a payment method to
410
-     * process a refund. This should handle firing the correct hooks to
411
-     * indicate
412
-     * what exactly happened and updating the transaction appropriately). This
413
-     * could be integrated directly into EE_Transaction upon save, but we want
414
-     * this logic to be separate from 'normal' plain-jane saving and updating
415
-     * of transactions and payments, and to be tied to payment processing.
416
-     * Note: this method DOES NOT save the payment passed into it. It is the responsibility
417
-     * of previous code to decide whether or not to save (because the payment passed into
418
-     * this method might be a temporary, never-to-be-saved payment from an offline gateway,
419
-     * in which case we only want that payment object for some temporary usage during this request,
420
-     * but we don't want it to be saved).
421
-     *
422
-     * @param EE_Transaction|int $transaction
423
-     * @param EE_Payment         $payment
424
-     * @param boolean            $update_txn
425
-     *                        whether or not to call
426
-     *                        EE_Transaction_Processor::
427
-     *                        update_transaction_and_registrations_after_checkout_or_payment()
428
-     *                        (you can save 1 DB query if you know you're going
429
-     *                        to save it later instead)
430
-     * @param bool               $IPN
431
-     *                        if processing IPNs or other similar payment
432
-     *                        related activities that occur in alternate
433
-     *                        requests than the main one that is processing the
434
-     *                        TXN, then set this to true to check whether the
435
-     *                        TXN is locked before updating
436
-     * @throws \EE_Error
437
-     */
438
-    public function update_txn_based_on_payment($transaction, $payment, $update_txn = true, $IPN = false)
439
-    {
440
-        $do_action = 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__not_successful';
441
-        /** @type EE_Transaction $transaction */
442
-        $transaction = EEM_Transaction::instance()->ensure_is_obj($transaction);
443
-        // can we freely update the TXN at this moment?
444
-        if ($IPN && $transaction->is_locked()) {
445
-            // don't update the transaction at this exact moment
446
-            // because the TXN is active in another request
447
-            EE_Cron_Tasks::schedule_update_transaction_with_payment(
448
-                time(),
449
-                $transaction->ID(),
450
-                $payment->ID()
451
-            );
452
-        } else {
453
-            // verify payment and that it has been saved
454
-            if ($payment instanceof EE_Payment && $payment->ID()) {
455
-                if (
456
-                    $payment->payment_method() instanceof EE_Payment_Method
457
-                    && $payment->payment_method()->type_obj() instanceof EE_PMT_Base
458
-                ) {
459
-                    $payment->payment_method()->type_obj()->update_txn_based_on_payment($payment);
460
-                    // update TXN registrations with payment info
461
-                    $this->process_registration_payments($transaction, $payment);
462
-                }
463
-                $do_action = $payment->just_approved()
464
-                    ? 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__successful'
465
-                    : $do_action;
466
-            } else {
467
-                // send out notifications
468
-                add_filter('FHEE__EED_Messages___maybe_registration__deliver_notifications', '__return_true');
469
-                $do_action = 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__no_payment_made';
470
-            }
471
-            if ($payment instanceof EE_Payment && $payment->status() !== EEM_Payment::status_id_failed) {
472
-                /** @type EE_Transaction_Payments $transaction_payments */
473
-                $transaction_payments = EE_Registry::instance()->load_class('Transaction_Payments');
474
-                // set new value for total paid
475
-                $transaction_payments->calculate_total_payments_and_update_status($transaction);
476
-                // call EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment() ???
477
-                if ($update_txn) {
478
-                    $this->_post_payment_processing($transaction, $payment, $IPN);
479
-                }
480
-            }
481
-            // granular hook for others to use.
482
-            do_action($do_action, $transaction, $payment);
483
-            do_action('AHEE_log', __CLASS__, __FUNCTION__, $do_action, '$do_action');
484
-            //global hook for others to use.
485
-            do_action('AHEE__EE_Payment_Processor__update_txn_based_on_payment', $transaction, $payment);
486
-        }
487
-    }
488
-
489
-
490
-
491
-    /**
492
-     * update registrations REG_paid field after successful payment and link registrations with payment
493
-     *
494
-     * @param EE_Transaction    $transaction
495
-     * @param EE_Payment        $payment
496
-     * @param EE_Registration[] $registrations
497
-     * @throws \EE_Error
498
-     */
499
-    public function process_registration_payments(
500
-        EE_Transaction $transaction,
501
-        EE_Payment $payment,
502
-        $registrations = array()
503
-    ) {
504
-        // only process if payment was successful
505
-        if ($payment->status() !== EEM_Payment::status_id_approved) {
506
-            return;
507
-        }
508
-        //EEM_Registration::instance()->show_next_x_db_queries();
509
-        if (empty($registrations)) {
510
-            // find registrations with monies owing that can receive a payment
511
-            $registrations = $transaction->registrations(
512
-                array(
513
-                    array(
514
-                        // only these reg statuses can receive payments
515
-                        'STS_ID'           => array('IN', EEM_Registration::reg_statuses_that_allow_payment()),
516
-                        'REG_final_price'  => array('!=', 0),
517
-                        'REG_final_price*' => array('!=', 'REG_paid', true),
518
-                    ),
519
-                )
520
-            );
521
-        }
522
-        // still nothing ??!??
523
-        if (empty($registrations)) {
524
-            return;
525
-        }
526
-        // todo: break out the following logic into a separate strategy class
527
-        // todo: named something like "Sequential_Reg_Payment_Strategy"
528
-        // todo: which would apply payments using the capitalist "first come first paid" approach
529
-        // todo: then have another strategy class like "Distributed_Reg_Payment_Strategy"
530
-        // todo: which would be the socialist "everybody gets a piece of pie" approach,
531
-        // todo: which would be better for deposits, where you want a bit of the payment applied to each registration
532
-        $refund = $payment->is_a_refund();
533
-        // how much is available to apply to registrations?
534
-        $available_payment_amount = abs($payment->amount());
535
-        foreach ($registrations as $registration) {
536
-            if ($registration instanceof EE_Registration) {
537
-                // nothing left?
538
-                if ($available_payment_amount <= 0) {
539
-                    break;
540
-                }
541
-                if ($refund) {
542
-                    $available_payment_amount = $this->process_registration_refund($registration, $payment, $available_payment_amount);
543
-                } else {
544
-                    $available_payment_amount = $this->process_registration_payment($registration, $payment, $available_payment_amount);
545
-                }
546
-            }
547
-        }
548
-        if ($available_payment_amount > 0 && apply_filters('FHEE__EE_Payment_Processor__process_registration_payments__display_notifications', false)) {
549
-            EE_Error::add_attention(
550
-                sprintf(
551
-                    __('A remainder of %1$s exists after applying this payment to Registration(s) %2$s.%3$sPlease verify that the original payment amount of %4$s is correct. If so, you should edit this payment and select at least one additional registration in the "Registrations to Apply Payment to" section, so that the remainder of this payment can be applied to the additional registration(s).',
552
-                        'event_espresso'),
553
-                    EEH_Template::format_currency($available_payment_amount),
554
-                    implode(', ', array_keys($registrations)),
555
-                    '<br/>',
556
-                    EEH_Template::format_currency($payment->amount())
557
-                ),
558
-                __FILE__, __FUNCTION__, __LINE__
559
-            );
560
-        }
561
-    }
562
-
563
-
564
-
565
-    /**
566
-     * update registration REG_paid field after successful payment and link registration with payment
567
-     *
568
-     * @param EE_Registration $registration
569
-     * @param EE_Payment      $payment
570
-     * @param float           $available_payment_amount
571
-     * @return float
572
-     * @throws \EE_Error
573
-     */
574
-    public function process_registration_payment(
575
-        EE_Registration $registration,
576
-        EE_Payment $payment,
577
-        $available_payment_amount = 0.00
578
-    ) {
579
-        $owing = $registration->final_price() - $registration->paid();
580
-        if ($owing > 0) {
581
-            // don't allow payment amount to exceed the available payment amount, OR the amount owing
582
-            $payment_amount = min($available_payment_amount, $owing);
583
-            // update $available_payment_amount
584
-            $available_payment_amount -= $payment_amount;
585
-            //calculate and set new REG_paid
586
-            $registration->set_paid($registration->paid() + $payment_amount);
587
-            // now save it
588
-            $this->_apply_registration_payment($registration, $payment, $payment_amount);
589
-        }
590
-        return $available_payment_amount;
591
-    }
592
-
593
-
594
-
595
-    /**
596
-     * update registration REG_paid field after successful payment and link registration with payment
597
-     *
598
-     * @param EE_Registration $registration
599
-     * @param EE_Payment      $payment
600
-     * @param float           $payment_amount
601
-     * @return void
602
-     * @throws \EE_Error
603
-     */
604
-    protected function _apply_registration_payment(
605
-        EE_Registration $registration,
606
-        EE_Payment $payment,
607
-        $payment_amount = 0.00
608
-    ) {
609
-        // find any existing reg payment records for this registration and payment
610
-        $existing_reg_payment = EEM_Registration_Payment::instance()->get_one(
611
-            array(array('REG_ID' => $registration->ID(), 'PAY_ID' => $payment->ID()))
612
-        );
613
-        // if existing registration payment exists
614
-        if ($existing_reg_payment instanceof EE_Registration_Payment) {
615
-            // then update that record
616
-            $existing_reg_payment->set_amount($payment_amount);
617
-            $existing_reg_payment->save();
618
-        } else {
619
-            // or add new relation between registration and payment and set amount
620
-            $registration->_add_relation_to($payment, 'Payment', array('RPY_amount' => $payment_amount));
621
-            // make it stick
622
-            $registration->save();
623
-        }
624
-    }
625
-
626
-
627
-
628
-    /**
629
-     * update registration REG_paid field after refund and link registration with payment
630
-     *
631
-     * @param EE_Registration $registration
632
-     * @param EE_Payment      $payment
633
-     * @param float           $available_refund_amount - IMPORTANT !!! SEND AVAILABLE REFUND AMOUNT AS A POSITIVE NUMBER
634
-     * @return float
635
-     * @throws \EE_Error
636
-     */
637
-    public function process_registration_refund(
638
-        EE_Registration $registration,
639
-        EE_Payment $payment,
640
-        $available_refund_amount = 0.00
641
-    ) {
642
-        //EEH_Debug_Tools::printr( $payment->amount(), '$payment->amount()', __FILE__, __LINE__ );
643
-        if ($registration->paid() > 0) {
644
-            // ensure $available_refund_amount is NOT negative
645
-            $available_refund_amount = (float)abs($available_refund_amount);
646
-            // don't allow refund amount to exceed the available payment amount, OR the amount paid
647
-            $refund_amount = min($available_refund_amount, (float)$registration->paid());
648
-            // update $available_payment_amount
649
-            $available_refund_amount -= $refund_amount;
650
-            //calculate and set new REG_paid
651
-            $registration->set_paid($registration->paid() - $refund_amount);
652
-            // convert payment amount back to a negative value for storage in the db
653
-            $refund_amount = (float)abs($refund_amount) * -1;
654
-            // now save it
655
-            $this->_apply_registration_payment($registration, $payment, $refund_amount);
656
-        }
657
-        return $available_refund_amount;
658
-    }
659
-
660
-
661
-
662
-    /**
663
-     * Process payments and transaction after payment process completed.
664
-     * ultimately this will send the TXN and payment details off so that notifications can be sent out.
665
-     * if this request happens to be processing an IPN,
666
-     * then we will also set the Payment Options Reg Step to completed,
667
-     * and attempt to completely finalize the TXN if all of the other Reg Steps are completed as well.
668
-     *
669
-     * @param EE_Transaction $transaction
670
-     * @param EE_Payment     $payment
671
-     * @param bool           $IPN
672
-     * @throws \EE_Error
673
-     */
674
-    protected function _post_payment_processing(EE_Transaction $transaction, EE_Payment $payment, $IPN = false)
675
-    {
676
-        /** @type EE_Transaction_Processor $transaction_processor */
677
-        $transaction_processor = EE_Registry::instance()->load_class('Transaction_Processor');
678
-        // is the Payment Options Reg Step completed ?
679
-        $payment_options_step_completed = $transaction->reg_step_completed('payment_options');
680
-        // if the Payment Options Reg Step is completed...
681
-        $revisit = $payment_options_step_completed === true ? true : false;
682
-        // then this is kinda sorta a revisit with regards to payments at least
683
-        $transaction_processor->set_revisit($revisit);
684
-        // if this is an IPN, let's consider the Payment Options Reg Step completed if not already
685
-        if (
686
-            $IPN
687
-            && $payment_options_step_completed !== true
688
-            && ($payment->is_approved() || $payment->is_pending())
689
-        ) {
690
-            $payment_options_step_completed = $transaction->set_reg_step_completed(
691
-                'payment_options'
692
-            );
693
-        }
694
-        // maybe update status, but don't save transaction just yet
695
-        $transaction->update_status_based_on_total_paid(false);
696
-        // check if 'finalize_registration' step has been completed...
697
-        $finalized = $transaction->reg_step_completed('finalize_registration');
698
-        //  if this is an IPN and the final step has not been initiated
699
-        if ($IPN && $payment_options_step_completed && $finalized === false) {
700
-            // and if it hasn't already been set as being started...
701
-            $finalized = $transaction->set_reg_step_initiated('finalize_registration');
702
-        }
703
-        $transaction->save();
704
-        // because the above will return false if the final step was not fully completed, we need to check again...
705
-        if ($IPN && $finalized !== false) {
706
-            // and if we are all good to go, then send out notifications
707
-            add_filter('FHEE__EED_Messages___maybe_registration__deliver_notifications', '__return_true');
708
-            //ok, now process the transaction according to the payment
709
-            $transaction_processor->update_transaction_and_registrations_after_checkout_or_payment($transaction, $payment);
710
-        }
711
-        // DEBUG LOG
712
-        $payment_method = $payment->payment_method();
713
-        if ($payment_method instanceof EE_Payment_Method) {
714
-            $payment_method_type_obj = $payment_method->type_obj();
715
-            if ($payment_method_type_obj instanceof EE_PMT_Base) {
716
-                $gateway = $payment_method_type_obj->get_gateway();
717
-                if ($gateway instanceof EE_Gateway) {
718
-                    $gateway->log(
719
-                        array(
720
-                            'message'               => __('Post Payment Transaction Details', 'event_espresso'),
721
-                            'transaction'           => $transaction->model_field_array(),
722
-                            'finalized'             => $finalized,
723
-                            'IPN'                   => $IPN,
724
-                            'deliver_notifications' => has_filter(
725
-                                'FHEE__EED_Messages___maybe_registration__deliver_notifications'
726
-                            ),
727
-                        ),
728
-                        $payment
729
-                    );
730
-                }
731
-            }
732
-        }
733
-    }
734
-
735
-
736
-
737
-    /**
738
-     * Force posts to PayPal to use TLS v1.2. See:
739
-     * https://core.trac.wordpress.org/ticket/36320
740
-     * https://core.trac.wordpress.org/ticket/34924#comment:15
741
-     * https://www.paypal-knowledge.com/infocenter/index?page=content&widgetview=true&id=FAQ1914&viewlocale=en_US
742
-     * This will affect paypal standard, pro, express, and payflow.
743
-     */
744
-    public static function _curl_requests_to_paypal_use_tls($handle, $r, $url)
745
-    {
746
-        if (strstr($url, 'https://') && strstr($url, '.paypal.com')) {
747
-            //Use the value of the constant CURL_SSLVERSION_TLSv1 = 1
748
-            //instead of the constant because it might not be defined
749
-            curl_setopt($handle, CURLOPT_SSLVERSION, 1);
750
-        }
751
-    }
19
+	/**
20
+	 * @var EE_Payment_Processor $_instance
21
+	 * @access    private
22
+	 */
23
+	private static $_instance;
24
+
25
+
26
+
27
+	/**
28
+	 * @singleton method used to instantiate class object
29
+	 * @access    public
30
+	 * @return EE_Payment_Processor instance
31
+	 */
32
+	public static function instance()
33
+	{
34
+		// check if class object is instantiated
35
+		if ( ! self::$_instance instanceof EE_Payment_Processor) {
36
+			self::$_instance = new self();
37
+		}
38
+		return self::$_instance;
39
+	}
40
+
41
+
42
+
43
+	/**
44
+	 *private constructor to prevent direct creation
45
+	 *
46
+	 * @Constructor
47
+	 * @access private
48
+	 */
49
+	private function __construct()
50
+	{
51
+		do_action('AHEE__EE_Payment_Processor__construct');
52
+		add_action('http_api_curl', array($this, '_curl_requests_to_paypal_use_tls'), 10, 3);
53
+	}
54
+
55
+
56
+
57
+	/**
58
+	 * Using the selected gateway, processes the payment for that transaction, and updates the transaction
59
+	 * appropriately. Saves the payment that is generated
60
+	 *
61
+	 * @param EE_Payment_Method    $payment_method
62
+	 * @param EE_Transaction       $transaction
63
+	 * @param float                $amount       if only part of the transaction is to be paid for, how much.
64
+	 *                                           Leave null if payment is for the full amount owing
65
+	 * @param EE_Billing_Info_Form $billing_form (or probably null, if it's an offline or offsite payment method).
66
+	 *                                           Receive_form_submission() should have
67
+	 *                                           already been called on the billing form
68
+	 *                                           (ie, its inputs should have their normalized values set).
69
+	 * @param string               $return_url   string used mostly by offsite gateways to specify
70
+	 *                                           where to go AFTER the offsite gateway
71
+	 * @param string               $method       like 'CART', indicates who the client who called this was
72
+	 * @param bool                 $by_admin     TRUE if payment is being attempted from the admin
73
+	 * @param boolean              $update_txn   whether or not to call
74
+	 *                                           EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment()
75
+	 * @param string               $cancel_url   URL to return to if off-site payments are cancelled
76
+	 * @return \EE_Payment
77
+	 * @throws \EE_Error
78
+	 */
79
+	public function process_payment(
80
+		EE_Payment_Method $payment_method,
81
+		EE_Transaction $transaction,
82
+		$amount = null,
83
+		$billing_form = null,
84
+		$return_url = null,
85
+		$method = 'CART',
86
+		$by_admin = false,
87
+		$update_txn = true,
88
+		$cancel_url = ''
89
+	) {
90
+		if ((float)$amount < 0) {
91
+			throw new EE_Error(
92
+				sprintf(
93
+					__(
94
+						'Attempting to make a payment for a negative amount of %1$d for transaction %2$d. That should be a refund',
95
+						'event_espresso'
96
+					),
97
+					$amount,
98
+					$transaction->ID()
99
+				)
100
+			);
101
+		}
102
+		// verify payment method
103
+		$payment_method = EEM_Payment_Method::instance()->ensure_is_obj($payment_method, true);
104
+		// verify transaction
105
+		EEM_Transaction::instance()->ensure_is_obj($transaction);
106
+		$transaction->set_payment_method_ID($payment_method->ID());
107
+		// verify payment method type
108
+		if ($payment_method->type_obj() instanceof EE_PMT_Base) {
109
+			$payment = $payment_method->type_obj()->process_payment(
110
+				$transaction,
111
+				min($amount, $transaction->remaining()),//make sure we don't overcharge
112
+				$billing_form,
113
+				$return_url,
114
+				add_query_arg(array('ee_cancel_payment' => true), $cancel_url),
115
+				$method,
116
+				$by_admin
117
+			);
118
+			// check if payment method uses an off-site gateway
119
+			if ($payment_method->type_obj()->payment_occurs() !== EE_PMT_Base::offsite) {
120
+				// don't process payments for off-site gateways yet because no payment has occurred yet
121
+				$this->update_txn_based_on_payment($transaction, $payment, $update_txn);
122
+			}
123
+			return $payment;
124
+		} else {
125
+			EE_Error::add_error(
126
+				sprintf(
127
+					__('A valid payment method could not be determined due to a technical issue.%sPlease try again or contact %s for assistance.', 'event_espresso'),
128
+					'<br/>',
129
+					EE_Registry::instance()->CFG->organization->get_pretty('email')
130
+				), __FILE__, __FUNCTION__, __LINE__
131
+			);
132
+			return null;
133
+		}
134
+	}
135
+
136
+
137
+
138
+	/**
139
+	 * @param EE_Transaction|int $transaction
140
+	 * @param EE_Payment_Method  $payment_method
141
+	 * @throws EE_Error
142
+	 * @return string
143
+	 */
144
+	public function get_ipn_url_for_payment_method($transaction, $payment_method)
145
+	{
146
+		/** @type \EE_Transaction $transaction */
147
+		$transaction = EEM_Transaction::instance()->ensure_is_obj($transaction);
148
+		$primary_reg = $transaction->primary_registration();
149
+		if ( ! $primary_reg instanceof EE_Registration) {
150
+			throw new EE_Error(
151
+				sprintf(
152
+					__(
153
+						"Cannot get IPN URL for transaction with ID %d because it has no primary registration",
154
+						"event_espresso"
155
+					),
156
+					$transaction->ID()
157
+				)
158
+			);
159
+		}
160
+		$payment_method = EEM_Payment_Method::instance()->ensure_is_obj($payment_method, true);
161
+		$url = add_query_arg(
162
+			array(
163
+				'e_reg_url_link'    => $primary_reg->reg_url_link(),
164
+				'ee_payment_method' => $payment_method->slug(),
165
+			),
166
+			EE_Registry::instance()->CFG->core->txn_page_url()
167
+		);
168
+		return $url;
169
+	}
170
+
171
+
172
+
173
+	/**
174
+	 * Process the IPN. Firstly, we'll hope we put the standard args into the IPN URL so
175
+	 * we can easily find what registration the IPN is for and what payment method.
176
+	 * However, if not, we'll give all payment methods a chance to claim it and process it.
177
+	 * If a payment is found for the IPN info, it is saved.
178
+	 *
179
+	 * @param array              $_req_data            eg $_REQUEST
180
+	 * @param EE_Transaction|int $transaction          optional (or a transactions id)
181
+	 * @param EE_Payment_Method  $payment_method       (or a slug or id of one)
182
+	 * @param boolean            $update_txn           whether or not to call
183
+	 *                                                 EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment()
184
+	 * @param bool               $separate_IPN_request whether the IPN uses a separate request ( true like PayPal )
185
+	 *                                                 or is processed manually ( false like Mijireh )
186
+	 * @throws EE_Error
187
+	 * @throws Exception
188
+	 * @return EE_Payment
189
+	 */
190
+	public function process_ipn(
191
+		$_req_data,
192
+		$transaction = null,
193
+		$payment_method = null,
194
+		$update_txn = true,
195
+		$separate_IPN_request = true
196
+	) {
197
+		EE_Registry::instance()->load_model('Change_Log');
198
+		$_req_data = $this->_remove_unusable_characters_from_array((array)$_req_data);
199
+		EE_Processor_Base::set_IPN($separate_IPN_request);
200
+		$obj_for_log = null;
201
+		if ($transaction instanceof EE_Transaction) {
202
+			$obj_for_log = $transaction;
203
+			if ($payment_method instanceof EE_Payment_Method) {
204
+				$obj_for_log = EEM_Payment::instance()->get_one(
205
+					array(
206
+						array('TXN_ID' => $transaction->ID(), 'PMD_ID' => $payment_method->ID()),
207
+						'order_by' => array('PAY_timestamp' => 'desc'),
208
+					)
209
+				);
210
+			}
211
+		} else if ($payment_method instanceof EE_Payment) {
212
+			$obj_for_log = $payment_method;
213
+		}
214
+		$log = EEM_Change_Log::instance()->log(
215
+			EEM_Change_Log::type_gateway,
216
+			array('IPN data received' => $_req_data),
217
+			$obj_for_log
218
+		);
219
+		try {
220
+			/**
221
+			 * @var EE_Payment $payment
222
+			 */
223
+			$payment = null;
224
+			if ($transaction && $payment_method) {
225
+				/** @type EE_Transaction $transaction */
226
+				$transaction = EEM_Transaction::instance()->ensure_is_obj($transaction);
227
+				/** @type EE_Payment_Method $payment_method */
228
+				$payment_method = EEM_Payment_Method::instance()->ensure_is_obj($payment_method);
229
+				if ($payment_method->type_obj() instanceof EE_PMT_Base) {
230
+					try {
231
+						$payment = $payment_method->type_obj()->handle_ipn($_req_data, $transaction);
232
+						$log->set_object($payment);
233
+					} catch (EventEspresso\core\exceptions\IpnException $e) {
234
+						EEM_Change_Log::instance()->log(
235
+							EEM_Change_Log::type_gateway,
236
+							array(
237
+								'message'     => 'IPN Exception: ' . $e->getMessage(),
238
+								'current_url' => EEH_URL::current_url(),
239
+								'payment'     => $e->getPaymentProperties(),
240
+								'IPN_data'    => $e->getIpnData(),
241
+							),
242
+							$obj_for_log
243
+						);
244
+						return $e->getPayment();
245
+					}
246
+				} else {
247
+					// not a payment
248
+					EE_Error::add_error(
249
+						sprintf(
250
+							__('A valid payment method could not be determined due to a technical issue.%sPlease refresh your browser and try again or contact %s for assistance.', 'event_espresso'),
251
+							'<br/>',
252
+							EE_Registry::instance()->CFG->organization->get_pretty('email')
253
+						),
254
+						__FILE__, __FUNCTION__, __LINE__
255
+					);
256
+				}
257
+			} else {
258
+				//that's actually pretty ok. The IPN just wasn't able
259
+				//to identify which transaction or payment method this was for
260
+				// give all active payment methods a chance to claim it
261
+				$active_payment_methods = EEM_Payment_Method::instance()->get_all_active();
262
+				foreach ($active_payment_methods as $active_payment_method) {
263
+					try {
264
+						$payment = $active_payment_method->type_obj()->handle_unclaimed_ipn($_req_data);
265
+						$payment_method = $active_payment_method;
266
+						EEM_Change_Log::instance()->log(
267
+							EEM_Change_Log::type_gateway, array('IPN data' => $_req_data), $payment
268
+						);
269
+						break;
270
+					} catch (EventEspresso\core\exceptions\IpnException $e) {
271
+						EEM_Change_Log::instance()->log(
272
+							EEM_Change_Log::type_gateway,
273
+							array(
274
+								'message'     => 'IPN Exception: ' . $e->getMessage(),
275
+								'current_url' => EEH_URL::current_url(),
276
+								'payment'     => $e->getPaymentProperties(),
277
+								'IPN_data'    => $e->getIpnData(),
278
+							),
279
+							$obj_for_log
280
+						);
281
+						return $e->getPayment();
282
+					} catch (EE_Error $e) {
283
+						//that's fine- it apparently couldn't handle the IPN
284
+					}
285
+				}
286
+			}
287
+			// 			EEM_Payment_Log::instance()->log("got to 7",$transaction,$payment_method);
288
+			if ($payment instanceof EE_Payment) {
289
+				$payment->save();
290
+				//  update the TXN
291
+				$this->update_txn_based_on_payment($transaction, $payment, $update_txn, $separate_IPN_request);
292
+			} else {
293
+				//we couldn't find the payment for this IPN... let's try and log at least SOMETHING
294
+				if ($payment_method) {
295
+					EEM_Change_Log::instance()->log(EEM_Change_Log::type_gateway, array('IPN data' => $_req_data), $payment_method);
296
+				} elseif ($transaction) {
297
+					EEM_Change_Log::instance()->log(EEM_Change_Log::type_gateway, array('IPN data' => $_req_data), $transaction);
298
+				}
299
+			}
300
+			return $payment;
301
+		} catch (EE_Error $e) {
302
+			do_action(
303
+				'AHEE__log', __FILE__, __FUNCTION__, sprintf(
304
+					__('Error occurred while receiving IPN. Transaction: %1$s, req data: %2$s. The error was "%3$s"', 'event_espresso'),
305
+					print_r($transaction, true),
306
+					print_r($_req_data, true),
307
+					$e->getMessage()
308
+				)
309
+			);
310
+			throw $e;
311
+		}
312
+	}
313
+
314
+
315
+
316
+	/**
317
+	 * Removes any non-printable illegal characters from the input,
318
+	 * which might cause a raucous when trying to insert into the database
319
+	 *
320
+	 * @param  array $request_data
321
+	 * @return array
322
+	 */
323
+	protected function _remove_unusable_characters_from_array(array $request_data)
324
+	{
325
+		$return_data = array();
326
+		foreach ($request_data as $key => $value) {
327
+			$return_data[$this->_remove_unusable_characters($key)] = $this->_remove_unusable_characters($value);
328
+		}
329
+		return $return_data;
330
+	}
331
+
332
+
333
+
334
+	/**
335
+	 * Removes any non-printable illegal characters from the input,
336
+	 * which might cause a raucous when trying to insert into the database
337
+	 *
338
+	 * @param string $request_data
339
+	 * @return string
340
+	 */
341
+	protected function _remove_unusable_characters($request_data)
342
+	{
343
+		return preg_replace('/[^[:print:]]/', '', $request_data);
344
+	}
345
+
346
+
347
+
348
+	/**
349
+	 * Should be called just before displaying the payment attempt results to the user,
350
+	 * when the payment attempt has finished. Some payment methods may have special
351
+	 * logic to perform here. For example, if process_payment() happens on a special request
352
+	 * and then the user is redirected to a page that displays the payment's status, this
353
+	 * should be called while loading the page that displays the payment's status. If the user is
354
+	 * sent to an offsite payment provider, this should be called upon returning from that offsite payment
355
+	 * provider.
356
+	 *
357
+	 * @param EE_Transaction|int $transaction
358
+	 * @param bool               $update_txn whether or not to call
359
+	 *                                       EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment()
360
+	 * @throws \EE_Error
361
+	 * @return EE_Payment
362
+	 * @deprecated 4.6.24 method is no longer used. Instead it is up to client code, like SPCO,
363
+	 *                                       to call handle_ipn() for offsite gateways that don't receive separate IPNs
364
+	 */
365
+	public function finalize_payment_for($transaction, $update_txn = true)
366
+	{
367
+		/** @var $transaction EE_Transaction */
368
+		$transaction = EEM_Transaction::instance()->ensure_is_obj($transaction);
369
+		$last_payment_method = $transaction->payment_method();
370
+		if ($last_payment_method instanceof EE_Payment_Method) {
371
+			$payment = $last_payment_method->type_obj()->finalize_payment_for($transaction);
372
+			$this->update_txn_based_on_payment($transaction, $payment, $update_txn);
373
+			return $payment;
374
+		} else {
375
+			return null;
376
+		}
377
+	}
378
+
379
+
380
+
381
+	/**
382
+	 * Processes a direct refund request, saves the payment, and updates the transaction appropriately.
383
+	 *
384
+	 * @param EE_Payment_Method $payment_method
385
+	 * @param EE_Payment        $payment_to_refund
386
+	 * @param array             $refund_info
387
+	 * @return EE_Payment
388
+	 * @throws \EE_Error
389
+	 */
390
+	public function process_refund(
391
+		EE_Payment_Method $payment_method,
392
+		EE_Payment $payment_to_refund,
393
+		$refund_info = array()
394
+	) {
395
+		if ($payment_method instanceof EE_Payment_Method && $payment_method->type_obj()->supports_sending_refunds()) {
396
+			$payment_method->type_obj()->process_refund($payment_to_refund, $refund_info);
397
+			$this->update_txn_based_on_payment($payment_to_refund->transaction(), $payment_to_refund);
398
+		}
399
+		return $payment_to_refund;
400
+	}
401
+
402
+
403
+
404
+	/**
405
+	 * This should be called each time there may have been an update to a
406
+	 * payment on a transaction (ie, we asked for a payment to process a
407
+	 * payment for a transaction, or we told a payment method about an IPN, or
408
+	 * we told a payment method to
409
+	 * "finalize_payment_for" (a transaction), or we told a payment method to
410
+	 * process a refund. This should handle firing the correct hooks to
411
+	 * indicate
412
+	 * what exactly happened and updating the transaction appropriately). This
413
+	 * could be integrated directly into EE_Transaction upon save, but we want
414
+	 * this logic to be separate from 'normal' plain-jane saving and updating
415
+	 * of transactions and payments, and to be tied to payment processing.
416
+	 * Note: this method DOES NOT save the payment passed into it. It is the responsibility
417
+	 * of previous code to decide whether or not to save (because the payment passed into
418
+	 * this method might be a temporary, never-to-be-saved payment from an offline gateway,
419
+	 * in which case we only want that payment object for some temporary usage during this request,
420
+	 * but we don't want it to be saved).
421
+	 *
422
+	 * @param EE_Transaction|int $transaction
423
+	 * @param EE_Payment         $payment
424
+	 * @param boolean            $update_txn
425
+	 *                        whether or not to call
426
+	 *                        EE_Transaction_Processor::
427
+	 *                        update_transaction_and_registrations_after_checkout_or_payment()
428
+	 *                        (you can save 1 DB query if you know you're going
429
+	 *                        to save it later instead)
430
+	 * @param bool               $IPN
431
+	 *                        if processing IPNs or other similar payment
432
+	 *                        related activities that occur in alternate
433
+	 *                        requests than the main one that is processing the
434
+	 *                        TXN, then set this to true to check whether the
435
+	 *                        TXN is locked before updating
436
+	 * @throws \EE_Error
437
+	 */
438
+	public function update_txn_based_on_payment($transaction, $payment, $update_txn = true, $IPN = false)
439
+	{
440
+		$do_action = 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__not_successful';
441
+		/** @type EE_Transaction $transaction */
442
+		$transaction = EEM_Transaction::instance()->ensure_is_obj($transaction);
443
+		// can we freely update the TXN at this moment?
444
+		if ($IPN && $transaction->is_locked()) {
445
+			// don't update the transaction at this exact moment
446
+			// because the TXN is active in another request
447
+			EE_Cron_Tasks::schedule_update_transaction_with_payment(
448
+				time(),
449
+				$transaction->ID(),
450
+				$payment->ID()
451
+			);
452
+		} else {
453
+			// verify payment and that it has been saved
454
+			if ($payment instanceof EE_Payment && $payment->ID()) {
455
+				if (
456
+					$payment->payment_method() instanceof EE_Payment_Method
457
+					&& $payment->payment_method()->type_obj() instanceof EE_PMT_Base
458
+				) {
459
+					$payment->payment_method()->type_obj()->update_txn_based_on_payment($payment);
460
+					// update TXN registrations with payment info
461
+					$this->process_registration_payments($transaction, $payment);
462
+				}
463
+				$do_action = $payment->just_approved()
464
+					? 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__successful'
465
+					: $do_action;
466
+			} else {
467
+				// send out notifications
468
+				add_filter('FHEE__EED_Messages___maybe_registration__deliver_notifications', '__return_true');
469
+				$do_action = 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__no_payment_made';
470
+			}
471
+			if ($payment instanceof EE_Payment && $payment->status() !== EEM_Payment::status_id_failed) {
472
+				/** @type EE_Transaction_Payments $transaction_payments */
473
+				$transaction_payments = EE_Registry::instance()->load_class('Transaction_Payments');
474
+				// set new value for total paid
475
+				$transaction_payments->calculate_total_payments_and_update_status($transaction);
476
+				// call EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment() ???
477
+				if ($update_txn) {
478
+					$this->_post_payment_processing($transaction, $payment, $IPN);
479
+				}
480
+			}
481
+			// granular hook for others to use.
482
+			do_action($do_action, $transaction, $payment);
483
+			do_action('AHEE_log', __CLASS__, __FUNCTION__, $do_action, '$do_action');
484
+			//global hook for others to use.
485
+			do_action('AHEE__EE_Payment_Processor__update_txn_based_on_payment', $transaction, $payment);
486
+		}
487
+	}
488
+
489
+
490
+
491
+	/**
492
+	 * update registrations REG_paid field after successful payment and link registrations with payment
493
+	 *
494
+	 * @param EE_Transaction    $transaction
495
+	 * @param EE_Payment        $payment
496
+	 * @param EE_Registration[] $registrations
497
+	 * @throws \EE_Error
498
+	 */
499
+	public function process_registration_payments(
500
+		EE_Transaction $transaction,
501
+		EE_Payment $payment,
502
+		$registrations = array()
503
+	) {
504
+		// only process if payment was successful
505
+		if ($payment->status() !== EEM_Payment::status_id_approved) {
506
+			return;
507
+		}
508
+		//EEM_Registration::instance()->show_next_x_db_queries();
509
+		if (empty($registrations)) {
510
+			// find registrations with monies owing that can receive a payment
511
+			$registrations = $transaction->registrations(
512
+				array(
513
+					array(
514
+						// only these reg statuses can receive payments
515
+						'STS_ID'           => array('IN', EEM_Registration::reg_statuses_that_allow_payment()),
516
+						'REG_final_price'  => array('!=', 0),
517
+						'REG_final_price*' => array('!=', 'REG_paid', true),
518
+					),
519
+				)
520
+			);
521
+		}
522
+		// still nothing ??!??
523
+		if (empty($registrations)) {
524
+			return;
525
+		}
526
+		// todo: break out the following logic into a separate strategy class
527
+		// todo: named something like "Sequential_Reg_Payment_Strategy"
528
+		// todo: which would apply payments using the capitalist "first come first paid" approach
529
+		// todo: then have another strategy class like "Distributed_Reg_Payment_Strategy"
530
+		// todo: which would be the socialist "everybody gets a piece of pie" approach,
531
+		// todo: which would be better for deposits, where you want a bit of the payment applied to each registration
532
+		$refund = $payment->is_a_refund();
533
+		// how much is available to apply to registrations?
534
+		$available_payment_amount = abs($payment->amount());
535
+		foreach ($registrations as $registration) {
536
+			if ($registration instanceof EE_Registration) {
537
+				// nothing left?
538
+				if ($available_payment_amount <= 0) {
539
+					break;
540
+				}
541
+				if ($refund) {
542
+					$available_payment_amount = $this->process_registration_refund($registration, $payment, $available_payment_amount);
543
+				} else {
544
+					$available_payment_amount = $this->process_registration_payment($registration, $payment, $available_payment_amount);
545
+				}
546
+			}
547
+		}
548
+		if ($available_payment_amount > 0 && apply_filters('FHEE__EE_Payment_Processor__process_registration_payments__display_notifications', false)) {
549
+			EE_Error::add_attention(
550
+				sprintf(
551
+					__('A remainder of %1$s exists after applying this payment to Registration(s) %2$s.%3$sPlease verify that the original payment amount of %4$s is correct. If so, you should edit this payment and select at least one additional registration in the "Registrations to Apply Payment to" section, so that the remainder of this payment can be applied to the additional registration(s).',
552
+						'event_espresso'),
553
+					EEH_Template::format_currency($available_payment_amount),
554
+					implode(', ', array_keys($registrations)),
555
+					'<br/>',
556
+					EEH_Template::format_currency($payment->amount())
557
+				),
558
+				__FILE__, __FUNCTION__, __LINE__
559
+			);
560
+		}
561
+	}
562
+
563
+
564
+
565
+	/**
566
+	 * update registration REG_paid field after successful payment and link registration with payment
567
+	 *
568
+	 * @param EE_Registration $registration
569
+	 * @param EE_Payment      $payment
570
+	 * @param float           $available_payment_amount
571
+	 * @return float
572
+	 * @throws \EE_Error
573
+	 */
574
+	public function process_registration_payment(
575
+		EE_Registration $registration,
576
+		EE_Payment $payment,
577
+		$available_payment_amount = 0.00
578
+	) {
579
+		$owing = $registration->final_price() - $registration->paid();
580
+		if ($owing > 0) {
581
+			// don't allow payment amount to exceed the available payment amount, OR the amount owing
582
+			$payment_amount = min($available_payment_amount, $owing);
583
+			// update $available_payment_amount
584
+			$available_payment_amount -= $payment_amount;
585
+			//calculate and set new REG_paid
586
+			$registration->set_paid($registration->paid() + $payment_amount);
587
+			// now save it
588
+			$this->_apply_registration_payment($registration, $payment, $payment_amount);
589
+		}
590
+		return $available_payment_amount;
591
+	}
592
+
593
+
594
+
595
+	/**
596
+	 * update registration REG_paid field after successful payment and link registration with payment
597
+	 *
598
+	 * @param EE_Registration $registration
599
+	 * @param EE_Payment      $payment
600
+	 * @param float           $payment_amount
601
+	 * @return void
602
+	 * @throws \EE_Error
603
+	 */
604
+	protected function _apply_registration_payment(
605
+		EE_Registration $registration,
606
+		EE_Payment $payment,
607
+		$payment_amount = 0.00
608
+	) {
609
+		// find any existing reg payment records for this registration and payment
610
+		$existing_reg_payment = EEM_Registration_Payment::instance()->get_one(
611
+			array(array('REG_ID' => $registration->ID(), 'PAY_ID' => $payment->ID()))
612
+		);
613
+		// if existing registration payment exists
614
+		if ($existing_reg_payment instanceof EE_Registration_Payment) {
615
+			// then update that record
616
+			$existing_reg_payment->set_amount($payment_amount);
617
+			$existing_reg_payment->save();
618
+		} else {
619
+			// or add new relation between registration and payment and set amount
620
+			$registration->_add_relation_to($payment, 'Payment', array('RPY_amount' => $payment_amount));
621
+			// make it stick
622
+			$registration->save();
623
+		}
624
+	}
625
+
626
+
627
+
628
+	/**
629
+	 * update registration REG_paid field after refund and link registration with payment
630
+	 *
631
+	 * @param EE_Registration $registration
632
+	 * @param EE_Payment      $payment
633
+	 * @param float           $available_refund_amount - IMPORTANT !!! SEND AVAILABLE REFUND AMOUNT AS A POSITIVE NUMBER
634
+	 * @return float
635
+	 * @throws \EE_Error
636
+	 */
637
+	public function process_registration_refund(
638
+		EE_Registration $registration,
639
+		EE_Payment $payment,
640
+		$available_refund_amount = 0.00
641
+	) {
642
+		//EEH_Debug_Tools::printr( $payment->amount(), '$payment->amount()', __FILE__, __LINE__ );
643
+		if ($registration->paid() > 0) {
644
+			// ensure $available_refund_amount is NOT negative
645
+			$available_refund_amount = (float)abs($available_refund_amount);
646
+			// don't allow refund amount to exceed the available payment amount, OR the amount paid
647
+			$refund_amount = min($available_refund_amount, (float)$registration->paid());
648
+			// update $available_payment_amount
649
+			$available_refund_amount -= $refund_amount;
650
+			//calculate and set new REG_paid
651
+			$registration->set_paid($registration->paid() - $refund_amount);
652
+			// convert payment amount back to a negative value for storage in the db
653
+			$refund_amount = (float)abs($refund_amount) * -1;
654
+			// now save it
655
+			$this->_apply_registration_payment($registration, $payment, $refund_amount);
656
+		}
657
+		return $available_refund_amount;
658
+	}
659
+
660
+
661
+
662
+	/**
663
+	 * Process payments and transaction after payment process completed.
664
+	 * ultimately this will send the TXN and payment details off so that notifications can be sent out.
665
+	 * if this request happens to be processing an IPN,
666
+	 * then we will also set the Payment Options Reg Step to completed,
667
+	 * and attempt to completely finalize the TXN if all of the other Reg Steps are completed as well.
668
+	 *
669
+	 * @param EE_Transaction $transaction
670
+	 * @param EE_Payment     $payment
671
+	 * @param bool           $IPN
672
+	 * @throws \EE_Error
673
+	 */
674
+	protected function _post_payment_processing(EE_Transaction $transaction, EE_Payment $payment, $IPN = false)
675
+	{
676
+		/** @type EE_Transaction_Processor $transaction_processor */
677
+		$transaction_processor = EE_Registry::instance()->load_class('Transaction_Processor');
678
+		// is the Payment Options Reg Step completed ?
679
+		$payment_options_step_completed = $transaction->reg_step_completed('payment_options');
680
+		// if the Payment Options Reg Step is completed...
681
+		$revisit = $payment_options_step_completed === true ? true : false;
682
+		// then this is kinda sorta a revisit with regards to payments at least
683
+		$transaction_processor->set_revisit($revisit);
684
+		// if this is an IPN, let's consider the Payment Options Reg Step completed if not already
685
+		if (
686
+			$IPN
687
+			&& $payment_options_step_completed !== true
688
+			&& ($payment->is_approved() || $payment->is_pending())
689
+		) {
690
+			$payment_options_step_completed = $transaction->set_reg_step_completed(
691
+				'payment_options'
692
+			);
693
+		}
694
+		// maybe update status, but don't save transaction just yet
695
+		$transaction->update_status_based_on_total_paid(false);
696
+		// check if 'finalize_registration' step has been completed...
697
+		$finalized = $transaction->reg_step_completed('finalize_registration');
698
+		//  if this is an IPN and the final step has not been initiated
699
+		if ($IPN && $payment_options_step_completed && $finalized === false) {
700
+			// and if it hasn't already been set as being started...
701
+			$finalized = $transaction->set_reg_step_initiated('finalize_registration');
702
+		}
703
+		$transaction->save();
704
+		// because the above will return false if the final step was not fully completed, we need to check again...
705
+		if ($IPN && $finalized !== false) {
706
+			// and if we are all good to go, then send out notifications
707
+			add_filter('FHEE__EED_Messages___maybe_registration__deliver_notifications', '__return_true');
708
+			//ok, now process the transaction according to the payment
709
+			$transaction_processor->update_transaction_and_registrations_after_checkout_or_payment($transaction, $payment);
710
+		}
711
+		// DEBUG LOG
712
+		$payment_method = $payment->payment_method();
713
+		if ($payment_method instanceof EE_Payment_Method) {
714
+			$payment_method_type_obj = $payment_method->type_obj();
715
+			if ($payment_method_type_obj instanceof EE_PMT_Base) {
716
+				$gateway = $payment_method_type_obj->get_gateway();
717
+				if ($gateway instanceof EE_Gateway) {
718
+					$gateway->log(
719
+						array(
720
+							'message'               => __('Post Payment Transaction Details', 'event_espresso'),
721
+							'transaction'           => $transaction->model_field_array(),
722
+							'finalized'             => $finalized,
723
+							'IPN'                   => $IPN,
724
+							'deliver_notifications' => has_filter(
725
+								'FHEE__EED_Messages___maybe_registration__deliver_notifications'
726
+							),
727
+						),
728
+						$payment
729
+					);
730
+				}
731
+			}
732
+		}
733
+	}
734
+
735
+
736
+
737
+	/**
738
+	 * Force posts to PayPal to use TLS v1.2. See:
739
+	 * https://core.trac.wordpress.org/ticket/36320
740
+	 * https://core.trac.wordpress.org/ticket/34924#comment:15
741
+	 * https://www.paypal-knowledge.com/infocenter/index?page=content&widgetview=true&id=FAQ1914&viewlocale=en_US
742
+	 * This will affect paypal standard, pro, express, and payflow.
743
+	 */
744
+	public static function _curl_requests_to_paypal_use_tls($handle, $r, $url)
745
+	{
746
+		if (strstr($url, 'https://') && strstr($url, '.paypal.com')) {
747
+			//Use the value of the constant CURL_SSLVERSION_TLSv1 = 1
748
+			//instead of the constant because it might not be defined
749
+			curl_setopt($handle, CURLOPT_SSLVERSION, 1);
750
+		}
751
+	}
752 752
 }
Please login to merge, or discard this patch.
core/libraries/payment_methods/EEI_Payment_Method_Interfaces.php 1 patch
Spacing   +3 added lines, -3 removed lines patch added patch discarded remove patch
@@ -5,7 +5,7 @@  discard block
 block discarded – undo
5 5
  *
6 6
  * allows gateways to be used by different systems other than Event Espresso
7 7
  */
8
-interface EEI_Payment extends EEI_Base{
8
+interface EEI_Payment extends EEI_Base {
9 9
 
10 10
 	/**
11 11
 	 * @return string indicating which the payment is approved, pending, cancelled or failed
@@ -153,7 +153,7 @@  discard block
 block discarded – undo
153 153
 /**
154 154
  * Interface EEI_Payment_Method
155 155
  */
156
-interface EEI_Payment_Method{
156
+interface EEI_Payment_Method {
157 157
 
158 158
 }
159 159
 
@@ -172,7 +172,7 @@  discard block
 block discarded – undo
172 172
 	 * @param string $model_name
173 173
 	 * @return EE_Log
174 174
 	 */
175
-	public function gateway_log($message,$id,$model_name);
175
+	public function gateway_log($message, $id, $model_name);
176 176
 }
177 177
 
178 178
 
Please login to merge, or discard this patch.
payment_methods/Paypal_Express/EEG_Paypal_Express.gateway.php 2 patches
Indentation   +98 added lines, -100 removed lines patch added patch discarded remove patch
@@ -44,77 +44,76 @@  discard block
 block discarded – undo
44 44
 	 */
45 45
 	protected $_image_url;
46 46
 
47
-    /**
48
-     * gateway URL variable
49
-     *
50
-     * @var string
51
-     */
52
-    protected $_base_gateway_url = '';
53
-
54
-
55
-
56
-    /**
57
-     * EEG_Paypal_Express constructor.
58
-     */
59
-    public function __construct()
60
-    {
61
-        $this->_currencies_supported = array(
62
-            'USD',
63
-            'AUD',
64
-            'BRL',
65
-            'CAD',
66
-            'CZK',
67
-            'DKK',
68
-            'EUR',
69
-            'HKD',
70
-            'HUF',
71
-            'ILS',
72
-            'JPY',
73
-            'MYR',
74
-            'MXN',
75
-            'NOK',
76
-            'NZD',
77
-            'PHP',
78
-            'PLN',
79
-            'GBP',
80
-            'RUB',
81
-            'SGD',
82
-            'SEK',
83
-            'CHF',
84
-            'TWD',
85
-            'THB',
86
-            'TRY'
87
-        );
88
-        parent::__construct();
89
-    }
90
-
91
-
92
-
93
-    /**
94
-	 * Sets the gateway URL variable based on whether debug mode is enabled or not.
47
+	/**
48
+	 * gateway URL variable
49
+	 *
50
+	 * @var string
51
+	 */
52
+	protected $_base_gateway_url = '';
53
+
54
+
55
+
56
+	/**
57
+	 * EEG_Paypal_Express constructor.
58
+	 */
59
+	public function __construct()
60
+	{
61
+		$this->_currencies_supported = array(
62
+			'USD',
63
+			'AUD',
64
+			'BRL',
65
+			'CAD',
66
+			'CZK',
67
+			'DKK',
68
+			'EUR',
69
+			'HKD',
70
+			'HUF',
71
+			'ILS',
72
+			'JPY',
73
+			'MYR',
74
+			'MXN',
75
+			'NOK',
76
+			'NZD',
77
+			'PHP',
78
+			'PLN',
79
+			'GBP',
80
+			'RUB',
81
+			'SGD',
82
+			'SEK',
83
+			'CHF',
84
+			'TWD',
85
+			'THB',
86
+			'TRY'
87
+		);
88
+		parent::__construct();
89
+	}
90
+
95 91
 
92
+
93
+	/**
94
+	 * Sets the gateway URL variable based on whether debug mode is enabled or not.
96 95
 	 *
97 96
 *@param array $settings_array
98 97
 	 */
99 98
 	public function set_settings( $settings_array ) {
100 99
 		parent::set_settings($settings_array);
101 100
 		// Redirect URL.
102
-        $this->_base_gateway_url = $this->_debug_mode
103
-            ? 'https://api-3t.sandbox.paypal.com/nvp'
104
-            : 'https://api-3t.paypal.com/nvp';
101
+		$this->_base_gateway_url = $this->_debug_mode
102
+			? 'https://api-3t.sandbox.paypal.com/nvp'
103
+			: 'https://api-3t.paypal.com/nvp';
105 104
 	}
106 105
 
107 106
 
108 107
 
109
-    /**
110
-     * @param EEI_Payment $payment
111
-     * @param array       $billing_info
112
-     * @param string      $return_url
113
-     * @param string      $notify_url
114
-     * @param string      $cancel_url
115
-     * @return \EE_Payment|\EEI_Payment
116
-     * @throws \EE_Error
117
-     */
108
+	/**
109
+	 * @param EEI_Payment $payment
110
+	 * @param array       $billing_info
111
+	 * @param string      $return_url
112
+	 * @param string      $notify_url
113
+	 * @param string      $cancel_url
114
+	 * @return \EE_Payment|\EEI_Payment
115
+	 * @throws \EE_Error
116
+	 */
118 117
 	public function set_redirection_info( $payment, $billing_info = array(), $return_url = NULL, $notify_url = NULL, $cancel_url = NULL ) {
119 118
 		if ( ! $payment instanceof EEI_Payment ) {
120 119
 			$payment->set_gateway_response( __( 'Error. No associated payment was found.', 'event_espresso' ) );
@@ -202,9 +201,9 @@  discard block
 block discarded – undo
202 201
 				$token_request_dtls['L_PAYMENTREQUEST_0_NUMBER'.$item_num] = $item_num + 1;
203 202
 				// Item quantity.
204 203
 				$token_request_dtls['L_PAYMENTREQUEST_0_QTY'.$item_num] = 1;
205
-                // Digital item is sold.
206
-                $token_request_dtls['L_PAYMENTREQUEST_0_ITEMCATEGORY'.$item_num] = 'Physical';
207
-                $item_num++;
204
+				// Digital item is sold.
205
+				$token_request_dtls['L_PAYMENTREQUEST_0_ITEMCATEGORY'.$item_num] = 'Physical';
206
+				$item_num++;
208 207
 			}
209 208
 		} else {
210 209
 			// Just one Item.
@@ -272,7 +271,6 @@  discard block
 block discarded – undo
272 271
 
273 272
 
274 273
 	/**
275
-
276 274
 	 *  @param array $update_info {
277 275
 	 *	  @type string $gateway_txn_id
278 276
 	 *	  @type string status an EEMI_Payment status
@@ -292,8 +290,8 @@  discard block
 block discarded – undo
292 290
 				return $payment;
293 291
 			}
294 292
 			$primary_registrant = $transaction->primary_registration();
295
-            $payment_details = $payment->details();
296
-            // Check if we still have the token.
293
+			$payment_details = $payment->details();
294
+			// Check if we still have the token.
297 295
 			if ( ! isset($payment_details['TOKEN']) || empty($payment_details['TOKEN']) ) {
298 296
 				$payment->set_status( $this->_pay_model->failed_status() );
299 297
 				return $payment;
@@ -402,36 +400,36 @@  discard block
 block discarded – undo
402 400
 	 */
403 401
 	public function _ppExpress_check_response( $request_response ) {
404 402
 		if (empty($request_response['body']) || is_wp_error( $request_response ) ) {
405
-            // If we got here then there was an error in this request.
406
-            return array('status' => false, 'args' => $request_response);
407
-        }
408
-        $response_args = array();
409
-        parse_str( urldecode($request_response['body']), $response_args );
410
-        if ( ! isset($response_args['ACK'])) {
411
-            return array('status' => false, 'args' => $request_response);
412
-        }
413
-        if (
414
-            $response_args['ACK'] === 'Success'
415
-            && (
416
-                isset($response_args['PAYERID'])
417
-                || isset($response_args['PAYMENTINFO_0_TRANSACTIONID'])
418
-                || (isset($response_args['PAYMENTSTATUS']) && $response_args['PAYMENTSTATUS'] === 'Completed')
419
-                || isset($response_args['TOKEN'])
420
-            )
421
-        ) {
422
-            // Response status OK, return response parameters for further processing.
423
-            return array('status' => true, 'args' => $response_args);
424
-        } else {
425
-            $errors = $this->_get_errors($response_args);
426
-            return array('status' => false, 'args' => $errors);
427
-        }
403
+			// If we got here then there was an error in this request.
404
+			return array('status' => false, 'args' => $request_response);
405
+		}
406
+		$response_args = array();
407
+		parse_str( urldecode($request_response['body']), $response_args );
408
+		if ( ! isset($response_args['ACK'])) {
409
+			return array('status' => false, 'args' => $request_response);
410
+		}
411
+		if (
412
+			$response_args['ACK'] === 'Success'
413
+			&& (
414
+				isset($response_args['PAYERID'])
415
+				|| isset($response_args['PAYMENTINFO_0_TRANSACTIONID'])
416
+				|| (isset($response_args['PAYMENTSTATUS']) && $response_args['PAYMENTSTATUS'] === 'Completed')
417
+				|| isset($response_args['TOKEN'])
418
+			)
419
+		) {
420
+			// Response status OK, return response parameters for further processing.
421
+			return array('status' => true, 'args' => $response_args);
422
+		} else {
423
+			$errors = $this->_get_errors($response_args);
424
+			return array('status' => false, 'args' => $errors);
425
+		}
428 426
 	}
429 427
 
430 428
 
431 429
 	/**
432
-     *  Log a "Cleared" request.
433
-     *
434
-     * @param array $request
430
+	 *  Log a "Cleared" request.
431
+	 *
432
+	 * @param array $request
435 433
 	 * @param EEI_Payment  $payment
436 434
 	 * @param string  		$info
437 435
 	 * @return void
@@ -454,17 +452,17 @@  discard block
 block discarded – undo
454 452
 		$n = 0;
455 453
 		while ( isset($data_array["L_ERRORCODE{$n}"]) ) {
456 454
 			$l_error_code = isset($data_array["L_ERRORCODE{$n}"])
457
-                ? $data_array["L_ERRORCODE{$n}"]
458
-                : '';
455
+				? $data_array["L_ERRORCODE{$n}"]
456
+				: '';
459 457
 			$l_severity_code = isset($data_array["L_SEVERITYCODE{$n}"])
460
-                ? $data_array["L_SEVERITYCODE{$n}"]
461
-                : '';
458
+				? $data_array["L_SEVERITYCODE{$n}"]
459
+				: '';
462 460
 			$l_short_message = isset($data_array["L_SHORTMESSAGE{$n}"])
463
-                ? $data_array["L_SHORTMESSAGE{$n}"]
464
-                : '';
461
+				? $data_array["L_SHORTMESSAGE{$n}"]
462
+				: '';
465 463
 			$l_long_message = isset($data_array["L_LONGMESSAGE{$n}"])
466
-                ? $data_array["L_LONGMESSAGE{$n}"]
467
-                : '';
464
+				? $data_array["L_LONGMESSAGE{$n}"]
465
+				: '';
468 466
 
469 467
 			if ( $n === 0 ) {
470 468
 				$errors = array(
Please login to merge, or discard this patch.
Spacing   +97 added lines, -97 removed lines patch added patch discarded remove patch
@@ -1,4 +1,4 @@  discard block
 block discarded – undo
1
-<?php if ( ! defined( 'EVENT_ESPRESSO_VERSION' )) { exit('NO direct script access allowed'); }
1
+<?php if ( ! defined('EVENT_ESPRESSO_VERSION')) { exit('NO direct script access allowed'); }
2 2
 
3 3
 /**
4 4
  * ----------------------------------------------
@@ -96,7 +96,7 @@  discard block
 block discarded – undo
96 96
 	 *
97 97
 *@param array $settings_array
98 98
 	 */
99
-	public function set_settings( $settings_array ) {
99
+	public function set_settings($settings_array) {
100 100
 		parent::set_settings($settings_array);
101 101
 		// Redirect URL.
102 102
         $this->_base_gateway_url = $this->_debug_mode
@@ -115,19 +115,19 @@  discard block
 block discarded – undo
115 115
      * @return \EE_Payment|\EEI_Payment
116 116
      * @throws \EE_Error
117 117
      */
118
-	public function set_redirection_info( $payment, $billing_info = array(), $return_url = NULL, $notify_url = NULL, $cancel_url = NULL ) {
119
-		if ( ! $payment instanceof EEI_Payment ) {
120
-			$payment->set_gateway_response( __( 'Error. No associated payment was found.', 'event_espresso' ) );
121
-			$payment->set_status( $this->_pay_model->failed_status() );
118
+	public function set_redirection_info($payment, $billing_info = array(), $return_url = NULL, $notify_url = NULL, $cancel_url = NULL) {
119
+		if ( ! $payment instanceof EEI_Payment) {
120
+			$payment->set_gateway_response(__('Error. No associated payment was found.', 'event_espresso'));
121
+			$payment->set_status($this->_pay_model->failed_status());
122 122
 			return $payment;
123 123
 		}
124 124
 		$transaction = $payment->transaction();
125
-		if ( ! $transaction instanceof EEI_Transaction ) {
126
-			$payment->set_gateway_response( __( 'Could not process this payment because it has no associated transaction.', 'event_espresso' ) );
127
-			$payment->set_status( $this->_pay_model->failed_status() );
125
+		if ( ! $transaction instanceof EEI_Transaction) {
126
+			$payment->set_gateway_response(__('Could not process this payment because it has no associated transaction.', 'event_espresso'));
127
+			$payment->set_status($this->_pay_model->failed_status());
128 128
 			return $payment;
129 129
 		}
130
-		$order_description = substr( $this->_format_order_description($payment), 0, 127 );
130
+		$order_description = substr($this->_format_order_description($payment), 0, 127);
131 131
 		$primary_registration = $transaction->primary_registration();
132 132
 		$primary_attendee = $primary_registration instanceof EE_Registration ? $primary_registration->attendee() : false;
133 133
 		$locale = explode('-', get_bloginfo('language'));
@@ -141,37 +141,37 @@  discard block
 block discarded – undo
141 141
 			'RETURNURL' => $return_url,
142 142
 			'CANCELURL' => $cancel_url,
143 143
 			'PAYMENTREQUEST_0_PAYMENTACTION' => 'Sale',
144
-			'SOLUTIONTYPE' => 'Sole',	// Buyer does not need to create a PayPal account to check out. This is referred to as PayPal Account Optional.
145
-			'BUTTONSOURCE' => 'EventEspresso_SP',//EE will blow up if you change this
144
+			'SOLUTIONTYPE' => 'Sole', // Buyer does not need to create a PayPal account to check out. This is referred to as PayPal Account Optional.
145
+			'BUTTONSOURCE' => 'EventEspresso_SP', //EE will blow up if you change this
146 146
 			'LOCALECODE' => $locale[1]	// Locale of the pages displayed by PayPal during Express Checkout.
147 147
 		);
148 148
 
149 149
 		// Show itemized list.
150
-		if ( $this->_money->compare_floats( $payment->amount(), $transaction->total(), '==' ) ) {
150
+		if ($this->_money->compare_floats($payment->amount(), $transaction->total(), '==')) {
151 151
 			$item_num = 0;
152 152
 			$itemized_sum = 0;
153 153
 			$total_line_items = $transaction->total_line_item();
154 154
 			// Go through each item in the list.
155
-			foreach ( $total_line_items->get_items() as $line_item ) {
156
-				if ( $line_item instanceof EE_Line_Item ) {
155
+			foreach ($total_line_items->get_items() as $line_item) {
156
+				if ($line_item instanceof EE_Line_Item) {
157 157
 					// PayPal doesn't like line items with 0.00 amount, so we may skip those.
158
-					if ( EEH_Money::compare_floats( $line_item->total(), '0.00', '==' ) ) {
158
+					if (EEH_Money::compare_floats($line_item->total(), '0.00', '==')) {
159 159
 						continue;
160 160
 					}
161 161
 
162 162
 					$unit_price = $line_item->unit_price();
163 163
 					$line_item_quantity = $line_item->quantity();
164 164
 					// This is a discount.
165
-					if ( $line_item->is_percent() ) {
165
+					if ($line_item->is_percent()) {
166 166
 						$unit_price = $line_item->total();
167 167
 						$line_item_quantity = 1;
168 168
 					}
169 169
 					// Item Name.
170
-					$token_request_dtls['L_PAYMENTREQUEST_0_NAME'.$item_num] = substr($this->_format_line_item_name( $line_item, $payment), 0, 127);
170
+					$token_request_dtls['L_PAYMENTREQUEST_0_NAME'.$item_num] = substr($this->_format_line_item_name($line_item, $payment), 0, 127);
171 171
 					// Item description.
172
-					$token_request_dtls['L_PAYMENTREQUEST_0_DESC'.$item_num] = substr($this->_format_line_item_desc( $line_item, $payment), 0, 127);
172
+					$token_request_dtls['L_PAYMENTREQUEST_0_DESC'.$item_num] = substr($this->_format_line_item_desc($line_item, $payment), 0, 127);
173 173
 					// Cost of individual item.
174
-					$token_request_dtls['L_PAYMENTREQUEST_0_AMT'.$item_num] = $this->format_currency( $unit_price );
174
+					$token_request_dtls['L_PAYMENTREQUEST_0_AMT'.$item_num] = $this->format_currency($unit_price);
175 175
 					// Item Number.
176 176
 					$token_request_dtls['L_PAYMENTREQUEST_0_NUMBER'.$item_num] = $item_num + 1;
177 177
 					// Item quantity.
@@ -188,16 +188,16 @@  discard block
 block discarded – undo
188 188
 			$token_request_dtls['PAYMENTREQUEST_0_SHIPPINGAMT'] = '0';
189 189
 			$token_request_dtls['PAYMENTREQUEST_0_HANDLINGAMT'] = '0';
190 190
 
191
-			$itemized_sum_diff_from_txn_total = round( $transaction->total() - $itemized_sum - $total_line_items->get_total_tax(), 2 );
191
+			$itemized_sum_diff_from_txn_total = round($transaction->total() - $itemized_sum - $total_line_items->get_total_tax(), 2);
192 192
 			// If we were not able to recognize some item like promotion, surcharge or cancellation,
193 193
 			// add the difference as an extra line item.
194
-			if ( $this->_money->compare_floats( $itemized_sum_diff_from_txn_total, 0, '!=' ) ) {
194
+			if ($this->_money->compare_floats($itemized_sum_diff_from_txn_total, 0, '!=')) {
195 195
 				// Item Name.
196
-				$token_request_dtls['L_PAYMENTREQUEST_0_NAME'.$item_num] = substr( __( 'Other (promotion/surcharge/cancellation)', 'event_espresso' ), 0, 127 );
196
+				$token_request_dtls['L_PAYMENTREQUEST_0_NAME'.$item_num] = substr(__('Other (promotion/surcharge/cancellation)', 'event_espresso'), 0, 127);
197 197
 				// Item description.
198 198
 				$token_request_dtls['L_PAYMENTREQUEST_0_DESC'.$item_num] = '';
199 199
 				// Cost of individual item.
200
-				$token_request_dtls['L_PAYMENTREQUEST_0_AMT'.$item_num] = $this->format_currency( $itemized_sum_diff_from_txn_total );
200
+				$token_request_dtls['L_PAYMENTREQUEST_0_AMT'.$item_num] = $this->format_currency($itemized_sum_diff_from_txn_total);
201 201
 				// Item Number.
202 202
 				$token_request_dtls['L_PAYMENTREQUEST_0_NUMBER'.$item_num] = $item_num + 1;
203 203
 				// Item quantity.
@@ -209,11 +209,11 @@  discard block
 block discarded – undo
209 209
 		} else {
210 210
 			// Just one Item.
211 211
 			// Item Name.
212
-			$token_request_dtls['L_PAYMENTREQUEST_0_NAME0'] = substr( $this->_format_partial_payment_line_item_name($payment), 0, 127 );
212
+			$token_request_dtls['L_PAYMENTREQUEST_0_NAME0'] = substr($this->_format_partial_payment_line_item_name($payment), 0, 127);
213 213
 			// Item description.
214
-			$token_request_dtls['L_PAYMENTREQUEST_0_DESC0'] = substr( $this->_format_partial_payment_line_item_desc($payment), 0, 127 );
214
+			$token_request_dtls['L_PAYMENTREQUEST_0_DESC0'] = substr($this->_format_partial_payment_line_item_desc($payment), 0, 127);
215 215
 			// Cost of individual item.
216
-			$token_request_dtls['L_PAYMENTREQUEST_0_AMT0'] = $this->format_currency( $payment->amount() );
216
+			$token_request_dtls['L_PAYMENTREQUEST_0_AMT0'] = $this->format_currency($payment->amount());
217 217
 			// Item Number.
218 218
 			$token_request_dtls['L_PAYMENTREQUEST_0_NUMBER0'] = 1;
219 219
 			// Item quantity.
@@ -221,14 +221,14 @@  discard block
 block discarded – undo
221 221
 			// Digital item is sold.
222 222
 			$token_request_dtls['L_PAYMENTREQUEST_0_ITEMCATEGORY0'] = 'Physical';
223 223
 			// Item's sales S/H and tax amount.
224
-			$token_request_dtls['PAYMENTREQUEST_0_ITEMAMT'] = $this->format_currency( $payment->amount() );
224
+			$token_request_dtls['PAYMENTREQUEST_0_ITEMAMT'] = $this->format_currency($payment->amount());
225 225
 			$token_request_dtls['PAYMENTREQUEST_0_TAXAMT'] = '0';
226 226
 			$token_request_dtls['PAYMENTREQUEST_0_SHIPPINGAMT'] = '0';
227 227
 			$token_request_dtls['PAYMENTREQUEST_0_HANDLINGAMT'] = '0';
228 228
 		}
229 229
 		// Automatically filling out shipping and contact information.
230
-		if ( $this->_request_shipping_addr && $primary_attendee instanceof EEI_Attendee ) {
231
-			$token_request_dtls['NOSHIPPING'] = '2';	//  If you do not pass the shipping address, PayPal obtains it from the buyer's account profile.
230
+		if ($this->_request_shipping_addr && $primary_attendee instanceof EEI_Attendee) {
231
+			$token_request_dtls['NOSHIPPING'] = '2'; //  If you do not pass the shipping address, PayPal obtains it from the buyer's account profile.
232 232
 			$token_request_dtls['PAYMENTREQUEST_0_SHIPTOSTREET'] = $primary_attendee->address();
233 233
 			$token_request_dtls['PAYMENTREQUEST_0_SHIPTOSTREET2'] = $primary_attendee->address2();
234 234
 			$token_request_dtls['PAYMENTREQUEST_0_SHIPTOCITY'] = $primary_attendee->city();
@@ -237,34 +237,34 @@  discard block
 block discarded – undo
237 237
 			$token_request_dtls['PAYMENTREQUEST_0_SHIPTOZIP'] = $primary_attendee->zip();
238 238
 			$token_request_dtls['PAYMENTREQUEST_0_EMAIL'] = $primary_attendee->email();
239 239
 			$token_request_dtls['PAYMENTREQUEST_0_SHIPTOPHONENUM'] = $primary_attendee->phone();
240
-		} elseif ( ! $this->_request_shipping_addr ) {
240
+		} elseif ( ! $this->_request_shipping_addr) {
241 241
 			// Do not request shipping details on the PP Checkout page.
242 242
 			$token_request_dtls['NOSHIPPING'] = '1';
243 243
 			$token_request_dtls['REQCONFIRMSHIPPING'] = '0';
244 244
 
245 245
 		}
246 246
 		// Used a business/personal logo on the PayPal page.
247
-		if ( ! empty($this->_image_url) ) {
247
+		if ( ! empty($this->_image_url)) {
248 248
 			$token_request_dtls['LOGOIMG'] = $this->_image_url;
249 249
 		}
250 250
 		// Request PayPal token.
251
-		$token_request_response = $this->_ppExpress_request( $token_request_dtls, 'Payment Token', $payment );
252
-		$token_rstatus = $this->_ppExpress_check_response( $token_request_response );
253
-		$response_args = ( isset($token_rstatus['args']) && is_array($token_rstatus['args']) ) ? $token_rstatus['args'] : array();
254
-		if ( $token_rstatus['status'] ) {
251
+		$token_request_response = $this->_ppExpress_request($token_request_dtls, 'Payment Token', $payment);
252
+		$token_rstatus = $this->_ppExpress_check_response($token_request_response);
253
+		$response_args = (isset($token_rstatus['args']) && is_array($token_rstatus['args'])) ? $token_rstatus['args'] : array();
254
+		if ($token_rstatus['status']) {
255 255
 			// We got the Token so we may continue with the payment and redirect the client.
256
-			$payment->set_details( $response_args );
256
+			$payment->set_details($response_args);
257 257
 
258 258
 			$gateway_url = $this->_debug_mode ? 'https://www.sandbox.paypal.com' : 'https://www.paypal.com';
259
-			$payment->set_redirect_url( $gateway_url . '/checkoutnow?useraction=commit&cmd=_express-checkout&token=' . $response_args['TOKEN'] );
259
+			$payment->set_redirect_url($gateway_url.'/checkoutnow?useraction=commit&cmd=_express-checkout&token='.$response_args['TOKEN']);
260 260
 		} else {
261
-			if ( isset($response_args['L_ERRORCODE']) ) {
262
-				$payment->set_gateway_response( $response_args['L_ERRORCODE'] . '; ' . $response_args['L_SHORTMESSAGE'] );
261
+			if (isset($response_args['L_ERRORCODE'])) {
262
+				$payment->set_gateway_response($response_args['L_ERRORCODE'].'; '.$response_args['L_SHORTMESSAGE']);
263 263
 			} else {
264
-				$payment->set_gateway_response( __( 'Error occurred while trying to setup the Express Checkout.', 'event_espresso' ) );
264
+				$payment->set_gateway_response(__('Error occurred while trying to setup the Express Checkout.', 'event_espresso'));
265 265
 			}
266
-			$payment->set_details( $response_args );
267
-			$payment->set_status( $this->_pay_model->failed_status() );
266
+			$payment->set_details($response_args);
267
+			$payment->set_status($this->_pay_model->failed_status());
268 268
 		}
269 269
 
270 270
 		return $payment;
@@ -280,22 +280,22 @@  discard block
 block discarded – undo
280 280
 	 *  @param EEI_Transaction $transaction
281 281
 	 *  @return EEI_Payment
282 282
 	 */
283
-	public function handle_payment_update( $update_info, $transaction ) {
283
+	public function handle_payment_update($update_info, $transaction) {
284 284
 		$payment = $transaction instanceof EEI_Transaction ? $transaction->last_payment() : null;
285 285
 
286
-		if ( $payment instanceof EEI_Payment ) {
287
-			$this->log( array( 'Return from Authorization' => $update_info ), $payment );
286
+		if ($payment instanceof EEI_Payment) {
287
+			$this->log(array('Return from Authorization' => $update_info), $payment);
288 288
 			$transaction = $payment->transaction();
289
-			if ( ! $transaction instanceof EEI_Transaction ) {
290
-				$payment->set_gateway_response( __( 'Could not process this payment because it has no associated transaction.', 'event_espresso' ) );
291
-				$payment->set_status( $this->_pay_model->failed_status() );
289
+			if ( ! $transaction instanceof EEI_Transaction) {
290
+				$payment->set_gateway_response(__('Could not process this payment because it has no associated transaction.', 'event_espresso'));
291
+				$payment->set_status($this->_pay_model->failed_status());
292 292
 				return $payment;
293 293
 			}
294 294
 			$primary_registrant = $transaction->primary_registration();
295 295
             $payment_details = $payment->details();
296 296
             // Check if we still have the token.
297
-			if ( ! isset($payment_details['TOKEN']) || empty($payment_details['TOKEN']) ) {
298
-				$payment->set_status( $this->_pay_model->failed_status() );
297
+			if ( ! isset($payment_details['TOKEN']) || empty($payment_details['TOKEN'])) {
298
+				$payment->set_status($this->_pay_model->failed_status());
299 299
 				return $payment;
300 300
 			}
301 301
 
@@ -304,10 +304,10 @@  discard block
 block discarded – undo
304 304
 				'TOKEN' => $payment_details['TOKEN']
305 305
 			);
306 306
 			// Request Customer Details.
307
-			$cdetails_request_response = $this->_ppExpress_request( $cdetails_request_dtls, 'Customer Details', $payment );
308
-			$cdetails_rstatus = $this->_ppExpress_check_response( $cdetails_request_response );
309
-			$cdata_response_args = ( isset($cdetails_rstatus['args']) && is_array($cdetails_rstatus['args']) ) ? $cdetails_rstatus['args'] : array();
310
-			if ( $cdetails_rstatus['status'] ) {
307
+			$cdetails_request_response = $this->_ppExpress_request($cdetails_request_dtls, 'Customer Details', $payment);
308
+			$cdetails_rstatus = $this->_ppExpress_check_response($cdetails_request_response);
309
+			$cdata_response_args = (isset($cdetails_rstatus['args']) && is_array($cdetails_rstatus['args'])) ? $cdetails_rstatus['args'] : array();
310
+			if ($cdetails_rstatus['status']) {
311 311
 				// We got the PayerID so now we can Complete the transaction.
312 312
 				$docheckout_request_dtls = array(
313 313
 					'METHOD' => 'DoExpressCheckoutPayment',
@@ -318,39 +318,39 @@  discard block
 block discarded – undo
318 318
 					'PAYMENTREQUEST_0_CURRENCYCODE' => $payment->currency_code()
319 319
 				);
320 320
 				// Payment Checkout/Capture.
321
-				$docheckout_request_response = $this->_ppExpress_request( $docheckout_request_dtls, 'Do Payment', $payment );
322
-				$docheckout_rstatus = $this->_ppExpress_check_response( $docheckout_request_response );
323
-				$docheckout_response_args = ( isset($docheckout_rstatus['args']) && is_array($docheckout_rstatus['args']) ) ? $docheckout_rstatus['args'] : array();
324
-				if ( $docheckout_rstatus['status'] ) {
321
+				$docheckout_request_response = $this->_ppExpress_request($docheckout_request_dtls, 'Do Payment', $payment);
322
+				$docheckout_rstatus = $this->_ppExpress_check_response($docheckout_request_response);
323
+				$docheckout_response_args = (isset($docheckout_rstatus['args']) && is_array($docheckout_rstatus['args'])) ? $docheckout_rstatus['args'] : array();
324
+				if ($docheckout_rstatus['status']) {
325 325
 					// All is well, payment approved.
326 326
 					$primary_registration_code = $primary_registrant instanceof EE_Registration ? $primary_registrant->reg_code() : '';
327
-					$payment->set_extra_accntng( $primary_registration_code );
328
-					$payment->set_amount( isset($docheckout_response_args['PAYMENTINFO_0_AMT']) ? (float) $docheckout_response_args['PAYMENTINFO_0_AMT'] : 0 );
329
-					$payment->set_txn_id_chq_nmbr( isset( $docheckout_response_args['PAYMENTINFO_0_TRANSACTIONID'] ) ? $docheckout_response_args['PAYMENTINFO_0_TRANSACTIONID'] : null );
330
-					$payment->set_details( $cdata_response_args );
331
-					$payment->set_gateway_response( isset( $docheckout_response_args['PAYMENTINFO_0_ACK'] ) ? $docheckout_response_args['PAYMENTINFO_0_ACK'] : '' );
332
-					$payment->set_status( $this->_pay_model->approved_status() );
327
+					$payment->set_extra_accntng($primary_registration_code);
328
+					$payment->set_amount(isset($docheckout_response_args['PAYMENTINFO_0_AMT']) ? (float) $docheckout_response_args['PAYMENTINFO_0_AMT'] : 0);
329
+					$payment->set_txn_id_chq_nmbr(isset($docheckout_response_args['PAYMENTINFO_0_TRANSACTIONID']) ? $docheckout_response_args['PAYMENTINFO_0_TRANSACTIONID'] : null);
330
+					$payment->set_details($cdata_response_args);
331
+					$payment->set_gateway_response(isset($docheckout_response_args['PAYMENTINFO_0_ACK']) ? $docheckout_response_args['PAYMENTINFO_0_ACK'] : '');
332
+					$payment->set_status($this->_pay_model->approved_status());
333 333
 				} else {
334
-					if ( isset($docheckout_response_args['L_ERRORCODE']) ) {
335
-						$payment->set_gateway_response( $docheckout_response_args['L_ERRORCODE'] . '; ' . $docheckout_response_args['L_SHORTMESSAGE'] );
334
+					if (isset($docheckout_response_args['L_ERRORCODE'])) {
335
+						$payment->set_gateway_response($docheckout_response_args['L_ERRORCODE'].'; '.$docheckout_response_args['L_SHORTMESSAGE']);
336 336
 					} else {
337
-						$payment->set_gateway_response( __( 'Error occurred while trying to Capture the funds.', 'event_espresso' ) );
337
+						$payment->set_gateway_response(__('Error occurred while trying to Capture the funds.', 'event_espresso'));
338 338
 					}
339
-					$payment->set_details( $docheckout_response_args );
340
-					$payment->set_status( $this->_pay_model->declined_status() );
339
+					$payment->set_details($docheckout_response_args);
340
+					$payment->set_status($this->_pay_model->declined_status());
341 341
 				}
342 342
 			} else {
343
-				if ( isset($cdata_response_args['L_ERRORCODE']) ) {
344
-					$payment->set_gateway_response( $cdata_response_args['L_ERRORCODE'] . '; ' . $cdata_response_args['L_SHORTMESSAGE'] );
343
+				if (isset($cdata_response_args['L_ERRORCODE'])) {
344
+					$payment->set_gateway_response($cdata_response_args['L_ERRORCODE'].'; '.$cdata_response_args['L_SHORTMESSAGE']);
345 345
 				} else {
346
-					$payment->set_gateway_response( __( 'Error occurred while trying to get payment Details from PayPal.', 'event_espresso' ) );
346
+					$payment->set_gateway_response(__('Error occurred while trying to get payment Details from PayPal.', 'event_espresso'));
347 347
 				}
348
-				$payment->set_details( $cdata_response_args );
349
-				$payment->set_status( $this->_pay_model->failed_status() );
348
+				$payment->set_details($cdata_response_args);
349
+				$payment->set_status($this->_pay_model->failed_status());
350 350
 			}
351 351
 		} else {
352
-			$payment->set_gateway_response( __( 'Error occurred while trying to process the payment.', 'event_espresso' ) );
353
-			$payment->set_status( $this->_pay_model->failed_status() );
352
+			$payment->set_gateway_response(__('Error occurred while trying to process the payment.', 'event_espresso'));
353
+			$payment->set_status($this->_pay_model->failed_status());
354 354
 		}
355 355
 
356 356
 		return $payment;
@@ -365,16 +365,16 @@  discard block
 block discarded – undo
365 365
 	 *  @param EEI_Payment  $payment
366 366
 	 *	@return mixed
367 367
 	 */
368
-	public function _ppExpress_request( $request_params, $request_text, $payment ) {
368
+	public function _ppExpress_request($request_params, $request_text, $payment) {
369 369
 		$request_dtls = array(
370 370
 			'VERSION' => '204.0',
371
-			'USER' => urlencode( $this->_api_username ),
372
-			'PWD' => urlencode( $this->_api_password ),
373
-			'SIGNATURE' => urlencode( $this->_api_signature )
371
+			'USER' => urlencode($this->_api_username),
372
+			'PWD' => urlencode($this->_api_password),
373
+			'SIGNATURE' => urlencode($this->_api_signature)
374 374
 		);
375
-		$dtls = array_merge( $request_dtls, $request_params );
375
+		$dtls = array_merge($request_dtls, $request_params);
376 376
 
377
-		$this->_log_clean_request( $dtls, $payment, $request_text . ' Request' );
377
+		$this->_log_clean_request($dtls, $payment, $request_text.' Request');
378 378
 		// Request Customer Details.
379 379
 		$request_response = wp_remote_post(
380 380
 			$this->_base_gateway_url,
@@ -384,11 +384,11 @@  discard block
 block discarded – undo
384 384
 				'httpversion' => '1.1',
385 385
 				'cookies' => array(),
386 386
 				'headers' => array(),
387
-				'body' => http_build_query( $dtls )
387
+				'body' => http_build_query($dtls)
388 388
 			)
389 389
 		);
390 390
 		// Log the response.
391
-		$this->log( array( $request_text . ' Response' => $request_response), $payment );
391
+		$this->log(array($request_text.' Response' => $request_response), $payment);
392 392
 
393 393
 		return $request_response;
394 394
 	}
@@ -400,13 +400,13 @@  discard block
 block discarded – undo
400 400
 	 *	@param mixed        $request_response
401 401
 	 *	@return array
402 402
 	 */
403
-	public function _ppExpress_check_response( $request_response ) {
404
-		if (empty($request_response['body']) || is_wp_error( $request_response ) ) {
403
+	public function _ppExpress_check_response($request_response) {
404
+		if (empty($request_response['body']) || is_wp_error($request_response)) {
405 405
             // If we got here then there was an error in this request.
406 406
             return array('status' => false, 'args' => $request_response);
407 407
         }
408 408
         $response_args = array();
409
-        parse_str( urldecode($request_response['body']), $response_args );
409
+        parse_str(urldecode($request_response['body']), $response_args);
410 410
         if ( ! isset($response_args['ACK'])) {
411 411
             return array('status' => false, 'args' => $request_response);
412 412
         }
@@ -436,10 +436,10 @@  discard block
 block discarded – undo
436 436
 	 * @param string  		$info
437 437
 	 * @return void
438 438
 	 */
439
-	private function _log_clean_request($request, $payment, $info ) {
439
+	private function _log_clean_request($request, $payment, $info) {
440 440
 		$cleaned_request_data = $request;
441 441
 		unset($cleaned_request_data['PWD'], $cleaned_request_data['USER'], $cleaned_request_data['SIGNATURE']);
442
-		$this->log( array($info => $cleaned_request_data), $payment );
442
+		$this->log(array($info => $cleaned_request_data), $payment);
443 443
 	}
444 444
 
445 445
 
@@ -449,10 +449,10 @@  discard block
 block discarded – undo
449 449
 	 *  @param array	$data_array
450 450
 	 *  @return array
451 451
 	 */
452
-	private function _get_errors( $data_array ) {
452
+	private function _get_errors($data_array) {
453 453
 		$errors = array();
454 454
 		$n = 0;
455
-		while ( isset($data_array["L_ERRORCODE{$n}"]) ) {
455
+		while (isset($data_array["L_ERRORCODE{$n}"])) {
456 456
 			$l_error_code = isset($data_array["L_ERRORCODE{$n}"])
457 457
                 ? $data_array["L_ERRORCODE{$n}"]
458 458
                 : '';
@@ -466,7 +466,7 @@  discard block
 block discarded – undo
466 466
                 ? $data_array["L_LONGMESSAGE{$n}"]
467 467
                 : '';
468 468
 
469
-			if ( $n === 0 ) {
469
+			if ($n === 0) {
470 470
 				$errors = array(
471 471
 					'L_ERRORCODE' => $l_error_code,
472 472
 					'L_SHORTMESSAGE' => $l_short_message,
@@ -474,10 +474,10 @@  discard block
 block discarded – undo
474 474
 					'L_SEVERITYCODE' => $l_severity_code
475 475
 				);
476 476
 			} else {
477
-				$errors['L_ERRORCODE'] .= ', ' . $l_error_code;
478
-				$errors['L_SHORTMESSAGE'] .= ', ' . $l_short_message;
479
-				$errors['L_LONGMESSAGE'] .= ', ' . $l_long_message;
480
-				$errors['L_SEVERITYCODE'] .= ', ' . $l_severity_code;
477
+				$errors['L_ERRORCODE'] .= ', '.$l_error_code;
478
+				$errors['L_SHORTMESSAGE'] .= ', '.$l_short_message;
479
+				$errors['L_LONGMESSAGE'] .= ', '.$l_long_message;
480
+				$errors['L_SEVERITYCODE'] .= ', '.$l_severity_code;
481 481
 			}
482 482
 
483 483
 			$n++;
Please login to merge, or discard this patch.
modules/single_page_checkout/EED_Single_Page_Checkout.module.php 1 patch
Indentation   +1692 added lines, -1692 removed lines patch added patch discarded remove patch
@@ -2,7 +2,7 @@  discard block
 block discarded – undo
2 2
 use EventEspresso\core\exceptions\InvalidEntityException;
3 3
 
4 4
 if ( ! defined('EVENT_ESPRESSO_VERSION')) {
5
-    exit('No direct script access allowed');
5
+	exit('No direct script access allowed');
6 6
 }
7 7
 
8 8
 
@@ -17,1697 +17,1697 @@  discard block
 block discarded – undo
17 17
 class EED_Single_Page_Checkout extends EED_Module
18 18
 {
19 19
 
20
-    /**
21
-     * $_initialized - has the SPCO controller already been initialized ?
22
-     *
23
-     * @access private
24
-     * @var bool $_initialized
25
-     */
26
-    private static $_initialized = false;
27
-
28
-
29
-    /**
30
-     * $_checkout_verified - is the EE_Checkout verified as correct for this request ?
31
-     *
32
-     * @access private
33
-     * @var bool $_valid_checkout
34
-     */
35
-    private static $_checkout_verified = true;
36
-
37
-    /**
38
-     *    $_reg_steps_array - holds initial array of reg steps
39
-     *
40
-     * @access private
41
-     * @var array $_reg_steps_array
42
-     */
43
-    private static $_reg_steps_array = array();
44
-
45
-    /**
46
-     *    $checkout - EE_Checkout object for handling the properties of the current checkout process
47
-     *
48
-     * @access public
49
-     * @var EE_Checkout $checkout
50
-     */
51
-    public $checkout;
52
-
53
-
54
-
55
-    /**
56
-     * @return EED_Single_Page_Checkout
57
-     */
58
-    public static function instance()
59
-    {
60
-        add_filter('EED_Single_Page_Checkout__SPCO_active', '__return_true');
61
-        return parent::get_instance(__CLASS__);
62
-    }
63
-
64
-
65
-
66
-    /**
67
-     * @return EE_CART
68
-     */
69
-    public function cart()
70
-    {
71
-        return $this->checkout->cart;
72
-    }
73
-
74
-
75
-
76
-    /**
77
-     * @return EE_Transaction
78
-     */
79
-    public function transaction()
80
-    {
81
-        return $this->checkout->transaction;
82
-    }
83
-
84
-
85
-
86
-    /**
87
-     *    set_hooks - for hooking into EE Core, other modules, etc
88
-     *
89
-     * @access    public
90
-     * @return    void
91
-     * @throws \EE_Error
92
-     */
93
-    public static function set_hooks()
94
-    {
95
-        EED_Single_Page_Checkout::set_definitions();
96
-    }
97
-
98
-
99
-
100
-    /**
101
-     *    set_hooks_admin - for hooking into EE Admin Core, other modules, etc
102
-     *
103
-     * @access    public
104
-     * @return    void
105
-     * @throws \EE_Error
106
-     */
107
-    public static function set_hooks_admin()
108
-    {
109
-        EED_Single_Page_Checkout::set_definitions();
110
-        if ( ! (defined('DOING_AJAX') && DOING_AJAX)) {
111
-            // hook into the top of pre_get_posts to set the reg step routing, which gives other modules or plugins a chance to modify the reg steps, but just before the routes get called
112
-            add_action('pre_get_posts', array('EED_Single_Page_Checkout', 'load_reg_steps'), 1);
113
-            return;
114
-        }
115
-        // going to start an output buffer in case anything gets accidentally output that might disrupt our JSON response
116
-        ob_start();
117
-        EED_Single_Page_Checkout::load_request_handler();
118
-        EED_Single_Page_Checkout::load_reg_steps();
119
-        // set ajax hooks
120
-        add_action('wp_ajax_process_reg_step', array('EED_Single_Page_Checkout', 'process_reg_step'));
121
-        add_action('wp_ajax_nopriv_process_reg_step', array('EED_Single_Page_Checkout', 'process_reg_step'));
122
-        add_action('wp_ajax_display_spco_reg_step', array('EED_Single_Page_Checkout', 'display_reg_step'));
123
-        add_action('wp_ajax_nopriv_display_spco_reg_step', array('EED_Single_Page_Checkout', 'display_reg_step'));
124
-        add_action('wp_ajax_update_reg_step', array('EED_Single_Page_Checkout', 'update_reg_step'));
125
-        add_action('wp_ajax_nopriv_update_reg_step', array('EED_Single_Page_Checkout', 'update_reg_step'));
126
-    }
127
-
128
-
129
-
130
-    /**
131
-     *    process ajax request
132
-     *
133
-     * @param string $ajax_action
134
-     * @throws \EE_Error
135
-     */
136
-    public static function process_ajax_request($ajax_action)
137
-    {
138
-        EE_Registry::instance()->REQ->set('action', $ajax_action);
139
-        EED_Single_Page_Checkout::instance()->_initialize();
140
-    }
141
-
142
-
143
-
144
-    /**
145
-     *    ajax display registration step
146
-     *
147
-     * @throws \EE_Error
148
-     */
149
-    public static function display_reg_step()
150
-    {
151
-        EED_Single_Page_Checkout::process_ajax_request('display_spco_reg_step');
152
-    }
153
-
154
-
155
-
156
-    /**
157
-     *    ajax process registration step
158
-     *
159
-     * @throws \EE_Error
160
-     */
161
-    public static function process_reg_step()
162
-    {
163
-        EED_Single_Page_Checkout::process_ajax_request('process_reg_step');
164
-    }
165
-
166
-
167
-
168
-    /**
169
-     *    ajax process registration step
170
-     *
171
-     * @throws \EE_Error
172
-     */
173
-    public static function update_reg_step()
174
-    {
175
-        EED_Single_Page_Checkout::process_ajax_request('update_reg_step');
176
-    }
177
-
178
-
179
-
180
-    /**
181
-     *   update_checkout
182
-     *
183
-     * @access public
184
-     * @return void
185
-     * @throws \EE_Error
186
-     */
187
-    public static function update_checkout()
188
-    {
189
-        EED_Single_Page_Checkout::process_ajax_request('update_checkout');
190
-    }
191
-
192
-
193
-
194
-    /**
195
-     *    load_request_handler
196
-     *
197
-     * @access    public
198
-     * @return    void
199
-     */
200
-    public static function load_request_handler()
201
-    {
202
-        // load core Request_Handler class
203
-        if ( ! isset(EE_Registry::instance()->REQ)) {
204
-            EE_Registry::instance()->load_core('Request_Handler');
205
-        }
206
-    }
207
-
208
-
209
-
210
-    /**
211
-     *    set_definitions
212
-     *
213
-     * @access    public
214
-     * @return    void
215
-     * @throws \EE_Error
216
-     */
217
-    public static function set_definitions()
218
-    {
219
-        define('SPCO_BASE_PATH', rtrim(str_replace(array('\\', '/'), DS, plugin_dir_path(__FILE__)), DS) . DS);
220
-        define('SPCO_CSS_URL', plugin_dir_url(__FILE__) . 'css' . DS);
221
-        define('SPCO_IMG_URL', plugin_dir_url(__FILE__) . 'img' . DS);
222
-        define('SPCO_JS_URL', plugin_dir_url(__FILE__) . 'js' . DS);
223
-        define('SPCO_INC_PATH', SPCO_BASE_PATH . 'inc' . DS);
224
-        define('SPCO_REG_STEPS_PATH', SPCO_BASE_PATH . 'reg_steps' . DS);
225
-        define('SPCO_TEMPLATES_PATH', SPCO_BASE_PATH . 'templates' . DS);
226
-        EEH_Autoloader::register_autoloaders_for_each_file_in_folder(SPCO_BASE_PATH, true);
227
-        EE_Registry::$i18n_js_strings['registration_expiration_notice'] = sprintf(
228
-            __('%1$sWe\'re sorry, but you\'re registration time has expired.%2$s%4$sIf you still wish to complete your registration, please return to the %5$sEvent List%6$sEvent List%7$s and reselect your tickets if available. Please except our apologies for any inconvenience this may have caused.%8$s',
229
-                'event_espresso'),
230
-            '<h4 class="important-notice">',
231
-            '</h4>',
232
-            '<br />',
233
-            '<p>',
234
-            '<a href="' . get_post_type_archive_link('espresso_events') . '" title="',
235
-            '">',
236
-            '</a>',
237
-            '</p>'
238
-        );
239
-    }
240
-
241
-
242
-
243
-    /**
244
-     * load_reg_steps
245
-     * loads and instantiates each reg step based on the EE_Registry::instance()->CFG->registration->reg_steps array
246
-     *
247
-     * @access    private
248
-     * @throws EE_Error
249
-     * @return void
250
-     */
251
-    public static function load_reg_steps()
252
-    {
253
-        static $reg_steps_loaded = false;
254
-        if ($reg_steps_loaded) {
255
-            return;
256
-        }
257
-        // filter list of reg_steps
258
-        $reg_steps_to_load = (array)apply_filters(
259
-            'AHEE__SPCO__load_reg_steps__reg_steps_to_load',
260
-            EED_Single_Page_Checkout::get_reg_steps()
261
-        );
262
-        // sort by key (order)
263
-        ksort($reg_steps_to_load);
264
-        // loop through folders
265
-        foreach ($reg_steps_to_load as $order => $reg_step) {
266
-            // we need a
267
-            if (isset($reg_step['file_path'], $reg_step['class_name'], $reg_step['slug'])) {
268
-                // copy over to the reg_steps_array
269
-                EED_Single_Page_Checkout::$_reg_steps_array[$order] = $reg_step;
270
-                // register custom key route for each reg step
271
-                // ie: step=>"slug" - this is the entire reason we load the reg steps array now
272
-                EE_Config::register_route($reg_step['slug'], 'EED_Single_Page_Checkout', 'run', 'step');
273
-                // add AJAX or other hooks
274
-                if (isset($reg_step['has_hooks']) && $reg_step['has_hooks']) {
275
-                    // setup autoloaders if necessary
276
-                    if ( ! class_exists($reg_step['class_name'])) {
277
-                        EEH_Autoloader::register_autoloaders_for_each_file_in_folder($reg_step['file_path'], true);
278
-                    }
279
-                    if (is_callable($reg_step['class_name'], 'set_hooks')) {
280
-                        call_user_func(array($reg_step['class_name'], 'set_hooks'));
281
-                    }
282
-                }
283
-            }
284
-        }
285
-        $reg_steps_loaded = true;
286
-    }
287
-
288
-
289
-
290
-    /**
291
-     *    get_reg_steps
292
-     *
293
-     * @access    public
294
-     * @return    array
295
-     */
296
-    public static function get_reg_steps()
297
-    {
298
-        $reg_steps = EE_Registry::instance()->CFG->registration->reg_steps;
299
-        if (empty($reg_steps)) {
300
-            $reg_steps = array(
301
-                10  => array(
302
-                    'file_path'  => SPCO_REG_STEPS_PATH . 'attendee_information',
303
-                    'class_name' => 'EE_SPCO_Reg_Step_Attendee_Information',
304
-                    'slug'       => 'attendee_information',
305
-                    'has_hooks'  => false,
306
-                ),
307
-                20  => array(
308
-                    'file_path'  => SPCO_REG_STEPS_PATH . 'registration_confirmation',
309
-                    'class_name' => 'EE_SPCO_Reg_Step_Registration_Confirmation',
310
-                    'slug'       => 'registration_confirmation',
311
-                    'has_hooks'  => false,
312
-                ),
313
-                30  => array(
314
-                    'file_path'  => SPCO_REG_STEPS_PATH . 'payment_options',
315
-                    'class_name' => 'EE_SPCO_Reg_Step_Payment_Options',
316
-                    'slug'       => 'payment_options',
317
-                    'has_hooks'  => true,
318
-                ),
319
-                999 => array(
320
-                    'file_path'  => SPCO_REG_STEPS_PATH . 'finalize_registration',
321
-                    'class_name' => 'EE_SPCO_Reg_Step_Finalize_Registration',
322
-                    'slug'       => 'finalize_registration',
323
-                    'has_hooks'  => false,
324
-                ),
325
-            );
326
-        }
327
-        return $reg_steps;
328
-    }
329
-
330
-
331
-
332
-    /**
333
-     *    registration_checkout_for_admin
334
-     *
335
-     * @access    public
336
-     * @return    string
337
-     * @throws \EE_Error
338
-     */
339
-    public static function registration_checkout_for_admin()
340
-    {
341
-        EED_Single_Page_Checkout::load_reg_steps();
342
-        EE_Registry::instance()->REQ->set('step', 'attendee_information');
343
-        EE_Registry::instance()->REQ->set('action', 'display_spco_reg_step');
344
-        EE_Registry::instance()->REQ->set('process_form_submission', false);
345
-        EED_Single_Page_Checkout::instance()->_initialize();
346
-        EED_Single_Page_Checkout::instance()->_display_spco_reg_form();
347
-        return EE_Registry::instance()->REQ->get_output();
348
-    }
349
-
350
-
351
-
352
-    /**
353
-     * process_registration_from_admin
354
-     *
355
-     * @access public
356
-     * @return \EE_Transaction
357
-     * @throws \EE_Error
358
-     */
359
-    public static function process_registration_from_admin()
360
-    {
361
-        EED_Single_Page_Checkout::load_reg_steps();
362
-        EE_Registry::instance()->REQ->set('step', 'attendee_information');
363
-        EE_Registry::instance()->REQ->set('action', 'process_reg_step');
364
-        EE_Registry::instance()->REQ->set('process_form_submission', true);
365
-        EED_Single_Page_Checkout::instance()->_initialize();
366
-        if (EED_Single_Page_Checkout::instance()->checkout->current_step->completed()) {
367
-            $final_reg_step = end(EED_Single_Page_Checkout::instance()->checkout->reg_steps);
368
-            if ($final_reg_step instanceof EE_SPCO_Reg_Step_Finalize_Registration) {
369
-                EED_Single_Page_Checkout::instance()->checkout->set_reg_step_initiated($final_reg_step);
370
-                if ($final_reg_step->process_reg_step()) {
371
-                    $final_reg_step->set_completed();
372
-                    EED_Single_Page_Checkout::instance()->checkout->update_txn_reg_steps_array();
373
-                    return EED_Single_Page_Checkout::instance()->checkout->transaction;
374
-                }
375
-            }
376
-        }
377
-        return null;
378
-    }
379
-
380
-
381
-
382
-    /**
383
-     *    run
384
-     *
385
-     * @access    public
386
-     * @param WP_Query $WP_Query
387
-     * @return    void
388
-     * @throws \EE_Error
389
-     */
390
-    public function run($WP_Query)
391
-    {
392
-        if (
393
-            $WP_Query instanceof WP_Query
394
-            && $WP_Query->is_main_query()
395
-            && apply_filters('FHEE__EED_Single_Page_Checkout__run', true)
396
-            && $this->_is_reg_checkout()
397
-        ) {
398
-            $this->_initialize();
399
-        }
400
-    }
401
-
402
-
403
-
404
-    /**
405
-     * determines whether current url matches reg page url
406
-     *
407
-     * @return bool
408
-     */
409
-    protected function _is_reg_checkout()
410
-    {
411
-        // get current permalink for reg page without any extra query args
412
-        $reg_page_url = \get_permalink(EE_Config::instance()->core->reg_page_id);
413
-        // get request URI for current request, but without the scheme or host
414
-        $current_request_uri = \EEH_URL::filter_input_server_url('REQUEST_URI');
415
-        $current_request_uri = html_entity_decode($current_request_uri);
416
-        // get array of query args from the current request URI
417
-        $query_args = \EEH_URL::get_query_string($current_request_uri);
418
-        // grab page id if it is set
419
-        $page_id = isset($query_args['page_id']) ? absint($query_args['page_id']) : 0;
420
-        // and remove the page id from the query args (we will re-add it later)
421
-        unset($query_args['page_id']);
422
-        // now strip all query args from current request URI
423
-        $current_request_uri = remove_query_arg(array_flip($query_args), $current_request_uri);
424
-        // and re-add the page id if it was set
425
-        if ($page_id) {
426
-            $current_request_uri = add_query_arg('page_id', $page_id, $current_request_uri);
427
-        }
428
-        // remove slashes and ?
429
-        $current_request_uri = trim($current_request_uri, '?/');
430
-        // is current request URI part of the known full reg page URL ?
431
-        return ! empty($current_request_uri) && strpos($reg_page_url, $current_request_uri) !== false;
432
-    }
433
-
434
-
435
-
436
-    /**
437
-     *    run
438
-     *
439
-     * @access    public
440
-     * @param WP_Query $WP_Query
441
-     * @return    void
442
-     * @throws \EE_Error
443
-     */
444
-    public static function init($WP_Query)
445
-    {
446
-        EED_Single_Page_Checkout::instance()->run($WP_Query);
447
-    }
448
-
449
-
450
-
451
-    /**
452
-     *    _initialize - initial module setup
453
-     *
454
-     * @access    private
455
-     * @throws EE_Error
456
-     * @return    void
457
-     */
458
-    private function _initialize()
459
-    {
460
-        // ensure SPCO doesn't run twice
461
-        if (EED_Single_Page_Checkout::$_initialized) {
462
-            return;
463
-        }
464
-        try {
465
-            $this->_verify_session();
466
-            // setup the EE_Checkout object
467
-            $this->checkout = $this->_initialize_checkout();
468
-            // filter checkout
469
-            $this->checkout = apply_filters('FHEE__EED_Single_Page_Checkout___initialize__checkout', $this->checkout);
470
-            // get the $_GET
471
-            $this->_get_request_vars();
472
-            if ($this->_block_bots()) {
473
-                return;
474
-            }
475
-            // filter continue_reg
476
-            $this->checkout->continue_reg = apply_filters('FHEE__EED_Single_Page_Checkout__init___continue_reg', true, $this->checkout);
477
-            // load the reg steps array
478
-            if ( ! $this->_load_and_instantiate_reg_steps()) {
479
-                EED_Single_Page_Checkout::$_initialized = true;
480
-                return;
481
-            }
482
-            // set the current step
483
-            $this->checkout->set_current_step($this->checkout->step);
484
-            // and the next step
485
-            $this->checkout->set_next_step();
486
-            // verify that everything has been setup correctly
487
-            if ( ! ($this->_verify_transaction_and_get_registrations() && $this->_final_verifications())) {
488
-                EED_Single_Page_Checkout::$_initialized = true;
489
-                return;
490
-            }
491
-            // lock the transaction
492
-            $this->checkout->transaction->lock();
493
-            // make sure all of our cached objects are added to their respective model entity mappers
494
-            $this->checkout->refresh_all_entities();
495
-            // set amount owing
496
-            $this->checkout->amount_owing = $this->checkout->transaction->remaining();
497
-            // initialize each reg step, which gives them the chance to potentially alter the process
498
-            $this->_initialize_reg_steps();
499
-            // DEBUG LOG
500
-            //$this->checkout->log( __CLASS__, __FUNCTION__, __LINE__ );
501
-            // get reg form
502
-            if( ! $this->_check_form_submission()) {
503
-                EED_Single_Page_Checkout::$_initialized = true;
504
-                return;
505
-            }
506
-            // checkout the action!!!
507
-            $this->_process_form_action();
508
-            // add some style and make it dance
509
-            $this->add_styles_and_scripts();
510
-            // kk... SPCO has successfully run
511
-            EED_Single_Page_Checkout::$_initialized = true;
512
-            // set no cache headers and constants
513
-            EE_System::do_not_cache();
514
-            // add anchor
515
-            add_action('loop_start', array($this, 'set_checkout_anchor'), 1);
516
-            // remove transaction lock
517
-            add_action('shutdown', array($this, 'unlock_transaction'), 1);
518
-        } catch (Exception $e) {
519
-            EE_Error::add_error($e->getMessage(), __FILE__, __FUNCTION__, __LINE__);
520
-        }
521
-    }
522
-
523
-
524
-
525
-    /**
526
-     *    _verify_session
527
-     * checks that the session is valid and not expired
528
-     *
529
-     * @access    private
530
-     * @throws EE_Error
531
-     */
532
-    private function _verify_session()
533
-    {
534
-        if ( ! EE_Registry::instance()->SSN instanceof EE_Session) {
535
-            throw new EE_Error(__('The EE_Session class could not be loaded.', 'event_espresso'));
536
-        }
537
-        // is session still valid ?
538
-        if (EE_Registry::instance()->SSN->expired() && EE_Registry::instance()->REQ->get('e_reg_url_link', '') === '') {
539
-            $this->checkout = new EE_Checkout();
540
-            EE_Registry::instance()->SSN->reset_cart();
541
-            EE_Registry::instance()->SSN->reset_checkout();
542
-            EE_Registry::instance()->SSN->reset_transaction();
543
-            EE_Error::add_attention(EE_Registry::$i18n_js_strings['registration_expiration_notice'], __FILE__,
544
-                __FUNCTION__, __LINE__);
545
-            EE_Registry::instance()->SSN->reset_expired();
546
-        }
547
-    }
548
-
549
-
550
-
551
-    /**
552
-     *    _initialize_checkout
553
-     * loads and instantiates EE_Checkout
554
-     *
555
-     * @access    private
556
-     * @throws EE_Error
557
-     * @return EE_Checkout
558
-     */
559
-    private function _initialize_checkout()
560
-    {
561
-        // look in session for existing checkout
562
-        /** @type EE_Checkout $checkout */
563
-        $checkout = EE_Registry::instance()->SSN->checkout();
564
-        // verify
565
-        if ( ! $checkout instanceof EE_Checkout) {
566
-            // instantiate EE_Checkout object for handling the properties of the current checkout process
567
-            $checkout = EE_Registry::instance()->load_file(SPCO_INC_PATH, 'EE_Checkout', 'class', array(), false);
568
-        } else {
569
-            if ($checkout->current_step->is_final_step() && $checkout->exit_spco() === true) {
570
-                $this->unlock_transaction();
571
-                wp_safe_redirect($checkout->redirect_url);
572
-                exit();
573
-            }
574
-        }
575
-        $checkout = apply_filters('FHEE__EED_Single_Page_Checkout___initialize_checkout__checkout', $checkout);
576
-        // verify again
577
-        if ( ! $checkout instanceof EE_Checkout) {
578
-            throw new EE_Error(__('The EE_Checkout class could not be loaded.', 'event_espresso'));
579
-        }
580
-        // reset anything that needs a clean slate for each request
581
-        $checkout->reset_for_current_request();
582
-        return $checkout;
583
-    }
584
-
585
-
586
-
587
-    /**
588
-     *    _get_request_vars
589
-     *
590
-     * @access    private
591
-     * @return    void
592
-     * @throws \EE_Error
593
-     */
594
-    private function _get_request_vars()
595
-    {
596
-        // load classes
597
-        EED_Single_Page_Checkout::load_request_handler();
598
-        //make sure this request is marked as belonging to EE
599
-        EE_Registry::instance()->REQ->set_espresso_page(true);
600
-        // which step is being requested ?
601
-        $this->checkout->step = EE_Registry::instance()->REQ->get('step', $this->_get_first_step());
602
-        // which step is being edited ?
603
-        $this->checkout->edit_step = EE_Registry::instance()->REQ->get('edit_step', '');
604
-        // and what we're doing on the current step
605
-        $this->checkout->action = EE_Registry::instance()->REQ->get('action', 'display_spco_reg_step');
606
-        // timestamp
607
-        $this->checkout->uts = EE_Registry::instance()->REQ->get('uts', 0);
608
-        // returning to edit ?
609
-        $this->checkout->reg_url_link = EE_Registry::instance()->REQ->get('e_reg_url_link', '');
610
-        // or some other kind of revisit ?
611
-        $this->checkout->revisit = EE_Registry::instance()->REQ->get('revisit', false);
612
-        // and whether or not to generate a reg form for this request
613
-        $this->checkout->generate_reg_form = EE_Registry::instance()->REQ->get('generate_reg_form', true);        // TRUE 	FALSE
614
-        // and whether or not to process a reg form submission for this request
615
-        $this->checkout->process_form_submission = EE_Registry::instance()->REQ->get(
616
-            'process_form_submission',
617
-            $this->checkout->action === 'process_reg_step'
618
-        ); // TRUE 	FALSE
619
-        $this->checkout->process_form_submission = $this->checkout->action !== 'display_spco_reg_step'
620
-            ? $this->checkout->process_form_submission
621
-            : false;        // TRUE 	FALSE
622
-        // $this->_display_request_vars();
623
-    }
624
-
625
-
626
-
627
-    /**
628
-     *  _display_request_vars
629
-     *
630
-     * @access    protected
631
-     * @return    void
632
-     */
633
-    protected function _display_request_vars()
634
-    {
635
-        if ( ! WP_DEBUG) {
636
-            return;
637
-        }
638
-        EEH_Debug_Tools::printr($_REQUEST, '$_REQUEST', __FILE__, __LINE__);
639
-        EEH_Debug_Tools::printr($this->checkout->step, '$this->checkout->step', __FILE__, __LINE__);
640
-        EEH_Debug_Tools::printr($this->checkout->edit_step, '$this->checkout->edit_step', __FILE__, __LINE__);
641
-        EEH_Debug_Tools::printr($this->checkout->action, '$this->checkout->action', __FILE__, __LINE__);
642
-        EEH_Debug_Tools::printr($this->checkout->reg_url_link, '$this->checkout->reg_url_link', __FILE__, __LINE__);
643
-        EEH_Debug_Tools::printr($this->checkout->revisit, '$this->checkout->revisit', __FILE__, __LINE__);
644
-        EEH_Debug_Tools::printr($this->checkout->generate_reg_form, '$this->checkout->generate_reg_form', __FILE__, __LINE__);
645
-        EEH_Debug_Tools::printr($this->checkout->process_form_submission, '$this->checkout->process_form_submission', __FILE__, __LINE__);
646
-    }
647
-
648
-
649
-
650
-    /**
651
-     * _block_bots
652
-     * checks that the incoming request has either of the following set:
653
-     *  a uts (unix timestamp) which indicates that the request was redirected from the Ticket Selector
654
-     *  a REG URL Link, which indicates that the request is a return visit to SPCO for a valid TXN
655
-     * so if you're not coming from the Ticket Selector nor returning for a valid IP...
656
-     * then where you coming from man?
657
-     *
658
-     * @return boolean
659
-     */
660
-    private function _block_bots()
661
-    {
662
-        $invalid_checkout_access = \EED_Invalid_Checkout_Access::getInvalidCheckoutAccess();
663
-        if ($invalid_checkout_access->checkoutAccessIsInvalid($this->checkout)) {
664
-            return true;
665
-        }
666
-        return false;
667
-    }
668
-
669
-
670
-
671
-    /**
672
-     *    _get_first_step
673
-     *  gets slug for first step in $_reg_steps_array
674
-     *
675
-     * @access    private
676
-     * @throws EE_Error
677
-     * @return    string
678
-     */
679
-    private function _get_first_step()
680
-    {
681
-        $first_step = reset(EED_Single_Page_Checkout::$_reg_steps_array);
682
-        return isset($first_step['slug']) ? $first_step['slug'] : 'attendee_information';
683
-    }
684
-
685
-
686
-
687
-    /**
688
-     *    _load_and_instantiate_reg_steps
689
-     *  instantiates each reg step based on the loaded reg_steps array
690
-     *
691
-     * @access    private
692
-     * @throws EE_Error
693
-     * @return    bool
694
-     */
695
-    private function _load_and_instantiate_reg_steps()
696
-    {
697
-        // have reg_steps already been instantiated ?
698
-        if (
699
-            empty($this->checkout->reg_steps)
700
-            || apply_filters('FHEE__Single_Page_Checkout__load_reg_steps__reload_reg_steps', false, $this->checkout)
701
-        ) {
702
-            // if not, then loop through raw reg steps array
703
-            foreach (EED_Single_Page_Checkout::$_reg_steps_array as $order => $reg_step) {
704
-                if ( ! $this->_load_and_instantiate_reg_step($reg_step, $order)) {
705
-                    return false;
706
-                }
707
-            }
708
-            EE_Registry::instance()->CFG->registration->skip_reg_confirmation = true;
709
-            EE_Registry::instance()->CFG->registration->reg_confirmation_last = true;
710
-            // skip the registration_confirmation page ?
711
-            if (EE_Registry::instance()->CFG->registration->skip_reg_confirmation) {
712
-                // just remove it from the reg steps array
713
-                $this->checkout->remove_reg_step('registration_confirmation', false);
714
-            } else if (
715
-                isset($this->checkout->reg_steps['registration_confirmation'])
716
-                && EE_Registry::instance()->CFG->registration->reg_confirmation_last
717
-            ) {
718
-                // set the order to something big like 100
719
-                $this->checkout->set_reg_step_order('registration_confirmation', 100);
720
-            }
721
-            // filter the array for good luck
722
-            $this->checkout->reg_steps = apply_filters(
723
-                'FHEE__Single_Page_Checkout__load_reg_steps__reg_steps',
724
-                $this->checkout->reg_steps
725
-            );
726
-            // finally re-sort based on the reg step class order properties
727
-            $this->checkout->sort_reg_steps();
728
-        } else {
729
-            foreach ($this->checkout->reg_steps as $reg_step) {
730
-                // set all current step stati to FALSE
731
-                $reg_step->set_is_current_step(false);
732
-            }
733
-        }
734
-        if (empty($this->checkout->reg_steps)) {
735
-            EE_Error::add_error(__('No Reg Steps were loaded..', 'event_espresso'), __FILE__, __FUNCTION__, __LINE__);
736
-            return false;
737
-        }
738
-        // make reg step details available to JS
739
-        $this->checkout->set_reg_step_JSON_info();
740
-        return true;
741
-    }
742
-
743
-
744
-
745
-    /**
746
-     *     _load_and_instantiate_reg_step
747
-     *
748
-     * @access    private
749
-     * @param array $reg_step
750
-     * @param int   $order
751
-     * @return bool
752
-     */
753
-    private function _load_and_instantiate_reg_step($reg_step = array(), $order = 0)
754
-    {
755
-        // we need a file_path, class_name, and slug to add a reg step
756
-        if (isset($reg_step['file_path'], $reg_step['class_name'], $reg_step['slug'])) {
757
-            // if editing a specific step, but this is NOT that step... (and it's not the 'finalize_registration' step)
758
-            if (
759
-                $this->checkout->reg_url_link
760
-                && $this->checkout->step !== $reg_step['slug']
761
-                && $reg_step['slug'] !== 'finalize_registration'
762
-            ) {
763
-                return true;
764
-            }
765
-            // instantiate step class using file path and class name
766
-            $reg_step_obj = EE_Registry::instance()->load_file(
767
-                $reg_step['file_path'],
768
-                $reg_step['class_name'],
769
-                'class',
770
-                $this->checkout,
771
-                false
772
-            );
773
-            // did we gets the goods ?
774
-            if ($reg_step_obj instanceof EE_SPCO_Reg_Step) {
775
-                // set reg step order based on config
776
-                $reg_step_obj->set_order($order);
777
-                // add instantiated reg step object to the master reg steps array
778
-                $this->checkout->add_reg_step($reg_step_obj);
779
-            } else {
780
-                EE_Error::add_error(
781
-                    __('The current step could not be set.', 'event_espresso'),
782
-                    __FILE__, __FUNCTION__, __LINE__
783
-                );
784
-                return false;
785
-            }
786
-        } else {
787
-            if (WP_DEBUG) {
788
-                EE_Error::add_error(
789
-                    sprintf(
790
-                        __('A registration step could not be loaded. One or more of the following data points is invalid:%4$s%5$sFile Path: %1$s%6$s%5$sClass Name: %2$s%6$s%5$sSlug: %3$s%6$s%7$s', 'event_espresso'),
791
-                        isset($reg_step['file_path']) ? $reg_step['file_path'] : '',
792
-                        isset($reg_step['class_name']) ? $reg_step['class_name'] : '',
793
-                        isset($reg_step['slug']) ? $reg_step['slug'] : '',
794
-                        '<ul>',
795
-                        '<li>',
796
-                        '</li>',
797
-                        '</ul>'
798
-                    ),
799
-                    __FILE__, __FUNCTION__, __LINE__
800
-                );
801
-            }
802
-            return false;
803
-        }
804
-        return true;
805
-    }
806
-
807
-
808
-
809
-    /**
810
-     * _verify_transaction_and_get_registrations
811
-     *
812
-     * @access private
813
-     * @return bool
814
-     */
815
-    private function _verify_transaction_and_get_registrations()
816
-    {
817
-        // was there already a valid transaction in the checkout from the session ?
818
-        if ( ! $this->checkout->transaction instanceof EE_Transaction) {
819
-            // get transaction from db or session
820
-            $this->checkout->transaction = $this->checkout->reg_url_link && ! is_admin()
821
-                ? $this->_get_transaction_and_cart_for_previous_visit()
822
-                : $this->_get_cart_for_current_session_and_setup_new_transaction();
823
-            if ( ! $this->checkout->transaction instanceof EE_Transaction) {
824
-                EE_Error::add_error(
825
-                    __('Your Registration and Transaction information could not be retrieved from the db.',
826
-                        'event_espresso'),
827
-                    __FILE__, __FUNCTION__, __LINE__
828
-                );
829
-                $this->checkout->transaction = EE_Transaction::new_instance();
830
-                // add some style and make it dance
831
-                $this->add_styles_and_scripts();
832
-                EED_Single_Page_Checkout::$_initialized = true;
833
-                return false;
834
-            }
835
-            // and the registrations for the transaction
836
-            $this->_get_registrations($this->checkout->transaction);
837
-        }
838
-        return true;
839
-    }
840
-
841
-
842
-
843
-    /**
844
-     * _get_transaction_and_cart_for_previous_visit
845
-     *
846
-     * @access private
847
-     * @return mixed EE_Transaction|NULL
848
-     */
849
-    private function _get_transaction_and_cart_for_previous_visit()
850
-    {
851
-        /** @var $TXN_model EEM_Transaction */
852
-        $TXN_model = EE_Registry::instance()->load_model('Transaction');
853
-        // because the reg_url_link is present in the request, this is a return visit to SPCO, so we'll get the transaction data from the db
854
-        $transaction = $TXN_model->get_transaction_from_reg_url_link($this->checkout->reg_url_link);
855
-        // verify transaction
856
-        if ($transaction instanceof EE_Transaction) {
857
-            // and get the cart that was used for that transaction
858
-            $this->checkout->cart = $this->_get_cart_for_transaction($transaction);
859
-            return $transaction;
860
-        } else {
861
-            EE_Error::add_error(__('Your Registration and Transaction information could not be retrieved from the db.', 'event_espresso'), __FILE__, __FUNCTION__, __LINE__);
862
-            return null;
863
-        }
864
-    }
865
-
866
-
867
-
868
-    /**
869
-     * _get_cart_for_transaction
870
-     *
871
-     * @access private
872
-     * @param EE_Transaction $transaction
873
-     * @return EE_Cart
874
-     */
875
-    private function _get_cart_for_transaction($transaction)
876
-    {
877
-        return $this->checkout->get_cart_for_transaction($transaction);
878
-    }
879
-
880
-
881
-
882
-    /**
883
-     * get_cart_for_transaction
884
-     *
885
-     * @access public
886
-     * @param EE_Transaction $transaction
887
-     * @return EE_Cart
888
-     */
889
-    public function get_cart_for_transaction(EE_Transaction $transaction)
890
-    {
891
-        return $this->checkout->get_cart_for_transaction($transaction);
892
-    }
893
-
894
-
895
-
896
-    /**
897
-     * _get_transaction_and_cart_for_current_session
898
-     *    generates a new EE_Transaction object and adds it to the $_transaction property.
899
-     *
900
-     * @access private
901
-     * @return EE_Transaction
902
-     * @throws \EE_Error
903
-     */
904
-    private function _get_cart_for_current_session_and_setup_new_transaction()
905
-    {
906
-        //  if there's no transaction, then this is the FIRST visit to SPCO
907
-        // so load up the cart ( passing nothing for the TXN because it doesn't exist yet )
908
-        $this->checkout->cart = $this->_get_cart_for_transaction(null);
909
-        // and then create a new transaction
910
-        $transaction = $this->_initialize_transaction();
911
-        // verify transaction
912
-        if ($transaction instanceof EE_Transaction) {
913
-            // save it so that we have an ID for other objects to use
914
-            $transaction->save();
915
-            // and save TXN data to the cart
916
-            $this->checkout->cart->get_grand_total()->save_this_and_descendants_to_txn($transaction->ID());
917
-        } else {
918
-            EE_Error::add_error(__('A Valid Transaction could not be initialized.', 'event_espresso'), __FILE__, __FUNCTION__, __LINE__);
919
-        }
920
-        return $transaction;
921
-    }
922
-
923
-
924
-
925
-    /**
926
-     *    generates a new EE_Transaction object and adds it to the $_transaction property.
927
-     *
928
-     * @access private
929
-     * @return mixed EE_Transaction|NULL
930
-     */
931
-    private function _initialize_transaction()
932
-    {
933
-        try {
934
-            // ensure cart totals have been calculated
935
-            $this->checkout->cart->get_grand_total()->recalculate_total_including_taxes();
936
-            // grab the cart grand total
937
-            $cart_total = $this->checkout->cart->get_cart_grand_total();
938
-            // create new TXN
939
-            $transaction = EE_Transaction::new_instance(
940
-                array(
941
-                    'TXN_reg_steps' => $this->checkout->initialize_txn_reg_steps_array(),
942
-                    'TXN_total'     => $cart_total > 0 ? $cart_total : 0,
943
-                    'TXN_paid'      => 0,
944
-                    'STS_ID'        => EEM_Transaction::failed_status_code,
945
-                )
946
-            );
947
-            // save it so that we have an ID for other objects to use
948
-            $transaction->save();
949
-            // set cron job for following up on TXNs after their session has expired
950
-            EE_Cron_Tasks::schedule_expired_transaction_check(
951
-                EE_Registry::instance()->SSN->expiration() + 1,
952
-                $transaction->ID()
953
-            );
954
-            return $transaction;
955
-        } catch (Exception $e) {
956
-            EE_Error::add_error($e->getMessage(), __FILE__, __FUNCTION__, __LINE__);
957
-        }
958
-        return null;
959
-    }
960
-
961
-
962
-
963
-    /**
964
-     * _get_registrations
965
-     *
966
-     * @access private
967
-     * @param EE_Transaction $transaction
968
-     * @return void
969
-     * @throws \EventEspresso\core\exceptions\InvalidEntityException
970
-     * @throws \EE_Error
971
-     */
972
-    private function _get_registrations(EE_Transaction $transaction)
973
-    {
974
-        // first step: grab the registrants  { : o
975
-        $registrations = $transaction->registrations($this->checkout->reg_cache_where_params, true);
976
-        // verify registrations have been set
977
-        if (empty($registrations)) {
978
-            // if no cached registrations, then check the db
979
-            $registrations = $transaction->registrations($this->checkout->reg_cache_where_params, false);
980
-            // still nothing ? well as long as this isn't a revisit
981
-            if (empty($registrations) && ! $this->checkout->revisit) {
982
-                // generate new registrations from scratch
983
-                $registrations = $this->_initialize_registrations($transaction);
984
-            }
985
-        }
986
-        // sort by their original registration order
987
-        usort($registrations, array('EED_Single_Page_Checkout', 'sort_registrations_by_REG_count'));
988
-        // then loop thru the array
989
-        foreach ($registrations as $registration) {
990
-            // verify each registration
991
-            if ($registration instanceof EE_Registration) {
992
-                // we display all attendee info for the primary registrant
993
-                if ($this->checkout->reg_url_link === $registration->reg_url_link()
994
-                    && $registration->is_primary_registrant()
995
-                ) {
996
-                    $this->checkout->primary_revisit = true;
997
-                    break;
998
-                } else if ($this->checkout->revisit
999
-                           && $this->checkout->reg_url_link !== $registration->reg_url_link()
1000
-                ) {
1001
-                    // but hide info if it doesn't belong to you
1002
-                    $transaction->clear_cache('Registration', $registration->ID());
1003
-                }
1004
-                $this->checkout->set_reg_status_updated($registration->ID(), false);
1005
-            }
1006
-        }
1007
-    }
1008
-
1009
-
1010
-
1011
-    /**
1012
-     *    adds related EE_Registration objects for each ticket in the cart to the current EE_Transaction object
1013
-     *
1014
-     * @access private
1015
-     * @param EE_Transaction $transaction
1016
-     * @return    array
1017
-     * @throws \EventEspresso\core\exceptions\InvalidEntityException
1018
-     * @throws \EE_Error
1019
-     */
1020
-    private function _initialize_registrations(EE_Transaction $transaction)
1021
-    {
1022
-        $att_nmbr = 0;
1023
-        $registrations = array();
1024
-        if ($transaction instanceof EE_Transaction) {
1025
-            /** @type EE_Registration_Processor $registration_processor */
1026
-            $registration_processor = EE_Registry::instance()->load_class('Registration_Processor');
1027
-            $this->checkout->total_ticket_count = $this->checkout->cart->all_ticket_quantity_count();
1028
-            // now let's add the cart items to the $transaction
1029
-            foreach ($this->checkout->cart->get_tickets() as $line_item) {
1030
-                //do the following for each ticket of this type they selected
1031
-                for ($x = 1; $x <= $line_item->quantity(); $x++) {
1032
-                    $att_nmbr++;
1033
-                    /** @var EventEspresso\core\services\commands\registration\CreateRegistrationCommand $CreateRegistrationCommand */
1034
-                    $CreateRegistrationCommand = EE_Registry::instance()
1035
-                                                            ->create(
1036
-                                                                'EventEspresso\core\services\commands\registration\CreateRegistrationCommand',
1037
-                                                                array(
1038
-                                                                    $transaction,
1039
-                                                                    $line_item,
1040
-                                                                    $att_nmbr,
1041
-                                                                    $this->checkout->total_ticket_count,
1042
-                                                                )
1043
-                                                            );
1044
-                    // override capabilities for frontend registrations
1045
-                    if ( ! is_admin()) {
1046
-                        $CreateRegistrationCommand->setCapCheck(
1047
-                            new PublicCapabilities('', 'create_new_registration')
1048
-                        );
1049
-                    }
1050
-                    $registration = EE_Registry::instance()->BUS->execute($CreateRegistrationCommand);
1051
-                    if ( ! $registration instanceof EE_Registration) {
1052
-                        throw new InvalidEntityException($registration, 'EE_Registration');
1053
-                    }
1054
-                    $registrations[ $registration->ID() ] = $registration;
1055
-                }
1056
-            }
1057
-            $registration_processor->fix_reg_final_price_rounding_issue($transaction);
1058
-        }
1059
-        return $registrations;
1060
-    }
1061
-
1062
-
1063
-
1064
-    /**
1065
-     * sorts registrations by REG_count
1066
-     *
1067
-     * @access public
1068
-     * @param EE_Registration $reg_A
1069
-     * @param EE_Registration $reg_B
1070
-     * @return int
1071
-     */
1072
-    public static function sort_registrations_by_REG_count(EE_Registration $reg_A, EE_Registration $reg_B)
1073
-    {
1074
-        // this shouldn't ever happen within the same TXN, but oh well
1075
-        if ($reg_A->count() === $reg_B->count()) {
1076
-            return 0;
1077
-        }
1078
-        return ($reg_A->count() > $reg_B->count()) ? 1 : -1;
1079
-    }
1080
-
1081
-
1082
-
1083
-    /**
1084
-     *    _final_verifications
1085
-     * just makes sure that everything is set up correctly before proceeding
1086
-     *
1087
-     * @access    private
1088
-     * @return    bool
1089
-     * @throws \EE_Error
1090
-     */
1091
-    private function _final_verifications()
1092
-    {
1093
-        // filter checkout
1094
-        $this->checkout = apply_filters('FHEE__EED_Single_Page_Checkout___final_verifications__checkout', $this->checkout);
1095
-        //verify that current step is still set correctly
1096
-        if ( ! $this->checkout->current_step instanceof EE_SPCO_Reg_Step) {
1097
-            EE_Error::add_error(
1098
-                __('We\'re sorry but the registration process can not proceed because one or more registration steps were not setup correctly. Please refresh the page and try again or contact support.', 'event_espresso'),
1099
-                __FILE__,
1100
-                __FUNCTION__,
1101
-                __LINE__
1102
-            );
1103
-            return false;
1104
-        }
1105
-        // if returning to SPCO, then verify that primary registrant is set
1106
-        if ( ! empty($this->checkout->reg_url_link)) {
1107
-            $valid_registrant = $this->checkout->transaction->primary_registration();
1108
-            if ( ! $valid_registrant instanceof EE_Registration) {
1109
-                EE_Error::add_error(
1110
-                    __('We\'re sorry but there appears to be an error with the "reg_url_link" or the primary registrant for this transaction. Please refresh the page and try again or contact support.', 'event_espresso'),
1111
-                    __FILE__,
1112
-                    __FUNCTION__,
1113
-                    __LINE__
1114
-                );
1115
-                return false;
1116
-            }
1117
-            $valid_registrant = null;
1118
-            foreach ($this->checkout->transaction->registrations($this->checkout->reg_cache_where_params) as $registration) {
1119
-                if (
1120
-                    $registration instanceof EE_Registration
1121
-                    && $registration->reg_url_link() === $this->checkout->reg_url_link
1122
-                ) {
1123
-                    $valid_registrant = $registration;
1124
-                }
1125
-            }
1126
-            if ( ! $valid_registrant instanceof EE_Registration) {
1127
-                // hmmm... maybe we have the wrong session because the user is opening multiple tabs ?
1128
-                if (EED_Single_Page_Checkout::$_checkout_verified) {
1129
-                    // clear the session, mark the checkout as unverified, and try again
1130
-                    EE_Registry::instance()->SSN->clear_session();
1131
-                    EED_Single_Page_Checkout::$_initialized = false;
1132
-                    EED_Single_Page_Checkout::$_checkout_verified = false;
1133
-                    $this->_initialize();
1134
-                    EE_Error::reset_notices();
1135
-                    return false;
1136
-                }
1137
-                EE_Error::add_error(
1138
-                    __('We\'re sorry but there appears to be an error with the "reg_url_link" or the transaction itself. Please refresh the page and try again or contact support.', 'event_espresso'),
1139
-                    __FILE__,
1140
-                    __FUNCTION__,
1141
-                    __LINE__
1142
-                );
1143
-                return false;
1144
-            }
1145
-        }
1146
-        // now that things have been kinda sufficiently verified,
1147
-        // let's add the checkout to the session so that's available other systems
1148
-        EE_Registry::instance()->SSN->set_checkout($this->checkout);
1149
-        return true;
1150
-    }
1151
-
1152
-
1153
-
1154
-    /**
1155
-     *    _initialize_reg_steps
1156
-     * first makes sure that EE_Transaction_Processor::set_reg_step_initiated() is called as required
1157
-     * then loops thru all of the active reg steps and calls the initialize_reg_step() method
1158
-     *
1159
-     * @access    private
1160
-     * @param bool $reinitializing
1161
-     * @throws \EE_Error
1162
-     */
1163
-    private function _initialize_reg_steps($reinitializing = false)
1164
-    {
1165
-        $this->checkout->set_reg_step_initiated($this->checkout->current_step);
1166
-        // loop thru all steps to call their individual "initialize" methods and set i18n strings for JS
1167
-        foreach ($this->checkout->reg_steps as $reg_step) {
1168
-            if ( ! $reg_step->initialize_reg_step()) {
1169
-                // if not initialized then maybe this step is being removed...
1170
-                if ( ! $reinitializing && $reg_step->is_current_step()) {
1171
-                    // if it was the current step, then we need to start over here
1172
-                    $this->_initialize_reg_steps(true);
1173
-                    return;
1174
-                }
1175
-                continue;
1176
-            }
1177
-            // add css and JS for current step
1178
-            $reg_step->enqueue_styles_and_scripts();
1179
-            // i18n
1180
-            $reg_step->translate_js_strings();
1181
-            if ($reg_step->is_current_step()) {
1182
-                // the text that appears on the reg step form submit button
1183
-                $reg_step->set_submit_button_text();
1184
-            }
1185
-        }
1186
-        // dynamically creates hook point like: AHEE__Single_Page_Checkout___initialize_reg_step__attendee_information
1187
-        do_action("AHEE__Single_Page_Checkout___initialize_reg_step__{$this->checkout->current_step->slug()}", $this->checkout->current_step);
1188
-    }
1189
-
1190
-
1191
-
1192
-    /**
1193
-     * _check_form_submission
1194
-     *
1195
-     * @access private
1196
-     * @return boolean
1197
-     */
1198
-    private function _check_form_submission()
1199
-    {
1200
-        //does this request require the reg form to be generated ?
1201
-        if ($this->checkout->generate_reg_form) {
1202
-            // ever heard that song by Blue Rodeo ?
1203
-            try {
1204
-                $this->checkout->current_step->reg_form = $this->checkout->current_step->generate_reg_form();
1205
-                // if not displaying a form, then check for form submission
1206
-                if (
1207
-                    $this->checkout->process_form_submission
1208
-                    && $this->checkout->current_step->reg_form->was_submitted()
1209
-                ) {
1210
-                    // clear out any old data in case this step is being run again
1211
-                    $this->checkout->current_step->set_valid_data(array());
1212
-                    // capture submitted form data
1213
-                    $this->checkout->current_step->reg_form->receive_form_submission(
1214
-                        apply_filters('FHEE__Single_Page_Checkout___check_form_submission__request_params', EE_Registry::instance()->REQ->params(), $this->checkout)
1215
-                    );
1216
-                    // validate submitted form data
1217
-                    if ( ! $this->checkout->continue_reg || ! $this->checkout->current_step->reg_form->is_valid()) {
1218
-                        // thou shall not pass !!!
1219
-                        $this->checkout->continue_reg = false;
1220
-                        // any form validation errors?
1221
-                        if ($this->checkout->current_step->reg_form->submission_error_message() !== '') {
1222
-                            $submission_error_messages = array();
1223
-                            // bad, bad, bad registrant
1224
-                            foreach ($this->checkout->current_step->reg_form->get_validation_errors_accumulated() as $validation_error) {
1225
-                                if ($validation_error instanceof EE_Validation_Error) {
1226
-                                    $submission_error_messages[] = sprintf(
1227
-                                        __('%s : %s', 'event_espresso'),
1228
-                                        $validation_error->get_form_section()->html_label_text(),
1229
-                                        $validation_error->getMessage()
1230
-                                    );
1231
-                                }
1232
-                            }
1233
-                            EE_Error::add_error(implode('<br />', $submission_error_messages), __FILE__, __FUNCTION__, __LINE__);
1234
-                        }
1235
-                        // well not really... what will happen is we'll just get redirected back to redo the current step
1236
-                        $this->go_to_next_step();
1237
-                        return false;
1238
-                    }
1239
-                }
1240
-            } catch (EE_Error $e) {
1241
-                $e->get_error();
1242
-            }
1243
-        }
1244
-        return true;
1245
-    }
1246
-
1247
-
1248
-
1249
-    /**
1250
-     * _process_action
1251
-     *
1252
-     * @access private
1253
-     * @return void
1254
-     * @throws \EE_Error
1255
-     */
1256
-    private function _process_form_action()
1257
-    {
1258
-        // what cha wanna do?
1259
-        switch ($this->checkout->action) {
1260
-            // AJAX next step reg form
1261
-            case 'display_spco_reg_step' :
1262
-                $this->checkout->redirect = false;
1263
-                if (EE_Registry::instance()->REQ->ajax) {
1264
-                    $this->checkout->json_response->set_reg_step_html($this->checkout->current_step->display_reg_form());
1265
-                }
1266
-                break;
1267
-            default :
1268
-                // meh... do one of those other steps first
1269
-                if ( ! empty($this->checkout->action) && is_callable(array($this->checkout->current_step, $this->checkout->action))) {
1270
-                    // dynamically creates hook point like: AHEE__Single_Page_Checkout__before_attendee_information__process_reg_step
1271
-                    do_action("AHEE__Single_Page_Checkout__before_{$this->checkout->current_step->slug()}__{$this->checkout->action}", $this->checkout->current_step);
1272
-                    // call action on current step
1273
-                    if (call_user_func(array($this->checkout->current_step, $this->checkout->action))) {
1274
-                        // good registrant, you get to proceed
1275
-                        if (
1276
-                            $this->checkout->current_step->success_message() !== ''
1277
-                            && apply_filters(
1278
-                                'FHEE__Single_Page_Checkout___process_form_action__display_success',
1279
-                                false
1280
-                            )
1281
-                        ) {
1282
-                            EE_Error::add_success(
1283
-                                $this->checkout->current_step->success_message()
1284
-                                . '<br />' . $this->checkout->next_step->_instructions()
1285
-                            );
1286
-                        }
1287
-                        // pack it up, pack it in...
1288
-                        $this->_setup_redirect();
1289
-                    }
1290
-                    // dynamically creates hook point like: AHEE__Single_Page_Checkout__after_payment_options__process_reg_step
1291
-                    do_action("AHEE__Single_Page_Checkout__after_{$this->checkout->current_step->slug()}__{$this->checkout->action}", $this->checkout->current_step);
1292
-                } else {
1293
-                    EE_Error::add_error(
1294
-                        sprintf(
1295
-                            __('The requested form action "%s" does not exist for the current "%s" registration step.', 'event_espresso'),
1296
-                            $this->checkout->action,
1297
-                            $this->checkout->current_step->name()
1298
-                        ),
1299
-                        __FILE__,
1300
-                        __FUNCTION__,
1301
-                        __LINE__
1302
-                    );
1303
-                }
1304
-            // end default
1305
-        }
1306
-        // store our progress so far
1307
-        $this->checkout->stash_transaction_and_checkout();
1308
-        // advance to the next step! If you pass GO, collect $200
1309
-        $this->go_to_next_step();
1310
-    }
1311
-
1312
-
1313
-
1314
-    /**
1315
-     *        add_styles_and_scripts
1316
-     *
1317
-     * @access        public
1318
-     * @return        void
1319
-     */
1320
-    public function add_styles_and_scripts()
1321
-    {
1322
-        // i18n
1323
-        $this->translate_js_strings();
1324
-        if ($this->checkout->admin_request) {
1325
-            add_action('admin_enqueue_scripts', array($this, 'enqueue_styles_and_scripts'), 10);
1326
-        } else {
1327
-            add_action('wp_enqueue_scripts', array($this, 'enqueue_styles_and_scripts'), 10);
1328
-        }
1329
-    }
1330
-
1331
-
1332
-
1333
-    /**
1334
-     *        translate_js_strings
1335
-     *
1336
-     * @access        public
1337
-     * @return        void
1338
-     */
1339
-    public function translate_js_strings()
1340
-    {
1341
-        EE_Registry::$i18n_js_strings['revisit'] = $this->checkout->revisit;
1342
-        EE_Registry::$i18n_js_strings['e_reg_url_link'] = $this->checkout->reg_url_link;
1343
-        EE_Registry::$i18n_js_strings['server_error'] = __('An unknown error occurred on the server while attempting to process your request. Please refresh the page and try again or contact support.', 'event_espresso');
1344
-        EE_Registry::$i18n_js_strings['invalid_json_response'] = __('An invalid response was returned from the server while attempting to process your request. Please refresh the page and try again or contact support.', 'event_espresso');
1345
-        EE_Registry::$i18n_js_strings['validation_error'] = __('There appears to be a problem with the form validation configuration! Please check the admin settings or contact support.', 'event_espresso');
1346
-        EE_Registry::$i18n_js_strings['invalid_payment_method'] = __('There appears to be a problem with the payment method configuration! Please refresh the page and try again or contact support.', 'event_espresso');
1347
-        EE_Registry::$i18n_js_strings['reg_step_error'] = __('This registration step could not be completed. Please refresh the page and try again.', 'event_espresso');
1348
-        EE_Registry::$i18n_js_strings['invalid_coupon'] = __('We\'re sorry but that coupon code does not appear to be valid. If this is incorrect, please contact the site administrator.', 'event_espresso');
1349
-        EE_Registry::$i18n_js_strings['process_registration'] = sprintf(
1350
-            __('Please wait while we process your registration.%sDo not refresh the page or navigate away while this is happening.%sThank you for your patience.', 'event_espresso'),
1351
-            '<br/>',
1352
-            '<br/>'
1353
-        );
1354
-        EE_Registry::$i18n_js_strings['language'] = get_bloginfo('language');
1355
-        EE_Registry::$i18n_js_strings['EESID'] = EE_Registry::instance()->SSN->id();
1356
-        EE_Registry::$i18n_js_strings['currency'] = EE_Registry::instance()->CFG->currency;
1357
-        EE_Registry::$i18n_js_strings['datepicker_yearRange'] = '-150:+20';
1358
-        EE_Registry::$i18n_js_strings['timer_years'] = __('years', 'event_espresso');
1359
-        EE_Registry::$i18n_js_strings['timer_months'] = __('months', 'event_espresso');
1360
-        EE_Registry::$i18n_js_strings['timer_weeks'] = __('weeks', 'event_espresso');
1361
-        EE_Registry::$i18n_js_strings['timer_days'] = __('days', 'event_espresso');
1362
-        EE_Registry::$i18n_js_strings['timer_hours'] = __('hours', 'event_espresso');
1363
-        EE_Registry::$i18n_js_strings['timer_minutes'] = __('minutes', 'event_espresso');
1364
-        EE_Registry::$i18n_js_strings['timer_seconds'] = __('seconds', 'event_espresso');
1365
-        EE_Registry::$i18n_js_strings['timer_year'] = __('year', 'event_espresso');
1366
-        EE_Registry::$i18n_js_strings['timer_month'] = __('month', 'event_espresso');
1367
-        EE_Registry::$i18n_js_strings['timer_week'] = __('week', 'event_espresso');
1368
-        EE_Registry::$i18n_js_strings['timer_day'] = __('day', 'event_espresso');
1369
-        EE_Registry::$i18n_js_strings['timer_hour'] = __('hour', 'event_espresso');
1370
-        EE_Registry::$i18n_js_strings['timer_minute'] = __('minute', 'event_espresso');
1371
-        EE_Registry::$i18n_js_strings['timer_second'] = __('second', 'event_espresso');
1372
-        EE_Registry::$i18n_js_strings['registration_expiration_notice'] = sprintf(
1373
-            __(
1374
-                '%1$sWe\'re sorry, but your registration time has expired.%2$s%3$s%4$sIf you still wish to complete your registration, please return to the %5$sEvent List%6$sEvent List%7$s and reselect your tickets if available. Please except our apologies for any inconvenience this may have caused.%8$s',
1375
-                'event_espresso'
1376
-            ),
1377
-            '<h4 class="important-notice">',
1378
-            '</h4>',
1379
-            '<br />',
1380
-            '<p>',
1381
-            '<a href="' . get_post_type_archive_link('espresso_events') . '" title="',
1382
-            '">',
1383
-            '</a>',
1384
-            '</p>'
1385
-        );
1386
-        EE_Registry::$i18n_js_strings['ajax_submit'] = apply_filters('FHEE__Single_Page_Checkout__translate_js_strings__ajax_submit', true);
1387
-        EE_Registry::$i18n_js_strings['session_extension'] = absint(
1388
-            apply_filters('FHEE__EE_Session__extend_expiration__seconds_added', 10 * MINUTE_IN_SECONDS)
1389
-        );
1390
-        EE_Registry::$i18n_js_strings['session_expiration'] = gmdate(
1391
-            'M d, Y H:i:s', EE_Registry::instance()->SSN->expiration() + (get_option('gmt_offset') * HOUR_IN_SECONDS)
1392
-        );
1393
-    }
1394
-
1395
-
1396
-
1397
-    /**
1398
-     *    enqueue_styles_and_scripts
1399
-     *
1400
-     * @access        public
1401
-     * @return        void
1402
-     * @throws \EE_Error
1403
-     */
1404
-    public function enqueue_styles_and_scripts()
1405
-    {
1406
-        // load css
1407
-        wp_register_style('single_page_checkout', SPCO_CSS_URL . 'single_page_checkout.css', array(), EVENT_ESPRESSO_VERSION);
1408
-        wp_enqueue_style('single_page_checkout');
1409
-        // load JS
1410
-        wp_register_script('jquery_plugin', EE_THIRD_PARTY_URL . 'jquery	.plugin.min.js', array('jquery'), '1.0.1', true);
1411
-        wp_register_script('jquery_countdown', EE_THIRD_PARTY_URL . 'jquery	.countdown.min.js', array('jquery_plugin'), '2.0.2', true);
1412
-        wp_register_script('single_page_checkout', SPCO_JS_URL . 'single_page_checkout.js', array('espresso_core', 'underscore', 'ee_form_section_validation', 'jquery_countdown'), EVENT_ESPRESSO_VERSION, true);
1413
-        if ($this->checkout->registration_form instanceof EE_Form_Section_Proper) {
1414
-            $this->checkout->registration_form->enqueue_js();
1415
-        }
1416
-        if ($this->checkout->current_step->reg_form instanceof EE_Form_Section_Proper) {
1417
-            $this->checkout->current_step->reg_form->enqueue_js();
1418
-        }
1419
-        wp_enqueue_script('single_page_checkout');
1420
-        /**
1421
-         * global action hook for enqueueing styles and scripts with
1422
-         * spco calls.
1423
-         */
1424
-        do_action('AHEE__EED_Single_Page_Checkout__enqueue_styles_and_scripts', $this);
1425
-        /**
1426
-         * dynamic action hook for enqueueing styles and scripts with spco calls.
1427
-         * The hook will end up being something like AHEE__EED_Single_Page_Checkout__enqueue_styles_and_scripts__attendee_information
1428
-         */
1429
-        do_action('AHEE__EED_Single_Page_Checkout__enqueue_styles_and_scripts__' . $this->checkout->current_step->slug(), $this);
1430
-    }
1431
-
1432
-
1433
-
1434
-    /**
1435
-     *    display the Registration Single Page Checkout Form
1436
-     *
1437
-     * @access    private
1438
-     * @return    void
1439
-     * @throws \EE_Error
1440
-     */
1441
-    private function _display_spco_reg_form()
1442
-    {
1443
-        // if registering via the admin, just display the reg form for the current step
1444
-        if ($this->checkout->admin_request) {
1445
-            EE_Registry::instance()->REQ->add_output($this->checkout->current_step->display_reg_form());
1446
-        } else {
1447
-            // add powered by EE msg
1448
-            add_action('AHEE__SPCO__reg_form_footer', array('EED_Single_Page_Checkout', 'display_registration_footer'));
1449
-            $empty_cart = count($this->checkout->transaction->registrations($this->checkout->reg_cache_where_params)) < 1
1450
-                ? true
1451
-                : false;
1452
-            EE_Registry::$i18n_js_strings['empty_cart'] = $empty_cart;
1453
-            $cookies_not_set_msg = '';
1454
-            if ($empty_cart && ! isset($_COOKIE['ee_cookie_test'])) {
1455
-                $cookies_not_set_msg = apply_filters(
1456
-                    'FHEE__Single_Page_Checkout__display_spco_reg_form__cookies_not_set_msg',
1457
-                    sprintf(
1458
-                        __(
1459
-                            '%1$s%3$sIt appears your browser is not currently set to accept Cookies%4$s%5$sIn order to register for events, you need to enable cookies.%7$sIf you require assistance, then click the following link to learn how to %8$senable cookies%9$s%6$s%2$s',
1460
-                            'event_espresso'
1461
-                        ),
1462
-                        '<div class="ee-attention">',
1463
-                        '</div>',
1464
-                        '<h6 class="important-notice">',
1465
-                        '</h6>',
1466
-                        '<p>',
1467
-                        '</p>',
1468
-                        '<br />',
1469
-                        '<a href="http://www.whatarecookies.com/enable.asp" target="_blank">',
1470
-                        '</a>'
1471
-                    )
1472
-                );
1473
-            }
1474
-            $this->checkout->registration_form = new EE_Form_Section_Proper(
1475
-                array(
1476
-                    'name'            => 'single-page-checkout',
1477
-                    'html_id'         => 'ee-single-page-checkout-dv',
1478
-                    'layout_strategy' =>
1479
-                        new EE_Template_Layout(
1480
-                            array(
1481
-                                'layout_template_file' => SPCO_TEMPLATES_PATH . 'registration_page_wrapper.template.php',
1482
-                                'template_args'        => array(
1483
-                                    'empty_cart'              => $empty_cart,
1484
-                                    'revisit'                 => $this->checkout->revisit,
1485
-                                    'reg_steps'               => $this->checkout->reg_steps,
1486
-                                    'next_step'               => $this->checkout->next_step instanceof EE_SPCO_Reg_Step
1487
-                                        ? $this->checkout->next_step->slug()
1488
-                                        : '',
1489
-                                    'cancel_page_url'         => $this->checkout->cancel_page_url,
1490
-                                    'empty_msg'               => apply_filters(
1491
-                                        'FHEE__Single_Page_Checkout__display_spco_reg_form__empty_msg',
1492
-                                        sprintf(
1493
-                                            __('You need to %1$sReturn to Events list%2$sselect at least one event%3$s before you can proceed with the registration process.',
1494
-                                                'event_espresso'),
1495
-                                            '<a href="' . get_post_type_archive_link('espresso_events') . '" title="',
1496
-                                            '">',
1497
-                                            '</a>'
1498
-                                        )
1499
-                                    ),
1500
-                                    'cookies_not_set_msg'     => $cookies_not_set_msg,
1501
-                                    'registration_time_limit' => $this->checkout->get_registration_time_limit(),
1502
-                                    'session_expiration'      =>
1503
-                                        date('M d, Y H:i:s', EE_Registry::instance()->SSN->expiration() + (get_option('gmt_offset') * HOUR_IN_SECONDS)),
1504
-                                ),
1505
-                            )
1506
-                        ),
1507
-                )
1508
-            );
1509
-            // load template and add to output sent that gets filtered into the_content()
1510
-            EE_Registry::instance()->REQ->add_output($this->checkout->registration_form->get_html());
1511
-        }
1512
-    }
1513
-
1514
-
1515
-
1516
-    /**
1517
-     *    add_extra_finalize_registration_inputs
1518
-     *
1519
-     * @access    public
1520
-     * @param $next_step
1521
-     * @internal  param string $label
1522
-     * @return void
1523
-     */
1524
-    public function add_extra_finalize_registration_inputs($next_step)
1525
-    {
1526
-        if ($next_step === 'finalize_registration') {
1527
-            echo '<div id="spco-extra-finalize_registration-inputs-dv"></div>';
1528
-        }
1529
-    }
1530
-
1531
-
1532
-
1533
-    /**
1534
-     *    display_registration_footer
1535
-     *
1536
-     * @access    public
1537
-     * @return    string
1538
-     */
1539
-    public static function display_registration_footer()
1540
-    {
1541
-        if (
1542
-        apply_filters(
1543
-            'FHEE__EE_Front__Controller__show_reg_footer',
1544
-            EE_Registry::instance()->CFG->admin->show_reg_footer
1545
-        )
1546
-        ) {
1547
-            add_filter(
1548
-                'FHEE__EEH_Template__powered_by_event_espresso__url',
1549
-                function ($url) {
1550
-                    return apply_filters('FHEE__EE_Front_Controller__registration_footer__url', $url);
1551
-                }
1552
-            );
1553
-            echo apply_filters(
1554
-                'FHEE__EE_Front_Controller__display_registration_footer',
1555
-                \EEH_Template::powered_by_event_espresso(
1556
-                    '',
1557
-                    'espresso-registration-footer-dv',
1558
-                    array('utm_content' => 'registration_checkout')
1559
-                )
1560
-            );
1561
-        }
1562
-        return '';
1563
-    }
1564
-
1565
-
1566
-
1567
-    /**
1568
-     *    unlock_transaction
1569
-     *
1570
-     * @access    public
1571
-     * @return    void
1572
-     * @throws \EE_Error
1573
-     */
1574
-    public function unlock_transaction()
1575
-    {
1576
-        if ($this->checkout->transaction instanceof EE_Transaction) {
1577
-            $this->checkout->transaction->unlock();
1578
-        }
1579
-    }
1580
-
1581
-
1582
-
1583
-    /**
1584
-     *        _setup_redirect
1585
-     *
1586
-     * @access    private
1587
-     * @return void
1588
-     */
1589
-    private function _setup_redirect()
1590
-    {
1591
-        if ($this->checkout->continue_reg && $this->checkout->next_step instanceof EE_SPCO_Reg_Step) {
1592
-            $this->checkout->redirect = true;
1593
-            if (empty($this->checkout->redirect_url)) {
1594
-                $this->checkout->redirect_url = $this->checkout->next_step->reg_step_url();
1595
-            }
1596
-            $this->checkout->redirect_url = apply_filters(
1597
-                'FHEE__EED_Single_Page_Checkout___setup_redirect__checkout_redirect_url',
1598
-                $this->checkout->redirect_url,
1599
-                $this->checkout
1600
-            );
1601
-        }
1602
-    }
1603
-
1604
-
1605
-
1606
-    /**
1607
-     *   handle ajax message responses and redirects
1608
-     *
1609
-     * @access public
1610
-     * @return void
1611
-     * @throws \EE_Error
1612
-     */
1613
-    public function go_to_next_step()
1614
-    {
1615
-        if (EE_Registry::instance()->REQ->ajax) {
1616
-            // capture contents of output buffer we started earlier in the request, and insert into JSON response
1617
-            $this->checkout->json_response->set_unexpected_errors(ob_get_clean());
1618
-        }
1619
-        $this->unlock_transaction();
1620
-        // just return for these conditions
1621
-        if (
1622
-            $this->checkout->admin_request
1623
-            || $this->checkout->action === 'redirect_form'
1624
-            || $this->checkout->action === 'update_checkout'
1625
-        ) {
1626
-            return;
1627
-        }
1628
-        // AJAX response
1629
-        $this->_handle_json_response();
1630
-        // redirect to next step or the Thank You page
1631
-        $this->_handle_html_redirects();
1632
-        // hmmm... must be something wrong, so let's just display the form again !
1633
-        $this->_display_spco_reg_form();
1634
-    }
1635
-
1636
-
1637
-
1638
-    /**
1639
-     *   _handle_json_response
1640
-     *
1641
-     * @access protected
1642
-     * @return void
1643
-     */
1644
-    protected function _handle_json_response()
1645
-    {
1646
-        // if this is an ajax request
1647
-        if (EE_Registry::instance()->REQ->ajax) {
1648
-            // DEBUG LOG
1649
-            //$this->checkout->log(
1650
-            //	__CLASS__, __FUNCTION__, __LINE__,
1651
-            //	array(
1652
-            //		'json_response_redirect_url' => $this->checkout->json_response->redirect_url(),
1653
-            //		'redirect'                   => $this->checkout->redirect,
1654
-            //		'continue_reg'               => $this->checkout->continue_reg,
1655
-            //	)
1656
-            //);
1657
-            $this->checkout->json_response->set_registration_time_limit(
1658
-                $this->checkout->get_registration_time_limit()
1659
-            );
1660
-            $this->checkout->json_response->set_payment_amount($this->checkout->amount_owing);
1661
-            // just send the ajax (
1662
-            $json_response = apply_filters(
1663
-                'FHEE__EE_Single_Page_Checkout__JSON_response',
1664
-                $this->checkout->json_response
1665
-            );
1666
-            echo $json_response;
1667
-            exit();
1668
-        }
1669
-    }
1670
-
1671
-
1672
-
1673
-    /**
1674
-     *   _handle_redirects
1675
-     *
1676
-     * @access protected
1677
-     * @return void
1678
-     */
1679
-    protected function _handle_html_redirects()
1680
-    {
1681
-        // going somewhere ?
1682
-        if ($this->checkout->redirect && ! empty($this->checkout->redirect_url)) {
1683
-            // store notices in a transient
1684
-            EE_Error::get_notices(false, true, true);
1685
-            // DEBUG LOG
1686
-            //$this->checkout->log(
1687
-            //	__CLASS__, __FUNCTION__, __LINE__,
1688
-            //	array(
1689
-            //		'headers_sent' => headers_sent(),
1690
-            //		'redirect_url'     => $this->checkout->redirect_url,
1691
-            //		'headers_list'    => headers_list(),
1692
-            //	)
1693
-            //);
1694
-            wp_safe_redirect($this->checkout->redirect_url);
1695
-            exit();
1696
-        }
1697
-    }
1698
-
1699
-
1700
-
1701
-    /**
1702
-     *   set_checkout_anchor
1703
-     *
1704
-     * @access public
1705
-     * @return void
1706
-     */
1707
-    public function set_checkout_anchor()
1708
-    {
1709
-        echo '<a id="checkout" style="float: left; margin-left: -999em;"></a>';
1710
-    }
20
+	/**
21
+	 * $_initialized - has the SPCO controller already been initialized ?
22
+	 *
23
+	 * @access private
24
+	 * @var bool $_initialized
25
+	 */
26
+	private static $_initialized = false;
27
+
28
+
29
+	/**
30
+	 * $_checkout_verified - is the EE_Checkout verified as correct for this request ?
31
+	 *
32
+	 * @access private
33
+	 * @var bool $_valid_checkout
34
+	 */
35
+	private static $_checkout_verified = true;
36
+
37
+	/**
38
+	 *    $_reg_steps_array - holds initial array of reg steps
39
+	 *
40
+	 * @access private
41
+	 * @var array $_reg_steps_array
42
+	 */
43
+	private static $_reg_steps_array = array();
44
+
45
+	/**
46
+	 *    $checkout - EE_Checkout object for handling the properties of the current checkout process
47
+	 *
48
+	 * @access public
49
+	 * @var EE_Checkout $checkout
50
+	 */
51
+	public $checkout;
52
+
53
+
54
+
55
+	/**
56
+	 * @return EED_Single_Page_Checkout
57
+	 */
58
+	public static function instance()
59
+	{
60
+		add_filter('EED_Single_Page_Checkout__SPCO_active', '__return_true');
61
+		return parent::get_instance(__CLASS__);
62
+	}
63
+
64
+
65
+
66
+	/**
67
+	 * @return EE_CART
68
+	 */
69
+	public function cart()
70
+	{
71
+		return $this->checkout->cart;
72
+	}
73
+
74
+
75
+
76
+	/**
77
+	 * @return EE_Transaction
78
+	 */
79
+	public function transaction()
80
+	{
81
+		return $this->checkout->transaction;
82
+	}
83
+
84
+
85
+
86
+	/**
87
+	 *    set_hooks - for hooking into EE Core, other modules, etc
88
+	 *
89
+	 * @access    public
90
+	 * @return    void
91
+	 * @throws \EE_Error
92
+	 */
93
+	public static function set_hooks()
94
+	{
95
+		EED_Single_Page_Checkout::set_definitions();
96
+	}
97
+
98
+
99
+
100
+	/**
101
+	 *    set_hooks_admin - for hooking into EE Admin Core, other modules, etc
102
+	 *
103
+	 * @access    public
104
+	 * @return    void
105
+	 * @throws \EE_Error
106
+	 */
107
+	public static function set_hooks_admin()
108
+	{
109
+		EED_Single_Page_Checkout::set_definitions();
110
+		if ( ! (defined('DOING_AJAX') && DOING_AJAX)) {
111
+			// hook into the top of pre_get_posts to set the reg step routing, which gives other modules or plugins a chance to modify the reg steps, but just before the routes get called
112
+			add_action('pre_get_posts', array('EED_Single_Page_Checkout', 'load_reg_steps'), 1);
113
+			return;
114
+		}
115
+		// going to start an output buffer in case anything gets accidentally output that might disrupt our JSON response
116
+		ob_start();
117
+		EED_Single_Page_Checkout::load_request_handler();
118
+		EED_Single_Page_Checkout::load_reg_steps();
119
+		// set ajax hooks
120
+		add_action('wp_ajax_process_reg_step', array('EED_Single_Page_Checkout', 'process_reg_step'));
121
+		add_action('wp_ajax_nopriv_process_reg_step', array('EED_Single_Page_Checkout', 'process_reg_step'));
122
+		add_action('wp_ajax_display_spco_reg_step', array('EED_Single_Page_Checkout', 'display_reg_step'));
123
+		add_action('wp_ajax_nopriv_display_spco_reg_step', array('EED_Single_Page_Checkout', 'display_reg_step'));
124
+		add_action('wp_ajax_update_reg_step', array('EED_Single_Page_Checkout', 'update_reg_step'));
125
+		add_action('wp_ajax_nopriv_update_reg_step', array('EED_Single_Page_Checkout', 'update_reg_step'));
126
+	}
127
+
128
+
129
+
130
+	/**
131
+	 *    process ajax request
132
+	 *
133
+	 * @param string $ajax_action
134
+	 * @throws \EE_Error
135
+	 */
136
+	public static function process_ajax_request($ajax_action)
137
+	{
138
+		EE_Registry::instance()->REQ->set('action', $ajax_action);
139
+		EED_Single_Page_Checkout::instance()->_initialize();
140
+	}
141
+
142
+
143
+
144
+	/**
145
+	 *    ajax display registration step
146
+	 *
147
+	 * @throws \EE_Error
148
+	 */
149
+	public static function display_reg_step()
150
+	{
151
+		EED_Single_Page_Checkout::process_ajax_request('display_spco_reg_step');
152
+	}
153
+
154
+
155
+
156
+	/**
157
+	 *    ajax process registration step
158
+	 *
159
+	 * @throws \EE_Error
160
+	 */
161
+	public static function process_reg_step()
162
+	{
163
+		EED_Single_Page_Checkout::process_ajax_request('process_reg_step');
164
+	}
165
+
166
+
167
+
168
+	/**
169
+	 *    ajax process registration step
170
+	 *
171
+	 * @throws \EE_Error
172
+	 */
173
+	public static function update_reg_step()
174
+	{
175
+		EED_Single_Page_Checkout::process_ajax_request('update_reg_step');
176
+	}
177
+
178
+
179
+
180
+	/**
181
+	 *   update_checkout
182
+	 *
183
+	 * @access public
184
+	 * @return void
185
+	 * @throws \EE_Error
186
+	 */
187
+	public static function update_checkout()
188
+	{
189
+		EED_Single_Page_Checkout::process_ajax_request('update_checkout');
190
+	}
191
+
192
+
193
+
194
+	/**
195
+	 *    load_request_handler
196
+	 *
197
+	 * @access    public
198
+	 * @return    void
199
+	 */
200
+	public static function load_request_handler()
201
+	{
202
+		// load core Request_Handler class
203
+		if ( ! isset(EE_Registry::instance()->REQ)) {
204
+			EE_Registry::instance()->load_core('Request_Handler');
205
+		}
206
+	}
207
+
208
+
209
+
210
+	/**
211
+	 *    set_definitions
212
+	 *
213
+	 * @access    public
214
+	 * @return    void
215
+	 * @throws \EE_Error
216
+	 */
217
+	public static function set_definitions()
218
+	{
219
+		define('SPCO_BASE_PATH', rtrim(str_replace(array('\\', '/'), DS, plugin_dir_path(__FILE__)), DS) . DS);
220
+		define('SPCO_CSS_URL', plugin_dir_url(__FILE__) . 'css' . DS);
221
+		define('SPCO_IMG_URL', plugin_dir_url(__FILE__) . 'img' . DS);
222
+		define('SPCO_JS_URL', plugin_dir_url(__FILE__) . 'js' . DS);
223
+		define('SPCO_INC_PATH', SPCO_BASE_PATH . 'inc' . DS);
224
+		define('SPCO_REG_STEPS_PATH', SPCO_BASE_PATH . 'reg_steps' . DS);
225
+		define('SPCO_TEMPLATES_PATH', SPCO_BASE_PATH . 'templates' . DS);
226
+		EEH_Autoloader::register_autoloaders_for_each_file_in_folder(SPCO_BASE_PATH, true);
227
+		EE_Registry::$i18n_js_strings['registration_expiration_notice'] = sprintf(
228
+			__('%1$sWe\'re sorry, but you\'re registration time has expired.%2$s%4$sIf you still wish to complete your registration, please return to the %5$sEvent List%6$sEvent List%7$s and reselect your tickets if available. Please except our apologies for any inconvenience this may have caused.%8$s',
229
+				'event_espresso'),
230
+			'<h4 class="important-notice">',
231
+			'</h4>',
232
+			'<br />',
233
+			'<p>',
234
+			'<a href="' . get_post_type_archive_link('espresso_events') . '" title="',
235
+			'">',
236
+			'</a>',
237
+			'</p>'
238
+		);
239
+	}
240
+
241
+
242
+
243
+	/**
244
+	 * load_reg_steps
245
+	 * loads and instantiates each reg step based on the EE_Registry::instance()->CFG->registration->reg_steps array
246
+	 *
247
+	 * @access    private
248
+	 * @throws EE_Error
249
+	 * @return void
250
+	 */
251
+	public static function load_reg_steps()
252
+	{
253
+		static $reg_steps_loaded = false;
254
+		if ($reg_steps_loaded) {
255
+			return;
256
+		}
257
+		// filter list of reg_steps
258
+		$reg_steps_to_load = (array)apply_filters(
259
+			'AHEE__SPCO__load_reg_steps__reg_steps_to_load',
260
+			EED_Single_Page_Checkout::get_reg_steps()
261
+		);
262
+		// sort by key (order)
263
+		ksort($reg_steps_to_load);
264
+		// loop through folders
265
+		foreach ($reg_steps_to_load as $order => $reg_step) {
266
+			// we need a
267
+			if (isset($reg_step['file_path'], $reg_step['class_name'], $reg_step['slug'])) {
268
+				// copy over to the reg_steps_array
269
+				EED_Single_Page_Checkout::$_reg_steps_array[$order] = $reg_step;
270
+				// register custom key route for each reg step
271
+				// ie: step=>"slug" - this is the entire reason we load the reg steps array now
272
+				EE_Config::register_route($reg_step['slug'], 'EED_Single_Page_Checkout', 'run', 'step');
273
+				// add AJAX or other hooks
274
+				if (isset($reg_step['has_hooks']) && $reg_step['has_hooks']) {
275
+					// setup autoloaders if necessary
276
+					if ( ! class_exists($reg_step['class_name'])) {
277
+						EEH_Autoloader::register_autoloaders_for_each_file_in_folder($reg_step['file_path'], true);
278
+					}
279
+					if (is_callable($reg_step['class_name'], 'set_hooks')) {
280
+						call_user_func(array($reg_step['class_name'], 'set_hooks'));
281
+					}
282
+				}
283
+			}
284
+		}
285
+		$reg_steps_loaded = true;
286
+	}
287
+
288
+
289
+
290
+	/**
291
+	 *    get_reg_steps
292
+	 *
293
+	 * @access    public
294
+	 * @return    array
295
+	 */
296
+	public static function get_reg_steps()
297
+	{
298
+		$reg_steps = EE_Registry::instance()->CFG->registration->reg_steps;
299
+		if (empty($reg_steps)) {
300
+			$reg_steps = array(
301
+				10  => array(
302
+					'file_path'  => SPCO_REG_STEPS_PATH . 'attendee_information',
303
+					'class_name' => 'EE_SPCO_Reg_Step_Attendee_Information',
304
+					'slug'       => 'attendee_information',
305
+					'has_hooks'  => false,
306
+				),
307
+				20  => array(
308
+					'file_path'  => SPCO_REG_STEPS_PATH . 'registration_confirmation',
309
+					'class_name' => 'EE_SPCO_Reg_Step_Registration_Confirmation',
310
+					'slug'       => 'registration_confirmation',
311
+					'has_hooks'  => false,
312
+				),
313
+				30  => array(
314
+					'file_path'  => SPCO_REG_STEPS_PATH . 'payment_options',
315
+					'class_name' => 'EE_SPCO_Reg_Step_Payment_Options',
316
+					'slug'       => 'payment_options',
317
+					'has_hooks'  => true,
318
+				),
319
+				999 => array(
320
+					'file_path'  => SPCO_REG_STEPS_PATH . 'finalize_registration',
321
+					'class_name' => 'EE_SPCO_Reg_Step_Finalize_Registration',
322
+					'slug'       => 'finalize_registration',
323
+					'has_hooks'  => false,
324
+				),
325
+			);
326
+		}
327
+		return $reg_steps;
328
+	}
329
+
330
+
331
+
332
+	/**
333
+	 *    registration_checkout_for_admin
334
+	 *
335
+	 * @access    public
336
+	 * @return    string
337
+	 * @throws \EE_Error
338
+	 */
339
+	public static function registration_checkout_for_admin()
340
+	{
341
+		EED_Single_Page_Checkout::load_reg_steps();
342
+		EE_Registry::instance()->REQ->set('step', 'attendee_information');
343
+		EE_Registry::instance()->REQ->set('action', 'display_spco_reg_step');
344
+		EE_Registry::instance()->REQ->set('process_form_submission', false);
345
+		EED_Single_Page_Checkout::instance()->_initialize();
346
+		EED_Single_Page_Checkout::instance()->_display_spco_reg_form();
347
+		return EE_Registry::instance()->REQ->get_output();
348
+	}
349
+
350
+
351
+
352
+	/**
353
+	 * process_registration_from_admin
354
+	 *
355
+	 * @access public
356
+	 * @return \EE_Transaction
357
+	 * @throws \EE_Error
358
+	 */
359
+	public static function process_registration_from_admin()
360
+	{
361
+		EED_Single_Page_Checkout::load_reg_steps();
362
+		EE_Registry::instance()->REQ->set('step', 'attendee_information');
363
+		EE_Registry::instance()->REQ->set('action', 'process_reg_step');
364
+		EE_Registry::instance()->REQ->set('process_form_submission', true);
365
+		EED_Single_Page_Checkout::instance()->_initialize();
366
+		if (EED_Single_Page_Checkout::instance()->checkout->current_step->completed()) {
367
+			$final_reg_step = end(EED_Single_Page_Checkout::instance()->checkout->reg_steps);
368
+			if ($final_reg_step instanceof EE_SPCO_Reg_Step_Finalize_Registration) {
369
+				EED_Single_Page_Checkout::instance()->checkout->set_reg_step_initiated($final_reg_step);
370
+				if ($final_reg_step->process_reg_step()) {
371
+					$final_reg_step->set_completed();
372
+					EED_Single_Page_Checkout::instance()->checkout->update_txn_reg_steps_array();
373
+					return EED_Single_Page_Checkout::instance()->checkout->transaction;
374
+				}
375
+			}
376
+		}
377
+		return null;
378
+	}
379
+
380
+
381
+
382
+	/**
383
+	 *    run
384
+	 *
385
+	 * @access    public
386
+	 * @param WP_Query $WP_Query
387
+	 * @return    void
388
+	 * @throws \EE_Error
389
+	 */
390
+	public function run($WP_Query)
391
+	{
392
+		if (
393
+			$WP_Query instanceof WP_Query
394
+			&& $WP_Query->is_main_query()
395
+			&& apply_filters('FHEE__EED_Single_Page_Checkout__run', true)
396
+			&& $this->_is_reg_checkout()
397
+		) {
398
+			$this->_initialize();
399
+		}
400
+	}
401
+
402
+
403
+
404
+	/**
405
+	 * determines whether current url matches reg page url
406
+	 *
407
+	 * @return bool
408
+	 */
409
+	protected function _is_reg_checkout()
410
+	{
411
+		// get current permalink for reg page without any extra query args
412
+		$reg_page_url = \get_permalink(EE_Config::instance()->core->reg_page_id);
413
+		// get request URI for current request, but without the scheme or host
414
+		$current_request_uri = \EEH_URL::filter_input_server_url('REQUEST_URI');
415
+		$current_request_uri = html_entity_decode($current_request_uri);
416
+		// get array of query args from the current request URI
417
+		$query_args = \EEH_URL::get_query_string($current_request_uri);
418
+		// grab page id if it is set
419
+		$page_id = isset($query_args['page_id']) ? absint($query_args['page_id']) : 0;
420
+		// and remove the page id from the query args (we will re-add it later)
421
+		unset($query_args['page_id']);
422
+		// now strip all query args from current request URI
423
+		$current_request_uri = remove_query_arg(array_flip($query_args), $current_request_uri);
424
+		// and re-add the page id if it was set
425
+		if ($page_id) {
426
+			$current_request_uri = add_query_arg('page_id', $page_id, $current_request_uri);
427
+		}
428
+		// remove slashes and ?
429
+		$current_request_uri = trim($current_request_uri, '?/');
430
+		// is current request URI part of the known full reg page URL ?
431
+		return ! empty($current_request_uri) && strpos($reg_page_url, $current_request_uri) !== false;
432
+	}
433
+
434
+
435
+
436
+	/**
437
+	 *    run
438
+	 *
439
+	 * @access    public
440
+	 * @param WP_Query $WP_Query
441
+	 * @return    void
442
+	 * @throws \EE_Error
443
+	 */
444
+	public static function init($WP_Query)
445
+	{
446
+		EED_Single_Page_Checkout::instance()->run($WP_Query);
447
+	}
448
+
449
+
450
+
451
+	/**
452
+	 *    _initialize - initial module setup
453
+	 *
454
+	 * @access    private
455
+	 * @throws EE_Error
456
+	 * @return    void
457
+	 */
458
+	private function _initialize()
459
+	{
460
+		// ensure SPCO doesn't run twice
461
+		if (EED_Single_Page_Checkout::$_initialized) {
462
+			return;
463
+		}
464
+		try {
465
+			$this->_verify_session();
466
+			// setup the EE_Checkout object
467
+			$this->checkout = $this->_initialize_checkout();
468
+			// filter checkout
469
+			$this->checkout = apply_filters('FHEE__EED_Single_Page_Checkout___initialize__checkout', $this->checkout);
470
+			// get the $_GET
471
+			$this->_get_request_vars();
472
+			if ($this->_block_bots()) {
473
+				return;
474
+			}
475
+			// filter continue_reg
476
+			$this->checkout->continue_reg = apply_filters('FHEE__EED_Single_Page_Checkout__init___continue_reg', true, $this->checkout);
477
+			// load the reg steps array
478
+			if ( ! $this->_load_and_instantiate_reg_steps()) {
479
+				EED_Single_Page_Checkout::$_initialized = true;
480
+				return;
481
+			}
482
+			// set the current step
483
+			$this->checkout->set_current_step($this->checkout->step);
484
+			// and the next step
485
+			$this->checkout->set_next_step();
486
+			// verify that everything has been setup correctly
487
+			if ( ! ($this->_verify_transaction_and_get_registrations() && $this->_final_verifications())) {
488
+				EED_Single_Page_Checkout::$_initialized = true;
489
+				return;
490
+			}
491
+			// lock the transaction
492
+			$this->checkout->transaction->lock();
493
+			// make sure all of our cached objects are added to their respective model entity mappers
494
+			$this->checkout->refresh_all_entities();
495
+			// set amount owing
496
+			$this->checkout->amount_owing = $this->checkout->transaction->remaining();
497
+			// initialize each reg step, which gives them the chance to potentially alter the process
498
+			$this->_initialize_reg_steps();
499
+			// DEBUG LOG
500
+			//$this->checkout->log( __CLASS__, __FUNCTION__, __LINE__ );
501
+			// get reg form
502
+			if( ! $this->_check_form_submission()) {
503
+				EED_Single_Page_Checkout::$_initialized = true;
504
+				return;
505
+			}
506
+			// checkout the action!!!
507
+			$this->_process_form_action();
508
+			// add some style and make it dance
509
+			$this->add_styles_and_scripts();
510
+			// kk... SPCO has successfully run
511
+			EED_Single_Page_Checkout::$_initialized = true;
512
+			// set no cache headers and constants
513
+			EE_System::do_not_cache();
514
+			// add anchor
515
+			add_action('loop_start', array($this, 'set_checkout_anchor'), 1);
516
+			// remove transaction lock
517
+			add_action('shutdown', array($this, 'unlock_transaction'), 1);
518
+		} catch (Exception $e) {
519
+			EE_Error::add_error($e->getMessage(), __FILE__, __FUNCTION__, __LINE__);
520
+		}
521
+	}
522
+
523
+
524
+
525
+	/**
526
+	 *    _verify_session
527
+	 * checks that the session is valid and not expired
528
+	 *
529
+	 * @access    private
530
+	 * @throws EE_Error
531
+	 */
532
+	private function _verify_session()
533
+	{
534
+		if ( ! EE_Registry::instance()->SSN instanceof EE_Session) {
535
+			throw new EE_Error(__('The EE_Session class could not be loaded.', 'event_espresso'));
536
+		}
537
+		// is session still valid ?
538
+		if (EE_Registry::instance()->SSN->expired() && EE_Registry::instance()->REQ->get('e_reg_url_link', '') === '') {
539
+			$this->checkout = new EE_Checkout();
540
+			EE_Registry::instance()->SSN->reset_cart();
541
+			EE_Registry::instance()->SSN->reset_checkout();
542
+			EE_Registry::instance()->SSN->reset_transaction();
543
+			EE_Error::add_attention(EE_Registry::$i18n_js_strings['registration_expiration_notice'], __FILE__,
544
+				__FUNCTION__, __LINE__);
545
+			EE_Registry::instance()->SSN->reset_expired();
546
+		}
547
+	}
548
+
549
+
550
+
551
+	/**
552
+	 *    _initialize_checkout
553
+	 * loads and instantiates EE_Checkout
554
+	 *
555
+	 * @access    private
556
+	 * @throws EE_Error
557
+	 * @return EE_Checkout
558
+	 */
559
+	private function _initialize_checkout()
560
+	{
561
+		// look in session for existing checkout
562
+		/** @type EE_Checkout $checkout */
563
+		$checkout = EE_Registry::instance()->SSN->checkout();
564
+		// verify
565
+		if ( ! $checkout instanceof EE_Checkout) {
566
+			// instantiate EE_Checkout object for handling the properties of the current checkout process
567
+			$checkout = EE_Registry::instance()->load_file(SPCO_INC_PATH, 'EE_Checkout', 'class', array(), false);
568
+		} else {
569
+			if ($checkout->current_step->is_final_step() && $checkout->exit_spco() === true) {
570
+				$this->unlock_transaction();
571
+				wp_safe_redirect($checkout->redirect_url);
572
+				exit();
573
+			}
574
+		}
575
+		$checkout = apply_filters('FHEE__EED_Single_Page_Checkout___initialize_checkout__checkout', $checkout);
576
+		// verify again
577
+		if ( ! $checkout instanceof EE_Checkout) {
578
+			throw new EE_Error(__('The EE_Checkout class could not be loaded.', 'event_espresso'));
579
+		}
580
+		// reset anything that needs a clean slate for each request
581
+		$checkout->reset_for_current_request();
582
+		return $checkout;
583
+	}
584
+
585
+
586
+
587
+	/**
588
+	 *    _get_request_vars
589
+	 *
590
+	 * @access    private
591
+	 * @return    void
592
+	 * @throws \EE_Error
593
+	 */
594
+	private function _get_request_vars()
595
+	{
596
+		// load classes
597
+		EED_Single_Page_Checkout::load_request_handler();
598
+		//make sure this request is marked as belonging to EE
599
+		EE_Registry::instance()->REQ->set_espresso_page(true);
600
+		// which step is being requested ?
601
+		$this->checkout->step = EE_Registry::instance()->REQ->get('step', $this->_get_first_step());
602
+		// which step is being edited ?
603
+		$this->checkout->edit_step = EE_Registry::instance()->REQ->get('edit_step', '');
604
+		// and what we're doing on the current step
605
+		$this->checkout->action = EE_Registry::instance()->REQ->get('action', 'display_spco_reg_step');
606
+		// timestamp
607
+		$this->checkout->uts = EE_Registry::instance()->REQ->get('uts', 0);
608
+		// returning to edit ?
609
+		$this->checkout->reg_url_link = EE_Registry::instance()->REQ->get('e_reg_url_link', '');
610
+		// or some other kind of revisit ?
611
+		$this->checkout->revisit = EE_Registry::instance()->REQ->get('revisit', false);
612
+		// and whether or not to generate a reg form for this request
613
+		$this->checkout->generate_reg_form = EE_Registry::instance()->REQ->get('generate_reg_form', true);        // TRUE 	FALSE
614
+		// and whether or not to process a reg form submission for this request
615
+		$this->checkout->process_form_submission = EE_Registry::instance()->REQ->get(
616
+			'process_form_submission',
617
+			$this->checkout->action === 'process_reg_step'
618
+		); // TRUE 	FALSE
619
+		$this->checkout->process_form_submission = $this->checkout->action !== 'display_spco_reg_step'
620
+			? $this->checkout->process_form_submission
621
+			: false;        // TRUE 	FALSE
622
+		// $this->_display_request_vars();
623
+	}
624
+
625
+
626
+
627
+	/**
628
+	 *  _display_request_vars
629
+	 *
630
+	 * @access    protected
631
+	 * @return    void
632
+	 */
633
+	protected function _display_request_vars()
634
+	{
635
+		if ( ! WP_DEBUG) {
636
+			return;
637
+		}
638
+		EEH_Debug_Tools::printr($_REQUEST, '$_REQUEST', __FILE__, __LINE__);
639
+		EEH_Debug_Tools::printr($this->checkout->step, '$this->checkout->step', __FILE__, __LINE__);
640
+		EEH_Debug_Tools::printr($this->checkout->edit_step, '$this->checkout->edit_step', __FILE__, __LINE__);
641
+		EEH_Debug_Tools::printr($this->checkout->action, '$this->checkout->action', __FILE__, __LINE__);
642
+		EEH_Debug_Tools::printr($this->checkout->reg_url_link, '$this->checkout->reg_url_link', __FILE__, __LINE__);
643
+		EEH_Debug_Tools::printr($this->checkout->revisit, '$this->checkout->revisit', __FILE__, __LINE__);
644
+		EEH_Debug_Tools::printr($this->checkout->generate_reg_form, '$this->checkout->generate_reg_form', __FILE__, __LINE__);
645
+		EEH_Debug_Tools::printr($this->checkout->process_form_submission, '$this->checkout->process_form_submission', __FILE__, __LINE__);
646
+	}
647
+
648
+
649
+
650
+	/**
651
+	 * _block_bots
652
+	 * checks that the incoming request has either of the following set:
653
+	 *  a uts (unix timestamp) which indicates that the request was redirected from the Ticket Selector
654
+	 *  a REG URL Link, which indicates that the request is a return visit to SPCO for a valid TXN
655
+	 * so if you're not coming from the Ticket Selector nor returning for a valid IP...
656
+	 * then where you coming from man?
657
+	 *
658
+	 * @return boolean
659
+	 */
660
+	private function _block_bots()
661
+	{
662
+		$invalid_checkout_access = \EED_Invalid_Checkout_Access::getInvalidCheckoutAccess();
663
+		if ($invalid_checkout_access->checkoutAccessIsInvalid($this->checkout)) {
664
+			return true;
665
+		}
666
+		return false;
667
+	}
668
+
669
+
670
+
671
+	/**
672
+	 *    _get_first_step
673
+	 *  gets slug for first step in $_reg_steps_array
674
+	 *
675
+	 * @access    private
676
+	 * @throws EE_Error
677
+	 * @return    string
678
+	 */
679
+	private function _get_first_step()
680
+	{
681
+		$first_step = reset(EED_Single_Page_Checkout::$_reg_steps_array);
682
+		return isset($first_step['slug']) ? $first_step['slug'] : 'attendee_information';
683
+	}
684
+
685
+
686
+
687
+	/**
688
+	 *    _load_and_instantiate_reg_steps
689
+	 *  instantiates each reg step based on the loaded reg_steps array
690
+	 *
691
+	 * @access    private
692
+	 * @throws EE_Error
693
+	 * @return    bool
694
+	 */
695
+	private function _load_and_instantiate_reg_steps()
696
+	{
697
+		// have reg_steps already been instantiated ?
698
+		if (
699
+			empty($this->checkout->reg_steps)
700
+			|| apply_filters('FHEE__Single_Page_Checkout__load_reg_steps__reload_reg_steps', false, $this->checkout)
701
+		) {
702
+			// if not, then loop through raw reg steps array
703
+			foreach (EED_Single_Page_Checkout::$_reg_steps_array as $order => $reg_step) {
704
+				if ( ! $this->_load_and_instantiate_reg_step($reg_step, $order)) {
705
+					return false;
706
+				}
707
+			}
708
+			EE_Registry::instance()->CFG->registration->skip_reg_confirmation = true;
709
+			EE_Registry::instance()->CFG->registration->reg_confirmation_last = true;
710
+			// skip the registration_confirmation page ?
711
+			if (EE_Registry::instance()->CFG->registration->skip_reg_confirmation) {
712
+				// just remove it from the reg steps array
713
+				$this->checkout->remove_reg_step('registration_confirmation', false);
714
+			} else if (
715
+				isset($this->checkout->reg_steps['registration_confirmation'])
716
+				&& EE_Registry::instance()->CFG->registration->reg_confirmation_last
717
+			) {
718
+				// set the order to something big like 100
719
+				$this->checkout->set_reg_step_order('registration_confirmation', 100);
720
+			}
721
+			// filter the array for good luck
722
+			$this->checkout->reg_steps = apply_filters(
723
+				'FHEE__Single_Page_Checkout__load_reg_steps__reg_steps',
724
+				$this->checkout->reg_steps
725
+			);
726
+			// finally re-sort based on the reg step class order properties
727
+			$this->checkout->sort_reg_steps();
728
+		} else {
729
+			foreach ($this->checkout->reg_steps as $reg_step) {
730
+				// set all current step stati to FALSE
731
+				$reg_step->set_is_current_step(false);
732
+			}
733
+		}
734
+		if (empty($this->checkout->reg_steps)) {
735
+			EE_Error::add_error(__('No Reg Steps were loaded..', 'event_espresso'), __FILE__, __FUNCTION__, __LINE__);
736
+			return false;
737
+		}
738
+		// make reg step details available to JS
739
+		$this->checkout->set_reg_step_JSON_info();
740
+		return true;
741
+	}
742
+
743
+
744
+
745
+	/**
746
+	 *     _load_and_instantiate_reg_step
747
+	 *
748
+	 * @access    private
749
+	 * @param array $reg_step
750
+	 * @param int   $order
751
+	 * @return bool
752
+	 */
753
+	private function _load_and_instantiate_reg_step($reg_step = array(), $order = 0)
754
+	{
755
+		// we need a file_path, class_name, and slug to add a reg step
756
+		if (isset($reg_step['file_path'], $reg_step['class_name'], $reg_step['slug'])) {
757
+			// if editing a specific step, but this is NOT that step... (and it's not the 'finalize_registration' step)
758
+			if (
759
+				$this->checkout->reg_url_link
760
+				&& $this->checkout->step !== $reg_step['slug']
761
+				&& $reg_step['slug'] !== 'finalize_registration'
762
+			) {
763
+				return true;
764
+			}
765
+			// instantiate step class using file path and class name
766
+			$reg_step_obj = EE_Registry::instance()->load_file(
767
+				$reg_step['file_path'],
768
+				$reg_step['class_name'],
769
+				'class',
770
+				$this->checkout,
771
+				false
772
+			);
773
+			// did we gets the goods ?
774
+			if ($reg_step_obj instanceof EE_SPCO_Reg_Step) {
775
+				// set reg step order based on config
776
+				$reg_step_obj->set_order($order);
777
+				// add instantiated reg step object to the master reg steps array
778
+				$this->checkout->add_reg_step($reg_step_obj);
779
+			} else {
780
+				EE_Error::add_error(
781
+					__('The current step could not be set.', 'event_espresso'),
782
+					__FILE__, __FUNCTION__, __LINE__
783
+				);
784
+				return false;
785
+			}
786
+		} else {
787
+			if (WP_DEBUG) {
788
+				EE_Error::add_error(
789
+					sprintf(
790
+						__('A registration step could not be loaded. One or more of the following data points is invalid:%4$s%5$sFile Path: %1$s%6$s%5$sClass Name: %2$s%6$s%5$sSlug: %3$s%6$s%7$s', 'event_espresso'),
791
+						isset($reg_step['file_path']) ? $reg_step['file_path'] : '',
792
+						isset($reg_step['class_name']) ? $reg_step['class_name'] : '',
793
+						isset($reg_step['slug']) ? $reg_step['slug'] : '',
794
+						'<ul>',
795
+						'<li>',
796
+						'</li>',
797
+						'</ul>'
798
+					),
799
+					__FILE__, __FUNCTION__, __LINE__
800
+				);
801
+			}
802
+			return false;
803
+		}
804
+		return true;
805
+	}
806
+
807
+
808
+
809
+	/**
810
+	 * _verify_transaction_and_get_registrations
811
+	 *
812
+	 * @access private
813
+	 * @return bool
814
+	 */
815
+	private function _verify_transaction_and_get_registrations()
816
+	{
817
+		// was there already a valid transaction in the checkout from the session ?
818
+		if ( ! $this->checkout->transaction instanceof EE_Transaction) {
819
+			// get transaction from db or session
820
+			$this->checkout->transaction = $this->checkout->reg_url_link && ! is_admin()
821
+				? $this->_get_transaction_and_cart_for_previous_visit()
822
+				: $this->_get_cart_for_current_session_and_setup_new_transaction();
823
+			if ( ! $this->checkout->transaction instanceof EE_Transaction) {
824
+				EE_Error::add_error(
825
+					__('Your Registration and Transaction information could not be retrieved from the db.',
826
+						'event_espresso'),
827
+					__FILE__, __FUNCTION__, __LINE__
828
+				);
829
+				$this->checkout->transaction = EE_Transaction::new_instance();
830
+				// add some style and make it dance
831
+				$this->add_styles_and_scripts();
832
+				EED_Single_Page_Checkout::$_initialized = true;
833
+				return false;
834
+			}
835
+			// and the registrations for the transaction
836
+			$this->_get_registrations($this->checkout->transaction);
837
+		}
838
+		return true;
839
+	}
840
+
841
+
842
+
843
+	/**
844
+	 * _get_transaction_and_cart_for_previous_visit
845
+	 *
846
+	 * @access private
847
+	 * @return mixed EE_Transaction|NULL
848
+	 */
849
+	private function _get_transaction_and_cart_for_previous_visit()
850
+	{
851
+		/** @var $TXN_model EEM_Transaction */
852
+		$TXN_model = EE_Registry::instance()->load_model('Transaction');
853
+		// because the reg_url_link is present in the request, this is a return visit to SPCO, so we'll get the transaction data from the db
854
+		$transaction = $TXN_model->get_transaction_from_reg_url_link($this->checkout->reg_url_link);
855
+		// verify transaction
856
+		if ($transaction instanceof EE_Transaction) {
857
+			// and get the cart that was used for that transaction
858
+			$this->checkout->cart = $this->_get_cart_for_transaction($transaction);
859
+			return $transaction;
860
+		} else {
861
+			EE_Error::add_error(__('Your Registration and Transaction information could not be retrieved from the db.', 'event_espresso'), __FILE__, __FUNCTION__, __LINE__);
862
+			return null;
863
+		}
864
+	}
865
+
866
+
867
+
868
+	/**
869
+	 * _get_cart_for_transaction
870
+	 *
871
+	 * @access private
872
+	 * @param EE_Transaction $transaction
873
+	 * @return EE_Cart
874
+	 */
875
+	private function _get_cart_for_transaction($transaction)
876
+	{
877
+		return $this->checkout->get_cart_for_transaction($transaction);
878
+	}
879
+
880
+
881
+
882
+	/**
883
+	 * get_cart_for_transaction
884
+	 *
885
+	 * @access public
886
+	 * @param EE_Transaction $transaction
887
+	 * @return EE_Cart
888
+	 */
889
+	public function get_cart_for_transaction(EE_Transaction $transaction)
890
+	{
891
+		return $this->checkout->get_cart_for_transaction($transaction);
892
+	}
893
+
894
+
895
+
896
+	/**
897
+	 * _get_transaction_and_cart_for_current_session
898
+	 *    generates a new EE_Transaction object and adds it to the $_transaction property.
899
+	 *
900
+	 * @access private
901
+	 * @return EE_Transaction
902
+	 * @throws \EE_Error
903
+	 */
904
+	private function _get_cart_for_current_session_and_setup_new_transaction()
905
+	{
906
+		//  if there's no transaction, then this is the FIRST visit to SPCO
907
+		// so load up the cart ( passing nothing for the TXN because it doesn't exist yet )
908
+		$this->checkout->cart = $this->_get_cart_for_transaction(null);
909
+		// and then create a new transaction
910
+		$transaction = $this->_initialize_transaction();
911
+		// verify transaction
912
+		if ($transaction instanceof EE_Transaction) {
913
+			// save it so that we have an ID for other objects to use
914
+			$transaction->save();
915
+			// and save TXN data to the cart
916
+			$this->checkout->cart->get_grand_total()->save_this_and_descendants_to_txn($transaction->ID());
917
+		} else {
918
+			EE_Error::add_error(__('A Valid Transaction could not be initialized.', 'event_espresso'), __FILE__, __FUNCTION__, __LINE__);
919
+		}
920
+		return $transaction;
921
+	}
922
+
923
+
924
+
925
+	/**
926
+	 *    generates a new EE_Transaction object and adds it to the $_transaction property.
927
+	 *
928
+	 * @access private
929
+	 * @return mixed EE_Transaction|NULL
930
+	 */
931
+	private function _initialize_transaction()
932
+	{
933
+		try {
934
+			// ensure cart totals have been calculated
935
+			$this->checkout->cart->get_grand_total()->recalculate_total_including_taxes();
936
+			// grab the cart grand total
937
+			$cart_total = $this->checkout->cart->get_cart_grand_total();
938
+			// create new TXN
939
+			$transaction = EE_Transaction::new_instance(
940
+				array(
941
+					'TXN_reg_steps' => $this->checkout->initialize_txn_reg_steps_array(),
942
+					'TXN_total'     => $cart_total > 0 ? $cart_total : 0,
943
+					'TXN_paid'      => 0,
944
+					'STS_ID'        => EEM_Transaction::failed_status_code,
945
+				)
946
+			);
947
+			// save it so that we have an ID for other objects to use
948
+			$transaction->save();
949
+			// set cron job for following up on TXNs after their session has expired
950
+			EE_Cron_Tasks::schedule_expired_transaction_check(
951
+				EE_Registry::instance()->SSN->expiration() + 1,
952
+				$transaction->ID()
953
+			);
954
+			return $transaction;
955
+		} catch (Exception $e) {
956
+			EE_Error::add_error($e->getMessage(), __FILE__, __FUNCTION__, __LINE__);
957
+		}
958
+		return null;
959
+	}
960
+
961
+
962
+
963
+	/**
964
+	 * _get_registrations
965
+	 *
966
+	 * @access private
967
+	 * @param EE_Transaction $transaction
968
+	 * @return void
969
+	 * @throws \EventEspresso\core\exceptions\InvalidEntityException
970
+	 * @throws \EE_Error
971
+	 */
972
+	private function _get_registrations(EE_Transaction $transaction)
973
+	{
974
+		// first step: grab the registrants  { : o
975
+		$registrations = $transaction->registrations($this->checkout->reg_cache_where_params, true);
976
+		// verify registrations have been set
977
+		if (empty($registrations)) {
978
+			// if no cached registrations, then check the db
979
+			$registrations = $transaction->registrations($this->checkout->reg_cache_where_params, false);
980
+			// still nothing ? well as long as this isn't a revisit
981
+			if (empty($registrations) && ! $this->checkout->revisit) {
982
+				// generate new registrations from scratch
983
+				$registrations = $this->_initialize_registrations($transaction);
984
+			}
985
+		}
986
+		// sort by their original registration order
987
+		usort($registrations, array('EED_Single_Page_Checkout', 'sort_registrations_by_REG_count'));
988
+		// then loop thru the array
989
+		foreach ($registrations as $registration) {
990
+			// verify each registration
991
+			if ($registration instanceof EE_Registration) {
992
+				// we display all attendee info for the primary registrant
993
+				if ($this->checkout->reg_url_link === $registration->reg_url_link()
994
+					&& $registration->is_primary_registrant()
995
+				) {
996
+					$this->checkout->primary_revisit = true;
997
+					break;
998
+				} else if ($this->checkout->revisit
999
+						   && $this->checkout->reg_url_link !== $registration->reg_url_link()
1000
+				) {
1001
+					// but hide info if it doesn't belong to you
1002
+					$transaction->clear_cache('Registration', $registration->ID());
1003
+				}
1004
+				$this->checkout->set_reg_status_updated($registration->ID(), false);
1005
+			}
1006
+		}
1007
+	}
1008
+
1009
+
1010
+
1011
+	/**
1012
+	 *    adds related EE_Registration objects for each ticket in the cart to the current EE_Transaction object
1013
+	 *
1014
+	 * @access private
1015
+	 * @param EE_Transaction $transaction
1016
+	 * @return    array
1017
+	 * @throws \EventEspresso\core\exceptions\InvalidEntityException
1018
+	 * @throws \EE_Error
1019
+	 */
1020
+	private function _initialize_registrations(EE_Transaction $transaction)
1021
+	{
1022
+		$att_nmbr = 0;
1023
+		$registrations = array();
1024
+		if ($transaction instanceof EE_Transaction) {
1025
+			/** @type EE_Registration_Processor $registration_processor */
1026
+			$registration_processor = EE_Registry::instance()->load_class('Registration_Processor');
1027
+			$this->checkout->total_ticket_count = $this->checkout->cart->all_ticket_quantity_count();
1028
+			// now let's add the cart items to the $transaction
1029
+			foreach ($this->checkout->cart->get_tickets() as $line_item) {
1030
+				//do the following for each ticket of this type they selected
1031
+				for ($x = 1; $x <= $line_item->quantity(); $x++) {
1032
+					$att_nmbr++;
1033
+					/** @var EventEspresso\core\services\commands\registration\CreateRegistrationCommand $CreateRegistrationCommand */
1034
+					$CreateRegistrationCommand = EE_Registry::instance()
1035
+															->create(
1036
+																'EventEspresso\core\services\commands\registration\CreateRegistrationCommand',
1037
+																array(
1038
+																	$transaction,
1039
+																	$line_item,
1040
+																	$att_nmbr,
1041
+																	$this->checkout->total_ticket_count,
1042
+																)
1043
+															);
1044
+					// override capabilities for frontend registrations
1045
+					if ( ! is_admin()) {
1046
+						$CreateRegistrationCommand->setCapCheck(
1047
+							new PublicCapabilities('', 'create_new_registration')
1048
+						);
1049
+					}
1050
+					$registration = EE_Registry::instance()->BUS->execute($CreateRegistrationCommand);
1051
+					if ( ! $registration instanceof EE_Registration) {
1052
+						throw new InvalidEntityException($registration, 'EE_Registration');
1053
+					}
1054
+					$registrations[ $registration->ID() ] = $registration;
1055
+				}
1056
+			}
1057
+			$registration_processor->fix_reg_final_price_rounding_issue($transaction);
1058
+		}
1059
+		return $registrations;
1060
+	}
1061
+
1062
+
1063
+
1064
+	/**
1065
+	 * sorts registrations by REG_count
1066
+	 *
1067
+	 * @access public
1068
+	 * @param EE_Registration $reg_A
1069
+	 * @param EE_Registration $reg_B
1070
+	 * @return int
1071
+	 */
1072
+	public static function sort_registrations_by_REG_count(EE_Registration $reg_A, EE_Registration $reg_B)
1073
+	{
1074
+		// this shouldn't ever happen within the same TXN, but oh well
1075
+		if ($reg_A->count() === $reg_B->count()) {
1076
+			return 0;
1077
+		}
1078
+		return ($reg_A->count() > $reg_B->count()) ? 1 : -1;
1079
+	}
1080
+
1081
+
1082
+
1083
+	/**
1084
+	 *    _final_verifications
1085
+	 * just makes sure that everything is set up correctly before proceeding
1086
+	 *
1087
+	 * @access    private
1088
+	 * @return    bool
1089
+	 * @throws \EE_Error
1090
+	 */
1091
+	private function _final_verifications()
1092
+	{
1093
+		// filter checkout
1094
+		$this->checkout = apply_filters('FHEE__EED_Single_Page_Checkout___final_verifications__checkout', $this->checkout);
1095
+		//verify that current step is still set correctly
1096
+		if ( ! $this->checkout->current_step instanceof EE_SPCO_Reg_Step) {
1097
+			EE_Error::add_error(
1098
+				__('We\'re sorry but the registration process can not proceed because one or more registration steps were not setup correctly. Please refresh the page and try again or contact support.', 'event_espresso'),
1099
+				__FILE__,
1100
+				__FUNCTION__,
1101
+				__LINE__
1102
+			);
1103
+			return false;
1104
+		}
1105
+		// if returning to SPCO, then verify that primary registrant is set
1106
+		if ( ! empty($this->checkout->reg_url_link)) {
1107
+			$valid_registrant = $this->checkout->transaction->primary_registration();
1108
+			if ( ! $valid_registrant instanceof EE_Registration) {
1109
+				EE_Error::add_error(
1110
+					__('We\'re sorry but there appears to be an error with the "reg_url_link" or the primary registrant for this transaction. Please refresh the page and try again or contact support.', 'event_espresso'),
1111
+					__FILE__,
1112
+					__FUNCTION__,
1113
+					__LINE__
1114
+				);
1115
+				return false;
1116
+			}
1117
+			$valid_registrant = null;
1118
+			foreach ($this->checkout->transaction->registrations($this->checkout->reg_cache_where_params) as $registration) {
1119
+				if (
1120
+					$registration instanceof EE_Registration
1121
+					&& $registration->reg_url_link() === $this->checkout->reg_url_link
1122
+				) {
1123
+					$valid_registrant = $registration;
1124
+				}
1125
+			}
1126
+			if ( ! $valid_registrant instanceof EE_Registration) {
1127
+				// hmmm... maybe we have the wrong session because the user is opening multiple tabs ?
1128
+				if (EED_Single_Page_Checkout::$_checkout_verified) {
1129
+					// clear the session, mark the checkout as unverified, and try again
1130
+					EE_Registry::instance()->SSN->clear_session();
1131
+					EED_Single_Page_Checkout::$_initialized = false;
1132
+					EED_Single_Page_Checkout::$_checkout_verified = false;
1133
+					$this->_initialize();
1134
+					EE_Error::reset_notices();
1135
+					return false;
1136
+				}
1137
+				EE_Error::add_error(
1138
+					__('We\'re sorry but there appears to be an error with the "reg_url_link" or the transaction itself. Please refresh the page and try again or contact support.', 'event_espresso'),
1139
+					__FILE__,
1140
+					__FUNCTION__,
1141
+					__LINE__
1142
+				);
1143
+				return false;
1144
+			}
1145
+		}
1146
+		// now that things have been kinda sufficiently verified,
1147
+		// let's add the checkout to the session so that's available other systems
1148
+		EE_Registry::instance()->SSN->set_checkout($this->checkout);
1149
+		return true;
1150
+	}
1151
+
1152
+
1153
+
1154
+	/**
1155
+	 *    _initialize_reg_steps
1156
+	 * first makes sure that EE_Transaction_Processor::set_reg_step_initiated() is called as required
1157
+	 * then loops thru all of the active reg steps and calls the initialize_reg_step() method
1158
+	 *
1159
+	 * @access    private
1160
+	 * @param bool $reinitializing
1161
+	 * @throws \EE_Error
1162
+	 */
1163
+	private function _initialize_reg_steps($reinitializing = false)
1164
+	{
1165
+		$this->checkout->set_reg_step_initiated($this->checkout->current_step);
1166
+		// loop thru all steps to call their individual "initialize" methods and set i18n strings for JS
1167
+		foreach ($this->checkout->reg_steps as $reg_step) {
1168
+			if ( ! $reg_step->initialize_reg_step()) {
1169
+				// if not initialized then maybe this step is being removed...
1170
+				if ( ! $reinitializing && $reg_step->is_current_step()) {
1171
+					// if it was the current step, then we need to start over here
1172
+					$this->_initialize_reg_steps(true);
1173
+					return;
1174
+				}
1175
+				continue;
1176
+			}
1177
+			// add css and JS for current step
1178
+			$reg_step->enqueue_styles_and_scripts();
1179
+			// i18n
1180
+			$reg_step->translate_js_strings();
1181
+			if ($reg_step->is_current_step()) {
1182
+				// the text that appears on the reg step form submit button
1183
+				$reg_step->set_submit_button_text();
1184
+			}
1185
+		}
1186
+		// dynamically creates hook point like: AHEE__Single_Page_Checkout___initialize_reg_step__attendee_information
1187
+		do_action("AHEE__Single_Page_Checkout___initialize_reg_step__{$this->checkout->current_step->slug()}", $this->checkout->current_step);
1188
+	}
1189
+
1190
+
1191
+
1192
+	/**
1193
+	 * _check_form_submission
1194
+	 *
1195
+	 * @access private
1196
+	 * @return boolean
1197
+	 */
1198
+	private function _check_form_submission()
1199
+	{
1200
+		//does this request require the reg form to be generated ?
1201
+		if ($this->checkout->generate_reg_form) {
1202
+			// ever heard that song by Blue Rodeo ?
1203
+			try {
1204
+				$this->checkout->current_step->reg_form = $this->checkout->current_step->generate_reg_form();
1205
+				// if not displaying a form, then check for form submission
1206
+				if (
1207
+					$this->checkout->process_form_submission
1208
+					&& $this->checkout->current_step->reg_form->was_submitted()
1209
+				) {
1210
+					// clear out any old data in case this step is being run again
1211
+					$this->checkout->current_step->set_valid_data(array());
1212
+					// capture submitted form data
1213
+					$this->checkout->current_step->reg_form->receive_form_submission(
1214
+						apply_filters('FHEE__Single_Page_Checkout___check_form_submission__request_params', EE_Registry::instance()->REQ->params(), $this->checkout)
1215
+					);
1216
+					// validate submitted form data
1217
+					if ( ! $this->checkout->continue_reg || ! $this->checkout->current_step->reg_form->is_valid()) {
1218
+						// thou shall not pass !!!
1219
+						$this->checkout->continue_reg = false;
1220
+						// any form validation errors?
1221
+						if ($this->checkout->current_step->reg_form->submission_error_message() !== '') {
1222
+							$submission_error_messages = array();
1223
+							// bad, bad, bad registrant
1224
+							foreach ($this->checkout->current_step->reg_form->get_validation_errors_accumulated() as $validation_error) {
1225
+								if ($validation_error instanceof EE_Validation_Error) {
1226
+									$submission_error_messages[] = sprintf(
1227
+										__('%s : %s', 'event_espresso'),
1228
+										$validation_error->get_form_section()->html_label_text(),
1229
+										$validation_error->getMessage()
1230
+									);
1231
+								}
1232
+							}
1233
+							EE_Error::add_error(implode('<br />', $submission_error_messages), __FILE__, __FUNCTION__, __LINE__);
1234
+						}
1235
+						// well not really... what will happen is we'll just get redirected back to redo the current step
1236
+						$this->go_to_next_step();
1237
+						return false;
1238
+					}
1239
+				}
1240
+			} catch (EE_Error $e) {
1241
+				$e->get_error();
1242
+			}
1243
+		}
1244
+		return true;
1245
+	}
1246
+
1247
+
1248
+
1249
+	/**
1250
+	 * _process_action
1251
+	 *
1252
+	 * @access private
1253
+	 * @return void
1254
+	 * @throws \EE_Error
1255
+	 */
1256
+	private function _process_form_action()
1257
+	{
1258
+		// what cha wanna do?
1259
+		switch ($this->checkout->action) {
1260
+			// AJAX next step reg form
1261
+			case 'display_spco_reg_step' :
1262
+				$this->checkout->redirect = false;
1263
+				if (EE_Registry::instance()->REQ->ajax) {
1264
+					$this->checkout->json_response->set_reg_step_html($this->checkout->current_step->display_reg_form());
1265
+				}
1266
+				break;
1267
+			default :
1268
+				// meh... do one of those other steps first
1269
+				if ( ! empty($this->checkout->action) && is_callable(array($this->checkout->current_step, $this->checkout->action))) {
1270
+					// dynamically creates hook point like: AHEE__Single_Page_Checkout__before_attendee_information__process_reg_step
1271
+					do_action("AHEE__Single_Page_Checkout__before_{$this->checkout->current_step->slug()}__{$this->checkout->action}", $this->checkout->current_step);
1272
+					// call action on current step
1273
+					if (call_user_func(array($this->checkout->current_step, $this->checkout->action))) {
1274
+						// good registrant, you get to proceed
1275
+						if (
1276
+							$this->checkout->current_step->success_message() !== ''
1277
+							&& apply_filters(
1278
+								'FHEE__Single_Page_Checkout___process_form_action__display_success',
1279
+								false
1280
+							)
1281
+						) {
1282
+							EE_Error::add_success(
1283
+								$this->checkout->current_step->success_message()
1284
+								. '<br />' . $this->checkout->next_step->_instructions()
1285
+							);
1286
+						}
1287
+						// pack it up, pack it in...
1288
+						$this->_setup_redirect();
1289
+					}
1290
+					// dynamically creates hook point like: AHEE__Single_Page_Checkout__after_payment_options__process_reg_step
1291
+					do_action("AHEE__Single_Page_Checkout__after_{$this->checkout->current_step->slug()}__{$this->checkout->action}", $this->checkout->current_step);
1292
+				} else {
1293
+					EE_Error::add_error(
1294
+						sprintf(
1295
+							__('The requested form action "%s" does not exist for the current "%s" registration step.', 'event_espresso'),
1296
+							$this->checkout->action,
1297
+							$this->checkout->current_step->name()
1298
+						),
1299
+						__FILE__,
1300
+						__FUNCTION__,
1301
+						__LINE__
1302
+					);
1303
+				}
1304
+			// end default
1305
+		}
1306
+		// store our progress so far
1307
+		$this->checkout->stash_transaction_and_checkout();
1308
+		// advance to the next step! If you pass GO, collect $200
1309
+		$this->go_to_next_step();
1310
+	}
1311
+
1312
+
1313
+
1314
+	/**
1315
+	 *        add_styles_and_scripts
1316
+	 *
1317
+	 * @access        public
1318
+	 * @return        void
1319
+	 */
1320
+	public function add_styles_and_scripts()
1321
+	{
1322
+		// i18n
1323
+		$this->translate_js_strings();
1324
+		if ($this->checkout->admin_request) {
1325
+			add_action('admin_enqueue_scripts', array($this, 'enqueue_styles_and_scripts'), 10);
1326
+		} else {
1327
+			add_action('wp_enqueue_scripts', array($this, 'enqueue_styles_and_scripts'), 10);
1328
+		}
1329
+	}
1330
+
1331
+
1332
+
1333
+	/**
1334
+	 *        translate_js_strings
1335
+	 *
1336
+	 * @access        public
1337
+	 * @return        void
1338
+	 */
1339
+	public function translate_js_strings()
1340
+	{
1341
+		EE_Registry::$i18n_js_strings['revisit'] = $this->checkout->revisit;
1342
+		EE_Registry::$i18n_js_strings['e_reg_url_link'] = $this->checkout->reg_url_link;
1343
+		EE_Registry::$i18n_js_strings['server_error'] = __('An unknown error occurred on the server while attempting to process your request. Please refresh the page and try again or contact support.', 'event_espresso');
1344
+		EE_Registry::$i18n_js_strings['invalid_json_response'] = __('An invalid response was returned from the server while attempting to process your request. Please refresh the page and try again or contact support.', 'event_espresso');
1345
+		EE_Registry::$i18n_js_strings['validation_error'] = __('There appears to be a problem with the form validation configuration! Please check the admin settings or contact support.', 'event_espresso');
1346
+		EE_Registry::$i18n_js_strings['invalid_payment_method'] = __('There appears to be a problem with the payment method configuration! Please refresh the page and try again or contact support.', 'event_espresso');
1347
+		EE_Registry::$i18n_js_strings['reg_step_error'] = __('This registration step could not be completed. Please refresh the page and try again.', 'event_espresso');
1348
+		EE_Registry::$i18n_js_strings['invalid_coupon'] = __('We\'re sorry but that coupon code does not appear to be valid. If this is incorrect, please contact the site administrator.', 'event_espresso');
1349
+		EE_Registry::$i18n_js_strings['process_registration'] = sprintf(
1350
+			__('Please wait while we process your registration.%sDo not refresh the page or navigate away while this is happening.%sThank you for your patience.', 'event_espresso'),
1351
+			'<br/>',
1352
+			'<br/>'
1353
+		);
1354
+		EE_Registry::$i18n_js_strings['language'] = get_bloginfo('language');
1355
+		EE_Registry::$i18n_js_strings['EESID'] = EE_Registry::instance()->SSN->id();
1356
+		EE_Registry::$i18n_js_strings['currency'] = EE_Registry::instance()->CFG->currency;
1357
+		EE_Registry::$i18n_js_strings['datepicker_yearRange'] = '-150:+20';
1358
+		EE_Registry::$i18n_js_strings['timer_years'] = __('years', 'event_espresso');
1359
+		EE_Registry::$i18n_js_strings['timer_months'] = __('months', 'event_espresso');
1360
+		EE_Registry::$i18n_js_strings['timer_weeks'] = __('weeks', 'event_espresso');
1361
+		EE_Registry::$i18n_js_strings['timer_days'] = __('days', 'event_espresso');
1362
+		EE_Registry::$i18n_js_strings['timer_hours'] = __('hours', 'event_espresso');
1363
+		EE_Registry::$i18n_js_strings['timer_minutes'] = __('minutes', 'event_espresso');
1364
+		EE_Registry::$i18n_js_strings['timer_seconds'] = __('seconds', 'event_espresso');
1365
+		EE_Registry::$i18n_js_strings['timer_year'] = __('year', 'event_espresso');
1366
+		EE_Registry::$i18n_js_strings['timer_month'] = __('month', 'event_espresso');
1367
+		EE_Registry::$i18n_js_strings['timer_week'] = __('week', 'event_espresso');
1368
+		EE_Registry::$i18n_js_strings['timer_day'] = __('day', 'event_espresso');
1369
+		EE_Registry::$i18n_js_strings['timer_hour'] = __('hour', 'event_espresso');
1370
+		EE_Registry::$i18n_js_strings['timer_minute'] = __('minute', 'event_espresso');
1371
+		EE_Registry::$i18n_js_strings['timer_second'] = __('second', 'event_espresso');
1372
+		EE_Registry::$i18n_js_strings['registration_expiration_notice'] = sprintf(
1373
+			__(
1374
+				'%1$sWe\'re sorry, but your registration time has expired.%2$s%3$s%4$sIf you still wish to complete your registration, please return to the %5$sEvent List%6$sEvent List%7$s and reselect your tickets if available. Please except our apologies for any inconvenience this may have caused.%8$s',
1375
+				'event_espresso'
1376
+			),
1377
+			'<h4 class="important-notice">',
1378
+			'</h4>',
1379
+			'<br />',
1380
+			'<p>',
1381
+			'<a href="' . get_post_type_archive_link('espresso_events') . '" title="',
1382
+			'">',
1383
+			'</a>',
1384
+			'</p>'
1385
+		);
1386
+		EE_Registry::$i18n_js_strings['ajax_submit'] = apply_filters('FHEE__Single_Page_Checkout__translate_js_strings__ajax_submit', true);
1387
+		EE_Registry::$i18n_js_strings['session_extension'] = absint(
1388
+			apply_filters('FHEE__EE_Session__extend_expiration__seconds_added', 10 * MINUTE_IN_SECONDS)
1389
+		);
1390
+		EE_Registry::$i18n_js_strings['session_expiration'] = gmdate(
1391
+			'M d, Y H:i:s', EE_Registry::instance()->SSN->expiration() + (get_option('gmt_offset') * HOUR_IN_SECONDS)
1392
+		);
1393
+	}
1394
+
1395
+
1396
+
1397
+	/**
1398
+	 *    enqueue_styles_and_scripts
1399
+	 *
1400
+	 * @access        public
1401
+	 * @return        void
1402
+	 * @throws \EE_Error
1403
+	 */
1404
+	public function enqueue_styles_and_scripts()
1405
+	{
1406
+		// load css
1407
+		wp_register_style('single_page_checkout', SPCO_CSS_URL . 'single_page_checkout.css', array(), EVENT_ESPRESSO_VERSION);
1408
+		wp_enqueue_style('single_page_checkout');
1409
+		// load JS
1410
+		wp_register_script('jquery_plugin', EE_THIRD_PARTY_URL . 'jquery	.plugin.min.js', array('jquery'), '1.0.1', true);
1411
+		wp_register_script('jquery_countdown', EE_THIRD_PARTY_URL . 'jquery	.countdown.min.js', array('jquery_plugin'), '2.0.2', true);
1412
+		wp_register_script('single_page_checkout', SPCO_JS_URL . 'single_page_checkout.js', array('espresso_core', 'underscore', 'ee_form_section_validation', 'jquery_countdown'), EVENT_ESPRESSO_VERSION, true);
1413
+		if ($this->checkout->registration_form instanceof EE_Form_Section_Proper) {
1414
+			$this->checkout->registration_form->enqueue_js();
1415
+		}
1416
+		if ($this->checkout->current_step->reg_form instanceof EE_Form_Section_Proper) {
1417
+			$this->checkout->current_step->reg_form->enqueue_js();
1418
+		}
1419
+		wp_enqueue_script('single_page_checkout');
1420
+		/**
1421
+		 * global action hook for enqueueing styles and scripts with
1422
+		 * spco calls.
1423
+		 */
1424
+		do_action('AHEE__EED_Single_Page_Checkout__enqueue_styles_and_scripts', $this);
1425
+		/**
1426
+		 * dynamic action hook for enqueueing styles and scripts with spco calls.
1427
+		 * The hook will end up being something like AHEE__EED_Single_Page_Checkout__enqueue_styles_and_scripts__attendee_information
1428
+		 */
1429
+		do_action('AHEE__EED_Single_Page_Checkout__enqueue_styles_and_scripts__' . $this->checkout->current_step->slug(), $this);
1430
+	}
1431
+
1432
+
1433
+
1434
+	/**
1435
+	 *    display the Registration Single Page Checkout Form
1436
+	 *
1437
+	 * @access    private
1438
+	 * @return    void
1439
+	 * @throws \EE_Error
1440
+	 */
1441
+	private function _display_spco_reg_form()
1442
+	{
1443
+		// if registering via the admin, just display the reg form for the current step
1444
+		if ($this->checkout->admin_request) {
1445
+			EE_Registry::instance()->REQ->add_output($this->checkout->current_step->display_reg_form());
1446
+		} else {
1447
+			// add powered by EE msg
1448
+			add_action('AHEE__SPCO__reg_form_footer', array('EED_Single_Page_Checkout', 'display_registration_footer'));
1449
+			$empty_cart = count($this->checkout->transaction->registrations($this->checkout->reg_cache_where_params)) < 1
1450
+				? true
1451
+				: false;
1452
+			EE_Registry::$i18n_js_strings['empty_cart'] = $empty_cart;
1453
+			$cookies_not_set_msg = '';
1454
+			if ($empty_cart && ! isset($_COOKIE['ee_cookie_test'])) {
1455
+				$cookies_not_set_msg = apply_filters(
1456
+					'FHEE__Single_Page_Checkout__display_spco_reg_form__cookies_not_set_msg',
1457
+					sprintf(
1458
+						__(
1459
+							'%1$s%3$sIt appears your browser is not currently set to accept Cookies%4$s%5$sIn order to register for events, you need to enable cookies.%7$sIf you require assistance, then click the following link to learn how to %8$senable cookies%9$s%6$s%2$s',
1460
+							'event_espresso'
1461
+						),
1462
+						'<div class="ee-attention">',
1463
+						'</div>',
1464
+						'<h6 class="important-notice">',
1465
+						'</h6>',
1466
+						'<p>',
1467
+						'</p>',
1468
+						'<br />',
1469
+						'<a href="http://www.whatarecookies.com/enable.asp" target="_blank">',
1470
+						'</a>'
1471
+					)
1472
+				);
1473
+			}
1474
+			$this->checkout->registration_form = new EE_Form_Section_Proper(
1475
+				array(
1476
+					'name'            => 'single-page-checkout',
1477
+					'html_id'         => 'ee-single-page-checkout-dv',
1478
+					'layout_strategy' =>
1479
+						new EE_Template_Layout(
1480
+							array(
1481
+								'layout_template_file' => SPCO_TEMPLATES_PATH . 'registration_page_wrapper.template.php',
1482
+								'template_args'        => array(
1483
+									'empty_cart'              => $empty_cart,
1484
+									'revisit'                 => $this->checkout->revisit,
1485
+									'reg_steps'               => $this->checkout->reg_steps,
1486
+									'next_step'               => $this->checkout->next_step instanceof EE_SPCO_Reg_Step
1487
+										? $this->checkout->next_step->slug()
1488
+										: '',
1489
+									'cancel_page_url'         => $this->checkout->cancel_page_url,
1490
+									'empty_msg'               => apply_filters(
1491
+										'FHEE__Single_Page_Checkout__display_spco_reg_form__empty_msg',
1492
+										sprintf(
1493
+											__('You need to %1$sReturn to Events list%2$sselect at least one event%3$s before you can proceed with the registration process.',
1494
+												'event_espresso'),
1495
+											'<a href="' . get_post_type_archive_link('espresso_events') . '" title="',
1496
+											'">',
1497
+											'</a>'
1498
+										)
1499
+									),
1500
+									'cookies_not_set_msg'     => $cookies_not_set_msg,
1501
+									'registration_time_limit' => $this->checkout->get_registration_time_limit(),
1502
+									'session_expiration'      =>
1503
+										date('M d, Y H:i:s', EE_Registry::instance()->SSN->expiration() + (get_option('gmt_offset') * HOUR_IN_SECONDS)),
1504
+								),
1505
+							)
1506
+						),
1507
+				)
1508
+			);
1509
+			// load template and add to output sent that gets filtered into the_content()
1510
+			EE_Registry::instance()->REQ->add_output($this->checkout->registration_form->get_html());
1511
+		}
1512
+	}
1513
+
1514
+
1515
+
1516
+	/**
1517
+	 *    add_extra_finalize_registration_inputs
1518
+	 *
1519
+	 * @access    public
1520
+	 * @param $next_step
1521
+	 * @internal  param string $label
1522
+	 * @return void
1523
+	 */
1524
+	public function add_extra_finalize_registration_inputs($next_step)
1525
+	{
1526
+		if ($next_step === 'finalize_registration') {
1527
+			echo '<div id="spco-extra-finalize_registration-inputs-dv"></div>';
1528
+		}
1529
+	}
1530
+
1531
+
1532
+
1533
+	/**
1534
+	 *    display_registration_footer
1535
+	 *
1536
+	 * @access    public
1537
+	 * @return    string
1538
+	 */
1539
+	public static function display_registration_footer()
1540
+	{
1541
+		if (
1542
+		apply_filters(
1543
+			'FHEE__EE_Front__Controller__show_reg_footer',
1544
+			EE_Registry::instance()->CFG->admin->show_reg_footer
1545
+		)
1546
+		) {
1547
+			add_filter(
1548
+				'FHEE__EEH_Template__powered_by_event_espresso__url',
1549
+				function ($url) {
1550
+					return apply_filters('FHEE__EE_Front_Controller__registration_footer__url', $url);
1551
+				}
1552
+			);
1553
+			echo apply_filters(
1554
+				'FHEE__EE_Front_Controller__display_registration_footer',
1555
+				\EEH_Template::powered_by_event_espresso(
1556
+					'',
1557
+					'espresso-registration-footer-dv',
1558
+					array('utm_content' => 'registration_checkout')
1559
+				)
1560
+			);
1561
+		}
1562
+		return '';
1563
+	}
1564
+
1565
+
1566
+
1567
+	/**
1568
+	 *    unlock_transaction
1569
+	 *
1570
+	 * @access    public
1571
+	 * @return    void
1572
+	 * @throws \EE_Error
1573
+	 */
1574
+	public function unlock_transaction()
1575
+	{
1576
+		if ($this->checkout->transaction instanceof EE_Transaction) {
1577
+			$this->checkout->transaction->unlock();
1578
+		}
1579
+	}
1580
+
1581
+
1582
+
1583
+	/**
1584
+	 *        _setup_redirect
1585
+	 *
1586
+	 * @access    private
1587
+	 * @return void
1588
+	 */
1589
+	private function _setup_redirect()
1590
+	{
1591
+		if ($this->checkout->continue_reg && $this->checkout->next_step instanceof EE_SPCO_Reg_Step) {
1592
+			$this->checkout->redirect = true;
1593
+			if (empty($this->checkout->redirect_url)) {
1594
+				$this->checkout->redirect_url = $this->checkout->next_step->reg_step_url();
1595
+			}
1596
+			$this->checkout->redirect_url = apply_filters(
1597
+				'FHEE__EED_Single_Page_Checkout___setup_redirect__checkout_redirect_url',
1598
+				$this->checkout->redirect_url,
1599
+				$this->checkout
1600
+			);
1601
+		}
1602
+	}
1603
+
1604
+
1605
+
1606
+	/**
1607
+	 *   handle ajax message responses and redirects
1608
+	 *
1609
+	 * @access public
1610
+	 * @return void
1611
+	 * @throws \EE_Error
1612
+	 */
1613
+	public function go_to_next_step()
1614
+	{
1615
+		if (EE_Registry::instance()->REQ->ajax) {
1616
+			// capture contents of output buffer we started earlier in the request, and insert into JSON response
1617
+			$this->checkout->json_response->set_unexpected_errors(ob_get_clean());
1618
+		}
1619
+		$this->unlock_transaction();
1620
+		// just return for these conditions
1621
+		if (
1622
+			$this->checkout->admin_request
1623
+			|| $this->checkout->action === 'redirect_form'
1624
+			|| $this->checkout->action === 'update_checkout'
1625
+		) {
1626
+			return;
1627
+		}
1628
+		// AJAX response
1629
+		$this->_handle_json_response();
1630
+		// redirect to next step or the Thank You page
1631
+		$this->_handle_html_redirects();
1632
+		// hmmm... must be something wrong, so let's just display the form again !
1633
+		$this->_display_spco_reg_form();
1634
+	}
1635
+
1636
+
1637
+
1638
+	/**
1639
+	 *   _handle_json_response
1640
+	 *
1641
+	 * @access protected
1642
+	 * @return void
1643
+	 */
1644
+	protected function _handle_json_response()
1645
+	{
1646
+		// if this is an ajax request
1647
+		if (EE_Registry::instance()->REQ->ajax) {
1648
+			// DEBUG LOG
1649
+			//$this->checkout->log(
1650
+			//	__CLASS__, __FUNCTION__, __LINE__,
1651
+			//	array(
1652
+			//		'json_response_redirect_url' => $this->checkout->json_response->redirect_url(),
1653
+			//		'redirect'                   => $this->checkout->redirect,
1654
+			//		'continue_reg'               => $this->checkout->continue_reg,
1655
+			//	)
1656
+			//);
1657
+			$this->checkout->json_response->set_registration_time_limit(
1658
+				$this->checkout->get_registration_time_limit()
1659
+			);
1660
+			$this->checkout->json_response->set_payment_amount($this->checkout->amount_owing);
1661
+			// just send the ajax (
1662
+			$json_response = apply_filters(
1663
+				'FHEE__EE_Single_Page_Checkout__JSON_response',
1664
+				$this->checkout->json_response
1665
+			);
1666
+			echo $json_response;
1667
+			exit();
1668
+		}
1669
+	}
1670
+
1671
+
1672
+
1673
+	/**
1674
+	 *   _handle_redirects
1675
+	 *
1676
+	 * @access protected
1677
+	 * @return void
1678
+	 */
1679
+	protected function _handle_html_redirects()
1680
+	{
1681
+		// going somewhere ?
1682
+		if ($this->checkout->redirect && ! empty($this->checkout->redirect_url)) {
1683
+			// store notices in a transient
1684
+			EE_Error::get_notices(false, true, true);
1685
+			// DEBUG LOG
1686
+			//$this->checkout->log(
1687
+			//	__CLASS__, __FUNCTION__, __LINE__,
1688
+			//	array(
1689
+			//		'headers_sent' => headers_sent(),
1690
+			//		'redirect_url'     => $this->checkout->redirect_url,
1691
+			//		'headers_list'    => headers_list(),
1692
+			//	)
1693
+			//);
1694
+			wp_safe_redirect($this->checkout->redirect_url);
1695
+			exit();
1696
+		}
1697
+	}
1698
+
1699
+
1700
+
1701
+	/**
1702
+	 *   set_checkout_anchor
1703
+	 *
1704
+	 * @access public
1705
+	 * @return void
1706
+	 */
1707
+	public function set_checkout_anchor()
1708
+	{
1709
+		echo '<a id="checkout" style="float: left; margin-left: -999em;"></a>';
1710
+	}
1711 1711
 
1712 1712
 
1713 1713
 
Please login to merge, or discard this patch.
espresso.php 1 patch
Indentation   +215 added lines, -215 removed lines patch added patch discarded remove patch
@@ -1,5 +1,5 @@  discard block
 block discarded – undo
1 1
 <?php if ( ! defined('ABSPATH')) {
2
-    exit('No direct script access allowed');
2
+	exit('No direct script access allowed');
3 3
 }
4 4
 /*
5 5
   Plugin Name:		Event Espresso
@@ -40,239 +40,239 @@  discard block
 block discarded – undo
40 40
  * @since            4.0
41 41
  */
42 42
 if (function_exists('espresso_version')) {
43
-    /**
44
-     *    espresso_duplicate_plugin_error
45
-     *    displays if more than one version of EE is activated at the same time
46
-     */
47
-    function espresso_duplicate_plugin_error()
48
-    {
49
-        ?>
43
+	/**
44
+	 *    espresso_duplicate_plugin_error
45
+	 *    displays if more than one version of EE is activated at the same time
46
+	 */
47
+	function espresso_duplicate_plugin_error()
48
+	{
49
+		?>
50 50
         <div class="error">
51 51
             <p>
52 52
                 <?php echo esc_html__(
53
-                        'Can not run multiple versions of Event Espresso! One version has been automatically deactivated. Please verify that you have the correct version you want still active.',
54
-                        'event_espresso'
55
-                ); ?>
53
+						'Can not run multiple versions of Event Espresso! One version has been automatically deactivated. Please verify that you have the correct version you want still active.',
54
+						'event_espresso'
55
+				); ?>
56 56
             </p>
57 57
         </div>
58 58
         <?php
59
-        espresso_deactivate_plugin(plugin_basename(__FILE__));
60
-    }
59
+		espresso_deactivate_plugin(plugin_basename(__FILE__));
60
+	}
61 61
 
62
-    add_action('admin_notices', 'espresso_duplicate_plugin_error', 1);
62
+	add_action('admin_notices', 'espresso_duplicate_plugin_error', 1);
63 63
 } else {
64
-    define('EE_MIN_PHP_VER_REQUIRED', '5.3.9');
65
-    if ( ! version_compare(PHP_VERSION, EE_MIN_PHP_VER_REQUIRED, '>=')) {
66
-        /**
67
-         * espresso_minimum_php_version_error
68
-         *
69
-         * @return void
70
-         */
71
-        function espresso_minimum_php_version_error()
72
-        {
73
-            ?>
64
+	define('EE_MIN_PHP_VER_REQUIRED', '5.3.9');
65
+	if ( ! version_compare(PHP_VERSION, EE_MIN_PHP_VER_REQUIRED, '>=')) {
66
+		/**
67
+		 * espresso_minimum_php_version_error
68
+		 *
69
+		 * @return void
70
+		 */
71
+		function espresso_minimum_php_version_error()
72
+		{
73
+			?>
74 74
             <div class="error">
75 75
                 <p>
76 76
                     <?php
77
-                    printf(
78
-                            esc_html__(
79
-                                    'We\'re sorry, but Event Espresso requires PHP version %1$s or greater in order to operate. You are currently running version %2$s.%3$sIn order to update your version of PHP, you will need to contact your current hosting provider.%3$sFor information on stable PHP versions, please go to %4$s.',
80
-                                    'event_espresso'
81
-                            ),
82
-                            EE_MIN_PHP_VER_REQUIRED,
83
-                            PHP_VERSION,
84
-                            '<br/>',
85
-                            '<a href="http://php.net/downloads.php">http://php.net/downloads.php</a>'
86
-                    );
87
-                    ?>
77
+					printf(
78
+							esc_html__(
79
+									'We\'re sorry, but Event Espresso requires PHP version %1$s or greater in order to operate. You are currently running version %2$s.%3$sIn order to update your version of PHP, you will need to contact your current hosting provider.%3$sFor information on stable PHP versions, please go to %4$s.',
80
+									'event_espresso'
81
+							),
82
+							EE_MIN_PHP_VER_REQUIRED,
83
+							PHP_VERSION,
84
+							'<br/>',
85
+							'<a href="http://php.net/downloads.php">http://php.net/downloads.php</a>'
86
+					);
87
+					?>
88 88
                 </p>
89 89
             </div>
90 90
             <?php
91
-            espresso_deactivate_plugin(plugin_basename(__FILE__));
92
-        }
91
+			espresso_deactivate_plugin(plugin_basename(__FILE__));
92
+		}
93 93
 
94
-        add_action('admin_notices', 'espresso_minimum_php_version_error', 1);
95
-    } else {
96
-        /**
97
-         * espresso_version
98
-         * Returns the plugin version
99
-         *
100
-         * @return string
101
-         */
102
-        function espresso_version()
103
-        {
104
-            return apply_filters('FHEE__espresso__espresso_version', '4.9.26.rc.000');
105
-        }
94
+		add_action('admin_notices', 'espresso_minimum_php_version_error', 1);
95
+	} else {
96
+		/**
97
+		 * espresso_version
98
+		 * Returns the plugin version
99
+		 *
100
+		 * @return string
101
+		 */
102
+		function espresso_version()
103
+		{
104
+			return apply_filters('FHEE__espresso__espresso_version', '4.9.26.rc.000');
105
+		}
106 106
 
107
-        // define versions
108
-        define('EVENT_ESPRESSO_VERSION', espresso_version());
109
-        define('EE_MIN_WP_VER_REQUIRED', '4.1');
110
-        define('EE_MIN_WP_VER_RECOMMENDED', '4.4.2');
111
-        define('EE_MIN_PHP_VER_RECOMMENDED', '5.4.44');
112
-        define('EVENT_ESPRESSO_MAIN_FILE', __FILE__);
113
-        //used to be DIRECTORY_SEPARATOR, but that caused issues on windows
114
-        if ( ! defined('DS')) {
115
-            define('DS', '/');
116
-        }
117
-        if ( ! defined('PS')) {
118
-            define('PS', PATH_SEPARATOR);
119
-        }
120
-        if ( ! defined('SP')) {
121
-            define('SP', ' ');
122
-        }
123
-        if ( ! defined('EENL')) {
124
-            define('EENL', "\n");
125
-        }
126
-        define('EE_SUPPORT_EMAIL', '[email protected]');
127
-        // define the plugin directory and URL
128
-        define('EE_PLUGIN_BASENAME', plugin_basename(EVENT_ESPRESSO_MAIN_FILE));
129
-        define('EE_PLUGIN_DIR_PATH', plugin_dir_path(EVENT_ESPRESSO_MAIN_FILE));
130
-        define('EE_PLUGIN_DIR_URL', plugin_dir_url(EVENT_ESPRESSO_MAIN_FILE));
131
-        // main root folder paths
132
-        define('EE_ADMIN_PAGES', EE_PLUGIN_DIR_PATH . 'admin_pages' . DS);
133
-        define('EE_CORE', EE_PLUGIN_DIR_PATH . 'core' . DS);
134
-        define('EE_MODULES', EE_PLUGIN_DIR_PATH . 'modules' . DS);
135
-        define('EE_PUBLIC', EE_PLUGIN_DIR_PATH . 'public' . DS);
136
-        define('EE_SHORTCODES', EE_PLUGIN_DIR_PATH . 'shortcodes' . DS);
137
-        define('EE_WIDGETS', EE_PLUGIN_DIR_PATH . 'widgets' . DS);
138
-        define('EE_PAYMENT_METHODS', EE_PLUGIN_DIR_PATH . 'payment_methods' . DS);
139
-        define('EE_CAFF_PATH', EE_PLUGIN_DIR_PATH . 'caffeinated' . DS);
140
-        // core system paths
141
-        define('EE_ADMIN', EE_CORE . 'admin' . DS);
142
-        define('EE_CPTS', EE_CORE . 'CPTs' . DS);
143
-        define('EE_CLASSES', EE_CORE . 'db_classes' . DS);
144
-        define('EE_INTERFACES', EE_CORE . 'interfaces' . DS);
145
-        define('EE_BUSINESS', EE_CORE . 'business' . DS);
146
-        define('EE_MODELS', EE_CORE . 'db_models' . DS);
147
-        define('EE_HELPERS', EE_CORE . 'helpers' . DS);
148
-        define('EE_LIBRARIES', EE_CORE . 'libraries' . DS);
149
-        define('EE_TEMPLATES', EE_CORE . 'templates' . DS);
150
-        define('EE_THIRD_PARTY', EE_CORE . 'third_party_libs' . DS);
151
-        define('EE_GLOBAL_ASSETS', EE_TEMPLATES . 'global_assets' . DS);
152
-        define('EE_FORM_SECTIONS', EE_LIBRARIES . 'form_sections' . DS);
153
-        // gateways
154
-        define('EE_GATEWAYS', EE_MODULES . 'gateways' . DS);
155
-        define('EE_GATEWAYS_URL', EE_PLUGIN_DIR_URL . 'modules' . DS . 'gateways' . DS);
156
-        // asset URL paths
157
-        define('EE_TEMPLATES_URL', EE_PLUGIN_DIR_URL . 'core' . DS . 'templates' . DS);
158
-        define('EE_GLOBAL_ASSETS_URL', EE_TEMPLATES_URL . 'global_assets' . DS);
159
-        define('EE_IMAGES_URL', EE_GLOBAL_ASSETS_URL . 'images' . DS);
160
-        define('EE_THIRD_PARTY_URL', EE_PLUGIN_DIR_URL . 'core' . DS . 'third_party_libs' . DS);
161
-        define('EE_HELPERS_ASSETS', EE_PLUGIN_DIR_URL . 'core/helpers/assets/');
162
-        define('EE_LIBRARIES_URL', EE_PLUGIN_DIR_URL . 'core/libraries/');
163
-        // define upload paths
164
-        $uploads = wp_upload_dir();
165
-        // define the uploads directory and URL
166
-        define('EVENT_ESPRESSO_UPLOAD_DIR', $uploads['basedir'] . DS . 'espresso' . DS);
167
-        define('EVENT_ESPRESSO_UPLOAD_URL', $uploads['baseurl'] . DS . 'espresso' . DS);
168
-        // define the templates directory and URL
169
-        define('EVENT_ESPRESSO_TEMPLATE_DIR', $uploads['basedir'] . DS . 'espresso' . DS . 'templates' . DS);
170
-        define('EVENT_ESPRESSO_TEMPLATE_URL', $uploads['baseurl'] . DS . 'espresso' . DS . 'templates' . DS);
171
-        // define the gateway directory and URL
172
-        define('EVENT_ESPRESSO_GATEWAY_DIR', $uploads['basedir'] . DS . 'espresso' . DS . 'gateways' . DS);
173
-        define('EVENT_ESPRESSO_GATEWAY_URL', $uploads['baseurl'] . DS . 'espresso' . DS . 'gateways' . DS);
174
-        // languages folder/path
175
-        define('EE_LANGUAGES_SAFE_LOC', '..' . DS . 'uploads' . DS . 'espresso' . DS . 'languages' . DS);
176
-        define('EE_LANGUAGES_SAFE_DIR', EVENT_ESPRESSO_UPLOAD_DIR . 'languages' . DS);
177
-        //check for dompdf fonts in uploads
178
-        if (file_exists(EVENT_ESPRESSO_UPLOAD_DIR . 'fonts' . DS)) {
179
-            define('DOMPDF_FONT_DIR', EVENT_ESPRESSO_UPLOAD_DIR . 'fonts' . DS);
180
-        }
181
-        //ajax constants
182
-        define(
183
-                'EE_FRONT_AJAX',
184
-                isset($_REQUEST['ee_front_ajax']) || isset($_REQUEST['data']['ee_front_ajax']) ? true : false
185
-        );
186
-        define(
187
-                'EE_ADMIN_AJAX',
188
-                isset($_REQUEST['ee_admin_ajax']) || isset($_REQUEST['data']['ee_admin_ajax']) ? true : false
189
-        );
190
-        //just a handy constant occasionally needed for finding values representing infinity in the DB
191
-        //you're better to use this than its straight value (currently -1) in case you ever
192
-        //want to change its default value! or find when -1 means infinity
193
-        define('EE_INF_IN_DB', -1);
194
-        define('EE_INF', INF > (float)PHP_INT_MAX ? INF : PHP_INT_MAX);
195
-        define('EE_DEBUG', false);
196
-        /**
197
-         *    espresso_plugin_activation
198
-         *    adds a wp-option to indicate that EE has been activated via the WP admin plugins page
199
-         */
200
-        function espresso_plugin_activation()
201
-        {
202
-            update_option('ee_espresso_activation', true);
203
-        }
107
+		// define versions
108
+		define('EVENT_ESPRESSO_VERSION', espresso_version());
109
+		define('EE_MIN_WP_VER_REQUIRED', '4.1');
110
+		define('EE_MIN_WP_VER_RECOMMENDED', '4.4.2');
111
+		define('EE_MIN_PHP_VER_RECOMMENDED', '5.4.44');
112
+		define('EVENT_ESPRESSO_MAIN_FILE', __FILE__);
113
+		//used to be DIRECTORY_SEPARATOR, but that caused issues on windows
114
+		if ( ! defined('DS')) {
115
+			define('DS', '/');
116
+		}
117
+		if ( ! defined('PS')) {
118
+			define('PS', PATH_SEPARATOR);
119
+		}
120
+		if ( ! defined('SP')) {
121
+			define('SP', ' ');
122
+		}
123
+		if ( ! defined('EENL')) {
124
+			define('EENL', "\n");
125
+		}
126
+		define('EE_SUPPORT_EMAIL', '[email protected]');
127
+		// define the plugin directory and URL
128
+		define('EE_PLUGIN_BASENAME', plugin_basename(EVENT_ESPRESSO_MAIN_FILE));
129
+		define('EE_PLUGIN_DIR_PATH', plugin_dir_path(EVENT_ESPRESSO_MAIN_FILE));
130
+		define('EE_PLUGIN_DIR_URL', plugin_dir_url(EVENT_ESPRESSO_MAIN_FILE));
131
+		// main root folder paths
132
+		define('EE_ADMIN_PAGES', EE_PLUGIN_DIR_PATH . 'admin_pages' . DS);
133
+		define('EE_CORE', EE_PLUGIN_DIR_PATH . 'core' . DS);
134
+		define('EE_MODULES', EE_PLUGIN_DIR_PATH . 'modules' . DS);
135
+		define('EE_PUBLIC', EE_PLUGIN_DIR_PATH . 'public' . DS);
136
+		define('EE_SHORTCODES', EE_PLUGIN_DIR_PATH . 'shortcodes' . DS);
137
+		define('EE_WIDGETS', EE_PLUGIN_DIR_PATH . 'widgets' . DS);
138
+		define('EE_PAYMENT_METHODS', EE_PLUGIN_DIR_PATH . 'payment_methods' . DS);
139
+		define('EE_CAFF_PATH', EE_PLUGIN_DIR_PATH . 'caffeinated' . DS);
140
+		// core system paths
141
+		define('EE_ADMIN', EE_CORE . 'admin' . DS);
142
+		define('EE_CPTS', EE_CORE . 'CPTs' . DS);
143
+		define('EE_CLASSES', EE_CORE . 'db_classes' . DS);
144
+		define('EE_INTERFACES', EE_CORE . 'interfaces' . DS);
145
+		define('EE_BUSINESS', EE_CORE . 'business' . DS);
146
+		define('EE_MODELS', EE_CORE . 'db_models' . DS);
147
+		define('EE_HELPERS', EE_CORE . 'helpers' . DS);
148
+		define('EE_LIBRARIES', EE_CORE . 'libraries' . DS);
149
+		define('EE_TEMPLATES', EE_CORE . 'templates' . DS);
150
+		define('EE_THIRD_PARTY', EE_CORE . 'third_party_libs' . DS);
151
+		define('EE_GLOBAL_ASSETS', EE_TEMPLATES . 'global_assets' . DS);
152
+		define('EE_FORM_SECTIONS', EE_LIBRARIES . 'form_sections' . DS);
153
+		// gateways
154
+		define('EE_GATEWAYS', EE_MODULES . 'gateways' . DS);
155
+		define('EE_GATEWAYS_URL', EE_PLUGIN_DIR_URL . 'modules' . DS . 'gateways' . DS);
156
+		// asset URL paths
157
+		define('EE_TEMPLATES_URL', EE_PLUGIN_DIR_URL . 'core' . DS . 'templates' . DS);
158
+		define('EE_GLOBAL_ASSETS_URL', EE_TEMPLATES_URL . 'global_assets' . DS);
159
+		define('EE_IMAGES_URL', EE_GLOBAL_ASSETS_URL . 'images' . DS);
160
+		define('EE_THIRD_PARTY_URL', EE_PLUGIN_DIR_URL . 'core' . DS . 'third_party_libs' . DS);
161
+		define('EE_HELPERS_ASSETS', EE_PLUGIN_DIR_URL . 'core/helpers/assets/');
162
+		define('EE_LIBRARIES_URL', EE_PLUGIN_DIR_URL . 'core/libraries/');
163
+		// define upload paths
164
+		$uploads = wp_upload_dir();
165
+		// define the uploads directory and URL
166
+		define('EVENT_ESPRESSO_UPLOAD_DIR', $uploads['basedir'] . DS . 'espresso' . DS);
167
+		define('EVENT_ESPRESSO_UPLOAD_URL', $uploads['baseurl'] . DS . 'espresso' . DS);
168
+		// define the templates directory and URL
169
+		define('EVENT_ESPRESSO_TEMPLATE_DIR', $uploads['basedir'] . DS . 'espresso' . DS . 'templates' . DS);
170
+		define('EVENT_ESPRESSO_TEMPLATE_URL', $uploads['baseurl'] . DS . 'espresso' . DS . 'templates' . DS);
171
+		// define the gateway directory and URL
172
+		define('EVENT_ESPRESSO_GATEWAY_DIR', $uploads['basedir'] . DS . 'espresso' . DS . 'gateways' . DS);
173
+		define('EVENT_ESPRESSO_GATEWAY_URL', $uploads['baseurl'] . DS . 'espresso' . DS . 'gateways' . DS);
174
+		// languages folder/path
175
+		define('EE_LANGUAGES_SAFE_LOC', '..' . DS . 'uploads' . DS . 'espresso' . DS . 'languages' . DS);
176
+		define('EE_LANGUAGES_SAFE_DIR', EVENT_ESPRESSO_UPLOAD_DIR . 'languages' . DS);
177
+		//check for dompdf fonts in uploads
178
+		if (file_exists(EVENT_ESPRESSO_UPLOAD_DIR . 'fonts' . DS)) {
179
+			define('DOMPDF_FONT_DIR', EVENT_ESPRESSO_UPLOAD_DIR . 'fonts' . DS);
180
+		}
181
+		//ajax constants
182
+		define(
183
+				'EE_FRONT_AJAX',
184
+				isset($_REQUEST['ee_front_ajax']) || isset($_REQUEST['data']['ee_front_ajax']) ? true : false
185
+		);
186
+		define(
187
+				'EE_ADMIN_AJAX',
188
+				isset($_REQUEST['ee_admin_ajax']) || isset($_REQUEST['data']['ee_admin_ajax']) ? true : false
189
+		);
190
+		//just a handy constant occasionally needed for finding values representing infinity in the DB
191
+		//you're better to use this than its straight value (currently -1) in case you ever
192
+		//want to change its default value! or find when -1 means infinity
193
+		define('EE_INF_IN_DB', -1);
194
+		define('EE_INF', INF > (float)PHP_INT_MAX ? INF : PHP_INT_MAX);
195
+		define('EE_DEBUG', false);
196
+		/**
197
+		 *    espresso_plugin_activation
198
+		 *    adds a wp-option to indicate that EE has been activated via the WP admin plugins page
199
+		 */
200
+		function espresso_plugin_activation()
201
+		{
202
+			update_option('ee_espresso_activation', true);
203
+		}
204 204
 
205
-        register_activation_hook(EVENT_ESPRESSO_MAIN_FILE, 'espresso_plugin_activation');
206
-        /**
207
-         *    espresso_load_error_handling
208
-         *    this function loads EE's class for handling exceptions and errors
209
-         */
210
-        function espresso_load_error_handling()
211
-        {
212
-            // load debugging tools
213
-            if (WP_DEBUG === true && is_readable(EE_HELPERS . 'EEH_Debug_Tools.helper.php')) {
214
-                require_once(EE_HELPERS . 'EEH_Debug_Tools.helper.php');
215
-                EEH_Debug_Tools::instance();
216
-            }
217
-            // load error handling
218
-            if (is_readable(EE_CORE . 'EE_Error.core.php')) {
219
-                require_once(EE_CORE . 'EE_Error.core.php');
220
-            } else {
221
-                wp_die(esc_html__('The EE_Error core class could not be loaded.', 'event_espresso'));
222
-            }
223
-        }
205
+		register_activation_hook(EVENT_ESPRESSO_MAIN_FILE, 'espresso_plugin_activation');
206
+		/**
207
+		 *    espresso_load_error_handling
208
+		 *    this function loads EE's class for handling exceptions and errors
209
+		 */
210
+		function espresso_load_error_handling()
211
+		{
212
+			// load debugging tools
213
+			if (WP_DEBUG === true && is_readable(EE_HELPERS . 'EEH_Debug_Tools.helper.php')) {
214
+				require_once(EE_HELPERS . 'EEH_Debug_Tools.helper.php');
215
+				EEH_Debug_Tools::instance();
216
+			}
217
+			// load error handling
218
+			if (is_readable(EE_CORE . 'EE_Error.core.php')) {
219
+				require_once(EE_CORE . 'EE_Error.core.php');
220
+			} else {
221
+				wp_die(esc_html__('The EE_Error core class could not be loaded.', 'event_espresso'));
222
+			}
223
+		}
224 224
 
225
-        /**
226
-         *    espresso_load_required
227
-         *    given a class name and path, this function will load that file or throw an exception
228
-         *
229
-         * @param    string $classname
230
-         * @param    string $full_path_to_file
231
-         * @throws    EE_Error
232
-         */
233
-        function espresso_load_required($classname, $full_path_to_file)
234
-        {
235
-            static $error_handling_loaded = false;
236
-            if ( ! $error_handling_loaded) {
237
-                espresso_load_error_handling();
238
-                $error_handling_loaded = true;
239
-            }
240
-            if (is_readable($full_path_to_file)) {
241
-                require_once($full_path_to_file);
242
-            } else {
243
-                throw new EE_Error (
244
-                        sprintf(
245
-                                esc_html__(
246
-                                        'The %s class file could not be located or is not readable due to file permissions.',
247
-                                        'event_espresso'
248
-                                ),
249
-                                $classname
250
-                        )
251
-                );
252
-            }
253
-        }
225
+		/**
226
+		 *    espresso_load_required
227
+		 *    given a class name and path, this function will load that file or throw an exception
228
+		 *
229
+		 * @param    string $classname
230
+		 * @param    string $full_path_to_file
231
+		 * @throws    EE_Error
232
+		 */
233
+		function espresso_load_required($classname, $full_path_to_file)
234
+		{
235
+			static $error_handling_loaded = false;
236
+			if ( ! $error_handling_loaded) {
237
+				espresso_load_error_handling();
238
+				$error_handling_loaded = true;
239
+			}
240
+			if (is_readable($full_path_to_file)) {
241
+				require_once($full_path_to_file);
242
+			} else {
243
+				throw new EE_Error (
244
+						sprintf(
245
+								esc_html__(
246
+										'The %s class file could not be located or is not readable due to file permissions.',
247
+										'event_espresso'
248
+								),
249
+								$classname
250
+						)
251
+				);
252
+			}
253
+		}
254 254
 
255
-        espresso_load_required('EEH_Base', EE_CORE . 'helpers' . DS . 'EEH_Base.helper.php');
256
-        espresso_load_required('EEH_File', EE_CORE . 'helpers' . DS . 'EEH_File.helper.php');
257
-        espresso_load_required('EE_Bootstrap', EE_CORE . 'EE_Bootstrap.core.php');
258
-        new EE_Bootstrap();
259
-    }
255
+		espresso_load_required('EEH_Base', EE_CORE . 'helpers' . DS . 'EEH_Base.helper.php');
256
+		espresso_load_required('EEH_File', EE_CORE . 'helpers' . DS . 'EEH_File.helper.php');
257
+		espresso_load_required('EE_Bootstrap', EE_CORE . 'EE_Bootstrap.core.php');
258
+		new EE_Bootstrap();
259
+	}
260 260
 }
261 261
 if ( ! function_exists('espresso_deactivate_plugin')) {
262
-    /**
263
-     *    deactivate_plugin
264
-     * usage:  espresso_deactivate_plugin( plugin_basename( __FILE__ ));
265
-     *
266
-     * @access public
267
-     * @param string $plugin_basename - the results of plugin_basename( __FILE__ ) for the plugin's main file
268
-     * @return    void
269
-     */
270
-    function espresso_deactivate_plugin($plugin_basename = '')
271
-    {
272
-        if ( ! function_exists('deactivate_plugins')) {
273
-            require_once(ABSPATH . 'wp-admin/includes/plugin.php');
274
-        }
275
-        unset($_GET['activate'], $_REQUEST['activate']);
276
-        deactivate_plugins($plugin_basename);
277
-    }
262
+	/**
263
+	 *    deactivate_plugin
264
+	 * usage:  espresso_deactivate_plugin( plugin_basename( __FILE__ ));
265
+	 *
266
+	 * @access public
267
+	 * @param string $plugin_basename - the results of plugin_basename( __FILE__ ) for the plugin's main file
268
+	 * @return    void
269
+	 */
270
+	function espresso_deactivate_plugin($plugin_basename = '')
271
+	{
272
+		if ( ! function_exists('deactivate_plugins')) {
273
+			require_once(ABSPATH . 'wp-admin/includes/plugin.php');
274
+		}
275
+		unset($_GET['activate'], $_REQUEST['activate']);
276
+		deactivate_plugins($plugin_basename);
277
+	}
278 278
 }
Please login to merge, or discard this patch.
core/libraries/plugin_api/EE_Register_Addon.lib.php 2 patches
Indentation   +631 added lines, -631 removed lines patch added patch discarded remove patch
@@ -48,7 +48,7 @@  discard block
 block discarded – undo
48 48
 	protected static $_incompatible_addons = array(
49 49
 		'Multi_Event_Registration' => '2.0.11.rc.002',
50 50
 		'Promotions' => '1.0.0.rc.084',
51
-    );
51
+	);
52 52
 
53 53
 
54 54
 
@@ -219,659 +219,659 @@  discard block
 block discarded – undo
219 219
 	 */
220 220
 	public static function register( $addon_name = '', $setup_args = array() ) {
221 221
 		// required fields MUST be present, so let's make sure they are.
222
-        \EE_Register_Addon::_verify_parameters($addon_name, $setup_args);
223
-        // get class name for addon
222
+		\EE_Register_Addon::_verify_parameters($addon_name, $setup_args);
223
+		// get class name for addon
224 224
 		$class_name = \EE_Register_Addon::_parse_class_name($addon_name, $setup_args);
225 225
 		//setup $_settings array from incoming values.
226
-        $addon_settings = \EE_Register_Addon::_get_addon_settings($class_name, $setup_args);
227
-        // setup PUE
228
-        \EE_Register_Addon::_parse_pue_options($addon_name, $class_name, $setup_args);
229
-        // does this addon work with this version of core or WordPress ?
230
-        if ( ! \EE_Register_Addon::_addon_is_compatible($addon_name, $addon_settings) ) {
231
-            return;
226
+		$addon_settings = \EE_Register_Addon::_get_addon_settings($class_name, $setup_args);
227
+		// setup PUE
228
+		\EE_Register_Addon::_parse_pue_options($addon_name, $class_name, $setup_args);
229
+		// does this addon work with this version of core or WordPress ?
230
+		if ( ! \EE_Register_Addon::_addon_is_compatible($addon_name, $addon_settings) ) {
231
+			return;
232 232
 		}
233 233
 		// register namespaces
234
-        \EE_Register_Addon::_setup_namespaces($addon_settings);
235
-        // check if this is an activation request
236
-        if ( \EE_Register_Addon::_addon_activation($addon_name, $addon_settings)) {
237
-            // dont bother setting up the rest of the addon atm
238
-            return;
239
-        }
240
-        // we need cars
241
-        \EE_Register_Addon::_setup_autoloaders($addon_name);
242
-        // register new models and extensions
243
-        \EE_Register_Addon::_register_models_and_extensions($addon_name);
244
-        // setup DMS
245
-        \EE_Register_Addon::_register_data_migration_scripts($addon_name);
246
-        // if config_class is present let's register config.
247
-        \EE_Register_Addon::_register_config($addon_name);
248
-        // register admin pages
249
-        \EE_Register_Addon::_register_admin_pages($addon_name);
250
-        // add to list of modules to be registered
251
-        \EE_Register_Addon::_register_modules($addon_name);
252
-        // add to list of shortcodes to be registered
253
-        \EE_Register_Addon::_register_shortcodes($addon_name);
254
-        // add to list of widgets to be registered
255
-        \EE_Register_Addon::_register_widgets($addon_name);
256
-        // register capability related stuff.
257
-        \EE_Register_Addon::_register_capabilities($addon_name);
258
-        // any message type to register?
259
-        \EE_Register_Addon::_register_message_types($addon_name);
234
+		\EE_Register_Addon::_setup_namespaces($addon_settings);
235
+		// check if this is an activation request
236
+		if ( \EE_Register_Addon::_addon_activation($addon_name, $addon_settings)) {
237
+			// dont bother setting up the rest of the addon atm
238
+			return;
239
+		}
240
+		// we need cars
241
+		\EE_Register_Addon::_setup_autoloaders($addon_name);
242
+		// register new models and extensions
243
+		\EE_Register_Addon::_register_models_and_extensions($addon_name);
244
+		// setup DMS
245
+		\EE_Register_Addon::_register_data_migration_scripts($addon_name);
246
+		// if config_class is present let's register config.
247
+		\EE_Register_Addon::_register_config($addon_name);
248
+		// register admin pages
249
+		\EE_Register_Addon::_register_admin_pages($addon_name);
250
+		// add to list of modules to be registered
251
+		\EE_Register_Addon::_register_modules($addon_name);
252
+		// add to list of shortcodes to be registered
253
+		\EE_Register_Addon::_register_shortcodes($addon_name);
254
+		// add to list of widgets to be registered
255
+		\EE_Register_Addon::_register_widgets($addon_name);
256
+		// register capability related stuff.
257
+		\EE_Register_Addon::_register_capabilities($addon_name);
258
+		// any message type to register?
259
+		\EE_Register_Addon::_register_message_types($addon_name);
260 260
 		// any custom post type/ custom capabilities or default terms to register
261
-        \EE_Register_Addon::_register_custom_post_types($addon_name);
262
-        // and any payment methods
263
-        \EE_Register_Addon::_register_payment_methods($addon_name);
261
+		\EE_Register_Addon::_register_custom_post_types($addon_name);
262
+		// and any payment methods
263
+		\EE_Register_Addon::_register_payment_methods($addon_name);
264 264
 		// load and instantiate main addon class
265 265
 		\EE_Register_Addon::_load_and_init_addon_class($addon_name);
266 266
 	}
267 267
 
268 268
 
269 269
 
270
-    /**
271
-     * @param string $addon_name
272
-     * @param array  $setup_args
273
-     * @return void
274
-     * @throws \EE_Error
275
-     */
276
-    private static function _verify_parameters($addon_name, array $setup_args)
277
-    {
278
-        // required fields MUST be present, so let's make sure they are.
279
-        if (empty($addon_name) || ! is_array($setup_args)) {
280
-            throw new EE_Error(
281
-                __(
282
-                    'In order to register an EE_Addon with EE_Register_Addon::register(), you must include the "addon_name" (the name of the addon), and an array of arguments.',
283
-                    'event_espresso'
284
-                )
285
-            );
286
-        }
287
-        if ( ! isset($setup_args['main_file_path']) || empty($setup_args['main_file_path'])) {
288
-            throw new EE_Error(
289
-                sprintf(
290
-                    __(
291
-                        'When registering an addon, you didn\'t provide the "main_file_path", which is the full path to the main file loaded directly by Wordpress. You only provided %s',
292
-                        'event_espresso'
293
-                    ),
294
-                    implode(',', array_keys($setup_args))
295
-                )
296
-            );
297
-        }
298
-        // check that addon has not already been registered with that name
299
-        if (isset(self::$_settings[$addon_name]) && ! did_action('activate_plugin')) {
300
-            throw new EE_Error(
301
-                sprintf(
302
-                    __(
303
-                        'An EE_Addon with the name "%s" has already been registered and each EE_Addon requires a unique name.',
304
-                        'event_espresso'
305
-                    ),
306
-                    $addon_name
307
-                )
308
-            );
309
-        }
270
+	/**
271
+	 * @param string $addon_name
272
+	 * @param array  $setup_args
273
+	 * @return void
274
+	 * @throws \EE_Error
275
+	 */
276
+	private static function _verify_parameters($addon_name, array $setup_args)
277
+	{
278
+		// required fields MUST be present, so let's make sure they are.
279
+		if (empty($addon_name) || ! is_array($setup_args)) {
280
+			throw new EE_Error(
281
+				__(
282
+					'In order to register an EE_Addon with EE_Register_Addon::register(), you must include the "addon_name" (the name of the addon), and an array of arguments.',
283
+					'event_espresso'
284
+				)
285
+			);
286
+		}
287
+		if ( ! isset($setup_args['main_file_path']) || empty($setup_args['main_file_path'])) {
288
+			throw new EE_Error(
289
+				sprintf(
290
+					__(
291
+						'When registering an addon, you didn\'t provide the "main_file_path", which is the full path to the main file loaded directly by Wordpress. You only provided %s',
292
+						'event_espresso'
293
+					),
294
+					implode(',', array_keys($setup_args))
295
+				)
296
+			);
297
+		}
298
+		// check that addon has not already been registered with that name
299
+		if (isset(self::$_settings[$addon_name]) && ! did_action('activate_plugin')) {
300
+			throw new EE_Error(
301
+				sprintf(
302
+					__(
303
+						'An EE_Addon with the name "%s" has already been registered and each EE_Addon requires a unique name.',
304
+						'event_espresso'
305
+					),
306
+					$addon_name
307
+				)
308
+			);
309
+		}
310
+	}
311
+
312
+
313
+
314
+	/**
315
+	 * @param string $addon_name
316
+	 * @param array  $setup_args
317
+	 * @return string
318
+	 */
319
+	private static function _parse_class_name($addon_name, array $setup_args)
320
+	{
321
+		if (empty($setup_args['class_name'])) {
322
+			// generate one by first separating name with spaces
323
+			$class_name = str_replace(array('-', '_'), ' ', trim($addon_name));
324
+			//capitalize, then replace spaces with underscores
325
+			$class_name = str_replace(' ', '_', ucwords($class_name));
326
+		} else {
327
+			$class_name = $setup_args['class_name'];
328
+		}
329
+		return strpos($class_name, 'EE_') === 0 ? $class_name : 'EE_' . $class_name;
310 330
 	}
311 331
 
312 332
 
313 333
 
314
-    /**
315
-     * @param string $addon_name
316
-     * @param array  $setup_args
317
-     * @return string
318
-     */
319
-    private static function _parse_class_name($addon_name, array $setup_args)
320
-    {
321
-        if (empty($setup_args['class_name'])) {
322
-            // generate one by first separating name with spaces
323
-            $class_name = str_replace(array('-', '_'), ' ', trim($addon_name));
324
-            //capitalize, then replace spaces with underscores
325
-            $class_name = str_replace(' ', '_', ucwords($class_name));
326
-        } else {
327
-            $class_name = $setup_args['class_name'];
328
-        }
329
-        return strpos($class_name, 'EE_') === 0 ? $class_name : 'EE_' . $class_name;
330
-    }
331
-
332
-
333
-
334
-    /**
335
-     * @param string $class_name
336
-     * @param array  $setup_args
337
-     * @return array
338
-     */
339
-    private static function _get_addon_settings($class_name, array $setup_args)
340
-    {
341
-        //setup $_settings array from incoming values.
342
-        $addon_settings = array(
343
-            // generated from the addon name, changes something like "calendar" to "EE_Calendar"
344
-            'class_name'            => $class_name,
345
-            // the addon slug for use in URLs, etc
346
-            'plugin_slug'           => isset($setup_args['plugin_slug'])
347
-                ? (string)$setup_args['plugin_slug']
348
-                : '',
349
-            // page slug to be used when generating the "Settings" link on the WP plugin page
350
-            'plugin_action_slug'    => isset($setup_args['plugin_action_slug'])
351
-                ? (string)$setup_args['plugin_action_slug']
352
-                : '',
353
-            // the "software" version for the addon
354
-            'version'               => isset($setup_args['version'])
355
-                ? (string)$setup_args['version']
356
-                : '',
357
-            // the minimum version of EE Core that the addon will work with
358
-            'min_core_version'      => isset($setup_args['min_core_version'])
359
-                ? (string)$setup_args['min_core_version']
360
-                : '',
361
-            // the minimum version of WordPress that the addon will work with
362
-            'min_wp_version'        => isset($setup_args['min_wp_version'])
363
-                ? (string)$setup_args['min_wp_version']
364
-                : EE_MIN_WP_VER_REQUIRED,
365
-            // full server path to main file (file loaded directly by WP)
366
-            'main_file_path'        => isset($setup_args['main_file_path'])
367
-                ? (string)$setup_args['main_file_path']
368
-                : '',
369
-            // path to folder containing files for integrating with the EE core admin and/or setting up EE admin pages
370
-            'admin_path'            => isset($setup_args['admin_path'])
371
-                ? (string)$setup_args['admin_path'] : '',
372
-            // a method to be called when the EE Admin is first invoked, can be used for hooking into any admin page
373
-            'admin_callback'        => isset($setup_args['admin_callback'])
374
-                ? (string)$setup_args['admin_callback']
375
-                : '',
376
-            // the section name for this addon's configuration settings section (defaults to "addons")
377
-            'config_section'        => isset($setup_args['config_section'])
378
-                ? (string)$setup_args['config_section']
379
-                : 'addons',
380
-            // the class name for this addon's configuration settings object
381
-            'config_class'          => isset($setup_args['config_class'])
382
-                ? (string)$setup_args['config_class'] : '',
383
-            //the name given to the config for this addons' configuration settings object (optional)
384
-            'config_name'           => isset($setup_args['config_name'])
385
-                ? (string)$setup_args['config_name'] : '',
386
-            // an array of "class names" => "full server paths" for any classes that might be invoked by the addon
387
-            'autoloader_paths'      => isset($setup_args['autoloader_paths'])
388
-                ? (array)$setup_args['autoloader_paths']
389
-                : array(),
390
-            // an array of  "full server paths" for any folders containing classes that might be invoked by the addon
391
-            'autoloader_folders'    => isset($setup_args['autoloader_folders'])
392
-                ? (array)$setup_args['autoloader_folders']
393
-                : array(),
394
-            // array of full server paths to any EE_DMS data migration scripts used by the addon
395
-            'dms_paths'             => isset($setup_args['dms_paths'])
396
-                ? (array)$setup_args['dms_paths']
397
-                : array(),
398
-            // array of full server paths to any EED_Modules used by the addon
399
-            'module_paths'          => isset($setup_args['module_paths'])
400
-                ? (array)$setup_args['module_paths']
401
-                : array(),
402
-            // array of full server paths to any EES_Shortcodes used by the addon
403
-            'shortcode_paths'       => isset($setup_args['shortcode_paths'])
404
-                ? (array)$setup_args['shortcode_paths']
405
-                : array(),
406
-            // array of full server paths to any WP_Widgets used by the addon
407
-            'widget_paths'          => isset($setup_args['widget_paths'])
408
-                ? (array)$setup_args['widget_paths']
409
-                : array(),
410
-            // array of PUE options used by the addon
411
-            'pue_options'           => isset($setup_args['pue_options'])
412
-                ? (array)$setup_args['pue_options']
413
-                : array(),
414
-            'message_types'         => isset($setup_args['message_types'])
415
-                ? (array)$setup_args['message_types']
416
-                : array(),
417
-            'capabilities'          => isset($setup_args['capabilities'])
418
-                ? (array)$setup_args['capabilities']
419
-                : array(),
420
-            'capability_maps'       => isset($setup_args['capability_maps'])
421
-                ? (array)$setup_args['capability_maps']
422
-                : array(),
423
-            'model_paths'           => isset($setup_args['model_paths'])
424
-                ? (array)$setup_args['model_paths']
425
-                : array(),
426
-            'class_paths'           => isset($setup_args['class_paths'])
427
-                ? (array)$setup_args['class_paths']
428
-                : array(),
429
-            'model_extension_paths' => isset($setup_args['model_extension_paths'])
430
-                ? (array)$setup_args['model_extension_paths']
431
-                : array(),
432
-            'class_extension_paths' => isset($setup_args['class_extension_paths'])
433
-                ? (array)$setup_args['class_extension_paths']
434
-                : array(),
435
-            'custom_post_types'     => isset($setup_args['custom_post_types'])
436
-                ? (array)$setup_args['custom_post_types']
437
-                : array(),
438
-            'custom_taxonomies'     => isset($setup_args['custom_taxonomies'])
439
-                ? (array)$setup_args['custom_taxonomies']
440
-                : array(),
441
-            'payment_method_paths'  => isset($setup_args['payment_method_paths'])
442
-                ? (array)$setup_args['payment_method_paths']
443
-                : array(),
444
-            'default_terms'         => isset($setup_args['default_terms'])
445
-                ? (array)$setup_args['default_terms']
446
-                : array(),
447
-            // if not empty, inserts a new table row after this plugin's row on the WP Plugins page
448
-            // that can be used for adding upgrading/marketing info
449
-            'plugins_page_row'      => isset($setup_args['plugins_page_row'])
450
-                ? $setup_args['plugins_page_row']
451
-                : '',
452
-            'namespace'             => isset(
453
-                $setup_args['namespace'],
454
-                $setup_args['namespace']['FQNS'],
455
-                $setup_args['namespace']['DIR']
456
-            )
457
-                ? (array)$setup_args['namespace']
458
-                : array(),
459
-        );
460
-        // if plugin_action_slug is NOT set, but an admin page path IS set,
461
-        // then let's just use the plugin_slug since that will be used for linking to the admin page
462
-        $addon_settings['plugin_action_slug'] = empty($addon_settings['plugin_action_slug'])
463
-                                                && ! empty($addon_settings['admin_path'])
464
-            ? $addon_settings['plugin_slug']
465
-            : $addon_settings['plugin_action_slug'];
466
-        // full server path to main file (file loaded directly by WP)
467
-        $addon_settings['plugin_basename'] = plugin_basename($addon_settings['main_file_path']);
468
-        return $addon_settings;
334
+	/**
335
+	 * @param string $class_name
336
+	 * @param array  $setup_args
337
+	 * @return array
338
+	 */
339
+	private static function _get_addon_settings($class_name, array $setup_args)
340
+	{
341
+		//setup $_settings array from incoming values.
342
+		$addon_settings = array(
343
+			// generated from the addon name, changes something like "calendar" to "EE_Calendar"
344
+			'class_name'            => $class_name,
345
+			// the addon slug for use in URLs, etc
346
+			'plugin_slug'           => isset($setup_args['plugin_slug'])
347
+				? (string)$setup_args['plugin_slug']
348
+				: '',
349
+			// page slug to be used when generating the "Settings" link on the WP plugin page
350
+			'plugin_action_slug'    => isset($setup_args['plugin_action_slug'])
351
+				? (string)$setup_args['plugin_action_slug']
352
+				: '',
353
+			// the "software" version for the addon
354
+			'version'               => isset($setup_args['version'])
355
+				? (string)$setup_args['version']
356
+				: '',
357
+			// the minimum version of EE Core that the addon will work with
358
+			'min_core_version'      => isset($setup_args['min_core_version'])
359
+				? (string)$setup_args['min_core_version']
360
+				: '',
361
+			// the minimum version of WordPress that the addon will work with
362
+			'min_wp_version'        => isset($setup_args['min_wp_version'])
363
+				? (string)$setup_args['min_wp_version']
364
+				: EE_MIN_WP_VER_REQUIRED,
365
+			// full server path to main file (file loaded directly by WP)
366
+			'main_file_path'        => isset($setup_args['main_file_path'])
367
+				? (string)$setup_args['main_file_path']
368
+				: '',
369
+			// path to folder containing files for integrating with the EE core admin and/or setting up EE admin pages
370
+			'admin_path'            => isset($setup_args['admin_path'])
371
+				? (string)$setup_args['admin_path'] : '',
372
+			// a method to be called when the EE Admin is first invoked, can be used for hooking into any admin page
373
+			'admin_callback'        => isset($setup_args['admin_callback'])
374
+				? (string)$setup_args['admin_callback']
375
+				: '',
376
+			// the section name for this addon's configuration settings section (defaults to "addons")
377
+			'config_section'        => isset($setup_args['config_section'])
378
+				? (string)$setup_args['config_section']
379
+				: 'addons',
380
+			// the class name for this addon's configuration settings object
381
+			'config_class'          => isset($setup_args['config_class'])
382
+				? (string)$setup_args['config_class'] : '',
383
+			//the name given to the config for this addons' configuration settings object (optional)
384
+			'config_name'           => isset($setup_args['config_name'])
385
+				? (string)$setup_args['config_name'] : '',
386
+			// an array of "class names" => "full server paths" for any classes that might be invoked by the addon
387
+			'autoloader_paths'      => isset($setup_args['autoloader_paths'])
388
+				? (array)$setup_args['autoloader_paths']
389
+				: array(),
390
+			// an array of  "full server paths" for any folders containing classes that might be invoked by the addon
391
+			'autoloader_folders'    => isset($setup_args['autoloader_folders'])
392
+				? (array)$setup_args['autoloader_folders']
393
+				: array(),
394
+			// array of full server paths to any EE_DMS data migration scripts used by the addon
395
+			'dms_paths'             => isset($setup_args['dms_paths'])
396
+				? (array)$setup_args['dms_paths']
397
+				: array(),
398
+			// array of full server paths to any EED_Modules used by the addon
399
+			'module_paths'          => isset($setup_args['module_paths'])
400
+				? (array)$setup_args['module_paths']
401
+				: array(),
402
+			// array of full server paths to any EES_Shortcodes used by the addon
403
+			'shortcode_paths'       => isset($setup_args['shortcode_paths'])
404
+				? (array)$setup_args['shortcode_paths']
405
+				: array(),
406
+			// array of full server paths to any WP_Widgets used by the addon
407
+			'widget_paths'          => isset($setup_args['widget_paths'])
408
+				? (array)$setup_args['widget_paths']
409
+				: array(),
410
+			// array of PUE options used by the addon
411
+			'pue_options'           => isset($setup_args['pue_options'])
412
+				? (array)$setup_args['pue_options']
413
+				: array(),
414
+			'message_types'         => isset($setup_args['message_types'])
415
+				? (array)$setup_args['message_types']
416
+				: array(),
417
+			'capabilities'          => isset($setup_args['capabilities'])
418
+				? (array)$setup_args['capabilities']
419
+				: array(),
420
+			'capability_maps'       => isset($setup_args['capability_maps'])
421
+				? (array)$setup_args['capability_maps']
422
+				: array(),
423
+			'model_paths'           => isset($setup_args['model_paths'])
424
+				? (array)$setup_args['model_paths']
425
+				: array(),
426
+			'class_paths'           => isset($setup_args['class_paths'])
427
+				? (array)$setup_args['class_paths']
428
+				: array(),
429
+			'model_extension_paths' => isset($setup_args['model_extension_paths'])
430
+				? (array)$setup_args['model_extension_paths']
431
+				: array(),
432
+			'class_extension_paths' => isset($setup_args['class_extension_paths'])
433
+				? (array)$setup_args['class_extension_paths']
434
+				: array(),
435
+			'custom_post_types'     => isset($setup_args['custom_post_types'])
436
+				? (array)$setup_args['custom_post_types']
437
+				: array(),
438
+			'custom_taxonomies'     => isset($setup_args['custom_taxonomies'])
439
+				? (array)$setup_args['custom_taxonomies']
440
+				: array(),
441
+			'payment_method_paths'  => isset($setup_args['payment_method_paths'])
442
+				? (array)$setup_args['payment_method_paths']
443
+				: array(),
444
+			'default_terms'         => isset($setup_args['default_terms'])
445
+				? (array)$setup_args['default_terms']
446
+				: array(),
447
+			// if not empty, inserts a new table row after this plugin's row on the WP Plugins page
448
+			// that can be used for adding upgrading/marketing info
449
+			'plugins_page_row'      => isset($setup_args['plugins_page_row'])
450
+				? $setup_args['plugins_page_row']
451
+				: '',
452
+			'namespace'             => isset(
453
+				$setup_args['namespace'],
454
+				$setup_args['namespace']['FQNS'],
455
+				$setup_args['namespace']['DIR']
456
+			)
457
+				? (array)$setup_args['namespace']
458
+				: array(),
459
+		);
460
+		// if plugin_action_slug is NOT set, but an admin page path IS set,
461
+		// then let's just use the plugin_slug since that will be used for linking to the admin page
462
+		$addon_settings['plugin_action_slug'] = empty($addon_settings['plugin_action_slug'])
463
+												&& ! empty($addon_settings['admin_path'])
464
+			? $addon_settings['plugin_slug']
465
+			: $addon_settings['plugin_action_slug'];
466
+		// full server path to main file (file loaded directly by WP)
467
+		$addon_settings['plugin_basename'] = plugin_basename($addon_settings['main_file_path']);
468
+		return $addon_settings;
469 469
 	}
470 470
 
471 471
 
472 472
 
473
-    /**
474
-     * @param string $addon_name
475
-     * @param array  $addon_settings
476
-     * @return boolean
477
-     */
473
+	/**
474
+	 * @param string $addon_name
475
+	 * @param array  $addon_settings
476
+	 * @return boolean
477
+	 */
478 478
 	private static function _addon_is_compatible( $addon_name, array $addon_settings ) {
479
-        global $wp_version;
480
-        $incompatibility_message = '';
481
-        //check whether this addon version is compatible with EE core
482
-        if (
483
-            isset(EE_Register_Addon::$_incompatible_addons[$addon_name])
484
-            && ! self::_meets_min_core_version_requirement(
485
-                EE_Register_Addon::$_incompatible_addons[$addon_name],
486
-                $addon_settings['version']
487
-            )
488
-        ) {
489
-            $incompatibility_message = sprintf(
490
-                __(
491
-                    '%4$sIMPORTANT!%5$sThe Event Espresso "%1$s" addon is not compatible with this version of Event Espresso.%2$sPlease upgrade your "%1$s" addon to version %3$s or newer to resolve this issue.'
492
-                ),
493
-                $addon_name,
494
-                '<br />',
495
-                EE_Register_Addon::$_incompatible_addons[$addon_name],
496
-                '<span style="font-weight: bold; color: #D54E21;">',
497
-                '</span><br />'
498
-            );
499
-        } else if (
500
-            ! self::_meets_min_core_version_requirement($addon_settings['min_core_version'], espresso_version())
501
-        ) {
502
-            $incompatibility_message = sprintf(
503
-                __(
504
-                    '%5$sIMPORTANT!%6$sThe Event Espresso "%1$s" addon requires Event Espresso Core version "%2$s" or higher in order to run.%4$sYour version of Event Espresso Core is currently at "%3$s". Please upgrade Event Espresso Core first and then re-activate "%1$s".',
505
-                    'event_espresso'
506
-                ),
507
-                $addon_name,
508
-                self::_effective_version($addon_settings['min_core_version']),
509
-                self::_effective_version(espresso_version()),
510
-                '<br />',
511
-                '<span style="font-weight: bold; color: #D54E21;">',
512
-                '</span><br />'
513
-            );
514
-        } else if (version_compare($wp_version, $addon_settings['min_wp_version'], '<')) {
515
-            $incompatibility_message = sprintf(
516
-                __(
517
-                    '%4$sIMPORTANT!%5$sThe Event Espresso "%1$s" addon requires WordPress version "%2$s" or greater.%3$sPlease update your version of WordPress to use the "%1$s" addon and to keep your site secure.',
518
-                    'event_espresso'
519
-                ),
520
-                $addon_name,
521
-                $addon_settings['min_wp_version'],
522
-                '<br />',
523
-                '<span style="font-weight: bold; color: #D54E21;">',
524
-                '</span><br />'
525
-            );
526
-        }
527
-        if ( ! empty($incompatibility_message)) {
528
-            // remove 'activate' from the REQUEST
529
-            // so WP doesn't erroneously tell the user the plugin activated fine when it didn't
530
-            unset($_GET['activate'], $_REQUEST['activate']);
531
-            if (current_user_can('activate_plugins')) {
532
-                // show an error message indicating the plugin didn't activate properly
533
-                EE_Error::add_error($incompatibility_message, __FILE__, __FUNCTION__, __LINE__);
534
-            }
535
-            // BAIL FROM THE ADDON REGISTRATION PROCESS
536
-            return false;
537
-        }
538
-        // addon IS compatible
539
-        return true;
479
+		global $wp_version;
480
+		$incompatibility_message = '';
481
+		//check whether this addon version is compatible with EE core
482
+		if (
483
+			isset(EE_Register_Addon::$_incompatible_addons[$addon_name])
484
+			&& ! self::_meets_min_core_version_requirement(
485
+				EE_Register_Addon::$_incompatible_addons[$addon_name],
486
+				$addon_settings['version']
487
+			)
488
+		) {
489
+			$incompatibility_message = sprintf(
490
+				__(
491
+					'%4$sIMPORTANT!%5$sThe Event Espresso "%1$s" addon is not compatible with this version of Event Espresso.%2$sPlease upgrade your "%1$s" addon to version %3$s or newer to resolve this issue.'
492
+				),
493
+				$addon_name,
494
+				'<br />',
495
+				EE_Register_Addon::$_incompatible_addons[$addon_name],
496
+				'<span style="font-weight: bold; color: #D54E21;">',
497
+				'</span><br />'
498
+			);
499
+		} else if (
500
+			! self::_meets_min_core_version_requirement($addon_settings['min_core_version'], espresso_version())
501
+		) {
502
+			$incompatibility_message = sprintf(
503
+				__(
504
+					'%5$sIMPORTANT!%6$sThe Event Espresso "%1$s" addon requires Event Espresso Core version "%2$s" or higher in order to run.%4$sYour version of Event Espresso Core is currently at "%3$s". Please upgrade Event Espresso Core first and then re-activate "%1$s".',
505
+					'event_espresso'
506
+				),
507
+				$addon_name,
508
+				self::_effective_version($addon_settings['min_core_version']),
509
+				self::_effective_version(espresso_version()),
510
+				'<br />',
511
+				'<span style="font-weight: bold; color: #D54E21;">',
512
+				'</span><br />'
513
+			);
514
+		} else if (version_compare($wp_version, $addon_settings['min_wp_version'], '<')) {
515
+			$incompatibility_message = sprintf(
516
+				__(
517
+					'%4$sIMPORTANT!%5$sThe Event Espresso "%1$s" addon requires WordPress version "%2$s" or greater.%3$sPlease update your version of WordPress to use the "%1$s" addon and to keep your site secure.',
518
+					'event_espresso'
519
+				),
520
+				$addon_name,
521
+				$addon_settings['min_wp_version'],
522
+				'<br />',
523
+				'<span style="font-weight: bold; color: #D54E21;">',
524
+				'</span><br />'
525
+			);
526
+		}
527
+		if ( ! empty($incompatibility_message)) {
528
+			// remove 'activate' from the REQUEST
529
+			// so WP doesn't erroneously tell the user the plugin activated fine when it didn't
530
+			unset($_GET['activate'], $_REQUEST['activate']);
531
+			if (current_user_can('activate_plugins')) {
532
+				// show an error message indicating the plugin didn't activate properly
533
+				EE_Error::add_error($incompatibility_message, __FILE__, __FUNCTION__, __LINE__);
534
+			}
535
+			// BAIL FROM THE ADDON REGISTRATION PROCESS
536
+			return false;
537
+		}
538
+		// addon IS compatible
539
+		return true;
540 540
 	}
541 541
 
542 542
 
543 543
 
544
-    /**
545
-     * if plugin update engine is being used for auto-updates,
546
-     * then let's set that up now before going any further so that ALL addons can be updated
547
-     * (not needed if PUE is not being used)
548
-     *
549
-     * @param string $addon_name
550
-     * @param string $class_name
551
-     * @param array  $setup_args
552
-     * @return void
553
-     */
544
+	/**
545
+	 * if plugin update engine is being used for auto-updates,
546
+	 * then let's set that up now before going any further so that ALL addons can be updated
547
+	 * (not needed if PUE is not being used)
548
+	 *
549
+	 * @param string $addon_name
550
+	 * @param string $class_name
551
+	 * @param array  $setup_args
552
+	 * @return void
553
+	 */
554 554
 	private static function _parse_pue_options( $addon_name, $class_name, array $setup_args ) {
555
-        if ( ! empty($setup_args['pue_options'])) {
556
-            self::$_settings[$addon_name]['pue_options'] = array(
557
-                'pue_plugin_slug' => isset($setup_args['pue_options']['pue_plugin_slug'])
558
-                    ? (string)$setup_args['pue_options']['pue_plugin_slug']
559
-                    : 'espresso_' . strtolower($class_name),
560
-                'plugin_basename' => isset($setup_args['pue_options']['plugin_basename'])
561
-                    ? (string)$setup_args['pue_options']['plugin_basename']
562
-                    : plugin_basename($setup_args['main_file_path']),
563
-                'checkPeriod'     => isset($setup_args['pue_options']['checkPeriod'])
564
-                    ? (string)$setup_args['pue_options']['checkPeriod']
565
-                    : '24',
566
-                'use_wp_update'   => isset($setup_args['pue_options']['use_wp_update'])
567
-                    ? (string)$setup_args['pue_options']['use_wp_update']
568
-                    : false,
569
-            );
570
-            add_action(
571
-                'AHEE__EE_System__brew_espresso__after_pue_init',
572
-                array('EE_Register_Addon', 'load_pue_update')
573
-            );
574
-        }
555
+		if ( ! empty($setup_args['pue_options'])) {
556
+			self::$_settings[$addon_name]['pue_options'] = array(
557
+				'pue_plugin_slug' => isset($setup_args['pue_options']['pue_plugin_slug'])
558
+					? (string)$setup_args['pue_options']['pue_plugin_slug']
559
+					: 'espresso_' . strtolower($class_name),
560
+				'plugin_basename' => isset($setup_args['pue_options']['plugin_basename'])
561
+					? (string)$setup_args['pue_options']['plugin_basename']
562
+					: plugin_basename($setup_args['main_file_path']),
563
+				'checkPeriod'     => isset($setup_args['pue_options']['checkPeriod'])
564
+					? (string)$setup_args['pue_options']['checkPeriod']
565
+					: '24',
566
+				'use_wp_update'   => isset($setup_args['pue_options']['use_wp_update'])
567
+					? (string)$setup_args['pue_options']['use_wp_update']
568
+					: false,
569
+			);
570
+			add_action(
571
+				'AHEE__EE_System__brew_espresso__after_pue_init',
572
+				array('EE_Register_Addon', 'load_pue_update')
573
+			);
574
+		}
575 575
 	}
576 576
 
577 577
 
578 578
 
579
-    /**
580
-     * register namespaces right away before any other files or classes get loaded, but AFTER the version checks
581
-     *
582
-     * @param array $addon_settings
583
-     * @return void
584
-     */
585
-    private static function _setup_namespaces(array $addon_settings)
586
-    {
587
-        //
588
-        if (
589
-        isset(
590
-            $addon_settings['namespace'],
591
-            $addon_settings['namespace']['FQNS'],
592
-            $addon_settings['namespace']['DIR']
593
-        )
594
-        ) {
595
-            EE_Psr4AutoloaderInit::psr4_loader()->addNamespace(
596
-                $addon_settings['namespace']['FQNS'],
597
-                $addon_settings['namespace']['DIR']
598
-            );
599
-        }
600
-    }
601
-
602
-
603
-
604
-    /**
605
-     * @param string $addon_name
606
-     * @param array  $addon_settings
607
-     * @return bool
608
-     */
579
+	/**
580
+	 * register namespaces right away before any other files or classes get loaded, but AFTER the version checks
581
+	 *
582
+	 * @param array $addon_settings
583
+	 * @return void
584
+	 */
585
+	private static function _setup_namespaces(array $addon_settings)
586
+	{
587
+		//
588
+		if (
589
+		isset(
590
+			$addon_settings['namespace'],
591
+			$addon_settings['namespace']['FQNS'],
592
+			$addon_settings['namespace']['DIR']
593
+		)
594
+		) {
595
+			EE_Psr4AutoloaderInit::psr4_loader()->addNamespace(
596
+				$addon_settings['namespace']['FQNS'],
597
+				$addon_settings['namespace']['DIR']
598
+			);
599
+		}
600
+	}
601
+
602
+
603
+
604
+	/**
605
+	 * @param string $addon_name
606
+	 * @param array  $addon_settings
607
+	 * @return bool
608
+	 */
609 609
 	private static function _addon_activation( $addon_name, array $addon_settings ) {
610
-        // this is an activation request
611
-        if (did_action('activate_plugin')) {
612
-            //to find if THIS is the addon that was activated,
613
-            //just check if we have already registered it or not
614
-            //(as the newly-activated addon wasn't around the first time addons were registered)
615
-            if ( ! isset(self::$_settings[$addon_name])) {
616
-                self::$_settings[$addon_name] = $addon_settings;
617
-                $addon = self::_load_and_init_addon_class($addon_name);
618
-                $addon->set_activation_indicator_option();
619
-                // dont bother setting up the rest of the addon.
620
-                // we know it was just activated and the request will end soon
621
-            }
622
-            return true;
623
-        } else {
624
-            // make sure this was called in the right place!
625
-            if (
626
-                ! did_action('AHEE__EE_System__load_espresso_addons')
627
-                || did_action('AHEE__EE_System___detect_if_activation_or_upgrade__begin')
628
-            ) {
629
-                EE_Error::doing_it_wrong(
630
-                    __METHOD__,
631
-                    sprintf(
632
-                        __(
633
-                            'An attempt to register an EE_Addon named "%s" has failed because it was not registered at the correct time.  Please use the "AHEE__EE_System__load_espresso_addons" hook to register addons.',
634
-                            'event_espresso'
635
-                        ),
636
-                        $addon_name
637
-                    ),
638
-                    '4.3.0'
639
-                );
640
-            }
641
-            // make sure addon settings are set correctly without overwriting anything existing
642
-            if (isset(self::$_settings[$addon_name])) {
643
-                self::$_settings[$addon_name] += $addon_settings;
644
-            } else {
645
-                self::$_settings[$addon_name] = $addon_settings;
646
-            }
647
-        }
648
-        return false;
649
-    }
650
-
651
-
652
-
653
-    /**
654
-     * @param string $addon_name
655
-     * @return void
656
-     * @throws \EE_Error
657
-     */
658
-    private static function _setup_autoloaders($addon_name)
659
-    {
660
-        if ( ! empty(self::$_settings[$addon_name]['autoloader_paths'])) {
661
-            // setup autoloader for single file
662
-            EEH_Autoloader::instance()->register_autoloader(self::$_settings[$addon_name]['autoloader_paths']);
663
-        }
664
-        // setup autoloaders for folders
665
-        if ( ! empty(self::$_settings[$addon_name]['autoloader_folders'])) {
666
-            foreach ((array)self::$_settings[$addon_name]['autoloader_folders'] as $autoloader_folder) {
667
-                EEH_Autoloader::register_autoloaders_for_each_file_in_folder($autoloader_folder);
668
-            }
669
-        }
670
-    }
671
-
672
-
673
-
674
-    /**
675
-     * register new models and extensions
676
-     *
677
-     * @param string $addon_name
678
-     * @return void
679
-     * @throws \EE_Error
680
-     */
610
+		// this is an activation request
611
+		if (did_action('activate_plugin')) {
612
+			//to find if THIS is the addon that was activated,
613
+			//just check if we have already registered it or not
614
+			//(as the newly-activated addon wasn't around the first time addons were registered)
615
+			if ( ! isset(self::$_settings[$addon_name])) {
616
+				self::$_settings[$addon_name] = $addon_settings;
617
+				$addon = self::_load_and_init_addon_class($addon_name);
618
+				$addon->set_activation_indicator_option();
619
+				// dont bother setting up the rest of the addon.
620
+				// we know it was just activated and the request will end soon
621
+			}
622
+			return true;
623
+		} else {
624
+			// make sure this was called in the right place!
625
+			if (
626
+				! did_action('AHEE__EE_System__load_espresso_addons')
627
+				|| did_action('AHEE__EE_System___detect_if_activation_or_upgrade__begin')
628
+			) {
629
+				EE_Error::doing_it_wrong(
630
+					__METHOD__,
631
+					sprintf(
632
+						__(
633
+							'An attempt to register an EE_Addon named "%s" has failed because it was not registered at the correct time.  Please use the "AHEE__EE_System__load_espresso_addons" hook to register addons.',
634
+							'event_espresso'
635
+						),
636
+						$addon_name
637
+					),
638
+					'4.3.0'
639
+				);
640
+			}
641
+			// make sure addon settings are set correctly without overwriting anything existing
642
+			if (isset(self::$_settings[$addon_name])) {
643
+				self::$_settings[$addon_name] += $addon_settings;
644
+			} else {
645
+				self::$_settings[$addon_name] = $addon_settings;
646
+			}
647
+		}
648
+		return false;
649
+	}
650
+
651
+
652
+
653
+	/**
654
+	 * @param string $addon_name
655
+	 * @return void
656
+	 * @throws \EE_Error
657
+	 */
658
+	private static function _setup_autoloaders($addon_name)
659
+	{
660
+		if ( ! empty(self::$_settings[$addon_name]['autoloader_paths'])) {
661
+			// setup autoloader for single file
662
+			EEH_Autoloader::instance()->register_autoloader(self::$_settings[$addon_name]['autoloader_paths']);
663
+		}
664
+		// setup autoloaders for folders
665
+		if ( ! empty(self::$_settings[$addon_name]['autoloader_folders'])) {
666
+			foreach ((array)self::$_settings[$addon_name]['autoloader_folders'] as $autoloader_folder) {
667
+				EEH_Autoloader::register_autoloaders_for_each_file_in_folder($autoloader_folder);
668
+			}
669
+		}
670
+	}
671
+
672
+
673
+
674
+	/**
675
+	 * register new models and extensions
676
+	 *
677
+	 * @param string $addon_name
678
+	 * @return void
679
+	 * @throws \EE_Error
680
+	 */
681 681
 	private static function _register_models_and_extensions( $addon_name ) {
682
-        // register new models
683
-        if (
684
-            ! empty(self::$_settings[$addon_name]['model_paths'])
685
-            || ! empty(self::$_settings[$addon_name]['class_paths'])
686
-        ) {
687
-            EE_Register_Model::register(
688
-                $addon_name,
689
-                array(
690
-                    'model_paths' => self::$_settings[$addon_name]['model_paths'],
691
-                    'class_paths' => self::$_settings[$addon_name]['class_paths'],
692
-                )
693
-            );
694
-        }
695
-        // register model extensions
696
-        if (
697
-            ! empty(self::$_settings[$addon_name]['model_extension_paths'])
698
-            || ! empty(self::$_settings[$addon_name]['class_extension_paths'])
699
-        ) {
700
-            EE_Register_Model_Extensions::register(
701
-                $addon_name,
702
-                array(
703
-                    'model_extension_paths' => self::$_settings[$addon_name]['model_extension_paths'],
704
-                    'class_extension_paths' => self::$_settings[$addon_name]['class_extension_paths'],
705
-                )
706
-            );
707
-        }
708
-    }
709
-
710
-
711
-
712
-    /**
713
-     * @param string $addon_name
714
-     * @return void
715
-     * @throws \EE_Error
716
-     */
682
+		// register new models
683
+		if (
684
+			! empty(self::$_settings[$addon_name]['model_paths'])
685
+			|| ! empty(self::$_settings[$addon_name]['class_paths'])
686
+		) {
687
+			EE_Register_Model::register(
688
+				$addon_name,
689
+				array(
690
+					'model_paths' => self::$_settings[$addon_name]['model_paths'],
691
+					'class_paths' => self::$_settings[$addon_name]['class_paths'],
692
+				)
693
+			);
694
+		}
695
+		// register model extensions
696
+		if (
697
+			! empty(self::$_settings[$addon_name]['model_extension_paths'])
698
+			|| ! empty(self::$_settings[$addon_name]['class_extension_paths'])
699
+		) {
700
+			EE_Register_Model_Extensions::register(
701
+				$addon_name,
702
+				array(
703
+					'model_extension_paths' => self::$_settings[$addon_name]['model_extension_paths'],
704
+					'class_extension_paths' => self::$_settings[$addon_name]['class_extension_paths'],
705
+				)
706
+			);
707
+		}
708
+	}
709
+
710
+
711
+
712
+	/**
713
+	 * @param string $addon_name
714
+	 * @return void
715
+	 * @throws \EE_Error
716
+	 */
717 717
 	private static function _register_data_migration_scripts( $addon_name ) {
718
-        // setup DMS
719
-        if ( ! empty(self::$_settings[$addon_name]['dms_paths'])) {
720
-            EE_Register_Data_Migration_Scripts::register(
721
-                $addon_name,
722
-                array('dms_paths' => self::$_settings[$addon_name]['dms_paths'])
723
-            );
724
-        }
725
-    }
726
-
727
-
728
-    /**
729
-     * @param string $addon_name
730
-     * @return void
731
-     * @throws \EE_Error
732
-     */
718
+		// setup DMS
719
+		if ( ! empty(self::$_settings[$addon_name]['dms_paths'])) {
720
+			EE_Register_Data_Migration_Scripts::register(
721
+				$addon_name,
722
+				array('dms_paths' => self::$_settings[$addon_name]['dms_paths'])
723
+			);
724
+		}
725
+	}
726
+
727
+
728
+	/**
729
+	 * @param string $addon_name
730
+	 * @return void
731
+	 * @throws \EE_Error
732
+	 */
733 733
 	private static function _register_config( $addon_name ) {
734
-        // if config_class is present let's register config.
735
-        if ( ! empty(self::$_settings[$addon_name]['config_class'])) {
736
-            EE_Register_Config::register(
737
-                self::$_settings[$addon_name]['config_class'],
738
-                array(
739
-                    'config_section' => self::$_settings[$addon_name]['config_section'],
740
-                    'config_name'    => self::$_settings[$addon_name]['config_name'],
741
-                )
742
-            );
743
-        }
744
-    }
745
-
746
-
747
-    /**
748
-     * @param string $addon_name
749
-     * @return void
750
-     * @throws \EE_Error
751
-     */
734
+		// if config_class is present let's register config.
735
+		if ( ! empty(self::$_settings[$addon_name]['config_class'])) {
736
+			EE_Register_Config::register(
737
+				self::$_settings[$addon_name]['config_class'],
738
+				array(
739
+					'config_section' => self::$_settings[$addon_name]['config_section'],
740
+					'config_name'    => self::$_settings[$addon_name]['config_name'],
741
+				)
742
+			);
743
+		}
744
+	}
745
+
746
+
747
+	/**
748
+	 * @param string $addon_name
749
+	 * @return void
750
+	 * @throws \EE_Error
751
+	 */
752 752
 	private static function _register_admin_pages( $addon_name ) {
753
-        if ( ! empty(self::$_settings[$addon_name]['admin_path'])) {
754
-            EE_Register_Admin_Page::register(
755
-                $addon_name,
756
-                array('page_path' => self::$_settings[$addon_name]['admin_path'])
757
-            );
758
-        }
759
-    }
760
-
761
-
762
-    /**
763
-     * @param string $addon_name
764
-     * @return void
765
-     * @throws \EE_Error
766
-     */
753
+		if ( ! empty(self::$_settings[$addon_name]['admin_path'])) {
754
+			EE_Register_Admin_Page::register(
755
+				$addon_name,
756
+				array('page_path' => self::$_settings[$addon_name]['admin_path'])
757
+			);
758
+		}
759
+	}
760
+
761
+
762
+	/**
763
+	 * @param string $addon_name
764
+	 * @return void
765
+	 * @throws \EE_Error
766
+	 */
767 767
 	private static function _register_modules( $addon_name ) {
768
-        if ( ! empty(self::$_settings[$addon_name]['module_paths'])) {
769
-            EE_Register_Module::register(
770
-                $addon_name,
771
-                array('module_paths' => self::$_settings[$addon_name]['module_paths'])
772
-            );
773
-        }
774
-    }
775
-
776
-
777
-    /**
778
-     * @param string $addon_name
779
-     * @return void
780
-     * @throws \EE_Error
781
-     */
768
+		if ( ! empty(self::$_settings[$addon_name]['module_paths'])) {
769
+			EE_Register_Module::register(
770
+				$addon_name,
771
+				array('module_paths' => self::$_settings[$addon_name]['module_paths'])
772
+			);
773
+		}
774
+	}
775
+
776
+
777
+	/**
778
+	 * @param string $addon_name
779
+	 * @return void
780
+	 * @throws \EE_Error
781
+	 */
782 782
 	private static function _register_shortcodes( $addon_name ) {
783
-        if ( ! empty(self::$_settings[$addon_name]['shortcode_paths'])) {
784
-            EE_Register_Shortcode::register(
785
-                $addon_name,
786
-                array('shortcode_paths' => self::$_settings[$addon_name]['shortcode_paths'])
787
-            );
788
-        }
789
-    }
790
-
791
-
792
-    /**
793
-     * @param string $addon_name
794
-     * @return void
795
-     * @throws \EE_Error
796
-     */
783
+		if ( ! empty(self::$_settings[$addon_name]['shortcode_paths'])) {
784
+			EE_Register_Shortcode::register(
785
+				$addon_name,
786
+				array('shortcode_paths' => self::$_settings[$addon_name]['shortcode_paths'])
787
+			);
788
+		}
789
+	}
790
+
791
+
792
+	/**
793
+	 * @param string $addon_name
794
+	 * @return void
795
+	 * @throws \EE_Error
796
+	 */
797 797
 	private static function _register_widgets( $addon_name ) {
798
-        if ( ! empty(self::$_settings[$addon_name]['widget_paths'])) {
799
-            EE_Register_Widget::register(
800
-                $addon_name,
801
-                array('widget_paths' => self::$_settings[$addon_name]['widget_paths'])
802
-            );
803
-        }
804
-    }
805
-
806
-
807
-    /**
808
-     * @param string $addon_name
809
-     * @return void
810
-     * @throws \EE_Error
811
-     */
798
+		if ( ! empty(self::$_settings[$addon_name]['widget_paths'])) {
799
+			EE_Register_Widget::register(
800
+				$addon_name,
801
+				array('widget_paths' => self::$_settings[$addon_name]['widget_paths'])
802
+			);
803
+		}
804
+	}
805
+
806
+
807
+	/**
808
+	 * @param string $addon_name
809
+	 * @return void
810
+	 * @throws \EE_Error
811
+	 */
812 812
 	private static function _register_capabilities( $addon_name ) {
813
-        if ( ! empty(self::$_settings[$addon_name]['capabilities'])) {
814
-            EE_Register_Capabilities::register(
815
-                $addon_name,
816
-                array(
817
-                    'capabilities'    => self::$_settings[$addon_name]['capabilities'],
818
-                    'capability_maps' => self::$_settings[$addon_name]['capability_maps'],
819
-                )
820
-            );
821
-        }
822
-    }
823
-
824
-
825
-    /**
826
-     * @param string $addon_name
827
-     * @return void
828
-     * @throws \EE_Error
829
-     */
813
+		if ( ! empty(self::$_settings[$addon_name]['capabilities'])) {
814
+			EE_Register_Capabilities::register(
815
+				$addon_name,
816
+				array(
817
+					'capabilities'    => self::$_settings[$addon_name]['capabilities'],
818
+					'capability_maps' => self::$_settings[$addon_name]['capability_maps'],
819
+				)
820
+			);
821
+		}
822
+	}
823
+
824
+
825
+	/**
826
+	 * @param string $addon_name
827
+	 * @return void
828
+	 * @throws \EE_Error
829
+	 */
830 830
 	private static function _register_message_types( $addon_name ) {
831
-        if ( ! empty(self::$_settings[$addon_name]['message_types'])) {
832
-            add_action(
833
-                'EE_Brewing_Regular___messages_caf',
834
-                array('EE_Register_Addon', 'register_message_types')
835
-            );
836
-        }
837
-    }
838
-
839
-
840
-    /**
841
-     * @param string $addon_name
842
-     * @return void
843
-     * @throws \EE_Error
844
-     */
831
+		if ( ! empty(self::$_settings[$addon_name]['message_types'])) {
832
+			add_action(
833
+				'EE_Brewing_Regular___messages_caf',
834
+				array('EE_Register_Addon', 'register_message_types')
835
+			);
836
+		}
837
+	}
838
+
839
+
840
+	/**
841
+	 * @param string $addon_name
842
+	 * @return void
843
+	 * @throws \EE_Error
844
+	 */
845 845
 	private static function _register_custom_post_types( $addon_name ) {
846
-        if (
847
-            ! empty(self::$_settings[$addon_name]['custom_post_types'])
848
-            || ! empty(self::$_settings[$addon_name]['custom_taxonomies'])
849
-        ) {
850
-            EE_Register_CPT::register(
851
-                $addon_name,
852
-                array(
853
-                    'cpts'          => self::$_settings[$addon_name]['custom_post_types'],
854
-                    'cts'           => self::$_settings[$addon_name]['custom_taxonomies'],
855
-                    'default_terms' => self::$_settings[$addon_name]['default_terms'],
856
-                )
857
-            );
858
-        }
859
-    }
860
-
861
-
862
-    /**
863
-     * @param string $addon_name
864
-     * @return void
865
-     * @throws \EE_Error
866
-     */
846
+		if (
847
+			! empty(self::$_settings[$addon_name]['custom_post_types'])
848
+			|| ! empty(self::$_settings[$addon_name]['custom_taxonomies'])
849
+		) {
850
+			EE_Register_CPT::register(
851
+				$addon_name,
852
+				array(
853
+					'cpts'          => self::$_settings[$addon_name]['custom_post_types'],
854
+					'cts'           => self::$_settings[$addon_name]['custom_taxonomies'],
855
+					'default_terms' => self::$_settings[$addon_name]['default_terms'],
856
+				)
857
+			);
858
+		}
859
+	}
860
+
861
+
862
+	/**
863
+	 * @param string $addon_name
864
+	 * @return void
865
+	 * @throws \EE_Error
866
+	 */
867 867
 	private static function _register_payment_methods( $addon_name ) {
868
-        if ( ! empty(self::$_settings[$addon_name]['payment_method_paths'])) {
869
-            EE_Register_Payment_Method::register(
870
-                $addon_name,
871
-                array('payment_method_paths' => self::$_settings[$addon_name]['payment_method_paths'])
872
-            );
873
-        }
874
-    }
868
+		if ( ! empty(self::$_settings[$addon_name]['payment_method_paths'])) {
869
+			EE_Register_Payment_Method::register(
870
+				$addon_name,
871
+				array('payment_method_paths' => self::$_settings[$addon_name]['payment_method_paths'])
872
+			);
873
+		}
874
+	}
875 875
 
876 876
 
877 877
 
@@ -900,14 +900,14 @@  discard block
 block discarded – undo
900 900
 		//unfortunately this can't be hooked in upon construction, because we don't have
901 901
 		//the plugin mainfile's path upon construction.
902 902
 		register_deactivation_hook( $addon->get_main_plugin_file(), array( $addon, 'deactivation' ) );
903
-        // call any additional admin_callback functions during load_admin_controller hook
904
-        if ( ! empty(self::$_settings[$addon_name]['admin_callback'])) {
905
-            add_action(
906
-                'AHEE__EE_System__load_controllers__load_admin_controllers',
907
-                array($addon, self::$_settings[$addon_name]['admin_callback'])
908
-            );
909
-        }
910
-        return $addon;
903
+		// call any additional admin_callback functions during load_admin_controller hook
904
+		if ( ! empty(self::$_settings[$addon_name]['admin_callback'])) {
905
+			add_action(
906
+				'AHEE__EE_System__load_controllers__load_admin_controllers',
907
+				array($addon, self::$_settings[$addon_name]['admin_callback'])
908
+			);
909
+		}
910
+		return $addon;
911 911
 	}
912 912
 
913 913
 
@@ -923,7 +923,7 @@  discard block
 block discarded – undo
923 923
 		// cycle thru settings
924 924
 		foreach ( self::$_settings as $settings ) {
925 925
 			if ( ! empty( $settings['pue_options'] ) ) {
926
-                // initiate the class and start the plugin update engine!
926
+				// initiate the class and start the plugin update engine!
927 927
 				new PluginUpdateEngineChecker(
928 928
 				// host file URL
929 929
 					'https://eventespresso.com',
@@ -959,11 +959,11 @@  discard block
 block discarded – undo
959 959
 	 */
960 960
 	public static function register_message_types() {
961 961
 		foreach ( self::$_settings as $addon_name => $settings ) {
962
-		    if ( ! empty($settings['message_types'])) {
963
-                foreach ((array)$settings['message_types'] as $message_type => $message_type_settings) {
964
-                    EE_Register_Message_Type::register($message_type, $message_type_settings);
965
-                }
966
-            }
962
+			if ( ! empty($settings['message_types'])) {
963
+				foreach ((array)$settings['message_types'] as $message_type => $message_type_settings) {
964
+					EE_Register_Message_Type::register($message_type, $message_type_settings);
965
+				}
966
+			}
967 967
 		}
968 968
 	}
969 969
 
@@ -1005,15 +1005,15 @@  discard block
 block discarded – undo
1005 1005
 				EE_Register_Widget::deregister( $addon_name );
1006 1006
 			}
1007 1007
 			if ( ! empty( self::$_settings[ $addon_name ]['model_paths'] )
1008
-			     ||
1009
-			     ! empty( self::$_settings[ $addon_name ]['class_paths'] )
1008
+				 ||
1009
+				 ! empty( self::$_settings[ $addon_name ]['class_paths'] )
1010 1010
 			) {
1011 1011
 				// add to list of shortcodes to be registered
1012 1012
 				EE_Register_Model::deregister( $addon_name );
1013 1013
 			}
1014 1014
 			if ( ! empty( self::$_settings[ $addon_name ]['model_extension_paths'] )
1015
-			     ||
1016
-			     ! empty( self::$_settings[ $addon_name ]['class_extension_paths'] )
1015
+				 ||
1016
+				 ! empty( self::$_settings[ $addon_name ]['class_extension_paths'] )
1017 1017
 			) {
1018 1018
 				// add to list of shortcodes to be registered
1019 1019
 				EE_Register_Model_Extensions::deregister( $addon_name );
Please login to merge, or discard this patch.
Spacing   +119 added lines, -119 removed lines patch added patch discarded remove patch
@@ -1,5 +1,5 @@  discard block
 block discarded – undo
1
-<?php if ( ! defined( 'EVENT_ESPRESSO_VERSION' ) ) {
2
-	exit( 'No direct script access allowed' );
1
+<?php if ( ! defined('EVENT_ESPRESSO_VERSION')) {
2
+	exit('No direct script access allowed');
3 3
 }
4 4
 
5 5
 
@@ -61,23 +61,23 @@  discard block
 block discarded – undo
61 61
 	 * @param string $min_core_version
62 62
 	 * @return string always like '4.3.0.rc.000'
63 63
 	 */
64
-	protected static function _effective_version( $min_core_version ) {
64
+	protected static function _effective_version($min_core_version) {
65 65
 		// versions: 4 . 3 . 1 . p . 123
66 66
 		// offsets:    0 . 1 . 2 . 3 . 4
67
-		$version_parts = explode( '.', $min_core_version );
67
+		$version_parts = explode('.', $min_core_version);
68 68
 		//check they specified the micro version (after 2nd period)
69
-		if ( ! isset( $version_parts[2] ) ) {
69
+		if ( ! isset($version_parts[2])) {
70 70
 			$version_parts[2] = '0';
71 71
 		}
72 72
 		//if they didn't specify the 'p', or 'rc' part. Just assume the lowest possible
73 73
 		//soon we can assume that's 'rc', but this current version is 'alpha'
74
-		if ( ! isset( $version_parts[3] ) ) {
74
+		if ( ! isset($version_parts[3])) {
75 75
 			$version_parts[3] = 'dev';
76 76
 		}
77
-		if ( ! isset( $version_parts[4] ) ) {
77
+		if ( ! isset($version_parts[4])) {
78 78
 			$version_parts[4] = '000';
79 79
 		}
80
-		return implode( '.', $version_parts );
80
+		return implode('.', $version_parts);
81 81
 	}
82 82
 
83 83
 
@@ -94,8 +94,8 @@  discard block
 block discarded – undo
94 94
 		$actual_core_version = EVENT_ESPRESSO_VERSION
95 95
 	) {
96 96
 		return version_compare(
97
-			self::_effective_version( $actual_core_version ),
98
-			self::_effective_version( $min_core_version ),
97
+			self::_effective_version($actual_core_version),
98
+			self::_effective_version($min_core_version),
99 99
 			'>='
100 100
 		);
101 101
 	}
@@ -217,7 +217,7 @@  discard block
 block discarded – undo
217 217
 	 * @throws EE_Error
218 218
 	 * @return void
219 219
 	 */
220
-	public static function register( $addon_name = '', $setup_args = array() ) {
220
+	public static function register($addon_name = '', $setup_args = array()) {
221 221
 		// required fields MUST be present, so let's make sure they are.
222 222
         \EE_Register_Addon::_verify_parameters($addon_name, $setup_args);
223 223
         // get class name for addon
@@ -227,13 +227,13 @@  discard block
 block discarded – undo
227 227
         // setup PUE
228 228
         \EE_Register_Addon::_parse_pue_options($addon_name, $class_name, $setup_args);
229 229
         // does this addon work with this version of core or WordPress ?
230
-        if ( ! \EE_Register_Addon::_addon_is_compatible($addon_name, $addon_settings) ) {
230
+        if ( ! \EE_Register_Addon::_addon_is_compatible($addon_name, $addon_settings)) {
231 231
             return;
232 232
 		}
233 233
 		// register namespaces
234 234
         \EE_Register_Addon::_setup_namespaces($addon_settings);
235 235
         // check if this is an activation request
236
-        if ( \EE_Register_Addon::_addon_activation($addon_name, $addon_settings)) {
236
+        if (\EE_Register_Addon::_addon_activation($addon_name, $addon_settings)) {
237 237
             // dont bother setting up the rest of the addon atm
238 238
             return;
239 239
         }
@@ -326,7 +326,7 @@  discard block
 block discarded – undo
326 326
         } else {
327 327
             $class_name = $setup_args['class_name'];
328 328
         }
329
-        return strpos($class_name, 'EE_') === 0 ? $class_name : 'EE_' . $class_name;
329
+        return strpos($class_name, 'EE_') === 0 ? $class_name : 'EE_'.$class_name;
330 330
     }
331 331
 
332 332
 
@@ -344,105 +344,105 @@  discard block
 block discarded – undo
344 344
             'class_name'            => $class_name,
345 345
             // the addon slug for use in URLs, etc
346 346
             'plugin_slug'           => isset($setup_args['plugin_slug'])
347
-                ? (string)$setup_args['plugin_slug']
347
+                ? (string) $setup_args['plugin_slug']
348 348
                 : '',
349 349
             // page slug to be used when generating the "Settings" link on the WP plugin page
350 350
             'plugin_action_slug'    => isset($setup_args['plugin_action_slug'])
351
-                ? (string)$setup_args['plugin_action_slug']
351
+                ? (string) $setup_args['plugin_action_slug']
352 352
                 : '',
353 353
             // the "software" version for the addon
354 354
             'version'               => isset($setup_args['version'])
355
-                ? (string)$setup_args['version']
355
+                ? (string) $setup_args['version']
356 356
                 : '',
357 357
             // the minimum version of EE Core that the addon will work with
358 358
             'min_core_version'      => isset($setup_args['min_core_version'])
359
-                ? (string)$setup_args['min_core_version']
359
+                ? (string) $setup_args['min_core_version']
360 360
                 : '',
361 361
             // the minimum version of WordPress that the addon will work with
362 362
             'min_wp_version'        => isset($setup_args['min_wp_version'])
363
-                ? (string)$setup_args['min_wp_version']
363
+                ? (string) $setup_args['min_wp_version']
364 364
                 : EE_MIN_WP_VER_REQUIRED,
365 365
             // full server path to main file (file loaded directly by WP)
366 366
             'main_file_path'        => isset($setup_args['main_file_path'])
367
-                ? (string)$setup_args['main_file_path']
367
+                ? (string) $setup_args['main_file_path']
368 368
                 : '',
369 369
             // path to folder containing files for integrating with the EE core admin and/or setting up EE admin pages
370 370
             'admin_path'            => isset($setup_args['admin_path'])
371
-                ? (string)$setup_args['admin_path'] : '',
371
+                ? (string) $setup_args['admin_path'] : '',
372 372
             // a method to be called when the EE Admin is first invoked, can be used for hooking into any admin page
373 373
             'admin_callback'        => isset($setup_args['admin_callback'])
374
-                ? (string)$setup_args['admin_callback']
374
+                ? (string) $setup_args['admin_callback']
375 375
                 : '',
376 376
             // the section name for this addon's configuration settings section (defaults to "addons")
377 377
             'config_section'        => isset($setup_args['config_section'])
378
-                ? (string)$setup_args['config_section']
378
+                ? (string) $setup_args['config_section']
379 379
                 : 'addons',
380 380
             // the class name for this addon's configuration settings object
381 381
             'config_class'          => isset($setup_args['config_class'])
382
-                ? (string)$setup_args['config_class'] : '',
382
+                ? (string) $setup_args['config_class'] : '',
383 383
             //the name given to the config for this addons' configuration settings object (optional)
384 384
             'config_name'           => isset($setup_args['config_name'])
385
-                ? (string)$setup_args['config_name'] : '',
385
+                ? (string) $setup_args['config_name'] : '',
386 386
             // an array of "class names" => "full server paths" for any classes that might be invoked by the addon
387 387
             'autoloader_paths'      => isset($setup_args['autoloader_paths'])
388
-                ? (array)$setup_args['autoloader_paths']
388
+                ? (array) $setup_args['autoloader_paths']
389 389
                 : array(),
390 390
             // an array of  "full server paths" for any folders containing classes that might be invoked by the addon
391 391
             'autoloader_folders'    => isset($setup_args['autoloader_folders'])
392
-                ? (array)$setup_args['autoloader_folders']
392
+                ? (array) $setup_args['autoloader_folders']
393 393
                 : array(),
394 394
             // array of full server paths to any EE_DMS data migration scripts used by the addon
395 395
             'dms_paths'             => isset($setup_args['dms_paths'])
396
-                ? (array)$setup_args['dms_paths']
396
+                ? (array) $setup_args['dms_paths']
397 397
                 : array(),
398 398
             // array of full server paths to any EED_Modules used by the addon
399 399
             'module_paths'          => isset($setup_args['module_paths'])
400
-                ? (array)$setup_args['module_paths']
400
+                ? (array) $setup_args['module_paths']
401 401
                 : array(),
402 402
             // array of full server paths to any EES_Shortcodes used by the addon
403 403
             'shortcode_paths'       => isset($setup_args['shortcode_paths'])
404
-                ? (array)$setup_args['shortcode_paths']
404
+                ? (array) $setup_args['shortcode_paths']
405 405
                 : array(),
406 406
             // array of full server paths to any WP_Widgets used by the addon
407 407
             'widget_paths'          => isset($setup_args['widget_paths'])
408
-                ? (array)$setup_args['widget_paths']
408
+                ? (array) $setup_args['widget_paths']
409 409
                 : array(),
410 410
             // array of PUE options used by the addon
411 411
             'pue_options'           => isset($setup_args['pue_options'])
412
-                ? (array)$setup_args['pue_options']
412
+                ? (array) $setup_args['pue_options']
413 413
                 : array(),
414 414
             'message_types'         => isset($setup_args['message_types'])
415
-                ? (array)$setup_args['message_types']
415
+                ? (array) $setup_args['message_types']
416 416
                 : array(),
417 417
             'capabilities'          => isset($setup_args['capabilities'])
418
-                ? (array)$setup_args['capabilities']
418
+                ? (array) $setup_args['capabilities']
419 419
                 : array(),
420 420
             'capability_maps'       => isset($setup_args['capability_maps'])
421
-                ? (array)$setup_args['capability_maps']
421
+                ? (array) $setup_args['capability_maps']
422 422
                 : array(),
423 423
             'model_paths'           => isset($setup_args['model_paths'])
424
-                ? (array)$setup_args['model_paths']
424
+                ? (array) $setup_args['model_paths']
425 425
                 : array(),
426 426
             'class_paths'           => isset($setup_args['class_paths'])
427
-                ? (array)$setup_args['class_paths']
427
+                ? (array) $setup_args['class_paths']
428 428
                 : array(),
429 429
             'model_extension_paths' => isset($setup_args['model_extension_paths'])
430
-                ? (array)$setup_args['model_extension_paths']
430
+                ? (array) $setup_args['model_extension_paths']
431 431
                 : array(),
432 432
             'class_extension_paths' => isset($setup_args['class_extension_paths'])
433
-                ? (array)$setup_args['class_extension_paths']
433
+                ? (array) $setup_args['class_extension_paths']
434 434
                 : array(),
435 435
             'custom_post_types'     => isset($setup_args['custom_post_types'])
436
-                ? (array)$setup_args['custom_post_types']
436
+                ? (array) $setup_args['custom_post_types']
437 437
                 : array(),
438 438
             'custom_taxonomies'     => isset($setup_args['custom_taxonomies'])
439
-                ? (array)$setup_args['custom_taxonomies']
439
+                ? (array) $setup_args['custom_taxonomies']
440 440
                 : array(),
441 441
             'payment_method_paths'  => isset($setup_args['payment_method_paths'])
442
-                ? (array)$setup_args['payment_method_paths']
442
+                ? (array) $setup_args['payment_method_paths']
443 443
                 : array(),
444 444
             'default_terms'         => isset($setup_args['default_terms'])
445
-                ? (array)$setup_args['default_terms']
445
+                ? (array) $setup_args['default_terms']
446 446
                 : array(),
447 447
             // if not empty, inserts a new table row after this plugin's row on the WP Plugins page
448 448
             // that can be used for adding upgrading/marketing info
@@ -454,7 +454,7 @@  discard block
 block discarded – undo
454 454
                 $setup_args['namespace']['FQNS'],
455 455
                 $setup_args['namespace']['DIR']
456 456
             )
457
-                ? (array)$setup_args['namespace']
457
+                ? (array) $setup_args['namespace']
458 458
                 : array(),
459 459
         );
460 460
         // if plugin_action_slug is NOT set, but an admin page path IS set,
@@ -475,7 +475,7 @@  discard block
 block discarded – undo
475 475
      * @param array  $addon_settings
476 476
      * @return boolean
477 477
      */
478
-	private static function _addon_is_compatible( $addon_name, array $addon_settings ) {
478
+	private static function _addon_is_compatible($addon_name, array $addon_settings) {
479 479
         global $wp_version;
480 480
         $incompatibility_message = '';
481 481
         //check whether this addon version is compatible with EE core
@@ -551,20 +551,20 @@  discard block
 block discarded – undo
551 551
      * @param array  $setup_args
552 552
      * @return void
553 553
      */
554
-	private static function _parse_pue_options( $addon_name, $class_name, array $setup_args ) {
554
+	private static function _parse_pue_options($addon_name, $class_name, array $setup_args) {
555 555
         if ( ! empty($setup_args['pue_options'])) {
556 556
             self::$_settings[$addon_name]['pue_options'] = array(
557 557
                 'pue_plugin_slug' => isset($setup_args['pue_options']['pue_plugin_slug'])
558
-                    ? (string)$setup_args['pue_options']['pue_plugin_slug']
559
-                    : 'espresso_' . strtolower($class_name),
558
+                    ? (string) $setup_args['pue_options']['pue_plugin_slug']
559
+                    : 'espresso_'.strtolower($class_name),
560 560
                 'plugin_basename' => isset($setup_args['pue_options']['plugin_basename'])
561
-                    ? (string)$setup_args['pue_options']['plugin_basename']
561
+                    ? (string) $setup_args['pue_options']['plugin_basename']
562 562
                     : plugin_basename($setup_args['main_file_path']),
563 563
                 'checkPeriod'     => isset($setup_args['pue_options']['checkPeriod'])
564
-                    ? (string)$setup_args['pue_options']['checkPeriod']
564
+                    ? (string) $setup_args['pue_options']['checkPeriod']
565 565
                     : '24',
566 566
                 'use_wp_update'   => isset($setup_args['pue_options']['use_wp_update'])
567
-                    ? (string)$setup_args['pue_options']['use_wp_update']
567
+                    ? (string) $setup_args['pue_options']['use_wp_update']
568 568
                     : false,
569 569
             );
570 570
             add_action(
@@ -606,7 +606,7 @@  discard block
 block discarded – undo
606 606
      * @param array  $addon_settings
607 607
      * @return bool
608 608
      */
609
-	private static function _addon_activation( $addon_name, array $addon_settings ) {
609
+	private static function _addon_activation($addon_name, array $addon_settings) {
610 610
         // this is an activation request
611 611
         if (did_action('activate_plugin')) {
612 612
             //to find if THIS is the addon that was activated,
@@ -663,7 +663,7 @@  discard block
 block discarded – undo
663 663
         }
664 664
         // setup autoloaders for folders
665 665
         if ( ! empty(self::$_settings[$addon_name]['autoloader_folders'])) {
666
-            foreach ((array)self::$_settings[$addon_name]['autoloader_folders'] as $autoloader_folder) {
666
+            foreach ((array) self::$_settings[$addon_name]['autoloader_folders'] as $autoloader_folder) {
667 667
                 EEH_Autoloader::register_autoloaders_for_each_file_in_folder($autoloader_folder);
668 668
             }
669 669
         }
@@ -678,7 +678,7 @@  discard block
 block discarded – undo
678 678
      * @return void
679 679
      * @throws \EE_Error
680 680
      */
681
-	private static function _register_models_and_extensions( $addon_name ) {
681
+	private static function _register_models_and_extensions($addon_name) {
682 682
         // register new models
683 683
         if (
684 684
             ! empty(self::$_settings[$addon_name]['model_paths'])
@@ -714,7 +714,7 @@  discard block
 block discarded – undo
714 714
      * @return void
715 715
      * @throws \EE_Error
716 716
      */
717
-	private static function _register_data_migration_scripts( $addon_name ) {
717
+	private static function _register_data_migration_scripts($addon_name) {
718 718
         // setup DMS
719 719
         if ( ! empty(self::$_settings[$addon_name]['dms_paths'])) {
720 720
             EE_Register_Data_Migration_Scripts::register(
@@ -730,7 +730,7 @@  discard block
 block discarded – undo
730 730
      * @return void
731 731
      * @throws \EE_Error
732 732
      */
733
-	private static function _register_config( $addon_name ) {
733
+	private static function _register_config($addon_name) {
734 734
         // if config_class is present let's register config.
735 735
         if ( ! empty(self::$_settings[$addon_name]['config_class'])) {
736 736
             EE_Register_Config::register(
@@ -749,7 +749,7 @@  discard block
 block discarded – undo
749 749
      * @return void
750 750
      * @throws \EE_Error
751 751
      */
752
-	private static function _register_admin_pages( $addon_name ) {
752
+	private static function _register_admin_pages($addon_name) {
753 753
         if ( ! empty(self::$_settings[$addon_name]['admin_path'])) {
754 754
             EE_Register_Admin_Page::register(
755 755
                 $addon_name,
@@ -764,7 +764,7 @@  discard block
 block discarded – undo
764 764
      * @return void
765 765
      * @throws \EE_Error
766 766
      */
767
-	private static function _register_modules( $addon_name ) {
767
+	private static function _register_modules($addon_name) {
768 768
         if ( ! empty(self::$_settings[$addon_name]['module_paths'])) {
769 769
             EE_Register_Module::register(
770 770
                 $addon_name,
@@ -779,7 +779,7 @@  discard block
 block discarded – undo
779 779
      * @return void
780 780
      * @throws \EE_Error
781 781
      */
782
-	private static function _register_shortcodes( $addon_name ) {
782
+	private static function _register_shortcodes($addon_name) {
783 783
         if ( ! empty(self::$_settings[$addon_name]['shortcode_paths'])) {
784 784
             EE_Register_Shortcode::register(
785 785
                 $addon_name,
@@ -794,7 +794,7 @@  discard block
 block discarded – undo
794 794
      * @return void
795 795
      * @throws \EE_Error
796 796
      */
797
-	private static function _register_widgets( $addon_name ) {
797
+	private static function _register_widgets($addon_name) {
798 798
         if ( ! empty(self::$_settings[$addon_name]['widget_paths'])) {
799 799
             EE_Register_Widget::register(
800 800
                 $addon_name,
@@ -809,7 +809,7 @@  discard block
 block discarded – undo
809 809
      * @return void
810 810
      * @throws \EE_Error
811 811
      */
812
-	private static function _register_capabilities( $addon_name ) {
812
+	private static function _register_capabilities($addon_name) {
813 813
         if ( ! empty(self::$_settings[$addon_name]['capabilities'])) {
814 814
             EE_Register_Capabilities::register(
815 815
                 $addon_name,
@@ -827,7 +827,7 @@  discard block
 block discarded – undo
827 827
      * @return void
828 828
      * @throws \EE_Error
829 829
      */
830
-	private static function _register_message_types( $addon_name ) {
830
+	private static function _register_message_types($addon_name) {
831 831
         if ( ! empty(self::$_settings[$addon_name]['message_types'])) {
832 832
             add_action(
833 833
                 'EE_Brewing_Regular___messages_caf',
@@ -842,7 +842,7 @@  discard block
 block discarded – undo
842 842
      * @return void
843 843
      * @throws \EE_Error
844 844
      */
845
-	private static function _register_custom_post_types( $addon_name ) {
845
+	private static function _register_custom_post_types($addon_name) {
846 846
         if (
847 847
             ! empty(self::$_settings[$addon_name]['custom_post_types'])
848 848
             || ! empty(self::$_settings[$addon_name]['custom_taxonomies'])
@@ -864,7 +864,7 @@  discard block
 block discarded – undo
864 864
      * @return void
865 865
      * @throws \EE_Error
866 866
      */
867
-	private static function _register_payment_methods( $addon_name ) {
867
+	private static function _register_payment_methods($addon_name) {
868 868
         if ( ! empty(self::$_settings[$addon_name]['payment_method_paths'])) {
869 869
             EE_Register_Payment_Method::register(
870 870
                 $addon_name,
@@ -881,25 +881,25 @@  discard block
 block discarded – undo
881 881
 	 * @param string $addon_name
882 882
 	 * @return EE_Addon
883 883
 	 */
884
-	private static function _load_and_init_addon_class( $addon_name ) {
884
+	private static function _load_and_init_addon_class($addon_name) {
885 885
 		$addon = EE_Registry::instance()->load_addon(
886
-			dirname( self::$_settings[ $addon_name ]['main_file_path'] ),
887
-			self::$_settings[ $addon_name ]['class_name']
886
+			dirname(self::$_settings[$addon_name]['main_file_path']),
887
+			self::$_settings[$addon_name]['class_name']
888 888
 		);
889
-		$addon->set_name( $addon_name );
890
-		$addon->set_plugin_slug( self::$_settings[ $addon_name ]['plugin_slug'] );
891
-		$addon->set_plugin_basename( self::$_settings[ $addon_name ]['plugin_basename'] );
892
-		$addon->set_main_plugin_file( self::$_settings[ $addon_name ]['main_file_path'] );
893
-		$addon->set_plugin_action_slug( self::$_settings[ $addon_name ]['plugin_action_slug'] );
894
-		$addon->set_plugins_page_row( self::$_settings[ $addon_name ]['plugins_page_row'] );
895
-		$addon->set_version( self::$_settings[ $addon_name ]['version'] );
896
-		$addon->set_min_core_version( self::_effective_version( self::$_settings[ $addon_name ]['min_core_version'] ) );
897
-		$addon->set_config_section( self::$_settings[ $addon_name ]['config_section'] );
898
-		$addon->set_config_class( self::$_settings[ $addon_name ]['config_class'] );
899
-		$addon->set_config_name( self::$_settings[ $addon_name ]['config_name'] );
889
+		$addon->set_name($addon_name);
890
+		$addon->set_plugin_slug(self::$_settings[$addon_name]['plugin_slug']);
891
+		$addon->set_plugin_basename(self::$_settings[$addon_name]['plugin_basename']);
892
+		$addon->set_main_plugin_file(self::$_settings[$addon_name]['main_file_path']);
893
+		$addon->set_plugin_action_slug(self::$_settings[$addon_name]['plugin_action_slug']);
894
+		$addon->set_plugins_page_row(self::$_settings[$addon_name]['plugins_page_row']);
895
+		$addon->set_version(self::$_settings[$addon_name]['version']);
896
+		$addon->set_min_core_version(self::_effective_version(self::$_settings[$addon_name]['min_core_version']));
897
+		$addon->set_config_section(self::$_settings[$addon_name]['config_section']);
898
+		$addon->set_config_class(self::$_settings[$addon_name]['config_class']);
899
+		$addon->set_config_name(self::$_settings[$addon_name]['config_name']);
900 900
 		//unfortunately this can't be hooked in upon construction, because we don't have
901 901
 		//the plugin mainfile's path upon construction.
902
-		register_deactivation_hook( $addon->get_main_plugin_file(), array( $addon, 'deactivation' ) );
902
+		register_deactivation_hook($addon->get_main_plugin_file(), array($addon, 'deactivation'));
903 903
         // call any additional admin_callback functions during load_admin_controller hook
904 904
         if ( ! empty(self::$_settings[$addon_name]['admin_callback'])) {
905 905
             add_action(
@@ -919,18 +919,18 @@  discard block
 block discarded – undo
919 919
 	 */
920 920
 	public static function load_pue_update() {
921 921
 		// load PUE client
922
-		require_once EE_THIRD_PARTY . 'pue' . DS . 'pue-client.php';
922
+		require_once EE_THIRD_PARTY.'pue'.DS.'pue-client.php';
923 923
 		// cycle thru settings
924
-		foreach ( self::$_settings as $settings ) {
925
-			if ( ! empty( $settings['pue_options'] ) ) {
924
+		foreach (self::$_settings as $settings) {
925
+			if ( ! empty($settings['pue_options'])) {
926 926
                 // initiate the class and start the plugin update engine!
927 927
 				new PluginUpdateEngineChecker(
928 928
 				// host file URL
929 929
 					'https://eventespresso.com',
930 930
 					// plugin slug(s)
931 931
 					array(
932
-						'premium'    => array( 'p' => $settings['pue_options']['pue_plugin_slug'] ),
933
-						'prerelease' => array( 'beta' => $settings['pue_options']['pue_plugin_slug'] . '-pr' ),
932
+						'premium'    => array('p' => $settings['pue_options']['pue_plugin_slug']),
933
+						'prerelease' => array('beta' => $settings['pue_options']['pue_plugin_slug'].'-pr'),
934 934
 					),
935 935
 					// options
936 936
 					array(
@@ -958,9 +958,9 @@  discard block
 block discarded – undo
958 958
 	 * @throws \EE_Error
959 959
 	 */
960 960
 	public static function register_message_types() {
961
-		foreach ( self::$_settings as $addon_name => $settings ) {
961
+		foreach (self::$_settings as $addon_name => $settings) {
962 962
 		    if ( ! empty($settings['message_types'])) {
963
-                foreach ((array)$settings['message_types'] as $message_type => $message_type_settings) {
963
+                foreach ((array) $settings['message_types'] as $message_type => $message_type_settings) {
964 964
                     EE_Register_Message_Type::register($message_type, $message_type_settings);
965 965
                 }
966 966
             }
@@ -977,73 +977,73 @@  discard block
 block discarded – undo
977 977
 	 * @throws EE_Error
978 978
 	 * @return void
979 979
 	 */
980
-	public static function deregister( $addon_name = null ) {
981
-		if ( isset( self::$_settings[ $addon_name ] ) ) {
982
-			$class_name = self::$_settings[ $addon_name ]['class_name'];
983
-			if ( ! empty( self::$_settings[ $addon_name ]['dms_paths'] ) ) {
980
+	public static function deregister($addon_name = null) {
981
+		if (isset(self::$_settings[$addon_name])) {
982
+			$class_name = self::$_settings[$addon_name]['class_name'];
983
+			if ( ! empty(self::$_settings[$addon_name]['dms_paths'])) {
984 984
 				// setup DMS
985
-				EE_Register_Data_Migration_Scripts::deregister( $addon_name );
985
+				EE_Register_Data_Migration_Scripts::deregister($addon_name);
986 986
 			}
987
-			if ( ! empty( self::$_settings[ $addon_name ]['admin_path'] ) ) {
987
+			if ( ! empty(self::$_settings[$addon_name]['admin_path'])) {
988 988
 				// register admin page
989
-				EE_Register_Admin_Page::deregister( $addon_name );
989
+				EE_Register_Admin_Page::deregister($addon_name);
990 990
 			}
991
-			if ( ! empty( self::$_settings[ $addon_name ]['module_paths'] ) ) {
991
+			if ( ! empty(self::$_settings[$addon_name]['module_paths'])) {
992 992
 				// add to list of modules to be registered
993
-				EE_Register_Module::deregister( $addon_name );
993
+				EE_Register_Module::deregister($addon_name);
994 994
 			}
995
-			if ( ! empty( self::$_settings[ $addon_name ]['shortcode_paths'] ) ) {
995
+			if ( ! empty(self::$_settings[$addon_name]['shortcode_paths'])) {
996 996
 				// add to list of shortcodes to be registered
997
-				EE_Register_Shortcode::deregister( $addon_name );
997
+				EE_Register_Shortcode::deregister($addon_name);
998 998
 			}
999
-			if ( ! empty( self::$_settings[ $addon_name ]['config_class'] ) ) {
999
+			if ( ! empty(self::$_settings[$addon_name]['config_class'])) {
1000 1000
 				// if config_class present let's register config.
1001
-				EE_Register_Config::deregister( self::$_settings[ $addon_name ]['config_class'] );
1001
+				EE_Register_Config::deregister(self::$_settings[$addon_name]['config_class']);
1002 1002
 			}
1003
-			if ( ! empty( self::$_settings[ $addon_name ]['widget_paths'] ) ) {
1003
+			if ( ! empty(self::$_settings[$addon_name]['widget_paths'])) {
1004 1004
 				// add to list of widgets to be registered
1005
-				EE_Register_Widget::deregister( $addon_name );
1005
+				EE_Register_Widget::deregister($addon_name);
1006 1006
 			}
1007
-			if ( ! empty( self::$_settings[ $addon_name ]['model_paths'] )
1007
+			if ( ! empty(self::$_settings[$addon_name]['model_paths'])
1008 1008
 			     ||
1009
-			     ! empty( self::$_settings[ $addon_name ]['class_paths'] )
1009
+			     ! empty(self::$_settings[$addon_name]['class_paths'])
1010 1010
 			) {
1011 1011
 				// add to list of shortcodes to be registered
1012
-				EE_Register_Model::deregister( $addon_name );
1012
+				EE_Register_Model::deregister($addon_name);
1013 1013
 			}
1014
-			if ( ! empty( self::$_settings[ $addon_name ]['model_extension_paths'] )
1014
+			if ( ! empty(self::$_settings[$addon_name]['model_extension_paths'])
1015 1015
 			     ||
1016
-			     ! empty( self::$_settings[ $addon_name ]['class_extension_paths'] )
1016
+			     ! empty(self::$_settings[$addon_name]['class_extension_paths'])
1017 1017
 			) {
1018 1018
 				// add to list of shortcodes to be registered
1019
-				EE_Register_Model_Extensions::deregister( $addon_name );
1019
+				EE_Register_Model_Extensions::deregister($addon_name);
1020 1020
 			}
1021
-			if ( ! empty( self::$_settings[ $addon_name ]['message_types'] ) ) {
1022
-				foreach ((array)self::$_settings[ $addon_name ]['message_types'] as $message_type => $message_type_settings )
1021
+			if ( ! empty(self::$_settings[$addon_name]['message_types'])) {
1022
+				foreach ((array) self::$_settings[$addon_name]['message_types'] as $message_type => $message_type_settings)
1023 1023
 				{
1024
-					EE_Register_Message_Type::deregister( $message_type );
1024
+					EE_Register_Message_Type::deregister($message_type);
1025 1025
 				}
1026 1026
 			}
1027 1027
 			//deregister capabilities for addon
1028 1028
 			if (
1029
-				! empty( self::$_settings[ $addon_name ]['capabilities'] )
1030
-				|| ! empty( self::$_settings[ $addon_name ]['capability_maps'] )
1029
+				! empty(self::$_settings[$addon_name]['capabilities'])
1030
+				|| ! empty(self::$_settings[$addon_name]['capability_maps'])
1031 1031
 			) {
1032
-				EE_Register_Capabilities::deregister( $addon_name );
1032
+				EE_Register_Capabilities::deregister($addon_name);
1033 1033
 			}
1034 1034
 			//deregister custom_post_types for addon
1035
-			if ( ! empty( self::$_settings[ $addon_name ]['custom_post_types'] ) ) {
1036
-				EE_Register_CPT::deregister( $addon_name );
1035
+			if ( ! empty(self::$_settings[$addon_name]['custom_post_types'])) {
1036
+				EE_Register_CPT::deregister($addon_name);
1037 1037
 			}
1038 1038
 			remove_action(
1039
-				'deactivate_' . EE_Registry::instance()->addons->{$class_name}->get_main_plugin_file_basename(),
1040
-				array( EE_Registry::instance()->addons->{$class_name}, 'deactivation' )
1039
+				'deactivate_'.EE_Registry::instance()->addons->{$class_name}->get_main_plugin_file_basename(),
1040
+				array(EE_Registry::instance()->addons->{$class_name}, 'deactivation')
1041 1041
 			);
1042 1042
 			remove_action(
1043 1043
 				'AHEE__EE_System__perform_activations_upgrades_and_migrations',
1044
-				array( EE_Registry::instance()->addons->{$class_name}, 'initialize_db_if_no_migrations_required' )
1044
+				array(EE_Registry::instance()->addons->{$class_name}, 'initialize_db_if_no_migrations_required')
1045 1045
 			);
1046
-			unset( EE_Registry::instance()->addons->{$class_name}, self::$_settings[ $addon_name ] );
1046
+			unset(EE_Registry::instance()->addons->{$class_name}, self::$_settings[$addon_name]);
1047 1047
 		}
1048 1048
 	}
1049 1049
 
Please login to merge, or discard this patch.
modules/ticket_selector/EED_Ticket_Selector.module.php 2 patches
Indentation   +1207 added lines, -1207 removed lines patch added patch discarded remove patch
@@ -1,5 +1,5 @@  discard block
 block discarded – undo
1 1
 <?php if ( ! defined('EVENT_ESPRESSO_VERSION')) {
2
-    exit('No direct script access allowed');
2
+	exit('No direct script access allowed');
3 3
 }
4 4
 
5 5
 
@@ -14,1218 +14,1218 @@  discard block
 block discarded – undo
14 14
 class EED_Ticket_Selector extends EED_Module
15 15
 {
16 16
 
17
-    const debug = false;    //	true false
18
-
19
-    /**
20
-     * event that ticket selector is being generated for
21
-     *
22
-     * @access protected
23
-     * @var \EE_Event
24
-     */
25
-    protected static $_event;
26
-
27
-    /**
28
-     * array of datetimes and the spaces available for them
29
-     *
30
-     * @access private
31
-     * @var array
32
-     */
33
-    private static $_available_spaces = array();
34
-
35
-    /**
36
-     * max attendees that can register for event at one time
37
-     *
38
-     * @access private
39
-     * @var int
40
-     */
41
-    private static $_max_atndz = EE_INF;
42
-
43
-
44
-
45
-    /**
46
-     * Used to flag when the ticket selector is being called from an external iframe.
47
-     *
48
-     * @var bool
49
-     */
50
-    protected static $_in_iframe = false;
51
-
52
-
53
-
54
-    /**
55
-     * @return EED_Ticket_Selector
56
-     */
57
-    public static function instance()
58
-    {
59
-        return parent::get_instance(__CLASS__);
60
-    }
61
-
62
-
63
-
64
-    protected function set_config()
65
-    {
66
-        $this->set_config_section('template_settings');
67
-        $this->set_config_class('EE_Ticket_Selector_Config');
68
-        $this->set_config_name('EED_Ticket_Selector');
69
-    }
70
-
71
-
72
-
73
-    /**
74
-     *    set_hooks - for hooking into EE Core, other modules, etc
75
-     *
76
-     * @access    public
77
-     * @return    void
78
-     */
79
-    public static function set_hooks()
80
-    {
81
-        // routing
82
-        EE_Config::register_route('iframe', 'EED_Ticket_Selector', 'ticket_selector_iframe', 'ticket_selector');
83
-        EE_Config::register_route('process_ticket_selections', 'EED_Ticket_Selector', 'process_ticket_selections');
84
-        EE_Config::register_route('cancel_ticket_selections', 'EED_Ticket_Selector', 'cancel_ticket_selections');
85
-        add_action('wp_loaded', array('EED_Ticket_Selector', 'set_definitions'), 2);
86
-        add_action('AHEE_event_details_header_bottom', array('EED_Ticket_Selector', 'display_ticket_selector'), 10, 1);
87
-        add_action('wp_enqueue_scripts', array('EED_Ticket_Selector', 'load_tckt_slctr_assets'), 10);
88
-    }
89
-
90
-
91
-
92
-    /**
93
-     *    set_hooks_admin - for hooking into EE Admin Core, other modules, etc
94
-     *
95
-     * @access    public
96
-     * @return    void
97
-     */
98
-    public static function set_hooks_admin()
99
-    {
100
-        add_action('wp_loaded', array('EED_Ticket_Selector', 'set_definitions'), 2);
101
-        //add button for iframe code to event editor.
102
-        add_filter('get_sample_permalink_html', array('EED_Ticket_Selector', 'iframe_code_button'), 10, 2);
103
-        add_action('admin_enqueue_scripts', array('EED_Ticket_Selector', 'load_tckt_slctr_assets_admin'), 10);
104
-    }
105
-
106
-
107
-
108
-    /**
109
-     *    set_definitions
110
-     *
111
-     * @access    public
112
-     * @return    void
113
-     */
114
-    public static function set_definitions()
115
-    {
116
-        define('TICKET_SELECTOR_ASSETS_URL', plugin_dir_url(__FILE__) . 'assets' . DS);
117
-        define('TICKET_SELECTOR_TEMPLATES_PATH', str_replace('\\', DS, plugin_dir_path(__FILE__)) . 'templates' . DS);
118
-        //if config is not set, initialize
119
-        //If config is not set, set it.
120
-        if (EE_Registry::instance()->CFG->template_settings->EED_Ticket_Selector === null) {
121
-            EE_Registry::instance()->CFG->template_settings->EED_Ticket_Selector = new EE_Ticket_Selector_Config();
122
-        }
123
-        EE_Registry::$i18n_js_strings['ts_embed_iframe_title'] = __('Copy and Paste the following:', 'event_espresso');
124
-    }
125
-
126
-
127
-
128
-    /**
129
-     *    gets the ball rolling
130
-     *
131
-     * @access public
132
-     * @param    WP $WP
133
-     * @return void
134
-     */
135
-    public function run($WP)
136
-    {
137
-    }
138
-
139
-
140
-
141
-    /**
142
-     * ticket_selector_iframe
143
-     *
144
-     * @access    public
145
-     * @return    void
146
-     * @throws \EE_Error
147
-     */
148
-    public function ticket_selector_iframe()
149
-    {
150
-        self::$_in_iframe = true;
151
-        /** @type EEM_Event $EEM_Event */
152
-        $EEM_Event = EE_Registry::instance()->load_model('Event');
153
-        $event = $EEM_Event->get_one_by_ID(
154
-            EE_Registry::instance()->REQ->get('event', 0)
155
-        );
156
-        EE_Registry::instance()->REQ->set_espresso_page(true);
157
-        $template_args['ticket_selector'] = EED_Ticket_Selector::display_ticket_selector($event);
158
-        $template_args['css'] = apply_filters(
159
-            'FHEE__EED_Ticket_Selector__ticket_selector_iframe__css',
160
-            array(
161
-                TICKET_SELECTOR_ASSETS_URL . 'ticket_selector_embed.css?ver=' . EVENT_ESPRESSO_VERSION,
162
-                TICKET_SELECTOR_ASSETS_URL . 'ticket_selector.css?ver=' . EVENT_ESPRESSO_VERSION,
163
-                includes_url('css/dashicons.min.css?ver=' . $GLOBALS['wp_version']),
164
-                EE_GLOBAL_ASSETS_URL . 'css/espresso_default.css?ver=' . EVENT_ESPRESSO_VERSION,
165
-            )
166
-        );
167
-        EE_Registry::$i18n_js_strings['ticket_selector_iframe'] = true;
168
-        EE_Registry::$i18n_js_strings['EEDTicketSelectorMsg'] = esc_html__('Please choose at least one ticket before continuing.',
169
-            'event_espresso');
170
-        $template_args['eei18n'] = apply_filters(
171
-            'FHEE__EED_Ticket_Selector__ticket_selector_iframe__eei18n_js_strings',
172
-            EE_Registry::localize_i18n_js_strings()
173
-        );
174
-        $template_args['js'] = apply_filters(
175
-            'FHEE__EED_Ticket_Selector__ticket_selector_iframe__js',
176
-            array(
177
-                includes_url('js/jquery/jquery.js?ver=' . $GLOBALS['wp_version']),
178
-                EE_GLOBAL_ASSETS_URL . 'scripts/espresso_core.js?ver=' . EVENT_ESPRESSO_VERSION,
179
-                TICKET_SELECTOR_ASSETS_URL . 'ticket_selector_iframe_embed.js?ver=' . EVENT_ESPRESSO_VERSION,
180
-            )
181
-        );
182
-        $template_args['notices'] = EEH_Template::display_template(
183
-            EE_TEMPLATES . 'espresso-ajax-notices.template.php',
184
-            array(),
185
-            true
186
-        );
187
-        EEH_Template::display_template(
188
-            TICKET_SELECTOR_TEMPLATES_PATH . 'ticket_selector_chart_iframe.template.php',
189
-            $template_args
190
-        );
191
-        exit;
192
-    }
193
-
194
-
195
-
196
-    /**
197
-     * Adds an iframe embed code button to the Event editor.
198
-     *
199
-     * @param string $permalink_string The current html string for the permalink section.
200
-     * @param int    $id               The post id for the event.
201
-     * @return string The new html string for the permalink area.
202
-     */
203
-    public static function iframe_code_button($permalink_string, $id )
204
-    {
205
-        //make sure this is ONLY when editing and the event id has been set.
206
-        if ( ! empty($id)) {
207
-            $post = get_post($id);
208
-            //if NOT event then let's get out.
209
-            if ($post->post_type !== 'espresso_events') {
210
-                return $permalink_string;
211
-            }
212
-            $permalink_string .= '<a id="js-ticket-selector-embed-trigger" class="button button-small" href="#"  tabindex="-1">'
213
-                                 . __('Embed', 'event_espresso')
214
-                                 . '</a> ';
215
-            $ticket_selector_url = add_query_arg(array('ticket_selector' => 'iframe', 'event' => $id), site_url());
216
-            $iframe_string = esc_html(
217
-                '<iframe src="' . $ticket_selector_url . '" width="100%" height="100%"></iframe>'
218
-            );
219
-            $permalink_string .= '
17
+	const debug = false;    //	true false
18
+
19
+	/**
20
+	 * event that ticket selector is being generated for
21
+	 *
22
+	 * @access protected
23
+	 * @var \EE_Event
24
+	 */
25
+	protected static $_event;
26
+
27
+	/**
28
+	 * array of datetimes and the spaces available for them
29
+	 *
30
+	 * @access private
31
+	 * @var array
32
+	 */
33
+	private static $_available_spaces = array();
34
+
35
+	/**
36
+	 * max attendees that can register for event at one time
37
+	 *
38
+	 * @access private
39
+	 * @var int
40
+	 */
41
+	private static $_max_atndz = EE_INF;
42
+
43
+
44
+
45
+	/**
46
+	 * Used to flag when the ticket selector is being called from an external iframe.
47
+	 *
48
+	 * @var bool
49
+	 */
50
+	protected static $_in_iframe = false;
51
+
52
+
53
+
54
+	/**
55
+	 * @return EED_Ticket_Selector
56
+	 */
57
+	public static function instance()
58
+	{
59
+		return parent::get_instance(__CLASS__);
60
+	}
61
+
62
+
63
+
64
+	protected function set_config()
65
+	{
66
+		$this->set_config_section('template_settings');
67
+		$this->set_config_class('EE_Ticket_Selector_Config');
68
+		$this->set_config_name('EED_Ticket_Selector');
69
+	}
70
+
71
+
72
+
73
+	/**
74
+	 *    set_hooks - for hooking into EE Core, other modules, etc
75
+	 *
76
+	 * @access    public
77
+	 * @return    void
78
+	 */
79
+	public static function set_hooks()
80
+	{
81
+		// routing
82
+		EE_Config::register_route('iframe', 'EED_Ticket_Selector', 'ticket_selector_iframe', 'ticket_selector');
83
+		EE_Config::register_route('process_ticket_selections', 'EED_Ticket_Selector', 'process_ticket_selections');
84
+		EE_Config::register_route('cancel_ticket_selections', 'EED_Ticket_Selector', 'cancel_ticket_selections');
85
+		add_action('wp_loaded', array('EED_Ticket_Selector', 'set_definitions'), 2);
86
+		add_action('AHEE_event_details_header_bottom', array('EED_Ticket_Selector', 'display_ticket_selector'), 10, 1);
87
+		add_action('wp_enqueue_scripts', array('EED_Ticket_Selector', 'load_tckt_slctr_assets'), 10);
88
+	}
89
+
90
+
91
+
92
+	/**
93
+	 *    set_hooks_admin - for hooking into EE Admin Core, other modules, etc
94
+	 *
95
+	 * @access    public
96
+	 * @return    void
97
+	 */
98
+	public static function set_hooks_admin()
99
+	{
100
+		add_action('wp_loaded', array('EED_Ticket_Selector', 'set_definitions'), 2);
101
+		//add button for iframe code to event editor.
102
+		add_filter('get_sample_permalink_html', array('EED_Ticket_Selector', 'iframe_code_button'), 10, 2);
103
+		add_action('admin_enqueue_scripts', array('EED_Ticket_Selector', 'load_tckt_slctr_assets_admin'), 10);
104
+	}
105
+
106
+
107
+
108
+	/**
109
+	 *    set_definitions
110
+	 *
111
+	 * @access    public
112
+	 * @return    void
113
+	 */
114
+	public static function set_definitions()
115
+	{
116
+		define('TICKET_SELECTOR_ASSETS_URL', plugin_dir_url(__FILE__) . 'assets' . DS);
117
+		define('TICKET_SELECTOR_TEMPLATES_PATH', str_replace('\\', DS, plugin_dir_path(__FILE__)) . 'templates' . DS);
118
+		//if config is not set, initialize
119
+		//If config is not set, set it.
120
+		if (EE_Registry::instance()->CFG->template_settings->EED_Ticket_Selector === null) {
121
+			EE_Registry::instance()->CFG->template_settings->EED_Ticket_Selector = new EE_Ticket_Selector_Config();
122
+		}
123
+		EE_Registry::$i18n_js_strings['ts_embed_iframe_title'] = __('Copy and Paste the following:', 'event_espresso');
124
+	}
125
+
126
+
127
+
128
+	/**
129
+	 *    gets the ball rolling
130
+	 *
131
+	 * @access public
132
+	 * @param    WP $WP
133
+	 * @return void
134
+	 */
135
+	public function run($WP)
136
+	{
137
+	}
138
+
139
+
140
+
141
+	/**
142
+	 * ticket_selector_iframe
143
+	 *
144
+	 * @access    public
145
+	 * @return    void
146
+	 * @throws \EE_Error
147
+	 */
148
+	public function ticket_selector_iframe()
149
+	{
150
+		self::$_in_iframe = true;
151
+		/** @type EEM_Event $EEM_Event */
152
+		$EEM_Event = EE_Registry::instance()->load_model('Event');
153
+		$event = $EEM_Event->get_one_by_ID(
154
+			EE_Registry::instance()->REQ->get('event', 0)
155
+		);
156
+		EE_Registry::instance()->REQ->set_espresso_page(true);
157
+		$template_args['ticket_selector'] = EED_Ticket_Selector::display_ticket_selector($event);
158
+		$template_args['css'] = apply_filters(
159
+			'FHEE__EED_Ticket_Selector__ticket_selector_iframe__css',
160
+			array(
161
+				TICKET_SELECTOR_ASSETS_URL . 'ticket_selector_embed.css?ver=' . EVENT_ESPRESSO_VERSION,
162
+				TICKET_SELECTOR_ASSETS_URL . 'ticket_selector.css?ver=' . EVENT_ESPRESSO_VERSION,
163
+				includes_url('css/dashicons.min.css?ver=' . $GLOBALS['wp_version']),
164
+				EE_GLOBAL_ASSETS_URL . 'css/espresso_default.css?ver=' . EVENT_ESPRESSO_VERSION,
165
+			)
166
+		);
167
+		EE_Registry::$i18n_js_strings['ticket_selector_iframe'] = true;
168
+		EE_Registry::$i18n_js_strings['EEDTicketSelectorMsg'] = esc_html__('Please choose at least one ticket before continuing.',
169
+			'event_espresso');
170
+		$template_args['eei18n'] = apply_filters(
171
+			'FHEE__EED_Ticket_Selector__ticket_selector_iframe__eei18n_js_strings',
172
+			EE_Registry::localize_i18n_js_strings()
173
+		);
174
+		$template_args['js'] = apply_filters(
175
+			'FHEE__EED_Ticket_Selector__ticket_selector_iframe__js',
176
+			array(
177
+				includes_url('js/jquery/jquery.js?ver=' . $GLOBALS['wp_version']),
178
+				EE_GLOBAL_ASSETS_URL . 'scripts/espresso_core.js?ver=' . EVENT_ESPRESSO_VERSION,
179
+				TICKET_SELECTOR_ASSETS_URL . 'ticket_selector_iframe_embed.js?ver=' . EVENT_ESPRESSO_VERSION,
180
+			)
181
+		);
182
+		$template_args['notices'] = EEH_Template::display_template(
183
+			EE_TEMPLATES . 'espresso-ajax-notices.template.php',
184
+			array(),
185
+			true
186
+		);
187
+		EEH_Template::display_template(
188
+			TICKET_SELECTOR_TEMPLATES_PATH . 'ticket_selector_chart_iframe.template.php',
189
+			$template_args
190
+		);
191
+		exit;
192
+	}
193
+
194
+
195
+
196
+	/**
197
+	 * Adds an iframe embed code button to the Event editor.
198
+	 *
199
+	 * @param string $permalink_string The current html string for the permalink section.
200
+	 * @param int    $id               The post id for the event.
201
+	 * @return string The new html string for the permalink area.
202
+	 */
203
+	public static function iframe_code_button($permalink_string, $id )
204
+	{
205
+		//make sure this is ONLY when editing and the event id has been set.
206
+		if ( ! empty($id)) {
207
+			$post = get_post($id);
208
+			//if NOT event then let's get out.
209
+			if ($post->post_type !== 'espresso_events') {
210
+				return $permalink_string;
211
+			}
212
+			$permalink_string .= '<a id="js-ticket-selector-embed-trigger" class="button button-small" href="#"  tabindex="-1">'
213
+								 . __('Embed', 'event_espresso')
214
+								 . '</a> ';
215
+			$ticket_selector_url = add_query_arg(array('ticket_selector' => 'iframe', 'event' => $id), site_url());
216
+			$iframe_string = esc_html(
217
+				'<iframe src="' . $ticket_selector_url . '" width="100%" height="100%"></iframe>'
218
+			);
219
+			$permalink_string .= '
220 220
 <div id="js-ts-iframe" style="display:none">
221 221
 	<div style="width:100%; height: 500px;">
222 222
 		' . $iframe_string . '
223 223
 	</div>
224 224
 </div>';
225
-        }
226
-        return $permalink_string;
227
-    }
228
-
229
-
230
-
231
-    /**
232
-     *    finds and sets the EE_Event object for use throughout class
233
-     *
234
-     * @access    public
235
-     * @param    mixed $event
236
-     * @return    bool
237
-     */
238
-    protected static function set_event($event = null)
239
-    {
240
-        if ($event === null) {
241
-            global $post;
242
-            $event = $post;
243
-        }
244
-        if ($event instanceof EE_Event) {
245
-            self::$_event = $event;
246
-        } else if ($event instanceof WP_Post ) {
247
-            if ( isset($event->EE_Event) && $event->EE_Event instanceof EE_Event) {
248
-                self::$_event = $event->EE_Event;
249
-            } else if ( $event->post_type === 'espresso_events') {
250
-                $event->EE_Event = EEM_Event::instance()->instantiate_class_from_post_object($event);
251
-                self::$_event = $event->EE_Event;
252
-            }
253
-        } else {
254
-            $user_msg = __('No Event object or an invalid Event object was supplied.', 'event_espresso');
255
-            $dev_msg = $user_msg
256
-                       . __('In order to generate a ticket selector, please ensure you are passing either an EE_Event object or a WP_Post object of the post type "espresso_event" to the EE_Ticket_Selector class constructor.',
257
-                    'event_espresso');
258
-            EE_Error::add_error($user_msg . '||' . $dev_msg, __FILE__, __FUNCTION__, __LINE__);
259
-            return false;
260
-        }
261
-        return true;
262
-    }
263
-
264
-
265
-
266
-    /**
267
-     * creates buttons for selecting number of attendees for an event
268
-     *
269
-     * @access public
270
-     * @param EE_Event $event
271
-     * @param bool     $view_details
272
-     * @return string
273
-     * @throws \EE_Error
274
-     */
275
-    public static function display_ticket_selector($event = null, $view_details = false)
276
-    {
277
-        // reset filter for displaying submit button
278
-        remove_filter('FHEE__EE_Ticket_Selector__display_ticket_selector_submit', '__return_true');
279
-        // poke and prod incoming event till it tells us what it is
280
-        if ( ! EED_Ticket_Selector::set_event($event)) {
281
-            return false;
282
-        }
283
-        $event_post = self::$_event instanceof EE_Event ? self::$_event->ID() : $event;
284
-        // grab event status
285
-        $_event_active_status = self::$_event->get_active_status();
286
-        if (
287
-            ! is_admin()
288
-            && (
289
-                ! self::$_event->display_ticket_selector()
290
-                || $view_details
291
-                || post_password_required($event_post)
292
-                || (
293
-                    $_event_active_status !== EE_Datetime::active
294
-                    && $_event_active_status !== EE_Datetime::upcoming
295
-                    && $_event_active_status !== EE_Datetime::sold_out
296
-                    && ! (
297
-                        $_event_active_status === EE_Datetime::inactive
298
-                        && is_user_logged_in()
299
-                    )
300
-                )
301
-            )
302
-        ) {
303
-            return ! is_single() ? EED_Ticket_Selector::display_view_details_btn() : '';
304
-        }
305
-        $template_args = array();
306
-        $template_args['event_status'] = $_event_active_status;
307
-        $template_args['date_format'] = apply_filters('FHEE__EED_Ticket_Selector__display_ticket_selector__date_format',
308
-            get_option('date_format'));
309
-        $template_args['time_format'] = apply_filters('FHEE__EED_Ticket_Selector__display_ticket_selector__time_format',
310
-            get_option('time_format'));
311
-        $template_args['EVT_ID'] = self::$_event->ID();
312
-        $template_args['event'] = self::$_event;
313
-        // is the event expired ?
314
-        $template_args['event_is_expired'] = self::$_event->is_expired();
315
-        if ($template_args['event_is_expired']) {
316
-            return '<div class="ee-event-expired-notice"><span class="important-notice">'
317
-                   . __('We\'re sorry, but all tickets sales have ended because the event is expired.',
318
-                'event_espresso')
319
-                   . '</span></div>';
320
-        }
321
-        $ticket_query_args = array(
322
-            array('Datetime.EVT_ID' => self::$_event->ID()),
323
-            'order_by' => array(
324
-                'TKT_order'              => 'ASC',
325
-                'TKT_required'           => 'DESC',
326
-                'TKT_start_date'         => 'ASC',
327
-                'TKT_end_date'           => 'ASC',
328
-                'Datetime.DTT_EVT_start' => 'DESC',
329
-            ),
330
-        );
331
-        if ( ! EE_Registry::instance()->CFG->template_settings->EED_Ticket_Selector->show_expired_tickets) {
332
-            //use the correct applicable time query depending on what version of core is being run.
333
-            $current_time = method_exists('EEM_Datetime', 'current_time_for_query') ? time()
334
-                : current_time('timestamp');
335
-            $ticket_query_args[0]['TKT_end_date'] = array('>', $current_time);
336
-        }
337
-        // get all tickets for this event ordered by the datetime
338
-        $template_args['tickets'] = EEM_Ticket::instance()->get_all($ticket_query_args);
339
-        if (count($template_args['tickets']) < 1) {
340
-            return '<div class="ee-event-expired-notice"><span class="important-notice">'
341
-                   . __('We\'re sorry, but all ticket sales have ended.', 'event_espresso')
342
-                   . '</span></div>';
343
-        }
344
-        // filter the maximum qty that can appear in the Ticket Selector qty dropdowns
345
-        \EED_Ticket_Selector::$_max_atndz = apply_filters(
346
-            'FHEE__EE_Ticket_Selector__display_ticket_selector__max_tickets',
347
-            self::$_event->additional_limit()
348
-        );
349
-        $template_args['max_atndz'] = \EED_Ticket_Selector::$_max_atndz;
350
-        if ($template_args['max_atndz'] < 1) {
351
-            $sales_closed_msg = __('We\'re sorry, but ticket sales have been closed at this time. Please check back again later.',
352
-                'event_espresso');
353
-            if (current_user_can('edit_post', self::$_event->ID())) {
354
-                $sales_closed_msg .= sprintf(
355
-                    __('%sNote to Event Admin:%sThe "Maximum number of tickets allowed per order for this event" in the Event Registration Options has been set to "0". This effectively turns off ticket sales. %s(click to edit this event)%s',
356
-                        'event_espresso'),
357
-                    '<div class="ee-attention" style="text-align: left;"><b>',
358
-                    '</b><br />',
359
-                    $link = '<span class="edit-link"><a class="post-edit-link" href="'
360
-                            . get_edit_post_link(self::$_event->ID())
361
-                            . '">',
362
-                    '</a></span></div>'
363
-                );
364
-            }
365
-            return '<p><span class="important-notice">' . $sales_closed_msg . '</span></p>';
366
-        }
367
-        $templates['ticket_selector'] = TICKET_SELECTOR_TEMPLATES_PATH . 'ticket_selector_chart.template.php';
368
-        $templates['ticket_selector'] = apply_filters('FHEE__EE_Ticket_Selector__display_ticket_selector__template_path',
369
-            $templates['ticket_selector'], self::$_event);
370
-        // redirecting to another site for registration ??
371
-        $external_url = self::$_event->external_url() !== null || self::$_event->external_url() !== ''
372
-            ? self::$_event->external_url() : false;
373
-        // if not redirecting to another site for registration
374
-        if ( ! $external_url) {
375
-            // then display the ticket selector
376
-            $ticket_selector = EEH_Template::locate_template($templates['ticket_selector'], $template_args);
377
-        } else {
378
-            // if not we still need to trigger the display of the submit button
379
-            add_filter('FHEE__EE_Ticket_Selector__display_ticket_selector_submit', '__return_true');
380
-            //display notice to admin that registration is external
381
-            $ticket_selector = ! is_admin() ? ''
382
-                : __('Registration is at an external URL for this event.', 'event_espresso');
383
-        }
384
-        // now set up the form (but not for the admin)
385
-        $ticket_selector = ! is_admin()
386
-            ? EED_Ticket_Selector::ticket_selector_form_open(
387
-                self::$_event->ID(),
388
-                $external_url
389
-            ) . $ticket_selector
390
-            : $ticket_selector;
391
-        // submit button and form close tag
392
-        $ticket_selector .= ! is_admin() ? EED_Ticket_Selector::display_ticket_selector_submit($external_url) : '';
393
-        // set no cache headers and constants
394
-        EE_System::do_not_cache();
395
-        return $ticket_selector;
396
-    }
397
-
398
-
399
-
400
-    /**
401
-     *    ticket_selector_form_open
402
-     *
403
-     * @access        public
404
-     * @param        int    $ID
405
-     * @param        string $external_url
406
-     * @return        string
407
-     */
408
-    public static function ticket_selector_form_open($ID = 0, $external_url = '')
409
-    {
410
-        // if redirecting, we don't need any anything else
411
-        if ($external_url) {
412
-            $html = '<form method="GET" action="' . EEH_URL::refactor_url($external_url) . '"';
413
-            // open link in new window ?
414
-            $html .= apply_filters(
415
-                'FHEE__EventEspresso_modules_ticket_selector_DisplayTicketSelector__formOpen__external_url_target_blank',
416
-                false
417
-            )
418
-                ? ' target="_blank"'
419
-                : '';
420
-            $html .= '>';
421
-            $query_args = (array)EEH_URL::get_query_string($external_url);
422
-            foreach ($query_args as $query_arg => $value) {
423
-                $html .= '
225
+		}
226
+		return $permalink_string;
227
+	}
228
+
229
+
230
+
231
+	/**
232
+	 *    finds and sets the EE_Event object for use throughout class
233
+	 *
234
+	 * @access    public
235
+	 * @param    mixed $event
236
+	 * @return    bool
237
+	 */
238
+	protected static function set_event($event = null)
239
+	{
240
+		if ($event === null) {
241
+			global $post;
242
+			$event = $post;
243
+		}
244
+		if ($event instanceof EE_Event) {
245
+			self::$_event = $event;
246
+		} else if ($event instanceof WP_Post ) {
247
+			if ( isset($event->EE_Event) && $event->EE_Event instanceof EE_Event) {
248
+				self::$_event = $event->EE_Event;
249
+			} else if ( $event->post_type === 'espresso_events') {
250
+				$event->EE_Event = EEM_Event::instance()->instantiate_class_from_post_object($event);
251
+				self::$_event = $event->EE_Event;
252
+			}
253
+		} else {
254
+			$user_msg = __('No Event object or an invalid Event object was supplied.', 'event_espresso');
255
+			$dev_msg = $user_msg
256
+					   . __('In order to generate a ticket selector, please ensure you are passing either an EE_Event object or a WP_Post object of the post type "espresso_event" to the EE_Ticket_Selector class constructor.',
257
+					'event_espresso');
258
+			EE_Error::add_error($user_msg . '||' . $dev_msg, __FILE__, __FUNCTION__, __LINE__);
259
+			return false;
260
+		}
261
+		return true;
262
+	}
263
+
264
+
265
+
266
+	/**
267
+	 * creates buttons for selecting number of attendees for an event
268
+	 *
269
+	 * @access public
270
+	 * @param EE_Event $event
271
+	 * @param bool     $view_details
272
+	 * @return string
273
+	 * @throws \EE_Error
274
+	 */
275
+	public static function display_ticket_selector($event = null, $view_details = false)
276
+	{
277
+		// reset filter for displaying submit button
278
+		remove_filter('FHEE__EE_Ticket_Selector__display_ticket_selector_submit', '__return_true');
279
+		// poke and prod incoming event till it tells us what it is
280
+		if ( ! EED_Ticket_Selector::set_event($event)) {
281
+			return false;
282
+		}
283
+		$event_post = self::$_event instanceof EE_Event ? self::$_event->ID() : $event;
284
+		// grab event status
285
+		$_event_active_status = self::$_event->get_active_status();
286
+		if (
287
+			! is_admin()
288
+			&& (
289
+				! self::$_event->display_ticket_selector()
290
+				|| $view_details
291
+				|| post_password_required($event_post)
292
+				|| (
293
+					$_event_active_status !== EE_Datetime::active
294
+					&& $_event_active_status !== EE_Datetime::upcoming
295
+					&& $_event_active_status !== EE_Datetime::sold_out
296
+					&& ! (
297
+						$_event_active_status === EE_Datetime::inactive
298
+						&& is_user_logged_in()
299
+					)
300
+				)
301
+			)
302
+		) {
303
+			return ! is_single() ? EED_Ticket_Selector::display_view_details_btn() : '';
304
+		}
305
+		$template_args = array();
306
+		$template_args['event_status'] = $_event_active_status;
307
+		$template_args['date_format'] = apply_filters('FHEE__EED_Ticket_Selector__display_ticket_selector__date_format',
308
+			get_option('date_format'));
309
+		$template_args['time_format'] = apply_filters('FHEE__EED_Ticket_Selector__display_ticket_selector__time_format',
310
+			get_option('time_format'));
311
+		$template_args['EVT_ID'] = self::$_event->ID();
312
+		$template_args['event'] = self::$_event;
313
+		// is the event expired ?
314
+		$template_args['event_is_expired'] = self::$_event->is_expired();
315
+		if ($template_args['event_is_expired']) {
316
+			return '<div class="ee-event-expired-notice"><span class="important-notice">'
317
+				   . __('We\'re sorry, but all tickets sales have ended because the event is expired.',
318
+				'event_espresso')
319
+				   . '</span></div>';
320
+		}
321
+		$ticket_query_args = array(
322
+			array('Datetime.EVT_ID' => self::$_event->ID()),
323
+			'order_by' => array(
324
+				'TKT_order'              => 'ASC',
325
+				'TKT_required'           => 'DESC',
326
+				'TKT_start_date'         => 'ASC',
327
+				'TKT_end_date'           => 'ASC',
328
+				'Datetime.DTT_EVT_start' => 'DESC',
329
+			),
330
+		);
331
+		if ( ! EE_Registry::instance()->CFG->template_settings->EED_Ticket_Selector->show_expired_tickets) {
332
+			//use the correct applicable time query depending on what version of core is being run.
333
+			$current_time = method_exists('EEM_Datetime', 'current_time_for_query') ? time()
334
+				: current_time('timestamp');
335
+			$ticket_query_args[0]['TKT_end_date'] = array('>', $current_time);
336
+		}
337
+		// get all tickets for this event ordered by the datetime
338
+		$template_args['tickets'] = EEM_Ticket::instance()->get_all($ticket_query_args);
339
+		if (count($template_args['tickets']) < 1) {
340
+			return '<div class="ee-event-expired-notice"><span class="important-notice">'
341
+				   . __('We\'re sorry, but all ticket sales have ended.', 'event_espresso')
342
+				   . '</span></div>';
343
+		}
344
+		// filter the maximum qty that can appear in the Ticket Selector qty dropdowns
345
+		\EED_Ticket_Selector::$_max_atndz = apply_filters(
346
+			'FHEE__EE_Ticket_Selector__display_ticket_selector__max_tickets',
347
+			self::$_event->additional_limit()
348
+		);
349
+		$template_args['max_atndz'] = \EED_Ticket_Selector::$_max_atndz;
350
+		if ($template_args['max_atndz'] < 1) {
351
+			$sales_closed_msg = __('We\'re sorry, but ticket sales have been closed at this time. Please check back again later.',
352
+				'event_espresso');
353
+			if (current_user_can('edit_post', self::$_event->ID())) {
354
+				$sales_closed_msg .= sprintf(
355
+					__('%sNote to Event Admin:%sThe "Maximum number of tickets allowed per order for this event" in the Event Registration Options has been set to "0". This effectively turns off ticket sales. %s(click to edit this event)%s',
356
+						'event_espresso'),
357
+					'<div class="ee-attention" style="text-align: left;"><b>',
358
+					'</b><br />',
359
+					$link = '<span class="edit-link"><a class="post-edit-link" href="'
360
+							. get_edit_post_link(self::$_event->ID())
361
+							. '">',
362
+					'</a></span></div>'
363
+				);
364
+			}
365
+			return '<p><span class="important-notice">' . $sales_closed_msg . '</span></p>';
366
+		}
367
+		$templates['ticket_selector'] = TICKET_SELECTOR_TEMPLATES_PATH . 'ticket_selector_chart.template.php';
368
+		$templates['ticket_selector'] = apply_filters('FHEE__EE_Ticket_Selector__display_ticket_selector__template_path',
369
+			$templates['ticket_selector'], self::$_event);
370
+		// redirecting to another site for registration ??
371
+		$external_url = self::$_event->external_url() !== null || self::$_event->external_url() !== ''
372
+			? self::$_event->external_url() : false;
373
+		// if not redirecting to another site for registration
374
+		if ( ! $external_url) {
375
+			// then display the ticket selector
376
+			$ticket_selector = EEH_Template::locate_template($templates['ticket_selector'], $template_args);
377
+		} else {
378
+			// if not we still need to trigger the display of the submit button
379
+			add_filter('FHEE__EE_Ticket_Selector__display_ticket_selector_submit', '__return_true');
380
+			//display notice to admin that registration is external
381
+			$ticket_selector = ! is_admin() ? ''
382
+				: __('Registration is at an external URL for this event.', 'event_espresso');
383
+		}
384
+		// now set up the form (but not for the admin)
385
+		$ticket_selector = ! is_admin()
386
+			? EED_Ticket_Selector::ticket_selector_form_open(
387
+				self::$_event->ID(),
388
+				$external_url
389
+			) . $ticket_selector
390
+			: $ticket_selector;
391
+		// submit button and form close tag
392
+		$ticket_selector .= ! is_admin() ? EED_Ticket_Selector::display_ticket_selector_submit($external_url) : '';
393
+		// set no cache headers and constants
394
+		EE_System::do_not_cache();
395
+		return $ticket_selector;
396
+	}
397
+
398
+
399
+
400
+	/**
401
+	 *    ticket_selector_form_open
402
+	 *
403
+	 * @access        public
404
+	 * @param        int    $ID
405
+	 * @param        string $external_url
406
+	 * @return        string
407
+	 */
408
+	public static function ticket_selector_form_open($ID = 0, $external_url = '')
409
+	{
410
+		// if redirecting, we don't need any anything else
411
+		if ($external_url) {
412
+			$html = '<form method="GET" action="' . EEH_URL::refactor_url($external_url) . '"';
413
+			// open link in new window ?
414
+			$html .= apply_filters(
415
+				'FHEE__EventEspresso_modules_ticket_selector_DisplayTicketSelector__formOpen__external_url_target_blank',
416
+				false
417
+			)
418
+				? ' target="_blank"'
419
+				: '';
420
+			$html .= '>';
421
+			$query_args = (array)EEH_URL::get_query_string($external_url);
422
+			foreach ($query_args as $query_arg => $value) {
423
+				$html .= '
424 424
 				<input type="hidden" name="' . $query_arg . '" value="' . $value . '">';
425
-            }
426
-            return $html;
427
-        }
428
-        // if there is no submit button, then don't start building a form
429
-        // because the "View Details" button will build its own form
430
-        if ( ! apply_filters('FHEE__EE_Ticket_Selector__display_ticket_selector_submit', false)) {
431
-            return '';
432
-        }
433
-        $checkout_url = EEH_Event_View::event_link_url($ID);
434
-        if ( ! $checkout_url) {
435
-            EE_Error::add_error(__('The URL for the Event Details page could not be retrieved.', 'event_espresso'),
436
-                __FILE__, __FUNCTION__, __LINE__);
437
-        }
438
-        $extra_params = self::$_in_iframe ? ' target="_blank"' : '';
439
-        $html = '<form method="POST" action="' . $checkout_url . '"' . $extra_params . '>';
440
-        $html .= wp_nonce_field('process_ticket_selections', 'process_ticket_selections_nonce_' . $ID, true, false);
441
-        $html .= '<input type="hidden" name="ee" value="process_ticket_selections">';
442
-        $html = apply_filters('FHEE__EE_Ticket_Selector__ticket_selector_form_open__html', $html, self::$_event);
443
-        return $html;
444
-    }
445
-
446
-
447
-
448
-    /**
449
-     * display_ticket_selector_submit
450
-     *
451
-     * @param        string $external_url
452
-     * @return        string
453
-     * @throws \EE_Error
454
-     */
455
-    public static function display_ticket_selector_submit($external_url = '')
456
-    {
457
-        $html = '';
458
-        if ( ! is_admin()) {
459
-            // standard TS displayed with submit button, ie: "Register Now"
460
-            if (apply_filters('FHEE__EE_Ticket_Selector__display_ticket_selector_submit', false)) {
461
-                $html .= \EED_Ticket_Selector::display_register_now_button();
462
-                $html .= empty($external_url) ?
463
-                    \EED_Ticket_Selector::no_tkt_slctr_end_dv()
464
-                    : \EED_Ticket_Selector::clear_tkt_slctr();
465
-                $html .= '<br/>' . \EED_Ticket_Selector::ticket_selector_form_close();
466
-            } else if ( EED_Ticket_Selector::$_max_atndz === 1 ) {
467
-                // its a "Dude Where's my Ticket Selector?" (DWMTS) type event (ie: $_max_atndz === 1)
468
-                if ( EED_Ticket_Selector::$_event->is_sold_out() ) {
469
-                    // then instead of a View Details or Submit button, just display a "Sold Out" message
470
-                    $html .= apply_filters(
471
-                        'FHEE__EE_Ticket_Selector__display_ticket_selector_submit__sold_out_msg',
472
-                        sprintf(
473
-                            __(
474
-                                '%1$s"%2$s" is currently sold out.%4$sPlease check back again later, as spots may become available.%3$s',
475
-                                'event_espresso'
476
-                            ),
477
-                            '<p class="no-ticket-selector-msg clear-float">',
478
-                            EED_Ticket_Selector::$_event->name(),
479
-                            '</p>',
480
-                            '<br />'
481
-                        ),
482
-                        EED_Ticket_Selector::$_event
483
-                    );
484
-                    if (
485
-                        apply_filters(
486
-                            'FHEE__EE_Ticket_Selector__display_ticket_selector_submit__no_tickets_but_display_register_now_button',
487
-                            false,
488
-                            EED_Ticket_Selector::$_event
489
-                        )
490
-                    ) {
491
-                        $html .= \EED_Ticket_Selector::display_register_now_button();
492
-                    }
493
-                    // sold out DWMTS event, no TS, no submit or view details button, but has additional content
494
-                    $html .= \EED_Ticket_Selector::no_tkt_slctr_end_dv();
495
-                } else if (
496
-                    apply_filters('FHEE__EE_Ticket_Selector__hide_ticket_selector', false)
497
-                    && ! is_single()
498
-                ) {
499
-                    // this is a "Dude Where's my Ticket Selector?" (DWMTS) type event,
500
-                    // but no tickets are available, so display event's "View Details" button.
501
-                    // it is being viewed via somewhere other than a single post
502
-                    $html .= EED_Ticket_Selector::display_view_details_btn(true);
503
-                }
504
-            } else if (is_archive()) {
505
-                // event list, no tickets available so display event's "View Details" button
506
-                $html .= \EED_Ticket_Selector::no_tkt_slctr_end_dv();
507
-                $html .= EED_Ticket_Selector::display_view_details_btn();
508
-            } else {
509
-                if (
510
-                    apply_filters(
511
-                        'FHEE__EE_Ticket_Selector__display_ticket_selector_submit__no_tickets_but_display_register_now_button',
512
-                        false,
513
-                        EED_Ticket_Selector::$_event
514
-                    )
515
-                ) {
516
-                    $html .= \EED_Ticket_Selector::display_register_now_button();
517
-                }
518
-                // no submit or view details button, and no additional content
519
-                $html .= \EED_Ticket_Selector::no_tkt_slctr_end_dv();
520
-            }
521
-            if ( ! is_archive()) {
522
-                $html .= \EEH_Template::powered_by_event_espresso('', '', array('utm_content' => 'ticket_selector'));
523
-            }
524
-        }
525
-        return $html;
526
-    }
527
-
528
-
529
-
530
-    /**
531
-     * @return string
532
-     */
533
-    public static function clear_tkt_slctr()
534
-    {
535
-        // standard TS displayed, appears after a "Register Now" or "view Details" button
536
-        return '<div class="clear"></div>';
537
-    }
538
-
539
-
540
-
541
-    /**
542
-     * @deprecated 4.9.13
543
-     * @return string
544
-     */
545
-    public static function tkt_slctr_end_dv()
546
-    {
547
-        return \EED_Ticket_Selector::clear_tkt_slctr();
548
-    }
549
-
550
-
551
-
552
-    /**
553
-     * @return string
554
-     */
555
-    public static function no_tkt_slctr_end_dv()
556
-    {
557
-        // DWMTS event, no TS, appears after a "Register Now" or "view Details" button
558
-        return '<div class="clear"></div></div>';
559
-    }
560
-
561
-
562
-
563
-    /**
564
-     *    ticket_selector_form_close
565
-     *
566
-     * @access        public
567
-     * @access        public
568
-     * @return        string
569
-     */
570
-    public static function ticket_selector_form_close()
571
-    {
572
-        return '</form>';
573
-    }
574
-
575
-
576
-
577
-    /**
578
-     * @return string
579
-     * @throws \EE_Error
580
-     */
581
-    public static function display_register_now_button()
582
-    {
583
-        $btn_text = apply_filters(
584
-            'FHEE__EE_Ticket_Selector__display_ticket_selector_submit__btn_text',
585
-            __('Register Now', 'event_espresso'),
586
-            EED_Ticket_Selector::$_event
587
-        );
588
-        $external_url = EED_Ticket_Selector::$_event->external_url();
589
-        $html = '<input id="ticket-selector-submit-' . EED_Ticket_Selector::$_event->ID() . '-btn"';
590
-        $html .= ' class="ticket-selector-submit-btn ';
591
-        $html .= empty($external_url) ? 'ticket-selector-submit-ajax"' : '"';
592
-        $html .= ' type="submit" value="' . $btn_text . '" />';
593
-        $html .= apply_filters(
594
-            'FHEE__EE_Ticket_Selector__after_ticket_selector_submit',
595
-            '',
596
-            EED_Ticket_Selector::$_event
597
-        );
598
-        return $html;
599
-    }
600
-
601
-
602
-    /**
603
-     * display_view_details_btn
604
-     *
605
-     * @access public
606
-     * @param bool $DWMTS indicates a "Dude Where's my Ticket Selector?" (DWMTS) type event
607
-     *                    (ie: $_max_atndz === 1) where there are no available tickets,
608
-     *                    either because they are sold out, expired, or not yet on sale.
609
-     *                    In this case, we need to close the form BEFORE adding any closing divs
610
-     * @return string
611
-     * @throws \EE_Error
612
-     */
613
-    public static function display_view_details_btn($DWMTS = false)
614
-    {
615
-        if ( ! self::$_event->get_permalink()) {
616
-            EE_Error::add_error(
617
-                __('The URL for the Event Details page could not be retrieved.', 'event_espresso'),
618
-                __FILE__, __FUNCTION__, __LINE__
619
-            );
620
-        }
621
-        $view_details_btn = '<form method="POST" action="';
622
-        $view_details_btn .= apply_filters(
623
-            'FHEE__EE_Ticket_Selector__display_view_details_btn__btn_url',
624
-            self::$_event->get_permalink(),
625
-            self::$_event
626
-        );
627
-        $view_details_btn .= '">';
628
-        $btn_text = apply_filters(
629
-            'FHEE__EE_Ticket_Selector__display_view_details_btn__btn_text',
630
-            __('View Details', 'event_espresso'),
631
-            self::$_event
632
-        );
633
-        $view_details_btn .= '<input id="ticket-selector-submit-'
634
-                             . self::$_event->ID()
635
-                             . '-btn" class="ticket-selector-submit-btn view-details-btn" type="submit" value="'
636
-                             . $btn_text
637
-                             . '" />';
638
-        $view_details_btn .= apply_filters('FHEE__EE_Ticket_Selector__after_view_details_btn', '', self::$_event);
639
-        if ($DWMTS) {
640
-            $view_details_btn .= \EED_Ticket_Selector::ticket_selector_form_close();
641
-            $view_details_btn .= \EED_Ticket_Selector::no_tkt_slctr_end_dv();
642
-            $view_details_btn .= '<br/>';
643
-        } else {
644
-            $view_details_btn .= \EED_Ticket_Selector::clear_tkt_slctr();
645
-            $view_details_btn .= '<br/>';
646
-            $view_details_btn .= \EED_Ticket_Selector::ticket_selector_form_close();
647
-        }
648
-        return $view_details_btn;
649
-    }
650
-
651
-
652
-
653
-    /**
654
-     *    cancel_ticket_selections
655
-     *
656
-     * @access        public
657
-     * @access        public
658
-     * @return        string
659
-     */
660
-    public static function cancel_ticket_selections()
661
-    {
662
-        // check nonce
663
-        if ( ! EED_Ticket_Selector::process_ticket_selector_nonce('cancel_ticket_selections')) {
664
-            return false;
665
-        }
666
-        EE_Registry::instance()->SSN->clear_session(__CLASS__, __FUNCTION__);
667
-        if (EE_Registry::instance()->REQ->is_set('event_id')) {
668
-            wp_safe_redirect(
669
-                EEH_Event_View::event_link_url(
670
-                    EE_Registry::instance()->REQ->get('event_id')
671
-                )
672
-            );
673
-        } else {
674
-            wp_safe_redirect(
675
-                site_url('/' . EE_Registry::instance()->CFG->core->event_cpt_slug . '/')
676
-            );
677
-        }
678
-        die();
679
-    }
680
-
681
-
682
-
683
-    /**
684
-     *    process_ticket_selector_nonce
685
-     *
686
-     * @access public
687
-     * @param  string $nonce_name
688
-     * @param string  $id
689
-     * @return bool
690
-     */
691
-    public static function process_ticket_selector_nonce($nonce_name, $id = '')
692
-    {
693
-        $nonce_name_with_id = ! empty($id) ? "{$nonce_name}_nonce_{$id}" : "{$nonce_name}_nonce";
694
-        if (
695
-            ! is_admin()
696
-            && (
697
-                ! EE_Registry::instance()->REQ->is_set($nonce_name_with_id)
698
-                || ! wp_verify_nonce(
699
-                    EE_Registry::instance()->REQ->get($nonce_name_with_id),
700
-                    $nonce_name
701
-                )
702
-            )
703
-        ) {
704
-            EE_Error::add_error(
705
-                sprintf(
706
-                    __(
707
-                        'We\'re sorry but your request failed to pass a security check.%sPlease click the back button on your browser and try again.',
708
-                        'event_espresso'
709
-                    ),
710
-                    '<br/>'
711
-                ),
712
-                __FILE__,
713
-                __FUNCTION__,
714
-                __LINE__
715
-            );
716
-            return false;
717
-        }
718
-        return true;
719
-    }
720
-
721
-
722
-
723
-    /**
724
-     *    process_ticket_selections
725
-     *
726
-     * @access public
727
-     * @return array|boolean
728
-     * @throws \EE_Error
729
-     */
730
-    public function process_ticket_selections()
731
-    {
732
-        do_action('EED_Ticket_Selector__process_ticket_selections__before');
733
-        // do we have an event id?
734
-        if ( ! EE_Registry::instance()->REQ->is_set('tkt-slctr-event-id')) {
735
-            // $_POST['tkt-slctr-event-id'] was not set ?!?!?!?
736
-            EE_Error::add_error(
737
-                sprintf(
738
-                    __(
739
-                        'An event id was not provided or was not received.%sPlease click the back button on your browser and try again.',
740
-                        'event_espresso'
741
-                    ),
742
-                    '<br/>'
743
-                ),
744
-                __FILE__,
745
-                __FUNCTION__,
746
-                __LINE__
747
-            );
748
-        }
749
-        //if event id is valid
750
-        $id = absint(EE_Registry::instance()->REQ->get('tkt-slctr-event-id'));
751
-        // check nonce
752
-        if ( ! EED_Ticket_Selector::process_ticket_selector_nonce('process_ticket_selections', $id)) {
753
-            return false;
754
-        }
755
-        //		d( EE_Registry::instance()->REQ );
756
-        self::$_available_spaces = array(
757
-            'tickets'   => array(),
758
-            'datetimes' => array(),
759
-        );
760
-        //we should really only have 1 registration in the works now (ie, no MER) so clear any previous items in the cart.
761
-        // When MER happens this will probably need to be tweaked, possibly wrapped in a conditional checking for some constant defined in MER etc.
762
-        EE_Registry::instance()->load_core('Session');
763
-        // unless otherwise requested, clear the session
764
-        if (apply_filters('FHEE__EE_Ticket_Selector__process_ticket_selections__clear_session', true)) {
765
-            EE_Registry::instance()->SSN->clear_session(__CLASS__, __FUNCTION__);
766
-        }
767
-        //d( EE_Registry::instance()->SSN );
768
-        do_action('AHEE_log', __FILE__, __FUNCTION__, '');
769
-        // validate/sanitize data
770
-        $valid = self::_validate_post_data($id);
771
-        //EEH_Debug_Tools::printr( $_REQUEST, '$_REQUEST', __FILE__, __LINE__ );
772
-        //EEH_Debug_Tools::printr( $valid, '$valid', __FILE__, __LINE__ );
773
-        //EEH_Debug_Tools::printr( $valid[ 'total_tickets' ], 'total_tickets', __FILE__, __LINE__ );
774
-        //EEH_Debug_Tools::printr( $valid[ 'max_atndz' ], 'max_atndz', __FILE__, __LINE__ );
775
-        //check total tickets ordered vs max number of attendees that can register
776
-        if ($valid['total_tickets'] > $valid['max_atndz']) {
777
-            // ordering too many tickets !!!
778
-            $total_tickets_string = _n('You have attempted to purchase %s ticket.',
779
-                'You have attempted to purchase %s tickets.', $valid['total_tickets'], 'event_espresso');
780
-            $limit_error_1 = sprintf($total_tickets_string, $valid['total_tickets']);
781
-            // dev only message
782
-            $max_atndz_string = _n('The registration limit for this event is %s ticket per registration, therefore the total number of tickets you may purchase at a time can not exceed %s.',
783
-                'The registration limit for this event is %s tickets per registration, therefore the total number of tickets you may purchase at a time can not exceed %s.',
784
-                $valid['max_atndz'], 'event_espresso');
785
-            $limit_error_2 = sprintf($max_atndz_string, $valid['max_atndz'], $valid['max_atndz']);
786
-            EE_Error::add_error($limit_error_1 . '<br/>' . $limit_error_2, __FILE__, __FUNCTION__, __LINE__);
787
-        } else {
788
-            // all data appears to be valid
789
-            $tckts_slctd = false;
790
-            $tickets_added = 0;
791
-            $valid = apply_filters('FHEE__EED_Ticket_Selector__process_ticket_selections__valid_post_data', $valid);
792
-            if ($valid['total_tickets'] > 0) {
793
-                // load cart
794
-                EE_Registry::instance()->load_core('Cart');
795
-                // cycle thru the number of data rows sent from the event listing
796
-                for ($x = 0; $x < $valid['rows']; $x++) {
797
-                    // does this row actually contain a ticket quantity?
798
-                    if (isset($valid['qty'][$x]) && $valid['qty'][$x] > 0) {
799
-                        // YES we have a ticket quantity
800
-                        $tckts_slctd = true;
801
-                        //						d( $valid['ticket_obj'][$x] );
802
-                        if ($valid['ticket_obj'][$x] instanceof EE_Ticket) {
803
-                            // then add ticket to cart
804
-                            $tickets_added += self::_add_ticket_to_cart($valid['ticket_obj'][$x], $valid['qty'][$x]);
805
-                            if (EE_Error::has_error()) {
806
-                                break;
807
-                            }
808
-                        } else {
809
-                            // nothing added to cart retrieved
810
-                            EE_Error::add_error(
811
-                                sprintf(__('A valid ticket could not be retrieved for the event.%sPlease click the back button on your browser and try again.',
812
-                                    'event_espresso'), '<br/>'),
813
-                                __FILE__, __FUNCTION__, __LINE__
814
-                            );
815
-                        }
816
-                    }
817
-                }
818
-            }
819
-            do_action(
820
-                'AHEE__EE_Ticket_Selector__process_ticket_selections__after_tickets_added_to_cart',
821
-                EE_Registry::instance()->CART,
822
-                $this
823
-            );
824
-            //d( EE_Registry::instance()->CART );
825
-            //die(); // <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< KILL REDIRECT HERE BEFORE CART UPDATE
826
-            if (apply_filters('FHEE__EED_Ticket_Selector__process_ticket_selections__tckts_slctd', $tckts_slctd)) {
827
-                if (apply_filters('FHEE__EED_Ticket_Selector__process_ticket_selections__success', $tickets_added)) {
828
-                    do_action(
829
-                        'FHEE__EE_Ticket_Selector__process_ticket_selections__before_redirecting_to_checkout',
830
-                        EE_Registry::instance()->CART,
831
-                        $this
832
-                    );
833
-                    EE_Registry::instance()->CART->recalculate_all_cart_totals();
834
-                    EE_Registry::instance()->CART->save_cart(false);
835
-                    // exit('KILL REDIRECT AFTER CART UPDATE'); // <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< OR HERE TO KILL REDIRECT AFTER CART UPDATE
836
-                    // just return TRUE for registrations being made from admin
837
-                    if (is_admin()) {
838
-                        return true;
839
-                    }
840
-                    EE_Error::get_notices(false, true);
841
-                    wp_safe_redirect(
842
-                        apply_filters(
843
-                            'FHEE__EE_Ticket_Selector__process_ticket_selections__success_redirect_url',
844
-                            EE_Registry::instance()->CFG->core->reg_page_url()
845
-                        )
846
-                    );
847
-                    exit();
848
-                } else {
849
-                    if ( ! EE_Error::has_error() && ! EE_Error::has_error(true, 'attention')) {
850
-                        // nothing added to cart
851
-                        EE_Error::add_attention(__('No tickets were added for the event', 'event_espresso'), __FILE__,
852
-                            __FUNCTION__, __LINE__);
853
-                    }
854
-                }
855
-            } else {
856
-                // no ticket quantities were selected
857
-                EE_Error::add_error(__('You need to select a ticket quantity before you can proceed.',
858
-                    'event_espresso'), __FILE__, __FUNCTION__, __LINE__);
859
-            }
860
-        }
861
-        //die(); // <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< KILL BEFORE REDIRECT
862
-        // at this point, just return if registration is being made from admin
863
-        if (is_admin()) {
864
-            return false;
865
-        }
866
-        if ($valid['return_url']) {
867
-            EE_Error::get_notices(false, true);
868
-            wp_safe_redirect($valid['return_url']);
869
-            exit();
870
-        } elseif (isset($event_to_add['id'])) {
871
-            EE_Error::get_notices(false, true);
872
-            wp_safe_redirect(get_permalink($event_to_add['id']));
873
-            exit();
874
-        } else {
875
-            echo EE_Error::get_notices();
876
-        }
877
-        return false;
878
-    }
879
-
880
-
881
-
882
-    /**
883
-     *    validate_post_data
884
-     *
885
-     * @access        private
886
-     * @param int $id
887
-     * @return array|FALSE
888
-     */
889
-    private static function _validate_post_data($id = 0)
890
-    {
891
-        do_action('AHEE_log', __FILE__, __FUNCTION__, '');
892
-        if ( ! $id) {
893
-            EE_Error::add_error(
894
-                __('The event id provided was not valid.', 'event_espresso'),
895
-                __FILE__,
896
-                __FUNCTION__,
897
-                __LINE__
898
-            );
899
-            return false;
900
-        }
901
-        // start with an empty array()
902
-        $valid_data = array();
903
-        // grab valid id
904
-        $valid_data['id'] = $id;
905
-        // grab and sanitize return-url
906
-        $valid_data['return_url'] = esc_url_raw(EE_Registry::instance()->REQ->get('tkt-slctr-return-url-' . $id));
907
-        // array of other form names
908
-        $inputs_to_clean = array(
909
-            'event_id'   => 'tkt-slctr-event-id',
910
-            'max_atndz'  => 'tkt-slctr-max-atndz-',
911
-            'rows'       => 'tkt-slctr-rows-',
912
-            'qty'        => 'tkt-slctr-qty-',
913
-            'ticket_id'  => 'tkt-slctr-ticket-id-',
914
-            'return_url' => 'tkt-slctr-return-url-',
915
-        );
916
-        // let's track the total number of tickets ordered.'
917
-        $valid_data['total_tickets'] = 0;
918
-        // cycle through $inputs_to_clean array
919
-        foreach ($inputs_to_clean as $what => $input_to_clean) {
920
-            // check for POST data
921
-            if (EE_Registry::instance()->REQ->is_set($input_to_clean . $id)) {
922
-                // grab value
923
-                $input_value = EE_Registry::instance()->REQ->get($input_to_clean . $id);
924
-                switch ($what) {
925
-                    // integers
926
-                    case 'event_id':
927
-                        $valid_data[$what] = absint($input_value);
928
-                        // get event via the event id we put in the form
929
-                        $valid_data['event'] = EE_Registry::instance()
930
-                                                          ->load_model('Event')
931
-                                                          ->get_one_by_ID($valid_data['event_id']);
932
-                        break;
933
-                    case 'rows':
934
-                    case 'max_atndz':
935
-                        $valid_data[$what] = absint($input_value);
936
-                        break;
937
-                    // arrays of integers
938
-                    case 'qty':
939
-                        /** @var array $row_qty */
940
-                        $row_qty = $input_value;
941
-                        // if qty is coming from a radio button input, then we need to assemble an array of rows
942
-                        if ( ! is_array($row_qty)) {
943
-                            // get number of rows
944
-                            $rows = EE_Registry::instance()->REQ->is_set('tkt-slctr-rows-' . $id)
945
-                                ? absint(EE_Registry::instance()->REQ->get('tkt-slctr-rows-' . $id))
946
-                                : 1;
947
-                            // explode ints by the dash
948
-                            $row_qty = explode('-', $row_qty);
949
-                            $row = isset($row_qty[0]) ? absint($row_qty[0]) : 1;
950
-                            $qty = isset($row_qty[1]) ? absint($row_qty[1]) : 0;
951
-                            $row_qty = array($row => $qty);
952
-                            //								 d( $row_qty );
953
-                            for ($x = 1; $x <= $rows; $x++) {
954
-                                if ( ! isset($row_qty[$x])) {
955
-                                    $row_qty[$x] = 0;
956
-                                }
957
-                            }
958
-                        }
959
-                        ksort($row_qty);
960
-                        //							 d( $row_qty );
961
-                        // cycle thru values
962
-                        foreach ($row_qty as $qty) {
963
-                            $qty = absint($qty);
964
-                            // sanitize as integers
965
-                            $valid_data[$what][] = $qty;
966
-                            $valid_data['total_tickets'] += $qty;
967
-                        }
968
-                        break;
969
-                    // array of integers
970
-                    case 'ticket_id':
971
-                        $value_array = array();
972
-                        // cycle thru values
973
-                        foreach ((array)$input_value as $key => $value) {
974
-                            // allow only numbers, letters,  spaces, commas and dashes
975
-                            $value_array[$key] = wp_strip_all_tags($value);
976
-                            // get ticket via the ticket id we put in the form
977
-                            $ticket_obj = EE_Registry::instance()->load_model('Ticket')->get_one_by_ID($value);
978
-                            $valid_data['ticket_obj'][$key] = $ticket_obj;
979
-                        }
980
-                        $valid_data[$what] = $value_array;
981
-                        break;
982
-                    case 'return_url' :
983
-                        // grab and sanitize return-url
984
-                        $valid_data[$what] = esc_url_raw($input_value);
985
-                        break;
986
-                }    // end switch $what
987
-            }
988
-        }    // end foreach $inputs_to_clean
989
-        //		d( $valid_data );
990
-        //		die();
991
-        return $valid_data;
992
-    }
993
-
994
-
995
-
996
-    /**
997
-     *    adds a ticket to the cart
998
-     *
999
-     * @access   private
1000
-     * @param EE_Ticket $ticket
1001
-     * @param int       $qty
1002
-     * @return TRUE on success, FALSE on fail
1003
-     * @throws \EE_Error
1004
-     */
1005
-    private static function _add_ticket_to_cart(EE_Ticket $ticket = null, $qty = 1)
1006
-    {
1007
-        do_action('AHEE_log', __FILE__, __FUNCTION__, '');
1008
-        // get the number of spaces left for this datetime ticket
1009
-        $available_spaces = self::_ticket_datetime_availability($ticket);
1010
-        // compare available spaces against the number of tickets being purchased
1011
-        if ($available_spaces >= $qty) {
1012
-            // allow addons to prevent a ticket from being added to cart
1013
-            if ( ! apply_filters('FHEE__EE_Ticket_Selector___add_ticket_to_cart__allow_add_to_cart', true, $ticket,
1014
-                $qty, $available_spaces)
1015
-            ) {
1016
-                return false;
1017
-            }
1018
-            $qty = absint(apply_filters('FHEE__EE_Ticket_Selector___add_ticket_to_cart__ticket_qty', $qty, $ticket));
1019
-            // add event to cart
1020
-            if (EE_Registry::instance()->CART->add_ticket_to_cart($ticket, $qty)) {
1021
-                self::_recalculate_ticket_datetime_availability($ticket, $qty);
1022
-                return true;
1023
-            } else {
1024
-                return false;
1025
-            }
1026
-        } else {
1027
-            // tickets can not be purchased but let's find the exact number left for the last ticket selected PRIOR to subtracting tickets
1028
-            $available_spaces = self::_ticket_datetime_availability($ticket, true);
1029
-            // greedy greedy greedy eh?
1030
-            if ($available_spaces > 0) {
1031
-                if (
1032
-                apply_filters(
1033
-                    'FHEE__EE_Ticket_Selector___add_ticket_to_cart__allow_display_availability_error',
1034
-                    true,
1035
-                    $ticket,
1036
-                    $qty,
1037
-                    $available_spaces
1038
-                )
1039
-                ) {
1040
-                    EED_Ticket_Selector::_display_availability_error($available_spaces);
1041
-                }
1042
-            } else {
1043
-                EE_Error::add_error(
1044
-                    __('We\'re sorry, but there are no available spaces left for this event at this particular date and time.',
1045
-                        'event_espresso'),
1046
-                    __FILE__, __FUNCTION__, __LINE__
1047
-                );
1048
-            }
1049
-            return false;
1050
-        }
1051
-    }
1052
-
1053
-
1054
-
1055
-    /**
1056
-     *  _display_availability_error
1057
-     *
1058
-     * @access    private
1059
-     * @param int $available_spaces
1060
-     * @throws \EE_Error
1061
-     */
1062
-    private static function _display_availability_error($available_spaces = 1)
1063
-    {
1064
-        // add error messaging - we're using the _n function that will generate
1065
-        // the appropriate singular or plural message based on the number of $available_spaces
1066
-        if (EE_Registry::instance()->CART->all_ticket_quantity_count()) {
1067
-            $msg = sprintf(
1068
-                _n(
1069
-                    'We\'re sorry, but there is only %1$s available space left for this event at this particular date and time. Please select a different number (or different combination) of tickets by cancelling the current selection and choosing again, or proceed to registration.',
1070
-                    'We\'re sorry, but there are only %1$s available spaces left for this event at this particular date and time. Please select a different number (or different combination) of tickets by cancelling the current selection and choosing again, or proceed to registration.',
1071
-                    $available_spaces,
1072
-                    'event_espresso'
1073
-                ),
1074
-                $available_spaces,
1075
-                '<br />'
1076
-            );
1077
-        } else {
1078
-            $msg = sprintf(
1079
-                _n(
1080
-                    'We\'re sorry, but there is only %1$s available space left for this event at this particular date and time. Please select a different number (or different combination) of tickets.',
1081
-                    'We\'re sorry, but there are only %1$s available spaces left for this event at this particular date and time. Please select a different number (or different combination) of tickets.',
1082
-                    $available_spaces,
1083
-                    'event_espresso'
1084
-                ),
1085
-                $available_spaces,
1086
-                '<br />'
1087
-            );
1088
-        }
1089
-        EE_Error::add_error($msg, __FILE__, __FUNCTION__, __LINE__);
1090
-    }
1091
-
1092
-
1093
-
1094
-    /**
1095
-     * _ticket_datetime_availability
1096
-     * creates an array of tickets plus all of the datetimes available to each ticket
1097
-     * and tracks the spaces remaining for each of those datetimes
1098
-     *
1099
-     * @access private
1100
-     * @param EE_Ticket $ticket - selected ticket
1101
-     * @param bool      $get_original_ticket_spaces
1102
-     * @return int
1103
-     * @throws \EE_Error
1104
-     */
1105
-    private static function _ticket_datetime_availability(EE_Ticket $ticket, $get_original_ticket_spaces = false)
1106
-    {
1107
-        // if the $_available_spaces array has not been set up yet...
1108
-        if ( ! isset(self::$_available_spaces['tickets'][$ticket->ID()])) {
1109
-            self::_set_initial_ticket_datetime_availability($ticket);
1110
-        }
1111
-        $available_spaces = $ticket->qty() - $ticket->sold();
1112
-        if (isset(self::$_available_spaces['tickets'][$ticket->ID()])) {
1113
-            // loop thru tickets, which will ALSO include individual ticket records AND a total
1114
-            foreach ((array)self::$_available_spaces['tickets'][$ticket->ID()] as $DTD_ID => $spaces) {
1115
-                // if we want the original datetime availability BEFORE we started subtracting tickets ?
1116
-                if ($get_original_ticket_spaces) {
1117
-                    // then grab the available spaces from the "tickets" array and compare with the above to get the lowest number
1118
-                    $available_spaces = min($available_spaces,
1119
-                        self::$_available_spaces['tickets'][$ticket->ID()][$DTD_ID]);
1120
-                } else {
1121
-                    // we want the updated ticket availability as stored in the "datetimes" array
1122
-                    $available_spaces = min($available_spaces, self::$_available_spaces['datetimes'][$DTD_ID]);
1123
-                }
1124
-            }
1125
-        }
1126
-        return $available_spaces;
1127
-    }
1128
-
1129
-
1130
-
1131
-    /**
1132
-     * _set_initial_ticket_datetime_availability
1133
-     *
1134
-     * @access private
1135
-     * @param EE_Ticket $ticket
1136
-     * @return void
1137
-     * @throws \EE_Error
1138
-     */
1139
-    private static function _set_initial_ticket_datetime_availability(EE_Ticket $ticket)
1140
-    {
1141
-        // first, get all of the datetimes that are available to this ticket
1142
-        $datetimes = $ticket->get_many_related(
1143
-            'Datetime',
1144
-            array(
1145
-                array(
1146
-                    'DTT_EVT_end' => array(
1147
-                        '>=',
1148
-                        EEM_Datetime::instance()->current_time_for_query('DTT_EVT_end'),
1149
-                    ),
1150
-                ),
1151
-                'order_by' => array('DTT_EVT_start' => 'ASC'),
1152
-            )
1153
-        );
1154
-        if ( ! empty($datetimes)) {
1155
-            // now loop thru all of the datetimes
1156
-            foreach ($datetimes as $datetime) {
1157
-                if ($datetime instanceof EE_Datetime) {
1158
-                    // the number of spaces available for the datetime without considering individual ticket quantities
1159
-                    $spaces_remaining = $datetime->spaces_remaining();
1160
-                    // save the total available spaces ( the lesser of the ticket qty minus the number of tickets sold or the datetime spaces remaining) to this ticket using the datetime ID as the key
1161
-                    self::$_available_spaces['tickets'][$ticket->ID()][$datetime->ID()] = min(
1162
-                        $ticket->qty() - $ticket->sold(),
1163
-                        $spaces_remaining
1164
-                    );
1165
-                    // if the remaining spaces for this datetime is already set, then compare that against the datetime spaces remaining, and take the lowest number,
1166
-                    // else just take the datetime spaces remaining, and assign to the datetimes array
1167
-                    self::$_available_spaces['datetimes'][$datetime->ID()] = isset(self::$_available_spaces['datetimes'][$datetime->ID()])
1168
-                        ? min(self::$_available_spaces['datetimes'][$datetime->ID()], $spaces_remaining)
1169
-                        : $spaces_remaining;
1170
-                }
1171
-            }
1172
-        }
1173
-    }
1174
-
1175
-
1176
-
1177
-    /**
1178
-     *    _recalculate_ticket_datetime_availability
1179
-     *
1180
-     * @access    private
1181
-     * @param    EE_Ticket $ticket
1182
-     * @param    int       $qty
1183
-     * @return    void
1184
-     */
1185
-    private static function _recalculate_ticket_datetime_availability(EE_Ticket $ticket, $qty = 0)
1186
-    {
1187
-        if (isset(self::$_available_spaces['tickets'][$ticket->ID()])) {
1188
-            // loop thru tickets, which will ALSO include individual ticket records AND a total
1189
-            foreach ((array)self::$_available_spaces['tickets'][$ticket->ID()] as $DTD_ID => $spaces) {
1190
-                // subtract the qty of selected tickets from each datetime's available spaces this ticket has access to,
1191
-                self::$_available_spaces['datetimes'][$DTD_ID] -= $qty;
1192
-            }
1193
-        }
1194
-    }
1195
-
1196
-
1197
-
1198
-    /**
1199
-     *    load js
1200
-     *
1201
-     * @access        public
1202
-     * @return        void
1203
-     */
1204
-    public static function load_tckt_slctr_assets()
1205
-    {
1206
-        // add some style
1207
-        if (apply_filters('FHEE__EED_Ticket_Selector__load_tckt_slctr_assets', false)) {
1208
-            wp_register_style('ticket_selector', TICKET_SELECTOR_ASSETS_URL . 'ticket_selector.css');
1209
-            wp_enqueue_style('ticket_selector');
1210
-            // make it dance
1211
-            // wp_register_script('ticket_selector', TICKET_SELECTOR_ASSETS_URL . 'ticket_selector.js', array('espresso_core'), '', TRUE);
1212
-            // wp_enqueue_script('ticket_selector');
1213
-        }
1214
-    }
1215
-
1216
-
1217
-
1218
-    public static function load_tckt_slctr_assets_admin()
1219
-    {
1220
-        //iframe button js on admin event editor page
1221
-        if (EE_Registry::instance()->REQ->get('page') === 'espresso_events'
1222
-            && EE_Registry::instance()->REQ->get('action') === 'edit'
1223
-        ) {
1224
-            wp_register_script('ticket_selector_embed', TICKET_SELECTOR_ASSETS_URL . 'ticket-selector-embed.js',
1225
-                array('ee-dialog'), EVENT_ESPRESSO_VERSION, true);
1226
-            wp_enqueue_script('ticket_selector_embed');
1227
-        }
1228
-    }
425
+			}
426
+			return $html;
427
+		}
428
+		// if there is no submit button, then don't start building a form
429
+		// because the "View Details" button will build its own form
430
+		if ( ! apply_filters('FHEE__EE_Ticket_Selector__display_ticket_selector_submit', false)) {
431
+			return '';
432
+		}
433
+		$checkout_url = EEH_Event_View::event_link_url($ID);
434
+		if ( ! $checkout_url) {
435
+			EE_Error::add_error(__('The URL for the Event Details page could not be retrieved.', 'event_espresso'),
436
+				__FILE__, __FUNCTION__, __LINE__);
437
+		}
438
+		$extra_params = self::$_in_iframe ? ' target="_blank"' : '';
439
+		$html = '<form method="POST" action="' . $checkout_url . '"' . $extra_params . '>';
440
+		$html .= wp_nonce_field('process_ticket_selections', 'process_ticket_selections_nonce_' . $ID, true, false);
441
+		$html .= '<input type="hidden" name="ee" value="process_ticket_selections">';
442
+		$html = apply_filters('FHEE__EE_Ticket_Selector__ticket_selector_form_open__html', $html, self::$_event);
443
+		return $html;
444
+	}
445
+
446
+
447
+
448
+	/**
449
+	 * display_ticket_selector_submit
450
+	 *
451
+	 * @param        string $external_url
452
+	 * @return        string
453
+	 * @throws \EE_Error
454
+	 */
455
+	public static function display_ticket_selector_submit($external_url = '')
456
+	{
457
+		$html = '';
458
+		if ( ! is_admin()) {
459
+			// standard TS displayed with submit button, ie: "Register Now"
460
+			if (apply_filters('FHEE__EE_Ticket_Selector__display_ticket_selector_submit', false)) {
461
+				$html .= \EED_Ticket_Selector::display_register_now_button();
462
+				$html .= empty($external_url) ?
463
+					\EED_Ticket_Selector::no_tkt_slctr_end_dv()
464
+					: \EED_Ticket_Selector::clear_tkt_slctr();
465
+				$html .= '<br/>' . \EED_Ticket_Selector::ticket_selector_form_close();
466
+			} else if ( EED_Ticket_Selector::$_max_atndz === 1 ) {
467
+				// its a "Dude Where's my Ticket Selector?" (DWMTS) type event (ie: $_max_atndz === 1)
468
+				if ( EED_Ticket_Selector::$_event->is_sold_out() ) {
469
+					// then instead of a View Details or Submit button, just display a "Sold Out" message
470
+					$html .= apply_filters(
471
+						'FHEE__EE_Ticket_Selector__display_ticket_selector_submit__sold_out_msg',
472
+						sprintf(
473
+							__(
474
+								'%1$s"%2$s" is currently sold out.%4$sPlease check back again later, as spots may become available.%3$s',
475
+								'event_espresso'
476
+							),
477
+							'<p class="no-ticket-selector-msg clear-float">',
478
+							EED_Ticket_Selector::$_event->name(),
479
+							'</p>',
480
+							'<br />'
481
+						),
482
+						EED_Ticket_Selector::$_event
483
+					);
484
+					if (
485
+						apply_filters(
486
+							'FHEE__EE_Ticket_Selector__display_ticket_selector_submit__no_tickets_but_display_register_now_button',
487
+							false,
488
+							EED_Ticket_Selector::$_event
489
+						)
490
+					) {
491
+						$html .= \EED_Ticket_Selector::display_register_now_button();
492
+					}
493
+					// sold out DWMTS event, no TS, no submit or view details button, but has additional content
494
+					$html .= \EED_Ticket_Selector::no_tkt_slctr_end_dv();
495
+				} else if (
496
+					apply_filters('FHEE__EE_Ticket_Selector__hide_ticket_selector', false)
497
+					&& ! is_single()
498
+				) {
499
+					// this is a "Dude Where's my Ticket Selector?" (DWMTS) type event,
500
+					// but no tickets are available, so display event's "View Details" button.
501
+					// it is being viewed via somewhere other than a single post
502
+					$html .= EED_Ticket_Selector::display_view_details_btn(true);
503
+				}
504
+			} else if (is_archive()) {
505
+				// event list, no tickets available so display event's "View Details" button
506
+				$html .= \EED_Ticket_Selector::no_tkt_slctr_end_dv();
507
+				$html .= EED_Ticket_Selector::display_view_details_btn();
508
+			} else {
509
+				if (
510
+					apply_filters(
511
+						'FHEE__EE_Ticket_Selector__display_ticket_selector_submit__no_tickets_but_display_register_now_button',
512
+						false,
513
+						EED_Ticket_Selector::$_event
514
+					)
515
+				) {
516
+					$html .= \EED_Ticket_Selector::display_register_now_button();
517
+				}
518
+				// no submit or view details button, and no additional content
519
+				$html .= \EED_Ticket_Selector::no_tkt_slctr_end_dv();
520
+			}
521
+			if ( ! is_archive()) {
522
+				$html .= \EEH_Template::powered_by_event_espresso('', '', array('utm_content' => 'ticket_selector'));
523
+			}
524
+		}
525
+		return $html;
526
+	}
527
+
528
+
529
+
530
+	/**
531
+	 * @return string
532
+	 */
533
+	public static function clear_tkt_slctr()
534
+	{
535
+		// standard TS displayed, appears after a "Register Now" or "view Details" button
536
+		return '<div class="clear"></div>';
537
+	}
538
+
539
+
540
+
541
+	/**
542
+	 * @deprecated 4.9.13
543
+	 * @return string
544
+	 */
545
+	public static function tkt_slctr_end_dv()
546
+	{
547
+		return \EED_Ticket_Selector::clear_tkt_slctr();
548
+	}
549
+
550
+
551
+
552
+	/**
553
+	 * @return string
554
+	 */
555
+	public static function no_tkt_slctr_end_dv()
556
+	{
557
+		// DWMTS event, no TS, appears after a "Register Now" or "view Details" button
558
+		return '<div class="clear"></div></div>';
559
+	}
560
+
561
+
562
+
563
+	/**
564
+	 *    ticket_selector_form_close
565
+	 *
566
+	 * @access        public
567
+	 * @access        public
568
+	 * @return        string
569
+	 */
570
+	public static function ticket_selector_form_close()
571
+	{
572
+		return '</form>';
573
+	}
574
+
575
+
576
+
577
+	/**
578
+	 * @return string
579
+	 * @throws \EE_Error
580
+	 */
581
+	public static function display_register_now_button()
582
+	{
583
+		$btn_text = apply_filters(
584
+			'FHEE__EE_Ticket_Selector__display_ticket_selector_submit__btn_text',
585
+			__('Register Now', 'event_espresso'),
586
+			EED_Ticket_Selector::$_event
587
+		);
588
+		$external_url = EED_Ticket_Selector::$_event->external_url();
589
+		$html = '<input id="ticket-selector-submit-' . EED_Ticket_Selector::$_event->ID() . '-btn"';
590
+		$html .= ' class="ticket-selector-submit-btn ';
591
+		$html .= empty($external_url) ? 'ticket-selector-submit-ajax"' : '"';
592
+		$html .= ' type="submit" value="' . $btn_text . '" />';
593
+		$html .= apply_filters(
594
+			'FHEE__EE_Ticket_Selector__after_ticket_selector_submit',
595
+			'',
596
+			EED_Ticket_Selector::$_event
597
+		);
598
+		return $html;
599
+	}
600
+
601
+
602
+	/**
603
+	 * display_view_details_btn
604
+	 *
605
+	 * @access public
606
+	 * @param bool $DWMTS indicates a "Dude Where's my Ticket Selector?" (DWMTS) type event
607
+	 *                    (ie: $_max_atndz === 1) where there are no available tickets,
608
+	 *                    either because they are sold out, expired, or not yet on sale.
609
+	 *                    In this case, we need to close the form BEFORE adding any closing divs
610
+	 * @return string
611
+	 * @throws \EE_Error
612
+	 */
613
+	public static function display_view_details_btn($DWMTS = false)
614
+	{
615
+		if ( ! self::$_event->get_permalink()) {
616
+			EE_Error::add_error(
617
+				__('The URL for the Event Details page could not be retrieved.', 'event_espresso'),
618
+				__FILE__, __FUNCTION__, __LINE__
619
+			);
620
+		}
621
+		$view_details_btn = '<form method="POST" action="';
622
+		$view_details_btn .= apply_filters(
623
+			'FHEE__EE_Ticket_Selector__display_view_details_btn__btn_url',
624
+			self::$_event->get_permalink(),
625
+			self::$_event
626
+		);
627
+		$view_details_btn .= '">';
628
+		$btn_text = apply_filters(
629
+			'FHEE__EE_Ticket_Selector__display_view_details_btn__btn_text',
630
+			__('View Details', 'event_espresso'),
631
+			self::$_event
632
+		);
633
+		$view_details_btn .= '<input id="ticket-selector-submit-'
634
+							 . self::$_event->ID()
635
+							 . '-btn" class="ticket-selector-submit-btn view-details-btn" type="submit" value="'
636
+							 . $btn_text
637
+							 . '" />';
638
+		$view_details_btn .= apply_filters('FHEE__EE_Ticket_Selector__after_view_details_btn', '', self::$_event);
639
+		if ($DWMTS) {
640
+			$view_details_btn .= \EED_Ticket_Selector::ticket_selector_form_close();
641
+			$view_details_btn .= \EED_Ticket_Selector::no_tkt_slctr_end_dv();
642
+			$view_details_btn .= '<br/>';
643
+		} else {
644
+			$view_details_btn .= \EED_Ticket_Selector::clear_tkt_slctr();
645
+			$view_details_btn .= '<br/>';
646
+			$view_details_btn .= \EED_Ticket_Selector::ticket_selector_form_close();
647
+		}
648
+		return $view_details_btn;
649
+	}
650
+
651
+
652
+
653
+	/**
654
+	 *    cancel_ticket_selections
655
+	 *
656
+	 * @access        public
657
+	 * @access        public
658
+	 * @return        string
659
+	 */
660
+	public static function cancel_ticket_selections()
661
+	{
662
+		// check nonce
663
+		if ( ! EED_Ticket_Selector::process_ticket_selector_nonce('cancel_ticket_selections')) {
664
+			return false;
665
+		}
666
+		EE_Registry::instance()->SSN->clear_session(__CLASS__, __FUNCTION__);
667
+		if (EE_Registry::instance()->REQ->is_set('event_id')) {
668
+			wp_safe_redirect(
669
+				EEH_Event_View::event_link_url(
670
+					EE_Registry::instance()->REQ->get('event_id')
671
+				)
672
+			);
673
+		} else {
674
+			wp_safe_redirect(
675
+				site_url('/' . EE_Registry::instance()->CFG->core->event_cpt_slug . '/')
676
+			);
677
+		}
678
+		die();
679
+	}
680
+
681
+
682
+
683
+	/**
684
+	 *    process_ticket_selector_nonce
685
+	 *
686
+	 * @access public
687
+	 * @param  string $nonce_name
688
+	 * @param string  $id
689
+	 * @return bool
690
+	 */
691
+	public static function process_ticket_selector_nonce($nonce_name, $id = '')
692
+	{
693
+		$nonce_name_with_id = ! empty($id) ? "{$nonce_name}_nonce_{$id}" : "{$nonce_name}_nonce";
694
+		if (
695
+			! is_admin()
696
+			&& (
697
+				! EE_Registry::instance()->REQ->is_set($nonce_name_with_id)
698
+				|| ! wp_verify_nonce(
699
+					EE_Registry::instance()->REQ->get($nonce_name_with_id),
700
+					$nonce_name
701
+				)
702
+			)
703
+		) {
704
+			EE_Error::add_error(
705
+				sprintf(
706
+					__(
707
+						'We\'re sorry but your request failed to pass a security check.%sPlease click the back button on your browser and try again.',
708
+						'event_espresso'
709
+					),
710
+					'<br/>'
711
+				),
712
+				__FILE__,
713
+				__FUNCTION__,
714
+				__LINE__
715
+			);
716
+			return false;
717
+		}
718
+		return true;
719
+	}
720
+
721
+
722
+
723
+	/**
724
+	 *    process_ticket_selections
725
+	 *
726
+	 * @access public
727
+	 * @return array|boolean
728
+	 * @throws \EE_Error
729
+	 */
730
+	public function process_ticket_selections()
731
+	{
732
+		do_action('EED_Ticket_Selector__process_ticket_selections__before');
733
+		// do we have an event id?
734
+		if ( ! EE_Registry::instance()->REQ->is_set('tkt-slctr-event-id')) {
735
+			// $_POST['tkt-slctr-event-id'] was not set ?!?!?!?
736
+			EE_Error::add_error(
737
+				sprintf(
738
+					__(
739
+						'An event id was not provided or was not received.%sPlease click the back button on your browser and try again.',
740
+						'event_espresso'
741
+					),
742
+					'<br/>'
743
+				),
744
+				__FILE__,
745
+				__FUNCTION__,
746
+				__LINE__
747
+			);
748
+		}
749
+		//if event id is valid
750
+		$id = absint(EE_Registry::instance()->REQ->get('tkt-slctr-event-id'));
751
+		// check nonce
752
+		if ( ! EED_Ticket_Selector::process_ticket_selector_nonce('process_ticket_selections', $id)) {
753
+			return false;
754
+		}
755
+		//		d( EE_Registry::instance()->REQ );
756
+		self::$_available_spaces = array(
757
+			'tickets'   => array(),
758
+			'datetimes' => array(),
759
+		);
760
+		//we should really only have 1 registration in the works now (ie, no MER) so clear any previous items in the cart.
761
+		// When MER happens this will probably need to be tweaked, possibly wrapped in a conditional checking for some constant defined in MER etc.
762
+		EE_Registry::instance()->load_core('Session');
763
+		// unless otherwise requested, clear the session
764
+		if (apply_filters('FHEE__EE_Ticket_Selector__process_ticket_selections__clear_session', true)) {
765
+			EE_Registry::instance()->SSN->clear_session(__CLASS__, __FUNCTION__);
766
+		}
767
+		//d( EE_Registry::instance()->SSN );
768
+		do_action('AHEE_log', __FILE__, __FUNCTION__, '');
769
+		// validate/sanitize data
770
+		$valid = self::_validate_post_data($id);
771
+		//EEH_Debug_Tools::printr( $_REQUEST, '$_REQUEST', __FILE__, __LINE__ );
772
+		//EEH_Debug_Tools::printr( $valid, '$valid', __FILE__, __LINE__ );
773
+		//EEH_Debug_Tools::printr( $valid[ 'total_tickets' ], 'total_tickets', __FILE__, __LINE__ );
774
+		//EEH_Debug_Tools::printr( $valid[ 'max_atndz' ], 'max_atndz', __FILE__, __LINE__ );
775
+		//check total tickets ordered vs max number of attendees that can register
776
+		if ($valid['total_tickets'] > $valid['max_atndz']) {
777
+			// ordering too many tickets !!!
778
+			$total_tickets_string = _n('You have attempted to purchase %s ticket.',
779
+				'You have attempted to purchase %s tickets.', $valid['total_tickets'], 'event_espresso');
780
+			$limit_error_1 = sprintf($total_tickets_string, $valid['total_tickets']);
781
+			// dev only message
782
+			$max_atndz_string = _n('The registration limit for this event is %s ticket per registration, therefore the total number of tickets you may purchase at a time can not exceed %s.',
783
+				'The registration limit for this event is %s tickets per registration, therefore the total number of tickets you may purchase at a time can not exceed %s.',
784
+				$valid['max_atndz'], 'event_espresso');
785
+			$limit_error_2 = sprintf($max_atndz_string, $valid['max_atndz'], $valid['max_atndz']);
786
+			EE_Error::add_error($limit_error_1 . '<br/>' . $limit_error_2, __FILE__, __FUNCTION__, __LINE__);
787
+		} else {
788
+			// all data appears to be valid
789
+			$tckts_slctd = false;
790
+			$tickets_added = 0;
791
+			$valid = apply_filters('FHEE__EED_Ticket_Selector__process_ticket_selections__valid_post_data', $valid);
792
+			if ($valid['total_tickets'] > 0) {
793
+				// load cart
794
+				EE_Registry::instance()->load_core('Cart');
795
+				// cycle thru the number of data rows sent from the event listing
796
+				for ($x = 0; $x < $valid['rows']; $x++) {
797
+					// does this row actually contain a ticket quantity?
798
+					if (isset($valid['qty'][$x]) && $valid['qty'][$x] > 0) {
799
+						// YES we have a ticket quantity
800
+						$tckts_slctd = true;
801
+						//						d( $valid['ticket_obj'][$x] );
802
+						if ($valid['ticket_obj'][$x] instanceof EE_Ticket) {
803
+							// then add ticket to cart
804
+							$tickets_added += self::_add_ticket_to_cart($valid['ticket_obj'][$x], $valid['qty'][$x]);
805
+							if (EE_Error::has_error()) {
806
+								break;
807
+							}
808
+						} else {
809
+							// nothing added to cart retrieved
810
+							EE_Error::add_error(
811
+								sprintf(__('A valid ticket could not be retrieved for the event.%sPlease click the back button on your browser and try again.',
812
+									'event_espresso'), '<br/>'),
813
+								__FILE__, __FUNCTION__, __LINE__
814
+							);
815
+						}
816
+					}
817
+				}
818
+			}
819
+			do_action(
820
+				'AHEE__EE_Ticket_Selector__process_ticket_selections__after_tickets_added_to_cart',
821
+				EE_Registry::instance()->CART,
822
+				$this
823
+			);
824
+			//d( EE_Registry::instance()->CART );
825
+			//die(); // <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< KILL REDIRECT HERE BEFORE CART UPDATE
826
+			if (apply_filters('FHEE__EED_Ticket_Selector__process_ticket_selections__tckts_slctd', $tckts_slctd)) {
827
+				if (apply_filters('FHEE__EED_Ticket_Selector__process_ticket_selections__success', $tickets_added)) {
828
+					do_action(
829
+						'FHEE__EE_Ticket_Selector__process_ticket_selections__before_redirecting_to_checkout',
830
+						EE_Registry::instance()->CART,
831
+						$this
832
+					);
833
+					EE_Registry::instance()->CART->recalculate_all_cart_totals();
834
+					EE_Registry::instance()->CART->save_cart(false);
835
+					// exit('KILL REDIRECT AFTER CART UPDATE'); // <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< OR HERE TO KILL REDIRECT AFTER CART UPDATE
836
+					// just return TRUE for registrations being made from admin
837
+					if (is_admin()) {
838
+						return true;
839
+					}
840
+					EE_Error::get_notices(false, true);
841
+					wp_safe_redirect(
842
+						apply_filters(
843
+							'FHEE__EE_Ticket_Selector__process_ticket_selections__success_redirect_url',
844
+							EE_Registry::instance()->CFG->core->reg_page_url()
845
+						)
846
+					);
847
+					exit();
848
+				} else {
849
+					if ( ! EE_Error::has_error() && ! EE_Error::has_error(true, 'attention')) {
850
+						// nothing added to cart
851
+						EE_Error::add_attention(__('No tickets were added for the event', 'event_espresso'), __FILE__,
852
+							__FUNCTION__, __LINE__);
853
+					}
854
+				}
855
+			} else {
856
+				// no ticket quantities were selected
857
+				EE_Error::add_error(__('You need to select a ticket quantity before you can proceed.',
858
+					'event_espresso'), __FILE__, __FUNCTION__, __LINE__);
859
+			}
860
+		}
861
+		//die(); // <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< KILL BEFORE REDIRECT
862
+		// at this point, just return if registration is being made from admin
863
+		if (is_admin()) {
864
+			return false;
865
+		}
866
+		if ($valid['return_url']) {
867
+			EE_Error::get_notices(false, true);
868
+			wp_safe_redirect($valid['return_url']);
869
+			exit();
870
+		} elseif (isset($event_to_add['id'])) {
871
+			EE_Error::get_notices(false, true);
872
+			wp_safe_redirect(get_permalink($event_to_add['id']));
873
+			exit();
874
+		} else {
875
+			echo EE_Error::get_notices();
876
+		}
877
+		return false;
878
+	}
879
+
880
+
881
+
882
+	/**
883
+	 *    validate_post_data
884
+	 *
885
+	 * @access        private
886
+	 * @param int $id
887
+	 * @return array|FALSE
888
+	 */
889
+	private static function _validate_post_data($id = 0)
890
+	{
891
+		do_action('AHEE_log', __FILE__, __FUNCTION__, '');
892
+		if ( ! $id) {
893
+			EE_Error::add_error(
894
+				__('The event id provided was not valid.', 'event_espresso'),
895
+				__FILE__,
896
+				__FUNCTION__,
897
+				__LINE__
898
+			);
899
+			return false;
900
+		}
901
+		// start with an empty array()
902
+		$valid_data = array();
903
+		// grab valid id
904
+		$valid_data['id'] = $id;
905
+		// grab and sanitize return-url
906
+		$valid_data['return_url'] = esc_url_raw(EE_Registry::instance()->REQ->get('tkt-slctr-return-url-' . $id));
907
+		// array of other form names
908
+		$inputs_to_clean = array(
909
+			'event_id'   => 'tkt-slctr-event-id',
910
+			'max_atndz'  => 'tkt-slctr-max-atndz-',
911
+			'rows'       => 'tkt-slctr-rows-',
912
+			'qty'        => 'tkt-slctr-qty-',
913
+			'ticket_id'  => 'tkt-slctr-ticket-id-',
914
+			'return_url' => 'tkt-slctr-return-url-',
915
+		);
916
+		// let's track the total number of tickets ordered.'
917
+		$valid_data['total_tickets'] = 0;
918
+		// cycle through $inputs_to_clean array
919
+		foreach ($inputs_to_clean as $what => $input_to_clean) {
920
+			// check for POST data
921
+			if (EE_Registry::instance()->REQ->is_set($input_to_clean . $id)) {
922
+				// grab value
923
+				$input_value = EE_Registry::instance()->REQ->get($input_to_clean . $id);
924
+				switch ($what) {
925
+					// integers
926
+					case 'event_id':
927
+						$valid_data[$what] = absint($input_value);
928
+						// get event via the event id we put in the form
929
+						$valid_data['event'] = EE_Registry::instance()
930
+														  ->load_model('Event')
931
+														  ->get_one_by_ID($valid_data['event_id']);
932
+						break;
933
+					case 'rows':
934
+					case 'max_atndz':
935
+						$valid_data[$what] = absint($input_value);
936
+						break;
937
+					// arrays of integers
938
+					case 'qty':
939
+						/** @var array $row_qty */
940
+						$row_qty = $input_value;
941
+						// if qty is coming from a radio button input, then we need to assemble an array of rows
942
+						if ( ! is_array($row_qty)) {
943
+							// get number of rows
944
+							$rows = EE_Registry::instance()->REQ->is_set('tkt-slctr-rows-' . $id)
945
+								? absint(EE_Registry::instance()->REQ->get('tkt-slctr-rows-' . $id))
946
+								: 1;
947
+							// explode ints by the dash
948
+							$row_qty = explode('-', $row_qty);
949
+							$row = isset($row_qty[0]) ? absint($row_qty[0]) : 1;
950
+							$qty = isset($row_qty[1]) ? absint($row_qty[1]) : 0;
951
+							$row_qty = array($row => $qty);
952
+							//								 d( $row_qty );
953
+							for ($x = 1; $x <= $rows; $x++) {
954
+								if ( ! isset($row_qty[$x])) {
955
+									$row_qty[$x] = 0;
956
+								}
957
+							}
958
+						}
959
+						ksort($row_qty);
960
+						//							 d( $row_qty );
961
+						// cycle thru values
962
+						foreach ($row_qty as $qty) {
963
+							$qty = absint($qty);
964
+							// sanitize as integers
965
+							$valid_data[$what][] = $qty;
966
+							$valid_data['total_tickets'] += $qty;
967
+						}
968
+						break;
969
+					// array of integers
970
+					case 'ticket_id':
971
+						$value_array = array();
972
+						// cycle thru values
973
+						foreach ((array)$input_value as $key => $value) {
974
+							// allow only numbers, letters,  spaces, commas and dashes
975
+							$value_array[$key] = wp_strip_all_tags($value);
976
+							// get ticket via the ticket id we put in the form
977
+							$ticket_obj = EE_Registry::instance()->load_model('Ticket')->get_one_by_ID($value);
978
+							$valid_data['ticket_obj'][$key] = $ticket_obj;
979
+						}
980
+						$valid_data[$what] = $value_array;
981
+						break;
982
+					case 'return_url' :
983
+						// grab and sanitize return-url
984
+						$valid_data[$what] = esc_url_raw($input_value);
985
+						break;
986
+				}    // end switch $what
987
+			}
988
+		}    // end foreach $inputs_to_clean
989
+		//		d( $valid_data );
990
+		//		die();
991
+		return $valid_data;
992
+	}
993
+
994
+
995
+
996
+	/**
997
+	 *    adds a ticket to the cart
998
+	 *
999
+	 * @access   private
1000
+	 * @param EE_Ticket $ticket
1001
+	 * @param int       $qty
1002
+	 * @return TRUE on success, FALSE on fail
1003
+	 * @throws \EE_Error
1004
+	 */
1005
+	private static function _add_ticket_to_cart(EE_Ticket $ticket = null, $qty = 1)
1006
+	{
1007
+		do_action('AHEE_log', __FILE__, __FUNCTION__, '');
1008
+		// get the number of spaces left for this datetime ticket
1009
+		$available_spaces = self::_ticket_datetime_availability($ticket);
1010
+		// compare available spaces against the number of tickets being purchased
1011
+		if ($available_spaces >= $qty) {
1012
+			// allow addons to prevent a ticket from being added to cart
1013
+			if ( ! apply_filters('FHEE__EE_Ticket_Selector___add_ticket_to_cart__allow_add_to_cart', true, $ticket,
1014
+				$qty, $available_spaces)
1015
+			) {
1016
+				return false;
1017
+			}
1018
+			$qty = absint(apply_filters('FHEE__EE_Ticket_Selector___add_ticket_to_cart__ticket_qty', $qty, $ticket));
1019
+			// add event to cart
1020
+			if (EE_Registry::instance()->CART->add_ticket_to_cart($ticket, $qty)) {
1021
+				self::_recalculate_ticket_datetime_availability($ticket, $qty);
1022
+				return true;
1023
+			} else {
1024
+				return false;
1025
+			}
1026
+		} else {
1027
+			// tickets can not be purchased but let's find the exact number left for the last ticket selected PRIOR to subtracting tickets
1028
+			$available_spaces = self::_ticket_datetime_availability($ticket, true);
1029
+			// greedy greedy greedy eh?
1030
+			if ($available_spaces > 0) {
1031
+				if (
1032
+				apply_filters(
1033
+					'FHEE__EE_Ticket_Selector___add_ticket_to_cart__allow_display_availability_error',
1034
+					true,
1035
+					$ticket,
1036
+					$qty,
1037
+					$available_spaces
1038
+				)
1039
+				) {
1040
+					EED_Ticket_Selector::_display_availability_error($available_spaces);
1041
+				}
1042
+			} else {
1043
+				EE_Error::add_error(
1044
+					__('We\'re sorry, but there are no available spaces left for this event at this particular date and time.',
1045
+						'event_espresso'),
1046
+					__FILE__, __FUNCTION__, __LINE__
1047
+				);
1048
+			}
1049
+			return false;
1050
+		}
1051
+	}
1052
+
1053
+
1054
+
1055
+	/**
1056
+	 *  _display_availability_error
1057
+	 *
1058
+	 * @access    private
1059
+	 * @param int $available_spaces
1060
+	 * @throws \EE_Error
1061
+	 */
1062
+	private static function _display_availability_error($available_spaces = 1)
1063
+	{
1064
+		// add error messaging - we're using the _n function that will generate
1065
+		// the appropriate singular or plural message based on the number of $available_spaces
1066
+		if (EE_Registry::instance()->CART->all_ticket_quantity_count()) {
1067
+			$msg = sprintf(
1068
+				_n(
1069
+					'We\'re sorry, but there is only %1$s available space left for this event at this particular date and time. Please select a different number (or different combination) of tickets by cancelling the current selection and choosing again, or proceed to registration.',
1070
+					'We\'re sorry, but there are only %1$s available spaces left for this event at this particular date and time. Please select a different number (or different combination) of tickets by cancelling the current selection and choosing again, or proceed to registration.',
1071
+					$available_spaces,
1072
+					'event_espresso'
1073
+				),
1074
+				$available_spaces,
1075
+				'<br />'
1076
+			);
1077
+		} else {
1078
+			$msg = sprintf(
1079
+				_n(
1080
+					'We\'re sorry, but there is only %1$s available space left for this event at this particular date and time. Please select a different number (or different combination) of tickets.',
1081
+					'We\'re sorry, but there are only %1$s available spaces left for this event at this particular date and time. Please select a different number (or different combination) of tickets.',
1082
+					$available_spaces,
1083
+					'event_espresso'
1084
+				),
1085
+				$available_spaces,
1086
+				'<br />'
1087
+			);
1088
+		}
1089
+		EE_Error::add_error($msg, __FILE__, __FUNCTION__, __LINE__);
1090
+	}
1091
+
1092
+
1093
+
1094
+	/**
1095
+	 * _ticket_datetime_availability
1096
+	 * creates an array of tickets plus all of the datetimes available to each ticket
1097
+	 * and tracks the spaces remaining for each of those datetimes
1098
+	 *
1099
+	 * @access private
1100
+	 * @param EE_Ticket $ticket - selected ticket
1101
+	 * @param bool      $get_original_ticket_spaces
1102
+	 * @return int
1103
+	 * @throws \EE_Error
1104
+	 */
1105
+	private static function _ticket_datetime_availability(EE_Ticket $ticket, $get_original_ticket_spaces = false)
1106
+	{
1107
+		// if the $_available_spaces array has not been set up yet...
1108
+		if ( ! isset(self::$_available_spaces['tickets'][$ticket->ID()])) {
1109
+			self::_set_initial_ticket_datetime_availability($ticket);
1110
+		}
1111
+		$available_spaces = $ticket->qty() - $ticket->sold();
1112
+		if (isset(self::$_available_spaces['tickets'][$ticket->ID()])) {
1113
+			// loop thru tickets, which will ALSO include individual ticket records AND a total
1114
+			foreach ((array)self::$_available_spaces['tickets'][$ticket->ID()] as $DTD_ID => $spaces) {
1115
+				// if we want the original datetime availability BEFORE we started subtracting tickets ?
1116
+				if ($get_original_ticket_spaces) {
1117
+					// then grab the available spaces from the "tickets" array and compare with the above to get the lowest number
1118
+					$available_spaces = min($available_spaces,
1119
+						self::$_available_spaces['tickets'][$ticket->ID()][$DTD_ID]);
1120
+				} else {
1121
+					// we want the updated ticket availability as stored in the "datetimes" array
1122
+					$available_spaces = min($available_spaces, self::$_available_spaces['datetimes'][$DTD_ID]);
1123
+				}
1124
+			}
1125
+		}
1126
+		return $available_spaces;
1127
+	}
1128
+
1129
+
1130
+
1131
+	/**
1132
+	 * _set_initial_ticket_datetime_availability
1133
+	 *
1134
+	 * @access private
1135
+	 * @param EE_Ticket $ticket
1136
+	 * @return void
1137
+	 * @throws \EE_Error
1138
+	 */
1139
+	private static function _set_initial_ticket_datetime_availability(EE_Ticket $ticket)
1140
+	{
1141
+		// first, get all of the datetimes that are available to this ticket
1142
+		$datetimes = $ticket->get_many_related(
1143
+			'Datetime',
1144
+			array(
1145
+				array(
1146
+					'DTT_EVT_end' => array(
1147
+						'>=',
1148
+						EEM_Datetime::instance()->current_time_for_query('DTT_EVT_end'),
1149
+					),
1150
+				),
1151
+				'order_by' => array('DTT_EVT_start' => 'ASC'),
1152
+			)
1153
+		);
1154
+		if ( ! empty($datetimes)) {
1155
+			// now loop thru all of the datetimes
1156
+			foreach ($datetimes as $datetime) {
1157
+				if ($datetime instanceof EE_Datetime) {
1158
+					// the number of spaces available for the datetime without considering individual ticket quantities
1159
+					$spaces_remaining = $datetime->spaces_remaining();
1160
+					// save the total available spaces ( the lesser of the ticket qty minus the number of tickets sold or the datetime spaces remaining) to this ticket using the datetime ID as the key
1161
+					self::$_available_spaces['tickets'][$ticket->ID()][$datetime->ID()] = min(
1162
+						$ticket->qty() - $ticket->sold(),
1163
+						$spaces_remaining
1164
+					);
1165
+					// if the remaining spaces for this datetime is already set, then compare that against the datetime spaces remaining, and take the lowest number,
1166
+					// else just take the datetime spaces remaining, and assign to the datetimes array
1167
+					self::$_available_spaces['datetimes'][$datetime->ID()] = isset(self::$_available_spaces['datetimes'][$datetime->ID()])
1168
+						? min(self::$_available_spaces['datetimes'][$datetime->ID()], $spaces_remaining)
1169
+						: $spaces_remaining;
1170
+				}
1171
+			}
1172
+		}
1173
+	}
1174
+
1175
+
1176
+
1177
+	/**
1178
+	 *    _recalculate_ticket_datetime_availability
1179
+	 *
1180
+	 * @access    private
1181
+	 * @param    EE_Ticket $ticket
1182
+	 * @param    int       $qty
1183
+	 * @return    void
1184
+	 */
1185
+	private static function _recalculate_ticket_datetime_availability(EE_Ticket $ticket, $qty = 0)
1186
+	{
1187
+		if (isset(self::$_available_spaces['tickets'][$ticket->ID()])) {
1188
+			// loop thru tickets, which will ALSO include individual ticket records AND a total
1189
+			foreach ((array)self::$_available_spaces['tickets'][$ticket->ID()] as $DTD_ID => $spaces) {
1190
+				// subtract the qty of selected tickets from each datetime's available spaces this ticket has access to,
1191
+				self::$_available_spaces['datetimes'][$DTD_ID] -= $qty;
1192
+			}
1193
+		}
1194
+	}
1195
+
1196
+
1197
+
1198
+	/**
1199
+	 *    load js
1200
+	 *
1201
+	 * @access        public
1202
+	 * @return        void
1203
+	 */
1204
+	public static function load_tckt_slctr_assets()
1205
+	{
1206
+		// add some style
1207
+		if (apply_filters('FHEE__EED_Ticket_Selector__load_tckt_slctr_assets', false)) {
1208
+			wp_register_style('ticket_selector', TICKET_SELECTOR_ASSETS_URL . 'ticket_selector.css');
1209
+			wp_enqueue_style('ticket_selector');
1210
+			// make it dance
1211
+			// wp_register_script('ticket_selector', TICKET_SELECTOR_ASSETS_URL . 'ticket_selector.js', array('espresso_core'), '', TRUE);
1212
+			// wp_enqueue_script('ticket_selector');
1213
+		}
1214
+	}
1215
+
1216
+
1217
+
1218
+	public static function load_tckt_slctr_assets_admin()
1219
+	{
1220
+		//iframe button js on admin event editor page
1221
+		if (EE_Registry::instance()->REQ->get('page') === 'espresso_events'
1222
+			&& EE_Registry::instance()->REQ->get('action') === 'edit'
1223
+		) {
1224
+			wp_register_script('ticket_selector_embed', TICKET_SELECTOR_ASSETS_URL . 'ticket-selector-embed.js',
1225
+				array('ee-dialog'), EVENT_ESPRESSO_VERSION, true);
1226
+			wp_enqueue_script('ticket_selector_embed');
1227
+		}
1228
+	}
1229 1229
 
1230 1230
 
1231 1231
 
Please login to merge, or discard this patch.
Spacing   +44 added lines, -44 removed lines patch added patch discarded remove patch
@@ -14,7 +14,7 @@  discard block
 block discarded – undo
14 14
 class EED_Ticket_Selector extends EED_Module
15 15
 {
16 16
 
17
-    const debug = false;    //	true false
17
+    const debug = false; //	true false
18 18
 
19 19
     /**
20 20
      * event that ticket selector is being generated for
@@ -113,8 +113,8 @@  discard block
 block discarded – undo
113 113
      */
114 114
     public static function set_definitions()
115 115
     {
116
-        define('TICKET_SELECTOR_ASSETS_URL', plugin_dir_url(__FILE__) . 'assets' . DS);
117
-        define('TICKET_SELECTOR_TEMPLATES_PATH', str_replace('\\', DS, plugin_dir_path(__FILE__)) . 'templates' . DS);
116
+        define('TICKET_SELECTOR_ASSETS_URL', plugin_dir_url(__FILE__).'assets'.DS);
117
+        define('TICKET_SELECTOR_TEMPLATES_PATH', str_replace('\\', DS, plugin_dir_path(__FILE__)).'templates'.DS);
118 118
         //if config is not set, initialize
119 119
         //If config is not set, set it.
120 120
         if (EE_Registry::instance()->CFG->template_settings->EED_Ticket_Selector === null) {
@@ -158,10 +158,10 @@  discard block
 block discarded – undo
158 158
         $template_args['css'] = apply_filters(
159 159
             'FHEE__EED_Ticket_Selector__ticket_selector_iframe__css',
160 160
             array(
161
-                TICKET_SELECTOR_ASSETS_URL . 'ticket_selector_embed.css?ver=' . EVENT_ESPRESSO_VERSION,
162
-                TICKET_SELECTOR_ASSETS_URL . 'ticket_selector.css?ver=' . EVENT_ESPRESSO_VERSION,
163
-                includes_url('css/dashicons.min.css?ver=' . $GLOBALS['wp_version']),
164
-                EE_GLOBAL_ASSETS_URL . 'css/espresso_default.css?ver=' . EVENT_ESPRESSO_VERSION,
161
+                TICKET_SELECTOR_ASSETS_URL.'ticket_selector_embed.css?ver='.EVENT_ESPRESSO_VERSION,
162
+                TICKET_SELECTOR_ASSETS_URL.'ticket_selector.css?ver='.EVENT_ESPRESSO_VERSION,
163
+                includes_url('css/dashicons.min.css?ver='.$GLOBALS['wp_version']),
164
+                EE_GLOBAL_ASSETS_URL.'css/espresso_default.css?ver='.EVENT_ESPRESSO_VERSION,
165 165
             )
166 166
         );
167 167
         EE_Registry::$i18n_js_strings['ticket_selector_iframe'] = true;
@@ -174,18 +174,18 @@  discard block
 block discarded – undo
174 174
         $template_args['js'] = apply_filters(
175 175
             'FHEE__EED_Ticket_Selector__ticket_selector_iframe__js',
176 176
             array(
177
-                includes_url('js/jquery/jquery.js?ver=' . $GLOBALS['wp_version']),
178
-                EE_GLOBAL_ASSETS_URL . 'scripts/espresso_core.js?ver=' . EVENT_ESPRESSO_VERSION,
179
-                TICKET_SELECTOR_ASSETS_URL . 'ticket_selector_iframe_embed.js?ver=' . EVENT_ESPRESSO_VERSION,
177
+                includes_url('js/jquery/jquery.js?ver='.$GLOBALS['wp_version']),
178
+                EE_GLOBAL_ASSETS_URL.'scripts/espresso_core.js?ver='.EVENT_ESPRESSO_VERSION,
179
+                TICKET_SELECTOR_ASSETS_URL.'ticket_selector_iframe_embed.js?ver='.EVENT_ESPRESSO_VERSION,
180 180
             )
181 181
         );
182 182
         $template_args['notices'] = EEH_Template::display_template(
183
-            EE_TEMPLATES . 'espresso-ajax-notices.template.php',
183
+            EE_TEMPLATES.'espresso-ajax-notices.template.php',
184 184
             array(),
185 185
             true
186 186
         );
187 187
         EEH_Template::display_template(
188
-            TICKET_SELECTOR_TEMPLATES_PATH . 'ticket_selector_chart_iframe.template.php',
188
+            TICKET_SELECTOR_TEMPLATES_PATH.'ticket_selector_chart_iframe.template.php',
189 189
             $template_args
190 190
         );
191 191
         exit;
@@ -200,7 +200,7 @@  discard block
 block discarded – undo
200 200
      * @param int    $id               The post id for the event.
201 201
      * @return string The new html string for the permalink area.
202 202
      */
203
-    public static function iframe_code_button($permalink_string, $id )
203
+    public static function iframe_code_button($permalink_string, $id)
204 204
     {
205 205
         //make sure this is ONLY when editing and the event id has been set.
206 206
         if ( ! empty($id)) {
@@ -214,12 +214,12 @@  discard block
 block discarded – undo
214 214
                                  . '</a> ';
215 215
             $ticket_selector_url = add_query_arg(array('ticket_selector' => 'iframe', 'event' => $id), site_url());
216 216
             $iframe_string = esc_html(
217
-                '<iframe src="' . $ticket_selector_url . '" width="100%" height="100%"></iframe>'
217
+                '<iframe src="'.$ticket_selector_url.'" width="100%" height="100%"></iframe>'
218 218
             );
219 219
             $permalink_string .= '
220 220
 <div id="js-ts-iframe" style="display:none">
221 221
 	<div style="width:100%; height: 500px;">
222
-		' . $iframe_string . '
222
+		' . $iframe_string.'
223 223
 	</div>
224 224
 </div>';
225 225
         }
@@ -243,10 +243,10 @@  discard block
 block discarded – undo
243 243
         }
244 244
         if ($event instanceof EE_Event) {
245 245
             self::$_event = $event;
246
-        } else if ($event instanceof WP_Post ) {
247
-            if ( isset($event->EE_Event) && $event->EE_Event instanceof EE_Event) {
246
+        } else if ($event instanceof WP_Post) {
247
+            if (isset($event->EE_Event) && $event->EE_Event instanceof EE_Event) {
248 248
                 self::$_event = $event->EE_Event;
249
-            } else if ( $event->post_type === 'espresso_events') {
249
+            } else if ($event->post_type === 'espresso_events') {
250 250
                 $event->EE_Event = EEM_Event::instance()->instantiate_class_from_post_object($event);
251 251
                 self::$_event = $event->EE_Event;
252 252
             }
@@ -255,7 +255,7 @@  discard block
 block discarded – undo
255 255
             $dev_msg = $user_msg
256 256
                        . __('In order to generate a ticket selector, please ensure you are passing either an EE_Event object or a WP_Post object of the post type "espresso_event" to the EE_Ticket_Selector class constructor.',
257 257
                     'event_espresso');
258
-            EE_Error::add_error($user_msg . '||' . $dev_msg, __FILE__, __FUNCTION__, __LINE__);
258
+            EE_Error::add_error($user_msg.'||'.$dev_msg, __FILE__, __FUNCTION__, __LINE__);
259 259
             return false;
260 260
         }
261 261
         return true;
@@ -362,9 +362,9 @@  discard block
 block discarded – undo
362 362
                     '</a></span></div>'
363 363
                 );
364 364
             }
365
-            return '<p><span class="important-notice">' . $sales_closed_msg . '</span></p>';
365
+            return '<p><span class="important-notice">'.$sales_closed_msg.'</span></p>';
366 366
         }
367
-        $templates['ticket_selector'] = TICKET_SELECTOR_TEMPLATES_PATH . 'ticket_selector_chart.template.php';
367
+        $templates['ticket_selector'] = TICKET_SELECTOR_TEMPLATES_PATH.'ticket_selector_chart.template.php';
368 368
         $templates['ticket_selector'] = apply_filters('FHEE__EE_Ticket_Selector__display_ticket_selector__template_path',
369 369
             $templates['ticket_selector'], self::$_event);
370 370
         // redirecting to another site for registration ??
@@ -386,7 +386,7 @@  discard block
 block discarded – undo
386 386
             ? EED_Ticket_Selector::ticket_selector_form_open(
387 387
                 self::$_event->ID(),
388 388
                 $external_url
389
-            ) . $ticket_selector
389
+            ).$ticket_selector
390 390
             : $ticket_selector;
391 391
         // submit button and form close tag
392 392
         $ticket_selector .= ! is_admin() ? EED_Ticket_Selector::display_ticket_selector_submit($external_url) : '';
@@ -409,7 +409,7 @@  discard block
 block discarded – undo
409 409
     {
410 410
         // if redirecting, we don't need any anything else
411 411
         if ($external_url) {
412
-            $html = '<form method="GET" action="' . EEH_URL::refactor_url($external_url) . '"';
412
+            $html = '<form method="GET" action="'.EEH_URL::refactor_url($external_url).'"';
413 413
             // open link in new window ?
414 414
             $html .= apply_filters(
415 415
                 'FHEE__EventEspresso_modules_ticket_selector_DisplayTicketSelector__formOpen__external_url_target_blank',
@@ -418,10 +418,10 @@  discard block
 block discarded – undo
418 418
                 ? ' target="_blank"'
419 419
                 : '';
420 420
             $html .= '>';
421
-            $query_args = (array)EEH_URL::get_query_string($external_url);
421
+            $query_args = (array) EEH_URL::get_query_string($external_url);
422 422
             foreach ($query_args as $query_arg => $value) {
423 423
                 $html .= '
424
-				<input type="hidden" name="' . $query_arg . '" value="' . $value . '">';
424
+				<input type="hidden" name="' . $query_arg.'" value="'.$value.'">';
425 425
             }
426 426
             return $html;
427 427
         }
@@ -436,8 +436,8 @@  discard block
 block discarded – undo
436 436
                 __FILE__, __FUNCTION__, __LINE__);
437 437
         }
438 438
         $extra_params = self::$_in_iframe ? ' target="_blank"' : '';
439
-        $html = '<form method="POST" action="' . $checkout_url . '"' . $extra_params . '>';
440
-        $html .= wp_nonce_field('process_ticket_selections', 'process_ticket_selections_nonce_' . $ID, true, false);
439
+        $html = '<form method="POST" action="'.$checkout_url.'"'.$extra_params.'>';
440
+        $html .= wp_nonce_field('process_ticket_selections', 'process_ticket_selections_nonce_'.$ID, true, false);
441 441
         $html .= '<input type="hidden" name="ee" value="process_ticket_selections">';
442 442
         $html = apply_filters('FHEE__EE_Ticket_Selector__ticket_selector_form_open__html', $html, self::$_event);
443 443
         return $html;
@@ -462,10 +462,10 @@  discard block
 block discarded – undo
462 462
                 $html .= empty($external_url) ?
463 463
                     \EED_Ticket_Selector::no_tkt_slctr_end_dv()
464 464
                     : \EED_Ticket_Selector::clear_tkt_slctr();
465
-                $html .= '<br/>' . \EED_Ticket_Selector::ticket_selector_form_close();
466
-            } else if ( EED_Ticket_Selector::$_max_atndz === 1 ) {
465
+                $html .= '<br/>'.\EED_Ticket_Selector::ticket_selector_form_close();
466
+            } else if (EED_Ticket_Selector::$_max_atndz === 1) {
467 467
                 // its a "Dude Where's my Ticket Selector?" (DWMTS) type event (ie: $_max_atndz === 1)
468
-                if ( EED_Ticket_Selector::$_event->is_sold_out() ) {
468
+                if (EED_Ticket_Selector::$_event->is_sold_out()) {
469 469
                     // then instead of a View Details or Submit button, just display a "Sold Out" message
470 470
                     $html .= apply_filters(
471 471
                         'FHEE__EE_Ticket_Selector__display_ticket_selector_submit__sold_out_msg',
@@ -586,10 +586,10 @@  discard block
 block discarded – undo
586 586
             EED_Ticket_Selector::$_event
587 587
         );
588 588
         $external_url = EED_Ticket_Selector::$_event->external_url();
589
-        $html = '<input id="ticket-selector-submit-' . EED_Ticket_Selector::$_event->ID() . '-btn"';
589
+        $html = '<input id="ticket-selector-submit-'.EED_Ticket_Selector::$_event->ID().'-btn"';
590 590
         $html .= ' class="ticket-selector-submit-btn ';
591 591
         $html .= empty($external_url) ? 'ticket-selector-submit-ajax"' : '"';
592
-        $html .= ' type="submit" value="' . $btn_text . '" />';
592
+        $html .= ' type="submit" value="'.$btn_text.'" />';
593 593
         $html .= apply_filters(
594 594
             'FHEE__EE_Ticket_Selector__after_ticket_selector_submit',
595 595
             '',
@@ -672,7 +672,7 @@  discard block
 block discarded – undo
672 672
             );
673 673
         } else {
674 674
             wp_safe_redirect(
675
-                site_url('/' . EE_Registry::instance()->CFG->core->event_cpt_slug . '/')
675
+                site_url('/'.EE_Registry::instance()->CFG->core->event_cpt_slug.'/')
676 676
             );
677 677
         }
678 678
         die();
@@ -783,7 +783,7 @@  discard block
 block discarded – undo
783 783
                 'The registration limit for this event is %s tickets per registration, therefore the total number of tickets you may purchase at a time can not exceed %s.',
784 784
                 $valid['max_atndz'], 'event_espresso');
785 785
             $limit_error_2 = sprintf($max_atndz_string, $valid['max_atndz'], $valid['max_atndz']);
786
-            EE_Error::add_error($limit_error_1 . '<br/>' . $limit_error_2, __FILE__, __FUNCTION__, __LINE__);
786
+            EE_Error::add_error($limit_error_1.'<br/>'.$limit_error_2, __FILE__, __FUNCTION__, __LINE__);
787 787
         } else {
788 788
             // all data appears to be valid
789 789
             $tckts_slctd = false;
@@ -903,7 +903,7 @@  discard block
 block discarded – undo
903 903
         // grab valid id
904 904
         $valid_data['id'] = $id;
905 905
         // grab and sanitize return-url
906
-        $valid_data['return_url'] = esc_url_raw(EE_Registry::instance()->REQ->get('tkt-slctr-return-url-' . $id));
906
+        $valid_data['return_url'] = esc_url_raw(EE_Registry::instance()->REQ->get('tkt-slctr-return-url-'.$id));
907 907
         // array of other form names
908 908
         $inputs_to_clean = array(
909 909
             'event_id'   => 'tkt-slctr-event-id',
@@ -918,9 +918,9 @@  discard block
 block discarded – undo
918 918
         // cycle through $inputs_to_clean array
919 919
         foreach ($inputs_to_clean as $what => $input_to_clean) {
920 920
             // check for POST data
921
-            if (EE_Registry::instance()->REQ->is_set($input_to_clean . $id)) {
921
+            if (EE_Registry::instance()->REQ->is_set($input_to_clean.$id)) {
922 922
                 // grab value
923
-                $input_value = EE_Registry::instance()->REQ->get($input_to_clean . $id);
923
+                $input_value = EE_Registry::instance()->REQ->get($input_to_clean.$id);
924 924
                 switch ($what) {
925 925
                     // integers
926 926
                     case 'event_id':
@@ -941,8 +941,8 @@  discard block
 block discarded – undo
941 941
                         // if qty is coming from a radio button input, then we need to assemble an array of rows
942 942
                         if ( ! is_array($row_qty)) {
943 943
                             // get number of rows
944
-                            $rows = EE_Registry::instance()->REQ->is_set('tkt-slctr-rows-' . $id)
945
-                                ? absint(EE_Registry::instance()->REQ->get('tkt-slctr-rows-' . $id))
944
+                            $rows = EE_Registry::instance()->REQ->is_set('tkt-slctr-rows-'.$id)
945
+                                ? absint(EE_Registry::instance()->REQ->get('tkt-slctr-rows-'.$id))
946 946
                                 : 1;
947 947
                             // explode ints by the dash
948 948
                             $row_qty = explode('-', $row_qty);
@@ -970,7 +970,7 @@  discard block
 block discarded – undo
970 970
                     case 'ticket_id':
971 971
                         $value_array = array();
972 972
                         // cycle thru values
973
-                        foreach ((array)$input_value as $key => $value) {
973
+                        foreach ((array) $input_value as $key => $value) {
974 974
                             // allow only numbers, letters,  spaces, commas and dashes
975 975
                             $value_array[$key] = wp_strip_all_tags($value);
976 976
                             // get ticket via the ticket id we put in the form
@@ -1111,7 +1111,7 @@  discard block
 block discarded – undo
1111 1111
         $available_spaces = $ticket->qty() - $ticket->sold();
1112 1112
         if (isset(self::$_available_spaces['tickets'][$ticket->ID()])) {
1113 1113
             // loop thru tickets, which will ALSO include individual ticket records AND a total
1114
-            foreach ((array)self::$_available_spaces['tickets'][$ticket->ID()] as $DTD_ID => $spaces) {
1114
+            foreach ((array) self::$_available_spaces['tickets'][$ticket->ID()] as $DTD_ID => $spaces) {
1115 1115
                 // if we want the original datetime availability BEFORE we started subtracting tickets ?
1116 1116
                 if ($get_original_ticket_spaces) {
1117 1117
                     // then grab the available spaces from the "tickets" array and compare with the above to get the lowest number
@@ -1186,7 +1186,7 @@  discard block
 block discarded – undo
1186 1186
     {
1187 1187
         if (isset(self::$_available_spaces['tickets'][$ticket->ID()])) {
1188 1188
             // loop thru tickets, which will ALSO include individual ticket records AND a total
1189
-            foreach ((array)self::$_available_spaces['tickets'][$ticket->ID()] as $DTD_ID => $spaces) {
1189
+            foreach ((array) self::$_available_spaces['tickets'][$ticket->ID()] as $DTD_ID => $spaces) {
1190 1190
                 // subtract the qty of selected tickets from each datetime's available spaces this ticket has access to,
1191 1191
                 self::$_available_spaces['datetimes'][$DTD_ID] -= $qty;
1192 1192
             }
@@ -1205,7 +1205,7 @@  discard block
 block discarded – undo
1205 1205
     {
1206 1206
         // add some style
1207 1207
         if (apply_filters('FHEE__EED_Ticket_Selector__load_tckt_slctr_assets', false)) {
1208
-            wp_register_style('ticket_selector', TICKET_SELECTOR_ASSETS_URL . 'ticket_selector.css');
1208
+            wp_register_style('ticket_selector', TICKET_SELECTOR_ASSETS_URL.'ticket_selector.css');
1209 1209
             wp_enqueue_style('ticket_selector');
1210 1210
             // make it dance
1211 1211
             // wp_register_script('ticket_selector', TICKET_SELECTOR_ASSETS_URL . 'ticket_selector.js', array('espresso_core'), '', TRUE);
@@ -1221,7 +1221,7 @@  discard block
 block discarded – undo
1221 1221
         if (EE_Registry::instance()->REQ->get('page') === 'espresso_events'
1222 1222
             && EE_Registry::instance()->REQ->get('action') === 'edit'
1223 1223
         ) {
1224
-            wp_register_script('ticket_selector_embed', TICKET_SELECTOR_ASSETS_URL . 'ticket-selector-embed.js',
1224
+            wp_register_script('ticket_selector_embed', TICKET_SELECTOR_ASSETS_URL.'ticket-selector-embed.js',
1225 1225
                 array('ee-dialog'), EVENT_ESPRESSO_VERSION, true);
1226 1226
             wp_enqueue_script('ticket_selector_embed');
1227 1227
         }
Please login to merge, or discard this patch.